【问题标题】:angularjs - directive scope not cleaned up after binding to parent controller variableangularjs - 绑定到父控制器变量后未清理指令范围
【发布时间】:2014-09-08 12:36:45
【问题描述】:

我一直在构建一个指令,允许用户从建议列表中进行选择(水平布局(类似于自动完成小部件)。

指令(称为“建议”)通过绑定到控制器模型来获取其数据源

我希望用户能够通过按“enter”键或单击鼠标按钮从建议列表中进行选择。

从建议框中选择一个项目后,整个框应该消失(即支持建议的模型应该变成一个空数组)

鼠标点击效果非常好 - 但是按回车键会导致 scope.items 中的新项目保留

您可以通过加载下面的示例来复制我所说的内容:

1 - 点击“添加”按钮 - 这将在指令范围的项目数组中添加一个项目“是的”并更新 DOM

2 - 用鼠标单击任何选项 - ng-click 效果极佳,建议消失

3 - 刷新页面并重复步骤 1 - 然后使用左右箭头键并按 Enter。除了“是”之外的一切都消失了

<body ng-controller="Ctrl">
<button ng-click="add()">add</button>
<h2>select:</h2>
<suggestions items="items" on-select="alert(selection)"></suggestions>

Javascript:

var app = angular.module('app', []);

app.controller('Ctrl', function ($scope) {
    $scope.items = [
        {name: 'foo', code: 1},
        {name: 'bar', code: 2},
        {name: 'tar', code: 3}
    ];
    $scope.add = function () {
        $scope.items.push({name: 'yea', code: 4});
    };
    $scope.alert = function (selection) {
        console.log(selection);
        $scope.items = [];
    }
});

app.directive('suggestions', function () {
    return {
        scope: {
            items: "=",
            onSelect: "&onSelect"
        },
        link: function (scope, element) {
            var currentIdx = -1;
            scope.highlightItem = function (item) {
                element.find('.suggestion-container>span.suggestion-item').removeClass('suggestion-item-selected');
                $(item).addClass("suggestion-item-selected");
                currentIdx = $(item).index();
            };
            // handle left, right arrow navigation
            $(document).keydown(function (e) {
                var spanSize = element.find('span.suggestion-item').size();
                if (scope.items.length == 0 || currentIdx == -1)
                    return;
                switch (e.which) {
                    case 37: // left
                        currentIdx = Math.max(currentIdx - 1, 0);
                        break;
                    case 39: // right
                        currentIdx = Math.min(currentIdx + 1, spanSize - 1);
                        break;
                    default:
                        return;
                }
                scope.highlightItem(element.find(".suggestion-container>span.suggestion-item:eq(" + currentIdx + ")"));
            });
            // handle enter key
            $(document).keydown(function (e) {
                if (scope.items.length <= 0 || currentIdx == -1)
                    return;
                if (e.which == 13) {
                    scope.$apply(function () {
                        scope.onSelect({selection: scope.items[currentIdx]});
                        currentIdx = -1;
                    });
                }
            });
            // handle hover
            element.children('.suggestion-container').on('mouseenter', 'span.suggestion-item', function () {
                scope.highlightItem(this);
            });
            element.children('.suggestion-container').on('mouseleave', function () {
                element.find('.suggestion-container>span.suggestion-item').removeClass('suggestion-item-selected');
            });
        },
        restrict: 'E',
        template: '<div>{{items}}</div><div class="suggestion-container"><span ng-click="onSelect({selection:item})" class="suggestion-item" ng-repeat="item in items">{{item.name}}</span></div>'
    };
});

风格

     .suggestion-item-selected {
        background-color: #46b8da;
        cursor: pointer;
        color: #ffffff;
    }

    .suggestion-item {
        cursor: pointer;
        padding-left: 2px;
        padding-right: 2px;

        border-width: thin;
        border-style: solid;
        border-color: #777777;

        margin-right: 2px;}

谢谢,

【问题讨论】:

  • 紧跟在“e.which == 13”块之后或内部的console.out 表明指令范围的项目确实已重置为空数组“[]”,即绑定有效。但随后对访问指令的 scope.items 的调用显示“是的”被重新添加进来。几乎看起来 Ctrl 的 add() 方法被无意中再次调用了。

标签: javascript angularjs


【解决方案1】:

回答了我自己的问题:

原因是因为“add()”再次被调用。按“左”“右”也有聚焦“添加”按钮的副作用

【讨论】:

    猜你喜欢
    • 2019-04-01
    • 1970-01-01
    • 2016-05-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-01-24
    • 1970-01-01
    相关资源
    最近更新 更多