如何在Aurelia的自定义属性中访问点击处理程序?

时间:2017-02-28 07:47:42

标签: aurelia aurelia-binding

是否可以访问自定义属性中元素的点击处理程序?我想实现这样的目标:

<button click.delegate="callSomeMethod()" log-click>Click</button>

其中log-click是一个自定义属性,用于包装click调用并使用某种行为对其进行修饰。

一个非工作的例子,但显示了我想要实现的目标:

class LogClickCustomAttribute {
  @bindable click;
  attached() {
    let originalClick = this.click;
    this.click = () => {
      console.log('decoreated!');
      return originalClick();
    };
  }
}

我想要实现的真实用例是一个禁用自身的按钮,直到click处理程序返回的promise解析为止。 Like promise-btn for Angular

<button click.delegate="request()" disable-until-request-resolves>Click</button>

4 个答案:

答案 0 :(得分:3)

我不知道是否可以在自定义属性中访问标准HTML元素的属性,例如button。但是,如果为按钮创建自定义元素,这很容易:

GistRun:https://gist.run/?id=d18de213112c5f21631da457f218ca3f

自定义-button.html

<template>
  <button click.delegate="onButtonClicked()">Test</button>
</template>

自定义-button.js

import {bindable} from 'aurelia-framework';

export class CustomButton {
  @bindable() onClicked;

  onButtonClicked() {
    if (typeof this.onClicked === 'function') {
      this.onClicked();
    }
  }
}

<强>登录click.js

import {inject} from 'aurelia-framework';
import {CustomButton} from 'custom-button';

@inject(CustomButton)
export class LogClickCustomAttribute {
  constructor(customButton) {
    this.customButton = customButton;
  }

  bind() {
    let originalOnClicked = this.customButton.onClicked;

    this.customButton.onClicked = () => {
      console.log('decorated!');
      return originalOnClicked();
    };
  }
}

<强> app.html

<template>
  <require from="./custom-button"></require>
  <require from="./log-click"></require>
  <custom-button on-clicked.call="test()" log-click>Test</custom-button>
</template>

<强> app.js

export class App {
  test() {
    console.log("The button was clicked.");
  }
}

答案 1 :(得分:1)

鉴于Aurelia如何附加事件处理程序,您将无法完全按照自己的意愿行事。

话虽这么说,您可以使用如下所示的简单自定义属性向控制台注销事件:

<强>登录event.js

import { inject } from 'aurelia-framework';

@inject(Element)
export class LogEventCustomAttribute {
  constructor(el) {
    this.el = el;
  }

  attached() {
    const eventName = this.value || 'click';

    let handler = (e) => console.log('event logged', e);

    if (this.el.addEventListener) { // DOM standard
      this.el.addEventListener(eventName, handler, false)
    } else if (this.el.attachEvent) { // IE
      this.el.attachEvent(eventName, handler)
    }
  } 
} 

答案 2 :(得分:1)

您可以将事件处理程序添加到自定义属性的构造函数中的元素。

    @inject(Element)
    export class ClickThisCustomAttribute {

        constructor(element) {
            element.addEventListener('click', () => {
            this.doSomething();
            });
        }
    }

答案 3 :(得分:0)

与我做出的承诺点击最接近的事情是:

import { autoinject, bindable } from "aurelia-framework";

@autoinject
export class PromiseClickCustomAttribute {
  @bindable({ primaryProperty: true }) delegate: Function;

  constructor(private element: Element) {
    this.element.addEventListener("click", async () => {
      this.element.classList.add("disabled");
      this.element.classList.add("loading");
      await this.delegate();
      this.element.classList.remove("disabled");
      this.element.classList.remove("loading");
    })
  }
}
<div class="ui container">
    <h2>Promise Click</h2>
    <div class="ui input">
        <button class="ui button" promise-click.bind="alertLater">Toast Later</button>
    </div>
</div>
alertLater = () => {
    return new Promise((resolve) => {
      setTimeout(() => {
        alert("Promise Resolved");
        resolve();
      }, 3000);
    });
  }