在尝试了一些方法后,我搜索了高低,以便找到一个看似简单的问题的好方法。
我有一个可排序的章节列表,我正在使用平均来为流星应用程序进行jquery可排序的工作。拖放可排序部分很容易(使用平均值),但应用章节的正确(整数)顺序非常棘手。
常见的应用程序是应用于目录的章节编号。
我尝试了什么:
随着章节数量的增加,这会变得复杂。我觉得解决方案太复杂了。
chaptersList html:
<template name="chaptersList">
<div id="items">
{{#each publishedChapters}}
{{> chapterItem}}
{{/each}}
</div><!--items-->
</template>
chaptersList js:
Template.chaptersList.rendered = function() {
this.$('#items').sortable({
stop: function(e, ui) {
// get the dragged html element and the one before
// and after it
el = ui.item.get(0)
before = ui.item.prev().get(0)
after = ui.item.next().get(0)
if(!before) {
//if it was dragged into the first position grab the
// next element's data context and subtract one from the order
newOrder = 1;
} else if(!after) {
//if it was dragged into the last position grab the
// previous element's data context and add one to the order
newOrder = Blaze.getData(before).order + 1
}
else
//else take the average of the two orders of the previous
// and next elements
newOrder = (Blaze.getData(after).order +
Blaze.getData(before).order)/2
newOrder = Math.round(newOrder)
//update the Items' orders
Chapters.update({_id: Blaze.getData(el)._id}, {$set: {order: newOrder}})
}
})
}
Template.chaptersList.helpers({
publishedChapters: function() {
return Chapters.find({ published: true },
{ sort: {order: 1}
});
},
items: function() {
return Chapters.find({}, {
sort: {order: 1 }
})
}
});
chapterItem html:
<template name="chapterItem">
<div class="item">
<h3 class="headroom-10 chapter-title-small">
<a href="{{pathFor 'showChapter'}}">{{title}}</a>
</h3>
<p class="chapter-text">{{#markdown}}{{chapterTease}}{{/markdown}}</p>
{{#if ownChapter}}
<a href="{{pathFor 'editChapter'}}" class="chapter-text">Edit</a>
<span class="delete">
<a href="#">Delete</a>
</span>
{{/if}}
</div>
</template>
感谢您的宝贵见解。
答案 0 :(得分:1)
我经历了同样的问题,并且在我的案例中让它干净利落的技巧是从排序中取消可排序的操作,让Blaze在项目被删除后接管。否则,可排序的排序和Blaze排序最终会互相摔跤。
我将新订购的商品保存为一个批次,但这不一定是必需的。
Template.builder.rendered = function(){
var self = this;
this.$("ol.sortable").sortable({
axis: "y",
containment: "ol.sortable",
tolerance: "pointer",
update: function(event, ui){
var
items = $(this).find("li"),
picks = _.map(items, function(item){
var obj = Blaze.getData(item);
obj.position = $(item).index() + 1;
return obj;
});
self.$('ol.sortable').sortable('cancel');
Meteor.call(
"orderPicks",
team,
picks,
function(error, result){}
);
}
});
}
在服务器上:
Meteor.methods({
orderPicks: function(team, picks){
Teams.update(team,
{ $set: {picks: picks} }
);
return true;
}
});
我相信我从另一个SO线程中选择了这个;我不记得了。无论如何,它可以无缝地适用于一组中等大小的物品。
HTML:
<template name="builder">
<ol class="builder sortable">
{{#each team.picks}}
<li>{{position}}. {{name}}</li>
{{/each}}
</ol>
</template>
答案 1 :(得分:0)
这个答案是对@jeremy上述对话的跟进,使嵌套数组方法适用于单个文档。
它目前无法正常运行,但通过在此处发布,我希望能够获得洞察力,让它发挥作用并提供另一种解决方案。
现在,拖放项目时排序顺序不会改变。如果您能看到原因,请告诉我,或者您也可以编辑答案:
将ID添加到li:
chapterId: function() {
return Chapters.findOne(this._id)._id
}
HTML:
<li class="item headroom-20" id="{{chapterId}}">
可排序的JS:
Template.chaptersList.rendered = function(){
var self = this;
this.$("ol.items").sortable({
axis: "y",
containment: "ol.items",
tolerance: "pointer",
update: function(event, ui){
var items = $(".items").find("li");
var publishedChaptersCount = items.length;
var sortedIds = [];
for (var i = 0; i < publishedChaptersCount; i++) {
var obj = $(items[i]).attr('id');
sortedIds.push(obj);
}
self.$('ol.items').sortable('cancel');
Meteor.call(
"chapterOrderUpdate",
sortedIds,
function(error, result){}
);
}
});
}
流星法:
Meteor.methods({
chapterOrderUpdate: function(sortedIds){
var publishedChaptersCount = sortedIds.length;
for (var i = 0; i < publishedChaptersCount; i++) {
var chapterId = sortedIds[i];
Chapters.update({_id: chapterId}, { $set: { order: i+1 } })
}
}
});