Ember handlebars顯示對象的鍵

2018-01-06 17:12 更新

在實際的開發(fā)過程中你很有可能需要顯示出對象數組的鍵或者值,如果你需要同時顯示出對象的鍵和值你可以使用{{#each-in}}標簽。
注意:each-in標簽是Ember 2.0才有的功能,之前的版本是無法使用這個標簽的,如果是2.0一下的版本會報錯:Uncaught Error: Assertion Failed: A helper named 'each-in' coulad not be found
準備工作:使用Ember CLI生成一個component,與此同時會生成一個對應的模板文件。
ember generate component store-categories
執(zhí)行上述命令得到下面的3個文件:

app/components/store-categories.js
app/templates/components/store-categories.hbs
tests/integration/components/store-categories-test.js

然后在app/router.js增加一個路由設置,在map方法里添加this.route('store-categories');;此時可以直接訪問http://localhost:4200/store-categories;

http://guides.emberjs.com/v2.0.0/templates/displaying-the-keys-in-an-object/

在組件中增加測試數據

// app/components/store-categories.js
import Ember from 'ember';


export default Ember.Component.extend({
    // https://guides.emberjs.com/v2.4.0/components/the-component-lifecycle/
    willRender: function() {
        //  設置一個對象到屬性“categories”上,并且設置到categories屬性上的對象結構是:key為字符串,value為數組
        this.set('categories', {
          'Bourbons': ['Bulleit', 'Four Roses', 'Woodford Reserve'],
          'Ryes': ['WhistlePig', 'High West']
        });
    }
));

willRender方法在組件渲染的時候執(zhí)行,更多有關組件的介紹會在后面章節(jié)——組件中介紹,想了解更多有關組件的介紹會在后面的文章中一一介紹,目前你暫且把組件當做是一個提取出來的公共HTML代碼。

有了測試數據之后我們怎么去使用each-in標簽遍歷出數組的鍵呢?



<ul>
  {{#each-in categories as |category products|}}
    <li>{{category}}
      <ol>
        {{#each products as |product|}}
          <li>{{product}}</li>
        {{/each}}
      </ol>
    </li>
  {{/each-in}}
</ul>

上述模板代碼中第一個位置參數category就是迭代器的鍵,第二個位置參數product就是鍵所對應的值。

為了顯示效果,在application.hbs中調用這個組件,組件的調用非常簡單,直接使用{{組件名}}方式調用。



{{store-categories}}

渲染后結果如下圖:

result

重渲染

{{each-in}}表達式不會根據屬性值變化而自動更新。上述示例中,如果你給屬性categories增加一個元素值,模板上顯示的數據不會自動更新。為了演示這個特性在組件中增加一個觸發(fā)屬性變化的按鈕,首先需要在組件類app/components/store-categories.js中增加一個action方法(有關action會在后面的章節(jié)介紹,暫時把他看做是一個普通的js函數),然后在app/templates/components/store-categories.hbs中增加一個觸發(fā)的按鈕。

import Ember from 'ember';


export default Ember.Component.extend({
    // willRender方法在組件渲染的時候執(zhí)行,更多有關組件的介紹會在后面章節(jié)——組件,中介紹
    willRender: function() {
        //  設置一個對象到屬性“categories”上,并且設置到categories屬性上的對象結構是:key為字符串,value為數組
        this.set('categories', {
          'Bourbons': ['Bulleit', 'Four Roses', 'Woodford Reserve'],
          'Ryes': ['WhistlePig', 'High West']
        });
    },
    actions: {
        addCategory: function(category) {
            console.log('清空數據');
            let categories = this.get('categories');
            // console.log(categories);
            categories['Bourbons'] = [];
            //  手動執(zhí)行重渲染方法更新dom元素,但是并沒有達到預期效果
            // 還不知道是什么原因
            this.rerender();
        }
    }
});





<ul>
  {{#each-in categories as |category products|}}
    <li>{{category}}
      <ol>
        {{#each products as |product|}}
          <li>{{product}}</li>
        {{/each}}
      </ol>
    </li>
  {{/each-in}}
</ul>


<button onclick={{action 'addCategory'}}>點擊清空數據</button>

但是很遺憾,即使是手動調用了rerender方法也沒辦法觸發(fā)重渲染,界面顯示的數據并沒有發(fā)生變化。后續(xù)找到原因后再補上?。?/p>

空數組處理

空數組處理與表達式{{each}}一樣,同樣是判斷屬性不是nullundefined、[]就顯示出數據,否則執(zhí)行else部分。

{{#each-in people as |name person|}}
  Hello, {{name}}! You are {{person.age}} years old.
{{else}}
  Sorry, nobody is here.
{{/each-in}}

可以參考上一篇的{{each}}標簽測試,這里不再贅述。
博文完整代碼放在Github(博文經過多次修改,博文上的代碼與github代碼可能又出入,不過影響不大?。绻阌X得博文對你有點用,請在github項目上給我點個star吧。您的肯定對我來說是最大的動力??!

以上內容是否對您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號
微信公眾號

編程獅公眾號