Search code examples
angularangular-signals

Template doesn't update when Signal's value changes


My template:

{{ announcements().start | date: "d MMM" }} -
{{ announcements().end | date: "mediumDate" }}

<button type="button" class="btn btn-primary" (click)="goForward()">
  <i class="bi bi-chevron-right"></i>
</button>

My component:

export class AnnouncementsComponent {
  readonly announcements: Signal<Announcements>;
  announcementsForm: FormGroup;
  constructor(
    private announcementsServ: AnnouncementsService,
    private logger: NGXLogger,
    private fb: FormBuilder,
  ) {
    this.announcements = this.announcementsServ.announcements.asReadonly();
    this.announcementsForm = this.fb.group({ content: '' });
    effect(() => {
      this.announcementsForm.setValue({
        content: this.announcements().content,
      });
    });
  }
  goForward() {
    this.announcementsServ.goForward();
  }
  goBackwards() {
    this.announcementsServ.goBackwards();
  }
  onSubmit() {
    this.announcementsServ.changeContent(this.announcementsForm.value.content);
  }
}

My service:

@Injectable()
export class AnnouncementsService {
  announcements: WritableSignal<Announcements>;
  constructor(private logger: NGXLogger) {
    this.announcements = signal({
      start: new Date('2023-08-27'),
      end: new Date('2023-09-03'),
      content: `some content`,
    });
  }

  changeDates(howMuch: number) {
    this.announcements.update((announcements: Announcements) => {
      announcements.start.setDate(announcements.start.getDate() + howMuch);
      announcements.end.setDate(announcements.end.getDate() + howMuch);
      return announcements;
    });
  }

  goForward() {
    this.changeDates(7);
  }
  goBackwards() {
    this.changeDates(-7);
  }

  changeContent(content: string) {
    this.logger.debug(content);
  }
}

Effect executes successfully in both component and service, but template doesn't wanna update. Why?

I used this pattern successfully in another component and service, but with boolean Signal. Is it problem with signals of single object?


Solution

  • The pipe only rerenders when the Date is new and not for mutations. https://angular.io/api/common/DatePipe#description

    Note that mutating a Date object does not cause the pipe to be rendered again. To ensure that the pipe is executed, you must create a new Date object.