簡體   English   中英

聚合物數據綁定到屬性中的奇怪行為

[英]Strange behavior in Polymer data-binding to an attribute

使用Polymer 1.0,我試圖綁定到自定義元素的屬性,並僅顯示它。

自定義元素實際上是<iron-input>列表,具有添加和刪除按鈕。 我想將該列表中的任何更改反映給主持人。 它還具有minItemSize屬性,這意味着它至少具有這么多的元素。 因此,我向觀察者添加了一個檢查,並添加了其他元素,以防它低於此數字。

但是,當我綁定到保存列表的屬性時,事情就變得不同步了,我可以從ui中刪除所有輸入。

我有兩個<dyn-inputlist>元素。 在其中一個中,我不綁定到data屬性,在另一個中,我綁定。

第一個行為符合預期:單擊按鈕時添加和刪除。

另一個不起作用,因為您可以刪除所有輸入框。 即使數據本身已更新並充滿了其他項目,但由於某些原因,UI仍未反映出這一點。 (檢查元素的data屬性確實表明它具有正確的項目數)

我還希望,如果我在兩個dyn-inputlist元素上都設置了data={{myData}} ,它們總是顯示相同的內容。 但是,在每個組件上隨機按下添加/刪除按鈕會使它們不同步。

我想念什么嗎? 提前致謝。

index.html

<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <script src="bower_components/webcomponentsjs/webcomponents.js"></script>
    <link rel="import" href="components/dyn-inputlist.html"/>
</head>
<body>

<template is="dom-bind">
    <dyn-inputlist min-item-size="4"></dyn-inputlist>
    <div>{{mydata}}</div>
    <dyn-inputlist min-item-size="4" data="{{mydata}}"></dyn-inputlist>
</template>

</body>
</html>

dyn-inputlist.html

<link rel="import" href="../../polymer/polymer.html">
<link rel="import" href="../../iron-input/iron-input.html">

<dom-module id="dyn-inputlist">
    <template>
        <button on-click="removeItem">x</button>
        <button on-click="addItem">+</button>
        <template is="dom-repeat" items="{{data}}">
            <div>
                <span>{{index}}</span>
                <input is="iron-input" bind-value="{{item.content}}">
            </div>
        </template>
    </template>
    <script>
        Polymer({
            is: 'dyn-inputlist',
            properties: {
                minItemSize: {
                    type: Number,
                    notify: true,
                    value: 1
                },
                data: {
                    type: Array,
                    reflectToAttribute: true,
                    notify: true,
                    value: function () {
                        return []
                    }
                }
            },

            observers: ['_dataChanged(data.*)'],

            addItem: function (e) {
                this.unshift('data', {content: ""});
                this.reflectPropertyToAttribute('data')
            },

            removeItem: function (e) {
                this.shift('data');
                this.reflectPropertyToAttribute('data')
            },

            _dataChanged: function (e) {
                if (this.data != null) {
                    while (this.data.length < this.minItemSize) {
                        this.push('data', {content: ""})
                    }
                } else {
                    this.data = [{content: ""}];
                }
                this.reflectPropertyToAttribute('data');
            }

        });
    </script>
</dom-module>

編輯:這是實時代碼: http : //jsbin.com/poquke/1/edit?html,輸出

我已經對您的代碼進行了一些嘗試,我注意到如果將代碼包裝在異步函數中的已更改處理程序中,它將可以正常工作。 這解決了您描述的兩個問題。

_dataChanged: function (e) {
    this.async(function(){
        if (this.data != null) {

            while (this.data.length < this.minItemSize) {
                this.push('data', {content: ""})
            }
        } else {
            this.data = [{content: ""}];
        }
    });
}

對於這種行為,我沒有一個完美的解釋。 我認為這與Polymer處理變化觀察的方式有關。 每次您在更改后的處理程序中推送到數據數組時,實際上這都會更改數據,從而應再次觸發該處理程序。

如果您簡化,則不需要異步。

這是簡化的代碼,當您推入最小值時,它消除了對_dataChanged的重復調用,並允許Polymer的內置事件系統負責更新和通知其他元素。 函數:_createNewItem()用於創建對象。 這簡化了處理項目對象創建的位置。

http://jsbin.com/vemita/6/edit?html,output

鏈接和URL參考已從上面問題中的示例代碼更改為與Polyserve一起使用的聚合物元素和演示頁面標准一致。

我已經對您的原始代碼發表了評論,說明了每行應該或不應該出現的原因。 這包括更改_dataChanged的原因

http://jsbin.com/ponafoxade/1/edit?html,output

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM