@alfadocs/ui-kit-debug 0.69.0 → 0.70.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/_chunks/{agenda-card-BxSFkqgY.js → agenda-card-BQ-IKAru.js} +2 -2
- package/dist/_chunks/{agenda-card-BxSFkqgY.js.map → agenda-card-BQ-IKAru.js.map} +1 -1
- package/dist/_chunks/{agenda-tray-g0kg7HwB.js → agenda-tray-CGXRk58j.js} +2 -2
- package/dist/_chunks/{agenda-tray-g0kg7HwB.js.map → agenda-tray-CGXRk58j.js.map} +1 -1
- package/dist/_chunks/{ai-consent-banner-CXlsNX1c.js → ai-consent-banner-Be-h9mRI.js} +3 -3
- package/dist/_chunks/{ai-consent-banner-CXlsNX1c.js.map → ai-consent-banner-Be-h9mRI.js.map} +1 -1
- package/dist/_chunks/ai-tools-rail-B5NEghsp.js +511 -0
- package/dist/_chunks/ai-tools-rail-B5NEghsp.js.map +1 -0
- package/dist/_chunks/{alert-_mUKLmwA.js → alert-CHYZ96tR.js} +150 -96
- package/dist/_chunks/alert-CHYZ96tR.js.map +1 -0
- package/dist/_chunks/{anamnesis-card-DRmE24OQ.js → anamnesis-card-DvYCa16e.js} +2 -2
- package/dist/_chunks/{anamnesis-card-DRmE24OQ.js.map → anamnesis-card-DvYCa16e.js.map} +1 -1
- package/dist/_chunks/anatomy-scheme-CJB6dI6p.js +2445 -0
- package/dist/_chunks/anatomy-scheme-CJB6dI6p.js.map +1 -0
- package/dist/_chunks/annotation-marker-qt5R9WZX.js +120 -0
- package/dist/_chunks/annotation-marker-qt5R9WZX.js.map +1 -0
- package/dist/_chunks/{antenatal-schedule-timeline-35ebkcZT.js → antenatal-schedule-timeline-CwXrQRm1.js} +2 -2
- package/dist/_chunks/{antenatal-schedule-timeline-35ebkcZT.js.map → antenatal-schedule-timeline-CwXrQRm1.js.map} +1 -1
- package/dist/_chunks/appointment-card-C06aZqA7.js +310 -0
- package/dist/_chunks/appointment-card-C06aZqA7.js.map +1 -0
- package/dist/_chunks/appointment-timeline-BJM0S_Fg.js +386 -0
- package/dist/_chunks/appointment-timeline-BJM0S_Fg.js.map +1 -0
- package/dist/_chunks/appointment-tray-DRRw5ROi.js +193 -0
- package/dist/_chunks/appointment-tray-DRRw5ROi.js.map +1 -0
- package/dist/_chunks/{audio-recorder-DYXXnGug.js → audio-recorder-Cpdk5qpQ.js} +2 -2
- package/dist/_chunks/{audio-recorder-DYXXnGug.js.map → audio-recorder-Cpdk5qpQ.js.map} +1 -1
- package/dist/_chunks/{badge-CqGsX32l.js → badge-DCOqV9mI.js} +32 -27
- package/dist/_chunks/badge-DCOqV9mI.js.map +1 -0
- package/dist/_chunks/{bishop-score-PJI3AXzA.js → bishop-score-DnYWtZa_.js} +2 -2
- package/dist/_chunks/{bishop-score-PJI3AXzA.js.map → bishop-score-DnYWtZa_.js.map} +1 -1
- package/dist/_chunks/{bmi-calculator-BZtIJ53x.js → bmi-calculator-zjeY4E7J.js} +2 -2
- package/dist/_chunks/{bmi-calculator-BZtIJ53x.js.map → bmi-calculator-zjeY4E7J.js.map} +1 -1
- package/dist/_chunks/{booking-C3VqFReX.js → booking-DUBI0oqt.js} +4 -4
- package/dist/_chunks/{booking-C3VqFReX.js.map → booking-DUBI0oqt.js.map} +1 -1
- package/dist/_chunks/{care-plan-card-CvFGXa2z.js → care-plan-card-C5sTfY9G.js} +5 -5
- package/dist/_chunks/{care-plan-card-CvFGXa2z.js.map → care-plan-card-C5sTfY9G.js.map} +1 -1
- package/dist/_chunks/{care-plan-entry-card-C3E_gClk.js → care-plan-entry-card-CXnxGCWA.js} +5 -5
- package/dist/_chunks/{care-plan-entry-card-C3E_gClk.js.map → care-plan-entry-card-CXnxGCWA.js.map} +1 -1
- package/dist/_chunks/care-plan-header-BUwqDTtz.js +206 -0
- package/dist/_chunks/care-plan-header-BUwqDTtz.js.map +1 -0
- package/dist/_chunks/clinical-note-card-BUvNMNGL.js +436 -0
- package/dist/_chunks/clinical-note-card-BUvNMNGL.js.map +1 -0
- package/dist/_chunks/{contact-profile-card-Dramqa9C.js → contact-profile-card-DDPwRFiP.js} +2 -2
- package/dist/_chunks/{contact-profile-card-Dramqa9C.js.map → contact-profile-card-DDPwRFiP.js.map} +1 -1
- package/dist/_chunks/control-room-rail-Y8ryLYsP.js +229 -0
- package/dist/_chunks/control-room-rail-Y8ryLYsP.js.map +1 -0
- package/dist/_chunks/{cycle-calculator-DmRGJNaT.js → cycle-calculator-CCmPwcBl.js} +2 -2
- package/dist/_chunks/{cycle-calculator-DmRGJNaT.js.map → cycle-calculator-CCmPwcBl.js.map} +1 -1
- package/dist/_chunks/{dependent-selector-CG_FOHya.js → dependent-selector-DUV4thxX.js} +2 -2
- package/dist/_chunks/{dependent-selector-CG_FOHya.js.map → dependent-selector-DUV4thxX.js.map} +1 -1
- package/dist/_chunks/{document-scanner-CTubA0-N.js → document-scanner-C_AxLooF.js} +3 -3
- package/dist/_chunks/{document-scanner-CTubA0-N.js.map → document-scanner-C_AxLooF.js.map} +1 -1
- package/dist/_chunks/{due-date-calculator-BTmsIQqD.js → due-date-calculator-Brdj-euS.js} +3 -3
- package/dist/_chunks/{due-date-calculator-BTmsIQqD.js.map → due-date-calculator-Brdj-euS.js.map} +1 -1
- package/dist/_chunks/editable-currency-cell-renderer-C9twtALM.js +328 -0
- package/dist/_chunks/editable-currency-cell-renderer-C9twtALM.js.map +1 -0
- package/dist/_chunks/email-input-DJ7EXklP.js +397 -0
- package/dist/_chunks/{email-input-B_Y55f5G.js.map → email-input-DJ7EXklP.js.map} +1 -1
- package/dist/_chunks/{entity-card-COhmqHly.js → entity-card-9_62gY7l.js} +38 -20
- package/dist/_chunks/{entity-card-COhmqHly.js.map → entity-card-9_62gY7l.js.map} +1 -1
- package/dist/_chunks/entity-summary-BxRjFh_4.js +138 -0
- package/dist/_chunks/entity-summary-BxRjFh_4.js.map +1 -0
- package/dist/_chunks/{fetal-weight-CRz7KE2D.js → fetal-weight-DNCkyeVo.js} +2 -2
- package/dist/_chunks/{fetal-weight-CRz7KE2D.js.map → fetal-weight-DNCkyeVo.js.map} +1 -1
- package/dist/_chunks/field-value-NXYczdpO.js +415 -0
- package/dist/_chunks/field-value-NXYczdpO.js.map +1 -0
- package/dist/_chunks/{file-upload-5ScQd4fE.js → file-upload-DwZcAK8D.js} +2 -1
- package/dist/_chunks/{file-upload-5ScQd4fE.js.map → file-upload-DwZcAK8D.js.map} +1 -1
- package/dist/_chunks/{freemium-paywall-DZ2mBS3w.js → freemium-paywall-WYlNO7yT.js} +2 -2
- package/dist/_chunks/{freemium-paywall-DZ2mBS3w.js.map → freemium-paywall-WYlNO7yT.js.map} +1 -1
- package/dist/_chunks/{gestational-age-calculator-BleUdhbI.js → gestational-age-calculator-CF2ISaYQ.js} +3 -3
- package/dist/_chunks/{gestational-age-calculator-BleUdhbI.js.map → gestational-age-calculator-CF2ISaYQ.js.map} +1 -1
- package/dist/_chunks/hash-CysBBS_N.js +17 -0
- package/dist/_chunks/hash-CysBBS_N.js.map +1 -0
- package/dist/_chunks/{hcg-doubling-CnjDXX6U.js → hcg-doubling-C7bmuaU3.js} +2 -2
- package/dist/_chunks/{hcg-doubling-CnjDXX6U.js.map → hcg-doubling-C7bmuaU3.js.map} +1 -1
- package/dist/_chunks/{actions-cell-renderer-DrcaxB0w.js → link-cell-renderer-CTXqtXV-.js} +715 -592
- package/dist/_chunks/link-cell-renderer-CTXqtXV-.js.map +1 -0
- package/dist/_chunks/lock-CKOIn0IK.js +15 -0
- package/dist/_chunks/lock-CKOIn0IK.js.map +1 -0
- package/dist/_chunks/{marketplace-app-shell-6T9W4Knl.js → marketplace-app-shell-Skhfp6vK.js} +3 -3
- package/dist/_chunks/{marketplace-app-shell-6T9W4Knl.js.map → marketplace-app-shell-Skhfp6vK.js.map} +1 -1
- package/dist/_chunks/notes-panel-ay8_lPrA.js +158 -0
- package/dist/_chunks/notes-panel-ay8_lPrA.js.map +1 -0
- package/dist/_chunks/{notification-card-BiESdm8q.js → notification-card-D2jiKSJJ.js} +27 -23
- package/dist/_chunks/notification-card-D2jiKSJJ.js.map +1 -0
- package/dist/_chunks/{notification-tray-Btb9oQeZ.js → notification-tray-AEun6DN2.js} +2 -2
- package/dist/_chunks/{notification-tray-Btb9oQeZ.js.map → notification-tray-AEun6DN2.js.map} +1 -1
- package/dist/_chunks/{operator-hero-CP2Nhupm.js → operator-hero-CR0Rqh4-.js} +3 -3
- package/dist/_chunks/{operator-hero-CP2Nhupm.js.map → operator-hero-CR0Rqh4-.js.map} +1 -1
- package/dist/_chunks/patient-details-Dlhqb5ig.js +675 -0
- package/dist/_chunks/patient-details-Dlhqb5ig.js.map +1 -0
- package/dist/_chunks/{patient-search-CBC_ySF6.js → patient-search-Be6cLrHR.js} +2 -2
- package/dist/_chunks/{patient-search-CBC_ySF6.js.map → patient-search-Be6cLrHR.js.map} +1 -1
- package/dist/_chunks/patient-summary-card-WySCMwwA.js +437 -0
- package/dist/_chunks/patient-summary-card-WySCMwwA.js.map +1 -0
- package/dist/_chunks/patient-table-CHxf3Oqk.js +1110 -0
- package/dist/_chunks/patient-table-CHxf3Oqk.js.map +1 -0
- package/dist/_chunks/{payment-form-DvjwYVIT.js → payment-form-CxqIXqw7.js} +2 -2
- package/dist/_chunks/{payment-form-DvjwYVIT.js.map → payment-form-CxqIXqw7.js.map} +1 -1
- package/dist/_chunks/{payment-request-card-DioWKBUq.js → payment-request-card-BcZJwu9z.js} +125 -136
- package/dist/_chunks/payment-request-card-BcZJwu9z.js.map +1 -0
- package/dist/_chunks/{pdf-viewer-D6BPfW2D.js → pdf-viewer-QfebdLOd.js} +192 -214
- package/dist/_chunks/pdf-viewer-QfebdLOd.js.map +1 -0
- package/dist/_chunks/{periodontal-chart-card-BuDEMbHE.js → periodontal-chart-card-hRRJY1NN.js} +2 -2
- package/dist/_chunks/{periodontal-chart-card-BuDEMbHE.js.map → periodontal-chart-card-hRRJY1NN.js.map} +1 -1
- package/dist/_chunks/{practice-results-KrTHqZua.js → practice-results-C6qDfxos.js} +3 -3
- package/dist/_chunks/{practice-results-KrTHqZua.js.map → practice-results-C6qDfxos.js.map} +1 -1
- package/dist/_chunks/{pregnancy-dating-DORUAOHB.js → pregnancy-dating-CRVWswD-.js} +3 -3
- package/dist/_chunks/{pregnancy-dating-DORUAOHB.js.map → pregnancy-dating-CRVWswD-.js.map} +1 -1
- package/dist/_chunks/{pregnancy-weight-gain-DVz4rr7-.js → pregnancy-weight-gain-BUNpTsH-.js} +2 -2
- package/dist/_chunks/{pregnancy-weight-gain-DVz4rr7-.js.map → pregnancy-weight-gain-BUNpTsH-.js.map} +1 -1
- package/dist/_chunks/radiograph-panel.agent-CAX-C3g3.js +558 -0
- package/dist/_chunks/radiograph-panel.agent-CAX-C3g3.js.map +1 -0
- package/dist/_chunks/{rich-text-editor-BsV7zUdg.js → rich-text-editor-DlCqPixb.js} +410 -394
- package/dist/_chunks/{rich-text-editor-BsV7zUdg.js.map → rich-text-editor-DlCqPixb.js.map} +1 -1
- package/dist/_chunks/{sign-document-B4DeRhTe.js → sign-document-By6hMOra.js} +2 -2
- package/dist/_chunks/{sign-document-B4DeRhTe.js.map → sign-document-By6hMOra.js.map} +1 -1
- package/dist/_chunks/{stepper-accordion-Dki6r9ZE.js → stepper-accordion-DC-H-8v4.js} +38 -48
- package/dist/_chunks/stepper-accordion-DC-H-8v4.js.map +1 -0
- package/dist/_chunks/tab-bar-Bv9nGNdO.js +262 -0
- package/dist/_chunks/tab-bar-Bv9nGNdO.js.map +1 -0
- package/dist/_chunks/tooth-scheme-BhQoPNBD.js +2131 -0
- package/dist/_chunks/tooth-scheme-BhQoPNBD.js.map +1 -0
- package/dist/_chunks/{transaction-chip-DK84XCBU.js → transaction-chip-CscoQbxF.js} +88 -61
- package/dist/_chunks/transaction-chip-CscoQbxF.js.map +1 -0
- package/dist/_chunks/use-clamp-overflow-DQE2kwZ9.js +20 -0
- package/dist/_chunks/use-clamp-overflow-DQE2kwZ9.js.map +1 -0
- package/dist/_chunks/use-overflow-collapse-BIOzKbni.js +32 -0
- package/dist/_chunks/use-overflow-collapse-BIOzKbni.js.map +1 -0
- package/dist/_chunks/use-persistent-state-nZwZAnE9.js +24 -0
- package/dist/_chunks/use-persistent-state-nZwZAnE9.js.map +1 -0
- package/dist/_chunks/{warning-stack-BsgaEbL8.js → warning-stack--sTrrBDA.js} +86 -101
- package/dist/_chunks/warning-stack--sTrrBDA.js.map +1 -0
- package/dist/_chunks/{workflow-map-Bdam9pGp.js → workflow-map-Dy8mLCqF.js} +3 -3
- package/dist/_chunks/{workflow-map-Bdam9pGp.js.map → workflow-map-Dy8mLCqF.js.map} +1 -1
- package/dist/_chunks/zoom-out-CgVtf2Wx.js +29 -0
- package/dist/_chunks/zoom-out-CgVtf2Wx.js.map +1 -0
- package/dist/agent/index.js +5 -4
- package/dist/agent/index.js.map +1 -1
- package/dist/agent/types.d.ts +19 -2
- package/dist/agent/types.d.ts.map +1 -1
- package/dist/agent-catalog.json +1253 -86
- package/dist/agent-i18n/en.json +108 -6
- package/dist/components/_shared/entity-card/entity-card.d.ts +6 -0
- package/dist/components/_shared/entity-card/entity-card.d.ts.map +1 -1
- package/dist/components/_shared/entity-card/index.d.ts +1 -1
- package/dist/components/_shared/entity-card/index.d.ts.map +1 -1
- package/dist/components/_shared/field-value.d.ts +21 -0
- package/dist/components/_shared/field-value.d.ts.map +1 -0
- package/dist/components/_shared/field-visibility-cog.d.ts +20 -0
- package/dist/components/_shared/field-visibility-cog.d.ts.map +1 -0
- package/dist/components/_shared/field-visibility.d.ts +36 -0
- package/dist/components/_shared/field-visibility.d.ts.map +1 -0
- package/dist/components/_shared/patient-fields.d.ts +119 -0
- package/dist/components/_shared/patient-fields.d.ts.map +1 -0
- package/dist/components/agenda-card/index.js +1 -1
- package/dist/components/agenda-tray/index.js +1 -1
- package/dist/components/ai-consent-banner/index.js +1 -1
- package/dist/components/ai-tools-rail/ai-tools-rail.d.ts +75 -0
- package/dist/components/ai-tools-rail/ai-tools-rail.d.ts.map +1 -1
- package/dist/components/ai-tools-rail/index.js +1 -1
- package/dist/components/alert/alert.d.ts +5 -0
- package/dist/components/alert/alert.d.ts.map +1 -1
- package/dist/components/alert/index.js +1 -1
- package/dist/components/anamnesis-card/index.js +1 -1
- package/dist/components/anatomy-scheme/anatomy-face-paths.d.ts +15 -0
- package/dist/components/anatomy-scheme/anatomy-face-paths.d.ts.map +1 -0
- package/dist/components/anatomy-scheme/anatomy-muscle-paths.d.ts +20 -0
- package/dist/components/anatomy-scheme/anatomy-muscle-paths.d.ts.map +1 -0
- package/dist/components/anatomy-scheme/anatomy-scheme-data.d.ts +121 -0
- package/dist/components/anatomy-scheme/anatomy-scheme-data.d.ts.map +1 -0
- package/dist/components/anatomy-scheme/anatomy-scheme.agent.d.ts +6 -0
- package/dist/components/anatomy-scheme/anatomy-scheme.agent.d.ts.map +1 -0
- package/dist/components/anatomy-scheme/anatomy-scheme.d.ts +69 -0
- package/dist/components/anatomy-scheme/anatomy-scheme.d.ts.map +1 -0
- package/dist/components/anatomy-scheme/index.d.ts +6 -0
- package/dist/components/anatomy-scheme/index.d.ts.map +1 -0
- package/dist/components/anatomy-scheme/index.js +17 -0
- package/dist/components/anatomy-scheme/index.js.map +1 -0
- package/dist/components/annotation-marker/annotation-marker.d.ts +33 -0
- package/dist/components/annotation-marker/annotation-marker.d.ts.map +1 -0
- package/dist/components/annotation-marker/index.d.ts +3 -0
- package/dist/components/annotation-marker/index.d.ts.map +1 -0
- package/dist/components/annotation-marker/index.js +7 -0
- package/dist/components/annotation-marker/index.js.map +1 -0
- package/dist/components/appointment-card/appointment-card.d.ts +25 -1
- package/dist/components/appointment-card/appointment-card.d.ts.map +1 -1
- package/dist/components/appointment-card/index.js +6 -5
- package/dist/components/appointment-card/index.js.map +1 -1
- package/dist/components/appointment-timeline/appointment-timeline.agent.d.ts +4 -0
- package/dist/components/appointment-timeline/appointment-timeline.agent.d.ts.map +1 -0
- package/dist/components/appointment-timeline/appointment-timeline.d.ts +66 -0
- package/dist/components/appointment-timeline/appointment-timeline.d.ts.map +1 -0
- package/dist/components/appointment-timeline/index.d.ts +4 -0
- package/dist/components/appointment-timeline/index.d.ts.map +1 -0
- package/dist/components/appointment-timeline/index.js +6 -0
- package/dist/components/appointment-timeline/index.js.map +1 -0
- package/dist/components/audio-recorder/index.js +1 -1
- package/dist/components/badge/badge.d.ts +6 -2
- package/dist/components/badge/badge.d.ts.map +1 -1
- package/dist/components/badge/index.js +1 -1
- package/dist/components/bishop-score/index.js +1 -1
- package/dist/components/bmi-calculator/index.js +1 -1
- package/dist/components/booking/index.js +1 -1
- package/dist/components/care-plan-card/index.js +1 -1
- package/dist/components/care-plan-entry-card/index.js +1 -1
- package/dist/components/care-plan-header/care-plan-header.agent.d.ts +4 -0
- package/dist/components/care-plan-header/care-plan-header.agent.d.ts.map +1 -0
- package/dist/components/care-plan-header/care-plan-header.d.ts +100 -0
- package/dist/components/care-plan-header/care-plan-header.d.ts.map +1 -0
- package/dist/components/care-plan-header/index.d.ts +4 -0
- package/dist/components/care-plan-header/index.d.ts.map +1 -0
- package/dist/components/care-plan-header/index.js +6 -0
- package/dist/components/care-plan-header/index.js.map +1 -0
- package/dist/components/clinical-note-card/clinical-note-card.d.ts +21 -1
- package/dist/components/clinical-note-card/clinical-note-card.d.ts.map +1 -1
- package/dist/components/clinical-note-card/index.js +1 -1
- package/dist/components/contact-profile-card/index.js +1 -1
- package/dist/components/control-room-rail/control-room-context.d.ts +53 -0
- package/dist/components/control-room-rail/control-room-context.d.ts.map +1 -0
- package/dist/components/control-room-rail/control-room-rail.d.ts +35 -0
- package/dist/components/control-room-rail/control-room-rail.d.ts.map +1 -0
- package/dist/components/control-room-rail/index.d.ts +5 -0
- package/dist/components/control-room-rail/index.d.ts.map +1 -0
- package/dist/components/control-room-rail/index.js +9 -0
- package/dist/components/control-room-rail/index.js.map +1 -0
- package/dist/components/cycle-calculator/index.js +1 -1
- package/dist/components/data-table/cell-renderers/actions-cell-renderer.d.ts +18 -0
- package/dist/components/data-table/cell-renderers/actions-cell-renderer.d.ts.map +1 -1
- package/dist/components/data-table/index.d.ts +1 -1
- package/dist/components/data-table/index.d.ts.map +1 -1
- package/dist/components/data-table/index.js +32 -31
- package/dist/components/dependent-selector/index.js +1 -1
- package/dist/components/document-scanner/index.js +1 -1
- package/dist/components/due-date-calculator/index.js +2 -2
- package/dist/components/email-input/email-input.d.ts.map +1 -1
- package/dist/components/email-input/index.js +1 -1
- package/dist/components/entity-summary/entity-summary.d.ts +43 -0
- package/dist/components/entity-summary/entity-summary.d.ts.map +1 -0
- package/dist/components/entity-summary/index.d.ts +3 -0
- package/dist/components/entity-summary/index.d.ts.map +1 -0
- package/dist/components/entity-summary/index.js +5 -0
- package/dist/components/entity-summary/index.js.map +1 -0
- package/dist/components/fetal-weight/index.js +1 -1
- package/dist/components/file-upload/index.js +1 -1
- package/dist/components/freemium-paywall/index.js +1 -1
- package/dist/components/gestational-age-calculator/index.js +1 -1
- package/dist/components/hcg-doubling/index.js +1 -1
- package/dist/components/index.d.ts +9 -0
- package/dist/components/index.d.ts.map +1 -1
- package/dist/components/notes-panel/index.d.ts +3 -0
- package/dist/components/notes-panel/index.d.ts.map +1 -0
- package/dist/components/notes-panel/index.js +5 -0
- package/dist/components/notes-panel/index.js.map +1 -0
- package/dist/components/notes-panel/notes-panel.d.ts +64 -0
- package/dist/components/notes-panel/notes-panel.d.ts.map +1 -0
- package/dist/components/notification-card/index.js +1 -1
- package/dist/components/notification-card/notification-card.d.ts.map +1 -1
- package/dist/components/notification-tray/index.js +1 -1
- package/dist/components/operator-hero/index.js +1 -1
- package/dist/components/patient-details/index.d.ts +5 -0
- package/dist/components/patient-details/index.d.ts.map +1 -0
- package/dist/components/patient-details/index.js +6 -0
- package/dist/components/patient-details/index.js.map +1 -0
- package/dist/components/patient-details/patient-details.agent.d.ts +4 -0
- package/dist/components/patient-details/patient-details.agent.d.ts.map +1 -0
- package/dist/components/patient-details/patient-details.d.ts +96 -0
- package/dist/components/patient-details/patient-details.d.ts.map +1 -0
- package/dist/components/patient-search/index.js +1 -1
- package/dist/components/patient-summary-card/index.js +1 -1
- package/dist/components/patient-summary-card/patient-summary-card.agent.d.ts.map +1 -1
- package/dist/components/patient-summary-card/patient-summary-card.d.ts +40 -1
- package/dist/components/patient-summary-card/patient-summary-card.d.ts.map +1 -1
- package/dist/components/patient-table/columns.d.ts +69 -40
- package/dist/components/patient-table/columns.d.ts.map +1 -1
- package/dist/components/patient-table/index.d.ts +2 -6
- package/dist/components/patient-table/index.d.ts.map +1 -1
- package/dist/components/patient-table/index.js +8 -9
- package/dist/components/patient-table/patient-table.d.ts +38 -4
- package/dist/components/patient-table/patient-table.d.ts.map +1 -1
- package/dist/components/patient-table/types.d.ts +52 -2
- package/dist/components/patient-table/types.d.ts.map +1 -1
- package/dist/components/patient-table/use-responsive-columns.d.ts +8 -6
- package/dist/components/patient-table/use-responsive-columns.d.ts.map +1 -1
- package/dist/components/payment-card/index.js +1 -1
- package/dist/components/payment-form/index.js +1 -1
- package/dist/components/pdf-viewer/index.js +1 -1
- package/dist/components/periodontal-chart-card/index.js +1 -1
- package/dist/components/practice-results/index.js +1 -1
- package/dist/components/pregnancy-dating/index.js +1 -1
- package/dist/components/pregnancy-weight-gain/index.js +1 -1
- package/dist/components/radiograph-panel/index.d.ts +4 -0
- package/dist/components/radiograph-panel/index.d.ts.map +1 -0
- package/dist/components/radiograph-panel/index.js +7 -0
- package/dist/components/radiograph-panel/index.js.map +1 -0
- package/dist/components/radiograph-panel/radiograph-panel.agent.d.ts +13 -0
- package/dist/components/radiograph-panel/radiograph-panel.agent.d.ts.map +1 -0
- package/dist/components/radiograph-panel/radiograph-panel.d.ts +36 -0
- package/dist/components/radiograph-panel/radiograph-panel.d.ts.map +1 -0
- package/dist/components/rich-text-editor/index.js +1 -1
- package/dist/components/rich-text-editor/rich-text-editor.d.ts.map +1 -1
- package/dist/components/sidebar/index.js +1 -1
- package/dist/components/sign-document/index.js +1 -1
- package/dist/components/stepper-accordion/index.js +1 -1
- package/dist/components/tab-bar/index.js +1 -1
- package/dist/components/tab-bar/tab-bar.d.ts +18 -1
- package/dist/components/tab-bar/tab-bar.d.ts.map +1 -1
- package/dist/components/tooth-scheme/index.d.ts +2 -2
- package/dist/components/tooth-scheme/index.d.ts.map +1 -1
- package/dist/components/tooth-scheme/index.js +30 -23
- package/dist/components/tooth-scheme/tooth-data.d.ts +112 -1
- package/dist/components/tooth-scheme/tooth-data.d.ts.map +1 -1
- package/dist/components/tooth-scheme/tooth-scheme.agent.d.ts +2 -2
- package/dist/components/tooth-scheme/tooth-scheme.agent.d.ts.map +1 -1
- package/dist/components/tooth-scheme/tooth-scheme.d.ts +75 -11
- package/dist/components/tooth-scheme/tooth-scheme.d.ts.map +1 -1
- package/dist/components/transaction-chip/index.js +1 -1
- package/dist/components/transaction-chip/transaction-chip.d.ts +2 -2
- package/dist/components/transaction-chip/transaction-chip.d.ts.map +1 -1
- package/dist/components/warning-stack/index.js +1 -1
- package/dist/components/warning-stack/warning-stack.d.ts +10 -7
- package/dist/components/warning-stack/warning-stack.d.ts.map +1 -1
- package/dist/components/workflow/index.js +1 -1
- package/dist/hooks/index.d.ts +1 -0
- package/dist/hooks/index.d.ts.map +1 -1
- package/dist/hooks/index.js +24 -22
- package/dist/hooks/index.js.map +1 -1
- package/dist/hooks/use-clamp-overflow.d.ts +19 -0
- package/dist/hooks/use-clamp-overflow.d.ts.map +1 -0
- package/dist/hooks/use-overflow-collapse.d.ts +46 -0
- package/dist/hooks/use-overflow-collapse.d.ts.map +1 -0
- package/dist/hooks/use-persistent-state.d.ts +7 -1
- package/dist/hooks/use-persistent-state.d.ts.map +1 -1
- package/dist/hooks/use-scroll-overflow.d.ts +36 -0
- package/dist/hooks/use-scroll-overflow.d.ts.map +1 -0
- package/dist/i18n/locales/ar.d.ts +308 -24
- package/dist/i18n/locales/ar.d.ts.map +1 -1
- package/dist/i18n/locales/ar.js +322 -27
- package/dist/i18n/locales/ar.js.map +1 -1
- package/dist/i18n/locales/de.d.ts +308 -24
- package/dist/i18n/locales/de.d.ts.map +1 -1
- package/dist/i18n/locales/de.js +322 -27
- package/dist/i18n/locales/de.js.map +1 -1
- package/dist/i18n/locales/el.d.ts +308 -24
- package/dist/i18n/locales/el.d.ts.map +1 -1
- package/dist/i18n/locales/el.js +322 -27
- package/dist/i18n/locales/el.js.map +1 -1
- package/dist/i18n/locales/en.d.ts +309 -32
- package/dist/i18n/locales/en.d.ts.map +1 -1
- package/dist/i18n/locales/en.js +323 -35
- package/dist/i18n/locales/en.js.map +1 -1
- package/dist/i18n/locales/es.d.ts +308 -24
- package/dist/i18n/locales/es.d.ts.map +1 -1
- package/dist/i18n/locales/es.js +322 -27
- package/dist/i18n/locales/es.js.map +1 -1
- package/dist/i18n/locales/fr.d.ts +308 -24
- package/dist/i18n/locales/fr.d.ts.map +1 -1
- package/dist/i18n/locales/fr.js +322 -27
- package/dist/i18n/locales/fr.js.map +1 -1
- package/dist/i18n/locales/hi.d.ts +308 -24
- package/dist/i18n/locales/hi.d.ts.map +1 -1
- package/dist/i18n/locales/hi.js +322 -27
- package/dist/i18n/locales/hi.js.map +1 -1
- package/dist/i18n/locales/it.d.ts +308 -24
- package/dist/i18n/locales/it.d.ts.map +1 -1
- package/dist/i18n/locales/it.js +322 -27
- package/dist/i18n/locales/it.js.map +1 -1
- package/dist/i18n/locales/ja.d.ts +308 -24
- package/dist/i18n/locales/ja.d.ts.map +1 -1
- package/dist/i18n/locales/ja.js +322 -27
- package/dist/i18n/locales/ja.js.map +1 -1
- package/dist/i18n/locales/nl.d.ts +308 -24
- package/dist/i18n/locales/nl.d.ts.map +1 -1
- package/dist/i18n/locales/nl.js +322 -27
- package/dist/i18n/locales/nl.js.map +1 -1
- package/dist/i18n/locales/pl.d.ts +308 -24
- package/dist/i18n/locales/pl.d.ts.map +1 -1
- package/dist/i18n/locales/pl.js +322 -27
- package/dist/i18n/locales/pl.js.map +1 -1
- package/dist/i18n/locales/pt.d.ts +308 -24
- package/dist/i18n/locales/pt.d.ts.map +1 -1
- package/dist/i18n/locales/pt.js +322 -27
- package/dist/i18n/locales/pt.js.map +1 -1
- package/dist/i18n/locales/ro.d.ts +308 -24
- package/dist/i18n/locales/ro.d.ts.map +1 -1
- package/dist/i18n/locales/ro.js +322 -27
- package/dist/i18n/locales/ro.js.map +1 -1
- package/dist/i18n/locales/ru.d.ts +308 -24
- package/dist/i18n/locales/ru.d.ts.map +1 -1
- package/dist/i18n/locales/ru.js +322 -27
- package/dist/i18n/locales/ru.js.map +1 -1
- package/dist/i18n/locales/sq.d.ts +308 -24
- package/dist/i18n/locales/sq.d.ts.map +1 -1
- package/dist/i18n/locales/sq.js +322 -27
- package/dist/i18n/locales/sq.js.map +1 -1
- package/dist/i18n/locales/sv.d.ts +308 -24
- package/dist/i18n/locales/sv.d.ts.map +1 -1
- package/dist/i18n/locales/sv.js +322 -27
- package/dist/i18n/locales/sv.js.map +1 -1
- package/dist/i18n/locales/tr.d.ts +308 -24
- package/dist/i18n/locales/tr.d.ts.map +1 -1
- package/dist/i18n/locales/tr.js +322 -27
- package/dist/i18n/locales/tr.js.map +1 -1
- package/dist/i18n/locales/zh.d.ts +308 -24
- package/dist/i18n/locales/zh.d.ts.map +1 -1
- package/dist/i18n/locales/zh.js +322 -27
- package/dist/i18n/locales/zh.js.map +1 -1
- package/dist/index.js +672 -623
- package/dist/index.js.map +1 -1
- package/dist/locales/ar.json +311 -27
- package/dist/locales/de.json +311 -27
- package/dist/locales/el.json +311 -27
- package/dist/locales/en.json +311 -27
- package/dist/locales/es.json +311 -27
- package/dist/locales/fr.json +311 -27
- package/dist/locales/hi.json +311 -27
- package/dist/locales/it.json +311 -27
- package/dist/locales/ja.json +311 -27
- package/dist/locales/nl.json +311 -27
- package/dist/locales/pl.json +311 -27
- package/dist/locales/pt.json +311 -27
- package/dist/locales/ro.json +311 -27
- package/dist/locales/ru.json +311 -27
- package/dist/locales/sq.json +311 -27
- package/dist/locales/sv.json +311 -27
- package/dist/locales/tr.json +311 -27
- package/dist/locales/zh.json +311 -27
- package/dist/patterns/marketplace-app-shell/index.js +1 -1
- package/dist/tokens.css +1 -1
- package/package.json +37 -1
- package/dist/_chunks/actions-cell-renderer-DrcaxB0w.js.map +0 -1
- package/dist/_chunks/ai-tools-rail-BA_sqy1A.js +0 -373
- package/dist/_chunks/ai-tools-rail-BA_sqy1A.js.map +0 -1
- package/dist/_chunks/alert-_mUKLmwA.js.map +0 -1
- package/dist/_chunks/appointment-tray-CZtvtaH-.js +0 -431
- package/dist/_chunks/appointment-tray-CZtvtaH-.js.map +0 -1
- package/dist/_chunks/badge-CqGsX32l.js.map +0 -1
- package/dist/_chunks/clinical-note-card-DqQYf_D4.js +0 -333
- package/dist/_chunks/clinical-note-card-DqQYf_D4.js.map +0 -1
- package/dist/_chunks/editable-currency-cell-renderer-kgqp_mIw.js +0 -448
- package/dist/_chunks/editable-currency-cell-renderer-kgqp_mIw.js.map +0 -1
- package/dist/_chunks/email-input-B_Y55f5G.js +0 -396
- package/dist/_chunks/notification-card-BiESdm8q.js.map +0 -1
- package/dist/_chunks/patient-summary-card-B836_fDB.js +0 -435
- package/dist/_chunks/patient-summary-card-B836_fDB.js.map +0 -1
- package/dist/_chunks/patient-table-CDuosVru.js +0 -889
- package/dist/_chunks/patient-table-CDuosVru.js.map +0 -1
- package/dist/_chunks/payment-request-card-DioWKBUq.js.map +0 -1
- package/dist/_chunks/pdf-viewer-D6BPfW2D.js.map +0 -1
- package/dist/_chunks/stepper-accordion-Dki6r9ZE.js.map +0 -1
- package/dist/_chunks/tab-bar-B1ovILzh.js +0 -105
- package/dist/_chunks/tab-bar-B1ovILzh.js.map +0 -1
- package/dist/_chunks/tooth-scheme-yBr53cvv.js +0 -1330
- package/dist/_chunks/tooth-scheme-yBr53cvv.js.map +0 -1
- package/dist/_chunks/transaction-chip-DK84XCBU.js.map +0 -1
- package/dist/_chunks/use-persistent-state-i23OWy6G.js +0 -24
- package/dist/_chunks/use-persistent-state-i23OWy6G.js.map +0 -1
- package/dist/_chunks/warning-stack-BsgaEbL8.js.map +0 -1
- package/dist/components/patient-table/cell-renderers/contact-cell.d.ts +0 -45
- package/dist/components/patient-table/cell-renderers/contact-cell.d.ts.map +0 -1
- package/dist/components/patient-table/cell-renderers/patient-identity-cell.d.ts +0 -26
- package/dist/components/patient-table/cell-renderers/patient-identity-cell.d.ts.map +0 -1
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"patient-table-CDuosVru.js","sources":["../../node_modules/lucide-react/dist/esm/icons/mail-x.js","../../node_modules/lucide-react/dist/esm/icons/message-square-off.js","../../node_modules/lucide-react/dist/esm/icons/message-square.js","../../src/components/patient-table/cell-renderers/balance-badge-cell.tsx","../../src/components/patient-table/cell-renderers/care-plan-status-cell.tsx","../../src/components/patient-table/cell-renderers/contact-cell.tsx","../../src/components/patient-table/cell-renderers/next-appointment-cell.tsx","../../src/components/patient-table/cell-renderers/patient-identity-cell.tsx","../../src/components/patient-table/columns.ts","../../src/components/patient-table/use-responsive-columns.ts","../../src/components/patient-table/patient-table.tsx"],"sourcesContent":["/**\n * @license lucide-react v1.8.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst __iconNode = [\n [\"path\", { d: \"M22 13V6a2 2 0 0 0-2-2H4a2 2 0 0 0-2 2v12c0 1.1.9 2 2 2h9\", key: \"1j9vog\" }],\n [\"path\", { d: \"m22 7-8.97 5.7a1.94 1.94 0 0 1-2.06 0L2 7\", key: \"1ocrg3\" }],\n [\"path\", { d: \"m17 17 4 4\", key: \"1b3523\" }],\n [\"path\", { d: \"m21 17-4 4\", key: \"uinynz\" }]\n];\nconst MailX = createLucideIcon(\"mail-x\", __iconNode);\n\nexport { __iconNode, MailX as default };\n//# sourceMappingURL=mail-x.js.map\n","/**\n * @license lucide-react v1.8.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst __iconNode = [\n [\n \"path\",\n {\n d: \"M19 19H6.828a2 2 0 0 0-1.414.586l-2.202 2.202A.7.7 0 0 1 2 21.286V5a2 2 0 0 1 1.184-1.826\",\n key: \"1wyg69\"\n }\n ],\n [\"path\", { d: \"m2 2 20 20\", key: \"1ooewy\" }],\n [\"path\", { d: \"M8.656 3H20a2 2 0 0 1 2 2v11.344\", key: \"mhl4k6\" }]\n];\nconst MessageSquareOff = createLucideIcon(\"message-square-off\", __iconNode);\n\nexport { __iconNode, MessageSquareOff as default };\n//# sourceMappingURL=message-square-off.js.map\n","/**\n * @license lucide-react v1.8.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst __iconNode = [\n [\n \"path\",\n {\n d: \"M22 17a2 2 0 0 1-2 2H6.828a2 2 0 0 0-1.414.586l-2.202 2.202A.71.71 0 0 1 2 21.286V5a2 2 0 0 1 2-2h16a2 2 0 0 1 2 2z\",\n key: \"18887p\"\n }\n ]\n];\nconst MessageSquare = createLucideIcon(\"message-square\", __iconNode);\n\nexport { __iconNode, MessageSquare as default };\n//# sourceMappingURL=message-square.js.map\n","import type { CustomCellRendererProps } from 'ag-grid-react';\nimport { useTranslation } from 'react-i18next';\nimport { Badge } from '../../badge/badge';\nimport type { PatientRow } from '../types';\n\n/**\n * patient-table — BalanceBadgeCell\n * ----------------------------------------------------------------------------\n * Threshold-coloured unpaid-balance badge for the patient grid.\n *\n * Reads {@link PatientRow.unpaidAmount} (integer cents), formats it to the\n * display currency via `Intl.NumberFormat` (cents → major unit at the render\n * boundary — see types.ts), and wraps the result in a kit {@link Badge} whose\n * semantic variant buckets by outstanding-balance threshold:\n *\n * | cents bucket | meaning | Badge variant |\n * | ----------------------- | ------------------ | ------------- |\n * | `0` | settled | `success` |\n * | `> 0` and `<= 50000` | small balance | `warning` |\n * | `> 50000` | overdue / large | `error` |\n *\n * NOTE on the variant name: the task brief calls the red bucket\n * `destructive`; the kit `Badge` exposes that semantic tier as the `error`\n * variant (backed by the `--destructive` / `--error-foreground` tokens). There\n * is no `destructive` Badge variant, so `error` is the correct destructive-tier\n * mapping — recorded here so the brief↔code discrepancy is intentional.\n *\n * The bucket meaning is colour-coded, so it is also surfaced as an sr-only\n * status word inside the badge (alongside the `withDot` indicator) — the\n * threshold tier is never conveyed by colour alone.\n *\n * Returns `null` when `unpaidAmount` is missing / non-finite (empty cell), per\n * the data-table renderer convention.\n */\n\n/** Display + threshold-classification result for a single balance value. */\ntype BalanceBucket = {\n variant: 'success' | 'warning' | 'error';\n /** i18n key suffix under `ui.patientTable.balance.status.*`. */\n statusKey: 'settled' | 'pending' | 'overdue';\n};\n\n/** Cents at or below which a non-zero balance is treated as a small balance. */\nconst SMALL_BALANCE_CENTS_MAX = 50000;\n\nfunction classifyBalance(cents: number): BalanceBucket {\n if (cents === 0) return { variant: 'success', statusKey: 'settled' };\n if (cents <= SMALL_BALANCE_CENTS_MAX)\n return { variant: 'warning', statusKey: 'pending' };\n return { variant: 'error', statusKey: 'overdue' };\n}\n\nfunction readUnpaidCents(value: unknown): number | null {\n if (value == null || value === '') return null;\n const n = typeof value === 'number' ? value : Number(value);\n return Number.isFinite(n) ? n : null;\n}\n\nexport interface BalanceBadgeCellParams {\n /** ISO 4217 currency code used to format the balance. Default `'EUR'`. */\n currency?: string;\n /**\n * `Intl.NumberFormat` escape hatch, merged on top of the currency defaults.\n * E.g. `{ maximumFractionDigits: 0 }` for whole-currency display.\n */\n options?: Intl.NumberFormatOptions;\n}\n\nexport function BalanceBadgeCell(\n props: CustomCellRendererProps<PatientRow> & BalanceBadgeCellParams,\n) {\n const { value, currency = 'EUR', options } = props;\n const { t, i18n } = useTranslation('ui');\n\n const cents = readUnpaidCents(value);\n if (cents === null) return null;\n\n const locale = i18n.language || 'en';\n const formatted = new Intl.NumberFormat(locale, {\n style: 'currency',\n currency,\n ...options,\n }).format(cents / 100);\n\n const { variant, statusKey } = classifyBalance(cents);\n const status = t(`patientTable.balance.status.${statusKey}`);\n\n return (\n <Badge variant={variant} withDot size=\"sm\" className=\"ds:tabular-nums\">\n {/* Visible: the formatted amount. The threshold meaning is colour-coded,\n so the status word is surfaced to AT as sr-only text — the bucket is\n never conveyed by colour alone. */}\n <span>{formatted}</span>\n <span className=\"ds:sr-only\">{status}</span>\n </Badge>\n );\n}\n","/**\n * care-plan-status-cell — patient-table cell renderer\n * ----------------------------------------------------------------------------\n * A thin domain preset over the data-table `StatusCellRenderer` / kit `Badge`:\n * it bakes the patient care-plan lifecycle `variantMap` so consumers don't have\n * to re-declare it on every column, and localises the label via the `ui`\n * namespace (`ui.patientTable.carePlanStatus.*`).\n *\n * Reads `PatientRow.carePlanStatus` (preferring `data.carePlanStatus`, falling\n * back to AG Grid's resolved `value`), maps it to a Badge variant:\n *\n * accepted → success estimate → info none → neutral (muted)\n *\n * GROUND-TRUTH NOTES (vs. the task brief):\n * • `StatusCellRenderer` is not exported from a barrel and is a tiny wrapper\n * around `Badge`; this preset composes `Badge` directly (same primitive,\n * no extra indirection) rather than wrapping the wrapper.\n * • The brand says the \"muted\" variant is `none`; `Badge`'s neutral variant is\n * already the muted grey chip, so `none → 'neutral'`.\n * • No event handling: a status badge is presentational, so there are no\n * provided callbacks to wire.\n */\nimport type { CustomCellRendererProps } from 'ag-grid-react';\nimport { useTranslation } from 'react-i18next';\nimport { Badge } from '../../badge/badge';\nimport type { PatientCarePlanStatus, PatientRow } from '../types';\n\n/** Badge variant baked per care-plan lifecycle state. */\ntype CarePlanBadgeVariant = 'success' | 'info' | 'neutral';\n\n/**\n * Lifecycle → Badge-variant map. Frozen so it can't be mutated by a consumer\n * holding the reference.\n */\nconst CARE_PLAN_VARIANT_MAP: Readonly<\n Record<PatientCarePlanStatus, CarePlanBadgeVariant>\n> = {\n accepted: 'success',\n estimate: 'info',\n none: 'neutral',\n};\n\n/**\n * `cellRendererParams` for `CarePlanStatusCell`.\n *\n * The lifecycle status, label source and variant map are all baked in, so the\n * only knob is the Badge size — defaults to the compact `sm` chip that fits the\n * standard AG Grid row height.\n */\nexport interface CarePlanStatusCellParams {\n /** Badge size. Defaults to `'sm'` to fit the standard row height. */\n size?: 'sm' | 'md' | 'lg';\n}\n\nfunction isCarePlanStatus(value: unknown): value is PatientCarePlanStatus {\n return value === 'accepted' || value === 'estimate' || value === 'none';\n}\n\n/**\n * Patient care-plan lifecycle badge cell.\n *\n * Pass as `cellRenderer` on the `carePlanStatus` column; the patient\n * `variantMap` and localisation are handled internally.\n */\nexport function CarePlanStatusCell(\n props: CustomCellRendererProps<PatientRow, PatientCarePlanStatus> &\n CarePlanStatusCellParams,\n) {\n const { t } = useTranslation('ui');\n const { data, value, size = 'sm' } = props;\n\n // Prefer the typed row field; fall back to AG Grid's resolved cell value.\n const raw = data?.carePlanStatus ?? value;\n if (!isCarePlanStatus(raw)) return null;\n\n const variant = CARE_PLAN_VARIANT_MAP[raw];\n\n return (\n <Badge variant={variant} withDot size={size}>\n {t(`patientTable.carePlanStatus.${raw}`)}\n </Badge>\n );\n}\n","import type { CustomCellRendererProps } from 'ag-grid-react';\nimport { useTranslation } from 'react-i18next';\nimport { cva } from 'class-variance-authority';\nimport { Mail, MailX, MessageSquare, MessageSquareOff } from 'lucide-react';\nimport { Tooltip } from '../../tooltip';\nimport type { PatientRow } from '../types';\n\n/* -------------------------------------------------------------------------- */\n/* Params */\n/* -------------------------------------------------------------------------- */\n\n/**\n * `cellRendererParams` for {@link ContactCell}.\n *\n * Passed through AG Grid's `cellRendererParams` on the column definition.\n * Everything the renderer needs about the patient comes from the row `data`\n * (PHI stays as text content — never a DOM attribute); these params only tune\n * presentation.\n */\nexport interface ContactCellParams {\n /**\n * Mask the email line — replaces the address with a fixed placeholder so the\n * cell still communicates that an email exists without exposing it (privacy /\n * screen-share contexts). The phone line and eligibility affordances are\n * unaffected. Default `false`.\n */\n hideDetails?: boolean;\n}\n\n/* -------------------------------------------------------------------------- */\n/* CVA — eligibility affordance */\n/* -------------------------------------------------------------------------- */\n\nconst eligibilityVariants = cva(\n [\n 'ds:inline-flex ds:items-center ds:justify-center ds:size-4 ds:shrink-0',\n 'ds:rounded-[var(--radius-sm)]',\n ].join(' '),\n {\n variants: {\n eligible: {\n // Eligible → success-tinted glyph; ineligible → muted/greyed glyph.\n true: 'ds:text-[color:var(--success)]',\n false: 'ds:text-[color:var(--muted-foreground)]',\n },\n },\n defaultVariants: {\n eligible: false,\n },\n },\n);\n\n/* -------------------------------------------------------------------------- */\n/* ContactCell */\n/* -------------------------------------------------------------------------- */\n\n/**\n * Contact + reminder-eligibility cell for the patient grid.\n *\n * Renders the primary phone (`phoneNumbers[0].number`) and email stacked, plus\n * two small inline status glyphs:\n *\n * • SMS-reminder eligibility — eligible when **any** phone number has\n * `smsEnabled`.\n * • Email-reminder eligibility — eligible when `emailEnabled && emailValid`.\n *\n * The glyphs are informational only — no row action is dispatched and they are\n * not keyboard-focusable. Each is a labelled `role=\"img\"` element: the\n * eligibility state is exposed to assistive tech through its `aria-label`, with\n * a pointer `Tooltip` reinforcing it for sighted users.\n *\n * Honours the `hideDetails` `cellRendererParam`: when `true`, the email address\n * is masked behind a placeholder while still indicating an address is on file.\n *\n * PHI rule (PRS 26 §6): phone / email reach the DOM as **text content only** —\n * never as `data-*` attributes.\n */\nexport function ContactCell(\n props: CustomCellRendererProps<PatientRow> & ContactCellParams,\n) {\n const { data, hideDetails = false } = props;\n const { t } = useTranslation('ui');\n\n if (!data) return null;\n\n const { phoneNumbers, email, emailEnabled, emailValid } = data;\n\n const primaryPhone = phoneNumbers?.[0]?.number ?? '';\n const hasEmail = Boolean(email);\n\n const smsEligible = (phoneNumbers ?? []).some((p) => p.smsEnabled);\n const emailEligible = Boolean(emailEnabled && emailValid);\n\n // Nothing to surface for this row.\n if (!primaryPhone && !hasEmail) return null;\n\n const emailText = hideDetails\n ? t('patientTable.contact.emailMasked')\n : (email ?? '');\n\n const smsLabel = smsEligible\n ? t('patientTable.contact.smsEligible')\n : t('patientTable.contact.smsIneligible');\n\n const emailLabel = emailEligible\n ? t('patientTable.contact.emailEligible')\n : t('patientTable.contact.emailIneligible');\n\n return (\n <span className=\"ds:inline-flex ds:items-center ds:gap-[var(--spacing-sm)]\">\n <span className=\"ds:flex ds:flex-col ds:gap-[var(--spacing-2xs)] ds:min-w-0 ds:leading-tight\">\n {primaryPhone ? (\n <span className=\"type-meta ds:truncate ds:text-start\">\n {primaryPhone}\n </span>\n ) : null}\n {hasEmail ? (\n <span className=\"type-meta ds:truncate ds:text-start ds:text-[color:var(--muted-foreground)]\">\n {emailText}\n </span>\n ) : null}\n </span>\n\n <span className=\"ds:inline-flex ds:items-center ds:gap-[var(--spacing-2xs)] ds:shrink-0\">\n <Tooltip label={smsLabel}>\n <span\n role=\"img\"\n aria-label={smsLabel}\n className={eligibilityVariants({ eligible: smsEligible })}\n >\n {smsEligible ? (\n <MessageSquare aria-hidden size={14} className=\"ds:size-[14px]\" />\n ) : (\n <MessageSquareOff\n aria-hidden\n size={14}\n className=\"ds:size-[14px]\"\n />\n )}\n </span>\n </Tooltip>\n\n <Tooltip label={emailLabel}>\n <span\n role=\"img\"\n aria-label={emailLabel}\n className={eligibilityVariants({ eligible: emailEligible })}\n >\n {emailEligible ? (\n <Mail aria-hidden size={14} className=\"ds:size-[14px]\" />\n ) : (\n <MailX aria-hidden size={14} className=\"ds:size-[14px]\" />\n )}\n </span>\n </Tooltip>\n </span>\n </span>\n );\n}\n\nContactCell.displayName = 'ContactCell';\n","/**\n * next-appointment-cell — patient-table cell renderer\n * ----------------------------------------------------------------------------\n * Smart upcoming-appointment cell. Renders `PatientRow.nextAppointment` as a\n * locale-aware *relative* phrase (\"in 3 days\", \"tomorrow\") via the kit\n * `Timestamp`, mirroring the `relative` preset of the data-table\n * `DateCellRenderer`. When the appointment falls within a configurable window\n * (default 7 days from now), the cell takes a token-bound emphasis treatment so\n * imminent visits stand out at a glance. When `nextAppointment` is absent it\n * renders a muted \"no upcoming\" empty-state label.\n *\n * Reads `PatientRow.nextAppointment` (preferring the typed `data.nextAppointment`\n * field, falling back to AG Grid's resolved `value`).\n *\n * GROUND-TRUTH NOTES (vs. the task brief):\n * • The brief asked for a highlight \"within 7 days\". That window is exposed as\n * `soonWithinDays` (default 7) so a column can tune it without a new renderer,\n * matching the param-driven shape of the other patient renderers.\n * • The brief named `Avatar`, `Tag`, `Icon`, `IconButton`, `Tooltip` as\n * candidate primitives. This cell is purely presentational (a date + optional\n * emphasis), so it composes only `Timestamp` plus a decorative lucide glyph —\n * the same minimal-primitive approach the analogous `CarePlanStatusCell`\n * takes. There is no `Icon`/`IconButton` standalone component in the kit\n * (renderers use `lucide-react` glyphs directly), and no row callback is\n * provided, so no interactive affordance is wired.\n * • The emphasis is a CVA `tone` variant bound entirely to design tokens\n * (`--warning-foreground`); NO colour is hardcoded and nothing is pushed into\n * AG Grid `cellStyle`/`cellClass`.\n * • PHI rule (PRS 26 §6): no row field reaches a DOM `data-*` attribute here.\n */\nimport { cva, type VariantProps } from 'class-variance-authority';\nimport { CalendarClock } from 'lucide-react';\nimport type { CustomCellRendererProps } from 'ag-grid-react';\nimport { useTranslation } from 'react-i18next';\nimport { Timestamp } from '../../timestamp';\nimport type { PatientRow } from '../types';\n\n/* ------------------------------------------------------------------ */\n/* CVA — cell wrapper */\n/* */\n/* `tone` is the only stylistic axis: `soon` lifts the row to a */\n/* token-bound warning emphasis, `default` inherits the cell colour. */\n/* ------------------------------------------------------------------ */\n\nconst nextAppointmentVariants = cva(\n 'ds:inline-flex ds:items-center ds:gap-[var(--spacing-xs)] ds:whitespace-nowrap',\n {\n variants: {\n tone: {\n default: '',\n // Imminent visit: warning foreground token + medium weight. Fully\n // token-bound — no literal colour, no AG Grid cellStyle.\n soon: 'ds:text-[color:var(--warning-foreground)] ds:font-medium',\n // Absent appointment: muted empty state.\n empty: 'ds:text-[color:var(--muted-foreground)]',\n },\n },\n defaultVariants: { tone: 'default' },\n },\n);\n\ntype NextAppointmentVariantProps = VariantProps<typeof nextAppointmentVariants>;\n\n/* ------------------------------------------------------------------ */\n/* Params */\n/* ------------------------------------------------------------------ */\n\n/**\n * `cellRendererParams` for {@link NextAppointmentCell}.\n *\n * Localisation and the relative-date formatting are handled internally; the\n * only knob is the imminence window.\n */\nexport interface NextAppointmentCellParams {\n /**\n * Highlight the cell when the appointment is at most this many days away\n * (and not in the past). Defaults to `7`. A value `<= 0` disables the\n * highlight.\n */\n soonWithinDays?: number;\n}\n\nconst DAY_MS = 24 * 60 * 60 * 1000;\nconst DEFAULT_SOON_WITHIN_DAYS = 7;\n\nfunction toTime(value: unknown): number | null {\n if (value == null || value === '') return null;\n const t =\n value instanceof Date\n ? value.getTime()\n : typeof value === 'number'\n ? value\n : new Date(String(value)).getTime();\n return Number.isNaN(t) ? null : t;\n}\n\n/**\n * Resolve the emphasis tone for a parsed appointment time. `soon` covers any\n * upcoming visit within the window (including today); past appointments fall\n * back to `default`.\n */\nfunction resolveTone(\n time: number,\n soonWithinDays: number,\n): NonNullable<NextAppointmentVariantProps['tone']> {\n if (soonWithinDays <= 0) return 'default';\n const deltaMs = time - Date.now();\n if (deltaMs < 0) return 'default';\n return deltaMs <= soonWithinDays * DAY_MS ? 'soon' : 'default';\n}\n\n/* ------------------------------------------------------------------ */\n/* NextAppointmentCell */\n/* ------------------------------------------------------------------ */\n\n/**\n * Smart upcoming-appointment cell.\n *\n * Pass as `cellRenderer` on the `nextAppointment` column; the relative\n * formatting, imminence emphasis and empty state are handled internally.\n */\nexport function NextAppointmentCell(\n props: CustomCellRendererProps<PatientRow, string> &\n NextAppointmentCellParams,\n) {\n const { t } = useTranslation('ui');\n const { data, value, soonWithinDays = DEFAULT_SOON_WITHIN_DAYS } = props;\n\n // Prefer the typed row field; fall back to AG Grid's resolved cell value.\n const time = toTime(data?.nextAppointment ?? value);\n\n if (time === null) {\n return (\n <span className={nextAppointmentVariants({ tone: 'empty' })}>\n {t('patientTable.nextAppointment.none')}\n </span>\n );\n }\n\n const tone = resolveTone(time, soonWithinDays);\n\n return (\n <span className={nextAppointmentVariants({ tone })}>\n {tone === 'soon' ? (\n <CalendarClock aria-hidden=\"true\" className=\"ds:size-3.5 ds:shrink-0\" />\n ) : null}\n <Timestamp value={time} format=\"relative\" shape=\"bare\" />\n </span>\n );\n}\n","/**\n * patient-identity-cell — patient-table composite identity cell renderer\n * ----------------------------------------------------------------------------\n * Renders the patient's Avatar (photo with initials fallback), full name and\n * Italian fiscal code as a single cell that links to the patient detail.\n *\n * Mirrors the kit's built-in `LinkCellRenderer` anchor/button handling\n * (src/components/data-table/cell-renderers/link-cell-renderer.tsx) and the\n * Avatar usage of `UserCellRenderer`. It surfaces an href when one can be\n * derived, otherwise falls back to a styled <button> that calls `onSelect`.\n *\n * PHI rule (26-agent-readiness §6): only `row.id` may appear in DOM `data-*`\n * attributes. Name and fiscal code are rendered as text content only — never as\n * attribute values or selectors.\n */\nimport type { MouseEvent } from 'react';\nimport type { CustomCellRendererProps } from 'ag-grid-react';\nimport { useTranslation } from 'react-i18next';\nimport { Avatar } from '../../avatar/avatar';\nimport type { PatientRow } from '../types';\n\n/** Derive a value directly or from the row, mirroring LinkCellRenderer. */\ntype Getter<T> = T | ((row: PatientRow) => T | undefined);\n\nexport interface PatientIdentityCellParams {\n /**\n * Anchor href for the patient detail — a string, or a function deriving it\n * from the row (e.g. `(row) => \\`/patients/${row.id}\\``). When omitted the\n * cell renders a button that invokes `onSelect` instead.\n */\n href?: Getter<string>;\n /**\n * Fallback / additional handler. Invoked with the row on click. When `href`\n * is absent the click default is prevented so navigation is driven entirely\n * by this callback.\n */\n onSelect?: (row: PatientRow) => void;\n}\n\nfunction resolve<T>(\n source: Getter<T> | undefined,\n row: PatientRow,\n): T | undefined {\n if (typeof source === 'function') {\n return (source as (row: PatientRow) => T | undefined)(row);\n }\n return source;\n}\n\n// Only allow same-origin / absolute http(s) / hash links into the DOM href.\n// Anything else collapses to '#', matching LinkCellRenderer's safeHref.\nfunction safeHref(href: string): string {\n return /^(https?:\\/\\/|\\/|#)/i.test(href) ? href : '#';\n}\n\nfunction fullName(row: PatientRow): string {\n return [row.firstName, row.lastName].filter(Boolean).join(' ').trim();\n}\n\n/**\n * Composite identity cell: Avatar + bold name + muted fiscal-code caption,\n * wrapped in a link (or button) to the patient detail. Returns `null` for\n * pinned (header/total) rows and for empty rows so the cell stays blank.\n */\nexport function PatientIdentityCell(\n props: CustomCellRendererProps<PatientRow> & PatientIdentityCellParams,\n) {\n const { data, node, href, onSelect } = props;\n const { t } = useTranslation('ui');\n\n // Pinned top/bottom rows (e.g. an aggregate total row) carry no patient\n // identity — skip them, exactly as an empty row.\n if (!data || node?.rowPinned) return null;\n\n const name = fullName(data);\n if (!name) return null;\n\n const resolvedHref = resolve(href, data);\n const fiscalCode = data.italianFiscalCode?.trim() || undefined;\n\n // Accessible name for the whole control — the visible name plus an\n // explicit \"View {{name}}\" so screen-reader users know it navigates.\n const linkLabel = t('patientTable.identity.viewPatient', { name });\n\n const interactiveClasses = [\n 'ds:group',\n 'ds:flex ds:items-center ds:gap-[var(--spacing-sm)]',\n 'ds:text-start',\n 'ds:rounded-[var(--radius-sm)]',\n 'ds:focus-visible:outline-[length:var(--focus-ring-width)]',\n 'ds:focus-visible:outline-solid',\n 'ds:focus-visible:outline-[color:var(--ring)]',\n 'ds:focus-visible:outline-offset-[length:var(--focus-ring-offset)]',\n ].join(' ');\n\n const handleClick = (event: MouseEvent) => {\n if (!onSelect) return;\n if (!resolvedHref) event.preventDefault();\n // Stop the grid's row-click selection from also firing.\n event.stopPropagation();\n onSelect(data);\n };\n\n const body = (\n <>\n <Avatar\n name={name}\n src={data.avatarUrl}\n size=\"sm\"\n aria-hidden=\"true\"\n className=\"ds:shrink-0\"\n />\n <span className=\"ds:flex ds:min-w-0 ds:flex-col ds:leading-tight\">\n <span className=\"ds:truncate ds:font-semibold ds:text-[color:var(--foreground)] ds:group-hover:underline\">\n {name}\n </span>\n {fiscalCode ? (\n <span className=\"type-meta ds:truncate ds:text-[color:var(--muted-foreground)]\">\n <span className=\"ds:sr-only\">\n {t('patientTable.identity.fiscalCodeLabel')}\n {': '}\n </span>\n {fiscalCode}\n </span>\n ) : null}\n </span>\n </>\n );\n\n return resolvedHref ? (\n <a\n href={safeHref(resolvedHref)}\n aria-label={linkLabel}\n onClick={handleClick}\n className={interactiveClasses}\n >\n {body}\n </a>\n ) : (\n <button\n type=\"button\"\n aria-label={linkLabel}\n onClick={handleClick}\n className={`ds:appearance-none ds:bg-transparent ds:p-0 ${interactiveClasses}`}\n >\n {body}\n </button>\n );\n}\n","/**\n * patient-table — column definitions\n * ----------------------------------------------------------------------------\n * `buildPatientColumns(t, opts)` returns the ordered `ColDef<PatientRow>[]` for\n * the patient grid: one leaf column per the workflow plan's 17-column spec, each\n * wiring the right cell renderer + the right kit filter + floatingFilter, a\n * localised `headerName` (from `ui.patientTable.column.*`) and a stable `colId`.\n *\n * RESPONSIVE TIER MECHANISM\n * -------------------------\n * Each column carries a custom `responsiveTier` (`P0`–`P3`) property. AG Grid's\n * `ColDef` is an open/extensible shape — extra properties on a colDef are passed\n * through untouched at runtime — but its TS type is closed, so a bare extra key\n * would not type-check. We therefore type each entry as `PatientColDefWithTier`\n * (`PatientColDef & { responsiveTier?: ResponsiveTier }`) and read the tier back\n * via the exported {@link getResponsiveTier} helper rather than through AG Grid's\n * loosely-typed `context: any` field — so the tier is fully typed end-to-end with\n * no `any`. The `useResponsiveColumns` hook consumes these tiers to toggle column\n * visibility by grid-container width.\n *\n * GROUND-TRUTH NOTES (vs. the task brief / workflow plan):\n * • The `select` checkbox column is NOT emitted here. The spec marks it\n * \"(built-in)\" — it is provided by the grid's `rowSelection` config\n * (`headerCheckbox: true, checkboxes: true`, see data-table.tsx), not as a\n * leaf colDef. It is always P0 and grid-managed, so the responsive hook never\n * touches it. `PatientColumnId` still lists `'select'` for ColumnToggle/agent\n * addressing parity.\n * • There is no standalone `Icon`/`IconButton` colDef primitive; the actions\n * column uses the kit's `ActionsCellRenderer` with `PatientRowAction`-shaped\n * `ActionDef`s. Its `collapsed` getter (`opts.getActionsCompact`) drives the\n * 180→88px compact density from the spec without rebuilding column state.\n * • `Default insurance` and `Fiscal code` are plain text columns (no dedicated\n * renderer) per the spec; they still get a `TextFilter` + floating filter.\n * • No colour, spacing, radius or font literal appears in any ColDef\n * `cellStyle`/`cellClass` here — only token-bound `ds:` utility classes — so\n * the AG Grid theme bridge (`ag-grid-theme.css`) stays in control of theming.\n * • PHI rule (PRS 26 §6): no `PatientRow` field other than `id` is ever placed\n * in a DOM `data-*` attribute. Renderers surface name/contact/DOB as text\n * content only; these defs pass values, not attributes.\n */\nimport type { TFunction } from 'i18next';\nimport { Eye, Mail, MessageSquare, Pencil, Trash2, Users } from 'lucide-react';\nimport { createElement } from 'react';\nimport {\n ActionsCellRenderer,\n DateCellRenderer,\n DateRangeFilter,\n DateRangeFloatingFilter,\n NumberFilter,\n NumberFloatingFilter,\n SelectFilter,\n SelectFloatingFilter,\n TagListCellRenderer,\n TextFilter,\n TextFloatingFilter,\n TypeaheadFilter,\n TypeaheadFloatingFilter,\n UserCellRenderer,\n type ActionDef,\n type UserCellValue,\n} from '../data-table';\nimport { BalanceBadgeCell } from './cell-renderers/balance-badge-cell';\nimport { CarePlanStatusCell } from './cell-renderers/care-plan-status-cell';\nimport { ContactCell } from './cell-renderers/contact-cell';\nimport { NextAppointmentCell } from './cell-renderers/next-appointment-cell';\nimport { PatientIdentityCell } from './cell-renderers/patient-identity-cell';\nimport type {\n PatientColDef,\n PatientColumnDef,\n PatientColumnId,\n PatientRow,\n PatientRowAction,\n ResponsiveTier,\n} from './types';\n\n/* -------------------------------------------------------------------------- */\n/* Responsive-tier extension */\n/* -------------------------------------------------------------------------- */\n\n/**\n * A patient leaf column carrying its responsive-priority tier. AG Grid passes\n * the extra `responsiveTier` key through untouched; we keep it strongly typed\n * (no `any`, no reliance on AG Grid's `context: any`) so the responsive hook can\n * read it back via {@link getResponsiveTier}.\n */\nexport type PatientColDefWithTier = PatientColDef & {\n /**\n * Responsive priority. Lower numbers survive longer as the grid narrows:\n * `P0` always visible, `P3` first to hide. Consumed by `useResponsiveColumns`.\n */\n responsiveTier?: ResponsiveTier;\n};\n\n/**\n * Read the responsive tier off a column definition. Returns `undefined` for\n * columns that opt out of responsive toggling (e.g. the pinned Identity / pinned\n * Actions columns deliberately omit a tier so they never auto-hide).\n */\nexport function getResponsiveTier(\n colDef: PatientColumnDef,\n): ResponsiveTier | undefined {\n return (colDef as PatientColDefWithTier).responsiveTier;\n}\n\n/* -------------------------------------------------------------------------- */\n/* Options */\n/* -------------------------------------------------------------------------- */\n\n/** Options threaded into {@link buildPatientColumns}. */\nexport interface BuildPatientColumnsOptions {\n /**\n * Mask sensitive contact details (email) in the Contact/Email cells. Forwarded\n * to `ContactCell`'s `hideDetails` param. Default `false`.\n */\n hideDetails?: boolean;\n /**\n * Live getter for the actions-column density. When it returns `true`, the\n * `ActionsCellRenderer` collapses its inline buttons into a single \"…\" overflow\n * menu (the spec's 180→88px compact density). Reading via a getter lets a\n * density toggle flip without rebuilding column defs (preserves column state) —\n * call `api.refreshCells({ force: true })` after flipping the backing value.\n * Defaults to a getter that always returns `false`.\n */\n getActionsCompact?: () => boolean;\n /**\n * Invoked when a per-row action button is activated, with the resolved action\n * descriptor and the patient row. Only `row.id` ever leaves this boundary into\n * persistence / agent surfaces — never PHI.\n */\n onRowAction?: (action: PatientRowAction, patient: PatientRow) => void;\n /**\n * Derive the patient-detail href for the Identity cell, e.g.\n * `(row) => \\`/patients/${row.id}\\``. When omitted the Identity cell renders a\n * button that calls `onRowAction` with the `show` action instead.\n */\n identityHref?: string | ((row: PatientRow) => string | undefined);\n}\n\n/* -------------------------------------------------------------------------- */\n/* Row actions */\n/* -------------------------------------------------------------------------- */\n\n/**\n * Build the per-row `ActionDef`s for the actions column. Each is mapped from the\n * spec's closed action set; `hidden` / `disabled` predicates encode the spec's\n * per-row rules (e.g. `sendEmailReminder` hidden when `!emailEnabled`).\n *\n * Bridges the kit `ActionDef<PatientRow>` shape (icon/label/onClick) to the\n * patient `onRowAction(action, patient)` contract by re-deriving a\n * `PatientRowAction` descriptor on click.\n */\nfunction buildRowActions(\n t: TFunction,\n onRowAction: BuildPatientColumnsOptions['onRowAction'],\n): ActionDef<PatientRow>[] {\n const dispatch =\n (action: PatientRowAction) =>\n (patient: PatientRow): void => {\n onRowAction?.(action, patient);\n };\n\n // Each entry pairs the kit ActionDef (what the renderer needs) with the\n // patient-typed descriptor handed back to `onRowAction`.\n const make = (\n action: PatientRowAction,\n overrides: Omit<ActionDef<PatientRow>, 'label' | 'onClick' | 'icon'>,\n ): ActionDef<PatientRow> => ({\n icon: action.icon,\n label: action.label,\n variant: action.variant,\n onClick: dispatch(action),\n ...overrides,\n });\n\n return [\n make(\n {\n id: 'show',\n label: t('patientTable.actions.show'),\n icon: createElement(Eye, { 'aria-hidden': 'true' }),\n },\n {},\n ),\n make(\n {\n id: 'edit',\n label: t('patientTable.actions.edit'),\n icon: createElement(Pencil, { 'aria-hidden': 'true' }),\n },\n {},\n ),\n make(\n {\n id: 'sendEmailReminder',\n label: t('patientTable.actions.sendEmailReminder'),\n icon: createElement(Mail, { 'aria-hidden': 'true' }),\n },\n // Hidden when the patient has email contact disabled (spec).\n { hidden: (patient) => !patient.emailEnabled },\n ),\n make(\n {\n id: 'sendSmsReminder',\n label: t('patientTable.actions.sendSmsReminder'),\n icon: createElement(MessageSquare, { 'aria-hidden': 'true' }),\n },\n // Hidden when no phone number is SMS-enabled (spec).\n {\n hidden: (patient) =>\n !(patient.phoneNumbers ?? []).some((p) => p.smsEnabled),\n },\n ),\n make(\n {\n id: 'reassign',\n label: t('patientTable.actions.reassign'),\n icon: createElement(Users, { 'aria-hidden': 'true' }),\n },\n {},\n ),\n make(\n {\n id: 'delete',\n label: t('patientTable.actions.delete'),\n icon: createElement(Trash2, { 'aria-hidden': 'true' }),\n variant: 'destructive',\n },\n // Disabled (with a reason) for archived patients — the row model's\n // closest \"cannot delete\" signal. Surfaced as the inline tooltip.\n {\n disabled: (patient) => Boolean(patient.isArchived),\n disabledReason: t('patientTable.actions.deleteLocked'),\n },\n ),\n ];\n}\n\n/* -------------------------------------------------------------------------- */\n/* buildPatientColumns */\n/* -------------------------------------------------------------------------- */\n\nconst NO = () => false;\n\n/**\n * Build the ordered patient-grid column definitions.\n *\n * @param t `react-i18next` translation fn (default `ui` namespace).\n * @param opts See {@link BuildPatientColumnsOptions} — density getter, row-action\n * callback, detail masking, identity href.\n * @returns Ordered `PatientColumnDef[]`. Leaf columns carry a `responsiveTier`\n * (read via {@link getResponsiveTier}); the pinned Identity and\n * Actions columns omit it so they never auto-hide.\n */\nexport function buildPatientColumns(\n t: TFunction,\n opts: BuildPatientColumnsOptions = {},\n): PatientColumnDef[] {\n const {\n hideDetails = false,\n getActionsCompact = NO,\n onRowAction,\n identityHref,\n } = opts;\n\n const actions = buildRowActions(t, onRowAction);\n\n const genderLabels: Record<NonNullable<PatientRow['gender']>, string> = {\n m: t('patientTable.gender.m'),\n f: t('patientTable.gender.f'),\n x: t('patientTable.gender.x'),\n };\n\n const header = (id: PatientColumnId): string =>\n t(`patientTable.column.${id}`);\n\n const columns: PatientColDefWithTier[] = [\n /* ── Identity (P0, pinned-start) ──────────────────────────────── */\n {\n colId: 'identity',\n headerName: header('identity'),\n // Pinned to the inline-start edge so the patient stays anchored while the\n // lower-priority field columns scroll. AG Grid `pinned` is physical; the\n // hook/grid set `enableRtl` so logical start resolves correctly per dir.\n pinned: 'left',\n cellRenderer: PatientIdentityCell,\n cellRendererParams: {\n href: identityHref,\n // When no detail href is supplied the cell renders a button; route its\n // click through the same `show` row action.\n onSelect: onRowAction\n ? (row: PatientRow) =>\n onRowAction(\n { id: 'show', label: t('patientTable.actions.show') },\n row,\n )\n : undefined,\n },\n // Sort + typeahead read the composed full name.\n valueGetter: (params) =>\n params.data\n ? [params.data.firstName, params.data.lastName]\n .filter(Boolean)\n .join(' ')\n .trim()\n : '',\n filter: TypeaheadFilter,\n floatingFilterComponent: TypeaheadFloatingFilter,\n minWidth: 220,\n flex: 2,\n // Identity is never auto-hidden (no tier) — it is the row anchor.\n },\n\n /* ── Next appointment (P1) ────────────────────────────────────── */\n {\n colId: 'nextAppointment',\n headerName: header('nextAppointment'),\n responsiveTier: 'P1',\n field: 'nextAppointment',\n cellRenderer: NextAppointmentCell,\n filter: DateRangeFilter,\n floatingFilterComponent: DateRangeFloatingFilter,\n minWidth: 160,\n width: 180,\n },\n\n /* ── Unpaid balance (P1) ──────────────────────────────────────── */\n {\n colId: 'unpaidBalance',\n headerName: header('unpaidBalance'),\n responsiveTier: 'P1',\n field: 'unpaidAmount',\n type: 'numericColumn',\n cellRenderer: BalanceBadgeCell,\n filter: NumberFilter,\n floatingFilterComponent: NumberFloatingFilter,\n // Money is integer cents; the inRange filter compares cents directly.\n filterParams: { defaultOperator: 'inRange', min: 0 },\n minWidth: 150,\n width: 170,\n },\n\n /* ── Phone / contact (P1) ─────────────────────────────────────── */\n {\n colId: 'phone',\n headerName: header('phone'),\n responsiveTier: 'P1',\n cellRenderer: ContactCell,\n cellRendererParams: { hideDetails },\n // Filter on the primary phone number string.\n filterValueGetter: (params) =>\n params.data?.phoneNumbers?.[0]?.number ?? '',\n filter: TextFilter,\n floatingFilterComponent: TextFloatingFilter,\n sortable: false,\n minWidth: 180,\n width: 220,\n },\n\n /* ── Email (P2) — masked under hideDetails ────────────────────── */\n {\n colId: 'email',\n headerName: header('email'),\n responsiveTier: 'P2',\n field: 'email',\n // When details are hidden the address never reaches the cell; the column\n // simply hides. The platform passes hideDetails from `hidePatientDetails`.\n //\n // Emit `hide` ONLY when masking (never a literal `hide: false`). A static\n // `hide: false` on the colDef is re-applied by AG Grid on every\n // `columnDefs` reconcile, which would clobber a runtime hide performed by\n // the ViewSwitcher (`api.setColumnsVisible(['email'], false)`) and silently\n // re-show the column. Columns that omit `hide` keep their runtime\n // visibility across reconciles — so `undefined` is the correct default.\n hide: hideDetails || undefined,\n filter: TextFilter,\n floatingFilterComponent: TextFloatingFilter,\n minWidth: 200,\n width: 240,\n },\n\n /* ── Care-plan status (P2) ────────────────────────────────────── */\n {\n colId: 'carePlanStatus',\n headerName: header('carePlanStatus'),\n responsiveTier: 'P2',\n field: 'carePlanStatus',\n cellRenderer: CarePlanStatusCell,\n filter: SelectFilter,\n floatingFilterComponent: SelectFloatingFilter,\n filterParams: {\n options: [\n {\n value: 'accepted',\n label: t('patientTable.carePlanStatus.accepted'),\n },\n {\n value: 'estimate',\n label: t('patientTable.carePlanStatus.estimate'),\n },\n { value: 'none', label: t('patientTable.carePlanStatus.none') },\n ],\n },\n sortable: false,\n minWidth: 130,\n width: 150,\n },\n\n /* ── Last visit (P2) ──────────────────────────────────────────── */\n {\n colId: 'lastVisit',\n headerName: header('lastVisit'),\n responsiveTier: 'P2',\n field: 'lastAppointment',\n cellRenderer: DateCellRenderer,\n cellRendererParams: { format: 'relative' },\n filter: DateRangeFilter,\n floatingFilterComponent: DateRangeFloatingFilter,\n minWidth: 140,\n width: 160,\n },\n\n /* ── Date of birth / age (P2) ─────────────────────────────────── */\n {\n colId: 'dateOfBirth',\n headerName: header('dateOfBirth'),\n responsiveTier: 'P2',\n field: 'dateOfBirth',\n cellRenderer: DateCellRenderer,\n cellRendererParams: { format: 'date' },\n filter: DateRangeFilter,\n floatingFilterComponent: DateRangeFloatingFilter,\n minWidth: 140,\n width: 160,\n },\n\n /* ── Gender (P3, hidden by default — opt-in via ColumnToggle) ──── */\n {\n colId: 'gender',\n headerName: header('gender'),\n responsiveTier: 'P3',\n field: 'gender',\n hide: true,\n // Map the raw code to a localised label for both cell + set filter.\n valueGetter: (params) =>\n params.data?.gender ? genderLabels[params.data.gender] : '',\n filter: SelectFilter,\n floatingFilterComponent: SelectFloatingFilter,\n filterParams: {\n options: [\n { value: genderLabels.m, label: genderLabels.m },\n { value: genderLabels.f, label: genderLabels.f },\n { value: genderLabels.x, label: genderLabels.x },\n ],\n },\n minWidth: 110,\n width: 130,\n },\n\n /* ── Source (P3) ──────────────────────────────────────────────── */\n {\n colId: 'source',\n headerName: header('source'),\n responsiveTier: 'P3',\n // TagListCellRenderer expects an array; wrap the single source string.\n valueGetter: (params) =>\n params.data?.source ? [params.data.source] : [],\n cellRenderer: TagListCellRenderer,\n filterValueGetter: (params) => params.data?.source ?? '',\n filter: SelectFilter,\n floatingFilterComponent: SelectFloatingFilter,\n sortable: false,\n minWidth: 120,\n width: 150,\n },\n\n /* ── Default insurance (P3, text) ─────────────────────────────── */\n {\n colId: 'defaultInsurance',\n headerName: header('defaultInsurance'),\n responsiveTier: 'P3',\n field: 'defaultInsurance',\n filter: SelectFilter,\n floatingFilterComponent: SelectFloatingFilter,\n minWidth: 140,\n width: 160,\n },\n\n /* ── Fiscal code (P3, text) ───────────────────────────────────── */\n {\n colId: 'fiscalCode',\n headerName: header('fiscalCode'),\n responsiveTier: 'P3',\n field: 'italianFiscalCode',\n filter: TextFilter,\n floatingFilterComponent: TextFloatingFilter,\n minWidth: 160,\n width: 180,\n },\n\n /* ── Tags (P3) ────────────────────────────────────────────────── */\n {\n colId: 'tags',\n headerName: header('tags'),\n responsiveTier: 'P3',\n field: 'tags',\n cellRenderer: TagListCellRenderer,\n // Match a single selected tag against the row's tag array.\n filterValueGetter: (params) => params.data?.tags ?? [],\n filter: SelectFilter,\n floatingFilterComponent: SelectFloatingFilter,\n sortable: false,\n minWidth: 160,\n width: 200,\n },\n\n /* ── Assigned member (P3) ─────────────────────────────────────── */\n {\n colId: 'assignedMember',\n headerName: header('assignedMember'),\n responsiveTier: 'P3',\n cellRenderer: UserCellRenderer,\n valueGetter: (params) =>\n params.data?.personalAssistant\n ? ({ name: params.data.personalAssistant } satisfies UserCellValue)\n : null,\n comparator: (a: UserCellValue | null, b: UserCellValue | null) =>\n (a?.name ?? '').localeCompare(b?.name ?? ''),\n filterValueGetter: (params) => params.data?.personalAssistant ?? '',\n filter: TypeaheadFilter,\n floatingFilterComponent: TypeaheadFloatingFilter,\n minWidth: 160,\n width: 180,\n },\n\n /* ── Created at (P3) ──────────────────────────────────────────── */\n {\n colId: 'createdAt',\n headerName: header('createdAt'),\n responsiveTier: 'P3',\n field: 'createdAt',\n cellRenderer: DateCellRenderer,\n cellRendererParams: { format: 'date' },\n filter: DateRangeFilter,\n floatingFilterComponent: DateRangeFloatingFilter,\n minWidth: 140,\n width: 160,\n },\n\n /* ── Actions (P0, pinned-end) ─────────────────────────────────── */\n {\n colId: 'actions',\n headerName: header('actions'),\n // Pinned to the inline-end edge so actions stay reachable while the field\n // columns scroll. AG Grid `pinned` is physical — the grid's `enableRtl`\n // flips this to the start edge under RTL.\n pinned: 'right',\n // Right-align the header (the class AG Grid's numericColumn uses); the\n // action group itself stays centred via the token-bound justify class.\n headerClass: 'ag-right-aligned-header',\n cellClass: 'ds:justify-center',\n cellRenderer: ActionsCellRenderer,\n cellRendererParams: {\n actions,\n intent: 'ghost',\n group: true,\n label: t('patientTable.actions.group'),\n collapsed: getActionsCompact,\n },\n sortable: false,\n filter: false,\n resizable: false,\n // Spec: 180px expanded → 88px collapsed (min). The renderer collapses to a\n // single overflow trigger via `getActionsCompact`; the column min lets it\n // shrink to the compact footprint.\n width: 180,\n minWidth: 88,\n // Actions are never auto-hidden (no tier) — they are always reachable.\n },\n ];\n\n return columns;\n}\n","/**\n * patient-table — responsive column hook\n * ----------------------------------------------------------------------------\n * `useResponsiveColumns(handleRef, opts)` toggles column visibility by the\n * `responsiveTier` (`P0`–`P3`) baked onto each `ColDef` by `buildPatientColumns`,\n * driven by the *grid container's* width — measured with a `ResizeObserver`, NOT\n * the viewport — so the table responds correctly when embedded in a narrow panel,\n * split pane or sidebar rather than only at browser-window breakpoints.\n *\n * BREAKPOINTS (container inline-size → highest tier kept visible):\n *\n * < 640px → P0 only (Identity + Actions; both are grid-anchored)\n * < 900px → P0 + P1\n * < 1200px → P0 + P1 + P2\n * ≥ 1200px → all tiers (P0–P3)\n *\n * Columns without a tier (the pinned Identity + Actions columns) are never\n * touched — they are the row anchors and stay visible at every width.\n *\n * RESPONSIVE ↔ PERSISTENCE RECONCILIATION\n * ---------------------------------------\n * `data-table.tsx` persists the full AG Grid column state to\n * `localStorage[\"data-table-col-state:<gridId>\"]` (load on grid-ready, save on\n * unmount). A user's explicit `ColumnToggle` choice lives in that persisted state\n * and MUST win over — and survive — the responsive baseline. Reconciliation:\n *\n * 1. The responsive baseline is exactly that — a *baseline*. We only auto\n * show/hide a column the user has NOT manually toggled this session.\n * 2. We track a `Set<colId>` of user-touched columns. We learn of a manual\n * toggle from the grid's `columnVisible` event: any such event whose\n * `source` is NOT `'api'` is user-driven (ColumnToggle tool panel, column\n * menu, context menu, drag), so we add those colIds to the set. Our own\n * responsive calls go through `setColumnsVisible(..., 'api')`, so they never\n * pollute the set (and we additionally guard with a re-entrancy flag).\n * 3. Once a column is user-touched, the hook leaves it alone forever this\n * session — its visibility is whatever the user chose, which is what\n * `data-table.tsx` then persists on unmount. The persisted choice therefore\n * wins on the next mount too: we seed the user-touched set from the saved\n * column state so a previously hidden/shown column is treated as a manual\n * override and not clobbered by the baseline on re-entry.\n *\n * CONSTRAINTS: no `any` (AG Grid's `ColumnEventType` is read off the typed event,\n * tier read via the typed `getResponsiveTier` helper). No DOM `data-*` attribute\n * is written here (PHI rule is moot — this hook only reads colIds and widths).\n */\nimport { useCallback, useEffect, useRef, type RefObject } from 'react';\nimport type { Column, ColumnVisibleEvent } from 'ag-grid-community';\nimport { getResponsiveTier } from './columns';\nimport type { PatientRow, PatientTableHandle, ResponsiveTier } from './types';\n\n/* -------------------------------------------------------------------------- */\n/* Breakpoint model */\n/* -------------------------------------------------------------------------- */\n\n/**\n * Container inline-size breakpoints. Each entry is the *minimum* container width\n * (px) at which the named tier becomes visible. Below the first threshold only\n * `P0` shows; at or above the last, everything shows.\n */\ninterface Breakpoint {\n /** Minimum container inline-size (px) for this tier to be shown. */\n minWidth: number;\n /** The tier this breakpoint reveals. */\n tier: ResponsiveTier;\n}\n\nconst DEFAULT_BREAKPOINTS: readonly Breakpoint[] = [\n { minWidth: 0, tier: 'P0' },\n { minWidth: 640, tier: 'P1' },\n { minWidth: 900, tier: 'P2' },\n { minWidth: 1200, tier: 'P3' },\n];\n\n/** Resolve the set of tiers that should be visible at a given container width. */\nfunction visibleTiersForWidth(\n width: number,\n breakpoints: readonly Breakpoint[],\n): Set<ResponsiveTier> {\n const visible = new Set<ResponsiveTier>();\n for (const bp of breakpoints) {\n if (width >= bp.minWidth) visible.add(bp.tier);\n }\n // P0 is always visible regardless of width.\n visible.add('P0');\n return visible;\n}\n\n/* -------------------------------------------------------------------------- */\n/* Options */\n/* -------------------------------------------------------------------------- */\n\nexport interface UseResponsiveColumnsOptions {\n /**\n * The grid container element to observe. The hook measures THIS element's\n * inline-size (not the viewport) so it works embedded. When the ref is unset\n * the hook is inert.\n */\n containerRef: RefObject<HTMLElement | null>;\n /**\n * Disable responsive toggling entirely (the `responsive={false}` escape hatch\n * on `PatientTable`). When `false` the hook unobserves and makes no visibility\n * changes — column visibility is left entirely to persistence / ColumnToggle.\n * Default `true`.\n */\n enabled?: boolean;\n /**\n * Override the container-width breakpoints. Ordered low→high `minWidth`; each\n * reveals its `tier`. Defaults to 640 / 900 / 1200 (P1 / P2 / P3).\n */\n breakpoints?: readonly Breakpoint[];\n}\n\n/* -------------------------------------------------------------------------- */\n/* Return shape */\n/* -------------------------------------------------------------------------- */\n\n/**\n * Imperative surface returned by {@link useResponsiveColumns}. The responsive\n * effect runs internally; `lockColumns` lets a caller (the view switcher) mark\n * columns as user-touched so the responsive baseline stops auto-managing them.\n */\nexport interface UseResponsiveColumnsResult {\n /**\n * Mark the given colIds as \"user-touched\" so the responsive baseline leaves\n * their visibility alone from here on — exactly as if the user had toggled\n * them via `ColumnToggle`. The view switcher calls this when it applies a\n * view's column visibility, so its programmatic (`source: 'api'`) visibility\n * writes are not immediately re-hidden/re-shown by the next responsive\n * reconcile pass. No-op (with the colIds still recorded for a later mount of\n * the effect) when the hook is disabled.\n */\n lockColumns: (colIds: readonly string[]) => void;\n}\n\n/* -------------------------------------------------------------------------- */\n/* Hook */\n/* -------------------------------------------------------------------------- */\n\n/**\n * Wire responsive, tier-driven column visibility to the patient grid.\n *\n * @param handleRef The `PatientTable` imperative handle ref — the hook reaches\n * the raw AG Grid API via `handleRef.current.getRawApi()`.\n * @param opts Container ref to observe, plus enable flag / breakpoint\n * overrides. See {@link UseResponsiveColumnsOptions}.\n * @returns {@link UseResponsiveColumnsResult} — `lockColumns(colIds)`\n * to mark columns user-touched (see the view-switcher\n * coordination note in patient-table.tsx).\n */\nexport function useResponsiveColumns(\n handleRef: RefObject<PatientTableHandle | null>,\n opts: UseResponsiveColumnsOptions,\n): UseResponsiveColumnsResult {\n const {\n containerRef,\n enabled = true,\n breakpoints = DEFAULT_BREAKPOINTS,\n } = opts;\n\n // colIds the user has explicitly toggled this session — responsive auto-toggle\n // must never override these (their persisted visibility wins). A ref, not\n // state: mutating it must not re-run the effect or re-render. Shared between\n // the responsive effect (which seeds + grows it from `columnVisible` events)\n // and the exported `lockColumns` (which the view switcher uses to register a\n // view-driven visibility change as a user override).\n const userTouchedRef = useRef<Set<string>>(new Set());\n // Re-entrancy guard: true while WE are applying a responsive change, so the\n // resulting `columnVisible` event is not misread as a user toggle even if a\n // future AG Grid version reports a non-`api` source for it.\n const applyingRef = useRef(false);\n\n useEffect(() => {\n const container = containerRef.current;\n if (!enabled || !container) return;\n\n // Resolve the live API lazily on each tick — the grid may not be ready on\n // the first observer callback.\n const getApi = () => handleRef.current?.getRawApi();\n\n /**\n * Record a user-driven visibility change so the column is left alone from\n * here on. `source: 'api'` is the only programmatic source the hook itself\n * uses; everything else (tool panel, column menu, context menu, drag) is the\n * user. The re-entrancy flag covers our own calls defensively.\n */\n const onColumnVisible = (event: ColumnVisibleEvent<PatientRow>) => {\n if (applyingRef.current) return;\n if (event.source === 'api') return;\n const touched = event.columns ?? (event.column ? [event.column] : []);\n for (const col of touched) {\n userTouchedRef.current.add(col.getColId());\n }\n };\n\n // The grid API is frequently not ready on the first effect tick (AG Grid\n // mounts asynchronously). `wired` ensures the one-time seed + listener\n // attach happens the first time we actually have an API, no matter whether\n // that is here on mount or later from a ResizeObserver tick.\n let wired = false;\n\n /**\n * One-time wiring once the API is live: seed the user-touched set from the\n * persisted/current column state, then subscribe to `columnVisible` so later\n * manual toggles are recorded. Seeding treats an already-hidden tiered\n * column that *would* be visible at the current width as a deliberate user\n * hide (restored from localStorage by data-table.tsx) so the baseline does\n * not clobber it. We only positively detect *hidden* overrides — auto-show\n * would otherwise fight a deliberate hide.\n */\n const ensureWired = (api: NonNullable<ReturnType<typeof getApi>>) => {\n if (wired) return;\n wired = true;\n const cols = api.getColumns();\n const width = container.getBoundingClientRect().width;\n const visibleTiers = visibleTiersForWidth(width, breakpoints);\n if (cols) {\n for (const col of cols) {\n const tier = getResponsiveTier(col.getColDef());\n if (tier && !col.isVisible() && visibleTiers.has(tier)) {\n userTouchedRef.current.add(col.getColId());\n }\n }\n }\n api.addEventListener('columnVisible', onColumnVisible);\n };\n\n /** Apply the responsive baseline for the current container width. */\n const reconcile = () => {\n const api = getApi();\n if (!api) return;\n ensureWired(api);\n const columns = api.getColumns();\n if (!columns) return;\n\n const width = container.getBoundingClientRect().width;\n const visibleTiers = visibleTiersForWidth(width, breakpoints);\n\n // Compute the show / hide buckets, skipping user-touched and untiered\n // columns. Batch the calls so AG Grid fires one event per direction.\n const toShow: Column[] = [];\n const toHide: Column[] = [];\n\n for (const col of columns) {\n const colId = col.getColId();\n // The user owns this column's visibility — never auto-manage it.\n if (userTouchedRef.current.has(colId)) continue;\n\n const tier = getResponsiveTier(col.getColDef());\n // No tier ⇒ anchor column (Identity / Actions): always left visible.\n if (!tier) continue;\n\n const shouldShow = visibleTiers.has(tier);\n if (shouldShow && !col.isVisible()) toShow.push(col);\n else if (!shouldShow && col.isVisible()) toHide.push(col);\n }\n\n if (toShow.length === 0 && toHide.length === 0) return;\n\n applyingRef.current = true;\n try {\n // AG Grid tags API-driven changes with `source: 'api'`, so the\n // resulting `columnVisible` events are ignored by `onColumnVisible`\n // (they are the baseline, not user intent). `applyingRef` is the belt\n // to that braces in case a future version reports a different source.\n if (toShow.length > 0) api.setColumnsVisible(toShow, true);\n if (toHide.length > 0) api.setColumnsVisible(toHide, false);\n } finally {\n applyingRef.current = false;\n }\n };\n\n // Observe the GRID CONTAINER (not the viewport) so embedded tables respond\n // to their own box. The first observer tick fires synchronously on observe,\n // and `reconcile` lazily wires + seeds the moment the grid API is live.\n const observer = new ResizeObserver(() => reconcile());\n observer.observe(container);\n reconcile();\n\n return () => {\n observer.disconnect();\n // The API may have torn down already on unmount; guard the removal.\n getApi()?.removeEventListener('columnVisible', onColumnVisible);\n };\n }, [containerRef, enabled, breakpoints, handleRef]);\n\n // Stable across renders — `userTouchedRef` is a ref, so adding to it never\n // re-runs the responsive effect. Recording a colId here makes the next\n // `reconcile` pass skip it (it `continue`s on `userTouchedRef.has(colId)`),\n // which is exactly how a manual ColumnToggle override is honoured. The view\n // switcher calls this for every column it shows/hides so the responsive\n // baseline doesn't immediately fight the applied view.\n const lockColumns = useCallback((colIds: readonly string[]) => {\n for (const id of colIds) userTouchedRef.current.add(id);\n }, []);\n\n return { lockColumns };\n}\n","/**\n * patient-table — Domain-Specific component\n * ----------------------------------------------------------------------------\n * `PatientTable` is a thin composition over the kit's `data-table` engine\n * (AG Grid Community) specialised for the AlfaDocs patient list. It bakes in:\n *\n * • `buildPatientColumns(t, …)` (the 17-column spec) merged with a\n * consumer-supplied `columns` override.\n * • the patient cell renderers (Identity / NextAppointment / BalanceBadge /\n * CarePlanStatus / Contact) via the column defs above.\n * • a default toolbar — `QuickSearch` + `FilterChips` + `ColumnToggle` +\n * `ExportMenu` + a `BulkAction` per `props.bulkActions` — overridable\n * wholesale via `props.toolbar`.\n * • `useResponsiveColumns` (container-width column-priority tiers) when\n * `props.responsive` (default `true`).\n * • multiple row selection, pagination, archived-row tint, loading / empty\n * overlays.\n * • `useAgentRegistration(dataTableAgent, handle, gridId)` — the SAME agent\n * adapter `data-table` registers, keyed by `gridId`.\n *\n * The `forwardRef` exposes the inner `DataTableHandle<PatientRow>` so consumers\n * (e.g. the `patients` pattern's WarningStack \"View\" actions) can drive the\n * grid imperatively — `setFilter`, `setSort`, `getSelection`, etc.\n *\n * CONSTRAINTS (CI-blocking — src/docs/23-constraints.mdx, 26-agent-readiness.mdx):\n * • No hardcoded colour / spacing / radius / shadow / font — token-bound `ds:`\n * utilities only. Row tint goes through the token-bound\n * `data-table-row-archived` class on the AG Grid theme bridge, never an\n * inline `cellStyle`.\n * • CSS logical properties only (`ms/me/ps/pe`, `text-start/text-end`).\n * • All user-visible strings via `useTranslation('ui')` → `ui.patientTable.*`.\n * • TypeScript strict — no `any`. `forwardRef` exposes the curated handle.\n * • PHI rule (PRS 26 §6): only `row.id` reaches DOM `data-*`. This component\n * writes no PHI attribute; AG Grid surfaces ids via its native `row-id`.\n */\nimport {\n forwardRef,\n useCallback,\n useImperativeHandle,\n useMemo,\n useRef,\n useState,\n type ReactNode,\n type RefObject,\n} from 'react';\nimport { useTranslation } from 'react-i18next';\nimport type { GetRowIdParams, RowClassParams } from 'ag-grid-community';\nimport { DataTable, dataTableAgent, type DataTableHandle } from '../data-table';\nimport { Select } from '../select';\nimport { useAgentRegistration } from '../../agent';\nimport {\n buildPatientColumns,\n getResponsiveTier,\n type BuildPatientColumnsOptions,\n} from './columns';\nimport {\n useResponsiveColumns,\n type UseResponsiveColumnsResult,\n} from './use-responsive-columns';\nimport type {\n PatientBulkAction,\n PatientColumnDef,\n PatientRow,\n PatientRowAction,\n PatientTableHandle,\n PatientView,\n} from './types';\n\n/* -------------------------------------------------------------------------- */\n/* Props */\n/* -------------------------------------------------------------------------- */\n\nexport interface PatientTableProps {\n /**\n * Row data. `undefined` ⇒ the grid renders its loading overlay (the\n * data-table contract: `rowData === undefined` is the loading sentinel). Pass\n * `[]` for an explicit empty state.\n */\n rowData?: PatientRow[];\n /**\n * Override / extend the baked patient columns. When provided, these column\n * definitions REPLACE the kit defaults entirely (the consumer is expected to\n * compose `buildPatientColumns(t, …)` — re-exported from the barrel — with\n * their own additions). When omitted, the kit's `buildPatientColumns` output\n * is used.\n */\n columns?: PatientColumnDef[];\n /**\n * REQUIRED. Persistence key (column state → `localStorage`) AND the agent\n * instance address (`data-component-id`). Two tables on one page need\n * distinct `gridId`s.\n */\n gridId: string;\n /** Row-height preset. Defaults to the engine default (`'default'`). */\n density?: 'compact' | 'default' | 'expanded';\n /**\n * Enable container-width column-priority responsiveness (lower-priority\n * columns hide as the grid narrows). Default `true`. Set `false` to leave\n * column visibility entirely to persistence / `ColumnToggle`.\n */\n responsive?: boolean;\n /**\n * Saved column/filter/sort presets. When non-empty AND no custom `toolbar`\n * is supplied, the default toolbar renders a `Select`-based view switcher in\n * the FilterBar; choosing a view applies its column visibility (via the\n * responsive-hook lock so the choice is honoured like a manual ColumnToggle),\n * `filterModel` (`setFilter`) and `sortModel` (`setSort`). Omitted entirely\n * when empty / undefined or when `toolbar` is supplied (a custom toolbar owns\n * its own view UI).\n */\n views?: PatientView[];\n /**\n * Invoked when a per-row action button is activated, with the resolved action\n * descriptor and the patient row. Only `row.id` ever leaves this boundary into\n * persistence / agent surfaces — never PHI.\n */\n onRowAction?: (action: PatientRowAction, patient: PatientRow) => void;\n /**\n * Toolbar bulk actions (operate on the current selection). Each renders a\n * `DataTable.Toolbar.BulkAction` that surfaces only while rows are selected;\n * its `onSelect` receives the selected row ids (never PHI).\n */\n bulkActions?: PatientBulkAction[];\n /**\n * Force the loading overlay independently of `rowData`. When `true` the grid\n * shows the loading skeleton even if `rowData` is an array (e.g. a background\n * refresh). `rowData === undefined` also triggers loading.\n */\n loading?: boolean;\n /**\n * Replace the default toolbar wholesale. Pass a `<DataTable.Toolbar>…</…>`\n * tree (it has access to the same toolbar context). When omitted the default\n * QuickSearch + FilterChips + ColumnToggle + ExportMenu + BulkActions toolbar\n * is rendered.\n */\n toolbar?: ReactNode;\n /**\n * Omit the `QuickSearch` field from the DEFAULT toolbar. The rest of the\n * default toolbar (view switcher when `views` is supplied, FilterChips,\n * ColumnToggle, ExportMenu, BulkActions) is unaffected. Ignored when a custom\n * `toolbar` is supplied (that toolbar owns its own composition). Default\n * `false` (search shown). Use for surfaces that provide their own search\n * affordance elsewhere on the page.\n */\n hideQuickSearch?: boolean;\n /**\n * Page-size dropdown options shown in the pagination panel — forwarded to the\n * underlying `DataTable.paginationPageSizeSelector`. Pass `false` to hide the\n * page-size chooser entirely (pagination navigation is unaffected). Default\n * `[10, 25, 50, 100]` (the engine default).\n */\n paginationPageSizeSelector?: number[] | false;\n /**\n * Mask sensitive contact details (email) in the Contact / Email columns.\n * Forwarded to `buildPatientColumns`' `hideDetails`. Ignored when `columns`\n * is supplied (the consumer owns their columns then). Default `false`.\n */\n hideDetails?: boolean;\n /**\n * Derive the patient-detail href for the Identity cell, e.g.\n * `(row) => \\`/patients/${row.id}\\``. Forwarded to `buildPatientColumns`.\n * Ignored when `columns` is supplied. When omitted the Identity cell routes\n * its click through `onRowAction` with the `show` action.\n */\n identityHref?: BuildPatientColumnsOptions['identityHref'];\n /** Override the default region aria-label (`ui.patientTable.regionLabel`). */\n 'aria-label'?: string;\n /** Extra class names merged onto the inner grid wrapper. */\n className?: string;\n}\n\n/* -------------------------------------------------------------------------- */\n/* Row class — archived tint */\n/* -------------------------------------------------------------------------- */\n\n/**\n * Token-bound archived-row tint. The class is defined on the AG Grid theme\n * bridge (`src/tokens/ag-grid-theme.css` → `.data-table-row-archived`) so the\n * recessive muted fill stays under token control — no colour ever enters a\n * `cellStyle` / `cellClass` literal here.\n */\nfunction getPatientRowClass(\n params: RowClassParams<PatientRow>,\n): string | undefined {\n return params.data?.isArchived ? 'data-table-row-archived' : undefined;\n}\n\n/* -------------------------------------------------------------------------- */\n/* Row id — key selection / bulk actions on the real patient id */\n/* -------------------------------------------------------------------------- */\n\n/**\n * Use the stable `PatientRow.id` as AG Grid's node id. Without this AG Grid\n * keys nodes by row index, so `getSelectedNodes().map(n => n.id)`,\n * `setSelection(ids)`, the bulk-action bridge and the agent adapter would all\n * receive index strings (`\"0\"`, `\"1\"`) instead of patient ids. Forwarded to the\n * engine via `gridOptions.getRowId` (the path `data-table.tsx` spreads through\n * untouched). `id` is the ONLY field permitted on a DOM hook (PHI rule).\n */\nfunction getPatientRowId(params: GetRowIdParams<PatientRow>): string {\n return params.data.id;\n}\n\n/* -------------------------------------------------------------------------- */\n/* View switcher — default-toolbar control for the `views` prop */\n/* -------------------------------------------------------------------------- */\n\ninterface ViewSwitcherProps {\n /** Saved views to choose from (already known non-empty by the caller). */\n views: PatientView[];\n /** The live patient-table handle ref (filter / sort / raw API access). */\n handleRef: RefObject<PatientTableHandle | null>;\n /**\n * Mark a view's visibility writes as user-touched so `useResponsiveColumns`\n * stops auto-managing them — see the coordination note at the call site.\n */\n lockColumns: UseResponsiveColumnsResult['lockColumns'];\n /** Accessible label for the control (`ui.patientTable.views.label`). */\n label: string;\n}\n\n/**\n * A minimal, accessible saved-view switcher rendered in the DEFAULT toolbar's\n * FilterBar. Uses the kit `Select` (convenience `options` form) — a small,\n * labelled single-choice control that fits the toolbar's compact density and\n * carries Radix's listbox a11y for free.\n *\n * On selection it applies the chosen {@link PatientView} through the patient\n * handle + raw AG Grid API:\n * • column visibility — show the view's listed toggleable columns, hide the\n * rest of the toggleable (tiered) ones. Untiered columns (the pinned\n * Identity / Actions anchors) are NEVER hidden.\n * • `filterModel` via `handle.setFilter`.\n * • `sortModel` via `handle.setSort`.\n *\n * RESPONSIVE COORDINATION (critical): a view-applied visibility change must not\n * be immediately re-hidden/re-shown by `useResponsiveColumns`. We route every\n * colId we touch through `lockColumns(colIds)`, which adds them to the same\n * `userTouchedRef` set the hook grows from non-`api` `columnVisible` events —\n * so from then on the responsive baseline treats them as a user override and\n * leaves them alone, exactly as a manual ColumnToggle would.\n */\nfunction ViewSwitcher({\n views,\n handleRef,\n lockColumns,\n label,\n}: ViewSwitcherProps) {\n const [activeViewId, setActiveViewId] = useState<string>('');\n\n const options = useMemo(\n () => views.map((view) => ({ value: view.id, label: view.label })),\n [views],\n );\n\n const applyView = useCallback(\n (viewId: string) => {\n const view = views.find((v) => v.id === viewId);\n const handle = handleRef.current;\n if (!view || !handle) return;\n\n const api = handle.getRawApi();\n if (api) {\n const wanted = new Set<string>(view.columns);\n const toShow: string[] = [];\n const toHide: string[] = [];\n for (const col of api.getColumns() ?? []) {\n // Only the tiered (auto-hideable) field columns participate; the\n // pinned Identity / Actions anchors carry no tier and are never\n // hidden by a view.\n if (getResponsiveTier(col.getColDef()) === undefined) continue;\n const colId = col.getColId();\n if (wanted.has(colId)) toShow.push(colId);\n else toHide.push(colId);\n }\n // Lock BEFORE the visibility write so a synchronous responsive\n // reconcile (e.g. a ResizeObserver tick triggered by the layout shift)\n // already sees these colIds as user-touched.\n lockColumns([...toShow, ...toHide]);\n if (toShow.length > 0) api.setColumnsVisible(toShow, true);\n if (toHide.length > 0) api.setColumnsVisible(toHide, false);\n }\n\n handle.setFilter(view.filterModel);\n handle.setSort(view.sortModel);\n api?.onFilterChanged();\n },\n [views, handleRef, lockColumns],\n );\n\n const handleValueChange = useCallback(\n (next: string) => {\n setActiveViewId(next);\n if (next) applyView(next);\n },\n [applyView],\n );\n\n return (\n // Width-constraining wrapper (same pattern as the toolbar's QuickSearch) so\n // the Select's intrinsic `w-full` trigger sizes to a compact, legible width\n // instead of absorbing the whole FilterBar row.\n <div className=\"ds:w-[12rem] ds:max-w-full ds:min-w-0 ds:shrink-0\">\n <Select\n options={options}\n value={activeViewId}\n onValueChange={handleValueChange}\n size=\"sm\"\n aria-label={label}\n />\n </div>\n );\n}\n\n/* -------------------------------------------------------------------------- */\n/* PatientTable */\n/* -------------------------------------------------------------------------- */\n\nexport const PatientTable = forwardRef<PatientTableHandle, PatientTableProps>(\n function PatientTable(\n {\n rowData,\n columns,\n gridId,\n density,\n responsive = true,\n views,\n onRowAction,\n bulkActions,\n loading = false,\n toolbar,\n hideQuickSearch = false,\n paginationPageSizeSelector,\n hideDetails = false,\n identityHref,\n 'aria-label': ariaLabel,\n className,\n },\n ref,\n ) {\n const { t } = useTranslation('ui');\n\n // Internal handle ref forwarded BOTH to the consumer's ref (below) and to\n // `useResponsiveColumns`, which reaches the live AG Grid API via\n // `handle.getRawApi()`.\n const handleRef = useRef<PatientTableHandle | null>(null);\n\n // Container the responsive hook observes (its inline-size drives the\n // column-priority tiers). Observing the grid's own box — not the viewport —\n // is what makes the table responsive when embedded in a narrow panel.\n const containerRef = useRef<HTMLDivElement | null>(null);\n\n // Mirror the handle into state once the inner DataTable mounts so the\n // agent-registration effect (which keys off `handle` reactively) fires with\n // a live handle. A bare ref mutation would not re-run the effect.\n const [registrableHandle, setRegistrableHandle] =\n useState<PatientTableHandle | null>(null);\n\n // Expose the inner DataTable handle to the consumer ref. Re-runs when the\n // mirrored handle becomes available so a consumer reading the ref in an\n // effect sees the live handle, not the initial `null`.\n useImperativeHandle(\n ref,\n () => (registrableHandle ?? handleRef.current) as PatientTableHandle,\n [registrableHandle],\n );\n\n // Responsive column-priority tiers, driven by the grid container's width.\n // Inert when `responsive` is false (the hook unobserves and makes no calls).\n // The container ref is widened to the hook's `HTMLElement` param at the call\n // site (RefObject is invariant on its element type) — same cast pattern as\n // `useDirection` in tooltip.tsx. `lockColumns` lets the ViewSwitcher mark a\n // view's visibility writes as user-touched (see ViewSwitcher's coordination\n // note) — called before the hook value is consumed in the default toolbar.\n const { lockColumns } = useResponsiveColumns(handleRef, {\n containerRef: containerRef as RefObject<HTMLElement | null>,\n enabled: responsive,\n });\n\n // Columns: consumer override wins wholesale; otherwise the baked patient\n // columns. Memoised on the inputs the builder reads — `density` included so\n // the actions column collapses (180→88px) to its compact footprint in the\n // `compact` density preset via `getActionsCompact`.\n const columnDefs = useMemo<PatientColumnDef[]>(\n () =>\n columns ??\n buildPatientColumns(t, {\n hideDetails,\n onRowAction,\n identityHref,\n getActionsCompact: () => density === 'compact',\n }),\n [columns, t, hideDetails, onRowAction, identityHref, density],\n );\n\n // Default toolbar — an optional ViewSwitcher + QuickSearch + FilterChips\n // (FilterBar slot) and ColumnToggle + ExportMenu + one BulkAction per\n // `bulkActions` (Actions slot). Overridable wholesale via `props.toolbar`;\n // when a custom `toolbar` is supplied the ViewSwitcher is NOT injected — a\n // custom toolbar owns its own view UI. The switcher is also omitted when\n // `views` is empty / undefined. All toolbar parts translate their own labels\n // through the `dataTable.*` namespace; the BulkAction labels come from the\n // consumer-supplied descriptors.\n const hasViews = (views?.length ?? 0) > 0;\n const defaultToolbar = (\n <DataTable.Toolbar>\n <DataTable.Toolbar.FilterBar>\n {hasViews && views ? (\n <ViewSwitcher\n views={views}\n handleRef={handleRef}\n lockColumns={lockColumns}\n label={t('patientTable.views.label')}\n />\n ) : null}\n {hideQuickSearch ? null : <DataTable.Toolbar.QuickSearch />}\n <DataTable.Toolbar.FilterChips />\n </DataTable.Toolbar.FilterBar>\n <DataTable.Toolbar.Actions>\n {bulkActions?.map((action) => (\n <DataTable.Toolbar.BulkAction\n key={action.id}\n label={action.label}\n icon={action.icon}\n variant={action.variant}\n onClick={(api) => {\n // Resolve the selection via the live grid API → row ids only\n // (never PHI). Falls back to an empty list if the API is unset.\n const ids =\n api\n ?.getSelectedNodes()\n .map((node) => node.id)\n .filter((id): id is string => id != null) ?? [];\n action.onSelect(ids);\n }}\n />\n ))}\n <DataTable.Toolbar.ColumnToggle />\n <DataTable.Toolbar.ExportMenu />\n </DataTable.Toolbar.Actions>\n </DataTable.Toolbar>\n );\n\n const toolbarContent = toolbar ?? defaultToolbar;\n\n // `rowData === undefined` is the data-table loading sentinel; `loading`\n // forces it independently (e.g. a background refresh over existing rows).\n const effectiveRowData = loading ? undefined : rowData;\n\n // Stable `gridOptions` forwarding `getRowId` so AG Grid keys nodes by the\n // real `PatientRow.id` (see getPatientRowId) — selection, bulk actions and\n // the agent adapter all then return patient ids, not row-index strings.\n const gridOptions = useMemo(() => ({ getRowId: getPatientRowId }), []);\n\n // Register the data-table agent adapter keyed by `gridId` — the same\n // adapter `data-table` registers internally. Idempotent overwrite with the\n // identical handle under the same `(adapterId, gridId)` key; both share the\n // unmount lifecycle so the dedup is harmless and the registration stays\n // addressable as `patient-table`'s `gridId` for the duration.\n useAgentRegistration(\n dataTableAgent,\n registrableHandle as DataTableHandle | null,\n gridId,\n );\n\n return (\n <div\n ref={containerRef}\n role=\"region\"\n aria-label={ariaLabel ?? t('patientTable.regionLabel')}\n data-component=\"patient-table\"\n data-component-id={gridId}\n className=\"ds:flex ds:w-full ds:min-h-0 ds:flex-1 ds:flex-col\"\n >\n <DataTable<PatientRow>\n ref={(instance) => {\n handleRef.current = instance;\n // Mirror into state once (or when the instance identity changes) so\n // the registration effect picks up the live handle.\n setRegistrableHandle((prev) =>\n prev === instance ? prev : instance,\n );\n }}\n gridId={gridId}\n columnDefs={columnDefs}\n rowData={effectiveRowData}\n rowSelection=\"multiple\"\n pagination\n {...(paginationPageSizeSelector !== undefined\n ? { paginationPageSizeSelector }\n : {})}\n density={density}\n getRowClass={getPatientRowClass}\n gridOptions={gridOptions}\n className={className}\n >\n {toolbarContent}\n </DataTable>\n </div>\n );\n },\n);\n\nPatientTable.displayName = 'PatientTable';\n"],"names":["__iconNode","MailX","createLucideIcon","MessageSquareOff","MessageSquare","SMALL_BALANCE_CENTS_MAX","classifyBalance","cents","readUnpaidCents","value","BalanceBadgeCell","props","currency","options","t","i18n","useTranslation","locale","formatted","variant","statusKey","status","jsxs","Badge","jsx","CARE_PLAN_VARIANT_MAP","isCarePlanStatus","CarePlanStatusCell","data","size","raw","eligibilityVariants","cva","ContactCell","hideDetails","phoneNumbers","email","emailEnabled","emailValid","primaryPhone","_a","hasEmail","smsEligible","p","emailEligible","emailText","smsLabel","emailLabel","Tooltip","Mail","nextAppointmentVariants","DAY_MS","DEFAULT_SOON_WITHIN_DAYS","toTime","resolveTone","time","soonWithinDays","deltaMs","NextAppointmentCell","tone","CalendarClock","Timestamp","resolve","source","row","safeHref","href","fullName","PatientIdentityCell","node","onSelect","name","resolvedHref","fiscalCode","linkLabel","interactiveClasses","handleClick","event","body","Fragment","Avatar","getResponsiveTier","colDef","buildRowActions","onRowAction","dispatch","action","patient","make","overrides","createElement","Eye","Pencil","Users","Trash2","NO","buildPatientColumns","opts","getActionsCompact","identityHref","actions","genderLabels","header","id","params","TypeaheadFilter","TypeaheadFloatingFilter","DateRangeFilter","DateRangeFloatingFilter","NumberFilter","NumberFloatingFilter","_c","_b","TextFilter","TextFloatingFilter","SelectFilter","SelectFloatingFilter","DateCellRenderer","TagListCellRenderer","UserCellRenderer","a","b","ActionsCellRenderer","DEFAULT_BREAKPOINTS","visibleTiersForWidth","width","breakpoints","visible","bp","useResponsiveColumns","handleRef","containerRef","enabled","userTouchedRef","useRef","applyingRef","useEffect","container","getApi","onColumnVisible","touched","col","wired","ensureWired","api","cols","visibleTiers","tier","reconcile","columns","toShow","toHide","colId","shouldShow","observer","useCallback","colIds","getPatientRowClass","getPatientRowId","ViewSwitcher","views","lockColumns","label","activeViewId","setActiveViewId","useState","useMemo","view","applyView","viewId","v","handle","wanted","handleValueChange","next","Select","PatientTable","forwardRef","rowData","gridId","density","responsive","bulkActions","loading","toolbar","hideQuickSearch","paginationPageSizeSelector","ariaLabel","className","ref","registrableHandle","setRegistrableHandle","useImperativeHandle","columnDefs","hasViews","defaultToolbar","DataTable","ids","toolbarContent","effectiveRowData","gridOptions","useAgentRegistration","dataTableAgent","instance","prev"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AASA,MAAMA,KAAa;AAAA,EACjB,CAAC,QAAQ,EAAE,GAAG,6DAA6D,KAAK,SAAQ,CAAE;AAAA,EAC1F,CAAC,QAAQ,EAAE,GAAG,6CAA6C,KAAK,SAAQ,CAAE;AAAA,EAC1E,CAAC,QAAQ,EAAE,GAAG,cAAc,KAAK,SAAQ,CAAE;AAAA,EAC3C,CAAC,QAAQ,EAAE,GAAG,cAAc,KAAK,SAAQ,CAAE;AAC7C,GACMC,KAAQC,EAAiB,UAAUF,EAAU;ACfnD;AAAA;AAAA;AAAA;AAAA;AAAA;AASA,MAAMA,KAAa;AAAA,EACjB;AAAA,IACE;AAAA,IACA;AAAA,MACE,GAAG;AAAA,MACH,KAAK;AAAA,IACX;AAAA,EACA;AAAA,EACE,CAAC,QAAQ,EAAE,GAAG,cAAc,KAAK,SAAQ,CAAE;AAAA,EAC3C,CAAC,QAAQ,EAAE,GAAG,oCAAoC,KAAK,SAAQ,CAAE;AACnE,GACMG,KAAmBD,EAAiB,sBAAsBF,EAAU;ACpB1E;AAAA;AAAA;AAAA;AAAA;AAAA;AASA,MAAMA,KAAa;AAAA,EACjB;AAAA,IACE;AAAA,IACA;AAAA,MACE,GAAG;AAAA,MACH,KAAK;AAAA,IACX;AAAA,EACA;AACA,GACMI,KAAgBF,EAAiB,kBAAkBF,EAAU,GCyB7DK,KAA0B;AAEhC,SAASC,GAAgBC,GAA8B;AACrD,SAAIA,MAAU,IAAU,EAAE,SAAS,WAAW,WAAW,UAAA,IACrDA,KAASF,KACJ,EAAE,SAAS,WAAW,WAAW,UAAA,IACnC,EAAE,SAAS,SAAS,WAAW,UAAA;AACxC;AAEA,SAASG,GAAgBC,GAA+B;AACtD,MAAIA,KAAS,QAAQA,MAAU,GAAI,QAAO;AAC1C,QAAM,IAAI,OAAOA,KAAU,WAAWA,IAAQ,OAAOA,CAAK;AAC1D,SAAO,OAAO,SAAS,CAAC,IAAI,IAAI;AAClC;AAYO,SAASC,GACdC,GACA;AACA,QAAM,EAAE,OAAAF,GAAO,UAAAG,IAAW,OAAO,SAAAC,MAAYF,GACvC,EAAE,GAAAG,GAAG,MAAAC,MAASC,EAAe,IAAI,GAEjCT,IAAQC,GAAgBC,CAAK;AACnC,MAAIF,MAAU,KAAM,QAAO;AAE3B,QAAMU,IAASF,EAAK,YAAY,MAC1BG,IAAY,IAAI,KAAK,aAAaD,GAAQ;AAAA,IAC9C,OAAO;AAAA,IACP,UAAAL;AAAA,IACA,GAAGC;AAAA,EAAA,CACJ,EAAE,OAAON,IAAQ,GAAG,GAEf,EAAE,SAAAY,GAAS,WAAAC,MAAcd,GAAgBC,CAAK,GAC9Cc,IAASP,EAAE,+BAA+BM,CAAS,EAAE;AAE3D,SACE,gBAAAE,EAACC,KAAM,SAAAJ,GAAkB,SAAO,IAAC,MAAK,MAAK,WAAU,mBAInD,UAAA;AAAA,IAAA,gBAAAK,EAAC,UAAM,UAAAN,EAAA,CAAU;AAAA,IACjB,gBAAAM,EAAC,QAAA,EAAK,WAAU,cAAc,UAAAH,EAAA,CAAO;AAAA,EAAA,GACvC;AAEJ;AC9DA,MAAMI,KAEF;AAAA,EACF,UAAU;AAAA,EACV,UAAU;AAAA,EACV,MAAM;AACR;AAcA,SAASC,GAAiBjB,GAAgD;AACxE,SAAOA,MAAU,cAAcA,MAAU,cAAcA,MAAU;AACnE;AAQO,SAASkB,GACdhB,GAEA;AACA,QAAM,EAAE,GAAAG,EAAA,IAAME,EAAe,IAAI,GAC3B,EAAE,MAAAY,GAAM,OAAAnB,GAAO,MAAAoB,IAAO,SAASlB,GAG/BmB,KAAMF,KAAA,gBAAAA,EAAM,mBAAkBnB;AACpC,MAAI,CAACiB,GAAiBI,CAAG,EAAG,QAAO;AAEnC,QAAMX,IAAUM,GAAsBK,CAAG;AAEzC,SACE,gBAAAN,EAACD,GAAA,EAAM,SAAAJ,GAAkB,SAAO,IAAC,MAAAU,GAC9B,UAAAf,EAAE,+BAA+BgB,CAAG,EAAE,EAAA,CACzC;AAEJ;ACjDA,MAAMC,IAAsBC;AAAA,EAC1B;AAAA,IACE;AAAA,IACA;AAAA,EAAA,EACA,KAAK,GAAG;AAAA,EACV;AAAA,IACE,UAAU;AAAA,MACR,UAAU;AAAA;AAAA,QAER,MAAM;AAAA,QACN,OAAO;AAAA,MAAA;AAAA,IACT;AAAA,IAEF,iBAAiB;AAAA,MACf,UAAU;AAAA,IAAA;AAAA,EACZ;AAEJ;AA2BO,SAASC,GACdtB,GACA;;AACA,QAAM,EAAE,MAAAiB,GAAM,aAAAM,IAAc,GAAA,IAAUvB,GAChC,EAAE,GAAAG,EAAA,IAAME,EAAe,IAAI;AAEjC,MAAI,CAACY,EAAM,QAAO;AAElB,QAAM,EAAE,cAAAO,GAAc,OAAAC,GAAO,cAAAC,GAAc,YAAAC,MAAeV,GAEpDW,MAAeC,IAAAL,KAAA,gBAAAA,EAAe,OAAf,gBAAAK,EAAmB,WAAU,IAC5CC,IAAW,EAAQL,GAEnBM,KAAeP,KAAgB,CAAA,GAAI,KAAK,CAACQ,MAAMA,EAAE,UAAU,GAC3DC,IAAgB,GAAQP,KAAgBC;AAG9C,MAAI,CAACC,KAAgB,CAACE,EAAU,QAAO;AAEvC,QAAMI,IAAYX,IACdpB,EAAE,kCAAkC,IACnCsB,KAAS,IAERU,IACFhC,EADa4B,IACX,qCACA,oCADkC,GAGlCK,IACFjC,EADe8B,IACb,uCACA,sCADoC;AAG1C,SACE,gBAAAtB,EAAC,QAAA,EAAK,WAAU,6DACd,UAAA;AAAA,IAAA,gBAAAA,EAAC,QAAA,EAAK,WAAU,+EACb,UAAA;AAAA,MAAAiB,IACC,gBAAAf,EAAC,QAAA,EAAK,WAAU,uCACb,aACH,IACE;AAAA,MACHiB,IACC,gBAAAjB,EAAC,QAAA,EAAK,WAAU,+EACb,aACH,IACE;AAAA,IAAA,GACN;AAAA,IAEA,gBAAAF,EAAC,QAAA,EAAK,WAAU,0EACd,UAAA;AAAA,MAAA,gBAAAE,EAACwB,GAAA,EAAQ,OAAOF,GACd,UAAA,gBAAAtB;AAAA,QAAC;AAAA,QAAA;AAAA,UACC,MAAK;AAAA,UACL,cAAYsB;AAAA,UACZ,WAAWf,EAAoB,EAAE,UAAUW,GAAa;AAAA,UAEvD,UAAAA,sBACEtC,IAAA,EAAc,eAAW,IAAC,MAAM,IAAI,WAAU,iBAAA,CAAiB,IAEhE,gBAAAoB;AAAA,YAACrB;AAAA,YAAA;AAAA,cACC,eAAW;AAAA,cACX,MAAM;AAAA,cACN,WAAU;AAAA,YAAA;AAAA,UAAA;AAAA,QACZ;AAAA,MAAA,GAGN;AAAA,MAEA,gBAAAqB,EAACwB,GAAA,EAAQ,OAAOD,GACd,UAAA,gBAAAvB;AAAA,QAAC;AAAA,QAAA;AAAA,UACC,MAAK;AAAA,UACL,cAAYuB;AAAA,UACZ,WAAWhB,EAAoB,EAAE,UAAUa,GAAe;AAAA,UAEzD,cACC,gBAAApB,EAACyB,IAAA,EAAK,eAAW,IAAC,MAAM,IAAI,WAAU,iBAAA,CAAiB,sBAEtDhD,IAAA,EAAM,eAAW,IAAC,MAAM,IAAI,WAAU,iBAAA,CAAiB;AAAA,QAAA;AAAA,MAAA,EAE5D,CACF;AAAA,IAAA,EAAA,CACF;AAAA,EAAA,GACF;AAEJ;AAEAgC,GAAY,cAAc;ACpH1B,MAAMiB,IAA0BlB;AAAA,EAC9B;AAAA,EACA;AAAA,IACE,UAAU;AAAA,MACR,MAAM;AAAA,QACJ,SAAS;AAAA;AAAA;AAAA,QAGT,MAAM;AAAA;AAAA,QAEN,OAAO;AAAA,MAAA;AAAA,IACT;AAAA,IAEF,iBAAiB,EAAE,MAAM,UAAA;AAAA,EAAU;AAEvC,GAuBMmB,KAAS,OAAU,KAAK,KACxBC,KAA2B;AAEjC,SAASC,GAAO5C,GAA+B;AAC7C,MAAIA,KAAS,QAAQA,MAAU,GAAI,QAAO;AAC1C,QAAMK,IACJL,aAAiB,OACbA,EAAM,QAAA,IACN,OAAOA,KAAU,WACfA,IACA,IAAI,KAAK,OAAOA,CAAK,CAAC,EAAE,QAAA;AAChC,SAAO,OAAO,MAAMK,CAAC,IAAI,OAAOA;AAClC;AAOA,SAASwC,GACPC,GACAC,GACkD;AAClD,MAAIA,KAAkB,EAAG,QAAO;AAChC,QAAMC,IAAUF,IAAO,KAAK,IAAA;AAC5B,SAAIE,IAAU,IAAU,YACjBA,KAAWD,IAAiBL,KAAS,SAAS;AACvD;AAYO,SAASO,GACd/C,GAEA;AACA,QAAM,EAAE,GAAAG,EAAA,IAAME,EAAe,IAAI,GAC3B,EAAE,MAAAY,GAAM,OAAAnB,GAAO,gBAAA+C,IAAiBJ,OAA6BzC,GAG7D4C,IAAOF,IAAOzB,KAAA,gBAAAA,EAAM,oBAAmBnB,CAAK;AAElD,MAAI8C,MAAS;AACX,WACE,gBAAA/B,EAAC,QAAA,EAAK,WAAW0B,EAAwB,EAAE,MAAM,QAAA,CAAS,GACvD,UAAApC,EAAE,mCAAmC,EAAA,CACxC;AAIJ,QAAM6C,IAAOL,GAAYC,GAAMC,CAAc;AAE7C,2BACG,QAAA,EAAK,WAAWN,EAAwB,EAAE,MAAAS,EAAA,CAAM,GAC9C,UAAA;AAAA,IAAAA,MAAS,SACR,gBAAAnC,EAACoC,IAAA,EAAc,eAAY,QAAO,WAAU,2BAA0B,IACpE;AAAA,sBACHC,IAAA,EAAU,OAAON,GAAM,QAAO,YAAW,OAAM,OAAA,CAAO;AAAA,EAAA,GACzD;AAEJ;AC9GA,SAASO,GACPC,GACAC,GACe;AACf,SAAI,OAAOD,KAAW,aACZA,EAA8CC,CAAG,IAEpDD;AACT;AAIA,SAASE,GAASC,GAAsB;AACtC,SAAO,uBAAuB,KAAKA,CAAI,IAAIA,IAAO;AACpD;AAEA,SAASC,GAASH,GAAyB;AACzC,SAAO,CAACA,EAAI,WAAWA,EAAI,QAAQ,EAAE,OAAO,OAAO,EAAE,KAAK,GAAG,EAAE,KAAA;AACjE;AAOO,SAASI,GACdzD,GACA;;AACA,QAAM,EAAE,MAAAiB,GAAM,MAAAyC,GAAM,MAAAH,GAAM,UAAAI,MAAa3D,GACjC,EAAE,GAAAG,EAAA,IAAME,EAAe,IAAI;AAIjC,MAAI,CAACY,KAAQyC,KAAA,QAAAA,EAAM,UAAW,QAAO;AAErC,QAAME,IAAOJ,GAASvC,CAAI;AAC1B,MAAI,CAAC2C,EAAM,QAAO;AAElB,QAAMC,IAAeV,GAAQI,GAAMtC,CAAI,GACjC6C,MAAajC,IAAAZ,EAAK,sBAAL,gBAAAY,EAAwB,WAAU,QAI/CkC,IAAY5D,EAAE,qCAAqC,EAAE,MAAAyD,GAAM,GAE3DI,IAAqB;AAAA,IACzB;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EAAA,EACA,KAAK,GAAG,GAEJC,IAAc,CAACC,MAAsB;AACzC,IAAKP,MACAE,KAAcK,EAAM,eAAA,GAEzBA,EAAM,gBAAA,GACNP,EAAS1C,CAAI;AAAA,EACf,GAEMkD,IACJ,gBAAAxD,EAAAyD,IAAA,EACE,UAAA;AAAA,IAAA,gBAAAvD;AAAA,MAACwD;AAAA,MAAA;AAAA,QACC,MAAAT;AAAA,QACA,KAAK3C,EAAK;AAAA,QACV,MAAK;AAAA,QACL,eAAY;AAAA,QACZ,WAAU;AAAA,MAAA;AAAA,IAAA;AAAA,IAEZ,gBAAAN,EAAC,QAAA,EAAK,WAAU,mDACd,UAAA;AAAA,MAAA,gBAAAE,EAAC,QAAA,EAAK,WAAU,2FACb,UAAA+C,GACH;AAAA,MACCE,IACC,gBAAAnD,EAAC,QAAA,EAAK,WAAU,iEACd,UAAA;AAAA,QAAA,gBAAAA,EAAC,QAAA,EAAK,WAAU,cACb,UAAA;AAAA,UAAAR,EAAE,uCAAuC;AAAA,UACzC;AAAA,QAAA,GACH;AAAA,QACC2D;AAAA,MAAA,EAAA,CACH,IACE;AAAA,IAAA,EAAA,CACN;AAAA,EAAA,GACF;AAGF,SAAOD,IACL,gBAAAhD;AAAA,IAAC;AAAA,IAAA;AAAA,MACC,MAAMyC,GAASO,CAAY;AAAA,MAC3B,cAAYE;AAAA,MACZ,SAASE;AAAA,MACT,WAAWD;AAAA,MAEV,UAAAG;AAAA,IAAA;AAAA,EAAA,IAGH,gBAAAtD;AAAA,IAAC;AAAA,IAAA;AAAA,MACC,MAAK;AAAA,MACL,cAAYkD;AAAA,MACZ,SAASE;AAAA,MACT,WAAW,+CAA+CD,CAAkB;AAAA,MAE3E,UAAAG;AAAA,IAAA;AAAA,EAAA;AAGP;AClDO,SAASG,EACdC,GAC4B;AAC5B,SAAQA,EAAiC;AAC3C;AAiDA,SAASC,GACPrE,GACAsE,GACyB;AACzB,QAAMC,IACJ,CAACC,MACD,CAACC,MAA8B;AAC7B,IAAAH,KAAA,QAAAA,EAAcE,GAAQC;AAAA,EACxB,GAIIC,IAAO,CACXF,GACAG,OAC2B;AAAA,IAC3B,MAAMH,EAAO;AAAA,IACb,OAAOA,EAAO;AAAA,IACd,SAASA,EAAO;AAAA,IAChB,SAASD,EAASC,CAAM;AAAA,IACxB,GAAGG;AAAA,EAAA;AAGL,SAAO;AAAA,IACLD;AAAA,MACE;AAAA,QACE,IAAI;AAAA,QACJ,OAAO1E,EAAE,2BAA2B;AAAA,QACpC,MAAM4E,EAAcC,IAAK,EAAE,eAAe,QAAQ;AAAA,MAAA;AAAA,MAEpD,CAAA;AAAA,IAAC;AAAA,IAEHH;AAAA,MACE;AAAA,QACE,IAAI;AAAA,QACJ,OAAO1E,EAAE,2BAA2B;AAAA,QACpC,MAAM4E,EAAcE,IAAQ,EAAE,eAAe,QAAQ;AAAA,MAAA;AAAA,MAEvD,CAAA;AAAA,IAAC;AAAA,IAEHJ;AAAA,MACE;AAAA,QACE,IAAI;AAAA,QACJ,OAAO1E,EAAE,wCAAwC;AAAA,QACjD,MAAM4E,EAAczC,IAAM,EAAE,eAAe,QAAQ;AAAA,MAAA;AAAA;AAAA,MAGrD,EAAE,QAAQ,CAACsC,MAAY,CAACA,EAAQ,aAAA;AAAA,IAAa;AAAA,IAE/CC;AAAA,MACE;AAAA,QACE,IAAI;AAAA,QACJ,OAAO1E,EAAE,sCAAsC;AAAA,QAC/C,MAAM4E,EAActF,IAAe,EAAE,eAAe,QAAQ;AAAA,MAAA;AAAA;AAAA,MAG9D;AAAA,QACE,QAAQ,CAACmF,MACP,EAAEA,EAAQ,gBAAgB,CAAA,GAAI,KAAK,CAAC5C,MAAMA,EAAE,UAAU;AAAA,MAAA;AAAA,IAC1D;AAAA,IAEF6C;AAAA,MACE;AAAA,QACE,IAAI;AAAA,QACJ,OAAO1E,EAAE,+BAA+B;AAAA,QACxC,MAAM4E,EAAcG,IAAO,EAAE,eAAe,QAAQ;AAAA,MAAA;AAAA,MAEtD,CAAA;AAAA,IAAC;AAAA,IAEHL;AAAA,MACE;AAAA,QACE,IAAI;AAAA,QACJ,OAAO1E,EAAE,6BAA6B;AAAA,QACtC,MAAM4E,EAAcI,IAAQ,EAAE,eAAe,QAAQ;AAAA,QACrD,SAAS;AAAA,MAAA;AAAA;AAAA;AAAA,MAIX;AAAA,QACE,UAAU,CAACP,MAAY,EAAQA,EAAQ;AAAA,QACvC,gBAAgBzE,EAAE,mCAAmC;AAAA,MAAA;AAAA,IACvD;AAAA,EACF;AAEJ;AAMA,MAAMiF,KAAK,MAAM;AAYV,SAASC,GACdlF,GACAmF,IAAmC,IACf;AACpB,QAAM;AAAA,IACJ,aAAA/D,IAAc;AAAA,IACd,mBAAAgE,IAAoBH;AAAA,IACpB,aAAAX;AAAA,IACA,cAAAe;AAAA,EAAA,IACEF,GAEEG,IAAUjB,GAAgBrE,GAAGsE,CAAW,GAExCiB,IAAkE;AAAA,IACtE,GAAGvF,EAAE,uBAAuB;AAAA,IAC5B,GAAGA,EAAE,uBAAuB;AAAA,IAC5B,GAAGA,EAAE,uBAAuB;AAAA,EAAA,GAGxBwF,IAAS,CAACC,MACdzF,EAAE,uBAAuByF,CAAE,EAAE;AAmT/B,SAjTyC;AAAA;AAAA,IAEvC;AAAA,MACE,OAAO;AAAA,MACP,YAAYD,EAAO,UAAU;AAAA;AAAA;AAAA;AAAA,MAI7B,QAAQ;AAAA,MACR,cAAclC;AAAA,MACd,oBAAoB;AAAA,QAClB,MAAM+B;AAAA;AAAA;AAAA,QAGN,UAAUf,IACN,CAACpB,MACCoB;AAAA,UACE,EAAE,IAAI,QAAQ,OAAOtE,EAAE,2BAA2B,EAAA;AAAA,UAClDkD;AAAA,QAAA,IAEJ;AAAA,MAAA;AAAA;AAAA,MAGN,aAAa,CAACwC,MACZA,EAAO,OACH,CAACA,EAAO,KAAK,WAAWA,EAAO,KAAK,QAAQ,EACzC,OAAO,OAAO,EACd,KAAK,GAAG,EACR,SACH;AAAA,MACN,QAAQC;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,MAAM;AAAA;AAAA,IAAA;AAAA;AAAA,IAKR;AAAA,MACE,OAAO;AAAA,MACP,YAAYJ,EAAO,iBAAiB;AAAA,MACpC,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,cAAc5C;AAAA,MACd,QAAQiD;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYN,EAAO,eAAe;AAAA,MAClC,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,MAAM;AAAA,MACN,cAAc5F;AAAA,MACd,QAAQmG;AAAA,MACR,yBAAyBC;AAAA;AAAA,MAEzB,cAAc,EAAE,iBAAiB,WAAW,KAAK,EAAA;AAAA,MACjD,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYR,EAAO,OAAO;AAAA,MAC1B,gBAAgB;AAAA,MAChB,cAAcrE;AAAA,MACd,oBAAoB,EAAE,aAAAC,EAAA;AAAA;AAAA,MAEtB,mBAAmB,CAACsE,MAAA;;AAClB,iBAAAO,KAAAC,KAAAxE,IAAAgE,EAAO,SAAP,gBAAAhE,EAAa,iBAAb,gBAAAwE,EAA4B,OAA5B,gBAAAD,EAAgC,WAAU;AAAA;AAAA,MAC5C,QAAQE;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYZ,EAAO,OAAO;AAAA,MAC1B,gBAAgB;AAAA,MAChB,OAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,MAUP,MAAMpE,KAAe;AAAA,MACrB,QAAQ+E;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYZ,EAAO,gBAAgB;AAAA,MACnC,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,cAAc3E;AAAA,MACd,QAAQwF;AAAA,MACR,yBAAyBC;AAAA,MACzB,cAAc;AAAA,QACZ,SAAS;AAAA,UACP;AAAA,YACE,OAAO;AAAA,YACP,OAAOtG,EAAE,sCAAsC;AAAA,UAAA;AAAA,UAEjD;AAAA,YACE,OAAO;AAAA,YACP,OAAOA,EAAE,sCAAsC;AAAA,UAAA;AAAA,UAEjD,EAAE,OAAO,QAAQ,OAAOA,EAAE,kCAAkC,EAAA;AAAA,QAAE;AAAA,MAChE;AAAA,MAEF,UAAU;AAAA,MACV,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYwF,EAAO,WAAW;AAAA,MAC9B,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,cAAce;AAAA,MACd,oBAAoB,EAAE,QAAQ,WAAA;AAAA,MAC9B,QAAQV;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYN,EAAO,aAAa;AAAA,MAChC,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,cAAce;AAAA,MACd,oBAAoB,EAAE,QAAQ,OAAA;AAAA,MAC9B,QAAQV;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYN,EAAO,QAAQ;AAAA,MAC3B,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,MAAM;AAAA;AAAA,MAEN,aAAa,CAACE;;AACZ,gBAAAhE,IAAAgE,EAAO,SAAP,QAAAhE,EAAa,SAAS6D,EAAaG,EAAO,KAAK,MAAM,IAAI;AAAA;AAAA,MAC3D,QAAQW;AAAA,MACR,yBAAyBC;AAAA,MACzB,cAAc;AAAA,QACZ,SAAS;AAAA,UACP,EAAE,OAAOf,EAAa,GAAG,OAAOA,EAAa,EAAA;AAAA,UAC7C,EAAE,OAAOA,EAAa,GAAG,OAAOA,EAAa,EAAA;AAAA,UAC7C,EAAE,OAAOA,EAAa,GAAG,OAAOA,EAAa,EAAA;AAAA,QAAE;AAAA,MACjD;AAAA,MAEF,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYC,EAAO,QAAQ;AAAA,MAC3B,gBAAgB;AAAA;AAAA,MAEhB,aAAa,CAACE,MAAA;;AACZ,gBAAAhE,IAAAgE,EAAO,SAAP,QAAAhE,EAAa,SAAS,CAACgE,EAAO,KAAK,MAAM,IAAI,CAAA;AAAA;AAAA,MAC/C,cAAcc;AAAA,MACd,mBAAmB,CAACd,MAAA;;AAAW,iBAAAhE,IAAAgE,EAAO,SAAP,gBAAAhE,EAAa,WAAU;AAAA;AAAA,MACtD,QAAQ2E;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYd,EAAO,kBAAkB;AAAA,MACrC,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,QAAQa;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYd,EAAO,YAAY;AAAA,MAC/B,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,QAAQW;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYZ,EAAO,MAAM;AAAA,MACzB,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,cAAcgB;AAAA;AAAA,MAEd,mBAAmB,CAACd,MAAA;;AAAW,iBAAAhE,IAAAgE,EAAO,SAAP,gBAAAhE,EAAa,SAAQ,CAAA;AAAA;AAAA,MACpD,QAAQ2E;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYd,EAAO,gBAAgB;AAAA,MACnC,gBAAgB;AAAA,MAChB,cAAciB;AAAA,MACd,aAAa,CAACf;;AACZ,gBAAAhE,IAAAgE,EAAO,SAAP,QAAAhE,EAAa,oBACR,EAAE,MAAMgE,EAAO,KAAK,kBAAA,IACrB;AAAA;AAAA,MACN,YAAY,CAACgB,GAAyBC,QACnCD,KAAA,gBAAAA,EAAG,SAAQ,IAAI,eAAcC,KAAA,gBAAAA,EAAG,SAAQ,EAAE;AAAA,MAC7C,mBAAmB,CAACjB,MAAA;;AAAW,iBAAAhE,IAAAgE,EAAO,SAAP,gBAAAhE,EAAa,sBAAqB;AAAA;AAAA,MACjE,QAAQiE;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYJ,EAAO,WAAW;AAAA,MAC9B,gBAAgB;AAAA,MAChB,OAAO;AAAA,MACP,cAAce;AAAA,MACd,oBAAoB,EAAE,QAAQ,OAAA;AAAA,MAC9B,QAAQV;AAAA,MACR,yBAAyBC;AAAA,MACzB,UAAU;AAAA,MACV,OAAO;AAAA,IAAA;AAAA;AAAA,IAIT;AAAA,MACE,OAAO;AAAA,MACP,YAAYN,EAAO,SAAS;AAAA;AAAA;AAAA;AAAA,MAI5B,QAAQ;AAAA;AAAA;AAAA,MAGR,aAAa;AAAA,MACb,WAAW;AAAA,MACX,cAAcoB;AAAA,MACd,oBAAoB;AAAA,QAClB,SAAAtB;AAAA,QACA,QAAQ;AAAA,QACR,OAAO;AAAA,QACP,OAAOtF,EAAE,4BAA4B;AAAA,QACrC,WAAWoF;AAAA,MAAA;AAAA,MAEb,UAAU;AAAA,MACV,QAAQ;AAAA,MACR,WAAW;AAAA;AAAA;AAAA;AAAA,MAIX,OAAO;AAAA,MACP,UAAU;AAAA;AAAA,IAAA;AAAA,EAEZ;AAIJ;ACngBA,MAAMyB,KAA6C;AAAA,EACjD,EAAE,UAAU,GAAG,MAAM,KAAA;AAAA,EACrB,EAAE,UAAU,KAAK,MAAM,KAAA;AAAA,EACvB,EAAE,UAAU,KAAK,MAAM,KAAA;AAAA,EACvB,EAAE,UAAU,MAAM,MAAM,KAAA;AAC1B;AAGA,SAASC,EACPC,GACAC,GACqB;AACrB,QAAMC,wBAAc,IAAA;AACpB,aAAWC,KAAMF;AACf,IAAID,KAASG,EAAG,YAAUD,EAAQ,IAAIC,EAAG,IAAI;AAG/C,SAAAD,EAAQ,IAAI,IAAI,GACTA;AACT;AAgEO,SAASE,GACdC,GACAjC,GAC4B;AAC5B,QAAM;AAAA,IACJ,cAAAkC;AAAA,IACA,SAAAC,IAAU;AAAA,IACV,aAAAN,IAAcH;AAAA,EAAA,IACZ1B,GAQEoC,IAAiBC,EAAoB,oBAAI,KAAK,GAI9CC,IAAcD,EAAO,EAAK;AAEhC,SAAAE,GAAU,MAAM;AACd,UAAMC,IAAYN,EAAa;AAC/B,QAAI,CAACC,KAAW,CAACK,EAAW;AAI5B,UAAMC,IAAS,MAAA;;AAAM,cAAAlG,IAAA0F,EAAU,YAAV,gBAAA1F,EAAmB;AAAA,OAQlCmG,IAAkB,CAAC9D,MAA0C;AAEjE,UADI0D,EAAY,WACZ1D,EAAM,WAAW,MAAO;AAC5B,YAAM+D,IAAU/D,EAAM,YAAYA,EAAM,SAAS,CAACA,EAAM,MAAM,IAAI;AAClE,iBAAWgE,KAAOD;AAChB,QAAAP,EAAe,QAAQ,IAAIQ,EAAI,SAAA,CAAU;AAAA,IAE7C;AAMA,QAAIC,IAAQ;AAWZ,UAAMC,IAAc,CAACC,MAAgD;AACnE,UAAIF,EAAO;AACX,MAAAA,IAAQ;AACR,YAAMG,IAAOD,EAAI,WAAA,GACXnB,IAAQY,EAAU,sBAAA,EAAwB,OAC1CS,IAAetB,EAAqBC,GAAOC,CAAW;AAC5D,UAAImB;AACF,mBAAWJ,KAAOI,GAAM;AACtB,gBAAME,IAAOlE,EAAkB4D,EAAI,UAAA,CAAW;AAC9C,UAAIM,KAAQ,CAACN,EAAI,UAAA,KAAeK,EAAa,IAAIC,CAAI,KACnDd,EAAe,QAAQ,IAAIQ,EAAI,SAAA,CAAU;AAAA,QAE7C;AAEF,MAAAG,EAAI,iBAAiB,iBAAiBL,CAAe;AAAA,IACvD,GAGMS,IAAY,MAAM;AACtB,YAAMJ,IAAMN,EAAA;AACZ,UAAI,CAACM,EAAK;AACV,MAAAD,EAAYC,CAAG;AACf,YAAMK,IAAUL,EAAI,WAAA;AACpB,UAAI,CAACK,EAAS;AAEd,YAAMxB,IAAQY,EAAU,sBAAA,EAAwB,OAC1CS,IAAetB,EAAqBC,GAAOC,CAAW,GAItDwB,IAAmB,CAAA,GACnBC,IAAmB,CAAA;AAEzB,iBAAWV,KAAOQ,GAAS;AACzB,cAAMG,IAAQX,EAAI,SAAA;AAElB,YAAIR,EAAe,QAAQ,IAAImB,CAAK,EAAG;AAEvC,cAAML,IAAOlE,EAAkB4D,EAAI,UAAA,CAAW;AAE9C,YAAI,CAACM,EAAM;AAEX,cAAMM,IAAaP,EAAa,IAAIC,CAAI;AACxC,QAAIM,KAAc,CAACZ,EAAI,cAAaS,EAAO,KAAKT,CAAG,IAC1C,CAACY,KAAcZ,EAAI,eAAaU,EAAO,KAAKV,CAAG;AAAA,MAC1D;AAEA,UAAI,EAAAS,EAAO,WAAW,KAAKC,EAAO,WAAW,IAE7C;AAAA,QAAAhB,EAAY,UAAU;AACtB,YAAI;AAKF,UAAIe,EAAO,SAAS,KAAGN,EAAI,kBAAkBM,GAAQ,EAAI,GACrDC,EAAO,SAAS,KAAGP,EAAI,kBAAkBO,GAAQ,EAAK;AAAA,QAC5D,UAAA;AACE,UAAAhB,EAAY,UAAU;AAAA,QACxB;AAAA;AAAA,IACF,GAKMmB,IAAW,IAAI,eAAe,MAAMN,GAAW;AACrD,WAAAM,EAAS,QAAQjB,CAAS,GAC1BW,EAAA,GAEO,MAAM;;AACX,MAAAM,EAAS,WAAA,IAETlH,IAAAkG,QAAA,QAAAlG,EAAU,oBAAoB,iBAAiBmG;AAAA,IACjD;AAAA,EACF,GAAG,CAACR,GAAcC,GAASN,GAAaI,CAAS,CAAC,GAY3C,EAAE,aAJWyB,EAAY,CAACC,MAA8B;AAC7D,eAAWrD,KAAMqD,EAAQ,CAAAvB,EAAe,QAAQ,IAAI9B,CAAE;AAAA,EACxD,GAAG,CAAA,CAAE,EAEI;AACX;ACnHA,SAASsD,GACPrD,GACoB;;AACpB,UAAOhE,IAAAgE,EAAO,SAAP,QAAAhE,EAAa,aAAa,4BAA4B;AAC/D;AAcA,SAASsH,GAAgBtD,GAA4C;AACnE,SAAOA,EAAO,KAAK;AACrB;AAyCA,SAASuD,GAAa;AAAA,EACpB,OAAAC;AAAA,EACA,WAAA9B;AAAA,EACA,aAAA+B;AAAA,EACA,OAAAC;AACF,GAAsB;AACpB,QAAM,CAACC,GAAcC,CAAe,IAAIC,EAAiB,EAAE,GAErDxJ,IAAUyJ;AAAA,IACd,MAAMN,EAAM,IAAI,CAACO,OAAU,EAAE,OAAOA,EAAK,IAAI,OAAOA,EAAK,MAAA,EAAQ;AAAA,IACjE,CAACP,CAAK;AAAA,EAAA,GAGFQ,IAAYb;AAAA,IAChB,CAACc,MAAmB;AAClB,YAAMF,IAAOP,EAAM,KAAK,CAACU,MAAMA,EAAE,OAAOD,CAAM,GACxCE,IAASzC,EAAU;AACzB,UAAI,CAACqC,KAAQ,CAACI,EAAQ;AAEtB,YAAM3B,IAAM2B,EAAO,UAAA;AACnB,UAAI3B,GAAK;AACP,cAAM4B,IAAS,IAAI,IAAYL,EAAK,OAAO,GACrCjB,IAAmB,CAAA,GACnBC,IAAmB,CAAA;AACzB,mBAAWV,KAAOG,EAAI,WAAA,KAAgB,CAAA,GAAI;AAIxC,cAAI/D,EAAkB4D,EAAI,UAAA,CAAW,MAAM,OAAW;AACtD,gBAAMW,IAAQX,EAAI,SAAA;AAClB,UAAI+B,EAAO,IAAIpB,CAAK,IAAGF,EAAO,KAAKE,CAAK,IACnCD,EAAO,KAAKC,CAAK;AAAA,QACxB;AAIA,QAAAS,EAAY,CAAC,GAAGX,GAAQ,GAAGC,CAAM,CAAC,GAC9BD,EAAO,SAAS,KAAGN,EAAI,kBAAkBM,GAAQ,EAAI,GACrDC,EAAO,SAAS,KAAGP,EAAI,kBAAkBO,GAAQ,EAAK;AAAA,MAC5D;AAEA,MAAAoB,EAAO,UAAUJ,EAAK,WAAW,GACjCI,EAAO,QAAQJ,EAAK,SAAS,GAC7BvB,KAAA,QAAAA,EAAK;AAAA,IACP;AAAA,IACA,CAACgB,GAAO9B,GAAW+B,CAAW;AAAA,EAAA,GAG1BY,IAAoBlB;AAAA,IACxB,CAACmB,MAAiB;AAChB,MAAAV,EAAgBU,CAAI,GAChBA,OAAgBA,CAAI;AAAA,IAC1B;AAAA,IACA,CAACN,CAAS;AAAA,EAAA;AAGZ;AAAA;AAAA;AAAA;AAAA,IAIE,gBAAAhJ,EAAC,OAAA,EAAI,WAAU,qDACb,UAAA,gBAAAA;AAAA,MAACuJ;AAAA,MAAA;AAAA,QACC,SAAAlK;AAAA,QACA,OAAOsJ;AAAA,QACP,eAAeU;AAAA,QACf,MAAK;AAAA,QACL,cAAYX;AAAA,MAAA;AAAA,IAAA,EACd,CACF;AAAA;AAEJ;AAMO,MAAMc,KAAeC;AAAA,EAC1B,SACE;AAAA,IACE,SAAAC;AAAA,IACA,SAAA7B;AAAA,IACA,QAAA8B;AAAA,IACA,SAAAC;AAAA,IACA,YAAAC,IAAa;AAAA,IACb,OAAArB;AAAA,IACA,aAAA5E;AAAA,IACA,aAAAkG;AAAA,IACA,SAAAC,IAAU;AAAA,IACV,SAAAC;AAAA,IACA,iBAAAC,IAAkB;AAAA,IAClB,4BAAAC;AAAA,IACA,aAAAxJ,IAAc;AAAA,IACd,cAAAiE;AAAA,IACA,cAAcwF;AAAA,IACd,WAAAC;AAAA,EAAA,GAEFC,GACA;AACA,UAAM,EAAE,GAAA/K,EAAA,IAAME,EAAe,IAAI,GAK3BkH,IAAYI,EAAkC,IAAI,GAKlDH,IAAeG,EAA8B,IAAI,GAKjD,CAACwD,GAAmBC,CAAoB,IAC5C1B,EAAoC,IAAI;AAK1C,IAAA2B;AAAA,MACEH;AAAA,MACA,MAAOC,KAAqB5D,EAAU;AAAA,MACtC,CAAC4D,CAAiB;AAAA,IAAA;AAUpB,UAAM,EAAE,aAAA7B,EAAA,IAAgBhC,GAAqBC,GAAW;AAAA,MACtD,cAAAC;AAAA,MACA,SAASkD;AAAA,IAAA,CACV,GAMKY,IAAa3B;AAAA,MACjB,MACEjB,KACArD,GAAoBlF,GAAG;AAAA,QACrB,aAAAoB;AAAA,QACA,aAAAkD;AAAA,QACA,cAAAe;AAAA,QACA,mBAAmB,MAAMiF,MAAY;AAAA,MAAA,CACtC;AAAA,MACH,CAAC/B,GAASvI,GAAGoB,GAAakD,GAAae,GAAciF,CAAO;AAAA,IAAA,GAWxDc,OAAYlC,KAAA,gBAAAA,EAAO,WAAU,KAAK,GAClCmC,KACJ,gBAAA7K,EAAC8K,EAAU,SAAV,EACC,UAAA;AAAA,MAAA,gBAAA9K,EAAC8K,EAAU,QAAQ,WAAlB,EACE,UAAA;AAAA,QAAAF,MAAYlC,IACX,gBAAAxI;AAAA,UAACuI;AAAA,UAAA;AAAA,YACC,OAAAC;AAAA,YACA,WAAA9B;AAAA,YACA,aAAA+B;AAAA,YACA,OAAOnJ,EAAE,0BAA0B;AAAA,UAAA;AAAA,QAAA,IAEnC;AAAA,QACH2K,IAAkB,OAAO,gBAAAjK,EAAC4K,EAAU,QAAQ,aAAlB,EAA8B;AAAA,QACzD,gBAAA5K,EAAC4K,EAAU,QAAQ,aAAlB,CAAA,CAA8B;AAAA,MAAA,GACjC;AAAA,MACA,gBAAA9K,EAAC8K,EAAU,QAAQ,SAAlB,EACE,UAAA;AAAA,QAAAd,KAAA,gBAAAA,EAAa,IAAI,CAAChG,MACjB,gBAAA9D;AAAA,UAAC4K,EAAU,QAAQ;AAAA,UAAlB;AAAA,YAEC,OAAO9G,EAAO;AAAA,YACd,MAAMA,EAAO;AAAA,YACb,SAASA,EAAO;AAAA,YAChB,SAAS,CAAC0D,MAAQ;AAGhB,oBAAMqD,MACJrD,KAAA,gBAAAA,EACI,mBACD,IAAI,CAAC3E,MAASA,EAAK,IACnB,OAAO,CAACkC,MAAqBA,KAAM,UAAS,CAAA;AACjD,cAAAjB,EAAO,SAAS+G,EAAG;AAAA,YACrB;AAAA,UAAA;AAAA,UAbK/G,EAAO;AAAA,QAAA;AAAA,QAgBhB,gBAAA9D,EAAC4K,EAAU,QAAQ,cAAlB,CAAA,CAA+B;AAAA,QAChC,gBAAA5K,EAAC4K,EAAU,QAAQ,YAAlB,CAAA,CAA6B;AAAA,MAAA,EAAA,CAChC;AAAA,IAAA,GACF,GAGIE,KAAiBd,KAAWW,IAI5BI,KAAmBhB,IAAU,SAAYL,GAKzCsB,KAAclC,EAAQ,OAAO,EAAE,UAAUR,GAAA,IAAoB,EAAE;AAOrE,WAAA2C;AAAA,MACEC;AAAA,MACAZ;AAAA,MACAX;AAAA,IAAA,GAIA,gBAAA3J;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,KAAK2G;AAAA,QACL,MAAK;AAAA,QACL,cAAYwD,KAAa7K,EAAE,0BAA0B;AAAA,QACrD,kBAAe;AAAA,QACf,qBAAmBqK;AAAA,QACnB,WAAU;AAAA,QAEV,UAAA,gBAAA3J;AAAA,UAAC4K;AAAA,UAAA;AAAA,YACC,KAAK,CAACO,MAAa;AACjB,cAAAzE,EAAU,UAAUyE,GAGpBZ;AAAA,gBAAqB,CAACa,MACpBA,MAASD,IAAWC,IAAOD;AAAA,cAAA;AAAA,YAE/B;AAAA,YACA,QAAAxB;AAAA,YACA,YAAAc;AAAA,YACA,SAASM;AAAA,YACT,cAAa;AAAA,YACb,YAAU;AAAA,YACT,GAAIb,MAA+B,SAChC,EAAE,4BAAAA,EAAA,IACF,CAAA;AAAA,YACJ,SAAAN;AAAA,YACA,aAAavB;AAAA,YACb,aAAA2C;AAAA,YACA,WAAAZ;AAAA,YAEC,UAAAU;AAAA,UAAA;AAAA,QAAA;AAAA,MACH;AAAA,IAAA;AAAA,EAGN;AACF;AAEAtB,GAAa,cAAc;","x_google_ignoreList":[0,1,2]}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"payment-request-card-DioWKBUq.js","sources":["../../node_modules/lucide-react/dist/esm/icons/credit-card.js","../../node_modules/lucide-react/dist/esm/icons/hash.js","../../node_modules/lucide-react/dist/esm/icons/receipt-text.js","../../src/components/payment-card/payment-card.agent.ts","../../src/components/payment-card/payment-card.tsx","../../src/components/payment-card/payment-request-card.agent.ts","../../src/components/payment-card/payment-request-card.tsx"],"sourcesContent":["/**\n * @license lucide-react v1.8.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst __iconNode = [\n [\"rect\", { width: \"20\", height: \"14\", x: \"2\", y: \"5\", rx: \"2\", key: \"ynyp8z\" }],\n [\"line\", { x1: \"2\", x2: \"22\", y1: \"10\", y2: \"10\", key: \"1b3vmo\" }]\n];\nconst CreditCard = createLucideIcon(\"credit-card\", __iconNode);\n\nexport { __iconNode, CreditCard as default };\n//# sourceMappingURL=credit-card.js.map\n","/**\n * @license lucide-react v1.8.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst __iconNode = [\n [\"line\", { x1: \"4\", x2: \"20\", y1: \"9\", y2: \"9\", key: \"4lhtct\" }],\n [\"line\", { x1: \"4\", x2: \"20\", y1: \"15\", y2: \"15\", key: \"vyu0kd\" }],\n [\"line\", { x1: \"10\", x2: \"8\", y1: \"3\", y2: \"21\", key: \"1ggp8o\" }],\n [\"line\", { x1: \"16\", x2: \"14\", y1: \"3\", y2: \"21\", key: \"weycgp\" }]\n];\nconst Hash = createLucideIcon(\"hash\", __iconNode);\n\nexport { __iconNode, Hash as default };\n//# sourceMappingURL=hash.js.map\n","/**\n * @license lucide-react v1.8.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst __iconNode = [\n [\"path\", { d: \"M13 16H8\", key: \"wsln4y\" }],\n [\"path\", { d: \"M14 8H8\", key: \"1l3xfs\" }],\n [\"path\", { d: \"M16 12H8\", key: \"1fr5h0\" }],\n [\n \"path\",\n {\n d: \"M4 3a1 1 0 0 1 1-1 1.3 1.3 0 0 1 .7.2l.933.6a1.3 1.3 0 0 0 1.4 0l.934-.6a1.3 1.3 0 0 1 1.4 0l.933.6a1.3 1.3 0 0 0 1.4 0l.933-.6a1.3 1.3 0 0 1 1.4 0l.934.6a1.3 1.3 0 0 0 1.4 0l.933-.6A1.3 1.3 0 0 1 19 2a1 1 0 0 1 1 1v18a1 1 0 0 1-1 1 1.3 1.3 0 0 1-.7-.2l-.933-.6a1.3 1.3 0 0 0-1.4 0l-.934.6a1.3 1.3 0 0 1-1.4 0l-.933-.6a1.3 1.3 0 0 0-1.4 0l-.933.6a1.3 1.3 0 0 1-1.4 0l-.934-.6a1.3 1.3 0 0 0-1.4 0l-.933.6a1.3 1.3 0 0 1-.7.2 1 1 0 0 1-1-1z\",\n key: \"ycz6yz\"\n }\n ]\n];\nconst ReceiptText = createLucideIcon(\"receipt-text\", __iconNode);\n\nexport { __iconNode, ReceiptText as default };\n//# sourceMappingURL=receipt-text.js.map\n","/* -------------------------------------------------------------------- */\n/* Agent adapter — PaymentCard. */\n/* */\n/* Read-only financial-record surface. Exposes the payment number */\n/* (identifier) and the resolved headline state (structural) — never */\n/* patient / operator names or any other PHI. No actions: the card is a */\n/* passive presentation surface. */\n/* -------------------------------------------------------------------- */\n\nimport type { AgentAdapter } from '../../agent/types';\nimport type { PaymentCardHandle } from './payment-card';\n\nexport const paymentCardAgent: AgentAdapter<PaymentCardHandle> = {\n id: 'payment-card',\n capabilities: [],\n state: {\n number: {\n type: 'string',\n descriptionKey: 'ui.agent.paymentCard.state.number',\n description: 'Payment number / reference currently rendered.',\n read: (handle) => handle.getNumber(),\n },\n state: {\n type: \"'debt' | 'to-invoice' | 'settled'\",\n descriptionKey: 'ui.agent.paymentCard.state.state',\n description:\n 'Resolved headline financial state. Structural state only — never patient identity.',\n read: (handle) => handle.getState(),\n },\n },\n actions: {},\n domHooks: {\n root: {\n attr: 'data-component',\n value: 'payment-card',\n description: 'Marks the PaymentCard root region.',\n },\n instanceId: {\n attr: 'data-component-id',\n sourceProp: 'id',\n description: 'Sourced from the id prop. Addresses a specific card.',\n },\n },\n};\n","import {\n forwardRef,\n useId,\n useMemo,\n type ComponentPropsWithoutRef,\n type ReactNode,\n} from 'react';\nimport { cva, type VariantProps } from 'class-variance-authority';\nimport { useTranslation } from 'react-i18next';\nimport {\n ArrowDownLeft,\n ArrowUpRight,\n CalendarDays,\n FileText,\n Hash,\n ReceiptText,\n User,\n UserCog,\n} from 'lucide-react';\nimport { Badge } from '../badge/badge';\nimport { Card } from '../card/card';\nimport { DescriptionList } from '../description-list/description-list';\nimport { KeyValueList, KeyValuePair } from '../key-value-pair/key-value-pair';\nimport { TransactionChip } from '../transaction-chip/transaction-chip';\nimport { entitySurfaceVariants } from '../_shared/entity-card';\nimport { useAgentRegistration } from '../../agent/registry';\nimport { paymentCardAgent } from './payment-card.agent';\n\n/* -------------------------------------------------------------------- */\n/* PaymentCard */\n/* */\n/* Financial-record card for a single payment / receipt. Replaces the */\n/* hand-rolled \"Pagamento\" / payment-row cards that the platform's */\n/* care-plan and patient-ledger surfaces compose today. Composes */\n/* TransactionChip (the settled/debt/to-invoice headline) + KeyValueList */\n/* (number, date, type, direction, relations) + DescriptionList (line */\n/* items) + Badge (the payment type). */\n/* */\n/* The component owns the ORDER, ICONS, and LABELS; the consumer passes */\n/* the data. Every visible string flows through `useTranslation('ui')` */\n/* against the `paymentCard.*` namespace. The agent state slot exposes */\n/* identifiers + structural state only — never patient names. */\n/* -------------------------------------------------------------------- */\n\n/* -------------------------------------------------------------------- */\n/* Vocabulary */\n/* -------------------------------------------------------------------- */\n\n/** Payment type → translation-key segment + Badge variant. */\nexport type PaymentType = 'full' | 'partial' | 'credit' | 'proforma' | 'other';\n\nexport type PaymentDirection = 'incoming' | 'outgoing';\n\ntype BadgeVariant = NonNullable<\n ComponentPropsWithoutRef<typeof Badge>['variant']\n>;\n\nconst PAYMENT_TYPE_BADGE = {\n full: 'success',\n partial: 'warning',\n credit: 'info',\n proforma: 'neutral',\n other: 'neutral',\n} as const satisfies Record<PaymentType, BadgeVariant>;\n\nconst DEFAULT_CURRENCY = 'EUR';\n\n// Inline English fallbacks — belt-and-braces only. The canonical keys\n// live in the locale bundle (`ui.paymentCard.*`); these guard against a\n// stale / not-yet-wired bundle so the card never renders a raw key.\nconst TYPE_DEFAULTS: Record<PaymentType, string> = {\n full: 'Full payment',\n partial: 'Partial payment',\n credit: 'Credit note',\n proforma: 'Proforma',\n other: 'Other',\n};\n\nconst DIRECTION_DEFAULTS: Record<PaymentDirection, string> = {\n incoming: 'Incoming',\n outgoing: 'Outgoing',\n};\n\n/* -------------------------------------------------------------------- */\n/* CVA — root */\n/* -------------------------------------------------------------------- */\n\nconst rootVariants = cva('ds:w-full ds:text-[color:var(--foreground)]', {\n variants: {\n surface: {\n flat: '',\n elevated: '',\n },\n },\n defaultVariants: { surface: 'elevated' },\n});\n\n/* -------------------------------------------------------------------- */\n/* Public types */\n/* -------------------------------------------------------------------- */\n\nexport interface PaymentLineItem {\n /** Human-readable description of the line. */\n description: string;\n /** Amount in the smallest currency unit (cents / centesimi). */\n amountCents: number;\n /** Optional VAT percentage (e.g. `22` for 22%). */\n vatPercentage?: number;\n}\n\nexport interface PaymentCardRelations {\n /** Care-plan / treatment-plan number this payment belongs to. */\n carePlanNumber?: string;\n /** Patient display name — rendered, but never exposed to the agent. */\n patientName?: string;\n /** Operator display name — rendered, but never exposed to the agent. */\n operatorName?: string;\n}\n\nexport interface PaymentCardHandle {\n /** Stable payment number currently rendered. Identifier only — no PHI. */\n getNumber: () => string;\n /** Resolved headline financial state. Structural state only. */\n getState: () => TransactionStateValue;\n}\n\n/** The TransactionChip state this card resolves the payment to. */\ntype TransactionStateValue = 'debt' | 'to-invoice' | 'settled';\n\nexport interface PaymentCardProps extends Omit<\n ComponentPropsWithoutRef<'div'>,\n 'aria-label' | 'children'\n> {\n /** Agent-readiness consumer id, surfaced as `data-component-id`. */\n id?: string;\n /** Human-readable payment number / reference. Rendered as the heading. */\n number: string;\n /** ISO-8601 date string for the payment date. */\n dateIso?: string;\n /** Payment type — drives the type Badge + label. */\n type: PaymentType;\n /** Money flow direction — incoming (patient → practice) or outgoing. */\n direction: PaymentDirection;\n /** Gross total in the smallest currency unit (cents). */\n grossCents?: number;\n /** Amount already paid, in cents. */\n paidCents?: number;\n /** Amount still outstanding, in cents. */\n unpaidCents?: number;\n /** Marks the record as written-off — renders a neutral chip. */\n writtenOff?: boolean;\n /** Linked entities (care plan / patient / operator). */\n relations?: PaymentCardRelations;\n /** Itemised breakdown rendered as a DescriptionList. */\n lineItems?: PaymentLineItem[];\n /** BCP-47 locale override. Falls back to the active i18next language. */\n locale?: string;\n /** ISO-4217 currency code. Defaults to `EUR`. */\n currency?: string;\n\n /* ----- Styling ----- */\n\n /**\n * `'elevated'` (default) wraps in `<Card variant=\"elevated\">`. `'flat'`\n * drops the Card — use inside an existing card / sheet.\n */\n surface?: 'flat' | 'elevated';\n\n /* ----- a11y ----- */\n\n /** Override the default region aria-label. */\n 'aria-label'?: string;\n}\n\n/* -------------------------------------------------------------------- */\n/* Helpers */\n/* -------------------------------------------------------------------- */\n\n/** Format cents → currency string for the consumer's locale. */\nfunction formatMoney(cents: number, currency: string, locale: string): string {\n try {\n return new Intl.NumberFormat(locale, {\n style: 'currency',\n currency,\n }).format(cents / 100);\n } catch {\n return (cents / 100).toFixed(2);\n }\n}\n\n/** Format an ISO date for the consumer's locale, gracefully degrading. */\nfunction formatDate(iso: string, locale: string): string {\n const date = new Date(iso);\n if (Number.isNaN(date.getTime())) return iso;\n try {\n return new Intl.DateTimeFormat(locale, {\n year: 'numeric',\n month: 'short',\n day: 'numeric',\n }).format(date);\n } catch {\n return iso;\n }\n}\n\n/**\n * Resolve the headline TransactionChip state from the paid / unpaid /\n * written-off inputs. Written-off → settled chip; an outstanding balance\n * → debt; a proforma with nothing paid → to-invoice; otherwise settled.\n */\nfunction resolveState(\n type: PaymentType,\n paidCents: number | undefined,\n unpaidCents: number | undefined,\n writtenOff: boolean | undefined,\n): TransactionStateValue {\n if (writtenOff) return 'settled';\n if (unpaidCents != null && unpaidCents > 0) return 'debt';\n if (type === 'proforma' && (paidCents == null || paidCents === 0)) {\n return 'to-invoice';\n }\n return 'settled';\n}\n\n/* -------------------------------------------------------------------- */\n/* Component */\n/* -------------------------------------------------------------------- */\n\nexport const PaymentCard = forwardRef<HTMLDivElement, PaymentCardProps>(\n (\n {\n id,\n number,\n dateIso,\n type,\n direction,\n grossCents,\n paidCents,\n unpaidCents,\n writtenOff = false,\n relations,\n lineItems,\n locale,\n currency = DEFAULT_CURRENCY,\n surface = 'elevated',\n 'aria-label': ariaLabel,\n className,\n ...rest\n },\n ref,\n ) => {\n const { t, i18n } = useTranslation();\n const headingId = useId();\n const activeLocale = locale ?? i18n.language ?? 'en';\n\n const resolvedAriaLabel =\n ariaLabel ??\n t('paymentCard.regionLabel', {\n number,\n defaultValue: 'Payment {{number}}',\n });\n\n const state = resolveState(type, paidCents, unpaidCents, writtenOff);\n\n // The chip headline reflects the most informative figure: the\n // outstanding balance when there's a debt, otherwise the gross total.\n const chipAmountCents =\n state === 'debt' && unpaidCents != null\n ? unpaidCents\n : (grossCents ?? paidCents ?? unpaidCents ?? 0);\n\n useAgentRegistration(\n paymentCardAgent,\n {\n getNumber: () => number,\n getState: () => state,\n },\n id,\n );\n\n const typeLabel = t(`paymentCard.type.${type}`, {\n defaultValue: TYPE_DEFAULTS[type],\n });\n const directionIcon =\n direction === 'incoming' ? (\n <ArrowDownLeft aria-hidden=\"true\" />\n ) : (\n <ArrowUpRight aria-hidden=\"true\" />\n );\n const directionLabel = t(`paymentCard.direction.${direction}`, {\n defaultValue: DIRECTION_DEFAULTS[direction],\n });\n\n // Compose the metadata rows in display order. Omitting a field omits\n // the row — KeyValueList collapses the subgrid cleanly.\n const rows: Array<{\n key: string;\n icon: ReactNode;\n label: string;\n value: ReactNode;\n }> = [];\n\n rows.push({\n key: 'number',\n icon: <Hash aria-hidden=\"true\" />,\n label: t('paymentCard.label.number', 'Number'),\n value: number,\n });\n\n if (dateIso) {\n rows.push({\n key: 'date',\n icon: <CalendarDays aria-hidden=\"true\" />,\n label: t('paymentCard.label.date', 'Date'),\n value: formatDate(dateIso, activeLocale),\n });\n }\n\n rows.push({\n key: 'type',\n icon: <ReceiptText aria-hidden=\"true\" />,\n label: t('paymentCard.label.type', 'Type'),\n value: <Badge variant={PAYMENT_TYPE_BADGE[type]}>{typeLabel}</Badge>,\n });\n\n rows.push({\n key: 'direction',\n icon: directionIcon,\n label: t('paymentCard.label.direction', 'Direction'),\n value: directionLabel,\n });\n\n if (relations?.carePlanNumber) {\n rows.push({\n key: 'carePlan',\n icon: <FileText aria-hidden=\"true\" />,\n label: t('paymentCard.label.carePlan', 'Care plan'),\n value: relations.carePlanNumber,\n });\n }\n\n if (relations?.patientName) {\n rows.push({\n key: 'patient',\n icon: <User aria-hidden=\"true\" />,\n label: t('paymentCard.label.patient', 'Patient'),\n value: relations.patientName,\n });\n }\n\n if (relations?.operatorName) {\n rows.push({\n key: 'operator',\n icon: <UserCog aria-hidden=\"true\" />,\n label: t('paymentCard.label.operator', 'Operator'),\n value: relations.operatorName,\n });\n }\n\n const formattedGross = useMemo(\n () =>\n grossCents != null\n ? formatMoney(grossCents, currency, activeLocale)\n : undefined,\n [grossCents, currency, activeLocale],\n );\n const formattedPaid = useMemo(\n () =>\n paidCents != null\n ? formatMoney(paidCents, currency, activeLocale)\n : undefined,\n [paidCents, currency, activeLocale],\n );\n const formattedUnpaid = useMemo(\n () =>\n unpaidCents != null\n ? formatMoney(unpaidCents, currency, activeLocale)\n : undefined,\n [unpaidCents, currency, activeLocale],\n );\n\n const hasAmounts =\n formattedGross != null ||\n formattedPaid != null ||\n formattedUnpaid != null;\n\n const hasLineItems = !!lineItems && lineItems.length > 0;\n\n const inner = (\n <div className=\"ds:flex ds:flex-col ds:gap-[var(--spacing-md)]\">\n {/* Heading row — payment number + headline TransactionChip. */}\n <div className=\"ds:flex ds:items-start ds:gap-[var(--spacing-md)] ds:flex-wrap\">\n <h3\n id={headingId}\n className=\"type-title-card ds:m-0 ds:text-[color:var(--foreground)]\"\n >\n {t('paymentCard.heading', {\n number,\n defaultValue: 'Payment {{number}}',\n })}\n </h3>\n <span className=\"ds:ms-auto ds:shrink-0\">\n <TransactionChip\n state={state}\n amount={chipAmountCents / 100}\n currency={currency}\n locale={activeLocale}\n size=\"lg\"\n />\n </span>\n </div>\n\n {/* Metadata rows. */}\n <KeyValueList rowGap=\"sm\">\n {rows.map((row) => (\n <KeyValuePair\n key={row.key}\n icon={row.icon as React.ReactElement}\n label={row.label}\n value={row.value}\n />\n ))}\n </KeyValueList>\n\n {/* Amount summary — gross / paid / outstanding. */}\n {hasAmounts ? (\n <DescriptionList layout=\"inline\" density=\"compact\" labelWidth=\"fixed\">\n {formattedGross != null ? (\n <DescriptionList.Row>\n <DescriptionList.Term>\n {t('paymentCard.label.gross', 'Gross total')}\n </DescriptionList.Term>\n <DescriptionList.Detail numeric>\n {formattedGross}\n </DescriptionList.Detail>\n </DescriptionList.Row>\n ) : null}\n {formattedPaid != null ? (\n <DescriptionList.Row>\n <DescriptionList.Term>\n {t('paymentCard.label.paid', 'Paid')}\n </DescriptionList.Term>\n <DescriptionList.Detail numeric>\n {formattedPaid}\n </DescriptionList.Detail>\n </DescriptionList.Row>\n ) : null}\n {formattedUnpaid != null ? (\n <DescriptionList.Row>\n <DescriptionList.Term>\n {t('paymentCard.label.unpaid', 'Outstanding')}\n </DescriptionList.Term>\n <DescriptionList.Detail numeric>\n {formattedUnpaid}\n </DescriptionList.Detail>\n </DescriptionList.Row>\n ) : null}\n </DescriptionList>\n ) : null}\n\n {/* Line items. */}\n {hasLineItems ? (\n <section\n aria-label={t('paymentCard.lineItems.heading', 'Line items')}\n className=\"ds:flex ds:flex-col ds:gap-[var(--spacing-xs)]\"\n >\n <h4 className=\"type-eyebrow ds:m-0 ds:text-[color:var(--muted-foreground)]\">\n {t('paymentCard.lineItems.heading', 'Line items')}\n </h4>\n <DescriptionList\n layout=\"inline\"\n density=\"compact\"\n labelWidth=\"auto\"\n >\n {lineItems!.map((item, index) => (\n <DescriptionList.Row key={`${item.description}-${index}`}>\n <DescriptionList.Term>\n {item.vatPercentage != null\n ? t('paymentCard.lineItems.withVat', {\n description: item.description,\n vat: item.vatPercentage,\n defaultValue: '{{description}} (VAT {{vat}}%)',\n })\n : item.description}\n </DescriptionList.Term>\n <DescriptionList.Detail numeric>\n {formatMoney(item.amountCents, currency, activeLocale)}\n </DescriptionList.Detail>\n </DescriptionList.Row>\n ))}\n </DescriptionList>\n </section>\n ) : null}\n </div>\n );\n\n return (\n <div\n ref={ref}\n role=\"region\"\n aria-label={resolvedAriaLabel}\n aria-labelledby={headingId}\n data-component=\"payment-card\"\n data-component-id={id}\n data-state={state}\n data-type={type}\n data-direction={direction}\n id={id}\n className={rootVariants({ surface, className })}\n {...rest}\n >\n {surface === 'elevated' ? (\n <Card variant=\"elevated\">\n <Card.Body>{inner}</Card.Body>\n </Card>\n ) : (\n <div className={entitySurfaceVariants({ surface: 'flat' })}>\n {inner}\n </div>\n )}\n </div>\n );\n },\n);\n\nPaymentCard.displayName = 'PaymentCard';\n\nexport type PaymentCardSurface = NonNullable<\n VariantProps<typeof rootVariants>['surface']\n>;\n","/* -------------------------------------------------------------------- */\n/* Agent adapter — PaymentRequestCard. */\n/* */\n/* Read-only payment-request surface. Exposes the lifecycle status */\n/* (structural state) only — never any patient identity or the hosted */\n/* payment URL. No actions: navigation to the pay link is a user-driven */\n/* affordance, not an agent operation. */\n/* -------------------------------------------------------------------- */\n\nimport type { AgentAdapter } from '../../agent/types';\nimport type { PaymentRequestCardHandle } from './payment-request-card';\n\nexport const paymentRequestCardAgent: AgentAdapter<PaymentRequestCardHandle> = {\n id: 'payment-request-card',\n capabilities: [],\n state: {\n status: {\n type: \"'new' | 'authorization_requested' | 'authorized' | 'paid' | 'failed' | 'cancelled'\",\n descriptionKey: 'ui.agent.paymentRequestCard.state.status',\n description:\n 'Current lifecycle status of the payment request. Structural state only.',\n read: (handle) => handle.getStatus(),\n },\n },\n actions: {},\n domHooks: {\n root: {\n attr: 'data-component',\n value: 'payment-request-card',\n description: 'Marks the PaymentRequestCard root region.',\n },\n instanceId: {\n attr: 'data-component-id',\n sourceProp: 'id',\n description:\n 'Sourced from the id prop. Addresses a specific request card.',\n },\n },\n};\n","import {\n forwardRef,\n useId,\n type ComponentPropsWithoutRef,\n type ReactNode,\n} from 'react';\nimport { cva, type VariantProps } from 'class-variance-authority';\nimport { useTranslation } from 'react-i18next';\nimport { CalendarClock, CreditCard, FileText } from 'lucide-react';\nimport { Badge } from '../badge/badge';\nimport { Card } from '../card/card';\nimport { KeyValueList, KeyValuePair } from '../key-value-pair/key-value-pair';\nimport { Link } from '../link/link';\nimport { TransactionChip } from '../transaction-chip/transaction-chip';\nimport { entitySurfaceVariants, isSafeEntityUrl } from '../_shared/entity-card';\nimport { useAgentRegistration } from '../../agent/registry';\nimport { paymentRequestCardAgent } from './payment-request-card.agent';\n\n/* -------------------------------------------------------------------- */\n/* PaymentRequestCard */\n/* */\n/* Companion to PaymentCard: a card for an *outstanding* payment request */\n/* (a Stripe / online-payment ask) rather than a recorded payment. Shows */\n/* the amount as a TransactionChip, the lifecycle status as a Badge, and */\n/* — when a safe `paymentUrl` is supplied — a \"Pay now\" Link. */\n/* */\n/* Every visible string flows through `useTranslation('ui')` against the */\n/* `paymentRequestCard.*` namespace. The agent state exposes the request */\n/* status (structural state) and never any patient identity. */\n/* -------------------------------------------------------------------- */\n\n/* -------------------------------------------------------------------- */\n/* Vocabulary */\n/* -------------------------------------------------------------------- */\n\nexport type PaymentRequestStatus =\n | 'new'\n | 'authorization_requested'\n | 'authorized'\n | 'paid'\n | 'failed'\n | 'cancelled';\n\ntype BadgeVariant = NonNullable<\n ComponentPropsWithoutRef<typeof Badge>['variant']\n>;\n\nconst STATUS_BADGE = {\n new: 'info',\n authorization_requested: 'warning',\n authorized: 'info',\n paid: 'success',\n failed: 'error',\n cancelled: 'neutral',\n} as const satisfies Record<PaymentRequestStatus, BadgeVariant>;\n\nconst DEFAULT_CURRENCY = 'EUR';\n\n// Inline English fallbacks — belt-and-braces only. The canonical keys\n// live in the locale bundle (`ui.paymentRequestCard.*`); these guard\n// against a stale / not-yet-wired bundle so the card never shows a key.\nconst STATUS_DEFAULTS: Record<PaymentRequestStatus, string> = {\n new: 'New',\n authorization_requested: 'Authorization requested',\n authorized: 'Authorized',\n paid: 'Paid',\n failed: 'Failed',\n cancelled: 'Cancelled',\n};\n\n/* -------------------------------------------------------------------- */\n/* CVA — root */\n/* -------------------------------------------------------------------- */\n\nconst rootVariants = cva('ds:w-full ds:text-[color:var(--foreground)]', {\n variants: {\n surface: {\n flat: '',\n elevated: '',\n },\n },\n defaultVariants: { surface: 'elevated' },\n});\n\n/* -------------------------------------------------------------------- */\n/* Public types */\n/* -------------------------------------------------------------------- */\n\nexport interface PaymentRequestCardHandle {\n /** Current lifecycle status. Structural state only — no PHI. */\n getStatus: () => PaymentRequestStatus;\n}\n\nexport interface PaymentRequestCardProps extends Omit<\n ComponentPropsWithoutRef<'div'>,\n 'aria-label' | 'children' | 'title'\n> {\n /** Agent-readiness consumer id, surfaced as `data-component-id`. */\n id?: string;\n /** Heading for the request. Falls back to a localised default. */\n title?: string;\n /** Optional supporting copy rendered beneath the heading. */\n description?: string;\n /** Requested amount in the smallest currency unit (cents). */\n amountCents: number;\n /** ISO-8601 due date. */\n dueDateIso?: string;\n /** Lifecycle status — drives the status Badge and pay-link gating. */\n status: PaymentRequestStatus;\n /** Hosted payment URL. Only rendered when it passes the URL allow-list. */\n paymentUrl?: string;\n /** Care-plan / treatment-plan number this request relates to. */\n carePlanNumber?: string;\n /** BCP-47 locale override. Falls back to the active i18next language. */\n locale?: string;\n /** ISO-4217 currency code. Defaults to `EUR`. */\n currency?: string;\n\n /* ----- Styling ----- */\n\n /**\n * `'elevated'` (default) wraps in `<Card variant=\"elevated\">`. `'flat'`\n * drops the Card — use inside an existing card / sheet.\n */\n surface?: 'flat' | 'elevated';\n\n /* ----- a11y ----- */\n\n /** Override the default region aria-label. */\n 'aria-label'?: string;\n}\n\n/* -------------------------------------------------------------------- */\n/* Helpers */\n/* -------------------------------------------------------------------- */\n\nfunction formatDate(iso: string, locale: string): string {\n const date = new Date(iso);\n if (Number.isNaN(date.getTime())) return iso;\n try {\n return new Intl.DateTimeFormat(locale, {\n year: 'numeric',\n month: 'short',\n day: 'numeric',\n }).format(date);\n } catch {\n return iso;\n }\n}\n\n/* -------------------------------------------------------------------- */\n/* Component */\n/* -------------------------------------------------------------------- */\n\nexport const PaymentRequestCard = forwardRef<\n HTMLDivElement,\n PaymentRequestCardProps\n>(\n (\n {\n id,\n title,\n description,\n amountCents,\n dueDateIso,\n status,\n paymentUrl,\n carePlanNumber,\n locale,\n currency = DEFAULT_CURRENCY,\n surface = 'elevated',\n 'aria-label': ariaLabel,\n className,\n ...rest\n },\n ref,\n ) => {\n const { t, i18n } = useTranslation();\n const headingId = useId();\n const activeLocale = locale ?? i18n.language ?? 'en';\n\n const resolvedTitle =\n title ?? t('paymentRequestCard.heading', 'Payment request');\n const resolvedAriaLabel = ariaLabel ?? resolvedTitle;\n\n useAgentRegistration(\n paymentRequestCardAgent,\n { getStatus: () => status },\n id,\n );\n\n const statusLabel = t(`paymentRequestCard.status.${status}`, {\n defaultValue: STATUS_DEFAULTS[status],\n });\n\n // A paid request settles; an open one is \"to-invoice\" (awaiting money);\n // anything terminal-but-unpaid renders as a debt.\n const chipState: 'to-invoice' | 'settled' | 'debt' =\n status === 'paid'\n ? 'settled'\n : status === 'failed' || status === 'cancelled'\n ? 'debt'\n : 'to-invoice';\n\n // The pay link only renders when the request is still actionable AND\n // the URL passes the shared card-family allow-list (no javascript:,\n // data:, protocol-relative). Otherwise the affordance is suppressed.\n const isActionable =\n status === 'new' ||\n status === 'authorization_requested' ||\n status === 'authorized';\n const showPayLink =\n isActionable && !!paymentUrl && isSafeEntityUrl(paymentUrl);\n\n const rows: Array<{\n key: string;\n icon: ReactNode;\n label: string;\n value: ReactNode;\n }> = [];\n\n rows.push({\n key: 'status',\n icon: <CreditCard aria-hidden=\"true\" />,\n label: t('paymentRequestCard.label.status', 'Status'),\n value: <Badge variant={STATUS_BADGE[status]}>{statusLabel}</Badge>,\n });\n\n if (dueDateIso) {\n rows.push({\n key: 'dueDate',\n icon: <CalendarClock aria-hidden=\"true\" />,\n label: t('paymentRequestCard.label.dueDate', 'Due date'),\n value: formatDate(dueDateIso, activeLocale),\n });\n }\n\n if (carePlanNumber) {\n rows.push({\n key: 'carePlan',\n icon: <FileText aria-hidden=\"true\" />,\n label: t('paymentRequestCard.label.carePlan', 'Care plan'),\n value: carePlanNumber,\n });\n }\n\n const inner = (\n <div className=\"ds:flex ds:flex-col ds:gap-[var(--spacing-md)]\">\n {/* Heading row — title + amount TransactionChip. */}\n <div className=\"ds:flex ds:items-start ds:gap-[var(--spacing-md)] ds:flex-wrap\">\n <div className=\"ds:flex ds:min-w-0 ds:flex-col ds:gap-[var(--spacing-2xs)]\">\n <h3\n id={headingId}\n className=\"type-title-card ds:m-0 ds:text-[color:var(--foreground)]\"\n >\n {resolvedTitle}\n </h3>\n {description ? (\n <p className=\"type-body-sm ds:m-0 ds:text-[color:var(--muted-foreground)]\">\n {description}\n </p>\n ) : null}\n </div>\n <span className=\"ds:ms-auto ds:shrink-0\">\n <TransactionChip\n state={chipState}\n amount={amountCents / 100}\n currency={currency}\n locale={activeLocale}\n size=\"lg\"\n />\n </span>\n </div>\n\n {/* Metadata rows. */}\n <KeyValueList rowGap=\"sm\">\n {rows.map((row) => (\n <KeyValuePair\n key={row.key}\n icon={row.icon as React.ReactElement}\n label={row.label}\n value={row.value}\n />\n ))}\n </KeyValueList>\n\n {/* Pay affordance — only when actionable + the URL is safe. */}\n {showPayLink ? (\n <div className=\"ds:flex\">\n <Link href={paymentUrl!} external startIcon={<CreditCard />}>\n {t('paymentRequestCard.pay', 'Pay now')}\n </Link>\n </div>\n ) : null}\n </div>\n );\n\n return (\n <div\n ref={ref}\n role=\"region\"\n aria-label={resolvedAriaLabel}\n aria-labelledby={headingId}\n data-component=\"payment-request-card\"\n data-component-id={id}\n data-status={status}\n id={id}\n className={rootVariants({ surface, className })}\n {...rest}\n >\n {surface === 'elevated' ? (\n <Card variant=\"elevated\">\n <Card.Body>{inner}</Card.Body>\n </Card>\n ) : (\n <div className={entitySurfaceVariants({ surface: 'flat' })}>\n {inner}\n </div>\n )}\n </div>\n );\n },\n);\n\nPaymentRequestCard.displayName = 'PaymentRequestCard';\n\nexport type PaymentRequestCardSurface = NonNullable<\n VariantProps<typeof rootVariants>['surface']\n>;\n"],"names":["__iconNode","CreditCard","createLucideIcon","Hash","ReceiptText","paymentCardAgent","handle","PAYMENT_TYPE_BADGE","DEFAULT_CURRENCY","TYPE_DEFAULTS","DIRECTION_DEFAULTS","rootVariants","cva","formatMoney","cents","currency","locale","formatDate","iso","date","resolveState","type","paidCents","unpaidCents","writtenOff","PaymentCard","forwardRef","id","number","dateIso","direction","grossCents","relations","lineItems","surface","ariaLabel","className","rest","ref","i18n","useTranslation","headingId","useId","activeLocale","resolvedAriaLabel","state","chipAmountCents","useAgentRegistration","typeLabel","directionIcon","jsx","ArrowDownLeft","ArrowUpRight","directionLabel","rows","CalendarDays","Badge","FileText","User","UserCog","formattedGross","useMemo","formattedPaid","formattedUnpaid","hasAmounts","hasLineItems","inner","jsxs","TransactionChip","KeyValueList","row","KeyValuePair","DescriptionList","item","index","Card","entitySurfaceVariants","paymentRequestCardAgent","STATUS_BADGE","STATUS_DEFAULTS","PaymentRequestCard","title","description","amountCents","dueDateIso","status","paymentUrl","carePlanNumber","t","resolvedTitle","statusLabel","chipState","showPayLink","isSafeEntityUrl","CalendarClock","Link"],"mappings":"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","x_google_ignoreList":[0,1,2]}
|