63. Custom Structural Directives (Implementing custom *NgIf)
Structural directives require managing template references to decide whether to render the content. We use two injectable services:
TemplateRef: Represents the content contained within the<ng-template>tag (the element the directive is applied to).ViewContainerRef: Represents the container where the template should be attached or detached (the location in the DOM).
Example: *appUnless (The opposite of *NgIf)
This directive displays content unless the condition is true.
typescript import { Directive, Input, TemplateRef, ViewContainerRef } from '@angular/core';
@Directive({ selector: '[appUnless]' }) export class UnlessDirective { private hasView = false;
// The setter function runs whenever the input value changes @Input() set appUnless(condition: boolean) { // condition is the boolean value passed to the directive (*appUnless='false') if (!condition && !this.hasView) { // 1. Create the embedded view (insert content into the DOM) this.vcRef.createEmbeddedView(this.templateRef); this.hasView = true; } else if (condition && this.hasView) { // 2. Clear the view (remove content from the DOM) this.vcRef.clear(); this.hasView = false; } }
// Inject TemplateRef (what to render) and ViewContainerRef (where to render)
constructor(
private templateRef: TemplateRef
Usage
html
Understanding TemplateRef and ViewContainerRef is the foundation for creating any custom structural directive, including complex ones like custom list renderers or permission-based content toggles.