How to Check Whether <Ng-Content> Is Empty? (In Angular 2+ Till Now)

How to check whether ng-content is empty? (in Angular 2+ till now)

Wrap ng-content in an HTML element like a div to get a local reference to it, then bind the ngIf expression to ref.children.length == 0:

template: `<div #ref><ng-content></ng-content></div> 
<span *ngIf=" ! ref.children.length">
Display this if ng-content is empty!
</span>`

Updated for Angular 12; old logic ("ref.nativeElement.childNodes.length") gives error, as nativeElement is undefined nowadays.

How to check whether ng-content exists

If you have a parent element of <ng-content> with a template variable (#panelHeading)

<div class="panel panel-default">
<div class="panel-heading" #panelHeading [hidden]="!showHeading">
<ng-content select="my-panel-heading"></ng-content>
</div>
<div class="panel-body">
<ng-content select="my-panel-content"></ng-content>
</div>
</div>

then you can query for it like

@ViewChild('panelHeading') panelHeading;

and set a property depending on whether there are children or not

constructor(private cdRef:ChangeDetectorRef) {}

showHeading:boolean = false;

ngAfterViewInit() {
this.showHeading = this.panelHeading.nativeElement && this.panelHeading.nativeElement.children.length > 0;
this.cdRef.detectChanges();
}

If <my-panel-heading> is an Angular2 component, then you can also use

@ContentChild(MyPanelHeading) panelHeading:MyPanelHeading;

constructor(private cdRef:ChangeDetectorRef) {}

showHeading:boolean = false;

ngAfterViewInit() {
this.showHeading = this.panelHeading != null;
this.cdRef.detectChanges();
}

If ng-content has content or empty Angular2

Use children instead of childNodes. Angular creates comment nodes for *ngIf* which are counted bychildNodes`

<div #contentWrapper [hidden]="isOpen">
<ng-content ></ng-content>
</div>

<span *ngIf="contentWrapper.children.length == 0">
<p>Display this if ng-content is empty!</p>
</span>

Plunker example

How to provide a fallback for empty ng-content in Angular?

You can check for projected content yourself and show alternative content when none was found:

@Component({
template: `
<div *ngIf="hasContent">alternative content</div>
<div #wrapper>
<ng-content></ng-content>
</div>
`
})
class MyComponent implements AfterContentInit {
@ContentChild('wrapper') wrapper:ElementRef;
hasContent = false;
ngAfterContentInit() {
this.hasContent = this.wrapper.childNodes.length > 0;
}
}

Angular 8: detect if a ng-content has content in it (or exists)

In Angular 8 you dont have to use the ngAfterViewInit life cycle hook. You can use the ngOnInit as long as you set the "static" value of the viewchild to true.

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

@Component({
selector: 'app-test',
templateUrl: './test.component.html',
styleUrls: ['./test.component.scss']
})
export class TestComponent implements OnInit {
@ViewChild('content', { read: ElementRef, static: true }) content: ElementRef;
constructor() { }

ngOnInit() {
console.log(!!this.content.nativeElement.innerHTML); // return true if there is a content
}
}

Note that you must wrap the ng-content directive with html tag (such as div, span etc) and to set the templateRef on this outer tag.

<div #content>
<ng-content></ng-content>
</div>

I putted it on stackblitz: https://stackblitz.com/edit/angular-8-communicating-between-components-mzneaa?file=app/app.component.html



Related Topics



Leave a reply



Submit