ChatGPT解决这个技术问题 Extra ChatGPT

Angular 2:组件交互,可选输入参数

我有一个实现,其中父希望通过使用子组件中可用的 @Input 参数将某些数据传递给子组件。但是,此数据传输是可选的,父级可能会也可能不会根据要求传递它。组件中是否可以有可选的输入参数。我在下面描述了一个场景:

 <parent>
    <child [showName]="true"></child> //passing parameter
    <child></child> //not willing to passing any parameter
</parent>



//child component definition
@Component {
    selector:'app-child',
    template:`<h1>Hi Children!</h1>
          <span *ngIf="showName">Alex!</span>`
}


export class child {

    @Input showName: boolean;

    constructor() { }

}
是的,您可以有可选输入,如果输入已初始化,请检查 ngAfterViewInit 生命周期事件
谢谢@galvan,它成功了!

A
Aravind

您可以使用 ( ? ) 运算符,如下所示

import {Component,Input} from '@angular/core';
@Component({
    selector:'child',
    template:`<h1>Hi Children!</h1>
          <span *ngIf="showName">Alex!</span>`
})


export class ChildComponent {

    @Input() showName?: boolean;

    constructor() { }

}

使用子组件的父组件将是

@Component({
  selector: 'my-app',
  template: `
    <div>
      <h2>Hello {{name}}</h2>
      <child [showName]="true"></child>
      <child ></child>
    </div>
  `,
})
export class App {
  name:string;
  constructor() {
    this.name = 'Angular2'
  }
}

LIVE DEMO


这应该是答案。也适用于默认值 @Input() showName?: boolean = true;
我想知道,与常规 @Input() showName: boolean; 有什么区别吗?然后检查是否不为空?我的意思是-有什么区别?
@RoyiNamir 最重要的是,我想说,它是一种文档形式。通过放置 ?您是否可以沟通您的组件是否可以处理未定义的输入。另外,我认为它可以被 strictNullChecks 编译器选项 christianliebel.com/2017/05/…
@MatthiasTylkowski 如果您设置了默认值,那么将其设为可选是没有意义的,因为它总是会被设置为某个值。
@MatthiasTylkowski 可选意味着 showName 属性可能不存在,但默认情况下将其设置为 true 意味着它将始终存在,因此将其设为可选没有意义。 (此处的 null 无关紧要,设置为 null 的属性仍然存在。可选仅与已定义或未定义有关。)-此处的可选不是指是否必须传入输入(默认情况下输入是可选的),而是是否属性 showName 必须存在于类中。
A
Arnaud P

默认情况下,输入值是可选的。仅当您的代码尝试访问未实际传递的输入的属性时(因为这些输入是 undefined),您的代码才会失败。

您可以实现 OnChanges 或将输入设为 setter 而不是属性,以便在实际传递值时执行您的代码。

export class child {

    @Input set showName(value: boolean) {
      this._showName = value;
      doSomethingWhenShowNameIsPassed(value);
    }

    constructor() { }
}

检查@galvan 的评论,这似乎是一个更好的解决方案。
为什么你认为它更好?当父级必须向服务器发出请求然后才将值传递给子级时,这可能是在调用 ngAfterViewInit() 之后的相当长的一段时间。 ngAfterViewInit() 可能适用于您的具体情况,但总的来说我不会推荐它。
你的意思是说,如果我在客户端动态更改值?正如你所解释的,我应该在子指令中调用 setter 方法吗?
您不需要调用 setter,但如果您有 <child [showName]="propOnParent"> 并且在某些异步调用完成后初始化了 propOnParent,则 Angular 会更新 <child> 中的 showName 输入,或者如果它是 setter,则调用具有更新值的设置器。
此外,如果您只关心问题中的 true 等静态绑定值,则 ngOnInit() 是比 ngAfterViewChecked() 更常见的生命周期挂钩。
A
Alexander Ciesielski

您在这里有两个选择。

1)您可以在孩子上使用*ngIf,以防孩子在其输入为空时不需要显示。

 <parent>
    <child *ngIf="true" [showName]="true"></child> //passing parameter
    <child></child> //not willing to passing any parameter
</parent>

2)如果孩子应该在没有任何输入的情况下显示,您可以使用修改后的设置器来检查输入变量的存在`

在 child.ts 中:

private _optionalObject: any;
@Input()
set optionalObject(optionalObject: any) {
    if(optionalObject) this._optionalObject = optionalObject;
}
get optionalObject() { return this._optionalObject; }

检查@galvan 的评论,这似乎是一个更好的解决方案。