ng-zorro UI源码技巧

Posted 房东家的猫

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了ng-zorro UI源码技巧相关的知识,希望对你有一定的参考价值。

在Angular 中转译

转移: 将代码从一种高级语言转换为另一种高级语言。

编译:将代码从高级语言转换为机器级语言

每个 Angular 项目都有一个名为tsconfig.json的文件,其中包含将 .js 文件转换为 .ts 文件的设置。

tsconfig.json官网地址

JIT和AOT编译的区别

  • JIT 编译是在应用程序运行时完成的,而 AOT 编译是在构建过程中完成的。

angular-cdk-dir

模块注入

import BidiModule from \'@angular/cdk/bidi\';

  imports: [ BidiModule, ]

文本方向

<p [dir]="dir">
  可以动态切换方向
</p>
// \'ltr\'(左到右)| \'rtl\' (右到左)
  dir = "rtl";
类似 text-align="left|right"   只是几个自带的盒子都会变成这样

可以把整个组件都添加这个效果

监听

<app-report2  [dir]="dir"></app-report2>
  dir: Direction = \'rtl\';

 constructor(
     private directionality: Directionality
  ) 

  ngOnInit(): void 
    this.directionality.change?.subscribe((direction: Direction) => 
      console.log(direction,\'被改变了111\');
    );
  

@Component

封装策略

@Component(
    encapsulation: ViewEncapsulation.Emulated  默认
)
  • ViewEncapsulation.Emulated:应用修改后的组件样式以模拟原生 Shadow DOM CSS 封装行为。
  • ViewEncapsulation.None:在没有任何封装的情况下全局应用组件样式。
  • ViewEncapsulation.ShadowDom: 使用浏览器原生的 Shadow DOM API 来封装样式。

如果我们想受到上级的影响可以使用ViewEncapsulation.None

@Input 父传子进行过滤筛选

<app-report2 [bool]="1" ></app-report2>
  @Input()
  @InputBoolean()
  bool:any = false;

InputBoolean 工具库, 我们如果写给别人用的组件, 不可能别人给了一个不符合我们规定的属性,我们就给他报错, 如果给的是其他类型, 我们可以把他强转到我们需要的类型,进行处理, InputBoolean 内部做了get,set 监控, 避免父级修改了, 儿子可以重新检测到


import coerceBooleanProperty from \'@angular/cdk/coercion\';

// 添加get set 当元素修改的时候重新执行
function propDecoratorFactory<T, D>(
  name: string,
  fallback: (v: T) => D
): (target: any, propName: string) => void 

  function propDecorator(
    target: any,
    propName: string,
    originalDescriptor?: TypedPropertyDescriptor<any>
  ): any 
    const privatePropName = `$$__zorroPropDecorator__$propName`;
    console.log(target);

    Object.defineProperty(target, privatePropName, 
      configurable: true,
      writable: true
    );

    return 
      get(): string 
        return originalDescriptor && originalDescriptor.get
          ? originalDescriptor.get.bind(this)()
          : this[privatePropName];
      ,
      set(value: T): void 
        if (originalDescriptor && originalDescriptor.set) 
          originalDescriptor.set.bind(this)(fallback(value));
        
        this[privatePropName] = fallback(value);
      
    ;
  

  return propDecorator;

// 我们可以自己写自定义的
export function InputBoolean(): any 
  return propDecoratorFactory(\'InputBoolean\', toBoolean);

// 我们可以自己写自定义的
export function toBoolean(value: boolean | string): boolean 
  return coerceBooleanProperty(value);

host 技巧

组件的最外层添加class或者属性

@Component(
  selector: \'app-report2\',
  templateUrl: \'./report2.component.html\',
  styleUrls: [\'./report2.component.scss\'],
  host:
    class:\'ant-xxx\',
    \'[class.aaa]\':`bool`,
    \'[class.bbb]\':`bool==true`,
  
)

bool 是下面组件使用的一个变量

tabindex

div添加获取焦点失去焦点属性

<div  tabindex="-1" (blur)="changeBlur()">kkkkkkkk</div>

startWith

  b = new Subject<string>();
  this.b.pipe(
      startWith(\'xxx\')
    ).subscribe(console.log)

这样我们就不一样要使用BehaviorSubject

exportAs 别名的使用

@Component(
  selector: \'button[nz-button], a[nz-button]\',
  exportAs: \'nzButton\',
)

使用

<button nz-button nzType="primary" #aaa=\'nzButton\'>Primary Button</button>
  @ViewChild(\'aaa\') aaa!: NzButtonComponent;
  ngAfterViewInit() 
    console.log(this.aaa); // NzButtonComponent
    	

我们在angular.js可能用的比较多

<input type="text" [(ngModel)]="str" #strA="ngModel">

  @ViewChild(\'strA\') strA!: NgModel;
  ngAfterViewInit() 
    if(this.strA)
        this.strA.control.valueChanges// 检测变化
    
    

stopPropagation与stopImmediatePropagation的区别

event.stopPropagation();阻止事件冒泡

event.stopImmediatePropagation(); 阻止事件冒泡并且阻止该元素上同事件类型的监听器被触发。

 可以同时用这两个, 用在按钮上
 event.preventDefault();
 event.stopImmediatePropagation();

默认我们阻止默认行为和停止事件传播, 所以不需要Angular运行变更检测

当我们点击按钮的时候,如果是禁用的是a链接或者loading开启的时候,就类似禁止点击

ngOnInit(): void 
 this.ngZone.runOutsideAngular(() => 
      fromEvent<MouseEvent>(this.elementRef.nativeElement, \'click\',  capture: true )
        .pipe(takeUntil(this.destroy$))
        .subscribe(event => 
          if ((this.disabled && (event.target as HTMLElement)?.tagName === \'A\') || this.nzLoading) 
            event.preventDefault();
            event.stopImmediatePropagation();
          
        );
    );
  

开发环境和打包后的资源处理

我们打包后想引入那时候的本地网址的地址, 和本地环境进行区别

类似我们需要的本地自定义图标

导入模块

app.module.ts

 providers: [
    
      provide: APP_BASE_HREF,
      useFactory: (s: PlatformLocation) => s.getBaseHrefFromDOM(),
      deps: [PlatformLocation],
    ,
 ]    

app.component.ts

constructor(
    @Inject(APP_BASE_HREF) href: string
  ) 
    this.nzIconService.fetchFromIconfont(
      scriptUrl: environment.production ? href + \'/assets/线上\' : \'../assets/本地用相对路径\',
    );

自定义图标的使用

<i nz-icon [nzIconfont]="\'icon-tuichu\'"></i>

决定自己的高度的是你的态度,而不是你的才能

记得我们是终身初学者和学习者

总有一天我也能成为大佬

以上是关于ng-zorro UI源码技巧的主要内容,如果未能解决你的问题,请参考以下文章

angular4.0 安装最新版本的nodejsnpm@angular/cli的方法

angular4.0 安装最新版本的nodejsnpm@angular/cli的方法

《Angular与ng-zorro结合》

使用 ng-zorro 构建动态菜单

无法渲染某些 NG-ZORRO 图标

如何将 storybook 集成到 antd angular(NG-ZORRO)