I have a video model that stores 'likes' as a manytomany field with User.
e.g
class Video(models.Model):
...
likes = models.ManyToManyField(User)
....
When I create a ModelForm based on Video Likes is displayed as a dropdown with a list of all users. This is obviously ont what I want. I would like a particular user to be able to add/ remove their own name from this list. How do I instead display 'likes' as a checkbox and still have the form validate correctly?
In your model form, create a custom field for likes; when this field is checked, set likes to request.user.
from django import forms
class VideoForm(forms.ModelForm):
likes = forms.BooleanField(label='Mark as favorite?')
class Meta:
model = Video
This will render likes as a checkbox (the default widget for BooleanField).
I would write my own widget for this field (or replace the field with a boolean field): https://docs.djangoproject.com/en/dev/topics/forms/modelforms/#overriding-the-default-field-types-or-widgets
Related
I use the Django built-in models.User as basic user model, plus a model called Profile containing other user information, which has a one-to-one field relation to User.
class Profile:
user = models.OneToOneField(User)
nickname = models.CharField()
bio = models.CharField
I would like to use modelform for both model in the register view.
And in the register page, the html form literally contains field in both User and Profile, and this form will be submitted with all params in the POST, which means in the view function I have to handle two modelform with one POST params dictionary.
I have no idea how to implement this view function.
Related to foreign key fields in the Django Admin, the default display
element is a drop down list box containing all of the foreign key
items from the related model. I my app it will contain thousands of items and I am looking to change the admin interface and have it use a text box instead of the populated drop down.
Looking for textbox with add/edit icon next to it, so that we dont get populated values, we just directly add or edit.
Is there any way around to achieve it.
What you are looking for is raw_id_fields
class ArticleAdmin(admin.ModelAdmin):
raw_id_fields = ("newspaper", )
By default, Django’s admin uses a select-box interface (<select>)
for fields that are ForeignKey. Sometimes you don’t want to incur
the overhead of having to select all the related instances to display
in the drop-down.
raw_id_fields is a list of fields you would like to change into an
Input widget for either a ForeignKey or ManyToManyField:
NOTE: The raw_id_fields Input widget should contain a primary key if the field is a ForeignKey or a comma separated list of values if the field is a ManyToManyField. The raw_id_fields widget shows a magnifying glass button next to the field which allows users to search for and select a value:
You can read the docs here
You can try use custom Form and realize custom Widget on this form field. (I use for this desicion 3rd party library django_select2)
from django import forms
from django_select2.forms import ModelSelect2Widget
class KeyWidget(ModelSelect2Widget):
model = ModelToKey
search_fields = ['field__icontains']
def label_from_instance(self, obj):
return u'{}'.format(obj.field)
class CustomForm(forms.ModelForm):
class Meta:
model = ModelWithKey
fields = ('foreign_key_field')
widgets = {
'foreign_key_field': KeyWidget(attrs={'style': 'width:550px'}),
}
In also you can overload Form __init__ for customize queryset of objects for choosing in this field.
I have a user, admin and employee models, both employee and admin are related to the user model with a oneToOne field what i would like to do is in the admin form i have one field "user"
instead of having a drop down field with all users i would like to have a search box so that when i search for a specific user i find him and choose him to be an admin.
how?
i also tried to add user's fields to admin's form but i couldn't
i tried the inline thing, the parent_link in the admin's model... but i couldn't find a solution
Now i would like to minimise the search through the long users list by adding a search box to the field
I have solved this type of problem using django-ajax-selects package. Hope this will help you.
app/admin.py:
from ajax_select import register, LookupChannel
#register('users')
class UsersLookup(LookupChannel):
model = User
def get_query(self, q, request):
return self.model.objects.filter(username__icontains=q)
class EmployeeAdminForm(forms.ModelForm):
user = AutoCompleteSelectField('users', required=False,
help_text=None)
class Meta:
model = Employee
fields = '__all__'
settings.py
AJAX_LOOKUP_CHANNELS = {
'users' : {'model': 'auth.user', 'search_field': 'username'},
}
Use django's raw_id_fields. With that you can declare a foreign key object searchable.
What I am trying to achieve is:
User fills in form
User has the option to see a Preview if the content he just provided
User can accept the Preview or work on the form
My Problem is when the User clicks on Preview I can pass a Modelform with the data and show it to him. But since there are no fields in the he can just click on Accept to publish his Content. I need a form which is like a Deny/Accept Dialog but still related to the Model because i have to make changes before saving it to the database.
I tried to exclude all fields and also fields=None
I read this but the solution looks a little hacky. FormPreview is not what i want because it is a too different approach.
Is there any way to create a form that consists of just a button? I am also able to pass the data from view to view, so in worst case it hasnt to be a ModelForm.
I found a solution which fits my needs:
Just take any_field and make it a hidden field:
from django.forms import HiddenInput
class MyModelForm(ModelForm):
class Meta:
model = MyModel
widgets = {'any_field': HiddenInput(),}
Dont forget to exclude all the other fields.
I am terribly sorry for the crummy title to this question. I can't think of how to phrase it in a simple context.
I am making a simple photo gallery. The admin can create a gallery page and upload images to it. For each gallery I want there to be a single banner image from one of the photos. The Photo model has a CharField which will tell if its a banner or not. Is there a way to make the variable to allow only one 'B' for every photo that belongs to a Gallery?
You should define a unique_together variable for your class. If names of your fields are album and banner, you should add this line to Meta class of your model.
unique_together = (("album", "banner"),)
Django Documents, unique-together
And i think, using charfield for a boolean value isn't a correct choice. You should change your banner field as BooleanField.
Why don't you create a OneToOne field?
class Gallery(models.Model):
...
banner = models.OneToOneField(Photo)
this way, you have an unique relationship between a gallery and a photo.