from django.contrib.admin import widgets from django.forms import ( Form, ModelForm, ModelMultipleChoiceField, ModelChoiceField, ChoiceField, CharField, ) from django.forms import inlineformset_factory from atlas.models import ( Case, Differential, Finding, Series, SeriesImage, SeriesFinding, Condition, Structure, ) from anatomy.models import Modality from generic.models import Examination, Sign # from generic.models import Examination, Site, Condition, Sign from django.contrib.admin.widgets import FilteredSelectMultiple from django.forms.widgets import RadioSelect, TextInput, Textarea from tinymce.widgets import TinyMCE from dal import autocomplete class ConditionForm(ModelForm): class Meta: model = Condition exclude = [] widgets = { "synonym": autocomplete.ModelSelect2Multiple( url="atlas:condition-autocomplete" ), "parent": autocomplete.ModelSelect2Multiple( url="atlas:condition-autocomplete" ), } class FindingForm(ModelForm): class Meta: model = Finding exclude = [] widgets = { "synonym": autocomplete.ModelSelect2Multiple( url="atlas:finding-autocomplete" ), } class StructureForm(ModelForm): class Meta: model = Structure exclude = [] widgets = { "synonym": autocomplete.ModelSelect2Multiple( url="atlas:structure-autocomplete" ), } class SeriesFindingForm(ModelForm): class Meta: model = SeriesFinding exclude = ["series", "annotation_json", "viewport_json"] widgets = { "findings": autocomplete.ModelSelect2Multiple( url="atlas:finding-autocomplete" ), "structures": autocomplete.ModelSelect2Multiple( url="atlas:structure-autocomplete" ), } def __init__(self, *args, **kwargs): if kwargs.get("series_id"): # 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["series"] = kwargs.pop("series_id") # elif 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["structures"] = [t.pk for t in kwargs["structures"].case.all()] # #initial["structures"] = [t.pk for t in kwargs["structures"].case.all()] super(SeriesFindingForm, self).__init__(*args, **kwargs) ModelForm.__init__(self, *args, **kwargs) class SeriesForm(ModelForm): class Media: # Django also includes a few javascript files necessary # for the operation of this form element. You need to # include # in the template. css = { "all": ["css/widgets.css"], } # Adding this javascript is crucial js = ["jsi18n.js", "tesseract.min.js"] 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["case"] = [t.pk for t in kwargs["instance"].case.all()] super(SeriesForm, self).__init__(*args, **kwargs) # self.fields["examination"] = ModelChoiceField( # queryset=Examination.objects.all(), # widget=FilteredSelectMultiple(verbose_name="Examination", is_stacked=False), # ) self.fields["modality"] = ModelChoiceField( required=True, queryset=Modality.objects.all(), ) ModelForm.__init__(self, *args, **kwargs) case_queryset = Case.objects.all() self.fields["case"] = ModelMultipleChoiceField( required=False, queryset=case_queryset, widget=FilteredSelectMultiple(verbose_name="Case", 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.case.clear() for case in self.cleaned_data["case"]: # We need the id here instance.case.add(case.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 = Series exclude = ["author"] widgets = { "examination": autocomplete.ModelSelect2( url="generic:examination-autocomplete" ), "description": Textarea(attrs={"maxlength": 1000, "rows": 5, "cols": 80}), } class CaseForm(ModelForm): # exams = ModelMultipleChoiceField(required=False, queryset=Exam.objects.all(),widget=FilteredSelectMultiple(verbose_name="Exams", is_stacked=False)) class Media: # Django also includes a few javascript files necessary # for the operation of this form element. You need to # include # in the template. css = { "all": ["css/widgets.css"], } # Adding this javascript is crucial js = ["jsi18n.js", "tesseract.min.js"] def __init__(self, *args, **kwargs): self.user = kwargs.pop( "user" ) # To get request.user. Do not use kwargs.pop('user', None) due to potential security hole 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["exams"] = [t.pk for t in kwargs["instance"].exams.all()] ModelForm.__init__(self, *args, **kwargs) super(CaseForm, self).__init__(*args, **kwargs) class Meta: model = Case # fields = ['due_back'] # fields = '__all__' fields = [ # "examination", # "site", "title", "subspecialty", "description", "history", "presentation", "discussion", "condition", "pathological_process", # "sign", "open_access", ] # fields = ['question', 'findings', 'subspecialty', 'references'] widgets = { # "normal": RadioSelect( # choices=[(True, 'Yes'), # (False, 'No')]) # "findings": TinyMCE(attrs={"cols": 80, "rows": 20}), # "mark_scheme": TinyMCE(attrs={"cols": 80, "rows": 30}), "description": Textarea(attrs={"cols": 80, "rows": 5}), "history": Textarea(attrs={"cols": 80, "rows": 5}), "discussion": Textarea(attrs={"cols": 80, "rows": 5}), "condition": autocomplete.ModelSelect2Multiple( url="atlas:condition-autocomplete" ), "presentation": autocomplete.ModelSelect2Multiple( url="atlas:presentation-autocomplete" ), } def save(self, commit=True): # Get the unsaved Case 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.exams.clear() # for exam in self.cleaned_data["exams"]: # # We need the id here # instance.exams.add(exam.pk) self.save_m2m = save_m2m # Do we need to save all changes now? # if commit: instance.save() self.save_m2m() return instance CaseDifferentialFormSet = inlineformset_factory( Case, Differential, exclude=[], can_delete=True, extra=1, max_num=10, widgets={ "condition": autocomplete.ModelSelect2(url="atlas:condition-autocomplete"), "text": Textarea(attrs={"maxlength": 1000, "rows": 3, "cols": 80}), }, ) SeriesFormSet = inlineformset_factory( Case, Series.case.through, exclude=[], can_delete=True, extra=0, max_num=10, field_classes="testing", ) SeriesImageFormSet = inlineformset_factory( Series, SeriesImage, exclude=[], can_delete=True, extra=0, max_num=2000, field_classes="testing", )