ModelForm

ModelForm:是将model和form组件结合起来的,本质是form组件

先有model,再建立modelform

 model.py:
             字段
       from django.db import models
       caption=models.CharField(verbose_name="调查问题",max_length=255)
       question_type=models.IntegerField(verbose_name="问题类型",choices=choices,default=1)

            
                   
                   
modelform.py:
            from django.forms import widgets,ModelForm
            class ModelForm(ModelForm):
          class Meta:
           model=Question
           fields=["caption","question_type"]
           widgets={
              "caption":widgets.TextInput(attrs={"class": "form-control", "id": "question"}),
              "question_type":widgets.Select(attrs={"class": "form-control", "id": "type"}),}
views.py:
      from django.shortcuts import render
      from .models import *
      from .forms import *
      def questionaire(request,questionaire_id):
       question_list = Question.objects.filter(survey_id=questionaire_id)
      for question_obj in question_list:
      questionform=Question_form(instance=question_obj)
      return render(request, "questionaire.html",locals())

区分两个对象
(book_obj与book_form):
        book_obj=Book.objects.filter(nid=id).first()  # 获取该书籍字段信息
        
        book_form:
            in 模板中:刻意渲染表单标签(input,select)
        
            in views:
            
            book_form.is_valid()  #校验用户输入的字段数据
            
            添加:book_form= BookForm(data=request.POST)   
                  book_form.save():添加一条记录
                  
            编辑:book_form = BookForm(data=request.POST,instance=book_obj)
                  book_form.save(): 编辑book_obj:book_obj.update(....)
                 
示例
models:

from django.db import models

# Create your models here.

class Class_info(models.Model):
"""班级表"""
name=models.CharField(verbose_name="班级(期)",max_length=32)
def __str__(self):
return self.name

class UserInfo(models.Model):
"""员工表"""
name=models.CharField(verbose_name="姓名",max_length=16)
def __str__(self):
return self.name

class Student(models.Model):
"""学生表"""
name=models.CharField(max_length=32)
pwd=models.CharField(max_length=32)
cls=models.ForeignKey("Class_info")
def __str__(self):
return self.name

class Questionaire(models.Model):
"""问卷表"""
name=models.CharField(verbose_name="调查问卷名称",max_length=128,unique=True)
class_info=models.ForeignKey("Class_info",verbose_name="问卷调查班级")
date=models.DateTimeField(verbose_name="问卷创建日期",auto_now_add=True)
creator=models.ForeignKey(verbose_name="创建者",to="UserInfo")
def __str__(self):
return self.name

class Question(models.Model):
"""问题表"""
survey=models.ForeignKey(verbose_name="问卷",to="Questionaire")
caption=models.CharField(verbose_name="调查问题",max_length=255)
date=models.DateTimeField(auto_now_add=True)
choices=(
(1,"打分(1~10)"),
(2,"单选"),
(3,"建议"),
)
question_type=models.IntegerField(verbose_name="问题类型",choices=choices,default=1)
def __str__(self):
return self.caption

class Option(models.Model):
"""单选题的选项"""

option_name=models.CharField(verbose_name='选项名称',max_length=32)
score=models.IntegerField(verbose_name='选项对应的分值')
question=models.ForeignKey("Question")
def __str__(self):
return self.option_name


class Answer(models.Model):
"""回答"""
student=models.ForeignKey("Student")
question=models.ForeignKey("Question")

# 三选一
option=models.ForeignKey("Option",null=True,blank=True)
val=models.IntegerField(null=True,blank=True)
content=models.CharField(max_length=255,null=True,blank=True)

 

forms:

class Question_form(ModelForm):
    class Meta:
        model=Question
        fields=["caption","question_type"]
        widgets={
            "caption":widgets.TextInput(attrs={"class": "form-control", "id": "question"}),
            "question_type":widgets.Select(attrs={"class": "form-control", "id": "type"}),

        }

class Option_model_form(ModelForm):
    class Meta:
        model=Option
        fields=["option_name","score"]
        widgets={
            "option_name":widgets.TextInput(attrs={"class": "form-control", "id": "option_name"}),
            "score":widgets.TextInput (attrs={"class": "form-control", "id": "score"})
        }
views:

