javascript - 如何使用 Aurelia 动态增强 HTML

标签 javascript aurelia

我们将所有页面内容和博客文章等存储在 WordPress 中,使用其 API 在我们的 Aurelia 应用程序中呈现数据。这运作良好;

<div class="excerpt" innerhtml.bind="post.excerpt.rendered"></div>

作者现在希望能够链接到弹出窗口或使用 route-href或其博客文章中的其他自定义 Aurelia 属性,但使用 innerhtml.bind 添加到页面的代码Aurelia 不会解析。

我喜欢正常的<a href="...">在 Aurelia 中“正常工作” - 但我们有大量自定义属性(例如 <button popup="name-of-popup">...</button> 作者无法使用。

我们如何克服这个问题?

编辑:根据@bigopon 的评论,我已经开始做一些事情,但仍然无法完全发挥作用。要么我不擅长搜索,要么 TemplatingEngine.enhance() 上的文档有点缺乏。方法,但我尝试创建一个像这样的自定义属性:

import {Aurelia, inject, TemplatingEngine} from 'aurelia-framework';

@inject(Element, Aurelia, TemplatingEngine)
export class AureliaEnhanceCustomAttribute {
    constructor (el, aurelia, templatingEngine) {
        this.el = el;
        this.aurelia = aurelia; // NOTE: I've never done this before - is it even correct?
        this.templatingEngine = templatingEngine;
    }

    attached () {
        this.el.innerHTML = this.value;

        // NOTE: Without checking for this we get an endless loop of attached() calls
        if (!this.el.classList.contains('au-target')) {
            this.templatingEngine.enhance({
                element: this.el,
                container: Aurelia.container, // NOTE: I'm guessing here
                resources: Aurelia.resources, // NOTE: Same here, but I need all my global resources to be available inside the enhanced element too
                bindingContext: {} // NOTE: Not sure what to pass in here at all.. :/
            });
        }
    }
}

我是这样使用它的:

<div aurelia-enhance.bind="exampleContent"></div>

哪里exampleContent是从 API 调用中获取的字符串,可能如下所示:'<my-custom-element></my-custom-element><button my-custom-attribute="some-value">Log in</button>' .

最佳答案

你走在正确的道路上。有几件事需要考虑

  • bindingContext/overrideContext:这两个可以通过 Hook 自定义属性的 bind 生命周期来获取。因此,您将能够将它们传递给 enhance 指令(仅需要 bindingContext,但传递两者更好,有助于遍历作用域)。关于绑定(bind)上下文,99% 它将是您所在的 View 模型,但您始终可以使用不同的对象。在本例中,this(自定义属性 View 模型)是正确的。

  • 资源:取决于您希望 TemplateEngine.prototype.enhance 返回的 View 的资源范围如何。传递全局 Aurelia 实例的 resources 将不会产生它所在的自定义元素的本地资源范围。为了与属性注释的元素具有相同的资源,请 Hook 在属性的created生命周期中,将第一个参数存储为owningView。这是包含该属性的自定义元素的 View 。然后你可以通过owningView.resources访问其资源

  • 清理:TemplatedEngine.prototype.enhance返回一个View,您需要将此引用存储到detached在属性生命周期中也解除绑定(bind)

  • sanitizer

示例:https://gist.run/?id=9dd32bc8a772526ae527f593e26b275b

上面的要点是我为回答关于 Discourse 的另一个问题而制作的继承/增强的示例。您可以查看select-field以查看更多示例。这与您在那里所做的类似。

P/S:如果您对解决方案感到满意,也许可以考虑写一篇博文/文章或在 Aurelia Discourse 论坛上打开一个主题来帮助其他可能也遇到困难的人。


更新的示例:

import {Aurelia, inject, TemplatingEngine, DOM} from 'aurelia-framework';

@inject(Element, TemplatingEngine)
export class AureliaEnhanceCustomAttribute {
    constructor (el, aurelia, templatingEngine) {
        this.el = el;
        this.templatingEngine = templatingEngine;
    }

    // Custom attribute doesn't have its own view
    // Only the view of the custom element that owns it
    created(owningElementView, thisView) {
        this.owningElementView = owningElementView;
    }

    bind(bindingContext, overrideContext) {
        this.bindingContext = bindingContext;
        this.overrideContext = overrideContext;
    }

    attached () {
        this.el.innerHTML = this.value;

        // NOTE: Without checking for this we get an endless loop of attached() calls

        if (!this.el.classList.contains('au-target')) {
            this.dynamicView = this. this.templatingEngine.enhance({
                element: this.el,
                // we have two choices here, either the container of owning element, or this attribute
                // Lets go with the element, since it propbably has everything we need
                container: this.owningElementView.container,
                // the resources has information about its parent,
                // So we just need the resources of the element containing this attribute
                resources: this.owningElementView.resources,
                // Or this.bindingContext (same)
                bindingContext: this,
                // this helps travel up
                overrideContext: this.overrideContext
            });
        }
    }

    detached() {
        this.dynamicView.detached();
    }

    unbind() {
        if (this.dynamicView) {
            this.dynamicView.unbind();
        }
    }
}

关于javascript - 如何使用 Aurelia 动态增强 HTML,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47509171/

相关文章:

javascript - webview中的远程网站可以与Phonegap结合使用吗?

javascript - aurelia-cli CSS 资源加载失败

javascript - 使用自定义元素内容作为项目模板

aurelia - Aurelia 是否提供基于属性(property)原始值(value)的任何类型的 Dirty 指标

javascript - 如何保留自动完成中输入的内容

javascript - 我们如何使用 `mouseover` 和 `mouseout` 事件?

javascript - JavaScript 中事件处理和定时器服务的优先级是什么?

javascript - react 窗口滚动到底部

gulp - Aurelia-Bundler 无法获取 aurelia-router.js

action - Aurelia 在一次操作中两次改变状态