""" Referrals forms for the Tenhal Multidisciplinary Healthcare Platform. This module contains forms for inter-discipline and external referrals. """ from django import forms from django.utils.translation import gettext_lazy as _ from crispy_forms.helper import FormHelper from crispy_forms.layout import Layout, Fieldset, Row, Column, Submit, HTML from .models import Referral class ReferralForm(forms.ModelForm): """ Form for creating referrals (internal and external). """ class Meta: model = Referral fields = [ 'patient', 'from_clinic', 'to_clinic', 'referred_to', 'referral_type', 'priority', 'reason', 'clinical_notes' ] widgets = { 'patient': forms.Select(attrs={'class': 'form-select select2', 'data-placeholder': 'Select patient'}), 'from_clinic': forms.Select(attrs={'class': 'form-select select2', 'data-placeholder': 'Select clinic'}), 'from_provider': forms.Select(attrs={'class': 'form-select select2', 'data-placeholder': 'Select provider'}), 'to_clinic': forms.Select(attrs={'class': 'form-select select2', 'data-placeholder': 'Select clinic'}), 'to_provider': forms.Select(attrs={'class': 'form-select select2', 'data-placeholder': 'Select provider'}), 'external_provider_name': forms.TextInput(attrs={'class': 'form-control'}), 'external_provider_contact': forms.TextInput(attrs={'class': 'form-control'}), 'urgency': forms.Select(attrs={'class': 'form-select'}), 'reason': forms.Textarea(attrs={'rows': 3, 'class': 'form-control'}), 'clinical_summary': forms.Textarea(attrs={'rows': 4, 'class': 'form-control'}), 'notes': forms.Textarea(attrs={'rows': 2, 'class': 'form-control'}), } def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.helper = FormHelper() self.helper.form_method = 'post' self.helper.layout = Layout( 'patient', Fieldset( _('From (Source)'), Row( Column('from_clinic', css_class='form-group col-md-6 mb-0'), Column('from_provider', css_class='form-group col-md-6 mb-0'), css_class='form-row' ), ), Fieldset( _('To (Destination) - Internal'), HTML('
{}
'.format(_('For internal referrals within the facility'))), Row( Column('to_clinic', css_class='form-group col-md-6 mb-0'), Column('to_provider', css_class='form-group col-md-6 mb-0'), css_class='form-row' ), ), Fieldset( _('To (Destination) - External'), HTML('{}
'.format(_('For external referrals to outside providers (leave internal fields empty)'))), Row( Column('external_provider_name', css_class='form-group col-md-6 mb-0'), Column('external_provider_contact', css_class='form-group col-md-6 mb-0'), css_class='form-row' ), ), Fieldset( _('Referral Details'), 'reason', 'urgency', 'clinical_summary', 'notes', ), Submit('submit', _('Create Referral'), css_class='btn btn-primary') ) def clean(self): cleaned_data = super().clean() to_clinic = cleaned_data.get('to_clinic') external_provider_name = cleaned_data.get('external_provider_name') # Validate that either internal or external destination is provided if not to_clinic and not external_provider_name: raise forms.ValidationError( _('Please specify either an internal clinic or an external provider.') ) # Validate that both are not provided if to_clinic and external_provider_name: raise forms.ValidationError( _('Please specify either internal OR external destination, not both.') ) # Validate external provider contact if external provider is specified if external_provider_name and not cleaned_data.get('external_provider_contact'): raise forms.ValidationError( _('External provider contact information is required for external referrals.') ) return cleaned_data class ExternalReferralForm(forms.Form): """ Form for external centers to refer patients to our center. Does not require authentication. """ # Referring Center Information referring_center_name = forms.CharField( label=_('Referring Center/Hospital Name'), max_length=200, widget=forms.TextInput(attrs={ 'class': 'form-control', 'placeholder': _('Enter your center name') }) ) referring_doctor_name = forms.CharField( label=_('Referring Doctor Name'), max_length=200, widget=forms.TextInput(attrs={ 'class': 'form-control', 'placeholder': _('Enter doctor name') }) ) referring_contact_phone = forms.CharField( label=_('Contact Phone'), max_length=20, widget=forms.TextInput(attrs={ 'class': 'form-control', 'placeholder': _('Enter phone number') }) ) referring_contact_email = forms.EmailField( label=_('Contact Email'), widget=forms.EmailInput(attrs={ 'class': 'form-control', 'placeholder': _('Enter email address') }) ) # Patient Information patient_first_name = forms.CharField( label=_('Patient First Name'), max_length=100, widget=forms.TextInput(attrs={ 'class': 'form-control', 'placeholder': _('Enter first name') }) ) patient_last_name = forms.CharField( label=_('Patient Last Name'), max_length=100, widget=forms.TextInput(attrs={ 'class': 'form-control', 'placeholder': _('Enter last name') }) ) patient_date_of_birth = forms.DateField( label=_('Date of Birth'), widget=forms.DateInput(attrs={ 'type': 'date', 'class': 'form-control' }) ) patient_sex = forms.ChoiceField( label=_('Sex'), choices=[ ('', _('Select...')), ('M', _('Male')), ('F', _('Female')) ], widget=forms.Select(attrs={'class': 'form-select'}) ) patient_national_id = forms.CharField( label=_('National ID (Optional)'), max_length=20, required=False, widget=forms.TextInput(attrs={ 'class': 'form-control', 'placeholder': _('Enter national ID if available') }) ) # Guardian/Caregiver Information caregiver_name = forms.CharField( label=_('Parent/Guardian Name'), max_length=200, widget=forms.TextInput(attrs={ 'class': 'form-control', 'placeholder': _('Enter parent/guardian name') }) ) caregiver_phone = forms.CharField( label=_('Parent/Guardian Phone'), max_length=20, widget=forms.TextInput(attrs={ 'class': 'form-control', 'placeholder': _('Enter phone number') }) ) caregiver_relationship = forms.CharField( label=_('Relationship to Patient'), max_length=100, widget=forms.TextInput(attrs={ 'class': 'form-control', 'placeholder': _('e.g., Mother, Father, Guardian') }) ) # Referral Details urgency = forms.ChoiceField( label=_('Urgency Level'), choices=Referral.Priority.choices, widget=forms.Select(attrs={'class': 'form-select'}) ) reason = forms.CharField( label=_('Reason for Referral'), widget=forms.Textarea(attrs={ 'rows': 4, 'class': 'form-control', 'placeholder': _('Please describe the reason for referral') }) ) clinical_summary = forms.CharField( label=_('Clinical Summary'), required=False, widget=forms.Textarea(attrs={ 'rows': 5, 'class': 'form-control', 'placeholder': _('Provide relevant clinical information, diagnosis, current treatment, etc.') }) ) requested_specialty = forms.ChoiceField( label=_('Requested Specialty'), choices=[ ('', _('Select specialty...')), ('MEDICAL', _('Medical')), ('OT', _('Occupational Therapy')), ('SLP', _('Speech-Language Pathology')), ('ABA', _('ABA Therapy')), ], widget=forms.Select(attrs={'class': 'form-select'}) ) def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.helper = FormHelper() self.helper.form_method = 'post' self.helper.layout = Layout( Fieldset( _('Referring Center Information'), 'referring_center_name', Row( Column('referring_doctor_name', css_class='form-group col-md-6 mb-0'), Column('referring_contact_phone', css_class='form-group col-md-6 mb-0'), css_class='form-row' ), 'referring_contact_email', ), Fieldset( _('Patient Information'), Row( Column('patient_first_name', css_class='form-group col-md-6 mb-0'), Column('patient_last_name', css_class='form-group col-md-6 mb-0'), css_class='form-row' ), Row( Column('patient_date_of_birth', css_class='form-group col-md-4 mb-0'), Column('patient_sex', css_class='form-group col-md-4 mb-0'), Column('patient_national_id', css_class='form-group col-md-4 mb-0'), css_class='form-row' ), ), Fieldset( _('Parent/Guardian Information'), 'caregiver_name', Row( Column('caregiver_phone', css_class='form-group col-md-6 mb-0'), Column('caregiver_relationship', css_class='form-group col-md-6 mb-0'), css_class='form-row' ), ), Fieldset( _('Referral Details'), Row( Column('urgency', css_class='form-group col-md-6 mb-0'), Column('requested_specialty', css_class='form-group col-md-6 mb-0'), css_class='form-row' ), 'reason', 'clinical_summary', ), Submit('submit', _('Submit Referral'), css_class='btn btn-primary btn-lg') ) class ReferralResponseForm(forms.Form): """ Form for responding to referrals. """ status = forms.ChoiceField( label=_('Status'), choices=Referral.Status.choices, widget=forms.RadioSelect ) response_notes = forms.CharField( label=_('Response Notes'), widget=forms.Textarea(attrs={'rows': 3}), required=False ) def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.helper = FormHelper() self.helper.form_method = 'post' self.helper.layout = Layout( 'status', 'response_notes', Submit('submit', _('Submit Response'), css_class='btn btn-primary') ) class ReferralSearchForm(forms.Form): """ Form for searching referrals. """ search_query = forms.CharField( required=False, label=_('Search'), widget=forms.TextInput(attrs={ 'placeholder': _('Patient name, MRN, Reason...'), 'class': 'form-control' }) ) status = forms.ChoiceField( required=False, label=_('Status'), choices=[('', _('All'))] + list(Referral.Status.choices), widget=forms.Select(attrs={'class': 'form-control'}) ) urgency = forms.ChoiceField( required=False, label=_('Urgency'), choices=[('', _('All'))] + list(Referral.Priority.choices), widget=forms.Select(attrs={'class': 'form-control'}) ) from_clinic = forms.ModelChoiceField( required=False, label=_('From Clinic'), queryset=None, # Will be set in __init__ widget=forms.Select(attrs={'class': 'form-select select2', 'data-placeholder': 'Select clinic'}) ) to_clinic = forms.ModelChoiceField( required=False, label=_('To Clinic'), queryset=None, # Will be set in __init__ widget=forms.Select(attrs={'class': 'form-select select2', 'data-placeholder': 'Select clinic'}) ) referral_type = forms.ChoiceField( required=False, label=_('Type'), choices=[ ('', _('All')), ('internal', _('Internal')), ('external', _('External')), ], widget=forms.Select(attrs={'class': 'form-control'}) ) date_from = forms.DateField( required=False, label=_('From Date'), widget=forms.DateInput(attrs={'type': 'date', 'class': 'form-control'}) ) date_to = forms.DateField( required=False, label=_('To Date'), widget=forms.DateInput(attrs={'type': 'date', 'class': 'form-control'}) ) def __init__(self, *args, **kwargs): tenant = kwargs.pop('tenant', None) super().__init__(*args, **kwargs) if tenant: from core.models import Clinic self.fields['from_clinic'].queryset = Clinic.objects.filter( tenant=tenant, is_active=True ) self.fields['to_clinic'].queryset = Clinic.objects.filter( tenant=tenant, is_active=True ) self.helper = FormHelper() self.helper.form_method = 'get' self.helper.layout = Layout( Row( Column('search_query', css_class='form-group col-md-3 mb-0'), Column('status', css_class='form-group col-md-2 mb-0'), Column('urgency', css_class='form-group col-md-1 mb-0'), Column('referral_type', css_class='form-group col-md-1 mb-0'), Column('from_clinic', css_class='form-group col-md-1.5 mb-0'), Column('to_clinic', css_class='form-group col-md-1.5 mb-0'), Column('date_from', css_class='form-group col-md-1 mb-0'), Column('date_to', css_class='form-group col-md-1 mb-0'), css_class='form-row' ), Submit('search', _('Search'), css_class='btn btn-primary') )