Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to force UI "refresh" on nativescript (typescript) with Observables throught http requests?

I'm using a TabView component with template syntax to iterate over it and add items inside (using an observable collection and async pipe). My items come from a http request.

My home.component.tns.html as follows:

<ActionBar title="Angular 2 Seed Advanced (nativescript)">
</ActionBar>
<StackLayout>
  <TabView selectedIndex="0" selectedColor="#FF0000">
    <template ngFor let-tab [ngForOf]="tabs | async">
      <StackLayout *tabItem="tab">
          <Label text="tab item"></Label>
      </StackLayout>
    </template>
  </TabView>

  <Button text="call something" (tap)="emptymethod()"></Button>

</StackLayout>

...and my home.component.ts:

...
    export class HomeComponent{

        public tabs: Observable<any[]>;

        constructor(private _menuService: MenuService) {

            this._menuService.getMenu()
                .map((menus) => {
                    let result: Array<any> = [];

                    if (menus) {
                        menus.forEach(menu => {
                            result.push({ 'title': menu.title });
                        });
                    }
                    return result;
                })
                .subscribe(
                data => {
                    this.tabs = Observable.of<any[]>(data);
                },
                error => error => this._log.debug(error));
        }

        emptymethod() {
            this._log.debug('HomeComponent - nada invoked');
        }

        ngOnInit() {

        }
    ...

When the interface is renderized, the TabView menu does not appears, but when i click over call something button and emptymethod is called the items inside the TabView appears, in other words, after the "refresh" that component appears...

This should not happens automatically?

like image 403
Richard Lee Avatar asked Dec 10 '22 16:12

Richard Lee


2 Answers

I had couple of situations with nativescript where the UI wont refresh (the zone will not trigger a UI refresh or something) and the easiest way to do it is to force the code to run into the zone. Here is small example

export class TestClass {
   constructor(private _ngZone: NgZone) {
   }
   someOperation(){
     this._ngZone.run(() => {
       //Do whatever you want here
     })
   }
}

I know this is not the best solution but thats the cleanest workaround currently I think

Here is another question that I asked months ago related to this: Angular 2 How to get Angular to detect changes made outside Angular?

like image 104
Denko Mancheski Avatar answered Dec 28 '22 08:12

Denko Mancheski


There seems to be a problem with how async operations and change detection is being handled in nativescript-angular when third party plugins are involved.

The current suggestion is to wrap all async notify calls within a zoned callback function.

The following video explains the issue and solution. Hope this helps. http://www.nativescriptsnacks.com/videos/2016/06/13/zoned-callbacks.html

More details on a corresponding feature request in Nativescript is present here. https://github.com/NativeScript/NativeScript/issues/2229

like image 39
abz Avatar answered Dec 28 '22 08:12

abz