import { Button, FormContainer, FormItem, Input, Notification, Radio, Select, Tabs, toast, } from '@/components/ui' import TabContent from '@/components/ui/Tabs/TabContent' import TabList from '@/components/ui/Tabs/TabList' import TabNav from '@/components/ui/Tabs/TabNav' import { UserInfoViewModel } from '@/proxy/admin/models' import { dynamicFetch } from '@/services/form.service' import { putUserDetail } from '@/services/identity.service' import { SelectBoxOption } from '@/types/shared' import { useLocalization } from '@/utils/hooks/useLocalization' import dayjs from 'dayjs' import { Field, FieldProps, Formik, FormikProps } from 'formik' import { useEffect, useMemo, useState } from 'react' import PlatformViewHost from '@/components/componentEditor/PlatformViewHost' type HealthValues = UserInfoViewModel & Record interface DoctorOption { key: string name: string diplomaNo?: string diplomaDate?: string ohsCertificateNo?: string ohsCertificateDate?: string } const H = '::Abp.Identity.User.HealthCard' const familyRows = ['Mother', 'Father', 'Sibling', 'Child'] const vaccinationRows = ['TetanusVaccination', 'HepatitisVaccination', 'OtherVaccination'] /** [alan, girintili mi] — görseldeki "- Kan" gibi alt kalemler girintilidir. */ const labRows: [string, boolean][] = [ ['LabBiologicalAnalysis', false], ['LabBlood', true], ['LabUrine', true], ['LabRadiological', false], ['LabRadiologicalPhysiological', false], ['LabAudiometry', true], ['LabPulmonaryFunction', true], ['LabPsychologicalTests', false], ['LabOther', false], ] const examRows: [string, boolean][] = [ ['ExamSensoryOrgans', false], ['ExamEye', true], ['ExamEnt', true], ['ExamSkin', true], ['ExamCardiovascular', false], ['ExamRespiratory', false], ['ExamDigestive', false], ['ExamUrogenital', false], ['ExamMusculoskeletal', false], ] const otherExamRows: [string, boolean][] = [ ['ExamNeurological', false], ['ExamPsychiatric', false], ['ExamOther', false], ['ExamBloodPressure', true], ['ExamPulse', true], ] const complaintRows = [ 'ComplaintProductiveCough', 'ComplaintDyspnea', 'ComplaintChestPain', 'ComplaintPalpitation', 'ComplaintBackPain', 'ComplaintDiarrheaConstipation', 'ComplaintJointPain', ] const diagnosisRows = [ 'DiagnosisHeartDisease', 'DiagnosisDiabetes', 'DiagnosisKidneyDisease', 'DiagnosisJaundice', 'DiagnosisPepticUlcer', 'DiagnosisHearingLoss', 'DiagnosisVisionImpairment', 'DiagnosisNervousSystemDisease', 'DiagnosisSkinDisease', 'DiagnosisFoodPoisoning', ] const questionRows = [ 'Hospitalized', 'HadSurgery', 'HadWorkAccident', 'OccupationalDiseaseExam', 'DisabilityPension', 'UnderTreatment', ] const bloodTypes = ['A Rh+', 'A Rh-', 'B Rh+', 'B Rh-', 'AB Rh+', 'AB Rh-', '0 Rh+', '0 Rh-'] /** Kullanıcıya göre süzülen alt listeler; sekme adı = ListForm kodunun son parçası. */ const healthLists = ['UserPeriodicExamination', 'UserPatientProtocol', 'UserSickLeave'] const fieldName = (name: string) => name.charAt(0).toLowerCase() + name.slice(1) const formatDateNo = (date?: string, no?: string) => `${date ? dayjs(date).format('DD.MM.YYYY') : ''} / ${no ?? ''}` interface HealthCardTabProps { userDetails: UserInfoViewModel onSaved: () => void } function HealthCardTab({ userDetails, onSaved }: HealthCardTabProps) { const { translate } = useLocalization() const [doctors, setDoctors] = useState([]) const [activeTab, setActiveTab] = useState('history') // Yeni satırın UserId değeri de bu filtreden dolar (applyNewRowDefaults). const userSearchParams = useMemo( () => new URLSearchParams({ filter: JSON.stringify(['UserId', '=', userDetails.id]) }), [userDetails.id], ) const isListTab = healthLists.includes(activeTab) useEffect(() => { // Hekim listesi kullanıcı ekranının alan lookup'ından gelir; sorgu kiracıya göre süzülür. const loadDoctors = async () => { try { const response = await dynamicFetch('list-form-select/lookup', 'POST', null, { listFormCode: 'AbpIdentity.Users', listFormFieldName: 'FitnessDoctorId', }) const rows = Array.isArray(response?.data) ? response.data : [] setDoctors( rows.map((row: Record) => ({ key: row.Key, name: row.Name, diplomaNo: row.DiplomaNo, diplomaDate: row.DiplomaDate, ohsCertificateNo: row.OhsCertificateNo, ohsCertificateDate: row.OhsCertificateDate, })), ) } catch (error) { console.error('Doctors could not be loaded:', error) setDoctors([]) } } void loadDoctors() }, []) const healthStatusOptions: SelectBoxOption[] = [ { value: 'Alive', label: translate('::App.StaticLookup.Alive') }, { value: 'Deceased', label: translate('::App.StaticLookup.Deceased') }, ] const bloodTypeOptions: SelectBoxOption[] = bloodTypes.map((bloodType) => ({ value: bloodType, label: bloodType, })) const smokingOptions: SelectBoxOption[] = [ { value: 'No', label: translate('::App.Platform.No') }, { value: 'Yes', label: translate('::App.Platform.Yes') }, { value: 'Quit', label: translate('::App.StaticLookup.Quit') }, ] const alcoholOptions: SelectBoxOption[] = [ { value: 'No', label: translate('::App.Platform.No') }, { value: 'Occasionally', label: translate('::App.StaticLookup.Occasionally') }, { value: 'Yes', label: translate('::App.Platform.Yes') }, ] const doctorOptions: SelectBoxOption[] = doctors.map((doctor) => ({ value: doctor.key, label: doctor.name, })) const label = (name: string) => translate(`${H}.${name}`) const renderSelect = (name: string, options: SelectBoxOption[], values: HealthValues) => ( {({ field, form }: FieldProps) => (
{label('OhsCertificateDateNo')}
) } const bodyMassIndex = (values: HealthValues) => { const height = Number(values.examHeight) const weight = Number(values.examWeight) if (!height || !weight) return 0 return Number((weight / (height / 100) ** 2).toFixed(2)) } return ( { setSubmitting(true) // Sayı kutusu metin döndürür; API decimal bekler. const toNumber = (value: unknown) => value === '' || value === null || value === undefined ? undefined : Number(value) await putUserDetail({ ...values, examHeight: toNumber(values.examHeight), examWeight: toNumber(values.examWeight), }) toast.push( {translate('::App.Platform.Save')} , { placement: 'bottom-end', }, ) onSaved() setSubmitting(false) }} > {(formik) => { const { isSubmitting, values } = formik return ( // Alt listeler bu bileşenin içinde çizildiği için form etiketi kullanılmaz; liste // düğmeleri kart formunu göndermesin.
setActiveTab(String(tab))}> {label('History')} {label('LabPhysical')} {label('Anamnesis')} {label('Result')} {healthLists.map((code) => ( {translate(`::App.IdentityManagement.${code}`)} ))}
{label('FamilyHistory')}
{familyRows.map((member) => (
{label(`${member}HealthStatus`)}
{renderSelect( fieldName(`${member}HealthStatus`), healthStatusOptions, values, )} {renderText( fieldName(`${member}HealthNote`), label(`${member}HealthNote`), )}
))}
{label('PersonalHistory')}
{translate('::Abp.Account.BloodType')}
{renderSelect('bloodType', bloodTypeOptions, values)}
{label('ChronicDisease')}
{renderText('chronicDisease', label('ChronicDisease'))}
{label('Immunization')}
{vaccinationRows.map((vaccination) => (
- {label(vaccination)}
{renderText(fieldName(vaccination), label(vaccination))}
))}
{label('LaboratoryFindings')}
{renderTextRows(labRows)}
{label('PhysicalExamResults')}
{renderTextRows(examRows)}
{renderTextRows(otherExamRows)} {['ExamHeight', 'ExamWeight'].map((name) => (
- {label(name)}
))}
- {label('BodyMassIndex')}
{renderSetAll([...complaintRows, ...diagnosisRows], formik)}
{label('ComplaintsQuestion')}
{renderYesNoRows(complaintRows, formik)}
{label('DiagnosesQuestion')}
{renderYesNoRows(diagnosisRows, formik)}
{renderSetAll(questionRows, formik)} {questionRows.map((name) => (
{label(name)}
{renderYesNo(fieldName(name), formik)} {renderText(fieldName(`${name}Note`), label(`${name}Note`))}
))} {( [ ['Smoking', smokingOptions], ['Alcohol', alcoholOptions], ] as const ).map(([name, options]) => (
{label(name)}
{renderSelect(fieldName(name), [...options], values)} {renderText(fieldName(`${name}Note`), label(`${name}Note`))}
))}
1.
{renderText('fitForWorkJob', label('FitForWorkJob'))}
{label('FitForWorkJobSuffix')}
2.
{renderText('fitForWorkCondition', label('FitForWorkCondition'))}
{label('FitForWorkConditionSuffix')}
{renderDoctor('FitnessDoctorId', values)}

{label('ShiftNightInfo')}

{['ShiftWorkFit', 'NightWorkFit'].map((name) => (
{label(name)}
{renderYesNo(fieldName(name), formik)}
))}
{renderDoctor('ShiftNightDoctorId', values)}
{healthLists.map((code) => (
))}
{!isListTab && (
)}
) }}
) } export default HealthCardTab