Angular(2+):在子组件中修改输入参数

时间:2019-01-16 13:20:19

标签: angular

在子组件中更改输入参数是否正常,还是应该将所有输入对象都视为只读对象,然后将任何更改发回给父组件并将其委托给父组件?修改输入参数是否会引起任何问题。

class ChildComponent {

  @Input() parentParam;
  @Output() clickValEvent = new EventEmitter<boolean>();

  let parentParamClone = Object.assign({}, parentParam);

  childClickEvent(val) {
    //Update value locally.
    // parentParam.clickVal = val;

    //Inform parent & let it do necessary change.
    // this.clickValEvent.emit(val);

    //Only play with local clone.
    // parentParamClone.clickVal = val;
    }
}

2 个答案:

答案 0 :(得分:0)

  1. 以只读方式传递您的@Input是我最常看到的, 这样,父母的财产就保持不变。

  2. 如果@Input的副本对您有用,则表示您 想要仅在孩子的组件内部以及所有 更改不会影响父级。

  3. 在必须更改对象并将其保留在父组件中时使用输出是一种方法(对我来说,这是更好的选择),但是我习惯于使用两种方式绑定而不是使用回调。 / p>

在您的示例中,如果您想要一个@input属性,以便在子组件中更改其值并改变其父亲属性,则应考虑两种方式绑定BANANA IN A BOX,因此代码应看起来像像这样:

class ChildComponent {

  @Input() parentParam;
  @Output() parentParamChange = new EventEmitter<boolean>(); // <- this EventEmitter must have the parentParam type.

  let parentParamClone = Object.assign({}, parentParam);

  childClickEvent(val) {
    //Inform parent & let it do necessary change, when you
    // update the parent's value, it will be reflected in this component.
     this.parentParamChange.emit(val);
}

您应该在html模板中使用这种方式:

...
[(parentParam)]="propertyYouArePassingHere"
...

代替

...
    [parentParam]="propertyYouArePassingHere"
    (clickValEvent)="captureOutputCallback()" 
 ...

注意:要使其正常工作,您必须具有遵循以下模式的输出名称: inputThatYouWantMakeTwoWayBindName + Change,这就是我将输出重命名为parentParamChange的原因。

答案 1 :(得分:0)

没错,是的,您可以修改子组件中的 @input 值,它会反映在您的父组件中。但是,您应该避免这种情况的原因有两个:

  1. 它不适用于原始值,如果您希望更改 @input 原始值并反映在您的父组件中,这将不起作用。

  2. 这不是一个好的做法,它为所有子组件提供了任意更新 @input 对象的机会,并使我们难以追踪值的变化。因此,使用 @output 为我们在未来维护代码方面节省了大量精力,因为它更具声明性。

我觉得很奇怪,我无法从 Angular 文档中找到对此的任何官方解释。与 ReactJsVueJs 不同,它们非常不鼓励我们改变子组件中的 props