示例任务应用程序拖放 [英] Sample task application with drag and drop
问题描述
app.js
App = Em.Application.create();
App.IndexRoute = Em.Route.extend({
model:function(){
return {
newTasks:Em.A([
{id:1,name:Task 1},
{id:2,name:Task 2},
{id:3,name:Task 3}
]),
inProgressTasks:Em.A([
{id:4,name:Task 4},
{id:5,name:Task 5}
]),
doneTasks:Em.A([
{id:6,name:Task 6}
])
};
}
});
App.IndexController = Em.Controller.extend({
actions:{
moveTask:function(taskID,from,to){
var model = this。 get('model');
var task = model [from] .findProperty('id',parseInt(taskID,10));
model [to] .pushObject(task);
model [from] .removeObject(task);
}
}
});
App.TaskContainerComponent = Em.Component.extend({
classNames:['col-xs-4','taskContainer'],
isOverdrop:false,
classNameBindings:['isOverdrop:isOverdrop'],
setOverdropIfNotOriginator:function(event,valueToSet){
var data = JSON.parse(event.dataTransfer.getData('text / data' ));
if(data.stage!== this.get('stage')){
this.set('isOverdrop',valueToSet);
}
} ,
dragEnter:function(event){
this.setOverdropIfNotOriginator(event,true);
},
dragLeave:function(event){
this.setOverdropIfNotOriginator(event,false);
},
dragOver:function(event){
this.setOverdropIfNotOriginator(event,true);
event.preventDefault();
},
drop:function(event){
var data = JSON.parse(event.dataTransfer.getData('text / data' ));
如果(data.stage === this.get('stage'))返回;
// from:data.stage,to:this.get('stage')
this.sendAction('action',data.id,data.stage,this.get ('阶段'));
this.set('isOverdrop',false);
}
});
App.DragTaskComponent = Em.Component.extend({
dragStart:function(event){
var data = {id:this.get('task.id') ,stage:this.get('stage')};
event.dataTransfer.setData('text / data',JSON.stringify(data));
}
});
index.html
<!DOCTYPE html>
< html>
< head>
< meta charset =utf-8>
< title>迷你Scrumboard< / title>
< link href =http://getbootstrap.com/dist/css/bootstrap.css =stylesheettype =text / css/>
< link rel =stylesheethref =css / normalize.css>
< link rel =stylesheethref =css / style.css>
< / head>
< body>
< script type =text / x-handlebarsdata-template-name =index>
< div class =contents>
< div class =row>
{{task-container containerTitle =Newstage =newTaskstasks = model.newTasks
action =moveTaskon =drop}}
{{task-container containerTitle =In Progressstage =inProgressTasks
tasks = model.inProgressTasks action =moveTaskon =drop}}
{{task-container containerTitle =Donestage =doneTasks tasks = model.doneTasks
action =moveTaskon =drop}}
< / div>
< br>
< br>
< / div>
< / script>
<! - 属性:task,stage - >
< script type =text / x-handlebarsid =components / drag-task>
< div class =taskdraggable =true>
{{task.name}}
< / div>
< / script>
<! - 属性:containerTitle,stage,tasks - >
< script type =text / x-handlebarsid =components / task-container>
< h3> {{containerTitle}}< / h3>
{{#each task in tasks}}
{{drag-task task = task stage = stage}}
{{/ each}}
< / script>
< script src =js / libs / jquery-1.10.2.js>< / script>
< script src =js / libs / handlebars-1.1.2.js>< / script>
< script src =js / libs / ember-1.5.1.js>< / script>
< script src =js / app.js>< / script>
<! - 激活测试运行器,添加?test查询字符串参数 - >
< script src =tests / runner.js>< / script>
< / body>
< / html>
我的本地框上的工作完全正常,但是在jsbin上出错。 p::::::::: //emberjs.jsbin.com/movex/4/edit?html,css,js,output
我猜这个问题与从拖放中解析输出,但是没有线索与此相关。
任何帮助将不胜感激...
更新:JSBin版本甚至在FF在Mac上,但不是Safari或Chrome ...:(
它不工作的原因是因为非常意外的方式,拖放规格工作,问题是在$ $ c> drag , dragEnter
, dragLeave
, dragOver
和 dragEnd
事件dragTransfer数据处于保护模式,根据规范意味着什么。
数据本身不可用,不能添加新数据。
看起来好像Mozilla行使了一些常识,并没有按照规范执行拖放操作,这就解释了为什么在Firefox中为您而工作,而不在其他地方。
得到你的js bin工作我向您的索引控制器添加了一个 theData
元素,并根据该值设置并获取JSON值。
这是工作版本。 http://emberjs.jsbin.com/dasonona/1/edit
app.js
App = Em.Application.create();
App.IndexRoute = Em.Route.extend({
model: function(){
return {
newTasks: Em.A([
{id: 1, name: "Task 1"},
{id: 2, name: "Task 2"},
{id: 3, name: "Task 3"}
]),
inProgressTasks: Em.A([
{id: 4, name: "Task 4"},
{id: 5, name: "Task 5"}
]),
doneTasks: Em.A([
{id: 6, name: "Task 6"}
])
};
}
});
App.IndexController = Em.Controller.extend({
actions: {
moveTask: function(taskID, from, to){
var model = this.get('model');
var task = model[from].findProperty('id', parseInt(taskID, 10));
model[to].pushObject(task);
model[from].removeObject(task);
}
}
});
App.TaskContainerComponent = Em.Component.extend({
classNames: ['col-xs-4', 'taskContainer'],
isOverdrop: false,
classNameBindings: ['isOverdrop:isOverdrop'],
setOverdropIfNotOriginator: function(event, valueToSet){
var data = JSON.parse(event.dataTransfer.getData('text/data'));
if(data.stage !== this.get('stage')) {
this.set('isOverdrop', valueToSet);
}
},
dragEnter: function(event) {
this.setOverdropIfNotOriginator(event, true);
},
dragLeave: function(event){
this.setOverdropIfNotOriginator(event, false);
},
dragOver: function(event){
this.setOverdropIfNotOriginator(event, true);
event.preventDefault();
},
drop: function(event) {
var data = JSON.parse(event.dataTransfer.getData('text/data'));
if(data.stage === this.get('stage')) return;
// from: data.stage, to: this.get('stage')
this.sendAction('action', data.id, data.stage, this.get('stage'));
this.set('isOverdrop', false);
}
});
App.DragTaskComponent = Em.Component.extend({
dragStart: function(event) {
var data = { id: this.get('task.id'), stage: this.get('stage')};
event.dataTransfer.setData('text/data', JSON.stringify(data));
}
});
index.html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Mini Scrumboard</title>
<link href="http://getbootstrap.com/dist/css/bootstrap.css" rel="stylesheet" type="text/css" />
<link rel="stylesheet" href="css/normalize.css">
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<script type="text/x-handlebars" data-template-name="index">
<div class="contents">
<div class="row">
{{ task-container containerTitle="New" stage="newTasks" tasks=model.newTasks
action="moveTask" on="drop"}}
{{ task-container containerTitle="In Progress" stage="inProgressTasks"
tasks=model.inProgressTasks action="moveTask" on="drop" }}
{{ task-container containerTitle="Done" stage="doneTasks" tasks=model.doneTasks
action="moveTask" on="drop" }}
</div>
<br>
<br>
</div>
</script>
<!-- Properties: task, stage -->
<script type="text/x-handlebars" id="components/drag-task">
<div class="task" draggable="true">
{{task.name}}
</div>
</script>
<!-- Properties: containerTitle, stage, tasks -->
<script type="text/x-handlebars" id="components/task-container">
<h3>{{containerTitle}}</h3>
{{#each task in tasks}}
{{drag-task task=task stage=stage}}
{{/each}}
</script>
<script src="js/libs/jquery-1.10.2.js"></script>
<script src="js/libs/handlebars-1.1.2.js"></script>
<script src="js/libs/ember-1.5.1.js"></script>
<script src="js/app.js"></script>
<!-- to activate the test runner, add the "?test" query string parameter -->
<script src="tests/runner.js"></script>
</body>
</html>
I have this working perfectly fine on my local box, but it is errorring out on jsbin.
http://emberjs.jsbin.com/movex/4/edit?html,css,js,output
I am guessing that the issue has to do with parsing the output from the drag and drop, but have no clue where to go with this.
Any help would be greatly appreciated...
UPDATE: The JSBin version even works fine on the FF on the Mac, but not on Safari or Chrome... :(
The reason it was not working is because of the very unexpected way that the drag and drop specifications work. The problem is that in the drag
, dragEnter
, dragLeave
, dragOver
and dragEnd
events the dragTransfer data is in protected mode. Which again according to the spec means.
the data itself is unavailable and no new data can be added.
It seems as though Mozilla exercised some common sense and didn't implement drag and drop in compliance with the spec. Which explains why it was working in Firefox for you, but nowhere else.
To get your jsbin working I added a theData
element to your index controller and did the setting and getting of the JSON values against that.
Here is the working version. http://emberjs.jsbin.com/dasonona/1/edit
这篇关于示例任务应用程序拖放的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!