我一直在寻找一种方法,允许用户轻松更改表单集中条目的顺序。我发现a StackOverflow question解决了这个问题,接受的答案引用了Django Snippet,它使用JQuery工具来拖放条目。这很漂亮很酷,但我有'额外'条目的问题。如果修改了“额外”条目然后拖动,我会在提交时收到错误:
(1048, "Column 'order' cannot be null")
我相信Django会将'额外'条目分开,因为它们必须插入而不是更新。所以重新排序可能会让事情变得混乱。有没有办法使这项工作,还是有其他建议重新排序和/或添加新条目?
编辑:添加了一些相关的代码摘录。我正在管理员中尝试这个,正如代码段所示。不过,我最终会把它放在我自己的页面中。
models.py:
class Section(models.Model):
section_id = models.AutoField(primary_key=True)
section_name = models.CharField(max_length=135)
score_order = models.IntegerField()
def __unicode__(self):
return self.section_name
class Meta:
db_table = u'section'
ordering = [u"score_order"]
class Chair(models.Model):
chair_id = models.AutoField(primary_key=True)
member = models.ForeignKey(Member, null=True, blank=True,
limit_choices_to={'current_member': True})
section = models.ForeignKey(Section)
description = models.CharField(max_length=135)
order = models.IntegerField(blank=True, null=True)
def __unicode__(self):
return "%s - %s" % (self.description, self.member)
class Meta:
db_table = u'chair'
ordering = (u'section', u'order')
admin.py
class SectionForm(forms.ModelForm):
model = Section
class Media:
js = (
'/scripts/jquery.js',
'/scripts/ui.core.js',
'/scripts/ui.sortable.js',
'/scripts/section-sort.js',
)
class ChairInline(admin.StackedInline):
model = Chair
admin.site.register(Section,
inlines = [ChairInline],
form = SectionForm,
)
答案 0 :(得分:2)
我找到了自己的解决方案。该片段为具有非空主键值的每一行设置顺序。但额外的行有一个空的主键,我相信他们必须留空,让Django知道它们是要插入而不是更新。我修改了函数以检查其他字段是否为空(幸运的是,我只有一对)以及主键:
jQuery(function($) {
$('div.inline-group').sortable({
items: 'div.inline-related',
handle: 'h3:first',
update: function() {
$(this).find('div.inline-related').each(function(i) {
if ($(this).find('input[id$=chair_id]').val() ||
$(this).find('select[id$=member]').val() ||
$(this).find('select[id$=description]').val()) {
$(this).find('input[id$=order]').val(i+1);
}
});
}
});
$('div.inline-related h3').css('cursor', 'move');
$('div.inline-related').find('input[id$=order]').parent('div').hide();
});
这对我有用。我可以通过向表单中添加隐藏字段来改进它,只要行上的任何字段被修改就会被设置。但在这一点上我仍然是一个jQuery n00b,所以这样做。如果有人有更好的想法,请随时发表评论或添加其他答案。
答案 1 :(得分:1)
我在其中一个应用中执行可排序的formset。我使用这个jQuery拖放插件:
http://www.isocra.com/2008/02/table-drag-and-drop-jquery-plugin/
我将插件的onDrop事件绑定到一个重置所有“order”字段值的函数。
此外,我将初始数据传递给formset,因此formset的额外“order”字段总是有一个值,如果没有可用的javascript - 用户将无法重新排序行,但他们可以编辑并在没有您描述的空错误的情况下发布更改。