angular国际化 / rxjs使用技巧

angular国际化 / rxjs使用技巧

设置 base href

ng build --base-href "/" --prod

async管道的用法

<ng-container *ngIf="num|async;let add;">
  <h1>{{add}}</h1>
</ng-container>

num=of(1)

排除主题文件

angular.json

<>
"styles": [
    "src/styles.css",
    {
      "input": "src/styles/themes/theme-light.css",
      "inject": false,
      "bundleName": "theme-light"
    },
    {
      "input": "src/styles/themes/theme-dark.css",
      "inject": false,
      "bundleName": "theme-dark"
    }
  ]
  1. inject: 设置此 false 将不包括来自“输入”路径的文件包
  2. bundleName:将创建一个单独的包,其中包含来自“输入”路径的样式表

可以通过简单地inject在工作区配置文件中设置false来排除样式表,即angular.json. 为了按需加载它们,我们将使用该bundleName选项

angular 表单拿不到禁用的值

getRawValue()

ng-content 插槽

命名插槽类似于属性的形式映射, 使用<ng-template> 或者div

父
<app-three>
  <ng-container *ngTemplateOutlet="aaa" attr1></ng-container>
</app-three>
<!--这种写的方式是为了不让当前组件看起来那么不简化-->
<ng-template #aaa >
  <p>This is another element to project into component</p>
</ng-template>

子
<ng-content select="[attr1]"></ng-content>

如果你想要用ng-container, 我们发现可以一次性编写多个

父
<ng-container ngProjectAs="complex-ele">
  <h1>    我是判断的插槽</h1>
</ng-container>
子
<ng-content select="['complex-ele','complex-ele1']"></ng-content>

我突然发现竟然不写在父组件类也能投影出来

angular 国际化

安装

npm install @ngx-translate/core @ngx-translate/http-loader

app.module.ts

export function createTranslateLoader(http: HttpClient) {
  return new TranslateHttpLoader(http, './assets/i18n/', '.json');
}

@NgModule({
  declarations: [
    AppComponent
  ],
  imports: [
    BrowserModule,
    AppRoutingModule,
    TranslateModule.forRoot({
      loader: {
        provide: TranslateLoader,
        useFactory: (createTranslateLoader),
        deps: [HttpClient],
      },
      defaultLanguage: 'en-US',
    }),
    FormsModule,
    HttpClientModule,
    BrowserAnimationsModule
  ],
  providers: [{provide: NZ_I18N, useValue: zh_CN}],
  bootstrap: [AppComponent]
})

/assets/i18n/ 里面新建en-US.jsonzh-CN.json

{
  "hello": "Hello, {{name}}!"
}

{
  "hello": "你好 {{name}}!"
}

组件里面使用

export class TwoComponent implements OnInit {
  constructor(public translateService: TranslateService) {
  }
  public changeLanguage(language: string): void {
    console.log(language);
    this.translateService.use(language);
  }
  ngOnInit(): void {
  }

}

html

<h3>{{ "hello" | translate: { name: "Angular" } }}</h3>
<button nz-button nzType="default" (click)="changeLanguage('zh-CN')">CLick</button>

rxjs EMPTY

EMPTY立即发出complete并且不发出任何值。

import { EMPTY } from 'rxjs';

EMPTY.subscribe({
  next: () => console.log('Next'),
  complete: () => console.log('Complete!')
});
// Complete!

当我们在过程中遇到错误, 我们不希望内部逻辑subscribe 发生,我们可以使用EMPTY 在错误发生后立即完成

 throwError('error1').pipe(
      catchError(err=>{
        console.log('报错1');
        return EMPTY
      })
    ).subscribe(res=>{
      console.log('执行吗');
    })
// 报错1
// 这样我们的EMPTY会让subscribe不执行

rxjs defer

创建 Observable,即只有在它被订阅时才创建。

假设我们希望在每个新订阅中都有一个随机数。有了defer它才有可能

 const s1 = defer(() =>of(Math.floor(Math.random()*100)));
    s1.subscribe(console.log);
    s1.subscribe(console.log);

为了比较,如果我们改为使用of,我们每次都会得到相同的数字

 const s= of(Math.floor(Math.random()*100));
    s.subscribe(console.log);
   s.subscribe(console.log);

rxjs defaultIfEmpty

如果源 Observable 结果为空,则此运算符将发出默认值。

当我们的 Observable 只发出 complete 时,在此之前没有发出任何值, defaultIfEmpty 将发出插入到它的值。

 let result = of().pipe(defaultIfEmpty<any>('默认的值'));
    result.subscribe(x => console.log(x));

我们可以思考,如果请求的时候返回都是空的情况, 我们可以设置默认值

rxjs generate

通过运行一个状态驱动的循环来生成一个 Observable,该循环在每次迭代时发出一个元素

generate(
  2,
  x => x <= 20,
  x => x + 3,
  x => '#'.repeat(x)
).subscribe(console.log);

/**
##
#####
########
###########
##############
#################
####################
*/

generate就像一个for循环

  • 2 设置的值
  • x<=20 循环的条件
  • x+3 每次循环增加的参数
  • '#'.repeat(x) 最后一个就是你从循环中返回的值

pluck

将每个源值映射到其指定的嵌套属性。

    of({ firstName: 'Cloe', lastName: 'Liz' }).pipe(pluck('firstName')).subscribe(console.log)
    // Cloe

简而言之,这就像使用map将值映射到其成员之一,但节省了编写它的样板。

pipe(map(v => v.firstName))
// 一样的效果
上一篇:cc 使用yarn


下一篇:RxJS+WebPack+TS实现组件间的松耦合