Miguel Miguel - 8 months ago 103
TypeScript Question

Refresh a ListView adding new elements on runtime in NativeScript and Angular

I'm building a ListView based component, similar to the groceries example in the {N} page. I have a "+" button, that needs to add new items to the list, I have this code:

import { Component, OnInit } from '@angular/core';

moduleId: module.id,
selector: 'my-list',
templateUrl: 'my-list.component.html'
export class ListComponent implements OnInit {
private myList: CustomObject;
constructor() { }

ngOnInit() { }

this.myList.push(new CustomObject());


And here is the template:

<Button text="+" (tap)="addItem()" ></Button>
<ListView [items]="myList">
<template let-item="item" let-i="i">
<Label text="item.name"></Label>

My problem is, when I click on the "+" button, I get an undescifrable exception. When I fill the list with code, no problem, but I need the user can add new elements to the view. How is the correct way to implement a dynamic ListView like I described?


An uncaught Exception ocurred on "main" thread.
com.tns.NativeScriptException: Calling js method getView failded

Error No suitable views found in list template! Nesting level:0 File:
line:135 column:8

StackTrace: Frame: function:'getSingleViewRecursive', file:....

Answer Source

In NativeScript + Angular-2 application you can use AsyncPipe

Example on how to provide data via async pipe in NativeScript + NG2 app can be found here

What is noticeable is the usage of RxObservable


import { Component, ChangeDetectionStrategy } from "@angular/core";
import { Observable as RxObservable } from "rxjs/Observable";

export class DataItem {
    constructor(public id: number, public name: string) { }

    templateUrl: "ui-category/listview/using-async-pipe/using-async-pipe.component.html",
    changeDetection: ChangeDetectionStrategy.OnPush,
export class UsingAsyncPipeComponent {
    public myItems: RxObservable<Array<DataItem>>;

    constructor() {
        let items = [];
        for (let i = 0; i < 3; i++) {
            items.push(new DataItem(i, "data item " + i));

        let subscr;
        this.myItems = RxObservable.create(subscriber => {
            subscr = subscriber;
            return function () {
                console.log("Unsubscribe called!");

        let counter = 2;
        let intervalId = setInterval(() => {
            items.push(new DataItem(counter + 1, "data item " + (counter + 1)));
        }, 1000);

        setTimeout(() => {
        }, 15000);


<ListView [items]="myItems | async" class="list-group">
    <template let-item="item" let-i="index" let-odd="odd" let-even="even">
        <GridLayout class="list-group-item" [class.odd]="odd" [class.even]="even">
            <Label [text]="item.name" android:class="label-item"></Label>

In this basic example the async is simulated with setInterval but based on the same logic you can achieve your desired UX with a button.