Выражение изменило ошибку: изменение значения привязки в шаблоне - PullRequest
1 голос
/ 28 июня 2019

Это шаблон моего компонента A:

<nb-tab tabTitle="Photos" [badgeText]="centerPictures?.pictures?.length" badgePosition="top right" 
            badgeStatus="info">
              <app-center-pictures #centerPictures [center]="center"></app-center-pictures> //Child component B
</nb-tab>
<nb-tab tabTitle="Facilities" [badgeText]="centerFacilities?.facilities?.length" badgePosition="top right" badgeStatus="info">
              <app-club-facilities #centerFacilities [centerId]="center.id"></app-club-facilities> // Child component C
</nb-tab>
<nb-tab tabTitle="Prices" [badgeText]="centerPrices?.priceRules?.length" badgePosition="top right" badgeStatus="info">
              <app-center-prices #centerPrices [currency]="center.currenciesAccepted"></app-center-prices> // Child component D
</nb-tab>

Я получил эту ошибку:

ExpressionChangedAfterItHasBeenCheckedError: Выражение изменилось после его проверки. Предыдущее значение: 'badgeText: null'. Текущее значение: 'badgeText: 0'

Я понимаю эту ошибку, но я не знаю, что делать. Это касается DOM [badgeText], а не функции A. Спасибо

РЕДАКТИРОВАТЬ: Comp A

IMPORTS

@Component({
  selector: 'app-center-detail',
  templateUrl: './center-detail.component.html',
  providers: [CentersService, PictureService],
  styleUrls: ['center-detail.component.css']
})

export class CenterDetailComponent implements OnInit {

  @ViewChild ('centerPictures') centerPictures;

  get centerPicturesCount(): number {
      console.log(this.centerPictures);
      return this.centerPictures.pictures.length;
  }

  center: Center;
  errorMessage: string;
  success: string;
  edit: boolean = false;

  constructor(
    private centerService: CentersService,
    private route: ActivatedRoute,
    private pictureService: PictureService
  ) { }

  ngOnInit() {
    this.getCenter();
  }

  getCenter() {
    const id = this.route.snapshot.paramMap.get('id');
    this.centerService.getCenter(id)
      .subscribe(
        center => this.center = center,
        error => {
          if (error.status === 404) {
            this.errorMessage = "Center not found";
          }
          else {
            this.errorMessage = "An error has occured";
          }
        }
      );
  }

  processFile(image, type: string) {
    this.success = null;
    this.errorMessage = null;

    if (image.files.length) {
      let picture = new UploadPicture(image.files[0]);
      this.pictureService.addCenterPicture(this.center.id, picture.header(type))
        .subscribe(
          () => {
            this.getCenter();
            this.success = 'Header picture has been successfully changed !';
          },
          error => this.errorMessage = error.message
        )
    }
  }
}

Компонент B:

IMPORTS

  @Component({
    selector: 'app-center-pictures',
    templateUrl: 'center-pictures.component.html',
    providers: [PictureService],
    styleUrls: ['center-pictures.component.css']
  })
export class CenterPicturesComponent implements OnInit {

  @Input() center: Center;
  facilities: CenterFacilities[];
  pictureUrl = environment.pictureUrl + '/';

  @ViewChild('updateData') updateData: TemplateRef<any>;
  window: NbWindowRef;

  pictures: PictureData[];
  uploads: UploadPicture[] = [`enter code here`];
  uploading: boolean = false;

  error: string;
  success: string;
  disabled: boolean = false;

  constructor(
    private pictureService: PictureService,
    private centersService: CentersService,
    private windowService: NbWindowService
  ) { }

  ngOnInit() {
    this.centersService.getCenterFacilities(this.center.id)
      .subscribe(
        facilities => {
          this.facilities = facilities
        },
        error => this.error = error.message
      )
    this.getCenterPictures();
  }

  getCenterPictures() {
    this.pictureService.getCenterPictures(this.center.id)
      .subscribe(
        pictures => this.pictures = pictures,
        error => this.error = error.message
      );
  }

