简体   繁体   English

Angular 材料列表选项返回真,即使假

[英]Angular Material List Option returns true, even if false

<mat-selection-list>
    <ng-container *ngFor="let cat of permissionCategories()">
        <mat-divider></mat-divider>
        <div mat-subheader>{{ cat }}</div>
        <mat-list-option *ngFor="let permission of permissionsOfCategory(cat)"
            [selected]="havePermission(permission)"
        >
            {{ permission.Name }}
        </mat-list-option>
    </ng-container>
</mat-selection-list>

And

havePermission(permission: Permission): boolean {
    return this.currentRankPermissions.includes(permission.Id);
}

I checked houndred times all values, and they are correct There are some permissions and havePermission returns true or false我检查了百次所有值,它们是正确的。有一些权限, havePermission返回真或假

UseLspdTablet true UseLspdTablet true
ModifyRanks true ModifyRanks true
AccessCitizenIndex true AccessCitizenIndex
AccessCitizenRegistry false访问公民注册表false
ArrestMandateCitizen false ArrestMandateCitizen false
ChangeCitizenPhoneNumber false更改公民电话号码false
ModifyCitizenWanted false修改CitizenWanted false
ShowCitizenCrimeCount false ShowCitizenCrimeCount错误
AccessVehicleIndex false AccessVehicleIndex
SetVehicleAsStolen false SetVehicleAsStolen false
SetVehicleAsWanted false SetVehicleAsWanted false
SetVehicleAsFound false SetVehicleAsFound false
SetVehicleNote false SetVehicleNote false

And every time I run this page, everything works perfectly, but then I wait 3 seconds (after this time there are some other updates on same page, none of them are accessing any of this variables or something ) and then in console they still show ok, but in page they all are selected, WHY每次我运行这个页面时,一切都很完美,但是我等了 3 秒钟(在这个时间之后,同一页面上还有一些其他更新,他们都没有访问任何这些变量或其他东西),然后在控制台中它们仍然显示好的,但是在页面中它们都被选中了,为什么

Also I noticed that there are thousends of console logs of this = thousends of rerenders.此外,我注意到有 thounds 的控制台日志这个 = thounds of rerenders。

Rest of maybe important code: Rest 可能很重要的代码:

  onTablesChanged() {
    this.allRanks = Array.from(this.db.Tables.Rank.values());

    if (this.permissionsOfRank.length <= 0) {
      this.permissionsOfRank = Array.from(this.db.Tables.PermissionOfRank.values());
    }
  }

  permissionCategories(): string[] {
    const res = [];
    Array.from(this.db.Tables.Permission.values()).forEach((permission: Permission) => {
      if (!res.includes(permission.Category)) {
        res.push(permission.Category);
      }
    });

    return res;
  }

  permissionsOfCategory(cat: string): Permission[] {
    return Array.from(this.db.Tables.Permission.values())
      .filter(c => c.Category === cat);
  }

Every 3 seconds onTablesChanged is called which cause this rerender, but it should cause 13 calls of havePermission , but it cause 99999999 of them, WHY每 3 秒调用一次onTablesChanged会导致此重新渲染,但它应该会导致 13 havePermission调用,但会导致其中 99999999 次,为什么

Windows 10 Angular 8.3.26 Typescript 3.5.3 @angular/material 8.2.3 Windows 10 Angular 8.3.26 Typescript 3.5.3 @angular/material 8.2.3

I ran this on FiveM Application (GTA V) - which just use chromium.我在 FiveM 应用程序(GTA V)上运行了它——它只使用了铬。

WHY为什么

In general use a function in the.html is bad idea.通常在.html中使用function是个坏主意。 I suppose your permissionCategories and permissionsOfCategory changes when the tables changes, that's you can mannage in the onTablesChanged.我想你的permissionCategories 和permissionOfCategory 会在表格发生变化时发生变化,那你可以在onTablesChanged 中进行管理。 So you can use this function to calculate a variable data that was an array of object.所以你可以使用这个 function 来计算一个变量data ,它是一个 object 的数组。 Each object has two properties: category and permissions (this last is an array).每个 object 都有两个属性: categorypermissions (最后一个是数组)。 So:所以:

data:any[] //<--declare a variable
onTablesChanged() {
    this.allRanks = Array.from(this.db.Tables.Rank.values());

    if (this.permissionsOfRank.length <= 0) {
      this.permissionsOfRank = Array.from(this.db.Tables.PermissionOfRank.values());
    }
    //here calculate data in the way
    data=this.permissionCategories().map(x=>({category:x,permissions:[]}))
    //data is an array ob object with "category" and "permissions"
    data.forEach(x=>{
      //with each element of data
       x.permissions=this.permissionsOfCategory(x.category)
          //x.permisions is an array of Permision, but 
          //you create an object with "permision", the Permision and "selected"
          .map(p=>({
               permission:p,
               selected:this.havePermission(x.category)
          })
    })
  }

And your.html还有你的.html

<mat-selection-list>
    <ng-container *ngFor="let cat of data">
        <mat-divider></mat-divider>
        <!--use cat.category-->
        <div mat-subheader>{{ cat.category }}</div>
                <!--use cat.permissions-->
        <mat-list-option *ngFor="let permission of cat.permissions"
            <!--use 
            [selected]="permission.selected"
        >
            {{ permission.permission.Name }}
        </mat-list-option>
    </ng-container>
</mat-selection-list>

I hope don't missing so much (I don't check the code), but remember: the idea is calculate all one time -using map to transform an array in an array of objects (one property the array and another property a value calculated) instead use complex function in the.html我希望不要错过太多(我不检查代码),但请记住:这个想法是一次计算 - 使用 map 将数组转换为对象数组(一个属性是数组,另一个属性是值计算)代替使用复数 function 中的.html

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

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