comfyui-frontend-package 1.37.10__py3-none-any.whl → 1.38.0__py3-none-any.whl
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.
- comfyui_frontend_package/static/assets/{AboutPanel-C5DQxPC9.js → AboutPanel-DeWaRZUc.js} +2 -2
- comfyui_frontend_package/static/assets/{AboutPanel-C5DQxPC9.js.map → AboutPanel-DeWaRZUc.js.map} +1 -1
- comfyui_frontend_package/static/assets/{AudioPreviewPlayer-BNO9ZjOM.js → AudioPreviewPlayer-CSxbl0y3.js} +2 -2
- comfyui_frontend_package/static/assets/{AudioPreviewPlayer-BNO9ZjOM.js.map → AudioPreviewPlayer-CSxbl0y3.js.map} +1 -1
- comfyui_frontend_package/static/assets/{ComfyQueueButton-D0Y-jFOd.js → ComfyQueueButton-BV0p-R1-.js} +2 -2
- comfyui_frontend_package/static/assets/{ComfyQueueButton-D0Y-jFOd.js.map → ComfyQueueButton-BV0p-R1-.js.map} +1 -1
- comfyui_frontend_package/static/assets/{ExtensionPanel-CbCxE4jg.js → ExtensionPanel-DvPzK040.js} +2 -2
- comfyui_frontend_package/static/assets/{ExtensionPanel-CbCxE4jg.js.map → ExtensionPanel-DvPzK040.js.map} +1 -1
- comfyui_frontend_package/static/assets/GraphView-2T90vQj0.css +1 -0
- comfyui_frontend_package/static/assets/GraphView-BuGkgiGk.js +15 -0
- comfyui_frontend_package/static/assets/GraphView-BuGkgiGk.js.map +1 -0
- comfyui_frontend_package/static/assets/{KeybindingPanel-Ceb51ttS.js → KeybindingPanel-DbjoObzw.js} +2 -2
- comfyui_frontend_package/static/assets/{KeybindingPanel-Ceb51ttS.js.map → KeybindingPanel-DbjoObzw.js.map} +1 -1
- comfyui_frontend_package/static/assets/LazyImage.vue_vue_type_script_setup_true_lang-Op4fug5d.js +2 -0
- comfyui_frontend_package/static/assets/LazyImage.vue_vue_type_script_setup_true_lang-Op4fug5d.js.map +1 -0
- comfyui_frontend_package/static/assets/{LegacyCreditsPanel-K_GDtrt_.js → LegacyCreditsPanel-BFKSdy5y.js} +2 -2
- comfyui_frontend_package/static/assets/{LegacyCreditsPanel-K_GDtrt_.js.map → LegacyCreditsPanel-BFKSdy5y.js.map} +1 -1
- comfyui_frontend_package/static/assets/{Load3D-CbCbkSys.js → Load3D-B3uXG_Os.js} +2 -2
- comfyui_frontend_package/static/assets/Load3D-B3uXG_Os.js.map +1 -0
- comfyui_frontend_package/static/assets/{Load3D.vue_vue_type_script_setup_true_lang-3QcwinlP.js → Load3D.vue_vue_type_script_setup_true_lang-CslfLloq.js} +2 -2
- comfyui_frontend_package/static/assets/{Load3D.vue_vue_type_script_setup_true_lang-3QcwinlP.js.map → Load3D.vue_vue_type_script_setup_true_lang-CslfLloq.js.map} +1 -1
- comfyui_frontend_package/static/assets/{Media3DTop--kp0iekJ.js → Media3DTop-CfCHfZKG.js} +2 -2
- comfyui_frontend_package/static/assets/{Media3DTop--kp0iekJ.js.map → Media3DTop-CfCHfZKG.js.map} +1 -1
- comfyui_frontend_package/static/assets/{ServerConfigPanel-BGnrWtif.js → ServerConfigPanel-DvFzfUMn.js} +2 -2
- comfyui_frontend_package/static/assets/{ServerConfigPanel-BGnrWtif.js.map → ServerConfigPanel-DvFzfUMn.js.map} +1 -1
- comfyui_frontend_package/static/assets/SubscriptionRequiredDialogContent-C1UryadQ.css +1 -0
- comfyui_frontend_package/static/assets/SubscriptionRequiredDialogContent-DTq1ffwv.js +2 -0
- comfyui_frontend_package/static/assets/{SubscriptionRequiredDialogContent-BMLw-0ti.js.map → SubscriptionRequiredDialogContent-DTq1ffwv.js.map} +1 -1
- comfyui_frontend_package/static/assets/{UserAvatar.vue_vue_type_script_setup_true_lang-48WRCWXz.js → UserAvatar.vue_vue_type_script_setup_true_lang-COE-v4cY.js} +2 -2
- comfyui_frontend_package/static/assets/{UserAvatar.vue_vue_type_script_setup_true_lang-48WRCWXz.js.map → UserAvatar.vue_vue_type_script_setup_true_lang-COE-v4cY.js.map} +1 -1
- comfyui_frontend_package/static/assets/{UserPanel-BfOBqtyE.js → UserPanel-Xvm9QBld.js} +2 -2
- comfyui_frontend_package/static/assets/{UserPanel-BfOBqtyE.js.map → UserPanel-Xvm9QBld.js.map} +1 -1
- comfyui_frontend_package/static/assets/{UserSelectView-hAFmUbm0.js → UserSelectView-Bh8_ghwS.js} +2 -2
- comfyui_frontend_package/static/assets/{UserSelectView-hAFmUbm0.js.map → UserSelectView-Bh8_ghwS.js.map} +1 -1
- comfyui_frontend_package/static/assets/{ValueControlPopover-BEbJxP9Z.js → ValueControlPopover-BrAoQ_2-.js} +2 -2
- comfyui_frontend_package/static/assets/{ValueControlPopover-BEbJxP9Z.js.map → ValueControlPopover-BrAoQ_2-.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetAudioUI-BuXP7XBQ.js → WidgetAudioUI-BjV6M32Q.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetAudioUI-BuXP7XBQ.js.map → WidgetAudioUI-BjV6M32Q.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetButton-vKBzo4q0.js → WidgetButton-Dk30Nukl.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetButton-vKBzo4q0.js.map → WidgetButton-Dk30Nukl.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetChart-Dz4GcJwO.js → WidgetChart-BntGUEQZ.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetChart-Dz4GcJwO.js.map → WidgetChart-BntGUEQZ.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetColorPicker-FoC3o0Lp.js → WidgetColorPicker-CkqNsGhI.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetColorPicker-FoC3o0Lp.js.map → WidgetColorPicker-CkqNsGhI.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetGalleria-CV4Nv2wv.js → WidgetGalleria-BYYCCQyX.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetGalleria-CV4Nv2wv.js.map → WidgetGalleria-BYYCCQyX.js.map} +1 -1
- comfyui_frontend_package/static/assets/WidgetInputNumber-psomfHIy.js +2 -0
- comfyui_frontend_package/static/assets/WidgetInputNumber-psomfHIy.js.map +1 -0
- comfyui_frontend_package/static/assets/{WidgetInputNumber.vue_vue_type_script_setup_true_lang-D-IwEPPr.js → WidgetInputNumber.vue_vue_type_script_setup_true_lang-qjF5C0EN.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetInputNumber.vue_vue_type_script_setup_true_lang-D-IwEPPr.js.map → WidgetInputNumber.vue_vue_type_script_setup_true_lang-qjF5C0EN.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetInputText-Cv8Z1_b9.js → WidgetInputText-Btor0Uhs.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetInputText-Cv8Z1_b9.js.map → WidgetInputText-Btor0Uhs.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetLayoutField.vue_vue_type_script_setup_true_lang-DFWVBJH-.js → WidgetLayoutField.vue_vue_type_script_setup_true_lang-Bq1noASf.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetLayoutField.vue_vue_type_script_setup_true_lang-DFWVBJH-.js.map → WidgetLayoutField.vue_vue_type_script_setup_true_lang-Bq1noASf.js.map} +1 -1
- comfyui_frontend_package/static/assets/WidgetLegacy-Cj4T7tN3.js +2 -0
- comfyui_frontend_package/static/assets/WidgetLegacy-Cj4T7tN3.js.map +1 -0
- comfyui_frontend_package/static/assets/{WidgetMarkdown-C4CnxNoM.js → WidgetMarkdown-CsRRMdeD.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetMarkdown-C4CnxNoM.js.map → WidgetMarkdown-CsRRMdeD.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetRecordAudio-BQ9yATXo.js → WidgetRecordAudio-CbCqPJqI.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetRecordAudio-BQ9yATXo.js.map → WidgetRecordAudio-CbCqPJqI.js.map} +1 -1
- comfyui_frontend_package/static/assets/WidgetSelect-DcVQrOUl.js +2 -0
- comfyui_frontend_package/static/assets/WidgetSelect-DcVQrOUl.js.map +1 -0
- comfyui_frontend_package/static/assets/{WidgetSelect.vue_vue_type_script_setup_true_lang-EU2Y4eXi.js → WidgetSelect.vue_vue_type_script_setup_true_lang-B0Z0OQv6.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetSelect.vue_vue_type_script_setup_true_lang-EU2Y4eXi.js.map → WidgetSelect.vue_vue_type_script_setup_true_lang-B0Z0OQv6.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetTextarea-C3Wo0ULT.js → WidgetTextarea-OMPagx9K.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetTextarea-C3Wo0ULT.js.map → WidgetTextarea-OMPagx9K.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetToggleSwitch-BZUubsU5.js → WidgetToggleSwitch-mOArdF4c.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetToggleSwitch-BZUubsU5.js.map → WidgetToggleSwitch-mOArdF4c.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetWithControl.vue_vue_type_script_setup_true_lang-B7cz0rwK.js → WidgetWithControl.vue_vue_type_script_setup_true_lang-Bx6suA2O.js} +3 -3
- comfyui_frontend_package/static/assets/{WidgetWithControl.vue_vue_type_script_setup_true_lang-B7cz0rwK.js.map → WidgetWithControl.vue_vue_type_script_setup_true_lang-Bx6suA2O.js.map} +1 -1
- comfyui_frontend_package/static/assets/{audioService-CNb54hvw.js → audioService-jRjL5LtP.js} +2 -2
- comfyui_frontend_package/static/assets/{audioService-CNb54hvw.js.map → audioService-jRjL5LtP.js.map} +1 -1
- comfyui_frontend_package/static/assets/{audioUtils-ClyG3xvN.js → audioUtils-DsaLmBXU.js} +2 -2
- comfyui_frontend_package/static/assets/{audioUtils-ClyG3xvN.js.map → audioUtils-DsaLmBXU.js.map} +1 -1
- comfyui_frontend_package/static/assets/{commands-DHxq3nWN.js → commands-6krn3srk.js} +2 -2
- comfyui_frontend_package/static/assets/commands-6krn3srk.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-B8TX-OdW.js +2 -0
- comfyui_frontend_package/static/assets/commands-B8TX-OdW.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-BBMcY34D.js +2 -0
- comfyui_frontend_package/static/assets/commands-BBMcY34D.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-C0R_Md8R.js +2 -0
- comfyui_frontend_package/static/assets/commands-C0R_Md8R.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-CAv4QkZ-.js +2 -0
- comfyui_frontend_package/static/assets/commands-CAv4QkZ-.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-CeIcZl_a.js +2 -0
- comfyui_frontend_package/static/assets/commands-CeIcZl_a.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-CtwQRBL_.js +2 -0
- comfyui_frontend_package/static/assets/commands-CtwQRBL_.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-DjX42wW9.js +2 -0
- comfyui_frontend_package/static/assets/commands-DjX42wW9.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-DzwpXu9N.js +2 -0
- comfyui_frontend_package/static/assets/commands-DzwpXu9N.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-E4h99f7h.js +2 -0
- comfyui_frontend_package/static/assets/commands-E4h99f7h.js.map +1 -0
- comfyui_frontend_package/static/assets/commands-we3Embjk.js +2 -0
- comfyui_frontend_package/static/assets/commands-we3Embjk.js.map +1 -0
- comfyui_frontend_package/static/assets/{index-B3VEOed6.js → index--yK73oka.js} +23 -23
- comfyui_frontend_package/static/assets/index--yK73oka.js.map +1 -0
- comfyui_frontend_package/static/assets/index-CofcAZPL.css +1 -0
- comfyui_frontend_package/static/assets/{index-B5S_Le6r.js → index-CwTFEsg4.js} +2 -2
- comfyui_frontend_package/static/assets/{index-B5S_Le6r.js.map → index-CwTFEsg4.js.map} +1 -1
- comfyui_frontend_package/static/assets/{index-CtDW77xi.js → index-Hz5b30sA.js} +2 -2
- comfyui_frontend_package/static/assets/{index-CtDW77xi.js.map → index-Hz5b30sA.js.map} +1 -1
- comfyui_frontend_package/static/assets/{keybindingService-50G4NbCc.js → keybindingService-XE4XFAxf.js} +2 -2
- comfyui_frontend_package/static/assets/{keybindingService-50G4NbCc.js.map → keybindingService-XE4XFAxf.js.map} +1 -1
- comfyui_frontend_package/static/assets/main-B1lLjnTc.js +17 -0
- comfyui_frontend_package/static/assets/main-B1lLjnTc.js.map +1 -0
- comfyui_frontend_package/static/assets/main-B6hk_BFB.js +17 -0
- comfyui_frontend_package/static/assets/main-B6hk_BFB.js.map +1 -0
- comfyui_frontend_package/static/assets/main-BJ1OB7_l.js +14 -0
- comfyui_frontend_package/static/assets/main-BJ1OB7_l.js.map +1 -0
- comfyui_frontend_package/static/assets/main-Beff11ll.js +17 -0
- comfyui_frontend_package/static/assets/main-Beff11ll.js.map +1 -0
- comfyui_frontend_package/static/assets/main-Bmv0nfqm.js +14 -0
- comfyui_frontend_package/static/assets/main-Bmv0nfqm.js.map +1 -0
- comfyui_frontend_package/static/assets/main-Bmv_vwNy.js +14 -0
- comfyui_frontend_package/static/assets/main-Bmv_vwNy.js.map +1 -0
- comfyui_frontend_package/static/assets/main-CC-DWYqg.js +17 -0
- comfyui_frontend_package/static/assets/main-CC-DWYqg.js.map +1 -0
- comfyui_frontend_package/static/assets/main-CPEN9kTz.js +17 -0
- comfyui_frontend_package/static/assets/main-CPEN9kTz.js.map +1 -0
- comfyui_frontend_package/static/assets/main-Ca_1lXEg.js +17 -0
- comfyui_frontend_package/static/assets/main-Ca_1lXEg.js.map +1 -0
- comfyui_frontend_package/static/assets/main-CiNLJloN.js +17 -0
- comfyui_frontend_package/static/assets/main-CiNLJloN.js.map +1 -0
- comfyui_frontend_package/static/assets/main-Dy-2iV5r.js +14 -0
- comfyui_frontend_package/static/assets/main-Dy-2iV5r.js.map +1 -0
- comfyui_frontend_package/static/assets/{vendor-primevue-Bp7MMXLP.js → vendor-primevue-DeKsC2uk.js} +2 -2
- comfyui_frontend_package/static/assets/{vendor-primevue-Bp7MMXLP.js.map → vendor-primevue-DeKsC2uk.js.map} +1 -1
- comfyui_frontend_package/static/index.html +1 -1
- {comfyui_frontend_package-1.37.10.dist-info → comfyui_frontend_package-1.38.0.dist-info}/METADATA +1 -1
- {comfyui_frontend_package-1.37.10.dist-info → comfyui_frontend_package-1.38.0.dist-info}/RECORD +134 -134
- comfyui_frontend_package/static/assets/GraphView-CepV6iZo.css +0 -1
- comfyui_frontend_package/static/assets/GraphView-_ZGu5uNf.js +0 -15
- comfyui_frontend_package/static/assets/GraphView-_ZGu5uNf.js.map +0 -1
- comfyui_frontend_package/static/assets/LazyImage.vue_vue_type_script_setup_true_lang-BHcWsrBj.js +0 -2
- comfyui_frontend_package/static/assets/LazyImage.vue_vue_type_script_setup_true_lang-BHcWsrBj.js.map +0 -1
- comfyui_frontend_package/static/assets/Load3D-CbCbkSys.js.map +0 -1
- comfyui_frontend_package/static/assets/SubscriptionRequiredDialogContent-BJ80blC4.css +0 -1
- comfyui_frontend_package/static/assets/SubscriptionRequiredDialogContent-BMLw-0ti.js +0 -2
- comfyui_frontend_package/static/assets/WidgetInputNumber-zsVb0Vit.js +0 -2
- comfyui_frontend_package/static/assets/WidgetInputNumber-zsVb0Vit.js.map +0 -1
- comfyui_frontend_package/static/assets/WidgetLegacy-Dh4xE798.js +0 -2
- comfyui_frontend_package/static/assets/WidgetLegacy-Dh4xE798.js.map +0 -1
- comfyui_frontend_package/static/assets/WidgetSelect-B9DwAKiE.js +0 -2
- comfyui_frontend_package/static/assets/WidgetSelect-B9DwAKiE.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-2re7xZu6.js +0 -2
- comfyui_frontend_package/static/assets/commands-2re7xZu6.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-5dfPmqrI.js +0 -2
- comfyui_frontend_package/static/assets/commands-5dfPmqrI.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-9-tUiihM.js +0 -2
- comfyui_frontend_package/static/assets/commands-9-tUiihM.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-BOYC3thj.js +0 -2
- comfyui_frontend_package/static/assets/commands-BOYC3thj.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-CSrZnGH2.js +0 -2
- comfyui_frontend_package/static/assets/commands-CSrZnGH2.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-DGL_KBDe.js +0 -2
- comfyui_frontend_package/static/assets/commands-DGL_KBDe.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-DHxq3nWN.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-DOgmN2m6.js +0 -2
- comfyui_frontend_package/static/assets/commands-DOgmN2m6.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-DoQ2gxMh.js +0 -2
- comfyui_frontend_package/static/assets/commands-DoQ2gxMh.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-irqWUFB-.js +0 -2
- comfyui_frontend_package/static/assets/commands-irqWUFB-.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-xGVSTfS4.js +0 -2
- comfyui_frontend_package/static/assets/commands-xGVSTfS4.js.map +0 -1
- comfyui_frontend_package/static/assets/index-B3VEOed6.js.map +0 -1
- comfyui_frontend_package/static/assets/index-CPtP45Cb.css +0 -1
- comfyui_frontend_package/static/assets/main-B3vd7GL1.js +0 -17
- comfyui_frontend_package/static/assets/main-B3vd7GL1.js.map +0 -1
- comfyui_frontend_package/static/assets/main-BKCc2TkD.js +0 -17
- comfyui_frontend_package/static/assets/main-BKCc2TkD.js.map +0 -1
- comfyui_frontend_package/static/assets/main-BNvzUx74.js +0 -17
- comfyui_frontend_package/static/assets/main-BNvzUx74.js.map +0 -1
- comfyui_frontend_package/static/assets/main-BPu7av80.js +0 -17
- comfyui_frontend_package/static/assets/main-BPu7av80.js.map +0 -1
- comfyui_frontend_package/static/assets/main-BQ4z0Xxc.js +0 -14
- comfyui_frontend_package/static/assets/main-BQ4z0Xxc.js.map +0 -1
- comfyui_frontend_package/static/assets/main-BoyaoV4J.js +0 -14
- comfyui_frontend_package/static/assets/main-BoyaoV4J.js.map +0 -1
- comfyui_frontend_package/static/assets/main-CJ1ZmTbz.js +0 -14
- comfyui_frontend_package/static/assets/main-CJ1ZmTbz.js.map +0 -1
- comfyui_frontend_package/static/assets/main-DxByB8u3.js +0 -17
- comfyui_frontend_package/static/assets/main-DxByB8u3.js.map +0 -1
- comfyui_frontend_package/static/assets/main-Dyk43SJi.js +0 -17
- comfyui_frontend_package/static/assets/main-Dyk43SJi.js.map +0 -1
- comfyui_frontend_package/static/assets/main-QMLeyFJQ.js +0 -17
- comfyui_frontend_package/static/assets/main-QMLeyFJQ.js.map +0 -1
- comfyui_frontend_package/static/assets/main-f7MqrMkx.js +0 -14
- comfyui_frontend_package/static/assets/main-f7MqrMkx.js.map +0 -1
- {comfyui_frontend_package-1.37.10.dist-info → comfyui_frontend_package-1.38.0.dist-info}/WHEEL +0 -0
- {comfyui_frontend_package-1.37.10.dist-info → comfyui_frontend_package-1.38.0.dist-info}/top_level.txt +0 -0
comfyui_frontend_package/static/assets/{WidgetChart-Dz4GcJwO.js.map → WidgetChart-BntGUEQZ.js.map}
RENAMED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WidgetChart-
|
|
1
|
+
{"version":3,"file":"WidgetChart-BntGUEQZ.js","sources":["../../src/renderer/extensions/vueNodes/widgets/components/WidgetChart.vue"],"sourcesContent":["<template>\n <div class=\"flex flex-col gap-1\">\n <div class=\"max-h-[48rem] rounded border p-4\">\n <Chart\n :type=\"chartType\"\n :data=\"chartData\"\n :options=\"chartOptions\"\n :aria-label=\"`${widget.name || $t('g.chart')} - ${chartType} ${$t('g.chartLowercase')}`\"\n />\n </div>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport type { ChartData } from 'chart.js'\nimport Chart from 'primevue/chart'\nimport { computed } from 'vue'\n\nimport type { ChartInputSpec } from '@/schemas/nodeDef/nodeDefSchemaV2'\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\n\ntype ChartWidgetOptions = NonNullable<ChartInputSpec['options']>\n\nconst value = defineModel<ChartData>({ required: true })\n\nconst props = defineProps<{\n widget: SimplifiedWidget<ChartData, ChartWidgetOptions>\n}>()\n\nconst chartType = computed(() => props.widget.options?.type ?? 'line')\n\nconst chartData = computed(() => value.value || { labels: [], datasets: [] })\n\nconst chartOptions = computed(() => ({\n responsive: true,\n maintainAspectRatio: false,\n plugins: {\n legend: {\n labels: {\n color: '#FFF',\n usePointStyle: true,\n pointStyle: 'circle'\n }\n }\n },\n scales: {\n x: {\n ticks: {\n color: '#9FA2BD'\n },\n grid: {\n display: true,\n color: '#9FA2BD',\n drawTicks: false,\n drawOnChartArea: true,\n drawBorder: false\n },\n border: {\n display: true,\n color: '#9FA2BD'\n }\n },\n y: {\n ticks: {\n color: '#9FA2BD'\n },\n grid: {\n display: false,\n drawTicks: false,\n drawOnChartArea: false,\n drawBorder: false\n },\n border: {\n display: true,\n color: '#9FA2BD'\n }\n }\n }\n}))\n</script>\n"],"names":["value","_useModel","__props","props","chartType","computed","chartData","chartOptions"],"mappings":"kXAuBA,MAAMA,EAAQC,EAAsBC,EAAA,YAAmB,EAEjDC,EAAQD,EAIRE,EAAYC,EAAS,IAAMF,EAAM,OAAO,SAAS,MAAQ,MAAM,EAE/DG,EAAYD,EAAS,IAAML,EAAM,OAAS,CAAE,OAAQ,CAAA,EAAI,SAAU,CAAA,EAAI,EAEtEO,EAAeF,EAAS,KAAO,CACnC,WAAY,GACZ,oBAAqB,GACrB,QAAS,CACP,OAAQ,CACN,OAAQ,CACN,MAAO,OACP,cAAe,GACf,WAAY,QAAA,CACd,CACF,EAEF,OAAQ,CACN,EAAG,CACD,MAAO,CACL,MAAO,SAAA,EAET,KAAM,CACJ,QAAS,GACT,MAAO,UACP,UAAW,GACX,gBAAiB,GACjB,WAAY,EAAA,EAEd,OAAQ,CACN,QAAS,GACT,MAAO,SAAA,CACT,EAEF,EAAG,CACD,MAAO,CACL,MAAO,SAAA,EAET,KAAM,CACJ,QAAS,GACT,UAAW,GACX,gBAAiB,GACjB,WAAY,EAAA,EAEd,OAAQ,CACN,QAAS,GACT,MAAO,SAAA,CACT,CACF,CACF,EACA"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
var P=Object.defineProperty;var n=(r,l)=>P(r,"name",{value:l,configurable:!0});import{x as V}from"./vendor-primevue-
|
|
2
|
-
//# sourceMappingURL=WidgetColorPicker-
|
|
1
|
+
var P=Object.defineProperty;var n=(r,l)=>P(r,"name",{value:l,configurable:!0});import{x as V}from"./vendor-primevue-DeKsC2uk.js";import{cI as d,cJ as a,c as x}from"./index--yK73oka.js";import{P as v,f as C}from"./widgetPropFilter-CygYoMQt.js";import{W as h}from"./index-Hz5b30sA.js";import{_ as b}from"./WidgetLayoutField.vue_vue_type_script_setup_true_lang-Bq1noASf.js";import{bx as E,E as p,r as k,w as D,j as U,d as B,k as F,e as u,s as L,by as s,z as O,m as R,u as W}from"./vendor-other-B8t_Wf2K.js";import"./vendor-vue-DaLZjKA7.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-DH0o8VQ7.js";import"./vendor-tiptap-VxK0yxkd.js";const y={class:"text-xs truncate min-w-[4ch]","data-testid":"widget-color-text"},q=E({__name:"WidgetColorPicker",props:{widget:{},modelValue:{}},emits:["update:modelValue"],setup(r,{emit:l}){const o=r,c=l,i=p(()=>{const e=o.widget.options?.format;return d(e)?e:"hex"}),t=k(a(o.modelValue||"#000000",d(o.widget.options?.format)?o.widget.options.format:"hex"));D(()=>o.modelValue,e=>{t.value=a(e||"#000000",i.value)});function f(e){t.value=e,c("update:modelValue",a(e,i.value))}n(f,"onPickerUpdate");const w=[...v],g=p(()=>C(o.widget.options,w));return(e,m)=>(B(),U(b,{widget:e.widget},{default:F(()=>[u("label",{class:L(s(x)(s(h),"flex items-center gap-2 w-full px-4 py-2"))},[O(s(V),R({modelValue:t.value,"onUpdate:modelValue":m[0]||(m[0]=_=>t.value=_)},g.value,{class:"h-4 w-8 overflow-hidden !rounded-full border-none","aria-label":e.widget.name,pt:{preview:"!w-full !h-full !border-none"},"onUpdate:modelValue":f}),null,16,["modelValue","aria-label"]),u("span",y,W(s(a)(t.value,i.value)),1)],2)]),_:1},8,["widget"]))}});export{q as default};
|
|
2
|
+
//# sourceMappingURL=WidgetColorPicker-CkqNsGhI.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WidgetColorPicker-
|
|
1
|
+
{"version":3,"file":"WidgetColorPicker-CkqNsGhI.js","sources":["../../src/renderer/extensions/vueNodes/widgets/components/WidgetColorPicker.vue"],"sourcesContent":["<!-- Needs custom color picker for alpha support -->\n<template>\n <WidgetLayoutField :widget=\"widget\">\n <label\n :class=\"\n cn(WidgetInputBaseClass, 'flex items-center gap-2 w-full px-4 py-2')\n \"\n >\n <ColorPicker\n v-model=\"localValue\"\n v-bind=\"filteredProps\"\n class=\"h-4 w-8 overflow-hidden !rounded-full border-none\"\n :aria-label=\"widget.name\"\n :pt=\"{\n preview: '!w-full !h-full !border-none'\n }\"\n @update:model-value=\"onPickerUpdate\"\n />\n <span\n class=\"text-xs truncate min-w-[4ch]\"\n data-testid=\"widget-color-text\"\n >{{ toHexFromFormat(localValue, format) }}</span\n >\n </label>\n </WidgetLayoutField>\n</template>\n\n<script setup lang=\"ts\">\nimport ColorPicker from 'primevue/colorpicker'\nimport { computed, ref, watch } from 'vue'\n\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\nimport { isColorFormat, toHexFromFormat } from '@/utils/colorUtil'\nimport type { ColorFormat, HSB } from '@/utils/colorUtil'\nimport { cn } from '@/utils/tailwindUtil'\nimport {\n PANEL_EXCLUDED_PROPS,\n filterWidgetProps\n} from '@/utils/widgetPropFilter'\n\nimport { WidgetInputBaseClass } from './layout'\nimport WidgetLayoutField from './layout/WidgetLayoutField.vue'\n\ntype WidgetOptions = { format?: ColorFormat } & Record<string, unknown>\n\nconst props = defineProps<{\n widget: SimplifiedWidget<string, WidgetOptions>\n modelValue: string\n}>()\n\nconst emit = defineEmits<{\n 'update:modelValue': [value: string]\n}>()\n\nconst format = computed<ColorFormat>(() => {\n const optionFormat = props.widget.options?.format\n return isColorFormat(optionFormat) ? optionFormat : 'hex'\n})\n\ntype PickerValue = string | HSB\nconst localValue = ref<PickerValue>(\n toHexFromFormat(\n props.modelValue || '#000000',\n isColorFormat(props.widget.options?.format)\n ? props.widget.options.format\n : 'hex'\n )\n)\n\nwatch(\n () => props.modelValue,\n (newVal) => {\n localValue.value = toHexFromFormat(newVal || '#000000', format.value)\n }\n)\n\nfunction onPickerUpdate(val: unknown) {\n localValue.value = val as PickerValue\n emit('update:modelValue', toHexFromFormat(val, format.value))\n}\n\n// ColorPicker specific excluded props include panel/overlay classes\nconst COLOR_PICKER_EXCLUDED_PROPS = [...PANEL_EXCLUDED_PROPS] as const\n\nconst filteredProps = computed(() =>\n filterWidgetProps(props.widget.options, COLOR_PICKER_EXCLUDED_PROPS)\n)\n</script>\n"],"names":["props","__props","emit","__emit","format","computed","optionFormat","isColorFormat","localValue","ref","toHexFromFormat","watch","newVal","onPickerUpdate","val","__name","COLOR_PICKER_EXCLUDED_PROPS","PANEL_EXCLUDED_PROPS","filteredProps","filterWidgetProps"],"mappings":"k0BA6CA,MAAMA,EAAQC,EAKRC,EAAOC,EAIPC,EAASC,EAAsB,IAAM,CACzC,MAAMC,EAAeN,EAAM,OAAO,SAAS,OAC3C,OAAOO,EAAcD,CAAY,EAAIA,EAAe,KACtD,CAAC,EAGKE,EAAaC,EACjBC,EACEV,EAAM,YAAc,UACpBO,EAAcP,EAAM,OAAO,SAAS,MAAM,EACtCA,EAAM,OAAO,QAAQ,OACrB,KAAA,CACN,EAGFW,EACE,IAAMX,EAAM,WACXY,GAAW,CACVJ,EAAW,MAAQE,EAAgBE,GAAU,UAAWR,EAAO,KAAK,CACtE,CAAA,EAGF,SAASS,EAAeC,EAAc,CACpCN,EAAW,MAAQM,EACnBZ,EAAK,oBAAqBQ,EAAgBI,EAAKV,EAAO,KAAK,CAAC,CAC9D,CAHSW,EAAAF,EAAA,kBAMT,MAAMG,EAA8B,CAAC,GAAGC,CAAoB,EAEtDC,EAAgBb,EAAS,IAC7Bc,EAAkBnB,EAAM,OAAO,QAASgB,CAA2B,CAAA"}
|
comfyui_frontend_package/static/assets/{WidgetGalleria-CV4Nv2wv.js → WidgetGalleria-BYYCCQyX.js}
RENAMED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{n as v}from"./vendor-primevue-
|
|
2
|
-
//# sourceMappingURL=WidgetGalleria-
|
|
1
|
+
import{n as v}from"./vendor-primevue-DeKsC2uk.js";import{u as w}from"./vendor-vue-DaLZjKA7.js";import{f as _,G as b}from"./widgetPropFilter-CygYoMQt.js";import{bx as x,cM as I,cN as y,r as $,E as s,c as B,d as N,z as P,k as d,e as u,by as i,m as E}from"./vendor-other-B8t_Wf2K.js";import{d as S}from"./index--yK73oka.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-DH0o8VQ7.js";import"./vendor-tiptap-VxK0yxkd.js";const V={class:"flex flex-col gap-1"},A=["src","alt"],C={class:"h-full w-full p-1"},G=["src","alt"],M=x({__name:"WidgetGalleria",props:I({widget:{}},{modelValue:{required:!0},modelModifiers:{}}),emits:["update:modelValue"],setup(c){const o=y(c,"modelValue"),r=c,n=$(0),{t:m}=w(),f=s(()=>_(r.widget.options,b)),t=s(()=>!o.value||!Array.isArray(o.value)?[]:o.value.filter(a=>a!=null).map((a,l)=>typeof a=="string"?{itemImageSrc:a,thumbnailImageSrc:a,alt:`Image ${l}`}:a??{})),g=s(()=>r.widget.options?.showThumbnails!==!1&&t.value.length>1),h=s(()=>r.widget.options?.showItemNavigators!==!1&&t.value.length>1);return(a,l)=>(N(),B("div",V,[P(i(v),E({"active-index":n.value,"onUpdate:activeIndex":l[0]||(l[0]=e=>n.value=e),value:t.value},f.value,{"show-thumbnails":g.value,"show-item-navigators":h.value,class:"max-w-full",pt:{thumbnails:{class:"overflow-hidden"},thumbnailContent:{class:"py-4 px-2"},thumbnailPrevButton:{class:"m-0"},thumbnailNextButton:{class:"m-0"}}}),{item:d(({item:e})=>[u("img",{src:e?.itemImageSrc||e?.src||"",alt:e?.alt||`${i(m)("g.galleryImage")} ${n.value+1} of ${t.value.length}`,class:"h-auto max-h-64 w-full object-contain"},null,8,A)]),thumbnail:d(({item:e})=>[u("div",C,[u("img",{src:e?.thumbnailImageSrc||e?.src||"",alt:e?.alt||`${i(m)("g.galleryThumbnail")} ${t.value.findIndex(p=>p===e)+1} of ${t.value.length}`,class:"h-full w-full rounded-lg object-cover"},null,8,G)])]),_:1},16,["active-index","value","show-thumbnails","show-item-navigators"])]))}}),q=S(M,[["__scopeId","data-v-34cd3eda"]]);export{q as default};
|
|
2
|
+
//# sourceMappingURL=WidgetGalleria-BYYCCQyX.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WidgetGalleria-
|
|
1
|
+
{"version":3,"file":"WidgetGalleria-BYYCCQyX.js","sources":["../../src/renderer/extensions/vueNodes/widgets/components/WidgetGalleria.vue"],"sourcesContent":["<template>\n <div class=\"flex flex-col gap-1\">\n <Galleria\n v-model:active-index=\"activeIndex\"\n :value=\"galleryImages\"\n v-bind=\"filteredProps\"\n :show-thumbnails=\"showThumbnails\"\n :show-item-navigators=\"showNavButtons\"\n class=\"max-w-full\"\n :pt=\"{\n thumbnails: {\n class: 'overflow-hidden'\n },\n thumbnailContent: {\n class: 'py-4 px-2'\n },\n thumbnailPrevButton: {\n class: 'm-0'\n },\n thumbnailNextButton: {\n class: 'm-0'\n }\n }\"\n >\n <template #item=\"{ item }\">\n <img\n :src=\"item?.itemImageSrc || item?.src || ''\"\n :alt=\"\n item?.alt ||\n `${t('g.galleryImage')} ${activeIndex + 1} of ${galleryImages.length}`\n \"\n class=\"h-auto max-h-64 w-full object-contain\"\n />\n </template>\n <template #thumbnail=\"{ item }\">\n <div class=\"h-full w-full p-1\">\n <img\n :src=\"item?.thumbnailImageSrc || item?.src || ''\"\n :alt=\"\n item?.alt ||\n `${t('g.galleryThumbnail')} ${galleryImages.findIndex((img) => img === item) + 1} of ${galleryImages.length}`\n \"\n class=\"h-full w-full rounded-lg object-cover\"\n />\n </div>\n </template>\n </Galleria>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport Galleria from 'primevue/galleria'\nimport { computed, ref } from 'vue'\nimport { useI18n } from 'vue-i18n'\n\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\nimport {\n GALLERIA_EXCLUDED_PROPS,\n filterWidgetProps\n} from '@/utils/widgetPropFilter'\n\nexport interface GalleryImage {\n itemImageSrc?: string\n thumbnailImageSrc?: string\n src?: string\n alt?: string\n}\n\nexport type GalleryValue = string[] | GalleryImage[]\n\nconst value = defineModel<GalleryValue>({ required: true })\n\nconst props = defineProps<{\n widget: SimplifiedWidget<GalleryValue>\n}>()\n\nconst activeIndex = ref(0)\n\nconst { t } = useI18n()\n\nconst filteredProps = computed(() =>\n filterWidgetProps(props.widget.options, GALLERIA_EXCLUDED_PROPS)\n)\n\nconst galleryImages = computed(() => {\n if (!value.value || !Array.isArray(value.value)) return []\n\n return value.value\n .filter((item) => item !== null && item !== undefined) // Filter out null/undefined\n .map((item, index) => {\n if (typeof item === 'string') {\n return {\n itemImageSrc: item,\n thumbnailImageSrc: item,\n alt: `Image ${index}`\n }\n }\n return item ?? {} // Ensure we have at least an empty object\n })\n})\n\nconst showThumbnails = computed(() => {\n return (\n props.widget.options?.showThumbnails !== false &&\n galleryImages.value.length > 1\n )\n})\n\nconst showNavButtons = computed(() => {\n return (\n props.widget.options?.showItemNavigators !== false &&\n galleryImages.value.length > 1\n )\n})\n</script>\n\n<style scoped>\n/* Ensure thumbnail container doesn't overflow */\n:deep(.p-galleria-thumbnails) {\n overflow: hidden;\n}\n\n/* Constrain thumbnail items to prevent overlap */\n:deep(.p-galleria-thumbnail-item) {\n flex-shrink: 0;\n}\n\n/* Ensure thumbnail wrapper maintains aspect ratio */\n:deep(.p-galleria-thumbnail) {\n overflow: hidden;\n}\n</style>\n"],"names":["value","_useModel","__props","props","activeIndex","ref","t","useI18n","filteredProps","computed","filterWidgetProps","GALLERIA_EXCLUDED_PROPS","galleryImages","item","index","showThumbnails","showNavButtons"],"mappings":"mpBAsEA,MAAMA,EAAQC,EAAyBC,EAAA,YAAmB,EAEpDC,EAAQD,EAIRE,EAAcC,EAAI,CAAC,EAEnB,CAAE,EAAAC,CAAA,EAAMC,EAAA,EAERC,EAAgBC,EAAS,IAC7BC,EAAkBP,EAAM,OAAO,QAASQ,CAAuB,CAAA,EAG3DC,EAAgBH,EAAS,IACzB,CAACT,EAAM,OAAS,CAAC,MAAM,QAAQA,EAAM,KAAK,EAAU,CAAA,EAEjDA,EAAM,MACV,OAAQa,GAASA,GAAS,IAA0B,EACpD,IAAI,CAACA,EAAMC,IACN,OAAOD,GAAS,SACX,CACL,aAAcA,EACd,kBAAmBA,EACnB,IAAK,SAASC,CAAK,EAAA,EAGhBD,GAAQ,CAAA,CAChB,CACJ,EAEKE,EAAiBN,EAAS,IAE5BN,EAAM,OAAO,SAAS,iBAAmB,IACzCS,EAAc,MAAM,OAAS,CAEhC,EAEKI,EAAiBP,EAAS,IAE5BN,EAAM,OAAO,SAAS,qBAAuB,IAC7CS,EAAc,MAAM,OAAS,CAEhC"}
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import{_ as o}from"./WidgetInputNumber.vue_vue_type_script_setup_true_lang-qjF5C0EN.js";import"./vendor-primevue-DeKsC2uk.js";import"./vendor-other-B8t_Wf2K.js";import"./index--yK73oka.js";import"./vendor-vue-DaLZjKA7.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-DH0o8VQ7.js";import"./vendor-tiptap-VxK0yxkd.js";import"./widgetPropFilter-CygYoMQt.js";import"./index-Hz5b30sA.js";import"./WidgetLayoutField.vue_vue_type_script_setup_true_lang-Bq1noASf.js";import"./WidgetWithControl.vue_vue_type_script_setup_true_lang-Bx6suA2O.js";export{o as default};
|
|
2
|
+
//# sourceMappingURL=WidgetInputNumber-psomfHIy.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"WidgetInputNumber-psomfHIy.js","sources":[],"sourcesContent":[],"names":[],"mappings":""}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
var E=Object.defineProperty;var f=(t,o)=>E(t,"name",{value:o,configurable:!0});import{J as S}from"./vendor-primevue-
|
|
2
|
-
//# sourceMappingURL=WidgetInputNumber.vue_vue_type_script_setup_true_lang-
|
|
1
|
+
var E=Object.defineProperty;var f=(t,o)=>E(t,"name",{value:o,configurable:!0});import{J as S}from"./vendor-primevue-DeKsC2uk.js";import{c as m,d as B,cF as U}from"./index--yK73oka.js";import{f as C,I as $,S as k}from"./widgetPropFilter-CygYoMQt.js";import{W as M}from"./index-Hz5b30sA.js";import{_ as W}from"./WidgetLayoutField.vue_vue_type_script_setup_true_lang-Bq1noASf.js";import{bx as N,cM as h,cN as x,E as d,h as L,j as c,d as g,k as b,l as R,e as w,by as l,m as V,p as z,L as A,r as F,s as G,z as T,t as X}from"./vendor-other-B8t_Wf2K.js";import{_ as j}from"./WidgetWithControl.vue_vue_type_script_setup_true_lang-Bx6suA2O.js";const J={class:"absolute top-5 right-8 h-4 w-7 -translate-y-4/5 flex"},O=N({__name:"WidgetInputNumberInput",props:h({widget:{}},{modelValue:{default:0},modelModifiers:{}}),emits:["update:modelValue"],setup(t){const o=t,s=x(t,"modelValue"),a=d(()=>C(o.widget.options,$)),e=d(()=>{const n=o.widget.options?.precision;return typeof n=="number"&&n>=0?n:void 0}),r=d(()=>{if(o.widget.options?.step2!==void 0)return Number(o.widget.options.step2);const n=o.widget.options?.step;return n!==void 0&&n>10?Number(n)/10:e.value!==void 0?e.value===0?1:Number((1/Math.pow(10,e.value)).toFixed(e.value)):0}),u=d(()=>o.widget.options?.useGrouping===!0),p=d(()=>{const n=s.value??0;return!Number.isFinite(n)||Math.abs(n)>Number.MAX_SAFE_INTEGER}),v=d(()=>p.value?"Increment/decrement disabled: value exceeds JavaScript precision limit (±2^53)":null);return(n,i)=>{const I=L("tooltip");return g(),c(W,{widget:n.widget},{default:b(()=>[R((g(),c(l(S),V({modelValue:s.value,"onUpdate:modelValue":i[0]||(i[0]=D=>s.value=D)},a.value,{fluid:"","button-layout":"horizontal",size:"small",variant:"outlined",step:r.value,"min-fraction-digits":e.value,"max-fraction-digits":e.value,"use-grouping":u.value,class:l(m)(l(M),"grow text-xs"),"aria-label":n.widget.name,"show-buttons":!p.value,pt:{root:{class:l(m)("[&>input]:bg-transparent [&>input]:border-0","[&>input]:truncate [&>input]:min-w-[4ch]",n.$slots.default&&"[&>input]:pr-7")},decrementButton:{class:"w-8 border-0"},incrementButton:{class:"w-8 border-0"}}}),{incrementicon:b(()=>i[1]||(i[1]=[w("span",{class:"pi pi-plus text-sm"},null,-1)])),decrementicon:b(()=>i[2]||(i[2]=[w("span",{class:"pi pi-minus text-sm"},null,-1)])),_:1},16,["modelValue","step","min-fraction-digits","max-fraction-digits","use-grouping","class","aria-label","show-buttons","pt"])),[[I,v.value]]),w("div",J,[z(n.$slots,"default",{},void 0,!0)])]),_:3},8,["widget"])}}}),_=B(O,[["__scopeId","data-v-618d59a6"]]);function q(t,o,s=!1){return d(()=>{const a=A(o);if(t?.step2!==void 0)return Number(t.step2);const e=t?.step;if(e!==void 0&&e>10)return Number(e)/10;if(a===void 0)return s?void 0:0;if(a===0)return 1;const r=1/Math.pow(10,a);return s?r:Number(r.toFixed(a))})}f(q,"useNumberStepCalculation");const y=m("inline-flex items-center justify-center border-0 bg-transparent text-inherit transition-colors duration-150 ease-in-out ","hover:bg-node-component-surface-hovered active:bg-node-component-surface-selected","disabled:bg-node-component-disabled disabled:text-node-icon-disabled disabled:cursor-not-allowed");function H(t){const{roundedLeft:o=!1,roundedRight:s=!1}=t??{},a=m(y,s&&"rounded-r-lg"),e=m(y,o&&"rounded-l-lg");return{incrementButton:{class:a},decrementButton:{class:e}}}f(H,"useNumberWidgetButtonPt");const K=N({__name:"WidgetInputNumberSlider",props:h({widget:{}},{modelValue:{default:0},modelModifiers:{}}),emits:["update:modelValue"],setup(t){const o=x(t,"modelValue"),s=F(0),a=f(i=>{i?.length&&(o.value=i[0])},"updateLocalValue"),e=f(i=>{if(i!==void 0){a([i]);return}s.value+=1},"handleNumberInputUpdate"),r=d(()=>C(t.widget.options,k)),u=t.widget.options?.precision,p=typeof u=="number"&&u>=0?u:void 0,v=q(t.widget.options,p,!0),n=H({roundedLeft:!0,roundedRight:!0});return(i,I)=>(g(),c(W,{widget:i.widget},{default:b(()=>[w("div",{class:G(l(m)(l(M),"flex items-center gap-2 pl-3 pr-2"))},[T(U,V({"model-value":[o.value]},r.value,{class:"flex-grow text-xs",step:l(v),"aria-label":i.widget.name,"onUpdate:modelValue":a}),null,16,["model-value","step","aria-label"]),(g(),c(l(S),V({key:s.value,"model-value":o.value},r.value,{step:l(v),"min-fraction-digits":l(p),"max-fraction-digits":l(p),"aria-label":i.widget.name,size:"small","pt:pc-input-text:root":"min-w-[4ch] bg-transparent border-none text-center truncate",class:"w-16",pt:l(n),"onUpdate:modelValue":e}),null,16,["model-value","step","min-fraction-digits","max-fraction-digits","aria-label","pt"]))],2)]),_:1},8,["widget"]))}}),P=B(K,[["__scopeId","data-v-989ee2f9"]]),ie=N({__name:"WidgetInputNumber",props:h({widget:{}},{modelValue:{default:0},modelModifiers:{}}),emits:["update:modelValue"],setup(t){const o=t,s=x(t,"modelValue"),a=d(()=>!!o.widget.controlWidget);return(e,r)=>a.value?(g(),c(j,{key:0,modelValue:s.value,"onUpdate:modelValue":r[0]||(r[0]=u=>s.value=u),widget:e.widget,component:e.widget.type==="slider"?P:_},null,8,["modelValue","widget","component"])):(g(),c(X(e.widget.type==="slider"?P:_),V({key:1,modelValue:s.value,"onUpdate:modelValue":r[1]||(r[1]=u=>s.value=u),widget:e.widget},e.$attrs),null,16,["modelValue","widget"]))}});export{ie as _};
|
|
2
|
+
//# sourceMappingURL=WidgetInputNumber.vue_vue_type_script_setup_true_lang-qjF5C0EN.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WidgetInputNumber.vue_vue_type_script_setup_true_lang-D-IwEPPr.js","sources":["../../src/renderer/extensions/vueNodes/widgets/components/WidgetInputNumberInput.vue","../../src/renderer/extensions/vueNodes/widgets/composables/useNumberStepCalculation.ts","../../src/renderer/extensions/vueNodes/widgets/composables/useNumberWidgetButtonPt.ts","../../src/renderer/extensions/vueNodes/widgets/components/WidgetInputNumberSlider.vue","../../src/renderer/extensions/vueNodes/widgets/components/WidgetInputNumber.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport InputNumber from 'primevue/inputnumber'\nimport { computed } from 'vue'\n\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\nimport { cn } from '@/utils/tailwindUtil'\nimport {\n INPUT_EXCLUDED_PROPS,\n filterWidgetProps\n} from '@/utils/widgetPropFilter'\n\nimport { WidgetInputBaseClass } from './layout'\nimport WidgetLayoutField from './layout/WidgetLayoutField.vue'\n\nconst props = defineProps<{\n widget: SimplifiedWidget<number>\n}>()\n\nconst modelValue = defineModel<number>({ default: 0 })\n\nconst filteredProps = computed(() =>\n filterWidgetProps(props.widget.options, INPUT_EXCLUDED_PROPS)\n)\n\n// Get the precision value for proper number formatting\nconst precision = computed(() => {\n const p = props.widget.options?.precision\n // Treat negative or non-numeric precision as undefined\n return typeof p === 'number' && p >= 0 ? p : undefined\n})\n\n// Calculate the step value based on precision or widget options\nconst stepValue = computed(() => {\n // Use step2 (correct input spec value) if available\n if (props.widget.options?.step2 !== undefined) {\n return Number(props.widget.options.step2)\n }\n // Use step / 10 for custom large step values (> 10) to match litegraph behavior\n // This is important for extensions like Impact Pack that use custom step values (e.g., 640)\n // We skip default step values (1, 10) to avoid affecting normal widgets\n const step = props.widget.options?.step\n if (step !== undefined && step > 10) {\n return Number(step) / 10\n }\n // Otherwise, derive from precision\n if (precision.value !== undefined) {\n if (precision.value === 0) {\n return 1\n }\n // For precision > 0, step = 1 / (10^precision)\n // precision 1 → 0.1, precision 2 → 0.01, etc.\n return Number((1 / Math.pow(10, precision.value)).toFixed(precision.value))\n }\n // Default to 'any' for unrestricted stepping\n return 0\n})\n\n// Disable grouping separators by default unless explicitly enabled by the node author\nconst useGrouping = computed(() => {\n return props.widget.options?.useGrouping === true\n})\n\n// Check if increment/decrement buttons should be disabled due to precision limits\nconst buttonsDisabled = computed(() => {\n const currentValue = modelValue.value ?? 0\n return (\n !Number.isFinite(currentValue) ||\n Math.abs(currentValue) > Number.MAX_SAFE_INTEGER\n )\n})\n\nconst buttonTooltip = computed(() => {\n if (buttonsDisabled.value) {\n return 'Increment/decrement disabled: value exceeds JavaScript precision limit (±2^53)'\n }\n return null\n})\n</script>\n\n<template>\n <WidgetLayoutField :widget>\n <InputNumber\n v-model=\"modelValue\"\n v-tooltip=\"buttonTooltip\"\n v-bind=\"filteredProps\"\n fluid\n button-layout=\"horizontal\"\n size=\"small\"\n variant=\"outlined\"\n :step=\"stepValue\"\n :min-fraction-digits=\"precision\"\n :max-fraction-digits=\"precision\"\n :use-grouping=\"useGrouping\"\n :class=\"cn(WidgetInputBaseClass, 'grow text-xs')\"\n :aria-label=\"widget.name\"\n :show-buttons=\"!buttonsDisabled\"\n :pt=\"{\n root: {\n class: cn(\n '[&>input]:bg-transparent [&>input]:border-0',\n '[&>input]:truncate [&>input]:min-w-[4ch]',\n $slots.default && '[&>input]:pr-7'\n )\n },\n decrementButton: {\n class: 'w-8 border-0'\n },\n incrementButton: {\n class: 'w-8 border-0'\n }\n }\"\n >\n <template #incrementicon>\n <span class=\"pi pi-plus text-sm\" />\n </template>\n <template #decrementicon>\n <span class=\"pi pi-minus text-sm\" />\n </template>\n </InputNumber>\n <div class=\"absolute top-5 right-8 h-4 w-7 -translate-y-4/5 flex\">\n <slot />\n </div>\n </WidgetLayoutField>\n</template>\n\n<style scoped>\n:deep(.p-inputnumber-input) {\n height: 1.625rem;\n margin: 1px 0;\n box-shadow: none;\n}\n</style>\n","import { computed, toValue } from 'vue'\nimport type { MaybeRefOrGetter } from 'vue'\n\ninterface NumberWidgetOptions {\n step?: number\n step2?: number\n precision?: number\n}\n\n/**\n * Shared composable for calculating step values in number input widgets\n * Handles both explicit step2 values and precision-derived steps\n */\nexport function useNumberStepCalculation(\n options: NumberWidgetOptions | undefined,\n precisionArg: MaybeRefOrGetter<number | undefined>,\n returnUndefinedForDefault = false\n) {\n return computed(() => {\n const precision = toValue(precisionArg)\n // Use step2 (correct input spec value) if available\n if (options?.step2 !== undefined) {\n return Number(options.step2)\n }\n // Use step / 10 for custom large step values (> 10) to match litegraph behavior\n // This is important for extensions like Impact Pack that use custom step values (e.g., 640)\n // We skip default step values (1, 10) to avoid affecting normal widgets\n const step = options?.step\n if (step !== undefined && step > 10) {\n return Number(step) / 10\n }\n\n if (precision === undefined) {\n return returnUndefinedForDefault ? undefined : 0\n }\n\n if (precision === 0) return 1\n\n // For precision > 0, step = 1 / (10^precision)\n const calculatedStep = 1 / Math.pow(10, precision)\n return returnUndefinedForDefault\n ? calculatedStep\n : Number(calculatedStep.toFixed(precision))\n })\n}\n","import { cn } from '@comfyorg/tailwind-utils'\n\nconst sharedButtonClasses = cn(\n 'inline-flex items-center justify-center border-0 bg-transparent text-inherit transition-colors duration-150 ease-in-out ',\n 'hover:bg-node-component-surface-hovered active:bg-node-component-surface-selected',\n 'disabled:bg-node-component-disabled disabled:text-node-icon-disabled disabled:cursor-not-allowed'\n)\n\nexport function useNumberWidgetButtonPt(options?: {\n roundedLeft?: boolean\n roundedRight?: boolean\n}) {\n const { roundedLeft = false, roundedRight = false } = options ?? {}\n\n const increment = cn(sharedButtonClasses, roundedRight && 'rounded-r-lg')\n const decrement = cn(sharedButtonClasses, roundedLeft && 'rounded-l-lg')\n\n return {\n incrementButton: {\n class: increment\n },\n decrementButton: {\n class: decrement\n }\n }\n}\n","<template>\n <WidgetLayoutField :widget=\"widget\">\n <div :class=\"cn(WidgetInputBaseClass, 'flex items-center gap-2 pl-3 pr-2')\">\n <Slider\n :model-value=\"[modelValue]\"\n v-bind=\"filteredProps\"\n class=\"flex-grow text-xs\"\n :step=\"stepValue\"\n :aria-label=\"widget.name\"\n @update:model-value=\"updateLocalValue\"\n />\n <InputNumber\n :key=\"timesEmptied\"\n :model-value=\"modelValue\"\n v-bind=\"filteredProps\"\n :step=\"stepValue\"\n :min-fraction-digits=\"precision\"\n :max-fraction-digits=\"precision\"\n :aria-label=\"widget.name\"\n size=\"small\"\n pt:pc-input-text:root=\"min-w-[4ch] bg-transparent border-none text-center truncate\"\n class=\"w-16\"\n :pt=\"sliderNumberPt\"\n @update:model-value=\"handleNumberInputUpdate\"\n />\n </div>\n </WidgetLayoutField>\n</template>\n\n<script setup lang=\"ts\">\nimport InputNumber from 'primevue/inputnumber'\nimport { computed, ref } from 'vue'\n\nimport Slider from '@/components/ui/slider/Slider.vue'\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\nimport { cn } from '@/utils/tailwindUtil'\nimport {\n STANDARD_EXCLUDED_PROPS,\n filterWidgetProps\n} from '@/utils/widgetPropFilter'\n\nimport { useNumberStepCalculation } from '../composables/useNumberStepCalculation'\nimport { useNumberWidgetButtonPt } from '../composables/useNumberWidgetButtonPt'\nimport { WidgetInputBaseClass } from './layout'\nimport WidgetLayoutField from './layout/WidgetLayoutField.vue'\n\nconst { widget } = defineProps<{\n widget: SimplifiedWidget<number>\n}>()\n\nconst modelValue = defineModel<number>({ default: 0 })\n\nconst timesEmptied = ref(0)\n\nconst updateLocalValue = (newValue: number[] | undefined): void => {\n if (newValue?.length) modelValue.value = newValue[0]\n}\n\nconst handleNumberInputUpdate = (newValue: number | undefined) => {\n if (newValue !== undefined) {\n updateLocalValue([newValue])\n return\n }\n timesEmptied.value += 1\n}\n\nconst filteredProps = computed(() =>\n filterWidgetProps(widget.options, STANDARD_EXCLUDED_PROPS)\n)\n\nconst p = widget.options?.precision\nconst precision = typeof p === 'number' && p >= 0 ? p : undefined\n\n// Calculate the step value based on precision or widget options\nconst stepValue = useNumberStepCalculation(widget.options, precision, true)\n\nconst sliderNumberPt = useNumberWidgetButtonPt({\n roundedLeft: true,\n roundedRight: true\n})\n</script>\n\n<style scoped>\n:deep(.p-inputnumber-button.p-disabled .pi),\n:deep(.p-inputnumber-button.p-disabled .p-icon) {\n color: var(--color-node-icon-disabled) !important;\n}\n</style>\n","<script setup lang=\"ts\">\nimport { computed } from 'vue'\n\nimport type {\n SimplifiedControlWidget,\n SimplifiedWidget\n} from '@/types/simplifiedWidget'\n\nimport WidgetInputNumberInput from './WidgetInputNumberInput.vue'\nimport WidgetInputNumberSlider from './WidgetInputNumberSlider.vue'\nimport WidgetWithControl from './WidgetWithControl.vue'\n\nconst props = defineProps<{\n widget: SimplifiedWidget<number>\n}>()\n\nconst modelValue = defineModel<number>({ default: 0 })\n\nconst hasControlAfterGenerate = computed(() => {\n return !!props.widget.controlWidget\n})\n</script>\n\n<template>\n <WidgetWithControl\n v-if=\"hasControlAfterGenerate\"\n v-model=\"modelValue\"\n :widget=\"widget as SimplifiedControlWidget<number>\"\n :component=\"\n widget.type === 'slider'\n ? WidgetInputNumberSlider\n : WidgetInputNumberInput\n \"\n />\n <component\n :is=\"\n widget.type === 'slider'\n ? WidgetInputNumberSlider\n : WidgetInputNumberInput\n \"\n v-else\n v-model=\"modelValue\"\n :widget=\"widget\"\n v-bind=\"$attrs\"\n />\n</template>\n"],"names":["props","__props","modelValue","_useModel","filteredProps","computed","filterWidgetProps","INPUT_EXCLUDED_PROPS","precision","p","stepValue","step","useGrouping","buttonsDisabled","currentValue","buttonTooltip","useNumberStepCalculation","options","precisionArg","returnUndefinedForDefault","toValue","calculatedStep","__name","sharedButtonClasses","cn","useNumberWidgetButtonPt","roundedLeft","roundedRight","increment","decrement","timesEmptied","ref","updateLocalValue","newValue","handleNumberInputUpdate","STANDARD_EXCLUDED_PROPS","sliderNumberPt","hasControlAfterGenerate"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"WidgetInputNumber.vue_vue_type_script_setup_true_lang-qjF5C0EN.js","sources":["../../src/renderer/extensions/vueNodes/widgets/components/WidgetInputNumberInput.vue","../../src/renderer/extensions/vueNodes/widgets/composables/useNumberStepCalculation.ts","../../src/renderer/extensions/vueNodes/widgets/composables/useNumberWidgetButtonPt.ts","../../src/renderer/extensions/vueNodes/widgets/components/WidgetInputNumberSlider.vue","../../src/renderer/extensions/vueNodes/widgets/components/WidgetInputNumber.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport InputNumber from 'primevue/inputnumber'\nimport { computed } from 'vue'\n\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\nimport { cn } from '@/utils/tailwindUtil'\nimport {\n INPUT_EXCLUDED_PROPS,\n filterWidgetProps\n} from '@/utils/widgetPropFilter'\n\nimport { WidgetInputBaseClass } from './layout'\nimport WidgetLayoutField from './layout/WidgetLayoutField.vue'\n\nconst props = defineProps<{\n widget: SimplifiedWidget<number>\n}>()\n\nconst modelValue = defineModel<number>({ default: 0 })\n\nconst filteredProps = computed(() =>\n filterWidgetProps(props.widget.options, INPUT_EXCLUDED_PROPS)\n)\n\n// Get the precision value for proper number formatting\nconst precision = computed(() => {\n const p = props.widget.options?.precision\n // Treat negative or non-numeric precision as undefined\n return typeof p === 'number' && p >= 0 ? p : undefined\n})\n\n// Calculate the step value based on precision or widget options\nconst stepValue = computed(() => {\n // Use step2 (correct input spec value) if available\n if (props.widget.options?.step2 !== undefined) {\n return Number(props.widget.options.step2)\n }\n // Use step / 10 for custom large step values (> 10) to match litegraph behavior\n // This is important for extensions like Impact Pack that use custom step values (e.g., 640)\n // We skip default step values (1, 10) to avoid affecting normal widgets\n const step = props.widget.options?.step\n if (step !== undefined && step > 10) {\n return Number(step) / 10\n }\n // Otherwise, derive from precision\n if (precision.value !== undefined) {\n if (precision.value === 0) {\n return 1\n }\n // For precision > 0, step = 1 / (10^precision)\n // precision 1 → 0.1, precision 2 → 0.01, etc.\n return Number((1 / Math.pow(10, precision.value)).toFixed(precision.value))\n }\n // Default to 'any' for unrestricted stepping\n return 0\n})\n\n// Disable grouping separators by default unless explicitly enabled by the node author\nconst useGrouping = computed(() => {\n return props.widget.options?.useGrouping === true\n})\n\n// Check if increment/decrement buttons should be disabled due to precision limits\nconst buttonsDisabled = computed(() => {\n const currentValue = modelValue.value ?? 0\n return (\n !Number.isFinite(currentValue) ||\n Math.abs(currentValue) > Number.MAX_SAFE_INTEGER\n )\n})\n\nconst buttonTooltip = computed(() => {\n if (buttonsDisabled.value) {\n return 'Increment/decrement disabled: value exceeds JavaScript precision limit (±2^53)'\n }\n return null\n})\n</script>\n\n<template>\n <WidgetLayoutField :widget>\n <InputNumber\n v-model=\"modelValue\"\n v-tooltip=\"buttonTooltip\"\n v-bind=\"filteredProps\"\n fluid\n button-layout=\"horizontal\"\n size=\"small\"\n variant=\"outlined\"\n :step=\"stepValue\"\n :min-fraction-digits=\"precision\"\n :max-fraction-digits=\"precision\"\n :use-grouping=\"useGrouping\"\n :class=\"cn(WidgetInputBaseClass, 'grow text-xs')\"\n :aria-label=\"widget.name\"\n :show-buttons=\"!buttonsDisabled\"\n :pt=\"{\n root: {\n class: cn(\n '[&>input]:bg-transparent [&>input]:border-0',\n '[&>input]:truncate [&>input]:min-w-[4ch]',\n $slots.default && '[&>input]:pr-7'\n )\n },\n decrementButton: {\n class: 'w-8 border-0'\n },\n incrementButton: {\n class: 'w-8 border-0'\n }\n }\"\n >\n <template #incrementicon>\n <span class=\"pi pi-plus text-sm\" />\n </template>\n <template #decrementicon>\n <span class=\"pi pi-minus text-sm\" />\n </template>\n </InputNumber>\n <div class=\"absolute top-5 right-8 h-4 w-7 -translate-y-4/5 flex\">\n <slot />\n </div>\n </WidgetLayoutField>\n</template>\n\n<style scoped>\n:deep(.p-inputnumber-input) {\n height: 1.625rem;\n margin: 1px 0;\n box-shadow: none;\n}\n</style>\n","import { computed, toValue } from 'vue'\nimport type { MaybeRefOrGetter } from 'vue'\n\ninterface NumberWidgetOptions {\n step?: number\n step2?: number\n precision?: number\n}\n\n/**\n * Shared composable for calculating step values in number input widgets\n * Handles both explicit step2 values and precision-derived steps\n */\nexport function useNumberStepCalculation(\n options: NumberWidgetOptions | undefined,\n precisionArg: MaybeRefOrGetter<number | undefined>,\n returnUndefinedForDefault = false\n) {\n return computed(() => {\n const precision = toValue(precisionArg)\n // Use step2 (correct input spec value) if available\n if (options?.step2 !== undefined) {\n return Number(options.step2)\n }\n // Use step / 10 for custom large step values (> 10) to match litegraph behavior\n // This is important for extensions like Impact Pack that use custom step values (e.g., 640)\n // We skip default step values (1, 10) to avoid affecting normal widgets\n const step = options?.step\n if (step !== undefined && step > 10) {\n return Number(step) / 10\n }\n\n if (precision === undefined) {\n return returnUndefinedForDefault ? undefined : 0\n }\n\n if (precision === 0) return 1\n\n // For precision > 0, step = 1 / (10^precision)\n const calculatedStep = 1 / Math.pow(10, precision)\n return returnUndefinedForDefault\n ? calculatedStep\n : Number(calculatedStep.toFixed(precision))\n })\n}\n","import { cn } from '@comfyorg/tailwind-utils'\n\nconst sharedButtonClasses = cn(\n 'inline-flex items-center justify-center border-0 bg-transparent text-inherit transition-colors duration-150 ease-in-out ',\n 'hover:bg-node-component-surface-hovered active:bg-node-component-surface-selected',\n 'disabled:bg-node-component-disabled disabled:text-node-icon-disabled disabled:cursor-not-allowed'\n)\n\nexport function useNumberWidgetButtonPt(options?: {\n roundedLeft?: boolean\n roundedRight?: boolean\n}) {\n const { roundedLeft = false, roundedRight = false } = options ?? {}\n\n const increment = cn(sharedButtonClasses, roundedRight && 'rounded-r-lg')\n const decrement = cn(sharedButtonClasses, roundedLeft && 'rounded-l-lg')\n\n return {\n incrementButton: {\n class: increment\n },\n decrementButton: {\n class: decrement\n }\n }\n}\n","<template>\n <WidgetLayoutField :widget=\"widget\">\n <div :class=\"cn(WidgetInputBaseClass, 'flex items-center gap-2 pl-3 pr-2')\">\n <Slider\n :model-value=\"[modelValue]\"\n v-bind=\"filteredProps\"\n class=\"flex-grow text-xs\"\n :step=\"stepValue\"\n :aria-label=\"widget.name\"\n @update:model-value=\"updateLocalValue\"\n />\n <InputNumber\n :key=\"timesEmptied\"\n :model-value=\"modelValue\"\n v-bind=\"filteredProps\"\n :step=\"stepValue\"\n :min-fraction-digits=\"precision\"\n :max-fraction-digits=\"precision\"\n :aria-label=\"widget.name\"\n size=\"small\"\n pt:pc-input-text:root=\"min-w-[4ch] bg-transparent border-none text-center truncate\"\n class=\"w-16\"\n :pt=\"sliderNumberPt\"\n @update:model-value=\"handleNumberInputUpdate\"\n />\n </div>\n </WidgetLayoutField>\n</template>\n\n<script setup lang=\"ts\">\nimport InputNumber from 'primevue/inputnumber'\nimport { computed, ref } from 'vue'\n\nimport Slider from '@/components/ui/slider/Slider.vue'\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\nimport { cn } from '@/utils/tailwindUtil'\nimport {\n STANDARD_EXCLUDED_PROPS,\n filterWidgetProps\n} from '@/utils/widgetPropFilter'\n\nimport { useNumberStepCalculation } from '../composables/useNumberStepCalculation'\nimport { useNumberWidgetButtonPt } from '../composables/useNumberWidgetButtonPt'\nimport { WidgetInputBaseClass } from './layout'\nimport WidgetLayoutField from './layout/WidgetLayoutField.vue'\n\nconst { widget } = defineProps<{\n widget: SimplifiedWidget<number>\n}>()\n\nconst modelValue = defineModel<number>({ default: 0 })\n\nconst timesEmptied = ref(0)\n\nconst updateLocalValue = (newValue: number[] | undefined): void => {\n if (newValue?.length) modelValue.value = newValue[0]\n}\n\nconst handleNumberInputUpdate = (newValue: number | undefined) => {\n if (newValue !== undefined) {\n updateLocalValue([newValue])\n return\n }\n timesEmptied.value += 1\n}\n\nconst filteredProps = computed(() =>\n filterWidgetProps(widget.options, STANDARD_EXCLUDED_PROPS)\n)\n\nconst p = widget.options?.precision\nconst precision = typeof p === 'number' && p >= 0 ? p : undefined\n\n// Calculate the step value based on precision or widget options\nconst stepValue = useNumberStepCalculation(widget.options, precision, true)\n\nconst sliderNumberPt = useNumberWidgetButtonPt({\n roundedLeft: true,\n roundedRight: true\n})\n</script>\n\n<style scoped>\n:deep(.p-inputnumber-button.p-disabled .pi),\n:deep(.p-inputnumber-button.p-disabled .p-icon) {\n color: var(--color-node-icon-disabled) !important;\n}\n</style>\n","<script setup lang=\"ts\">\nimport { computed } from 'vue'\n\nimport type {\n SimplifiedControlWidget,\n SimplifiedWidget\n} from '@/types/simplifiedWidget'\n\nimport WidgetInputNumberInput from './WidgetInputNumberInput.vue'\nimport WidgetInputNumberSlider from './WidgetInputNumberSlider.vue'\nimport WidgetWithControl from './WidgetWithControl.vue'\n\nconst props = defineProps<{\n widget: SimplifiedWidget<number>\n}>()\n\nconst modelValue = defineModel<number>({ default: 0 })\n\nconst hasControlAfterGenerate = computed(() => {\n return !!props.widget.controlWidget\n})\n</script>\n\n<template>\n <WidgetWithControl\n v-if=\"hasControlAfterGenerate\"\n v-model=\"modelValue\"\n :widget=\"widget as SimplifiedControlWidget<number>\"\n :component=\"\n widget.type === 'slider'\n ? WidgetInputNumberSlider\n : WidgetInputNumberInput\n \"\n />\n <component\n :is=\"\n widget.type === 'slider'\n ? WidgetInputNumberSlider\n : WidgetInputNumberInput\n \"\n v-else\n v-model=\"modelValue\"\n :widget=\"widget\"\n v-bind=\"$attrs\"\n />\n</template>\n"],"names":["props","__props","modelValue","_useModel","filteredProps","computed","filterWidgetProps","INPUT_EXCLUDED_PROPS","precision","p","stepValue","step","useGrouping","buttonsDisabled","currentValue","buttonTooltip","useNumberStepCalculation","options","precisionArg","returnUndefinedForDefault","toValue","calculatedStep","__name","sharedButtonClasses","cn","useNumberWidgetButtonPt","roundedLeft","roundedRight","increment","decrement","timesEmptied","ref","updateLocalValue","newValue","handleNumberInputUpdate","STANDARD_EXCLUDED_PROPS","sliderNumberPt","hasControlAfterGenerate"],"mappings":"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"}
|
comfyui_frontend_package/static/assets/{WidgetInputText-Cv8Z1_b9.js → WidgetInputText-Btor0Uhs.js}
RENAMED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{e as i}from"./vendor-primevue-
|
|
2
|
-
//# sourceMappingURL=WidgetInputText-
|
|
1
|
+
import{e as i}from"./vendor-primevue-DeKsC2uk.js";import{c as d}from"./index--yK73oka.js";import{f as p,I as u}from"./widgetPropFilter-CygYoMQt.js";import{W as n}from"./index-Hz5b30sA.js";import{_ as f}from"./WidgetLayoutField.vue_vue_type_script_setup_true_lang-Bq1noASf.js";import{bx as c,cM as g,cN as w,E as V,j as x,d as P,k as _,z as b,by as e,m as C}from"./vendor-other-B8t_Wf2K.js";import"./vendor-vue-DaLZjKA7.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-DH0o8VQ7.js";import"./vendor-tiptap-VxK0yxkd.js";const z=c({__name:"WidgetInputText",props:g({widget:{}},{modelValue:{default:""},modelModifiers:{}}),emits:["update:modelValue"],setup(t){const l=t,a=w(t,"modelValue"),r=V(()=>p(l.widget.options,u));return(o,s)=>(P(),x(f,{widget:o.widget},{default:_(()=>[b(e(i),C({modelValue:a.value,"onUpdate:modelValue":s[0]||(s[0]=m=>a.value=m)},r.value,{class:e(d)(e(n),"w-full text-xs py-2 px-4"),"aria-label":o.widget.name,size:"small",pt:{root:"truncate min-w-[4ch]"}}),null,16,["modelValue","class","aria-label"])]),_:1},8,["widget"]))}});export{z as default};
|
|
2
|
+
//# sourceMappingURL=WidgetInputText-Btor0Uhs.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WidgetInputText-
|
|
1
|
+
{"version":3,"file":"WidgetInputText-Btor0Uhs.js","sources":["../../src/renderer/extensions/vueNodes/widgets/components/WidgetInputText.vue"],"sourcesContent":["<template>\n <WidgetLayoutField :widget=\"widget\">\n <InputText\n v-model=\"modelValue\"\n v-bind=\"filteredProps\"\n :class=\"cn(WidgetInputBaseClass, 'w-full text-xs py-2 px-4')\"\n :aria-label=\"widget.name\"\n size=\"small\"\n :pt=\"{ root: 'truncate min-w-[4ch]' }\"\n />\n </WidgetLayoutField>\n</template>\n\n<script setup lang=\"ts\">\nimport InputText from 'primevue/inputtext'\nimport { computed } from 'vue'\n\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\nimport { cn } from '@/utils/tailwindUtil'\nimport {\n INPUT_EXCLUDED_PROPS,\n filterWidgetProps\n} from '@/utils/widgetPropFilter'\n\nimport { WidgetInputBaseClass } from './layout'\nimport WidgetLayoutField from './layout/WidgetLayoutField.vue'\n\nconst props = defineProps<{\n widget: SimplifiedWidget<string>\n}>()\n\nconst modelValue = defineModel<string>({ default: '' })\n\nconst filteredProps = computed(() =>\n filterWidgetProps(props.widget.options, INPUT_EXCLUDED_PROPS)\n)\n</script>\n"],"names":["props","__props","modelValue","_useModel","filteredProps","computed","filterWidgetProps","INPUT_EXCLUDED_PROPS"],"mappings":"2pBA2BA,MAAMA,EAAQC,EAIRC,EAAaC,EAAmBF,EAAA,YAAgB,EAEhDG,EAAgBC,EAAS,IAC7BC,EAAkBN,EAAM,OAAO,QAASO,CAAoB,CAAA"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{bx as l,i as u,c as o,d as s,q as i,e as r,by as a,F as m,A as g,u as p,I as n,s as c,p as f}from"./vendor-other-B8t_Wf2K.js";import{c as w}from"./index
|
|
2
|
-
//# sourceMappingURL=WidgetLayoutField.vue_vue_type_script_setup_true_lang-
|
|
1
|
+
import{bx as l,i as u,c as o,d as s,q as i,e as r,by as a,F as m,A as g,u as p,I as n,s as c,p as f}from"./vendor-other-B8t_Wf2K.js";import{c as w}from"./index--yK73oka.js";const y={class:"grid grid-cols-subgrid min-w-0 justify-between gap-1 text-node-component-slot-text"},b={key:0,class:"truncate content-center-safe"},h={class:"relative min-w-0 flex-1"},_=l({__name:"WidgetLayoutField",props:{widget:{}},setup(v){const d=u("hideLayoutField",!1);return(t,e)=>(s(),o("div",y,[a(d)?i("",!0):(s(),o("div",b,[t.widget.name?(s(),o(m,{key:0},[g(p(t.widget.label||t.widget.name),1)],64)):i("",!0)])),r("div",h,[r("div",{class:c(a(w)("cursor-default min-w-0 rounded-lg focus-within:ring focus-within:ring-component-node-widget-background-highlighted transition-all",t.widget.borderStyle)),onPointerdown:e[0]||(e[0]=n(()=>{},["stop"])),onPointermove:e[1]||(e[1]=n(()=>{},["stop"])),onPointerup:e[2]||(e[2]=n(()=>{},["stop"]))},[f(t.$slots,"default")],34)])]))}});export{_};
|
|
2
|
+
//# sourceMappingURL=WidgetLayoutField.vue_vue_type_script_setup_true_lang-Bq1noASf.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WidgetLayoutField.vue_vue_type_script_setup_true_lang-
|
|
1
|
+
{"version":3,"file":"WidgetLayoutField.vue_vue_type_script_setup_true_lang-Bq1noASf.js","sources":["../../src/renderer/extensions/vueNodes/widgets/components/layout/WidgetLayoutField.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport { inject } from 'vue'\n\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\nimport { cn } from '@/utils/tailwindUtil'\n\ndefineProps<{\n widget: Pick<\n SimplifiedWidget<string | number | undefined>,\n 'name' | 'label' | 'borderStyle'\n >\n}>()\n\nconst hideLayoutField = inject<boolean>('hideLayoutField', false)\n</script>\n\n<template>\n <div\n class=\"grid grid-cols-subgrid min-w-0 justify-between gap-1 text-node-component-slot-text\"\n >\n <div v-if=\"!hideLayoutField\" class=\"truncate content-center-safe\">\n <template v-if=\"widget.name\">\n {{ widget.label || widget.name }}\n </template>\n </div>\n <!-- basis-full grow -->\n <div class=\"relative min-w-0 flex-1\">\n <div\n :class=\"\n cn(\n 'cursor-default min-w-0 rounded-lg focus-within:ring focus-within:ring-component-node-widget-background-highlighted transition-all',\n widget.borderStyle\n )\n \"\n @pointerdown.stop\n @pointermove.stop\n @pointerup.stop\n >\n <slot />\n </div>\n </div>\n </div>\n</template>\n"],"names":["hideLayoutField","inject"],"mappings":"gaAaA,MAAMA,EAAkBC,EAAgB,kBAAmB,EAAK"}
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import{a$ as o}from"./index--yK73oka.js";import"./vendor-primevue-DeKsC2uk.js";import"./vendor-other-B8t_Wf2K.js";import"./vendor-vue-DaLZjKA7.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-DH0o8VQ7.js";import"./vendor-tiptap-VxK0yxkd.js";export{o as default};
|
|
2
|
+
//# sourceMappingURL=WidgetLegacy-Cj4T7tN3.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"WidgetLegacy-Cj4T7tN3.js","sources":[],"sourcesContent":[],"names":[],"mappings":""}
|
comfyui_frontend_package/static/assets/{WidgetMarkdown-C4CnxNoM.js → WidgetMarkdown-CsRRMdeD.js}
RENAMED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
var p=Object.defineProperty;var s=(t,a)=>p(t,"name",{value:a,configurable:!0});import{bx as c,cM as v,cN as w,r,E as g,c as k,d as b,e as M,l as V,s as y,v as $,z as x,I as i,by as B,n as h}from"./vendor-other-B8t_Wf2K.js";import{
|
|
2
|
-
//# sourceMappingURL=WidgetMarkdown-
|
|
1
|
+
var p=Object.defineProperty;var s=(t,a)=>p(t,"name",{value:a,configurable:!0});import{bx as c,cM as v,cN as w,r,E as g,c as k,d as b,e as M,l as V,s as y,v as $,z as x,I as i,by as B,n as h}from"./vendor-other-B8t_Wf2K.js";import{aa as z}from"./vendor-primevue-DeKsC2uk.js";import{bn as E}from"./index--yK73oka.js";import"./vendor-vue-DaLZjKA7.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-DH0o8VQ7.js";import"./vendor-tiptap-VxK0yxkd.js";const H=["innerHTML"],S=c({__name:"WidgetMarkdown",props:v({widget:{}},{modelValue:{default:""},modelModifiers:{}}),emits:["update:modelValue"],setup(t){const a=w(t,"modelValue"),l=r(!1),n=r(),d=g(()=>E(a.value||"")),u=s(async()=>{l.value||t.widget.options?.read_only||(l.value=!0,await h(),n.value?.$el?.focus())},"startEditing"),m=s(()=>{l.value=!1},"handleBlur");return(o,e)=>(b(),k("div",{class:"widget-markdown relative w-full",onDblclick:u},[M("div",{class:y(["comfy-markdown-content size-full min-h-[60px] overflow-y-auto rounded-lg text-sm",l.value===!1?"visible":"invisible"]),innerHTML:d.value},null,10,H),V(x(B(z),{ref_key:"textareaRef",ref:n,modelValue:a.value,"onUpdate:modelValue":e[0]||(e[0]=f=>a.value=f),"aria-label":`${o.$t("g.edit")} ${o.widget.name||o.$t("g.markdown")} ${o.$t("g.content")}`,class:"absolute inset-0 min-h-[60px] w-full resize-none",pt:{root:{class:"text-sm w-full h-full",onBlur:m}},"data-capture-wheel":"true",onClick:e[1]||(e[1]=i(()=>{},["stop"])),onKeydown:e[2]||(e[2]=i(()=>{},["stop"]))},null,8,["modelValue","aria-label","pt"]),[[$,l.value]])],32))}});export{S as default};
|
|
2
|
+
//# sourceMappingURL=WidgetMarkdown-CsRRMdeD.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WidgetMarkdown-
|
|
1
|
+
{"version":3,"file":"WidgetMarkdown-CsRRMdeD.js","sources":["../../src/renderer/extensions/vueNodes/widgets/components/WidgetMarkdown.vue"],"sourcesContent":["<template>\n <div class=\"widget-markdown relative w-full\" @dblclick=\"startEditing\">\n <!-- Display mode: Rendered markdown -->\n <div\n class=\"comfy-markdown-content size-full min-h-[60px] overflow-y-auto rounded-lg text-sm\"\n :class=\"isEditing === false ? 'visible' : 'invisible'\"\n v-html=\"renderedHtml\"\n />\n\n <!-- Edit mode: Textarea -->\n <Textarea\n v-show=\"isEditing\"\n ref=\"textareaRef\"\n v-model=\"modelValue\"\n :aria-label=\"`${$t('g.edit')} ${widget.name || $t('g.markdown')} ${$t('g.content')}`\"\n class=\"absolute inset-0 min-h-[60px] w-full resize-none\"\n :pt=\"{\n root: {\n class: 'text-sm w-full h-full',\n onBlur: handleBlur\n }\n }\"\n data-capture-wheel=\"true\"\n @click.stop\n @keydown.stop\n />\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport Textarea from 'primevue/textarea'\nimport { computed, nextTick, ref } from 'vue'\n\nimport type { SimplifiedWidget } from '@/types/simplifiedWidget'\nimport { renderMarkdownToHtml } from '@/utils/markdownRendererUtil'\n\nconst { widget } = defineProps<{\n widget: SimplifiedWidget<string>\n}>()\n\nconst modelValue = defineModel<string>({ default: '' })\n\n// State\nconst isEditing = ref(false)\nconst textareaRef = ref<InstanceType<typeof Textarea> | undefined>()\n\n// Computed\nconst renderedHtml = computed(() => {\n return renderMarkdownToHtml(modelValue.value || '')\n})\n\n// Methods\nconst startEditing = async () => {\n if (isEditing.value || widget.options?.read_only) return\n\n isEditing.value = true\n await nextTick()\n\n // Focus the textarea\n // @ts-expect-error - $el is an internal property of the Textarea component\n textareaRef.value?.$el?.focus()\n}\n\nconst handleBlur = () => {\n isEditing.value = false\n}\n</script>\n"],"names":["modelValue","_useModel","__props","isEditing","ref","textareaRef","renderedHtml","computed","renderMarkdownToHtml","startEditing","__name","nextTick","handleBlur"],"mappings":"+lBAwCA,MAAMA,EAAaC,EAAmBC,EAAA,YAAgB,EAGhDC,EAAYC,EAAI,EAAK,EACrBC,EAAcD,EAAA,EAGdE,EAAeC,EAAS,IACrBC,EAAqBR,EAAW,OAAS,EAAE,CACnD,EAGKS,EAAeC,EAAA,SAAY,CAC3BP,EAAU,OAASD,EAAA,OAAO,SAAS,YAEvCC,EAAU,MAAQ,GAClB,MAAMQ,EAAA,EAINN,EAAY,OAAO,KAAK,MAAA,EAC1B,EATqB,gBAWfO,EAAaF,EAAA,IAAM,CACvBP,EAAU,MAAQ,EACpB,EAFmB"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
var $=Object.defineProperty;var a=(i,l)=>$(i,"name",{value:l,configurable:!0});import{bk as G,c as b,d as k,e as h,r as v,n as K,cd as F,eG as J,bx as Q,cM as X,de as Y,E as N,cN as Z,o as ee,q as U,z as q,k as ae,A as te,u as V,by as n,F as ne,y as oe,G as le}from"./vendor-other-B8t_Wf2K.js";import{r as D,t as R,f as H}from"./index
|
|
2
|
-
//# sourceMappingURL=WidgetRecordAudio-
|
|
1
|
+
var $=Object.defineProperty;var a=(i,l)=>$(i,"name",{value:l,configurable:!0});import{bk as G,c as b,d as k,e as h,r as v,n as K,cd as F,eG as J,bx as Q,cM as X,de as Y,E as N,cN as Z,o as ee,q as U,z as q,k as ae,A as te,u as V,by as n,F as ne,y as oe,G as le}from"./vendor-other-B8t_Wf2K.js";import{r as D,t as R,f as H}from"./index--yK73oka.js";import{u as O}from"./audioService-jRjL5LtP.js";import{f as re}from"./audioUtils-DsaLmBXU.js";import{a3 as ie}from"./vendor-primevue-DeKsC2uk.js";import"./vendor-vue-DaLZjKA7.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-DH0o8VQ7.js";import"./vendor-tiptap-VxK0yxkd.js";const ue={viewBox:"0 0 24 24",width:"1.2em",height:"1.2em"};function se(i,l){return k(),b("svg",ue,[...l[0]||(l[0]=[h("g",{fill:"none",stroke:"currentColor","stroke-linecap":"round","stroke-linejoin":"round","stroke-width":"2"},[h("path",{d:"M12 19v3m7-12v2a7 7 0 0 1-14 0v-2"}),h("rect",{width:"6",height:"13",x:"9",y:"2",rx:"3"})],-1)])])}a(se,"render");const ce=G({name:"lucide-mic",render:se});function de(i,l={}){const o=v(!1),f=v(0),u=v(null);async function e(){if(!i.value)return!1;try{return await i.value.play(),o.value=!0,!0}catch(A){return console.warn("Audio playback failed:",A),o.value=!1,!1}}a(e,"play");function t(){i.value&&(i.value.pause(),i.value.currentTime=0),o.value=!1,l.onPlaybackEnded&&l.onPlaybackEnded()}a(t,"stop");function s(){o.value=!1,l.onPlaybackEnded&&l.onPlaybackEnded()}a(s,"onPlaybackEnded");function g(){i.value?.duration&&l.onMetadataLoaded&&l.onMetadataLoaded(i.value.duration)}a(g,"onMetadataLoaded");async function p(){f.value+=1,await K()}a(p,"resetAudioElement");function r(){return i.value?.currentTime||0}a(r,"getCurrentTime");function y(){return i.value?.duration||0}return a(y,"getDuration"),{isPlaying:o,audioElementKey:f,play:e,stop:t,onPlaybackEnded:s,onMetadataLoaded:g,resetAudioElement:p,getCurrentTime:r,getDuration:y,playbackTimerInterval:u}}a(de,"useAudioPlayback");function ve(i={}){const l=v(!1),o=v(null),f=v([]),u=v(null),e=v(null);async function t(){try{e.value?.startsWith("blob:")&&URL.revokeObjectURL(e.value),f.value=[],e.value=null,await O().registerWavEncoder(),u.value=await navigator.mediaDevices.getUserMedia({audio:!0}),o.value=new J(u.value,{mimeType:"audio/wav"}),o.value.ondataavailable=r=>{f.value.push(r.data)},o.value.onstop=async()=>{const r=new Blob(f.value,{type:"audio/wav"});e.value?.startsWith("blob:")&&URL.revokeObjectURL(e.value),e.value=URL.createObjectURL(r),i.onRecordingComplete&&await i.onRecordingComplete(r),g()},o.value.start(100),l.value=!0}catch(r){throw i.onError&&i.onError(r),r}}a(t,"startRecording");function s(){o.value&&o.value.state!=="inactive"?o.value.stop():g()}a(s,"stopRecording");function g(){l.value=!1,u.value&&(u.value.getTracks().forEach(r=>r.stop()),u.value=null)}a(g,"cleanup");function p(){s(),e.value&&(URL.revokeObjectURL(e.value),e.value=null)}return a(p,"dispose"),F(()=>{p()}),{isRecording:l,recordedURL:e,mediaRecorder:o,startRecording:t,stopRecording:s,dispose:p}}a(ve,"useAudioRecorder");function me(i={}){const{barCount:l=18,minHeight:o=4,maxHeight:f=32}=i,u=v(Array.from({length:l},()=>({height:16}))),e=v(null),t=v(null),s=v(null),g=v(null),p=v(null);function r(){u.value=Array.from({length:l},()=>({height:Math.random()*(f-o)+o}))}a(r,"initWaveform");function y(m){m.value&&(t.value&&s.value?A():w(),g.value=requestAnimationFrame(()=>y(m)))}a(y,"updateWaveform");function A(){if(!t.value||!s.value)return;t.value.getByteFrequencyData(s.value);const m=Math.floor(s.value.length/l);u.value=u.value.map((L,I)=>{let S=0;for(let P=0;P<m;P++)S+=s.value[I*m+P]||0;return{height:S/m/255*(f-o)+o}})}a(A,"updateWaveformFromAudio");function w(){u.value=u.value.map(m=>({height:Math.max(o,Math.min(f,m.height+(Math.random()-.5)*4))}))}a(w,"updateWaveformRandom");async function W(){e.value&&e.value.state!=="closed"&&await e.value.close(),e.value=null,p.value=null}a(W,"setupAudioContext");async function E(m){e.value=new window.AudioContext,t.value=e.value.createAnalyser(),e.value.createMediaStreamSource(m).connect(t.value),t.value.fftSize=256,s.value=new Uint8Array(t.value.frequencyBinCount)}a(E,"setupRecordingVisualization");async function C(m){return e.value&&e.value.state!=="closed"&&await e.value.close(),p.value=null,m?(e.value=new window.AudioContext,t.value=e.value.createAnalyser(),p.value=e.value.createMediaElementSource(m),p.value.connect(t.value),t.value.connect(e.value.destination),t.value.fftSize=256,s.value=new Uint8Array(t.value.frequencyBinCount),!0):!1}a(C,"setupPlaybackVisualization");function T(){g.value&&(cancelAnimationFrame(g.value),g.value=null)}a(T,"stopWaveform");function z(){T(),e.value&&e.value.state!=="closed"&&e.value.close(),e.value=null,p.value=null}return a(z,"dispose"),F(()=>{z()}),{waveformBars:u,initWaveform:r,updateWaveform:y,setupAudioContext:W,setupRecordingVisualization:E,setupPlaybackVisualization:C,stopWaveform:T,dispose:z}}a(me,"useAudioWaveform");const fe={class:"relative"},pe={class:"mb-4"},ge={key:0,class:"flex h-14 w-full items-center gap-4 rounded-lg px-4 bg-node-component-surface text-text-secondary"},ye={class:"flex min-w-30 items-center gap-2"},he={class:"min-w-20 text-xs"},be={class:"min-w-10 text-sm"},ke={class:"flex h-8 flex-1 items-center gap-2 overflow-x-clip"},we=["title"],xe=["title"],Re=["title"],_e=["title"],Ae=["src"],Be=Q({__name:"WidgetRecordAudio",props:X({readonly:{type:Boolean},nodeId:{}},{modelValue:{default:""},modelModifiers:{}}),emits:["update:modelValue"],setup(i){const l=i,o=v();let f="";const u=ve({onRecordingComplete:z,onError:a(()=>{H().addAlert(R("g.micPermissionDenied")||"Microphone permission denied")},"onError")}),e=me({barCount:18,minHeight:4,maxHeight:32}),t=de(o,{onPlaybackEnded:B,onMetadataLoaded:a(d=>{!w.value&&!r.value&&(s.value=Math.floor(d))},"onMetadataLoaded")}),s=v(0),{pause:g,resume:p}=Y(()=>{s.value+=1},1e3,{immediate:!1}),{isRecording:r,recordedURL:y}=u,{waveformBars:A}=e,{isPlaying:w,audioElementKey:W}=t,E=N(()=>r.value||w.value),C=Z(i,"modelValue"),T=N(()=>!l.nodeId||!D.canvas.graph?null:D.canvas.graph.getNodeById(l.nodeId));async function z(d){try{const c=await O().convertBlobToFileAndSubmit(d);C.value=c,f=c}catch{H().addAlert("Failed to upload recorded audio")}}a(z,"handleRecordingComplete");async function m(){if(!l.readonly)try{if(await e.setupAudioContext(),await u.startRecording(),u.mediaRecorder.value){const d=u.mediaRecorder.value.stream;d&&await e.setupRecordingVisualization(d)}s.value=0,p(),e.initWaveform(),e.updateWaveform(E)}catch(d){console.error("Failed to start recording:",d)}}a(m,"handleStartRecording");function L(){u.stopRecording(),g(),e.stopWaveform()}a(L,"handleStopRecording");async function I(){if(!y.value||(s.value=0,await t.resetAudioElement(),await new Promise(_=>setTimeout(_,50)),!o.value)||!await e.setupPlaybackVisualization(o.value))return;await t.play(),e.initWaveform(),e.updateWaveform(E);const c=setInterval(()=>{s.value=Math.floor(t.getCurrentTime())},100);t.playbackTimerInterval.value=c}a(I,"handlePlayRecording");function S(){t.stop(),B()}a(S,"handleStopPlayback");function B(){e.stopWaveform(),t.playbackTimerInterval.value!==null&&(clearInterval(t.playbackTimerInterval.value),t.playbackTimerInterval.value=null);const d=t.getDuration();d?s.value=Math.floor(d):s.value=0}a(B,"handlePlaybackEnded");async function j(){return r.value&&u.mediaRecorder.value&&(u.mediaRecorder.value.stop(),await new Promise((d,c)=>{let _=0;const x=50,M=a(()=>{!r.value&&C.value?d(void 0):++_>=x?c(new Error("Recording serialization timeout after 5 seconds")):setTimeout(M,100)},"checkRecording");M()})),C.value||f||""}a(j,"serializeValue");function P(){const d=T.value;if(!d?.widgets)return;const c=d.widgets.find(_=>_.name==="audio");c&&(c.serializeValue=j)}return a(P,"registerWidgetSerialization"),ee(()=>{e.initWaveform(),P()}),F(()=>{t.playbackTimerInterval.value!==null&&(clearInterval(t.playbackTimerInterval.value),t.playbackTimerInterval.value=null)}),(d,c)=>{const _=ce;return k(),b("div",fe,[h("div",pe,[q(n(ie),{class:"text-base-foreground w-full border-0 bg-secondary-background hover:bg-secondary-background-hover",disabled:n(r)||d.readonly,onClick:m},{default:ae(()=>[te(V(n(R)("g.startRecording","Start Recording"))+" ",1),q(_,{class:"ml-1"})]),_:1},8,["disabled"])]),n(r)||n(w)||n(y)?(k(),b("div",ge,[h("div",ye,[h("span",he,V(n(r)?n(R)("g.listening","Listening..."):n(w)?n(R)("g.playing","Playing..."):n(y)?n(R)("g.ready","Ready"):""),1),h("span",be,V(n(re)(s.value)),1)]),h("div",ke,[(k(!0),b(ne,null,oe(n(A),(x,M)=>(k(),b("div",{key:M,class:"max-h-8 min-h-1 w-0.75 rounded-[1.5px] bg-slate-100 transition-all duration-100",style:le({height:x.height+"px"}),title:`Bar ${M+1}: ${x.height}px`},null,12,we))),128))]),n(r)?(k(),b("button",{key:0,title:n(R)("g.stopRecording","Stop Recording"),class:"flex size-8 animate-pulse items-center justify-center rounded-full border-0 bg-smoke-500/33 transition-colors",onClick:L},c[2]||(c[2]=[h("div",{class:"size-2.5 rounded-sm bg-danger-100"},null,-1)]),8,xe)):!n(r)&&n(y)&&!n(w)?(k(),b("button",{key:1,title:n(R)("g.playRecording")||"Play Recording",class:"flex size-8 items-center justify-center rounded-full border-0 bg-smoke-500/33 transition-colors",onClick:I},c[3]||(c[3]=[h("i",{class:"text-text-secondary icon-[lucide--play] size-4"},null,-1)]),8,Re)):n(w)?(k(),b("button",{key:2,title:n(R)("g.stopPlayback")||"Stop Playback",class:"flex size-8 items-center justify-center rounded-full border-0 bg-smoke-500/33 transition-colors",onClick:S},c[4]||(c[4]=[h("i",{class:"text-text-secondary icon-[lucide--square] size-4"},null,-1)]),8,_e)):U("",!0)])):U("",!0),n(y)?(k(),b("audio",{ref_key:"audioRef",ref:o,key:n(W),src:n(y),class:"hidden",onEnded:c[0]||(c[0]=(...x)=>n(t).onPlaybackEnded&&n(t).onPlaybackEnded(...x)),onLoadedmetadata:c[1]||(c[1]=(...x)=>n(t).onMetadataLoaded&&n(t).onMetadataLoaded(...x))},null,40,Ae)):U("",!0)])}}});export{Be as default};
|
|
2
|
+
//# sourceMappingURL=WidgetRecordAudio-CbCqPJqI.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WidgetRecordAudio-BQ9yATXo.js","sources":["../../src/renderer/extensions/vueNodes/widgets/composables/audio/useAudioPlayback.ts","../../src/renderer/extensions/vueNodes/widgets/composables/audio/useAudioRecorder.ts","../../src/renderer/extensions/vueNodes/widgets/composables/audio/useAudioWaveform.ts","../../src/renderer/extensions/vueNodes/widgets/components/WidgetRecordAudio.vue"],"sourcesContent":["import { nextTick, ref } from 'vue'\nimport type { Ref } from 'vue'\n\ninterface AudioPlaybackOptions {\n onPlaybackEnded?: () => void\n onMetadataLoaded?: (duration: number) => void\n}\n\nexport function useAudioPlayback(\n audioRef: Ref<HTMLAudioElement | undefined>,\n options: AudioPlaybackOptions = {}\n) {\n const isPlaying = ref(false)\n const audioElementKey = ref(0)\n const playbackTimerInterval = ref<ReturnType<typeof setInterval> | null>(null)\n\n async function play() {\n if (!audioRef.value) return false\n\n try {\n await audioRef.value.play()\n isPlaying.value = true\n return true\n } catch (error) {\n console.warn('Audio playback failed:', error)\n isPlaying.value = false\n return false\n }\n }\n\n function stop() {\n if (audioRef.value) {\n audioRef.value.pause()\n audioRef.value.currentTime = 0\n }\n isPlaying.value = false\n if (options.onPlaybackEnded) {\n options.onPlaybackEnded()\n }\n }\n\n function onPlaybackEnded() {\n isPlaying.value = false\n if (options.onPlaybackEnded) {\n options.onPlaybackEnded()\n }\n }\n\n function onMetadataLoaded() {\n if (audioRef.value?.duration && options.onMetadataLoaded) {\n options.onMetadataLoaded(audioRef.value.duration)\n }\n }\n\n async function resetAudioElement() {\n audioElementKey.value += 1\n await nextTick()\n }\n\n function getCurrentTime() {\n return audioRef.value?.currentTime || 0\n }\n\n function getDuration() {\n return audioRef.value?.duration || 0\n }\n\n return {\n isPlaying,\n audioElementKey,\n play,\n stop,\n onPlaybackEnded,\n onMetadataLoaded,\n resetAudioElement,\n getCurrentTime,\n getDuration,\n playbackTimerInterval\n }\n}\n","import { MediaRecorder as ExtendableMediaRecorder } from 'extendable-media-recorder'\nimport { onUnmounted, ref } from 'vue'\n\nimport { useAudioService } from '@/services/audioService'\n\ninterface AudioRecorderOptions {\n onRecordingComplete?: (audioBlob: Blob) => Promise<void>\n onError?: (error: Error) => void\n}\n\nexport function useAudioRecorder(options: AudioRecorderOptions = {}) {\n const isRecording = ref(false)\n const mediaRecorder = ref<MediaRecorder | null>(null)\n const audioChunks = ref<Blob[]>([])\n const stream = ref<MediaStream | null>(null)\n const recordedURL = ref<string | null>(null)\n\n async function startRecording() {\n try {\n // Clean up previous recording\n if (recordedURL.value?.startsWith('blob:')) {\n URL.revokeObjectURL(recordedURL.value)\n }\n\n // Initialize\n audioChunks.value = []\n recordedURL.value = null\n\n // Register wav encoder and get media stream\n await useAudioService().registerWavEncoder()\n stream.value = await navigator.mediaDevices.getUserMedia({ audio: true })\n\n // Create media recorder\n mediaRecorder.value = new ExtendableMediaRecorder(stream.value, {\n mimeType: 'audio/wav'\n }) as unknown as MediaRecorder\n\n mediaRecorder.value.ondataavailable = (e) => {\n audioChunks.value.push(e.data)\n }\n\n mediaRecorder.value.onstop = async () => {\n const blob = new Blob(audioChunks.value, { type: 'audio/wav' })\n\n // Create blob URL for preview\n if (recordedURL.value?.startsWith('blob:')) {\n URL.revokeObjectURL(recordedURL.value)\n }\n recordedURL.value = URL.createObjectURL(blob)\n\n // Notify completion\n if (options.onRecordingComplete) {\n await options.onRecordingComplete(blob)\n }\n\n cleanup()\n }\n\n // Start recording\n mediaRecorder.value.start(100)\n isRecording.value = true\n } catch (err) {\n if (options.onError) {\n options.onError(err as Error)\n }\n throw err\n }\n }\n\n function stopRecording() {\n if (mediaRecorder.value && mediaRecorder.value.state !== 'inactive') {\n mediaRecorder.value.stop()\n } else {\n cleanup()\n }\n }\n\n function cleanup() {\n isRecording.value = false\n\n if (stream.value) {\n stream.value.getTracks().forEach((track) => track.stop())\n stream.value = null\n }\n }\n\n function dispose() {\n stopRecording()\n if (recordedURL.value) {\n URL.revokeObjectURL(recordedURL.value)\n recordedURL.value = null\n }\n }\n\n onUnmounted(() => {\n dispose()\n })\n\n return {\n isRecording,\n recordedURL,\n mediaRecorder,\n startRecording,\n stopRecording,\n dispose\n }\n}\n","import { onUnmounted, ref } from 'vue'\nimport type { Ref } from 'vue'\n\ninterface WaveformBar {\n height: number\n}\n\ninterface AudioWaveformOptions {\n barCount?: number\n minHeight?: number\n maxHeight?: number\n}\n\nexport function useAudioWaveform(options: AudioWaveformOptions = {}) {\n const { barCount = 18, minHeight = 4, maxHeight = 32 } = options\n\n const waveformBars = ref<WaveformBar[]>(\n Array.from({ length: barCount }, () => ({ height: 16 }))\n )\n const audioContext = ref<AudioContext | null>(null)\n const analyser = ref<AnalyserNode | null>(null)\n const dataArray = ref<Uint8Array | null>(null)\n const animationId = ref<number | null>(null)\n const mediaElementSource = ref<MediaElementAudioSourceNode | null>(null)\n\n function initWaveform() {\n waveformBars.value = Array.from({ length: barCount }, () => ({\n height: Math.random() * (maxHeight - minHeight) + minHeight\n }))\n }\n\n function updateWaveform(isActive: Ref<boolean>) {\n if (!isActive.value) return\n\n if (analyser.value && dataArray.value) {\n updateWaveformFromAudio()\n } else {\n updateWaveformRandom()\n }\n\n animationId.value = requestAnimationFrame(() => updateWaveform(isActive))\n }\n\n function updateWaveformFromAudio() {\n if (!analyser.value || !dataArray.value) return\n\n analyser.value.getByteFrequencyData(\n dataArray.value as Uint8Array<ArrayBuffer>\n )\n const samplesPerBar = Math.floor(dataArray.value.length / barCount)\n\n waveformBars.value = waveformBars.value.map((_, i) => {\n let sum = 0\n for (let j = 0; j < samplesPerBar; j++) {\n sum += dataArray.value![i * samplesPerBar + j] || 0\n }\n const average = sum / samplesPerBar\n const normalizedHeight =\n (average / 255) * (maxHeight - minHeight) + minHeight\n return { height: normalizedHeight }\n })\n }\n\n function updateWaveformRandom() {\n waveformBars.value = waveformBars.value.map((bar) => ({\n height: Math.max(\n minHeight,\n Math.min(maxHeight, bar.height + (Math.random() - 0.5) * 4)\n )\n }))\n }\n\n async function setupAudioContext() {\n if (audioContext.value && audioContext.value.state !== 'closed') {\n await audioContext.value.close()\n }\n audioContext.value = null\n mediaElementSource.value = null\n }\n\n async function setupRecordingVisualization(stream: MediaStream) {\n audioContext.value = new window.AudioContext()\n analyser.value = audioContext.value.createAnalyser()\n const source = audioContext.value.createMediaStreamSource(stream)\n source.connect(analyser.value)\n\n analyser.value.fftSize = 256\n dataArray.value = new Uint8Array(analyser.value.frequencyBinCount)\n }\n\n async function setupPlaybackVisualization(audioElement: HTMLAudioElement) {\n if (audioContext.value && audioContext.value.state !== 'closed') {\n await audioContext.value.close()\n }\n\n mediaElementSource.value = null\n\n if (!audioElement) return false\n\n audioContext.value = new window.AudioContext()\n analyser.value = audioContext.value.createAnalyser()\n\n mediaElementSource.value =\n audioContext.value.createMediaElementSource(audioElement)\n\n mediaElementSource.value.connect(analyser.value)\n analyser.value.connect(audioContext.value.destination)\n\n analyser.value.fftSize = 256\n dataArray.value = new Uint8Array(analyser.value.frequencyBinCount)\n\n return true\n }\n\n function stopWaveform() {\n if (animationId.value) {\n cancelAnimationFrame(animationId.value)\n animationId.value = null\n }\n }\n\n function dispose() {\n stopWaveform()\n if (audioContext.value && audioContext.value.state !== 'closed') {\n void audioContext.value.close()\n }\n audioContext.value = null\n mediaElementSource.value = null\n }\n\n onUnmounted(() => {\n dispose()\n })\n\n return {\n waveformBars,\n initWaveform,\n updateWaveform,\n setupAudioContext,\n setupRecordingVisualization,\n setupPlaybackVisualization,\n stopWaveform,\n dispose\n }\n}\n","<template>\n <div class=\"relative\">\n <div class=\"mb-4\">\n <Button\n class=\"text-base-foreground w-full border-0 bg-secondary-background hover:bg-secondary-background-hover\"\n :disabled=\"isRecording || readonly\"\n @click=\"handleStartRecording\"\n >\n {{ t('g.startRecording', 'Start Recording') }}\n <i-lucide:mic class=\"ml-1\" />\n </Button>\n </div>\n <div\n v-if=\"isRecording || isPlaying || recordedURL\"\n class=\"flex h-14 w-full items-center gap-4 rounded-lg px-4 bg-node-component-surface text-text-secondary\"\n >\n <!-- Recording Status -->\n <div class=\"flex min-w-30 items-center gap-2\">\n <span class=\"min-w-20 text-xs\">\n {{\n isRecording\n ? t('g.listening', 'Listening...')\n : isPlaying\n ? t('g.playing', 'Playing...')\n : recordedURL\n ? t('g.ready', 'Ready')\n : ''\n }}\n </span>\n <span class=\"min-w-10 text-sm\">{{ formatTime(timer) }}</span>\n </div>\n\n <!-- Waveform Visualization -->\n <div class=\"flex h-8 flex-1 items-center gap-2 overflow-x-clip\">\n <div\n v-for=\"(bar, index) in waveformBars\"\n :key=\"index\"\n class=\"max-h-8 min-h-1 w-0.75 rounded-[1.5px] bg-slate-100 transition-all duration-100\"\n :style=\"{ height: bar.height + 'px' }\"\n :title=\"`Bar ${index + 1}: ${bar.height}px`\"\n />\n </div>\n\n <!-- Control Button -->\n <button\n v-if=\"isRecording\"\n :title=\"t('g.stopRecording', 'Stop Recording')\"\n class=\"flex size-8 animate-pulse items-center justify-center rounded-full border-0 bg-smoke-500/33 transition-colors\"\n @click=\"handleStopRecording\"\n >\n <div class=\"size-2.5 rounded-sm bg-danger-100\" />\n </button>\n\n <button\n v-else-if=\"!isRecording && recordedURL && !isPlaying\"\n :title=\"t('g.playRecording') || 'Play Recording'\"\n class=\"flex size-8 items-center justify-center rounded-full border-0 bg-smoke-500/33 transition-colors\"\n @click=\"handlePlayRecording\"\n >\n <i class=\"text-text-secondary icon-[lucide--play] size-4\" />\n </button>\n\n <button\n v-else-if=\"isPlaying\"\n :title=\"t('g.stopPlayback') || 'Stop Playback'\"\n class=\"flex size-8 items-center justify-center rounded-full border-0 bg-smoke-500/33 transition-colors\"\n @click=\"handleStopPlayback\"\n >\n <i class=\"text-text-secondary icon-[lucide--square] size-4\" />\n </button>\n </div>\n <audio\n v-if=\"recordedURL\"\n ref=\"audioRef\"\n :key=\"audioElementKey\"\n :src=\"recordedURL\"\n class=\"hidden\"\n @ended=\"playback.onPlaybackEnded\"\n @loadedmetadata=\"playback.onMetadataLoaded\"\n />\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { useIntervalFn } from '@vueuse/core'\nimport { Button } from 'primevue'\nimport { computed, onMounted, onUnmounted, ref } from 'vue'\n\nimport { t } from '@/i18n'\nimport type { LGraphNode } from '@/lib/litegraph/src/LGraphNode'\nimport type { IBaseWidget } from '@/lib/litegraph/src/types/widgets'\nimport { useToastStore } from '@/platform/updates/common/toastStore'\nimport { app } from '@/scripts/app'\nimport { useAudioService } from '@/services/audioService'\n\nimport { useAudioPlayback } from '../composables/audio/useAudioPlayback'\nimport { useAudioRecorder } from '../composables/audio/useAudioRecorder'\nimport { useAudioWaveform } from '../composables/audio/useAudioWaveform'\nimport { formatTime } from '../utils/audioUtils'\n\nconst props = defineProps<{\n readonly?: boolean\n nodeId: string\n}>()\n\n// Audio element ref\nconst audioRef = ref<HTMLAudioElement>()\n\n// Keep track of the last uploaded path as a backup\nlet lastUploadedPath = ''\n\n// Composables\nconst recorder = useAudioRecorder({\n onRecordingComplete: handleRecordingComplete,\n onError: () => {\n useToastStore().addAlert(\n t('g.micPermissionDenied') || 'Microphone permission denied'\n )\n }\n})\n\nconst waveform = useAudioWaveform({\n barCount: 18,\n minHeight: 4,\n maxHeight: 32\n})\n\nconst playback = useAudioPlayback(audioRef, {\n onPlaybackEnded: handlePlaybackEnded,\n onMetadataLoaded: (duration) => {\n if (!isPlaying.value && !isRecording.value) {\n timer.value = Math.floor(duration)\n }\n }\n})\n\n// Timer for recording\nconst timer = ref(0)\nconst { pause: pauseTimer, resume: resumeTimer } = useIntervalFn(\n () => {\n timer.value += 1\n },\n 1000,\n { immediate: false }\n)\n\n// Destructure for template access\nconst { isRecording, recordedURL } = recorder\nconst { waveformBars } = waveform\nconst { isPlaying, audioElementKey } = playback\n\n// Computed for waveform animation\nconst isWaveformActive = computed(() => isRecording.value || isPlaying.value)\n\nconst modelValue = defineModel<string>({ default: '' })\n\nconst litegraphNode = computed(() => {\n if (!props.nodeId || !app.canvas.graph) return null\n return app.canvas.graph.getNodeById(props.nodeId) as LGraphNode | null\n})\n\nasync function handleRecordingComplete(blob: Blob) {\n try {\n const path = await useAudioService().convertBlobToFileAndSubmit(blob)\n modelValue.value = path\n lastUploadedPath = path\n } catch (e) {\n useToastStore().addAlert('Failed to upload recorded audio')\n }\n}\n\nasync function handleStartRecording() {\n if (props.readonly) return\n\n try {\n await waveform.setupAudioContext()\n await recorder.startRecording()\n\n // Setup waveform visualization for recording\n if (recorder.mediaRecorder.value) {\n const stream = recorder.mediaRecorder.value.stream\n if (stream) {\n await waveform.setupRecordingVisualization(stream)\n }\n }\n\n // Start timer\n timer.value = 0\n resumeTimer()\n waveform.initWaveform()\n waveform.updateWaveform(isWaveformActive)\n } catch (err) {\n console.error('Failed to start recording:', err)\n }\n}\n\nfunction handleStopRecording() {\n recorder.stopRecording()\n pauseTimer()\n waveform.stopWaveform()\n}\n\nasync function handlePlayRecording() {\n if (!recordedURL.value) return\n\n // Reset timer\n timer.value = 0\n\n // Reset and setup audio element\n await playback.resetAudioElement()\n\n // Wait for audio element to be ready\n await new Promise((resolve) => setTimeout(resolve, 50))\n\n if (!audioRef.value) return\n\n // Setup waveform visualization for playback\n const setupSuccess = await waveform.setupPlaybackVisualization(audioRef.value)\n if (!setupSuccess) return\n\n // Start playback\n await playback.play()\n\n // Update waveform\n waveform.initWaveform()\n waveform.updateWaveform(isWaveformActive)\n\n // Update timer from audio current time\n const timerInterval = setInterval(() => {\n timer.value = Math.floor(playback.getCurrentTime())\n }, 100)\n\n // Store interval for cleanup\n playback.playbackTimerInterval.value = timerInterval\n}\n\nfunction handleStopPlayback() {\n playback.stop()\n handlePlaybackEnded()\n}\n\nfunction handlePlaybackEnded() {\n waveform.stopWaveform()\n\n // Clear playback timer interval\n if (playback.playbackTimerInterval.value !== null) {\n clearInterval(playback.playbackTimerInterval.value)\n playback.playbackTimerInterval.value = null\n }\n\n const duration = playback.getDuration()\n if (duration) {\n timer.value = Math.floor(duration)\n } else {\n timer.value = 0\n }\n}\n\n// Serialization function for workflow execution\nasync function serializeValue() {\n if (isRecording.value && recorder.mediaRecorder.value) {\n recorder.mediaRecorder.value.stop()\n\n await new Promise((resolve, reject) => {\n let attempts = 0\n const maxAttempts = 50 // 5 seconds max (50 * 100ms)\n const checkRecording = () => {\n if (!isRecording.value && modelValue.value) {\n resolve(undefined)\n } else if (++attempts >= maxAttempts) {\n reject(new Error('Recording serialization timeout after 5 seconds'))\n } else {\n setTimeout(checkRecording, 100)\n }\n }\n checkRecording()\n })\n }\n\n return modelValue.value || lastUploadedPath || ''\n}\n\nfunction registerWidgetSerialization() {\n const node = litegraphNode.value\n if (!node?.widgets) return\n const targetWidget = node.widgets.find((w: IBaseWidget) => w.name === 'audio')\n if (targetWidget) {\n targetWidget.serializeValue = serializeValue\n }\n}\n\nonMounted(() => {\n waveform.initWaveform()\n registerWidgetSerialization()\n})\n\nonUnmounted(() => {\n if (playback.playbackTimerInterval.value !== null) {\n clearInterval(playback.playbackTimerInterval.value)\n playback.playbackTimerInterval.value = null\n }\n})\n</script>\n"],"names":["useAudioPlayback","audioRef","options","isPlaying","ref","audioElementKey","playbackTimerInterval","play","error","__name","stop","onPlaybackEnded","onMetadataLoaded","resetAudioElement","nextTick","getCurrentTime","getDuration","useAudioRecorder","isRecording","mediaRecorder","audioChunks","stream","recordedURL","startRecording","useAudioService","ExtendableMediaRecorder","e","blob","cleanup","err","stopRecording","track","dispose","onUnmounted","useAudioWaveform","barCount","minHeight","maxHeight","waveformBars","audioContext","analyser","dataArray","animationId","mediaElementSource","initWaveform","updateWaveform","isActive","updateWaveformFromAudio","updateWaveformRandom","samplesPerBar","_","i","sum","j","bar","setupAudioContext","setupRecordingVisualization","setupPlaybackVisualization","audioElement","stopWaveform","props","__props","lastUploadedPath","recorder","handleRecordingComplete","useToastStore","t","waveform","playback","handlePlaybackEnded","duration","timer","pauseTimer","resumeTimer","useIntervalFn","isWaveformActive","computed","modelValue","_useModel","litegraphNode","app","path","handleStartRecording","handleStopRecording","handlePlayRecording","resolve","timerInterval","handleStopPlayback","serializeValue","reject","attempts","maxAttempts","checkRecording","registerWidgetSerialization","node","targetWidget","w","onMounted"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"WidgetRecordAudio-CbCqPJqI.js","sources":["../../src/renderer/extensions/vueNodes/widgets/composables/audio/useAudioPlayback.ts","../../src/renderer/extensions/vueNodes/widgets/composables/audio/useAudioRecorder.ts","../../src/renderer/extensions/vueNodes/widgets/composables/audio/useAudioWaveform.ts","../../src/renderer/extensions/vueNodes/widgets/components/WidgetRecordAudio.vue"],"sourcesContent":["import { nextTick, ref } from 'vue'\nimport type { Ref } from 'vue'\n\ninterface AudioPlaybackOptions {\n onPlaybackEnded?: () => void\n onMetadataLoaded?: (duration: number) => void\n}\n\nexport function useAudioPlayback(\n audioRef: Ref<HTMLAudioElement | undefined>,\n options: AudioPlaybackOptions = {}\n) {\n const isPlaying = ref(false)\n const audioElementKey = ref(0)\n const playbackTimerInterval = ref<ReturnType<typeof setInterval> | null>(null)\n\n async function play() {\n if (!audioRef.value) return false\n\n try {\n await audioRef.value.play()\n isPlaying.value = true\n return true\n } catch (error) {\n console.warn('Audio playback failed:', error)\n isPlaying.value = false\n return false\n }\n }\n\n function stop() {\n if (audioRef.value) {\n audioRef.value.pause()\n audioRef.value.currentTime = 0\n }\n isPlaying.value = false\n if (options.onPlaybackEnded) {\n options.onPlaybackEnded()\n }\n }\n\n function onPlaybackEnded() {\n isPlaying.value = false\n if (options.onPlaybackEnded) {\n options.onPlaybackEnded()\n }\n }\n\n function onMetadataLoaded() {\n if (audioRef.value?.duration && options.onMetadataLoaded) {\n options.onMetadataLoaded(audioRef.value.duration)\n }\n }\n\n async function resetAudioElement() {\n audioElementKey.value += 1\n await nextTick()\n }\n\n function getCurrentTime() {\n return audioRef.value?.currentTime || 0\n }\n\n function getDuration() {\n return audioRef.value?.duration || 0\n }\n\n return {\n isPlaying,\n audioElementKey,\n play,\n stop,\n onPlaybackEnded,\n onMetadataLoaded,\n resetAudioElement,\n getCurrentTime,\n getDuration,\n playbackTimerInterval\n }\n}\n","import { MediaRecorder as ExtendableMediaRecorder } from 'extendable-media-recorder'\nimport { onUnmounted, ref } from 'vue'\n\nimport { useAudioService } from '@/services/audioService'\n\ninterface AudioRecorderOptions {\n onRecordingComplete?: (audioBlob: Blob) => Promise<void>\n onError?: (error: Error) => void\n}\n\nexport function useAudioRecorder(options: AudioRecorderOptions = {}) {\n const isRecording = ref(false)\n const mediaRecorder = ref<MediaRecorder | null>(null)\n const audioChunks = ref<Blob[]>([])\n const stream = ref<MediaStream | null>(null)\n const recordedURL = ref<string | null>(null)\n\n async function startRecording() {\n try {\n // Clean up previous recording\n if (recordedURL.value?.startsWith('blob:')) {\n URL.revokeObjectURL(recordedURL.value)\n }\n\n // Initialize\n audioChunks.value = []\n recordedURL.value = null\n\n // Register wav encoder and get media stream\n await useAudioService().registerWavEncoder()\n stream.value = await navigator.mediaDevices.getUserMedia({ audio: true })\n\n // Create media recorder\n mediaRecorder.value = new ExtendableMediaRecorder(stream.value, {\n mimeType: 'audio/wav'\n }) as unknown as MediaRecorder\n\n mediaRecorder.value.ondataavailable = (e) => {\n audioChunks.value.push(e.data)\n }\n\n mediaRecorder.value.onstop = async () => {\n const blob = new Blob(audioChunks.value, { type: 'audio/wav' })\n\n // Create blob URL for preview\n if (recordedURL.value?.startsWith('blob:')) {\n URL.revokeObjectURL(recordedURL.value)\n }\n recordedURL.value = URL.createObjectURL(blob)\n\n // Notify completion\n if (options.onRecordingComplete) {\n await options.onRecordingComplete(blob)\n }\n\n cleanup()\n }\n\n // Start recording\n mediaRecorder.value.start(100)\n isRecording.value = true\n } catch (err) {\n if (options.onError) {\n options.onError(err as Error)\n }\n throw err\n }\n }\n\n function stopRecording() {\n if (mediaRecorder.value && mediaRecorder.value.state !== 'inactive') {\n mediaRecorder.value.stop()\n } else {\n cleanup()\n }\n }\n\n function cleanup() {\n isRecording.value = false\n\n if (stream.value) {\n stream.value.getTracks().forEach((track) => track.stop())\n stream.value = null\n }\n }\n\n function dispose() {\n stopRecording()\n if (recordedURL.value) {\n URL.revokeObjectURL(recordedURL.value)\n recordedURL.value = null\n }\n }\n\n onUnmounted(() => {\n dispose()\n })\n\n return {\n isRecording,\n recordedURL,\n mediaRecorder,\n startRecording,\n stopRecording,\n dispose\n }\n}\n","import { onUnmounted, ref } from 'vue'\nimport type { Ref } from 'vue'\n\ninterface WaveformBar {\n height: number\n}\n\ninterface AudioWaveformOptions {\n barCount?: number\n minHeight?: number\n maxHeight?: number\n}\n\nexport function useAudioWaveform(options: AudioWaveformOptions = {}) {\n const { barCount = 18, minHeight = 4, maxHeight = 32 } = options\n\n const waveformBars = ref<WaveformBar[]>(\n Array.from({ length: barCount }, () => ({ height: 16 }))\n )\n const audioContext = ref<AudioContext | null>(null)\n const analyser = ref<AnalyserNode | null>(null)\n const dataArray = ref<Uint8Array | null>(null)\n const animationId = ref<number | null>(null)\n const mediaElementSource = ref<MediaElementAudioSourceNode | null>(null)\n\n function initWaveform() {\n waveformBars.value = Array.from({ length: barCount }, () => ({\n height: Math.random() * (maxHeight - minHeight) + minHeight\n }))\n }\n\n function updateWaveform(isActive: Ref<boolean>) {\n if (!isActive.value) return\n\n if (analyser.value && dataArray.value) {\n updateWaveformFromAudio()\n } else {\n updateWaveformRandom()\n }\n\n animationId.value = requestAnimationFrame(() => updateWaveform(isActive))\n }\n\n function updateWaveformFromAudio() {\n if (!analyser.value || !dataArray.value) return\n\n analyser.value.getByteFrequencyData(\n dataArray.value as Uint8Array<ArrayBuffer>\n )\n const samplesPerBar = Math.floor(dataArray.value.length / barCount)\n\n waveformBars.value = waveformBars.value.map((_, i) => {\n let sum = 0\n for (let j = 0; j < samplesPerBar; j++) {\n sum += dataArray.value![i * samplesPerBar + j] || 0\n }\n const average = sum / samplesPerBar\n const normalizedHeight =\n (average / 255) * (maxHeight - minHeight) + minHeight\n return { height: normalizedHeight }\n })\n }\n\n function updateWaveformRandom() {\n waveformBars.value = waveformBars.value.map((bar) => ({\n height: Math.max(\n minHeight,\n Math.min(maxHeight, bar.height + (Math.random() - 0.5) * 4)\n )\n }))\n }\n\n async function setupAudioContext() {\n if (audioContext.value && audioContext.value.state !== 'closed') {\n await audioContext.value.close()\n }\n audioContext.value = null\n mediaElementSource.value = null\n }\n\n async function setupRecordingVisualization(stream: MediaStream) {\n audioContext.value = new window.AudioContext()\n analyser.value = audioContext.value.createAnalyser()\n const source = audioContext.value.createMediaStreamSource(stream)\n source.connect(analyser.value)\n\n analyser.value.fftSize = 256\n dataArray.value = new Uint8Array(analyser.value.frequencyBinCount)\n }\n\n async function setupPlaybackVisualization(audioElement: HTMLAudioElement) {\n if (audioContext.value && audioContext.value.state !== 'closed') {\n await audioContext.value.close()\n }\n\n mediaElementSource.value = null\n\n if (!audioElement) return false\n\n audioContext.value = new window.AudioContext()\n analyser.value = audioContext.value.createAnalyser()\n\n mediaElementSource.value =\n audioContext.value.createMediaElementSource(audioElement)\n\n mediaElementSource.value.connect(analyser.value)\n analyser.value.connect(audioContext.value.destination)\n\n analyser.value.fftSize = 256\n dataArray.value = new Uint8Array(analyser.value.frequencyBinCount)\n\n return true\n }\n\n function stopWaveform() {\n if (animationId.value) {\n cancelAnimationFrame(animationId.value)\n animationId.value = null\n }\n }\n\n function dispose() {\n stopWaveform()\n if (audioContext.value && audioContext.value.state !== 'closed') {\n void audioContext.value.close()\n }\n audioContext.value = null\n mediaElementSource.value = null\n }\n\n onUnmounted(() => {\n dispose()\n })\n\n return {\n waveformBars,\n initWaveform,\n updateWaveform,\n setupAudioContext,\n setupRecordingVisualization,\n setupPlaybackVisualization,\n stopWaveform,\n dispose\n }\n}\n","<template>\n <div class=\"relative\">\n <div class=\"mb-4\">\n <Button\n class=\"text-base-foreground w-full border-0 bg-secondary-background hover:bg-secondary-background-hover\"\n :disabled=\"isRecording || readonly\"\n @click=\"handleStartRecording\"\n >\n {{ t('g.startRecording', 'Start Recording') }}\n <i-lucide:mic class=\"ml-1\" />\n </Button>\n </div>\n <div\n v-if=\"isRecording || isPlaying || recordedURL\"\n class=\"flex h-14 w-full items-center gap-4 rounded-lg px-4 bg-node-component-surface text-text-secondary\"\n >\n <!-- Recording Status -->\n <div class=\"flex min-w-30 items-center gap-2\">\n <span class=\"min-w-20 text-xs\">\n {{\n isRecording\n ? t('g.listening', 'Listening...')\n : isPlaying\n ? t('g.playing', 'Playing...')\n : recordedURL\n ? t('g.ready', 'Ready')\n : ''\n }}\n </span>\n <span class=\"min-w-10 text-sm\">{{ formatTime(timer) }}</span>\n </div>\n\n <!-- Waveform Visualization -->\n <div class=\"flex h-8 flex-1 items-center gap-2 overflow-x-clip\">\n <div\n v-for=\"(bar, index) in waveformBars\"\n :key=\"index\"\n class=\"max-h-8 min-h-1 w-0.75 rounded-[1.5px] bg-slate-100 transition-all duration-100\"\n :style=\"{ height: bar.height + 'px' }\"\n :title=\"`Bar ${index + 1}: ${bar.height}px`\"\n />\n </div>\n\n <!-- Control Button -->\n <button\n v-if=\"isRecording\"\n :title=\"t('g.stopRecording', 'Stop Recording')\"\n class=\"flex size-8 animate-pulse items-center justify-center rounded-full border-0 bg-smoke-500/33 transition-colors\"\n @click=\"handleStopRecording\"\n >\n <div class=\"size-2.5 rounded-sm bg-danger-100\" />\n </button>\n\n <button\n v-else-if=\"!isRecording && recordedURL && !isPlaying\"\n :title=\"t('g.playRecording') || 'Play Recording'\"\n class=\"flex size-8 items-center justify-center rounded-full border-0 bg-smoke-500/33 transition-colors\"\n @click=\"handlePlayRecording\"\n >\n <i class=\"text-text-secondary icon-[lucide--play] size-4\" />\n </button>\n\n <button\n v-else-if=\"isPlaying\"\n :title=\"t('g.stopPlayback') || 'Stop Playback'\"\n class=\"flex size-8 items-center justify-center rounded-full border-0 bg-smoke-500/33 transition-colors\"\n @click=\"handleStopPlayback\"\n >\n <i class=\"text-text-secondary icon-[lucide--square] size-4\" />\n </button>\n </div>\n <audio\n v-if=\"recordedURL\"\n ref=\"audioRef\"\n :key=\"audioElementKey\"\n :src=\"recordedURL\"\n class=\"hidden\"\n @ended=\"playback.onPlaybackEnded\"\n @loadedmetadata=\"playback.onMetadataLoaded\"\n />\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { useIntervalFn } from '@vueuse/core'\nimport { Button } from 'primevue'\nimport { computed, onMounted, onUnmounted, ref } from 'vue'\n\nimport { t } from '@/i18n'\nimport type { LGraphNode } from '@/lib/litegraph/src/LGraphNode'\nimport type { IBaseWidget } from '@/lib/litegraph/src/types/widgets'\nimport { useToastStore } from '@/platform/updates/common/toastStore'\nimport { app } from '@/scripts/app'\nimport { useAudioService } from '@/services/audioService'\n\nimport { useAudioPlayback } from '../composables/audio/useAudioPlayback'\nimport { useAudioRecorder } from '../composables/audio/useAudioRecorder'\nimport { useAudioWaveform } from '../composables/audio/useAudioWaveform'\nimport { formatTime } from '../utils/audioUtils'\n\nconst props = defineProps<{\n readonly?: boolean\n nodeId: string\n}>()\n\n// Audio element ref\nconst audioRef = ref<HTMLAudioElement>()\n\n// Keep track of the last uploaded path as a backup\nlet lastUploadedPath = ''\n\n// Composables\nconst recorder = useAudioRecorder({\n onRecordingComplete: handleRecordingComplete,\n onError: () => {\n useToastStore().addAlert(\n t('g.micPermissionDenied') || 'Microphone permission denied'\n )\n }\n})\n\nconst waveform = useAudioWaveform({\n barCount: 18,\n minHeight: 4,\n maxHeight: 32\n})\n\nconst playback = useAudioPlayback(audioRef, {\n onPlaybackEnded: handlePlaybackEnded,\n onMetadataLoaded: (duration) => {\n if (!isPlaying.value && !isRecording.value) {\n timer.value = Math.floor(duration)\n }\n }\n})\n\n// Timer for recording\nconst timer = ref(0)\nconst { pause: pauseTimer, resume: resumeTimer } = useIntervalFn(\n () => {\n timer.value += 1\n },\n 1000,\n { immediate: false }\n)\n\n// Destructure for template access\nconst { isRecording, recordedURL } = recorder\nconst { waveformBars } = waveform\nconst { isPlaying, audioElementKey } = playback\n\n// Computed for waveform animation\nconst isWaveformActive = computed(() => isRecording.value || isPlaying.value)\n\nconst modelValue = defineModel<string>({ default: '' })\n\nconst litegraphNode = computed(() => {\n if (!props.nodeId || !app.canvas.graph) return null\n return app.canvas.graph.getNodeById(props.nodeId) as LGraphNode | null\n})\n\nasync function handleRecordingComplete(blob: Blob) {\n try {\n const path = await useAudioService().convertBlobToFileAndSubmit(blob)\n modelValue.value = path\n lastUploadedPath = path\n } catch (e) {\n useToastStore().addAlert('Failed to upload recorded audio')\n }\n}\n\nasync function handleStartRecording() {\n if (props.readonly) return\n\n try {\n await waveform.setupAudioContext()\n await recorder.startRecording()\n\n // Setup waveform visualization for recording\n if (recorder.mediaRecorder.value) {\n const stream = recorder.mediaRecorder.value.stream\n if (stream) {\n await waveform.setupRecordingVisualization(stream)\n }\n }\n\n // Start timer\n timer.value = 0\n resumeTimer()\n waveform.initWaveform()\n waveform.updateWaveform(isWaveformActive)\n } catch (err) {\n console.error('Failed to start recording:', err)\n }\n}\n\nfunction handleStopRecording() {\n recorder.stopRecording()\n pauseTimer()\n waveform.stopWaveform()\n}\n\nasync function handlePlayRecording() {\n if (!recordedURL.value) return\n\n // Reset timer\n timer.value = 0\n\n // Reset and setup audio element\n await playback.resetAudioElement()\n\n // Wait for audio element to be ready\n await new Promise((resolve) => setTimeout(resolve, 50))\n\n if (!audioRef.value) return\n\n // Setup waveform visualization for playback\n const setupSuccess = await waveform.setupPlaybackVisualization(audioRef.value)\n if (!setupSuccess) return\n\n // Start playback\n await playback.play()\n\n // Update waveform\n waveform.initWaveform()\n waveform.updateWaveform(isWaveformActive)\n\n // Update timer from audio current time\n const timerInterval = setInterval(() => {\n timer.value = Math.floor(playback.getCurrentTime())\n }, 100)\n\n // Store interval for cleanup\n playback.playbackTimerInterval.value = timerInterval\n}\n\nfunction handleStopPlayback() {\n playback.stop()\n handlePlaybackEnded()\n}\n\nfunction handlePlaybackEnded() {\n waveform.stopWaveform()\n\n // Clear playback timer interval\n if (playback.playbackTimerInterval.value !== null) {\n clearInterval(playback.playbackTimerInterval.value)\n playback.playbackTimerInterval.value = null\n }\n\n const duration = playback.getDuration()\n if (duration) {\n timer.value = Math.floor(duration)\n } else {\n timer.value = 0\n }\n}\n\n// Serialization function for workflow execution\nasync function serializeValue() {\n if (isRecording.value && recorder.mediaRecorder.value) {\n recorder.mediaRecorder.value.stop()\n\n await new Promise((resolve, reject) => {\n let attempts = 0\n const maxAttempts = 50 // 5 seconds max (50 * 100ms)\n const checkRecording = () => {\n if (!isRecording.value && modelValue.value) {\n resolve(undefined)\n } else if (++attempts >= maxAttempts) {\n reject(new Error('Recording serialization timeout after 5 seconds'))\n } else {\n setTimeout(checkRecording, 100)\n }\n }\n checkRecording()\n })\n }\n\n return modelValue.value || lastUploadedPath || ''\n}\n\nfunction registerWidgetSerialization() {\n const node = litegraphNode.value\n if (!node?.widgets) return\n const targetWidget = node.widgets.find((w: IBaseWidget) => w.name === 'audio')\n if (targetWidget) {\n targetWidget.serializeValue = serializeValue\n }\n}\n\nonMounted(() => {\n waveform.initWaveform()\n registerWidgetSerialization()\n})\n\nonUnmounted(() => {\n if (playback.playbackTimerInterval.value !== null) {\n clearInterval(playback.playbackTimerInterval.value)\n playback.playbackTimerInterval.value = null\n }\n})\n</script>\n"],"names":["useAudioPlayback","audioRef","options","isPlaying","ref","audioElementKey","playbackTimerInterval","play","error","__name","stop","onPlaybackEnded","onMetadataLoaded","resetAudioElement","nextTick","getCurrentTime","getDuration","useAudioRecorder","isRecording","mediaRecorder","audioChunks","stream","recordedURL","startRecording","useAudioService","ExtendableMediaRecorder","e","blob","cleanup","err","stopRecording","track","dispose","onUnmounted","useAudioWaveform","barCount","minHeight","maxHeight","waveformBars","audioContext","analyser","dataArray","animationId","mediaElementSource","initWaveform","updateWaveform","isActive","updateWaveformFromAudio","updateWaveformRandom","samplesPerBar","_","i","sum","j","bar","setupAudioContext","setupRecordingVisualization","setupPlaybackVisualization","audioElement","stopWaveform","props","__props","lastUploadedPath","recorder","handleRecordingComplete","useToastStore","t","waveform","playback","handlePlaybackEnded","duration","timer","pauseTimer","resumeTimer","useIntervalFn","isWaveformActive","computed","modelValue","_useModel","litegraphNode","app","path","handleStartRecording","handleStopRecording","handlePlayRecording","resolve","timerInterval","handleStopPlayback","serializeValue","reject","attempts","maxAttempts","checkRecording","registerWidgetSerialization","node","targetWidget","w","onMounted"],"mappings":"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"}
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import{_ as o}from"./WidgetSelect.vue_vue_type_script_setup_true_lang-B0Z0OQv6.js";import"./index--yK73oka.js";import"./vendor-primevue-DeKsC2uk.js";import"./vendor-other-B8t_Wf2K.js";import"./vendor-vue-DaLZjKA7.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-DH0o8VQ7.js";import"./vendor-tiptap-VxK0yxkd.js";import"./widgetPropFilter-CygYoMQt.js";import"./index-Hz5b30sA.js";import"./WidgetLayoutField.vue_vue_type_script_setup_true_lang-Bq1noASf.js";import"./LazyImage.vue_vue_type_script_setup_true_lang-Op4fug5d.js";import"./WidgetWithControl.vue_vue_type_script_setup_true_lang-Bx6suA2O.js";export{o as default};
|
|
2
|
+
//# sourceMappingURL=WidgetSelect-DcVQrOUl.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"WidgetSelect-DcVQrOUl.js","sources":[],"sourcesContent":[],"names":[],"mappings":""}
|