class BookForm(forms.ModelForm): class Meta: model = models.Book fields = "__all__" labels = { "title": "书名", "price": "价格" } widgets = { "password": forms.widgets.PasswordInput(attrs={"class": "c1"}), }
model = models.Book # 对应的Model中的类 fields = "__all__" # 字段,若是是__all__,就是表示列出全部的字段 exclude = None # 排除的字段 labels = None # 提示信息 help_texts = None # 帮助提示信息 widgets = None # 自定义插件 error_messages = None # 自定义错误信息
from myapp.models import Book from myapp.forms import BookForm # 根据POST数据建立一个新的form对象 form_obj = BookForm(request.POST) # 建立书籍对象 new_ book = form_obj.save() # 基于一个书籍对象建立form对象 edit_obj = Book.objects.get(id=1) # 使用POST提交的数据更新书籍对象 form_obj = BookForm(request.POST, instance=edit_obj) form_obj.save()
from django import forms from django.utils.safestring import mark_safe from django.core.exceptions import ValidationError from rbac import models from django.utils.translation import ugettext_lazy ICON_LIST = [ ['fa-hand-scissors-o', '<i aria-hidden="true" class="fa fa-hand-scissors-o"></i>'], ['fa-hand-spock-o', '<i aria-hidden="true" class="fa fa-hand-spock-o"></i>'], ] for item in ICON_LIST: item[1] = mark_safe(item[1]) class BootStrapModelForm(forms.ModelForm): def __init__(self, *args, **kwargs): super(BootStrapModelForm, self).__init__(*args, **kwargs) # 统一给ModelForm生成字段添加样式 for name, field in self.fields.items(): field.widget.attrs['class'] = 'form-control' """ 基本用法: 首先从django.forms导入ModelForm; 编写一个本身的类,继承ModelForm; 在新类里,设置元类Meta; 在Meta中,设置model属性为你要关联的ORM模型,这里是Menu; 在Meta中,设置fields属性为你要在表单中使用的字段列表;列表里的值,应该是ORM模型model中的字段名。 """ class UserModelForm(BootStrapModelForm): confirm_password = forms.CharField(label='确认密码') # class Meta: model = models.UserInfo fields = ['name', 'email', 'password', 'confirm_password', 'icon'] # fields = '__all__' #表示将映射的模型中的所有字段都添加到表单类中来 exclude = ['pid'] #表示将model中,除了exclude属性中列出的字段以外的全部字段,添加到表单类中做为表单字段。 widgets = { 'name': forms.TextInput(attrs={'class': 'form-control'}), 'icon': forms.RadioSelect( choices=ICON_LIST, attrs={'class': 'clearfix'} ) } labels = { 'name': ugettext_lazy('Writer'), } help_texts = { 'name': ugettext_lazy('Some useful help text.'), } error_messages = { 'name': { 'max_length': ugettext_lazy("This writer's name is too long."), }, } def clean_confirm_password(self): """ 检测密码是否一致 :return: """ password = self.cleaned_data['password'] confirm_password = self.cleaned_data['confirm_password'] if password != confirm_password: raise ValidationError('两次密码输入不一致') return confirm_password # 能够在实例化一个表单时经过指定initial参数来提供表单中数据的初始值。
def menu_add(request): if request.method == 'GET': form = MenuModelForm() return render(request, 'rbac/change.html', {'form': form}) form = MenuModelForm(data=request.POST) if form.is_valid(): form.save() return redirect(memory_reverse(request, 'rbac:menu_list')) return render(request, 'rbac/change.html', {'form': form}) def menu_edit(request, pk): obj = models.Menu.objects.filter(id=pk).first() if not obj: return HttpResponse('菜单不存在') if request.method == 'GET': form = MenuModelForm(instance=obj) return render(request, 'rbac/change.html', {'form': form}) form = MenuModelForm(instance=obj, data=request.POST) if form.is_valid(): form.save() return redirect(memory_reverse(request, 'rbac:menu_list')) return render(request, 'rbac/change.html', {'form': form})
#models.py from django.db import models TITLE_CHOICES = ( ('MR', 'Mr.'), ('MRS', 'Mrs.'), ('MS', 'Ms.'), ) class Author(models.Model): name = models.CharField(max_length=100) title = models.CharField(max_length=3, choices=TITLE_CHOICES) birth_date = models.DateField(blank=True, null=True) def __str__(self): # __unicode__ on Python 2 return self.name class Book(models.Model): name = models.CharField(max_length=100) authors = models.ManyToManyField(Author) #myforms.py from django import forms class AuthorForm(forms.ModelForm): class Meta: model = models.Author fields = ['name', 'title', 'birth_date'] class BookForm(forms.ModelForm): class Meta: model = models.Book fields = ['name', 'authors'] #上面的ModelForm子类基本等同于下面的定义方式(惟一的区别是save()方法): from django import forms class AuthorForm(forms.Form): name = forms.CharField(max_length=100) title = forms.CharField( max_length=3, widget=forms.Select(choices=TITLE_CHOICES), ) birth_date = forms.DateField(required=False) class BookForm(forms.Form): name = forms.CharField(max_length=100) authors = forms.ModelMultipleChoiceField(queryset=Author.objects.all())
生成的Form类中将具备和指定的模型字段对应的表单字段,顺序为fields属性列表中指定的顺序。html
每一个模型字段有一个对应的默认表单字段。好比,模型中的CharField表现成表单中的CharField。模型中的ManyToManyField字段会表现成MultipleChoiceField字段。下面是完整的映射列表:数据库
ForeignKey被映射成为表单类的django.forms.ModelChoiceField,它的选项是一个模型的QuerySet,也就是能够选择的对象的列表,可是只能选择一个。django
ManyToManyField被映射成为表单类的django.forms.ModelMultipleChoiceField,它的选项也是一个模型的QuerySet,也就是能够选择的对象的列表,可是能够同时选择多个,多对多嘛。app
help_text
设置为模型字段的help_text
。模型字段 | 表单字段 |
---|---|
AutoField | 在Form类中没法使用 |
BigAutoField | 在Form类中没法使用 |
BigIntegerField | IntegerField,最小-9223372036854775808,最大9223372036854775807. |
BooleanField | BooleanField |
CharField | CharField,一样的最大长度限制。若是model设置了null=True,Form将使用empty_value |
CommaSeparatedIntegerField | CharField |
DateField | DateField |
DateTimeField | DateTimeField |
DecimalField | DecimalField |
EmailField | EmailField |
FileField | FileField |
FilePathField | FilePathField |
FloatField | FloatField |
ForeignKey | ModelChoiceField |
ImageField | ImageField |
IntegerField | IntegerField |
IPAddressField | IPAddressField |
GenericIPAddressField | GenericIPAddressField |
ManyToManyField | ModelMultipleChoiceField |
NullBooleanField | NullBooleanField |
PositiveIntegerField | IntegerField |
PositiveSmallIntegerField | IntegerField |
SlugField | SlugField |
SmallIntegerField | IntegerField |
TextField | CharField,并带有widget=forms.Textarea参数 |
TimeField | TimeField |
URLField | URLField |