指令可以理解为没有模版的组件,它需要一个宿主元素,如果使用方括号 [] 指定 Selector,该指令就变成一个属性型指令,angular除了属性型指令,还有结构型指令如ngIf等,,本文暂时先实现一个属性型指令。
import { Directive, HostBinding } from '@angular/core';
@Directive({
selector: '[appGridItem]'
})
export class GridItemDirective {
@HostBinding('style.display') display = 'grid';
@HostBinding('style.grid-template-areas') template = `'image' 'title'`;
@HostBinding('style.place-items') align = 'center';
@HostBinding('style.width') width = '4rem';
}
import {
Directive,
OnInit,
Input,
ElementRef,
Renderer2,
HostListener
} from '@angular/core';
@Directive({
selector: '[appGridItemImage]'
})
export class GridItemImageDirective implements OnInit {
@Input() appGridItemImage = '2rem';
constructor(private elr: ElementRef, private renderer: Renderer2) {}
ngOnInit(): void {
this.setStyle('grid-area', 'image');
this.setStyle('width', this.appGridItemImage);
this.setStyle('height', this.appGridItemImage);
this.setStyle('object-fit', 'cover');
}
private setStyle(styleName: string, styleValue: string | number) {
this.renderer.setStyle(this.elr.nativeElement, styleName, styleValue);
}
@HostListener('click', ['$event.target'])
handleClick(ev) {
console.log(ev);
}
}
import { Directive, Input, HostBinding } from '@angular/core';
@Directive({
selector: '[appGridItemTitle]'
})
export class GridItemTitleDirective {
@HostBinding('style.font-size') @Input() appGridItemTitle = '0.5rem';
@HostBinding('style.grid-area') area = 'title';
@HostBinding('style.white-space') wrap = 'nowrap';
}
// test.component.html 指令的使用
<div appGridItem *ngFor="let item of items">
<img appGridItemImage="'4rem'" src="item.imgUrl" alt="">
<span appGridItemTitle="'2rem'">{{item.title}}</span>
</div>