  processFile(image) {
    this.error = null;
    this.success = null;
    if (image.files.length) {
      let upload = new UploadPicture(image.files[0]);
      this.uploads.push(upload);
    }
  }

  removeUpload(upload) {
    const index = this.uploads.indexOf(upload);
    this.uploads.splice(index, 1);
  }

  uploadPictures() {
    this.error = null;
    this.success = null;
    if (!this.uploads.length) {
      return this.error = 'Please choose a picture to upload';
    }
    this.uploads.forEach((upload) => {
      this.uploading = true;
      this.pictureService.addCenterPicture(this.center.id, upload.picture())
        .subscribe(
          picture => {
            this.success = '\'' + picture.name + '\' has been uploaded';
            this.getCenterPictures();
            this.uploading = false;
          },
          error => this.error = error.message
        );
    });
    this.uploads.length = 0;
  }

  openWindow(picture: PictureData) {
    this.window = this.windowService.open(this.updateData, {
      title: picture.name,
      context: { picture: picture },
    });
  }

  updatePicture(picture: PictureData) {
    this.error = null;
    this.success = null;
    this.pictureService.updateCenterPicture(this.center.id, picture.id, {
      caption: picture.caption,
      activity: picture.activity,
      facilityId: picture.facilityId,
      isIndoor: picture.isIndoor
    }).subscribe(
      () => {
        this.success = '\'' + picture.name + '\' has been successfully updated';
        if (this.window)
          this.window.close();
      },
      error => this.error = error.message
    );
  }

  removePicture(id: string, name: string) {
    this.success = null;
    this.error = null;
    if (!this.disabled) {
      this.disabled = true;
      this.pictureService.deleteCenterPicture(this.center.id, id)
        .subscribe(
          () => {
            this.getCenterPictures();
            this.success = '\'' + name + '\' has been successfully removed';
            this.disabled = false;
          },
          error => this.error = error.message
        );
    }
  }
}

Ответы [ 3 ]

1 голос
/ 28 июня 2019

Вы попробуете это. Добавьте этот код в дочерний компонент B

@Output() picturesCount: EventEmitter<number>;
constructor() {
    this.picturesCount = new EventEmitter<number>();
}
getCenterPictures() {
    this.pictureService.getCenterPictures(this.center.id)
      .subscribe(
        pictures => {
          this.picturesCount.emit(pictrues.length);
        },
        error => this.error = error.message
      );
}

И компонент А:

public outPicturesCount: number = 0;
picturesCount(value: number) {
    this.outPicturesCount = value;
}

И шаблон:

<nb-tab tabTitle="Photos" [badgeText]="outPicturesCount" badgePosition="top right" 
            badgeStatus="info">
    <app-center-pictures (picturesCount)=picturesCount($event) #centerPictures [center]="center"></app-center-pictures> //Child component B
</nb-tab>
1 голос
/ 28 июня 2019

Сначала добавьте этот код в свой componentA.ts

@ViewChild ('centerPictures') centerPictures;

get centerPicturesCount(): number {
    return this.centerPictures.pictures.length;
}

И исправьте ваш шаблон так:

<nb-tab tabTitle="Photos" [badgeText]="centerPicturesCount" badgePosition="top right" 
            badgeStatus="info">
              <app-center-pictures #centerPictures [center]="center"></app-center-pictures> //Child component B
</nb-tab>
0 голосов
/ 01 июля 2019

Решено (спасибо Akai Crystal)

Комп. A:

public outPicturesCount: number = 0;
picturesCount(value: number) {
   this.outPicturesCount = value;
}

Комп. B:

@Output() picturesCount = new EventEmitter<number>();
getPictures() {
   .
   .
   .
   pictures => {
      this.pictures = pictures,
      this.picturesCount.emit(pictures.length);
   }

Шаблон:

<nb-tab tabTitle="Photos" [badgeText]="outPicturesCount" badgePosition="top right" 
badgeStatus="info">
   <app-center-pictures (picturesCount)=picturesCount($event) #centerPictures 
   [center]="center"></app-center-pictures>
</nb-tab>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...