from django.shortcuts import render,HttpResponse,redirect
from .models import *
from .forms import *
import json
# Create your views here.
def questionaire(request,questionaire_id):
    if request.method=="POST":
        response = {"state": True}


        try:
            print(json.loads(request.body.decode()))
            post_question_list=json.loads(request.body.decode())
            pre_question_list=list(Question.objects.filter(survey_id=questionaire_id).values("pk","caption","question_type"))

            post_question_dict={i["pk"]:i  for i in post_question_list}
            pre_question_dict={i["pk"]:i  for i in pre_question_list}


            print(" post_question_dict",post_question_dict)
            print(" pre_question_dict",pre_question_dict)

            post_question_set=set([row["pk"] for row in post_question_list])
            pre_question_set=set([row["pk"] for row in pre_question_list])

            print(" post_question_set", post_question_set)
            print(" pre_question_set", pre_question_set)

            # 删除问题
            del_question_pk_list=list(pre_question_set-post_question_set)
            print("del_question_pk_list",del_question_pk_list)
            Question.objects.filter(id__in=del_question_pk_list).delete()

            # 添加问题
            add_question_pk_list=list(post_question_set-pre_question_set)
            print("add_question_pk_list:",add_question_pk_list)

            for add_pk in add_question_pk_list:
                caption=post_question_dict.get(add_pk)["caption"]
                question_type=post_question_dict.get(add_pk)["question_type"]
                option_list=post_question_dict.get(add_pk)["option_list"]
                question_obj=Question.objects.create(caption=caption,question_type=question_type,survey_id=questionaire_id)

                if question_type==2:
                    for option in option_list:
                        Option.objects.create(option_name=option["option_name"],score=option["score"],question=question_obj)



            # 更新问题

            repeat_question_pk_list=list(pre_question_set & pre_question_set)
            print(repeat_question_pk_list)
            for repeat_pk in repeat_question_pk_list:
                post_question=post_question_dict.get(repeat_pk)
                pre_question=pre_question_dict.get(repeat_pk)


                current_question_post_option_list=post_question.pop("option_list")
                current_question_pre_option_list=list(Option.objects.filter(question_id=repeat_pk).values("pk","option_name","score"))

                if post_question==pre_question and current_question_post_option_list==current_question_pre_option_list:

                    print("%s 问题没有任何更改" % post_question.get("caption"))

                else:# 问题被更改了
                    current_question_pk=post_question.get("pk")
                    new_caption=post_question["caption"]
                    new_question_type=post_question["question_type"]
                    Question.objects.filter(pk=current_question_pk).update(caption=new_caption,question_type=new_question_type)
                    if new_question_type==2:
                        pre_option_pk_set=set([row["pk"] for row in current_question_pre_option_list])
                        post_option_pk_set=set([row["pk"] for row in current_question_post_option_list])

                        pre_option_dict={obj["pk"]:obj for obj in current_question_pre_option_list}
                        post_option_dict={obj["pk"]:obj for obj in current_question_post_option_list}

                        #添加选项
                        add_option_list=post_option_pk_set-post_option_pk_set
                        for add_option_pk in add_option_list:
                            option=post_question_dict.get("add_option_pk")["option_name"]
                            score=post_question_dict.get("add_option_pk")["score"]
                            Option.objects.create(option_name=option,score=score,question_id=current_question_pk)


                        #删除选项
                        del_option_list=pre_option_pk_set-post_option_pk_set
                        Option.objects.filter(id__in=del_option_list).delete()

                        # 更新选项
                        repeat_option_list = list(post_option_pk_set & pre_option_pk_set)

                        for option_pk in repeat_option_list:

                            if post_option_dict.get(option_pk) == pre_option_dict.get(option_pk):
                                print("option没有更改...")

                            else:
                                s = post_option_dict.get(option_pk)
                                s.pop("pk")
                                Option.objects.filter(id=option_pk).update(**s)

                print("问题更新结束....")
        except Exception as e:
            response["error_meg"] = e
            response["state"] = False

        return HttpResponse(json.dumps(response))

    else:
        questionaire_obj=Questionaire.objects.filter(id=questionaire_id).first()
        if not questionaire_obj:
            return HttpResponse("未找到符合要求的问卷调查!")  # 处理没有找到问卷对象的情况

        # question_list = Question.objects.filter(survey_id=questionaire_id)
        # question_model_form_list=[]
        # for question_obj in question_list:

        #     questionform=Question_form(instance=question_obj)
        #     question_model_form_list.append(questionform)
        # question_model_form_list = (Question_form(instance=question_obj) for question_obj in question_list)
        def generate_question_modelform_info():
            question_list = Question.objects.filter(survey_id=questionaire_id)
            for question in question_list:
                questionform = Question_form(instance=question)
                if question.question_type==2:
                    option_list=question.option_set.all()
                    option_model_form_list=((Option_model_form(instance=option),option)  for option in option_list)

                    yield {"question":question,"questionform":questionform,"option_model_form_list":option_model_form_list}
                else:
                    yield {"question":question,"questionform":questionform}


        return render(request, "questionaire.html",{"generate_question_modelform_info":generate_question_modelform_info()})

 

 

posted @ 2018-01-15 16:37  星雨5213  阅读(78)  评论(0)    收藏  举报