简体   繁体   English

来自@Input 的值在 ngOnInit Angular 之后无效

[英]value from @Input invalid after ngOnInit Angular

I face with strange problem an @Input variable changed after ngInit called.我遇到了一个奇怪的问题, @Input变量在ngInit调用后发生了变化。

So, I have 3 angular component like this所以,我有 3 个像这样的角度分量

AcComponent.html组件.html

<div *ngFor="let d of this.deviceService.ObservableDevice | async;index as idx; trackBy: trackingIdenity">
    <app-ac-controller [device]="d"></app-ac-controller>
</div>

AcController.html控制器.html

<div class="col-md-8 position-relative">
     <div class="vertical-line"></div>
     <app-ac-panel [ac]="this.device.ac" [deviceId]="this.device.id"></app-ac-panel>
</div>

And AcPanel.component.ts as leaf component the problem happen hereAcPanel.component.ts作为叶组件问题发生在这里

export class AcPanelComponent implements OnInit {
  @Input() public ac: AcModel;
  @Input() public deviceId: number;
  
  constructor(public deviceService: DeviceService, private cdr : ChangeDetectorRef) { 

  }

  ngOnInit(): void {
    console.log('ngOnInit: ' + this.deviceId);
  }

  public powerModeHandler(toMode: string): void {
    console.log(`powerModeHandler for deviceId ${this.deviceId}`);
  }

  public modeHandler(toMode: string): void {
    console.log(`modeHandler for deviceId ${this.deviceId}`);
  }
}

When I press button on element deviceId = 2当我按下元素deviceId = 2上的按钮时

  • press button to call powerModeHandler() log print correct deviceId = 2按下按钮调用 powerModeHandler() 日志打印正确的deviceId = 2

  • press button to call modeHandler() log print deviceId = 1 ???按下按钮调用 modeHandler() 日志打印deviceId = 1 ??? (I don't know why) I'm sure when ngInit it's assign correct deviceId on each element (我不知道为什么)我确定当ngInit它在每个元素上分配正确的deviceId

Here log when ngOnInit call这里记录ngOnInit调用时

ngOnInit: 1
ngOnInit: 2
ngOnInit: 3

Any one know what reason this case happen and how to fixed this.任何人都知道这种情况发生的原因以及如何解决这个问题。

Thank you.谢谢你。

Update.更新。 Added Stackblitz添加了堆栈闪电战

stackblitz here 在这里堆叠闪电战

It's the radio buttons....这是单选按钮....

Took me forever to home in on the problem.把我永远带回家解决这个问题。 Your radio buttons have all the same id attribute, and your label elements get confused!!您的单选按钮具有完全相同的id属性,并且您的label元素会变得混乱!!

This is what you have to do to fix it:这是你必须做的来修复它:

<input type="radio" class="btn-check" name="btnMode" id="btnCool_{{deviceId}}" autocomplete="off" (change)="this.modeHandler('COOL')">
<label class="btn rounded-0 fw-bold" for="btnCool_{{deviceId}}"
       [ngClass]="{'btn-info': this.ac.mode === 'COOL', 'btn-outline-info': this.ac.mode !== 'COOL'}">
  Cool
</label>

To be honest, I'd also change the name attribute in the same way...老实说,我也会以同样的方式更改name属性......

When you click on modeHandler in deviceId = 2 or 3 you see that page scrolls up to deviceId = 1 .当你点击modeHandlerdeviceId = 2 or 3 ,你看到页面滚动高达deviceId = 1 It seems you click on modeHandler in deviceId = 1 !!看来您在deviceId = 1单击了modeHandler !!

So this happen because you are in loop ( *ngFor ) and using same id for radio button (and also for label <label for="btnCool"> ).所以发生这种情况是因为您处于循环中( *ngFor )并且对单选按钮使用相同的id (以及标签<label for="btnCool"> )。

It is good idea to use dynamic id when you use *ngFor .使用*ngFor时最好使用动态 id。 you can use index or any id you know it is unique.您可以使用index或任何您知道它是唯一的id Here you can use deviceId在这里你可以使用deviceId

<div class="btn-group" role="group">
    <input type="radio" class="btn-check" name="btnMode" id="btnCool{{deviceId}}" autocomplete="off" (click)="this.powerModeHandler('COOL')">
    <label class="btn rounded-0 fw-bold" for="btnCool{{deviceId}}"
           [ngClass]="{'btn-info': this.ac.mode === 'COOL', 'btn-outline-info': this.ac.mode !== 'COOL'}">
        Cool
    </label>
    <input type="radio" class="btn-check" name="btnMode" id="btnDry{{deviceId}}" autocomplete="off" (click)="this.modeHandler('DRY')">
    <label class="btn fw-bold rounded-right" for="btnDry{{deviceId}}"
           [ngClass]="{'btn-secondary': this.ac.mode === 'DRY', 'btn-outline-secondary': this.ac.mode !== 'DRY'}">
        Dry
    </label>
</div>

ForkedStackblitz 分叉闪电战

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM