Reputation: 411
I have a requirement for layout something like this
I want to use CSS display: grid;
someFunction(data) {
this.data = data;
let parentDiv1 = document.createElement('div');
parentDiv1.className = 'div';
parentDiv1.textContent = 'Random Inner Text';
let cb1 = document.createElement('input');
cb1.type = 'checkbox';
cb1.className = 'check-box';
parentDiv1.appendChild(cb1);
this.tableKey = [
'',
`Text: ${this.data.someRandomText1}`,
`Text: ${this.data.someRandomText2}`,
`Text: ${this.data.someRandomText3}`,
`Text: ${this.data.someRandomText4}`,
`Text: ${this.data.someRandomText5}`,
parentDiv1,
`Text: ${this.data.someRandomText6}`,
`Text: ${this.data.someRandomText7}`,
`Text: ${this.data.someRandomText8}`,
parentDiv1
];
}
<div class="container">
<div class="table">
<ng-container *ngFor="let item of tableKey" [innerHTML]="item"></ng-container>
</div>
</div>
This is what the output is (Ignore CSS).
Now instead of [object HTMLDivElement]
I want a checkbox and text there. Is there a way?
Upvotes: 0
Views: 823
Reputation: 271
The best approach to this solution would be using outerHTML
property of the created element. And then sanitize it in the HTML component using a pipe.
// .component.ts
export class AppComponent implements OnInit {
name = "Angular " + VERSION.major;
tableKey: any[];
ngOnInit() {
let parentDiv1 = document.createElement("div");
parentDiv1.className = "div";
parentDiv1.textContent = "Random Inner Text";
let cb1 = document.createElement("input");
cb1.type = "checkbox";
cb1.className = "check-box";
parentDiv1.appendChild(cb1);
this.tableKey = [
"Random 1",
"Random 2",
"Random 3",
"Random 4",
"Random 5",
"Random 6",
parentDiv1.outerHTML,
"Random 7",
"Random 8"
];
}
}
// .pipe.ts
import {
Pipe,
PipeTransform
} from "@angular/core";
import {
DomSanitizer
} from "@angular/platform-browser";
@Pipe({
name: 'safeHtml'
})
export class SafeHtmlPipe implements PipeTransform {
constructor(private sanitized: DomSanitizer) {}
transform(value: string) {
return this.sanitized.bypassSecurityTrustHtml(value);
}
}
<div class="container">
<div *ngFor="let item of tableKey" [innerHTML]="item | safeHTML">
</div>
</div>
Upvotes: 0
Reputation: 34435
Method #1
You could use the outerHTML
property of the html element so that your array only contains string, and then sanitize these strings in the template so that the html can be displayed
component.ts
this.tableKey = ["text1", "text2",
parentDiv1.outerHTML, //Convert html element to string
component.html
<div *ngFor="let item of tableKey" [innerHTML]="item | safeHtml ">
Method #2
Only use one array of mixed strings/HtmlElements like in your example, and in the template decide how to display it based on the type
component.ts
this.tableKey = ["text1", "text2",
parentDiv1, //array of mixed elements
// ...
public isString(value: any)
{
return typeof(value) ==='string';
}
component.html
<ng-container *ngFor="let item of tableKey" >
<div *ngIf="isString(item)" [innerHTML]="item"></div> <!-- display string -->
<div *ngIf="!isString(item)" [innerHTML]="item.outerHTML | safeHtml" ></div> <!-- display html element -->
</ng-container>
See stackblitz demo
Upvotes: 1