Binding data from innerHtml
peripurnama opened this issue · comments
Feature Description
Binding data from innerHtml
Use Case
How to enter this html code
const fullContent = `<p>Test Syntax</p>
<pre><code [highlight]="`public class HelloWorld {
public static void main(String[] args) {
System.out.println("Hello World");
}
}`" [languages]="['java']"
(highlighted)="onHighlight($event)" [lineNumbers]="false"></code></pre>`;
from the code above this line that you want to highlight:
`public class HelloWorld {
public static void main(String[] args) {
System.out.println("Hello World");
}
}`
<div [innerHtml]="fullContent | safeMode"></div>
Tampilan yg di harapkan
You can already do that, however, you need to use the highlight service and manually highlight using highlightAll
or highlightElement
functions
i tried the manual way with this code it works, but in the browser there is a warning
var blocks = this.elementRef.nativeElement.querySelectorAll('pre code');
blocks.forEach((block:any) => {
this.highlightJS.hljs?.highlightElement(block);
});
One of your code blocks includes unescaped HTML. This is a potentially serious security risk.
I found a solution, you can use this method,
maybe in the library you can add this directive
@Pipe({ name: "safeHtml" })
export class SafeHtmlPipe implements PipeTransform {
constructor(private sanitizer: DomSanitizer) {}
transform(value:any) {
return this.sanitizer.bypassSecurityTrustHtml(value);
}
}
@Pipe({
name: 'highlightCode',
})
export class HighlightCodePipe implements PipeTransform {
constructor(private highlightJS: HighlightJS,
private sanitizer: DomSanitizer){
}
transform(htmlMarkup: string): string {
const preCodeRegex = /<pre><code(?: class="language-(.*)")?>([\s\S]*?)<\/code><\/pre>/g;
let result = htmlMarkup.replace(preCodeRegex, (_match, languageName, codeBlock) => {
let codeBlockHighlighted: string = '';
if (!languageName) {
codeBlockHighlighted = hljs.highlightAuto(codeBlock, ['java']).value || ''
} else {
codeBlockHighlighted = hljs.highlight(codeBlock, {
language: languageName,
ignoreIllegals: true
}).value || '';
}
const code = '<pre><code class="hljs">' + codeBlockHighlighted + '</pre></code>';
return code;
});
return result;
}
}
the html component will look like this
<div [innerHTML]="content | highlightCode | safeHtml"></div>
Be caution when using a pipe, it isn't ideal for heavy JS, because it will be executed with every change detection.
I built a directive for this. Hopefully, it helps people. Usage:
<pre ngsHighlightContent>
const myVar = 1;
console.log(myVar);
</pre>