28👍
from django.contrib import admin
from django import forms
class MyModel(MyBaseModel):
stuff = models.CharField('Stuff', max_length=255, default=None)
class Meta:
proxy = True
class MyModelForm(forms.ModelForm):
MY_CHOICES = (
('A', 'Choice A'),
('B', 'Choice B'),
)
stuff = forms.ChoiceField(choices=MY_CHOICES)
class MyModelAdmin(admin.ModelAdmin):
fields = ('stuff',)
list_display = ('stuff',)
form = MyModelForm
admin.site.register(MyModel, MyModelAdmin)
See: https://docs.djangoproject.com/en/dev/ref/forms/fields/#choicefield
7👍
You don’t need a custom form.
This is the minimum you need:
# models.py
from __future__ import unicode_literals
from django.db import models
class Photo(models.Model):
CHOICES = (
('hero', 'Hero'),
('story', 'Our Story'),
)
name = models.CharField(max_length=250, null=False, choices=CHOICES)
# admin.py
from django.contrib import admin
from .models import Photo
class PhotoAdmin(admin.ModelAdmin):
list_display = ('name',)
admin.site.register(Photo, PhotoAdmin)
- [Django]-Django can we select related a field on a prefetch related model?
- [Django]-Difference between ForeignKey(User, unique=True) and OneToOneField
- [Django]-Using subdomains in django
5👍
You need to override the form the ModelAdmin
is going to use:
class MyForm(forms.ModelForm):
stuff = forms.CharField('Stuff', max_length=255, choices=MY_CHOICES, default=None)
class Meta:
model = MyModel
fields = ('stuff', 'other_field', 'another_field')
class MyModelAdmin(admin.ModelAdmin):
fields = ('stuff',)
list_display = ('stuff',)
form = MyForm
If you need your choices to be dynamic, maybe you could do something similar to:
class MyForm(forms.ModelForm):
stuff = forms.CharField('Stuff', max_length=255, choices=MY_CHOICES, default=None)
def __init__(self, stuff_choices=(), *args, **kwargs):
# receive a tupple/list for custom choices
super(MyForm, self).__init__(*args, **kwargs)
self.fields['stuff'].choices = stuff_choices
and in your ModelAdmin
‘s __init__
define what MY_CHOICES
is going to be and assign the form instance there instead:
Good luck! 🙂
- [Django]-Byte Ranges in Django
- [Django]-Django test app error – Got an error creating the test database: permission denied to create database
- [Django]-Django TypeError: get() got multiple values for keyword argument 'invoice_id'
5👍
You can override formfield_for_choice_field()
that way you don’t need to create a new form.
class MyModelAdmin(admin.ModelAdmin):
def formfield_for_choice_field(self, db_field, request, **kwargs):
if db_field.name == 'status':
kwargs['choices'] = (
('accepted', 'Accepted'),
('denied', 'Denied'),
)
if request.user.is_superuser:
kwargs['choices'] += (('ready', 'Ready for deployment'),)
return super().formfield_for_choice_field(db_field, request, **kwargs)
- [Django]-Django Templating: how to access properties of the first item in a list
- [Django]-How to update manytomany field in Django?
- [Django]-Django: how to startapp inside an "apps" folder
0👍
in Gerard’s answer, if you keep :
def __init__(self, stuff_choices=(), *args, **kwargs):
then when you will try to add new model from admin, you will always get ‘This field is required.’ for all required fields.
you should remove stuff_choices=()
from initialization:
def __init__(self,*args, **kwargs):
- [Django]-Django – comparing old and new field value before saving
- [Django]-Check if OneToOneField is None in Django
- [Django]-How can I restrict Django's GenericForeignKey to a list of models?
0👍
You need to think of how you are going to store the data at a database level.
I suggest doing this:
- Run this pip command:
pip install django-multiselectfield
-
In your models.py file:
from multiselectfield import MultiSelectField MY_CHOICES = (('item_key1', 'Item title 1.1'), ('item_key2', 'Item title 1.2'), ('item_key3', 'Item title 1.3'), ('item_key4', 'Item title 1.4'), ('item_key5', 'Item title 1.5')) class MyModel(models.Model): my_field = MultiSelectField(choices=MY_CHOICES)
-
In your settings.py:
INSTALLED_APPS = ( 'django.contrib.auth', 'django.contrib.contenttypes', 'django.contrib.sessions', 'django.contrib.sites', 'django.contrib.admin', #.....................# 'multiselectfield', )
-
Watch the MAGIC happen!
Source:
- [Django]-Python / pip, how do I install a specific version of a git repository from github (what is the correct url)?
- [Django]-AttributeError: module 'html.parser' has no attribute 'HTMLParseError'
- [Django]-Can't run the server on Django (connection refused)
0👍
Below a solution that works immediately with Postgres’ special ArrayField
:
# models.py
class MyModel(models.Model):
class Meta:
app_label = 'appname'
name = models.CharField(max_length=1000, blank=True)
ROLE_1 = 'r1'
ROLE_2 = 'r2'
ROLE_3 = 'r3'
ROLE_CHOICES = (
(ROLE_1, 'role 1 name'),
(ROLE_2, 'role 2 name'),
(ROLE_3, 'role 3 name'),
)
roles = ArrayField(
models.CharField(choices=ROLE_CHOICES, max_length=2, blank=True),
default=list
)
# admin.py
class MyModelForm(ModelForm):
roles = MultipleChoiceField(choices=MyModel.ROLE_CHOICES, widget=CheckboxSelectMultiple)
@admin.register(MyModel)
class MyModelAdmin(admin.ModelAdmin):
form = MyModelForm
list_display = ("pk", "name", "roles")
(Django 2.2)
- [Django]-Django testing stored session data in tests
- [Django]-Django 1.5 index page
- [Django]-Django datefield filter by weekday/weekend