2015-10-02 45 views
0

的jsfiddle:https://jsfiddle.net/ghstahl/09tL1ku7/聚合物1.0觀察員觀看對象路徑沒有被觸發,即使數據已經改變

<script src="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/webcomponentsjs/webcomponents-lite.js"></script> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/polymer/polymer.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-styles/paper-styles.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-styles/color.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-styles/default-theme.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-ripple/paper-ripple.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-behaviors/paper-inky-focus-behavior.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-checked-element-behavior/iron-checked-element-behavior.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-toggle-button/paper-toggle-button.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-input/paper-input.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-button/paper-button.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-flex-layout/iron-flex-layout.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-flex-layout/classes/iron-flex-layout.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-flex-layout/classes/iron-shadow-flex-layout.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-dropdown-menu/paper-dropdown-menu.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-menu-button/paper-menu-button.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-a11y-keys-behavior/iron-a11y-keys-behavior.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-behaviors/iron-control-state.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-behaviors/iron-button-state.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-icons/iron-icons.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-icon/iron-icon.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/iron-selector/iron-selector.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-item/paper-item.html"> 
<link rel="import" href="https://cdn.rawgit.com/download/polymer-cdn/1.1.3/lib/paper-behaviors/paper-button-behavior.html"> 
<dom-module id="pingo-toggle"> 
<style> 
    .line { 
     margin-bottom: 40px; 
    } 
    .line span { 
     margin-left: 24px; 
    } 
</style> 
<template> 
    <div class="line"> 
     <paper-toggle-button checked={{singleToggle.data}}></paper-toggle-button> <span>{{singleToggle.label}}</span> 
<span>{{computeBooleanToString(singleToggle.data)}}</span> 

    </div> 
    <template is="dom-repeat" items="{{_workingArray}}"> 
     <div class="line"> 
      <paper-toggle-button checked={{item.value.data.checked}}></paper-toggle-button> 
<span>{{item.value.label}}</span> 
<span>{{item.value.id}}</span> 
<span>{{computeBooleanToString(item.value.data.checked)}}</span> 

     </div> 
    </template> 
</template> 
<script> 
    (function() { 
     Polymer({ 
      is: 'pingo-toggle', 
      properties: { 

       singleToggle: { 
        type: Object, 
        notify: true 
       }, 

       toggleItems: { 
        type: Object, 
        notify: true, 
        observer: '_toggleItemsChanged' 
       }, 
      }, 
      _toggleItemsChanged: function(newValue, oldValue) { 
       if (this.toggleItems !== undefined) { 
        this._workingArray = this._toArray(this.toggleItems); 
       } 
      }, 
      _toArray: function(obj) { 
       var index = 0; 
       var thisElement = this; 
       this._arrayData = Object.keys(obj).map(function(key) { 
        var id = "item_" + index; 
        ++index; 
        var val = {}; 
        val.data = obj[key]; 
        val.label = "hi:" + key; 
        val.data = obj[key]; 
        val.id = id; 
        val.original = obj.key; 
        return { 
         name: key, 
         value: val 
        }; 
       }); 
       return this._arrayData; 
      }, 
      computeBooleanToString: function(a) { 
       return a === true ? 'true' : 'false'; 
      } 
     }); 
    })(); 
</script> 
</dom-module> 
<dom-module id="pingo-toggle-container"> 
<style> 
</style> 
<template> 
    <pingo-toggle single-toggle={{_singleToggle}} toggle-items={{_toggleItems}}></pingo-toggle> 
    <paper-item>{{_singleToggleHello}}</paper-item> 
    <paper-item>{{_toggleItemsHello}}</paper-item> 
</template> 
<script> 
    (function() { 
     Polymer({ 
      is: 'pingo-toggle-container', 
      properties: { 
       _singleToggleHello: { 
        type: String, 
        notify: true, 
        value: "Well Hello There" 
       }, 
       _toggleItemsHello: { 
        type: String, 
        notify: true, 
        value: "Hi there from many" 
       }, 

       _singleToggle: { 
        type: Object, 
        notify: true, 
        value: { 
         label: "Single Toggle", 
         data: true 
        } 
       }, 
       _toggleItems: { 
        type: Object, 
        notify: true, 
        value: { 
         a: { 
          label: "a Toggle2", 
          checked: true 
         }, 
         b: { 
          label: "a Toggle2", 
          checked: false 
         } 
        } 
       } 
      }, 

      // Observers 
      ///////////////////////////////////////////////////////// 
      observers: ['_toggleItemsChanged(_toggleItems.*)', '_singleToggleChanged(_singleToggle.*)'], 
      // Smart check. only fire if we change state. 
      _singleToggleChanged: function(changeRecord) { 
       var thisElement = this; 

       this._singleToggleHello = this.computeBooleanToString(this._singleToggle.data) + Math.random() + changeRecord.path; 
       console.log("_singleToggle in pingo-toggle-container changed:" + changeRecord.path); 

      }, 
      _toggleItemsChanged: function(changeRecord) { 
       var thisElement = this; 

       this._toggleItemsHello = "_workingToggleItemsChanged fired" + Math.random() + changeRecord.path; 

       console.log("pingo-toggle-container notWorking:" + changeRecord.path); 

      }, 
      computeBooleanToString: function(a) { 
       return a === true ? 'true' : 'false'; 
      }, 

      ready: function(e) { 

      } 
     }); 
    })(); 
</script> 
</dom-module> 
<pingo-toggle-container></pingo-toggle-container> 

方案:父元素擁有的數據對象。父元素將數據對象的部分傳遞給綁定到對象中的值的子元素。當兒童更改該值時,由於它們具有對象引用,所以直接在父級擁有的主數據對象中更改數據。

問題:「_toggleItemsChanged(_toggleItems *)」閃光一次,在第一次,但從來沒有再次閃光,即使在_toggleItems數據已經改變。

證明:在pingo-toggle-container元素中;

  • 在_singleToggleChanged和_toggleItemsChanged處放置斷點。
    • 這兩個都在啓動。
  • 來回切換'hi:a'和'hi:b'。
    • 沒有任何火災。
  • 所以我把'hi:a'和'hi:b'都設爲True。
  • 'Single Toggle'會觸發,所以我切換並且我的斷點命中。
    • 評估this._toggleItems;
    • 嗯,你們都設置爲true。您可以將'hi:a'和'hi:b'切換爲false並重做測試。現在它們都被設置爲假。

你爲什麼不火的觀察員:[ '_toggleItemsChanged(_toggleItems )', '_singleToggleChanged(_singleToggle)'],用於數據的變化?

預計:我想_toggleItemsChanged函數被調用與_toggleItems.a.checked的changeRecord.path或repectively _toggleItems.a.checked。

回答

0

我不知道我是否可以理解你的榜樣,但我相信你正試圖觀察更深層次的財產變化。它不會工作。

觀察員無法看得更深。只有在使用時,他們纔會觀察到第一級屬性更改。如果您需要更深入,則需要觀察其他路徑,如_toggleItems.a。等。

+0

這是有道理的,因爲這是我也注意到了。我可能不得不從孩子那裏發起一個事件來表明深度路徑被改變了。 –