Gidon / Bıyık - Bir nesnenin özellikleri arasında dolaşmak için yerleşik bir yol var mı?


216

Soru başlığının dediği gibi, bir nesne özellikleri arasında döngü yapmanın bir bıyık / gidon yolu var mı?

Böylece

var o = {
  bob : 'For sure',
  roger: 'Unknown',
  donkey: 'What an ass'
}

Sonra şablon motorunda eşdeğer bir şey yapabilir miyim

for(var prop in o)
{
    // with say, prop a variable in the template and value the property value
}

?

Yanıtlar:


448

Gidon 1.0rc1'den beri yerleşik destek

Bu işlev için destek Handlebars.js'e eklenmiştir , bu nedenle harici yardımcılara gerek yoktur.

Bu nasıl kullanılır

Diziler için:

{{#each myArray}}
    Index: {{@index}} Value = {{this}}
{{/each}}

Nesneler için:

{{#each myObject}}
    Key: {{@key}} Value = {{this}}
{{/each}}

Yalnızca hasOwnPropertytesti geçen özelliklerin numaralandırılacağını unutmayın.


2
@Rafi: Veri yapınızı bilmeden bunun pek mantıklı olduğu söylenemez.
Jon

3
@Rafi: {{this.title}} demek istemiyor musunuz?
nevyn

2
@qodeninja: Basit: yukarıdaki örneklerde yer alan değerlerle - aynı şekilde {{#each this}}. Terim seçiminiz de kafa karıştırıcıdır (bir nesneyi "en üst düzey" yapan, diğerini ne yapmaz? Tam olarak "önceden tanımlanmış" anahtarlar nelerdir? Vb), bu yüzden bu kavramları tekrar gözden geçirmek isteyebilirsiniz.
Jon

1
yanlış değilse o zaman sadece v1.1.0 ile bu kullanılabilir, ama büyük cevap teşekkürler.
Renars Sirotins

2
Bunu yalnızca belirli bir özellik beyaz listesi için nasıl yaparsınız?
Marco Prins

70

Aslında bir yardımcı olarak uygulanması oldukça kolaydır:

Handlebars.registerHelper('eachProperty', function(context, options) {
    var ret = "";
    for(var prop in context)
    {
        ret = ret + options.fn({property:prop,value:context[prop]});
    }
    return ret;
});

Sonra şöyle kullanın:

{{#eachProperty object}}
    {{property}}: {{value}}<br/>
{{/eachProperty }}

2
İyi görünüyor, döngü prototip özellikleri üzerinde yineleme yapmamanız için döngü içine bir hasOwnProperty denetimi eklemeniz mi gerekiyor?
monkeyboy

@Ben için harika bir çözüm. Herhangi birinin bunu Ember ile kullanmaya çalışması durumunda, çözümün çalışmasını sağlamak için aşağıdaki cevabım bölümüne bakın.
flynfish

27

DÜZENLEME: Gidonların artık bunu gerçekleştirmek için yerleşik bir yolu var; bkz seçilen cevabı yukarıda. Sade Bıyık ile çalışırken, aşağıdakiler hala geçerlidir.

Bıyık, bir dizideki öğeleri yineleyebilir. Bu yüzden, Bıyık'ın çalışabileceği şekilde biçimlendirilmiş ayrı bir veri nesnesi oluşturmanızı öneririm:

var o = {
  bob : 'For sure',
  roger: 'Unknown',
  donkey: 'What an ass'
},
mustacheFormattedData = { 'people' : [] };

for (var prop in o){
  if (o.hasOwnProperty(prop)){
    mustacheFormattedData['people'].push({
      'key' : prop,
      'value' : o[prop]
     });
  }
}

Şimdi, Bıyık şablonunuz şuna benzer:

{{#people}}
  {{key}} : {{value}}
{{/people}}

"Boş Listeler" bölümüne bakın: https://github.com/janl/mustache.js


1
Yine de bazı ek alt özellikleri geçmek gerekir gibi öneri ile gidiş sona erdi. Yardım için teşekkürler!
Ben

Çok teşekkürler, fikriniz bana başka bir alternatif bakış gününü kurtardı. Bu satır anahtar mustacheFormattedData = {'people': []};
Matt

Bunu bir dizi "o" nesnesi ile nasıl yaparsınız?
red888

4

Bu @ Ben'in cevabı Ember ile kullanılmak üzere güncellenmiştir ... Ember.getbağlam, bir String olarak iletildiğinden kullanmanız gerektiğini unutmayın .

Ember.Handlebars.registerHelper('eachProperty', function(context, options) {
  var ret = "";
  var newContext = Ember.get(this, context);
  for(var prop in newContext)
  {
    if (newContext.hasOwnProperty(prop)) {
      ret = ret + options.fn({property:prop,value:newContext[prop]});
    }
  }
  return ret;
});

Şablon:

{{#eachProperty object}}
  {{key}}: {{value}}<br/>
{{/eachProperty }}

Teşekkürler @flynfish. bağlam Ember bir dizedir ?? öyle görünüyor ki ... biraz tuhaf.
Ben

Evet, Ember için yeni olduğumdan ve hala yolumu bulmaya çalıştığımdan emin değilim.
flynfish

1

@ Amit'in yanıtı iyi çünkü hem Bıyıkta hem de Gidonda çalışacak.

Sadece gidon çözümleri ile ilgili olarak, birkaç tane gördüm ve en iyi https://gist.github.com/1371586 adresindekieach_with_key blok yardımcısını beğendim .

  • Öncelikle onları yeniden yapılandırmanıza gerek kalmadan nesne değişmezlerini yinelemenizi sağlar ve
  • Anahtar değişken dediğin şey üzerinde kontrol sağlar. Birçok başka çözümler ile adlandırılmış nesne tuşlarını kullanarak konusunda dikkatli olmak zorunda 'key', ya da 'property'vb

Güzel bulmak. Sadece diğer okuyuculara bir uyarı: bu özünde "key_value" yardımcısının bir hatası var. Nasıl düzeltileceği ile ilgili yorumları okuyun.
sirentian

0

Ben'in çözümü için teşekkürler, kullanım durumum sadece belirli alanları sırayla görüntülemek için

nesne ile

Kod:

    handlebars.registerHelper('eachToDisplayProperty', function(context, toDisplays, options) {
    var ret = "";
    var toDisplayKeyList = toDisplays.split(",");
    for(var i = 0; i < toDisplayKeyList.length; i++) {
        toDisplayKey = toDisplayKeyList[i];
        if(context[toDisplayKey]) {
            ret = ret + options.fn({
                property : toDisplayKey,
                value : context[toDisplayKey]
            });
        }

    }
    return ret;
});

Kaynak nesne:

   { locationDesc:"abc", name:"ghi", description:"def", four:"you wont see this"}

Şablon:

{{#eachToDisplayProperty this "locationDesc,description,name"}}
    <div>
        {{property}} --- {{value}}
    </div>
    {{/eachToDisplayProperty}}

Çıktı:

locationDesc --- abc
description --- def
name --- ghi

0

Bu, verileri önceden biçimlendirmeden ve bunun yerine oluşturma sırasında almadan mustacheJS için yardımcı bir işlevdir.

var data = {
    valueFromMap: function() {
        return function(text, render) {
            // "this" will be an object with map key property
            // text will be color that we have between the mustache-tags
            // in the template
            // render is the function that mustache gives us

            // still need to loop since we have no idea what the key is
            // but there will only be one
            for ( var key in this) {
                if (this.hasOwnProperty(key)) {
                    return render(this[key][text]);
                }
            }
        };
    },

    list: {
        blueHorse: {
            color: 'blue'
        },

        redHorse: {
            color: 'red'
        }
    }
};

Şablon:

{{#list}}
    {{#.}}<span>color: {{#valueFromMap}}color{{/valueFromMap}}</span> <br/>{{/.}}
{{/list}}

Çıktılar:

color: blue
color: red

(sıra rastgele olabilir - bu bir harita) İstediğiniz harita öğesini biliyorsanız bu yararlı olabilir. Sadece falsi değerlerine dikkat edin.


-1

1.0.beta.6Gidonların eski sürümünü kullanıyordum , 1.1 - 1.3 sırasında bir yere bu işlevsellik eklendiğini düşünüyorum, bu yüzden 1.3.0'a güncelleme sorunu çözdü, işte kullanım:

Kullanımı:

{{#each object}}
  Key {{@key}} : Value {{this}}
{{/people}}
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.