Skip to content
This repository has been archived by the owner on Nov 6, 2024. It is now read-only.

Commit

Permalink
Add card image tag and horizontal card (#333)
Browse files Browse the repository at this point in the history
* Add card image tag
* Add FAB to image card
  • Loading branch information
scote authored Aug 9, 2018
1 parent d51a6f2 commit 610f2e0
Show file tree
Hide file tree
Showing 13 changed files with 319 additions and 14 deletions.
89 changes: 89 additions & 0 deletions demo/src/app/card/card.component.html
Original file line number Diff line number Diff line change
Expand Up @@ -94,14 +94,103 @@ <h5 class="light">Colors and hoverable</h5>
</p>
</div>

<h5 class="light">Image card</h5>

<div class="row">

<div class="col s12 m8 l6">
<mz-card>
<mz-card-image>
<img src="assets/card-1.jpg" />
</mz-card-image>
<mz-card-image-title>Card Title</mz-card-image-title>

<mz-card-content>
I am a very simple card. I am good at containing small bits of information. I am convenient because I require little markup to use effectively.
</mz-card-content>

<mz-card-action>
<a href="javascript:void(0)">This is a link</a>
<a href="javascript:void(0)">This is a link</a>
</mz-card-action>
</mz-card>
</div>

<p class="col s12 m4 l6">
Image card combining title, content and actions.
</p>
</div>

<h5 class="light">Horizontal Image card</h5>

<div class="row">

<div class="col s12 m8 l6">
<mz-card [horizontal]="true">
<mz-card-image>
<img src="assets/card-1.jpg" />
</mz-card-image>

<mz-card-content>
I am a very simple card. I am good at containing small bits of information. I am convenient because I require little markup to use effectively.
</mz-card-content>

<mz-card-action>
<a href="javascript:void(0)">This is a link</a>
<a href="javascript:void(0)">This is a link</a>
</mz-card-action>
</mz-card>
</div>

<p class="col s12 m4 l6">
Horizontal image card combining content and actions.
</p>
</div>

<h5 class="light">Image card with FAB</h5>

<div class="row">

<div class="col s12 m8 l6">
<mz-card>
<mz-card-image>
<img src="assets/card-1.jpg" />
<button mz-button mz-halfway-fab [float]="true"><i mz-icon [icon]="'add'"></i></button>
</mz-card-image>
<mz-card-image-title>Card Title</mz-card-image-title>

<mz-card-content>
I am a very simple card. I am good at containing small bits of information. I am convenient because I require little markup to use effectively.
</mz-card-content>

<mz-card-action>
<a href="javascript:void(0)">This is a link</a>
<a href="javascript:void(0)">This is a link</a>
</mz-card-action>
</mz-card>
</div>

<p class="col s12 m4 l6">
Add <code class="language-markup">mz-halfway-fab</code> directive to button for floating action button.
</p>
</div>

<div class="section">

<h5 class="light">HTML Structure</h5>

<app-code-snippet>
&lt;mz-card
class="blue-grey darken-1 white-text"
[horizontal]="true"
[hoverable]="true">
&lt;mz-card-image>
&lt;img src="assets/card-1.jpg" />
&lt;button mz-button mz-halfway-fab [float]="true">&lt;i mz-icon [icon]="'add'">&lt;/i>&lt;/button>
&lt;/mz-card-image>
&lt;mz-card-image-tilte>
Card Image Title
&lt;/mz-card-image-tiltle>
&lt;mz-card-title>
Card Title
&lt;/mz-card-title>
Expand Down
10 changes: 9 additions & 1 deletion demo/src/app/card/card.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,15 @@ import { IPropertyRow } from '../shared/properties-table/properties-table.compon
})
export class CardComponent {
properties: IPropertyRow[] = [
{ name: 'hoverable',
{
name: 'horizontal',
mandatory: false,
type: 'boolean',
description: `Change the card image to horizontal`,
defaultValue: `false`,
},
{
name: 'hoverable',
mandatory: false,
type: 'boolean',
description: `Box-shadow css animnation on card rollover`,
Expand Down
4 changes: 3 additions & 1 deletion demo/src/app/card/card.module.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { CommonModule } from '@angular/common';
import { NgModule } from '@angular/core';
import { RouterModule } from '@angular/router';
import { MzCardModule } from 'ngx-materialize';
import { MzButtonModule, MzCardModule, MzIconModule } from 'ngx-materialize';

import { CodeSnippetModule } from '../shared/code-snippet/code-snippet.module';
import { PropertiesTableModule } from '../shared/properties-table/properties-table.module';
Expand All @@ -12,7 +12,9 @@ import { ROUTES } from './card.routing';
imports: [
CodeSnippetModule,
CommonModule,
MzButtonModule,
MzCardModule,
MzIconModule,
PropertiesTableModule,
RouterModule.forChild(ROUTES),
],
Expand Down
Binary file added demo/src/assets/card-1.jpg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
24 changes: 16 additions & 8 deletions lib/src/card/card.component.html
Original file line number Diff line number Diff line change
@@ -1,12 +1,20 @@
<div class="card-content">

<div #cardTitle class="card-title" *ngIf="hasCardTitle">
<ng-content select="mz-card-title"></ng-content>
<div #cardImage class="card-image" *ngIf="hasCardImage">
<ng-content select="mz-card-image"></ng-content>
<div class="card-title" *ngIf="hasCardImageTitle">
<ng-content select="mz-card-image-title"></ng-content>
</div>

<ng-content select="mz-card-content"></ng-content>
</div>

<div #cardAction class="card-action" *ngIf="hasCardAction">
<ng-content select="mz-card-action"></ng-content>
<div [class.card-stacked]="horizontal">
<div class="card-content">
<div #cardTitle class="card-title" *ngIf="hasCardTitle">
<ng-content select="mz-card-title"></ng-content>
</div>

<ng-content select="mz-card-content"></ng-content>
</div>

<div #cardAction class="card-action" *ngIf="hasCardAction">
<ng-content select="mz-card-action"></ng-content>
</div>
</div>
24 changes: 22 additions & 2 deletions lib/src/card/card.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,16 @@ import {
})
export class MzCardComponent implements AfterViewInit {
@HostBinding('class.card') true;
@HostBinding('class.horizontal') @Input() horizontal: boolean;
@HostBinding('class.hoverable') @Input() hoverable: boolean;

@ViewChild('cardTitle') cardTitle: ElementRef;
@ViewChild('cardAction') cardAction: ElementRef;
@ViewChild('cardImage') cardImage: ElementRef;
@ViewChild('cardTitle') cardTitle: ElementRef;

hasCardAction = true;
hasCardImage = true;
hasCardImageTitle = true;
hasCardTitle = true;

constructor(
Expand All @@ -31,6 +35,8 @@ export class MzCardComponent implements AfterViewInit {
ngAfterViewInit() {
this.hasCardTitle = this.hasTitleTagAndNotEmpty();
this.hasCardAction = this.hasActionTagAndNotEmpty();
this.hasCardImage = this.hasImageTagAndNotEmpty();
this.hasCardImageTitle = this.hasImageTitleTagAndNotEmpty();
this.changeDetectorRef.detectChanges();
}

Expand All @@ -39,8 +45,18 @@ export class MzCardComponent implements AfterViewInit {
return this.isElementDisplayed(cardActionElement);
}

private hasImageTagAndNotEmpty(): boolean {
const cardImagelement = this.cardImage.nativeElement.querySelector('mz-card-image');
return this.isElementDisplayed(cardImagelement);
}

private hasImageTitleTagAndNotEmpty(): boolean {
const cardImageTitleElement = this.cardImage.nativeElement.querySelector('mz-card-image-title');
return this.isElementDisplayed(cardImageTitleElement);
}

private hasTitleTagAndNotEmpty(): boolean {
const cardTitleElement = this.cardTitle.nativeElement.querySelector('mz-card-title');
const cardTitleElement = this.cardTitle ? this.cardTitle.nativeElement.querySelector('mz-card-title') : null;
return this.isElementDisplayed(cardTitleElement);
}

Expand All @@ -52,6 +68,10 @@ export class MzCardComponent implements AfterViewInit {
// Declare the tags to avoid error: '<mz-card-x>' is not a known element
// https://github.com/angular/angular/issues/11251
// tslint:disable: directive-selector

@Directive({ selector: 'mz-card-image' }) export class MzCardImageDirective { }
@Directive({ selector: 'mz-card-image-title' }) export class MzCardImageTitleDirective { }
@Directive({ selector: 'mz-card-title' }) export class MzCardTitleDirective { }
@Directive({ selector: 'mz-card-content' }) export class MzCardContentDirective { }
@Directive({ selector: 'mz-card-action' }) export class MzCardActionDirective { }

95 changes: 95 additions & 0 deletions lib/src/card/card.component.view.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,19 @@ describe('MzCardComponent:view', () => {
});
}));

it('should set horizontal css class when horizontal is true', async(() => {

buildComponent<MzCardComponent>(`
<mz-card [horizontal]="true"></mz-card>
`).then((fixture) => {

nativeElement = fixture.nativeElement;
fixture.autoDetectChanges();

expect(card().classList).toContain('horizontal');
});
}));

it('should set hoverable css class when hoverable is true', async(() => {

buildComponent<MzCardComponent>(`
Expand Down Expand Up @@ -87,6 +100,88 @@ describe('MzCardComponent:view', () => {
}));
});

describe('card-image', () => {
let nativeElement: any;

function cardImage(): HTMLElement {
return nativeElement.querySelector('.card-image');
}

it('should transclude mz-card', async(() => {

buildComponent<MzCardComponent>(`
<mz-card>
<mz-card-image>
image-x
</mz-card-image>
</mz-card>`).then((fixture) => {

nativeElement = fixture.nativeElement;
fixture.autoDetectChanges();

expect(cardImage().innerText.trim()).toBe('image-x');
});
}));

it('should not display when mz-card-image tag is not present', async(() => {

buildComponent<MzCardComponent>(`
<mz-card>
<mz-card-content>
content-x
</mz-card-content>
</mz-card>
`).then((fixture) => {

nativeElement = fixture.nativeElement;
fixture.autoDetectChanges();

expect(cardImage()).toBeFalsy();
});
}));

describe('card-image-title', () => {

function cardImageTitle(): HTMLElement {
return nativeElement.querySelector('.card-image .card-title');
}

it('should transclude mz-card-image-title', async(() => {

buildComponent<MzCardComponent>(`
<mz-card>
<mz-card-image>
image-x
</mz-card-image>
<mz-card-image-title>image-title-x</mz-card-image-title>
</mz-card>`).then((fixture) => {

nativeElement = fixture.nativeElement;
fixture.autoDetectChanges();

expect(cardImageTitle().innerText.trim()).toBe('image-title-x');
});
}));

it('should not display when mz-card-image-title tag is not present', async(() => {

buildComponent<MzCardComponent>(`
<mz-card>
<mz-card-image>
image-x
</mz-card-image>
</mz-card>
`).then((fixture) => {

nativeElement = fixture.nativeElement;
fixture.autoDetectChanges();

expect(cardImageTitle()).toBeFalsy();
});
}));
});
});

describe('card-title', () => {

let nativeElement: any;
Expand Down
19 changes: 17 additions & 2 deletions lib/src/card/card.module.ts
Original file line number Diff line number Diff line change
@@ -1,20 +1,35 @@
import { CommonModule } from '@angular/common';
import { NgModule } from '@angular/core';

import { MzCardActionDirective, MzCardComponent, MzCardContentDirective, MzCardTitleDirective } from './card.component';
import {
MzCardActionDirective,
MzCardComponent,
MzCardContentDirective,
MzCardImageDirective,
MzCardImageTitleDirective,
MzCardTitleDirective,
} from './card.component';
import { MzHalfwayFabModule } from './halfway-fab/halfway-fab.module';

@NgModule({
imports: [CommonModule],
imports: [
CommonModule,
MzHalfwayFabModule,
],
declarations: [
MzCardActionDirective,
MzCardComponent,
MzCardContentDirective,
MzCardImageDirective,
MzCardImageTitleDirective,
MzCardTitleDirective,
],
exports: [
MzCardActionDirective,
MzCardComponent,
MzCardContentDirective,
MzCardImageDirective,
MzCardImageTitleDirective,
MzCardTitleDirective,
],
})
Expand Down
12 changes: 12 additions & 0 deletions lib/src/card/halfway-fab/halfway-fab.directive.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import { Directive, HostBinding } from '@angular/core';

@Directive({
selector: `
a[mz-halfway-fab],
a[mzHalfwayFab],
button[mz-halfway-fab],
button[mzHalfwayFab]`,
})
export class MzHalfwayFabDirective {
@HostBinding('class.halfway-fab') true;
}
Loading

0 comments on commit 610f2e0

Please sign in to comment.