2017-10-04 112 views
1

我是hyperHTML的新手,并正在尝试使用它。这是我的问题。如何为重复的模板元素添加事件处理程序。这里是我的web组件:重复元素上的​​事件处理程序

import css from './component.css'; 
 
import isJson from '../utils/isJson.js'; 
 
const hyper = hyperHTML; 
 

 
class IdxAdminTab extends HTMLElement { 
 
    constructor() { 
 
    super(); 
 
    this.attachShadow({mode: 'open'}); 
 
    } 
 

 
    attributeChangedCallback(name, oVal, nVal) { 
 
    if (name === 'tabs' && isJson(nVal)) { 
 
     this.tabs = JSON.parse(nVal); 
 
     this.tabs.forEach((tab) => { 
 
     tab.number = parseInt(tab.number, 10).toLocaleString(); 
 
     }); 
 
     this.updateView(); 
 
    } 
 
    } 
 

 
    clearSelections() { 
 
    this.tabs.forEach((tab) => { 
 
     tab.selected = false; 
 
    }); 
 
    } 
 

 
    connectedCallback() { 
 
    this.updateView(); 
 
    } 
 

 
    currentlySelected() { 
 
    return this.tabs.find((tab) => tab.selected); 
 
    } 
 

 
    disconnectedCallback() { 
 
    
 
    } 
 

 
    tabSelected(evn) { 
 
    
 
    } 
 

 
    updateView() { 
 
    hyper(this.shadowRoot)` 
 
     <style>${css}</style> 
 
     <div id="tab-container"> 
 
     ${this.tabs.map(tab => ` 
 
     <div class="${tab.selected ? 'selected' : ''}" id="${tab.id}" onclick="${this.selectedTab}"> 
 
      <div class="name">${tab.name}</div> 
 
      <div class="number">${tab.number}</div> 
 
     </div> 
 
     `)} 
 
     </div> 
 
     `; 
 
    } 
 

 
    static get observedAttributes() { 
 
    return ['tabs']; 
 
    } 
 
} 
 

 
customElements.define('idx-admin-tab', IdxAdminTab); 
 

 
export { IdxAdminTab };

我想在反复选项卡中添加一个单击处理程序和注册tabSelected的处理程序。我已经添加了点击事件处理抛出一个未捕获的语法错误:

(function(event){[object HTMLElement] 
 
})

回答

1

你的地图返回纯字符串,所以你的点击处理程序不指向一个功能,而是一个字符串表示你的功能。

 ${this.tabs.map(tab => ` 
     <div class="${tab.selected ? 'selected' : ''}" id="${tab.id}" onclick="${this.selectedTab}"> 
      <div class="name">${tab.name}</div> 
      <div class="number">${tab.number}</div> 
     </div> 
     `)} 

使用

hyperHTML.wire(tab)`<div>...</div>` 

代替。 CodePen

1

有两个与您的代码的小问题:

  1. 要返回如前所述
  2. 你是没有约束力的处理程序只是一个字符串

当你使用模板字面它容易忘记那些只是字符串。 您需要返回应始终指向同一选项卡的DOM节点(或导线)。

我假设tab.id是唯一的,我用它们作为绑定到组件本身的标识符。 这是一个更好的版本:

class IdxAdminTab extends HTMLElement { 
    constructor() { 
    super(); 
    this.selectedTab = this.selectedTab.bind(this); 
    this.render = hyper(this.attachShadow({mode: 'open'})); 
    this.updateView(); 
    } 

    selectedTab(e) { 
    console.log('tab selected'); 
    } 

    updateView() { 
    this.render` 
     <style>${css}</style> 
     <div id="tab-container"> 
     ${this.tabs.map(tab => hyper(this, `:${tab.id}`)` 
     <div class="${tab.selected ? 'selected' : ''}" id="${tab.id}" onclick="${this.selectedTab}"> 
      <div class="name">${tab.name}</div> 
      <div class="number">${tab.number}</div> 
     </div> 
     `)} 
     </div>`; 
    } 

} 

正如你可以看到,你甚至可以使用{mode: 'closed'}而作为渲染特性,一旦分配shadowRoot。

现在你有一个完整的工作组件。

但是,hyperHTML自带一个名为HyperHTMLElement的自定义元素帮助程序,查看其实用程序,也许它会让您的生活更轻松。

相关问题