In my last post I described how to move items up and down from the admin interface.

To achieve that, I wrote a model field called “OrderingField”.

Since Django 1.0 released yesterday, I decided to port my application. And not to my suprise, my custom field didn’t work anymore, since it is based on “oldforms” which have been abandoned in 1.0.

So here is a new, much neater, way to accomplish this:

You need a model with a integer field that represents the order:

class MyModel(models.Model):
	order = models.IntegerField(editable=False)
	#...

If you don’t know how to add a model to the admin interface and customise its look, please read this.

Because the integer field is’t editable, it won’t appear in the add/change form. Since 1.0 you can add a custom ModelForm to the admin site. Mine looks like this:

class MyModelAdminForm(forms.ModelForm):
	move = forms.CharField(widget=forms.Select)
	move.required = False
	move.widget.choices=(
			(models.BLANK_CHOICE_DASH[0]),
			('FIRST', 'First'),
			('UP', 'Up'),
			('DOWN', 'Down'),
			('LAST', 'Last'),
		)

	class Meta:
		model = MyModel

“move” is a field that doesn’t exist in MyModel. This will add a new field to the form, that “isn’t bound” to a model field.

Now add that to the ModelAdmin:

class MyModelAdmin(admin.ModelAdmin):
	form = MyModelAdminForm

	def save_model(self, request, obj, form, change):
		obj.save()
		move = form.cleaned_data['move']
		obj.move(move)

I also extended the save_model method to do something with the input data in the “move” field. First save the model, and then call the objects move method.

I described in my previous post how this method roughly should look like.

Finally register the model to the admin site:

admin.site.register(MyModel, MyModelAdmin)

Happy django’ing

UPDATE: I added this to djangosnippets.org.