Ember.js - 拖放列表

时间:2012-10-09 11:32:29

标签: jquery ember.js

我使用this question的示例来创建我可以在Web应用程序上使用的拖放脚本。

在为自己的目的重新设计之后,我想要实现一些功能。 我已经为自己尝试了一段时间,但我还没有找到解决方案......

关联的jsfiddle:http://jsfiddle.net/BLLTH/

特点:

  • 应从可用列表中删除已添加的对象

  • 通过单击“x”-symbol删除添加的对象,将其放回可用列表

  • 对象的顺序必须与添加的顺序相同

任何想法? =)

模板:

<script type="text/x-handlebars" >  
<b>Available Objects</b><br /><br />
{{#each App.objectsController}}
    {{#view App.ObjectView contentBinding="this"}}
        {{view.content.name}}<br />
    {{/view}}
{{/each}}
<br /><br /><br /><br />
{{#view App.ObjectDropTarget dragContextBinding="App.objectsController.currentDragItem"}}
    {{#each App.cartController}}
        {{#view App.ObjectView contentBinding="this" class="single"}}                
            {{view.content.name}}
        {{/view}}
    {{/each}}  
{{/view}}

的javascript:

App = Em.Application.create({});
DragNDrop = Em.Namespace.create();
DragNDrop.cancel = function(event) {
    event.preventDefault();
    return false;
};
DragNDrop.Draggable = Em.Mixin.create({
    attributeBindings: 'draggable',
    draggable: 'true',
    dragStart: function(event) {
        var dataTransfer = event.originalEvent.dataTransfer;
        dataTransfer.setData('Text', this.get('elementId'));
    }
});
DragNDrop.Droppable = Em.Mixin.create({
    dragEnter: DragNDrop.cancel,
    dragOver: DragNDrop.cancel,
    drop: function(event) {
        event.preventDefault();
        return false;
    }
});
App.Object = Em.Object.extend({
    name: null,
    isAdded: null
});
App.ObjectView = Em.View.extend(DragNDrop.Draggable, {
    tagName: 'div',
    // .setDragImage (in #dragStart) requires an HTML element as the first argument
    // so you must tell Ember to create the view and it's element and then get the 
    // HTML representation of that element.  
    dragStart: function(event) {
        this._super(event);
        // Let the controller know this view is dragging
        this.setPath('content.isDragging', true);
        // Set the drag image and location relative to the mouse/touch event     
    },
    dragEnd: function(event) {
        // Let the controller know this view is done dragging
        this.setPath('content.isDragging', false);
    }
});
App.ObjectDropTarget = Em.View.extend(DragNDrop.Droppable, {
    tagName: 'div',
    classNames: ['dropTarget'],
    classNameBindings: ['cartAction'],
    // This will determine which class (if any) you should add to
    // the view when you are in the process of dragging an item.
    drop: function(event) {
        var viewId = event.originalEvent.dataTransfer.getData('Text'),
        view = Em.View.views[viewId];
        // Set view properties
        // Must be within `Ember.run.next` to always work
        Em.run.next(this, function() {
            view.setPath('content.isAdded', !view.getPath('content.isAdded'));
        });
        return this._super(event);
    }
});
App.objectsController = Em.ArrayController.create({
    content: [
    App.Object.create({
        name: "Object 1",
        isAdded: false
    }),
    App.Object.create({
        name: "Object 2",
        isAdded: false
    }),
    App.Object.create({
        name: "Object 3",
        isAdded: false
    }),
    App.Object.create({
        name: "Object 4",
        isAdded: false
    })
    ],
    currentDragItem: Em.computed(function(key, value) {
        return this.findProperty('isDragging', true);
    }).property('@each.isDragging').cacheable(),
    objectsInCart: Em.computed(function(key, value) {
        return this.filterProperty('isAdded', true);
    }).property('@each.isAdded').cacheable()
});
App.cartController = Em.ArrayController.create({
    content: Em.computed(function(key, value) {
        var cartItems = this.get('cartItems');
        if (!Em.empty(cartItems)) {
            // Sort desc by name
            return cartItems.sort(function(a, b) {
                 if ((a.get('name').toLowerCase()) < (b.get('name').toLowerCase())) return -1;
                 else return 1;
            });
        }
    }).property('cartItems').cacheable(),
    cartItemsBinding: 'App.objectsController.objectsInCart'
 });​

1 个答案:

答案 0 :(得分:3)

我已在http://jsfiddle.net/QE9CS/

为您实现了前两个功能

“已经添加的对象应该从可用列表中删除”是通过在阵列上创建另一个计算属性来实现的。

“通过单击”x“-symbol删除添加的对象,将其放回可用列表”只使用标准Ember {{action}}帮助程序。

编辑:

完整版http://jsfiddle.net/R9hnY/ 我已将isAdded转换为计算属性,该属性设置对象的值,并在适当的时间从cartController的内容中添加或删除对象。从而为cartController提供了一个有序的对象数组,以便从中进行渲染。