Angular Js拖放 - 将$ index传递给Directive

时间:2015-06-15 01:51:46

标签: javascript angularjs drag-and-drop

我成功地在Angular JS中实现了拖放功能。

基本理念就像将城市与国家匹配。我可以拖动城市并进入“国家/地区”框。但是,丢弃的项目会反映在所有国家/地区框中。但由于我使用了ng-repeat,我发现很难获取指令中的$ index值。

我的实施是here



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

module.directive('draggable', function () {
    return {
        restrict: 'A',
        link: function (scope, element, attrs) {
            element[0].addEventListener('dragstart', scope.handleDragStart, false);
            element[0].addEventListener('dragend', scope.handleDragEnd, false);
        }
    }
});

module.directive('droppable', function () {
    return {
        restrict: 'A',
        link: function (scope, element, attrs) {
            element[0].addEventListener('drop', scope.handleDrop, false);
            element[0].addEventListener('dragover', scope.handleDragOver, false);
        }
    }
});

module.controller("MainController", function ($scope) {
    $scope.questions = [{
        city: "Delhi",
        country: "India"
    }, {
        city: "Tokyo",
        country: "Japan"
    }, {
        city: "Doha",
        country: "Qatar"
    }, ];

    $scope.answers = [];

    $scope.handleDragStart = function (e) {
        this.style.opacity = '0.9';
        e.dataTransfer.setData('text/plain', this.innerHTML);
    };

    $scope.handleDragEnd = function (e) {
        this.style.opacity = '1.0';
    };

    $scope.handleDrop = function (e) {
        e.preventDefault();
        e.stopPropagation();
        var dataText = e.dataTransfer.getData('text/plain');
        $scope.$apply(function () {
            $scope.answers[id].country = $scope.questions[$index].country
            $scope.answers[id].city = dataText;
        });
        console.log($scope.answers[$index]);
    };

    $scope.handleDragOver = function (e) {
        e.preventDefault();
        e.dataTransfer.dropEffect = 'move';
        return false;
    };
});

.container {
    width: 100%;
    border: 1px solid #CCC;
    box-shadow: 0 1px 5px #CCC;
    border-radius: 5px;
    font-family: verdana;
    margin: 25px auto;
}
.left {
    float: left;
}
.right {
    float : right;
}
.container header {

    padding: 10px;
}
.container h1 {
    padding: 0;
    margin: 0;
    font-size: 16px;
    font-weight: normal;
    text-shadow: 0 1px 2px white;
    color: #888;
    text-align: center;
}
.container section {
    padding: 10px 30px;
    font-size: 12px;
    line-height: 300%;
    color: #333;
}
.default {
    clear : both;
}

<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<body ng-app="my-app">
    <div ng-controller="MainController">
         <h3>Match the following</h3>

        <div class="container">
            <header>
                 <h1>Drag and drop a city into the corresponding Country box</h1>

            </header>
            <section>
                <div draggable="true" ng-repeat="qs in questions">{{qs.city}}</div>
            </section>
        </div>
        <div class="container" ng-repeat="qs in questions">
            <header>
                 <h1>{{qs.country}}</h1>

            </header>
            <section droppable="true"> <span>{{droppedCity}}</span> 
            </section>
        </div>
        <div class="default"> <pre>{{items|json}}</pre>
        </div>
    </div>
</body>
&#13;
&#13;
&#13;

任何帮助都会有用。 感谢。

1 个答案:

答案 0 :(得分:0)

您的代码存在很多问题。我建议研究官方文档和一些与自定义指令和隔离范围相关的SO问题。以下是一些更新的代码,其中包含许多更改和updated fiddle

<body ng-app="my-app">
<div ng-controller="MainController">
     <h3>Match the following</h3>

    <div class="container">
        <header>
             <h1>Drag and drop a city into the corresponding Country box</h1>

        </header>
        <section>
            <div draggable="true" ng-repeat="qs in questions" index="{{$index}}">{{qs.city}}</div>
        </section>
    </div>
    <div class="container" ng-repeat="qs in questions">
        <header>
             <h1>{{qs.country}}</h1>

        </header>
        <section droppable="true" index="{{$index}}"> <span>{{droppedCity}}</span> 
        </section>
    </div>
    <div class="default"> <pre>{{items|json}}</pre>
    </div>
</div>

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

module.directive('draggable', function () {
    return {
        restrict: 'A',
        scope: {
            index: '@'
        },

        link: function (scope, element, attrs) {
            element[0].addEventListener('dragstart', scope.handleDragStart, false);
            element[0].addEventListener('dragend', scope.handleDragEnd, false);
        },
        controller: function($scope) {
            $scope.handleDragStart = function (e) {
                console.log('starting drag', $scope.index);
                this.style.opacity = '0.9';
                e.dataTransfer.setData('text/plain', this.innerHTML);
            };

            $scope.handleDragEnd = function (e) {
                this.style.opacity = '1.0';
            };
        }
    };
});

module.directive('droppable', function () {
    return {
        restrict: 'A',
         scope: {
            index: '@'
        },
        link: function (scope, element, attrs) {
            element[0].addEventListener('drop', scope.handleDrop, false);
            element[0].addEventListener('dragover', scope.handleDragOver, false);
        },
        controller: function($scope) {
            $scope.handleDrop = function (e) {
                e.preventDefault();
                e.stopPropagation();
                var dataText = e.dataTransfer.getData('text/plain');
                $scope.$parent.answers.push({country: $scope.$parent.questions[$scope.index].country});
                $scope.$parent.answers.push({city: $scope.$parent.questions[$scope.index].city});                    
            };

            $scope.handleDragOver = function (e) {
                e.preventDefault();
                e.dataTransfer.dropEffect = 'move';
                console.log('dragging over', $scope.$parent.questions[$scope.index].country);
                return;
            };
        }
    };
});

module.controller("MainController", function ($scope) {
    $scope.questions = [{
        city: "Delhi",
        country: "India"
    }, {
        city: "Tokyo",
        country: "Japan"
    }, {
        city: "Doha",
        country: "Qatar"
    }, ];

    $scope.answers = [];
});