最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Angular2 Wait DOM element to load - Stack Overflow

programmeradmin5浏览0评论

I have Component which has a member array variable. This array is bind to DOM with *ngFor. When I add new variable to array my view changes accordingly. Array holds tab names and initially it is set to have only 1 tab. When I refresh page array reinitialized which is what I was expecting. But when I logout and then log back in(router navigation) I see all previous tabs. It is weird to me, because if I console.log(myTabs) array has only 1 element(homeTab).

UPDATE:

.html

<div style="display: table-caption" id="notify-tabs">
    <ul class="nav nav-tabs" role="tablist" id="nav-bar">
        <li role="presentation" data-toggle="tab" id="homeTab" [class.active]="activeTab==='homeTab'"><a (click)="setValues('home')">Home</a>
        <li role="presentation" *ngFor="let tab of myTabs" data-toggle="tab" id={{tab}} [class.active]="activeTab===tab.toString()"><a (click)="setValues(tab)">{{tab}}</a>
    </ul>
</div>

ponent.ts

@Component({

    selector: 'notify-homepage',
        templateUrl: 'app/home/homeponent.html',
        styleUrls: ['styles/css/bootstrap.min.css', 'styles/home.css'],
        directives: [DynamicComponent, TileComponent, MapComponent, HeaderComponent, ConversationComponent, ROUTER_DIRECTIVES]
})
export class HomeComponent{
    public myTabs: number[] = [21442];
    public activeTab: string = 'homeTab';

    ngOnInit() {
    //Assume fully operating MapService here
    this.subscription = this.mapService.conversationId.subscribe(
        (id: number) => {
            this.myTabs.push(id);
            this.setValues(id);
            this.activeTab = id.toString();               
        })
    }
    ngOnDestroy() {
    this.subscription.unsubscribe();
    ...
}
}

map.service.ts

@Injectable()
export class MapService {
    private conversationIdSource = new ReplaySubject<number>();
    public conversationId = this.conversationIdSource.asObservable();

    ...

     showConversation(id: number) {
         this.conversationIdSource.next(id);
     }
}

I have Component which has a member array variable. This array is bind to DOM with *ngFor. When I add new variable to array my view changes accordingly. Array holds tab names and initially it is set to have only 1 tab. When I refresh page array reinitialized which is what I was expecting. But when I logout and then log back in(router navigation) I see all previous tabs. It is weird to me, because if I console.log(myTabs) array has only 1 element(homeTab).

UPDATE:

.html

<div style="display: table-caption" id="notify-tabs">
    <ul class="nav nav-tabs" role="tablist" id="nav-bar">
        <li role="presentation" data-toggle="tab" id="homeTab" [class.active]="activeTab==='homeTab'"><a (click)="setValues('home')">Home</a>
        <li role="presentation" *ngFor="let tab of myTabs" data-toggle="tab" id={{tab}} [class.active]="activeTab===tab.toString()"><a (click)="setValues(tab)">{{tab}}</a>
    </ul>
</div>

.ponent.ts

@Component({

    selector: 'notify-homepage',
        templateUrl: 'app/home/home.ponent.html',
        styleUrls: ['styles/css/bootstrap.min.css', 'styles/home.css'],
        directives: [DynamicComponent, TileComponent, MapComponent, HeaderComponent, ConversationComponent, ROUTER_DIRECTIVES]
})
export class HomeComponent{
    public myTabs: number[] = [21442];
    public activeTab: string = 'homeTab';

    ngOnInit() {
    //Assume fully operating MapService here
    this.subscription = this.mapService.conversationId.subscribe(
        (id: number) => {
            this.myTabs.push(id);
            this.setValues(id);
            this.activeTab = id.toString();               
        })
    }
    ngOnDestroy() {
    this.subscription.unsubscribe();
    ...
}
}

map.service.ts

@Injectable()
export class MapService {
    private conversationIdSource = new ReplaySubject<number>();
    public conversationId = this.conversationIdSource.asObservable();

    ...

     showConversation(id: number) {
         this.conversationIdSource.next(id);
     }
}
Share Improve this question edited Jul 28, 2016 at 15:11 Yhlas asked Jul 26, 2016 at 22:13 YhlasYhlas 4213 gold badges5 silver badges17 bronze badges 4
  • can't you observe the array to get event each time it is edited ? (if i understood well you can subscribe to this kind of events) – anotherdev Commented Jul 26, 2016 at 22:40
  • Could you show a little example pls? – Yhlas Commented Jul 26, 2016 at 22:54
  • Object.observe(myarray, function(changes) { }); I think there is better (rxjs ?) – anotherdev Commented Jul 26, 2016 at 22:59
  • I tried subscribing to my array and act upon change but that is still to early. When array changes it add a new <li> item to DOM and only after that I can modify it. So I have to wait until view is initialized somehow. – Yhlas Commented Jul 27, 2016 at 15:27
Add a ment  | 

2 Answers 2

Reset to default 3

The answer of @Andrei works, but in my opinion there's a better and more elegant solution.

Just use a bination of @ViewChild() and setters.

For example:

// ponent.html

<ng-el ... #myElement>

// ponent.ts

@ViewChild('myElement') set(el) {
  if (el) {
    console.log('element loaded!');
  }
}

Check Lifecycle hooks:

  1. OnChanges https://angular.io/docs/ts/latest/guide/lifecycle-hooks.html#!#onchanges
  2. DoCheck https://angular.io/docs/ts/latest/guide/lifecycle-hooks.html#!#docheck

They help tracking changing in Input and local variables.

OnChanges for Input variables:

ngOnChanges(changes: {[propertyName: string]: SimpleChange}) {
  for (let propName in changes) {
    let chng = changes[propName];
    let cur  = JSON.stringify(chng.currentValue);
    let prev = JSON.stringify(chng.previousValue);
    this.changeLog.push(`${propName}: currentValue = ${cur}, previousValue = ${prev}`);
  }
}

DoCheck for everything:

ngDoCheck() {
  if (this.hero.name !== this.oldHeroName) {
    this.changeDetected = true;
    this.changeLog.push(`DoCheck: Hero name changed to "${this.hero.name}" from "${this.oldHeroName}"`);
    this.oldHeroName = this.hero.name;
  }
}
发布评论

评论列表(0)

  1. 暂无评论