zhelyazko
zhelyazko

Reputation: 57

How to update data on change when using TemplateRef from parent component in child in Angular

I have a child component which renders template from parent like embededView.

exports class ParentComponent {
   public someProp: string;

   ngOnInit() {
      this.someHttpFunc();
   }

   public someHttpFunc() {
      // make some http call and update this.someProp
   }
}
exports class ChildComponent {
   @Input() someRef: TemplateRef<any>
   @ViewChild("content", { read: ViewContainerRef }) contentRef: ViewContainerRef;

   ngOnInit() {
     this.contentRef.createEmbeddedView(someRef);
   }
}

My parent.component.html:

<child someRef="template"></child>
<ng-template #template>

  <div>{{ someProp }}</div>
</ng-template>

My child.component.html

<div #content></div>

The problem is that when the http call in someHttpFunc() finish the result of someProp in the child component is not automatically updated. When I set timeout for this.contentRef.createEmbeddedView(someRef); everything works fine, but definitely it's not a good solution

Upvotes: 0

Views: 1759

Answers (2)

German Quinteros
German Quinteros

Reputation: 1930

Try doing this:

parent.component.ts

exports class ParentComponent {
   public someProp$: Observable<string>;
   private propSource: Subject<string>;

   constructor() {
     this.propSource = new Subject();
     this.someProp$ = this.propSource.asObservable();
   }
   ngOnInit() {
      this.someHttpFunc();
   }

   public someHttpFunc() {
      // psuedo code for http calls
      httpCall.subscribe(() => {
        const newValue = 'x'; // here it's the new value of your props
        this.propSource.next(newValue)
      });
   }
}

parent.component.html

<child someRef="template"></child>
  <ng-template #template>

  <div>{{ someProp$ | async }}</div>
</ng-template>

Upvotes: 2

Chunbin Li
Chunbin Li

Reputation: 2244

maybe you can try using setter , like these code

exports class ChildComponent {
  @Input()
  set someRef(newTemplate: TemplateRef < any > ) {
    if (!newTemplate) {
      return;
    }

    this.contentRef.createEmbeddedView(someRef);

  }

  @ViewChild("content", {
    read: ViewContainerRef
  }) contentRef: ViewContainerRef;
}

Upvotes: 0

Related Questions