Reputation: 1787
For the context I'm building syntax highlighting for my angular (1.5.8) application. For syntax highlighting I use Prism.js
which unfortunately can't highlight my code when I use ng-include
in my HTML. Quite understandable since it introduces asynchronity. So to overcome the problem I'm creating an angular directive so that I can write something like this:
<prism lang="html">
<md-toolbar layout layout-align="end center"></md-toolbar>
</prism>
Then in my directive I'm runnin the contents of the directive through Prism.highlight(transclusion, Prism.languages[this.lang])
so far so good. It works, but the only problem is, that angular parses my transclusion beforehand and modifies my input html that it adds additional classes because of my used layout
and layout-align
directives.
Here lies my question. Can I tell angular that "do not parse this chunk of code"?
Edit: I tried to wrap the input in <pre></pre>
but that didn't help. Angular still parsed it and added classes.
Edit2: While I'm writing this I have an idea to put html elements outside of angular context giving them unique id. Then writing <prism code-id="some-unique-id">
then the directive could fetch the dom elem referenced by that uid and include it in the dom. Well, ugly af but could work am I right?
Edit3: I'm extending the post with more code so that you get the whole picture
1: In styleguide.html
<!-- MATERIAL DESIGN -->
<div id="material">
<h1>Material design assets</h1>
<div ng-include="'./material.html'"></div>
</div>
2: In material.html
<section>
<h2>Dialog</h2>
<md-button class="md-accent">Open sample dialog</md-button>
<prism lang="html">
<md-toolbar class="md-primary">
<header class="md-toolbar-tools">
<h3 class="md-headline">{{ 'Dialog title' | translate }}</h3>
<!-- SPACER -->
<span flex></span>
<md-button class="md-icon-button" ng-click="ctrl.close()"><i class="material-icons">close</i></md-button>
</header>
</md-toolbar>
<md-dialog-content>
<div class="md-dialog-content">
<!-- Content here -->
</div>
</md-dialog-content>
<md-dialog-actions layout-padding layout layout-align="end center">
<!-- stuff here -->
</md-dialog-actions>
</prism>
</section>
3: In the component
class PrismHighlighter {
static get $descriptor() {
return {
controller: PrismHighlighter,
template: `
<pre>
<code class="language-{{$ctrl.lang}}">
<ng-transclude class="transclusion"></ng-transclude>
</code>
</pre>
`,
transclude: true,
bindings: {
lang: '@'
}
}
}
static get $inject() {
return ['$element'];
}
constructor($element) {
this.element = $element;
}
$postLink() {
const codeElem = this.element.find('code');
const transclusion = $(this.element).find('ng-transclude').html();
const hCode = Prism.highlight(transclusion, Prism.languages[this.lang]);
codeElem.html(hCode);
}
}
module.component('prism', PrismHighlighter.$descriptor);
4: And the output
Now you can clearly see that there are a lot of angular added things there what I don't want :/
Upvotes: 2
Views: 505
Reputation: 18018
Use ng-non-bindable
directive around it.
For Angular 1.x you can just use:
<div ng-non-bindable>
</div>
For angular 2.x this check this post that shows how to do the same.
Reference:
https://docs.angularjs.org/api/ng/directive/ngNonBindable
Upvotes: 1