Files
penracourses/generic/forms.py
T
2022-11-28 15:48:50 +00:00

353 lines
12 KiB
Python
Executable File

from django.forms import (
Form,
ModelForm,
ModelMultipleChoiceField,
ModelChoiceField,
ChoiceField,
CharField,
HiddenInput,
EmailField,
IntegerField,
)
from django.forms import inlineformset_factory
from atlas.models import CaseCollection
from django.contrib.auth.models import User
from generic.models import (
CidUser,
CidUserGroup,
Examination,
QuestionNote,
Supervisor,
UserGrades,
UserProfile,
UserUserGroup,
)
from django.contrib.admin.widgets import FilteredSelectMultiple
from django.forms.widgets import RadioSelect, TextInput, Textarea
from rapids.models import Rapid
from anatomy.models import AnatomyQuestion
from longs.models import Long
from django.shortcuts import render, get_object_or_404, redirect
from django.contrib.contenttypes.models import ContentType
from physics.models import CidUserAnswer as PhysicsCidUserAnswer, Question
from physics.models import Exam as PhysicsExam
from physics.models import Question as SbasQuestion
from anatomy.models import CidUserAnswer as AnatomyCidUserAnswer
from anatomy.models import Exam as AnatomyExam
from anatomy.models import AnatomyQuestion
from anatomy.models import Answer as AnatomyAnswer
from rapids.models import CidUserAnswer as RapidsCidUserAnswer
from rapids.models import Exam as RapidsExam
from rapids.models import Rapid
from rapids.models import Answer as RapidAnswer
from longs.models import CidUserAnswer as LongsCidUserAnswer
from longs.models import Exam as LongsExam
from longs.models import Long
from sbas.models import CidUserAnswer as SbasCidUserAnswer
from sbas.models import Exam as SbasExam
from sbas.models import Question as SbasQuestion
class ExamFormMixin:
def __init__(self, *args, user, **kwargs) -> None:
super(ModelForm, self).__init__(*args, **kwargs)
if user.is_superuser or user.groups.filter(name="cid_manager").exists():
cid_user_group_queryset = CidUserGroup.objects.all()
user_user_group_queryset = UserUserGroup.objects.all()
else:
cid_user_group_queryset = CidUserGroup.objects.none()
user_user_group_queryset = UserUserGroup.objects.none()
self.fields["cid_user_groups"] = ModelMultipleChoiceField(
required=False,
queryset=cid_user_group_queryset,
)
self.fields["user_user_groups"] = ModelMultipleChoiceField(
required=False,
queryset=user_user_group_queryset,
)
class Meta:
fields = [
"name",
"time_limit",
"open_access",
"authors_only",
"exam_mode",
"include_history",
"active",
"publish_results",
"archive",
"cid_user_groups",
"user_user_groups",
# "author",
]
def save(self, commit=True):
instance = ModelForm.save(self, False)
instance.save()
self.save_m2m()
return instance
class ExamAuthorFormMixin(ModelForm):
class Meta:
fields = ["author"]
def __init__(self, *args, **kwargs):
ModelForm.__init__(self, *args, **kwargs)
self.fields["author"] = ModelMultipleChoiceField(
queryset=User.objects.all(),
widget=FilteredSelectMultiple(verbose_name="Authors", is_stacked=False),
)
class ExaminationForm(ModelForm):
class Meta:
model = Examination
fields = ["examination"]
class QuestionNoteForm(ModelForm):
class Meta:
model = QuestionNote
fields = ["content_type", "object_id", "author", "note_type", "note"]
widgets = {"content_type": HiddenInput(), "object_id": HiddenInput()}
def __init__(self, *args, **kwargs):
question_type = kwargs.pop("question_type")
pk = kwargs.pop("pk")
user = kwargs.pop("user")
# if question_type == "rapid":
# question = Rapid
# content_type = ContentType.objects.get(model="rapid")
# elif question_type == "anatomy":
# question = AnatomyQuestion
# content_type = ContentType.objects.get(model="anatomyquestion")
# elif question_type == "long":
# question = Long
# content_type = ContentType.objects.get(model="long")
# else:
# raise PermissionError()
# get_object_or_404(question, pk=pk)
# We get the 'initial' keyword argument or initialize it
# as a dict if it didn't exist.
# if kwargs.get("instance"):
ModelForm.__init__(self, *args, **kwargs)
super(QuestionNoteForm, self).__init__(*args, **kwargs)
# initial = kwargs.setdefault("initial", {})
## The widget for a ModelMultipleChoiceField expects
## a list of primary key for the selected data.
##initial["content_type"] = question
##initial["content_id"] = pk
# self.fields["content_type"].initial = content_type
# self.fields["object_id"].initial = pk
class CidUserForm(ModelForm):
class Meta:
model = CidUser
fields = [
"passcode",
"active",
"internal_candidate",
"name",
"email",
"supervisor",
"login_email_sent",
"results_email_sent",
"group",
]
class CidUserExamForm(ModelForm):
def __init__(self, *args, **kwargs):
if kwargs.get("instance"):
# We get the 'initial' keyword argument or initialize it
# as a dict if it didn't exist.
initial = kwargs.setdefault("initial", {})
# The widget for a ModelMultipleChoiceField expects
# a list of primary key for the selected data.
initial["physics_exams"] = [
t.pk for t in kwargs["instance"].physics_exams.all()
]
initial["anatomy_exams"] = [
t.pk for t in kwargs["instance"].anatomy_exams.all()
]
initial["sba_exams"] = [t.pk for t in kwargs["instance"].sba_exams.all()]
initial["rapid_exams"] = [
t.pk for t in kwargs["instance"].rapid_exams.all()
]
initial["longs_exams"] = [
t.pk for t in kwargs["instance"].longs_exams.all()
]
initial["casecollection_exams"] = [
t.pk for t in kwargs["instance"].casecollection_exams.all()
]
ModelForm.__init__(self, *args, **kwargs)
super(CidUserExamForm, self).__init__(*args, **kwargs)
self.fields["physics_exams"] = ModelMultipleChoiceField(
required=False,
queryset=PhysicsExam.objects.filter(archive=False),
widget=FilteredSelectMultiple(
verbose_name="Physics Exams", is_stacked=False
),
)
self.fields["anatomy_exams"] = ModelMultipleChoiceField(
required=False,
queryset=AnatomyExam.objects.filter(archive=False),
widget=FilteredSelectMultiple(
verbose_name="Anatomy Exams", is_stacked=False
),
)
self.fields["sba_exams"] = ModelMultipleChoiceField(
required=False,
queryset=SbasExam.objects.filter(archive=False),
widget=FilteredSelectMultiple(verbose_name="SBA Exams", is_stacked=False),
)
self.fields["rapid_exams"] = ModelMultipleChoiceField(
required=False,
queryset=RapidsExam.objects.filter(archive=False),
widget=FilteredSelectMultiple(verbose_name="Rapid Exams", is_stacked=False),
)
self.fields["longs_exams"] = ModelMultipleChoiceField(
required=False,
queryset=LongsExam.objects.filter(archive=False),
widget=FilteredSelectMultiple(verbose_name="Long Exams", is_stacked=False),
)
self.fields["casecollection_exams"] = ModelMultipleChoiceField(
required=False,
queryset=CaseCollection.objects.filter(archive=False),
widget=FilteredSelectMultiple(
verbose_name="Case Collection", is_stacked=False
),
)
def save(self, commit=True):
# Get the unsaved Long instance
instance = ModelForm.save(self, False)
# Prepare a 'save_m2m' method for the form,
old_save_m2m = self.save_m2m
def save_m2m():
old_save_m2m()
instance.physics_exams.clear()
for physics_exams in self.cleaned_data["physics_exams"]:
instance.physics_exams.add(physics_exams.pk)
instance.anatomy_exams.clear()
for anatomy_exams in self.cleaned_data["anatomy_exams"]:
instance.anatomy_exams.add(anatomy_exams.pk)
instance.sba_exams.clear()
for sba_exams in self.cleaned_data["sba_exams"]:
instance.sba_exams.add(sba_exams.pk)
instance.rapid_exams.clear()
for rapid_exams in self.cleaned_data["rapid_exams"]:
instance.rapid_exams.add(rapid_exams.pk)
instance.longs_exams.clear()
for longs_exams in self.cleaned_data["longs_exams"]:
instance.longs_exams.add(longs_exams.pk)
instance.casecollection_exams.clear()
for casecollection_exams in self.cleaned_data["casecollection_exams"]:
instance.casecollection_exams.add(casecollection_exams.pk)
self.save_m2m = save_m2m
# Do we need to save all changes now?
# if commit:
instance.save()
self.save_m2m()
return instance
class Meta:
model = CidUser
fields = []
class CidUserGroupModelChoiceField(ModelMultipleChoiceField):
def label_from_instance(self, obj):
return f"{obj.cid} [{obj.email}]"
class CidUserGroupForm(ModelForm):
class Meta:
model = CidUserGroup
fields = ["name", "archive"]
class UserUserGroupModelChoiceField(ModelMultipleChoiceField):
def label_from_instance(self, obj):
return f"{obj.username} ({obj.userprofile.grade}) [{obj.email}]"
class UserUserGroupForm(ModelForm):
users = UserUserGroupModelChoiceField(
required=False,
queryset=User.objects.all(),
widget=FilteredSelectMultiple(verbose_name="Users", is_stacked=False),
)
class Meta:
model = UserUserGroup
fields = ["name", "archive", "users"]
# class UserForm(ModelForm):
# class Meta:
# model = User
# fields = ["first_name", "last_name", "email"]
#
# class UserProfileForm(ModelForm):
# class Meta:
# model = UserProfile
# fields = ["supervisor_name", "supervisor_email", "registration_number", "peninsula_trainee"]
GRADE_CHOICES = (
("ST1", "ST1"),
("ST2", "ST2"),
("ST3", "ST3"),
("ST4", "ST4"),
("ST5", "ST5"),
)
class UserUserForm(Form):
username = EmailField(
required=True,
help_text="Username / email should be the same. Ideally this should be an nhs email.",
)
first_name = CharField(max_length=255, required=True)
last_name = CharField(max_length=255, required=True)
grade = ModelChoiceField(UserGrades.objects.all(), required=False)
supervisor = ModelChoiceField(
Supervisor.objects.all(), required=False
) # Needs to be a user/object ref
#
# class Meta:
#
# fields = ("username", "first_name", "last_name")
class SupervisorForm(ModelForm):
class Meta:
model = Supervisor
exclude = ("",)