删除后指令采取其他指令的数据

时间:2016-05-25 20:10:48

标签: javascript angularjs angularjs-directive angularjs-scope

编辑:感谢SimonSchüpbach,我能够通过更改模板来解决问题。请参阅最终解决方案。

让我们在前言中说我们是Angular的软中间人的初学者。

在我们的一个项目中,我们使用angularjs 1.4.x和ng-cart(https://github.com/snapjay/ngCart)。它工作得很好,但后来我们遇到了客户的要求,产生了新的奇怪问题。

我们将fsCounter作为指令添加到购物车页面,以便用户可以添加或删除商品。这一切都很好,但用户也可以选择从购物车视图中删除项目。删除按预期工作但它似乎影响了取代它的项目的范围。

让我说清楚一下: 假设我们的购物车页面中有2个产品,它会显示类似的内容

Product_1     {price}   {counter} {total} delete_btn
Product_2     {price}   {counter} {total} delete_btn

每个fsCounter都是自己的范围

return {
    restrict: "A",
    scope: {
        value: "=value",
        index: "=index"
    },
    link: //other logic

然而,当我们在视觉上和指令中删除第一个项目时,数据似乎发生了变化。所以我们的第二行现在将继承第一行的计数器。 指令的数据如下:

Product_1:
itemId:3,
quantity:2,
{other data}

Product_2:

itemId:8,
quantity:5,
{other data}

但是一旦我们删除第一个指令(我们获取范围,删除DOM元素,销毁范围),第二个指令现在将拥有这些数据:

Product_2:
itemId:3,
quantity:2,
{other data}

以下是模板代码:

<div class="unItem" ng-repeat="item in ngCart.getCart().items track by $index">
    <div class="photo"><img src="{[{ item.getImage() }]}" alt=""></div>
    <div class="details">
        <h3>{[{ item.getName() }]} <span>{[{ item.getPrice() | currency:$}]}</span></h3>
        <md-select ng-model="attributes" placeholder="Attribut" class="select-attribut" ng-show="item.hasAttributes()" ng-change="item.updateSelected(attributes)">
            <md-option ng-repeat="attr in item.getAttributes()" ng-selected="attr == item.getSelected()" ng-value="attr">{[{ attr }]}</md-option>
        </md-select>
    </div>

    <div class="quantity">
        <div fs-counter-dynamic value="itemQuantity"
                            data-min="1"
                            data-max="999"
                            data-step="1"
                            data-addclass="add-quantity"
                            data-width="130px"
                            data-itemid="{[{ item.getId() }]}"
                            data-editable
                            ng-model="itemQuantity"
                            name="quantity" id="quantity-{[{ item.getId() }]}",
                            index="{[{ item.getId() }]}"

                            ></div>
    </div>
    <div class="total">Total : {[{ item.getTotal() | currency }]}</div>
    <div class="delete"><a ng-click="ngCart.removeItemById(item.getId());"></a></div>
</div>

这是正常行为吗?有没有办法强制指令保留自己的数据?根据我的理解,每个指令都有自己的范围,所以我认为发生的是,当我们删除第一个时,它会将数据保存在某种类型的数组中,表示“指令1数据是:”,当我们删除第一个指令,第二个指令成为第一个指令。

所以基本上,我们做错了什么或者无论如何重新映射数据?

希望它足够清楚, 谢谢!

编辑:添加了HTML代码

Edit2:答案: 新的FsCounter模板如下所示:

            <div fs-counter-dynamic value="item._quantity"
                            data-min="1"
                            data-max="999"
                            data-step="1"
                            data-addclass="add-quantity"
                            data-width="130px"
                            data-itemid="{[{ item.getId() }]}"
                            data-editable
                            ng-model="item._quantity"
                            name="quantity" id="quantity{[{ item.getId() }]}"
                            ></div>

1 个答案:

答案 0 :(得分:2)

您知道ng-repeat,那么您没有这样的问题

<div ng-repeat="product in products">
   <fs-counter index="product.index" value="product.value"></fs-counter>
</div>

并在您的控制器中

$scope.products = [
   {index:1, value:"Cola"},
   {index:2,,value:"Fanta"}
]

删除您必须执行的元素

$scope.products.splice(0,1);

修改

我建议在ng-repeat内使用的项目中保存所有必要的数据。您的问题是,您将数组中的数据与$scope中的其他数据混合在一起。您的指令可能会发生$watch次更改,但如果您使用ng-repeat进行更改,则所有内容都会自动完成。

$scope.products = [
   {index:1, name:"Cola", price:1.50, image:"your/path.png", attributes:{...}},
   {index:2, name:"Fanta", price:1.40,  image:"your/path.png"}
]

然后在你的HTML中

<div class="unItem" ng-repeat="item in ngCart.products track by $index">
    <div class="photo"><img ng-src="item.image" alt=""></div>
    <div class="details">
        <h3>{{item.name}} <span>{{item.price | currency}}</span></h3>
    </div>

    <div class="quantity">
        <div fs-counter-dynamic value="item.quantity"
                            data-min="1"
                            data-max="999"
                            data-step="1"
                            data-addclass="add-quantity"
                            data-width="130px"
                            data-itemid="item.index"
                            data-editable
                            ng-model="item.quantity"
                            name="quantity" id="{{'quantity-' + $index}}",
                            index="item.index"

                            ></div>
    </div>
    <div class="total">Total : {{ item.price * item.quantity | currency }}</div>
    <div class="delete"><a ng-click="ngCart.removeItemById(item.index);"></a></div>
</div>