2016-05-19 10 views
1

In meiner Webanwendung verwende ich einen Markdown-Wertkonverter, um HTML aus einer Markdown-Zeichenfolge, z.Wie könnte ein Aurelia-Bindungsverhalten einen innerHTML-Inhalt verbessern?

<div innerhtml.bind="string | markdown"></div> 

Das funktioniert schön und in den div ich ein HTML-Rendering des Markdown-Gehalts in string bekommen.

Der Wertkonverter ist in der Lage, ein benutzerdefiniertes Aurelia-Element in der Ausgabe darzustellen, aber dieses Element innerhalb der Ausgabe des Wertkonverters als String wird nicht von der Aurelia-Templating-Engine verbessert.

Wäre ein bindendes Verhalten in der Lage, die TemplatingEngine zu verwenden, um die Ausgabe des Wertkonverters zu verbessern, der einmal im DOM gerendert wird, jedes Mal, wenn sich der Quellwert ändert? Etwas wie:

<div innerhtml.bind="string | markdown & enhance"></div> 

Ich habe dies versucht, aber es funktioniert nicht (es wird ausgewertet, bevor target seine Kinder bekommt):

export class EnhanceBindingBehavior { 

    private templatingEngine: TemplatingEngine; 

    public constructor(templatingEngine: TemplatingEngine) { 
     this.templatingEngine = templatingEngine; 
    } 

    public bind(binding: Binding, scope: Scope): void { 
     let target: HTMLElement = binding["target"]; 
     for (let i = 0; i < target.children.length; i++) { 
      console.log("enhancing element " + i); 
      this.enhance(target.children[i]); 
     } 

    } 

    public unbind(binding: Binding, scope: Scope): void { 

    } 

    private enhance(element: Element): void { 
     this.templatingEngine.enhance({ 
      element: element 
     }); 
    } 
} 

Wäre es überhaupt possibile sein?

Antwort

1

Das bind Methode des Bindungsverhaltens wird immediately before aufgerufen die Bindungs ​​Instanz applies the model value to the target element was erklärt, warum die Kinder des div nicht existieren yet- der string | markdown Teil des Bindungsausdruckes noch nicht angewandt worden.

Ich denke, ein Aurelia benutzerdefinierte Attribut wäre eine bessere Lösung für diesen Anwendungsfall. Etwas wie:

<div enhance.bind="myMarkdownString | markdown"> 

Oder auch:

<div enhanced-markdown.bind="myMarkdownString"> 

Beides würde Ihnen eine bessere Kontrolle über den Prozess.

3

von Jeremy Antwort inspiriert, machte ich dieses benutzerdefinierte Attribut:

export class EnhancedCustomAttribute { 

    private templatingEngine: TemplatingEngine; 

    private element: HTMLElement; 

    private value: string; 

    public constructor(templatingEngine: TemplatingEngine, element: Element) { 
     this.templatingEngine = templatingEngine; 
     this.element = <HTMLElement> element; 
    } 

    public valueChanged(html: string) { 
     this.enhance(html); 
    } 

    private enhance(html: string) { 
     this.element.innerHTML = html; 
     for (let i = 0; i < this.element.children.length; i++) { 
      this.templatingEngine.enhance(this.element.children.item(i)); 
     } 
    } 

}