I've found a solution to render tags registered in taggit models as choices list by doing:
from taggit.models import Tag
class BlogPost(models.Model):
tags = models.ForeignKey(Tag, on_delete=models.CASCADE, default='')
(i changed something in taggit folder i guess, .... i forgot but i works without any problem )
but i would like to change label name ("Tags" by default)
i tried in forms.py:
imports ...
class PostForm(forms.ModelForm):
tag = [(i, i) for i in Tag.objects.all()]
tags = forms.ChoiceField(label='another label name', choices=tag )
class Meta:
model = BlogPost
fields = ('tags',)
it shows the result i expected but when i save or POST it return a form validation error 'Cannot assign "u'tag name'": "BlogPost.tags" must be a "Tag" instance.'
so can someone handle this and thanks
you need to use pk as key
class PostForm(forms.ModelForm):
tag = [(i.pk, i.title) for i in Tag.objects.all()]
# ^^^^^
tags = forms.ChoiceField(label='another label name', choices=tag )
and may be better solution is to use ModelChoiceField
tags = forms.ModelChoiceField(queryset=Tag.objects.all(), empty_label=None)
Related
I would like to do the exact same thing as this has the only difference that the default text disappears when the user enters text
name = models.CharField(max_length=16, default="default value")
Exemple :
i'm using this method for my form
class Device(models.Model):
phone_regex = RegexValidator(regex=r'^[0-9]{10}$', message="Error: Format 0611223344")
name = models.CharField(max_length=16, default="default value")
[....cut code....]
class DeviceForm(ModelForm):
class Meta:
model = Device
fields = ['name']
Looks like you want a placeholder value on your field. Add the following code to your Form class.
name = forms.CharField(
label='Name',
widget=forms.TextInput(attrs={'placeholder': 'Type name here...'})
)
The way to do this is to use Django Forms' widget properties. Here, you can change the HTML that will be rendered client-side.
class YourForm(ModelForm):
class Meta:
model = YourModel
fields = ('your', 'fields')
widgets = {
'form_field': forms.TextInput(attrs={'placeholder': "Search Content..."}
}
The above code will render an input tag for the field form_field, and add an HTML attribute of placeholder with the value of Search Content...
I've one app named Question where i defined two models Question and Alternative in models.py as follows :
class Question(models.Model):
question = models.CharField(max_length=255, blank=False, null=False)
chapter = models.ForeignKey(Chapter, on_delete=models.CASCADE)
rating = models.IntegerField(default=1)
class Alternative(models.Model):
alternative = models.CharField(max_length=255, blank=False, null=False)
question = models.ForeignKey(Question, on_delete=models.CASCADE)
i've made a Custom form AlternativeForm where i've created a extra field which i want to appear in my Alternative forms as well as Question admin view where Alternative fields will appear in the inline view But the extra field value will not be saved in DB(cause i want to do some manual operations with the value of that fields). my forms.py is as follows:
class AlternativeForm(forms.ModelForm):
extra_field = forms.BooleanField(required=False)
def save(self, commit=True):
extra_field = self.cleaned_data.get('extra_field', None)
# will do something with extra_field here...
return super(AlternativeForm, self).save(commit=commit)
class Meta:
model = Alternative
fields = '__all__'
and in my admin.py i've made an inline relationship between them as follows:
class AlternativeInline(admin.TabularInline):
form = AlternativeForm
model = Alternative
#admin.register(Question)
class QuestionAdmin(admin.ModelAdmin):
inlines = [AlternativeInline,]
#admin.register(Alternative)
class AlternativeAdmin(admin.ModelAdmin):
model = Alternative
form = AlternativeForm
I'm getting AttributeError: Unable to lookup 'extra_field' on Alternative or AlternativeInline in this case. I want to show those extra field in the Inline view of Questionapps admin view. Is there any way to do it or what is wrong in my current approach.
Thanks.
I found the solution when speculating this post. One should define the label field in the custom field like the following to avoid such error AttributeError: Unable to lookup 'extra_field' on Alternative or AlternativeInline.
class AlternativeForm(forms.ModelForm):
extra_field = forms.BooleanField(label='is_answer', required=False)
def save(self, commit=True):
# extra_field = self.cleaned_data.get('extra_field', None)
# ...do something with extra_field here...
return super(AlternativeForm, self).save(commit=commit)
To have the extra fields in the admin:
class YourModelAdmin(admin.ModelAdmin):
form = YourModelForm
fieldsets = (
(None, {
'fields': ('other fields here', 'extra_field',),
}),
)
This is the model for icons displayed on top of a text, they get a name and the icon.
from django.db import models
from django.utils.translation import ugettext as _
from django.conf import settings
class SomeSortOfIcon(models.Model):
name = models.CharField(max_length=200,
verbose_name=_('Icon Name'),
help_text=_('This value will be shown to the user.'))
image = models.ForeignKey(
getattr(settings, 'WAGTAILIMAGES_IMAGE_MODEL', 'wagtailimages.Image'),
on_delete=models.PROTECT,
related_name='+',
verbose_name=_('Icon'),
)
def __str__(self):
return self.name
class Meta:
verbose_name = _('Icon')
verbose_name_plural = _('Icons')
This is the code for the Block that's going to be added into a streamfield onto the page.
from django.db import models
from django import forms
from django.utils.translation import ugettext as _
from wagtail.wagtailcore import blocks
from xxx.models import SomeSortOfIcon
class SomeSortOfIconChooserBlock(blocks.ChoiceBlock):
## PROBLEM HERE, where do I get the choices from?
choices = tuple([(element.name, element.image) for element in SomeSortOfIcon.objects.all()])
target_model = SomeSortOfIcon
class SomeBox(blocks.StructBlock):
headline = blocks.TextBlock(required=True)
some_icon = SomeSortOfIconChooserBlock(label='Icon', required=True)
info_box_content = blocks.RichTextBlock(label='Content', required=True)
class Meta:
template = 'blocks/some_box.html'
icon = 'form'
label = _('Some Box')
So, I do get the Block added to the streamfield and for the icon I want a dropdown menu with the choices from the icon model. It's supposed to display the name and when you chose one it is going to be automatically added by name into the html.
I get the dropdown menu, but it is empty. I tried to use the choices attribute, but I don't know how to connect it to the other model.
Can anyone please help? It'd be much appreciated.
You can do that by inheriting from the ChooserBlock.
class SomeSortOfIconChooserBlock(blocks.ChooserBlock):
target_model = SomeSortOfIcon
widget = forms.Select
class Meta:
icon = "icon"
# Return the key value for the select field
def value_for_form(self, value):
if isinstance(value, self.target_model):
return value.pk
else:
return value
and in your block just use
class SomeBox(blocks.StructBlock):
headline = blocks.TextBlock(required=True)
some_icon = SomeSortOfIconChooserBlock(required=True)
info_box_content = blocks.RichTextBlock(label='Content', required=True)
class Meta:
template = 'blocks/some_box.html'
icon = 'form'
label = _('Some Box')
This will give you a drop down based on the objects of the SomeSortOfIcon model.
I have some form modelformset_factory with model contains ForeignKey, but I need display this ForeignKey(ModelChoiceField) like CharField.
I use like that:
class SingleNeedFormWithDescription(ModelForm):
helper = StandardFormHelper()
helper.template = 'template.html'
need = CharField()
class Meta:
model = NeedMembershipOrganization
fields = ['need', 'description']
I have id of need in my template, but I need need.title or need.__str__().
My model:
class NeedMembershipOrganization(Model):
need = ForeignKey('needs.Need')
organization = ForeignKey(Organization)
description = TextField(blank=True, null=True, verbose_name='description')
Thanks!
You can change the ModelChoiceField widget to a TextInput, but you might have to figure out some way to validate and parse the input.
class SingleNeedFormWithDescription(ModelForm):
need = forms.ModelChoiceField(
queryset=Need.objects.all(),
widget=forms.TextInput)
I have a models in models.py
class Page(models.Model):
url = models.CharField(verbose_name="url", unique=True, db_index=True, max_length=255)
template = models.ForeignKey(Template)
class PageToBlock(models.Model):
page = models.ForeignKey(Page)
placeholder = models.ForeignKey(Placeholder)
block = models.ForeignKey(Block,null=True)
and some code in views
PTBFormSet = inlineformset_factory(models.Page, models.PageToBlock, extra=0, can_delete=False)
formset = PTBFormSet(instance=page)
for form in formset:
# i need initial here for processing
print form.fields['placeholder'].initial #print None!, but in final rendered form it has value
How to extract initial?
form.initials['placeholder'] works fine