comfyui-frontend-package 1.37.3__py3-none-any.whl → 1.37.4__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-BwfERTOT.js +2 -0
- comfyui_frontend_package/static/assets/{AboutPanel-6wNn9DuA.js.map → AboutPanel-BwfERTOT.js.map} +1 -1
- comfyui_frontend_package/static/assets/{AudioPreviewPlayer-ybC6cXRM.js → AudioPreviewPlayer-DT9nrYD6.js} +2 -2
- comfyui_frontend_package/static/assets/{AudioPreviewPlayer-ybC6cXRM.js.map → AudioPreviewPlayer-DT9nrYD6.js.map} +1 -1
- comfyui_frontend_package/static/assets/ComfyQueueButton-DazIfwpa.js +2 -0
- comfyui_frontend_package/static/assets/{ComfyQueueButton-BbIk3ALi.js.map → ComfyQueueButton-DazIfwpa.js.map} +1 -1
- comfyui_frontend_package/static/assets/ExtensionPanel-D539Wx81.js +2 -0
- comfyui_frontend_package/static/assets/{ExtensionPanel-DYw7d35v.js.map → ExtensionPanel-D539Wx81.js.map} +1 -1
- comfyui_frontend_package/static/assets/GraphView-C_FQc1Au.js +16 -0
- comfyui_frontend_package/static/assets/GraphView-C_FQc1Au.js.map +1 -0
- comfyui_frontend_package/static/assets/{GraphView-DwAYVX4H.css → GraphView-Ck9hVEEV.css} +1 -1
- comfyui_frontend_package/static/assets/{KeybindingPanel-D0MD69FX.js → KeybindingPanel-Bj61UMoX.js} +2 -2
- comfyui_frontend_package/static/assets/{KeybindingPanel-D0MD69FX.js.map → KeybindingPanel-Bj61UMoX.js.map} +1 -1
- comfyui_frontend_package/static/assets/LazyImage.vue_vue_type_script_setup_true_lang-DyOiHvnA.js +2 -0
- comfyui_frontend_package/static/assets/LazyImage.vue_vue_type_script_setup_true_lang-DyOiHvnA.js.map +1 -0
- comfyui_frontend_package/static/assets/LegacyCreditsPanel-BNqPlgUn.js +2 -0
- comfyui_frontend_package/static/assets/{LegacyCreditsPanel-BMvul305.js.map → LegacyCreditsPanel-BNqPlgUn.js.map} +1 -1
- comfyui_frontend_package/static/assets/Load3D-CaNKqgIL.js +2 -0
- comfyui_frontend_package/static/assets/Load3D-CaNKqgIL.js.map +1 -0
- comfyui_frontend_package/static/assets/{Load3D.vue_vue_type_script_setup_true_lang-BtNou66j.js → Load3D.vue_vue_type_script_setup_true_lang-gf2aN2_8.js} +2 -2
- comfyui_frontend_package/static/assets/{Load3D.vue_vue_type_script_setup_true_lang-BtNou66j.js.map → Load3D.vue_vue_type_script_setup_true_lang-gf2aN2_8.js.map} +1 -1
- comfyui_frontend_package/static/assets/{Media3DBottom-Bk7TM-zH.js → Media3DBottom-D9M9b2ls.js} +2 -2
- comfyui_frontend_package/static/assets/{Media3DBottom-Bk7TM-zH.js.map → Media3DBottom-D9M9b2ls.js.map} +1 -1
- comfyui_frontend_package/static/assets/{Media3DTop-CIsQ4Ccc.js → Media3DTop-B-qNqlQF.js} +2 -2
- comfyui_frontend_package/static/assets/{Media3DTop-CIsQ4Ccc.js.map → Media3DTop-B-qNqlQF.js.map} +1 -1
- comfyui_frontend_package/static/assets/{MediaAudioBottom-CWxtJ5vP.js → MediaAudioBottom-d7EZ2Wx5.js} +2 -2
- comfyui_frontend_package/static/assets/{MediaAudioBottom-CWxtJ5vP.js.map → MediaAudioBottom-d7EZ2Wx5.js.map} +1 -1
- comfyui_frontend_package/static/assets/{MediaImageBottom-OWiMf_6W.js → MediaImageBottom-B-9SOOhn.js} +2 -2
- comfyui_frontend_package/static/assets/{MediaImageBottom-OWiMf_6W.js.map → MediaImageBottom-B-9SOOhn.js.map} +1 -1
- comfyui_frontend_package/static/assets/{MediaTitle.vue_vue_type_script_setup_true_lang-C59zAxW0.js → MediaTitle.vue_vue_type_script_setup_true_lang-DVzYM9UW.js} +2 -2
- comfyui_frontend_package/static/assets/{MediaTitle.vue_vue_type_script_setup_true_lang-C59zAxW0.js.map → MediaTitle.vue_vue_type_script_setup_true_lang-DVzYM9UW.js.map} +1 -1
- comfyui_frontend_package/static/assets/{MediaVideoBottom-OKuLWTbn.js → MediaVideoBottom-D6IR52ja.js} +2 -2
- comfyui_frontend_package/static/assets/{MediaVideoBottom-OKuLWTbn.js.map → MediaVideoBottom-D6IR52ja.js.map} +1 -1
- comfyui_frontend_package/static/assets/{ServerConfigPanel-5RPRkuvl.js → ServerConfigPanel-BBWOQ7ej.js} +2 -2
- comfyui_frontend_package/static/assets/{ServerConfigPanel-5RPRkuvl.js.map → ServerConfigPanel-BBWOQ7ej.js.map} +1 -1
- comfyui_frontend_package/static/assets/{SubscriptionRequiredDialogContent-CtCWM_jj.js → SubscriptionRequiredDialogContent-oUSDZGJZ.js} +2 -2
- comfyui_frontend_package/static/assets/{SubscriptionRequiredDialogContent-CtCWM_jj.js.map → SubscriptionRequiredDialogContent-oUSDZGJZ.js.map} +1 -1
- comfyui_frontend_package/static/assets/{UserPanel-CrxHTRQZ.js → UserPanel-Do_alb49.js} +2 -2
- comfyui_frontend_package/static/assets/{UserPanel-CrxHTRQZ.js.map → UserPanel-Do_alb49.js.map} +1 -1
- comfyui_frontend_package/static/assets/{UserSelectView-tu0lXAri.js → UserSelectView-DVJzD33o.js} +2 -2
- comfyui_frontend_package/static/assets/{UserSelectView-tu0lXAri.js.map → UserSelectView-DVJzD33o.js.map} +1 -1
- comfyui_frontend_package/static/assets/{ValueControlPopover-CgyNfIEw.js → ValueControlPopover-CZIsPw9J.js} +2 -2
- comfyui_frontend_package/static/assets/{ValueControlPopover-CgyNfIEw.js.map → ValueControlPopover-CZIsPw9J.js.map} +1 -1
- comfyui_frontend_package/static/assets/WidgetAudioUI-CbC597q0.js +2 -0
- comfyui_frontend_package/static/assets/{WidgetAudioUI-BZL35TlT.js.map → WidgetAudioUI-CbC597q0.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetButton-Dkge0J8R.js → WidgetButton-Df2ihQh6.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetButton-Dkge0J8R.js.map → WidgetButton-Df2ihQh6.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetColorPicker-vRHta_Kz.js → WidgetColorPicker-DgI8RjHJ.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetColorPicker-vRHta_Kz.js.map → WidgetColorPicker-DgI8RjHJ.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetGalleria-BoWBT6i_.js → WidgetGalleria-Cyz9lzP-.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetGalleria-BoWBT6i_.js.map → WidgetGalleria-Cyz9lzP-.js.map} +1 -1
- comfyui_frontend_package/static/assets/WidgetInputNumber-wD2uHC32.js +2 -0
- comfyui_frontend_package/static/assets/WidgetInputNumber-wD2uHC32.js.map +1 -0
- comfyui_frontend_package/static/assets/{WidgetInputNumber.vue_vue_type_script_setup_true_lang-aeh2Ot2n.js → WidgetInputNumber.vue_vue_type_script_setup_true_lang-XbRdxGIz.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetInputNumber.vue_vue_type_script_setup_true_lang-aeh2Ot2n.js.map → WidgetInputNumber.vue_vue_type_script_setup_true_lang-XbRdxGIz.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetInputText-BRV8PzCv.js → WidgetInputText-BR3C0fCV.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetInputText-BRV8PzCv.js.map → WidgetInputText-BR3C0fCV.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetLayoutField.vue_vue_type_script_setup_true_lang-Dps42A-g.js → WidgetLayoutField.vue_vue_type_script_setup_true_lang-CZj3E4v6.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetLayoutField.vue_vue_type_script_setup_true_lang-Dps42A-g.js.map → WidgetLayoutField.vue_vue_type_script_setup_true_lang-CZj3E4v6.js.map} +1 -1
- comfyui_frontend_package/static/assets/WidgetLegacy-CkV176Xm.js +2 -0
- comfyui_frontend_package/static/assets/WidgetLegacy-CkV176Xm.js.map +1 -0
- comfyui_frontend_package/static/assets/WidgetMarkdown-rM_UPCA-.js +2 -0
- comfyui_frontend_package/static/assets/{WidgetMarkdown-DIMd79hN.js.map → WidgetMarkdown-rM_UPCA-.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetRecordAudio-DwHSqiBz.js → WidgetRecordAudio-CLpvV8e9.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetRecordAudio-DwHSqiBz.js.map → WidgetRecordAudio-CLpvV8e9.js.map} +1 -1
- comfyui_frontend_package/static/assets/WidgetSelect-BwcPw-lE.js +2 -0
- comfyui_frontend_package/static/assets/WidgetSelect-BwcPw-lE.js.map +1 -0
- comfyui_frontend_package/static/assets/{WidgetSelect.vue_vue_type_script_setup_true_lang-CMg0GtSC.js → WidgetSelect.vue_vue_type_script_setup_true_lang-CITubFAk.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetSelect.vue_vue_type_script_setup_true_lang-CMg0GtSC.js.map → WidgetSelect.vue_vue_type_script_setup_true_lang-CITubFAk.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetTextarea-CZnqW4e_.js → WidgetTextarea-CwUMJ-23.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetTextarea-CZnqW4e_.js.map → WidgetTextarea-CwUMJ-23.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetToggleSwitch-DwYqmS17.js → WidgetToggleSwitch-DqQpfrDq.js} +2 -2
- comfyui_frontend_package/static/assets/{WidgetToggleSwitch-DwYqmS17.js.map → WidgetToggleSwitch-DqQpfrDq.js.map} +1 -1
- comfyui_frontend_package/static/assets/{WidgetWithControl.vue_vue_type_script_setup_true_lang-COy_p9Eh.js → WidgetWithControl.vue_vue_type_script_setup_true_lang-JSl33v3j.js} +3 -3
- comfyui_frontend_package/static/assets/{WidgetWithControl.vue_vue_type_script_setup_true_lang-COy_p9Eh.js.map → WidgetWithControl.vue_vue_type_script_setup_true_lang-JSl33v3j.js.map} +1 -1
- comfyui_frontend_package/static/assets/{audioService-Bh6LQBV8.js → audioService-DKN4T_Yr.js} +2 -2
- comfyui_frontend_package/static/assets/{audioService-Bh6LQBV8.js.map → audioService-DKN4T_Yr.js.map} +1 -1
- comfyui_frontend_package/static/assets/{audioUtils-DlA-QHPJ.js → audioUtils-WBbpBG9r.js} +2 -2
- comfyui_frontend_package/static/assets/{audioUtils-DlA-QHPJ.js.map → audioUtils-WBbpBG9r.js.map} +1 -1
- comfyui_frontend_package/static/assets/{commands-CHktpNSL.js → commands-CRVPkENB.js} +2 -2
- comfyui_frontend_package/static/assets/commands-CRVPkENB.js.map +1 -0
- comfyui_frontend_package/static/assets/{index-2-qFLlQP.js → index-CuKlxAeN.js} +30 -28
- comfyui_frontend_package/static/assets/index-CuKlxAeN.js.map +1 -0
- comfyui_frontend_package/static/assets/index-Cv1aHIoL.css +1 -0
- comfyui_frontend_package/static/assets/{index-_AAd9eTu.js → index-DEqR9lwu.js} +2 -2
- comfyui_frontend_package/static/assets/{index-_AAd9eTu.js.map → index-DEqR9lwu.js.map} +1 -1
- comfyui_frontend_package/static/assets/index-KizWjI6s.js +5 -0
- comfyui_frontend_package/static/assets/{index-DKofvZ3r.js.map → index-KizWjI6s.js.map} +1 -1
- comfyui_frontend_package/static/assets/{keybindingService-CWbdWLPI.js → keybindingService-O5KDQleT.js} +2 -2
- comfyui_frontend_package/static/assets/{keybindingService-CWbdWLPI.js.map → keybindingService-O5KDQleT.js.map} +1 -1
- comfyui_frontend_package/static/assets/main-10VBfKWj.js +14 -0
- comfyui_frontend_package/static/assets/main-10VBfKWj.js.map +1 -0
- comfyui_frontend_package/static/assets/nodeDefs-D9VHUZJt.js +53 -0
- comfyui_frontend_package/static/assets/nodeDefs-D9VHUZJt.js.map +1 -0
- comfyui_frontend_package/static/assets/{vendor-three-BKWXAgVe.js → vendor-three-29bN5sfh.js} +2 -2
- comfyui_frontend_package/static/assets/{vendor-three-BKWXAgVe.js.map → vendor-three-29bN5sfh.js.map} +1 -1
- comfyui_frontend_package/static/index.html +1 -1
- {comfyui_frontend_package-1.37.3.dist-info → comfyui_frontend_package-1.37.4.dist-info}/METADATA +1 -1
- {comfyui_frontend_package-1.37.3.dist-info → comfyui_frontend_package-1.37.4.dist-info}/RECORD +101 -101
- comfyui_frontend_package/static/assets/AboutPanel-6wNn9DuA.js +0 -2
- comfyui_frontend_package/static/assets/ComfyQueueButton-BbIk3ALi.js +0 -2
- comfyui_frontend_package/static/assets/ExtensionPanel-DYw7d35v.js +0 -2
- comfyui_frontend_package/static/assets/GraphView-CjDjhvN7.js +0 -16
- comfyui_frontend_package/static/assets/GraphView-CjDjhvN7.js.map +0 -1
- comfyui_frontend_package/static/assets/LazyImage.vue_vue_type_script_setup_true_lang-CcI-aYhS.js +0 -2
- comfyui_frontend_package/static/assets/LazyImage.vue_vue_type_script_setup_true_lang-CcI-aYhS.js.map +0 -1
- comfyui_frontend_package/static/assets/LegacyCreditsPanel-BMvul305.js +0 -2
- comfyui_frontend_package/static/assets/Load3D-BplYUML3.js +0 -2
- comfyui_frontend_package/static/assets/Load3D-BplYUML3.js.map +0 -1
- comfyui_frontend_package/static/assets/WidgetAudioUI-BZL35TlT.js +0 -2
- comfyui_frontend_package/static/assets/WidgetInputNumber-DMqIMaoH.js +0 -2
- comfyui_frontend_package/static/assets/WidgetInputNumber-DMqIMaoH.js.map +0 -1
- comfyui_frontend_package/static/assets/WidgetLegacy-BWDBwsli.js +0 -2
- comfyui_frontend_package/static/assets/WidgetLegacy-BWDBwsli.js.map +0 -1
- comfyui_frontend_package/static/assets/WidgetMarkdown-DIMd79hN.js +0 -2
- comfyui_frontend_package/static/assets/WidgetSelect-BOvzWMtV.js +0 -2
- comfyui_frontend_package/static/assets/WidgetSelect-BOvzWMtV.js.map +0 -1
- comfyui_frontend_package/static/assets/commands-CHktpNSL.js.map +0 -1
- comfyui_frontend_package/static/assets/index-2-qFLlQP.js.map +0 -1
- comfyui_frontend_package/static/assets/index-571Fkv7y.css +0 -1
- comfyui_frontend_package/static/assets/index-DKofvZ3r.js +0 -5
- comfyui_frontend_package/static/assets/main-DGOENlHZ.js +0 -14
- comfyui_frontend_package/static/assets/main-DGOENlHZ.js.map +0 -1
- comfyui_frontend_package/static/assets/nodeDefs-DtmuHPr3.js +0 -53
- comfyui_frontend_package/static/assets/nodeDefs-DtmuHPr3.js.map +0 -1
- {comfyui_frontend_package-1.37.3.dist-info → comfyui_frontend_package-1.37.4.dist-info}/WHEEL +0 -0
- {comfyui_frontend_package-1.37.3.dist-info → comfyui_frontend_package-1.37.4.dist-info}/top_level.txt +0 -0
comfyui_frontend_package/static/assets/{MediaAudioBottom-CWxtJ5vP.js → MediaAudioBottom-d7EZ2Wx5.js}
RENAMED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{
|
|
2
|
-
//# sourceMappingURL=MediaAudioBottom-
|
|
1
|
+
import{du as i,dn as n}from"./index-CuKlxAeN.js";import{_ as m}from"./MediaTitle.vue_vue_type_script_setup_true_lang-DVzYM9UW.js";import{bx as r,E as l,c as t,d as s,z as c,q as p,e as f,u as d,by as u}from"./vendor-other-CSX7WseZ.js";import"./vendor-primevue-B6rcS73U.js";import"./vendor-vue-CXt3ZZQ3.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-29bN5sfh.js";import"./vendor-tiptap-BkFTmTb3.js";const _={class:"flex flex-col items-center gap-1"},x={key:0,class:"flex items-center gap-2 text-xs text-zinc-400"},b=r({__name:"MediaAudioBottom",props:{asset:{}},setup(a){const o=l(()=>i(a.asset.name).filename);return(e,z)=>(s(),t("div",_,[c(m,{"file-name":o.value},null,8,["file-name"]),e.asset.size?(s(),t("div",x,[f("span",null,d(u(n)(e.asset.size)),1)])):p("",!0)]))}});export{b as default};
|
|
2
|
+
//# sourceMappingURL=MediaAudioBottom-d7EZ2Wx5.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MediaAudioBottom-
|
|
1
|
+
{"version":3,"file":"MediaAudioBottom-d7EZ2Wx5.js","sources":["../../src/platform/assets/components/MediaAudioBottom.vue"],"sourcesContent":["<template>\n <div class=\"flex flex-col items-center gap-1\">\n <MediaTitle :file-name=\"fileName\" />\n <!-- TBD: File size will be provided by backend history API -->\n <div\n v-if=\"asset.size\"\n class=\"flex items-center gap-2 text-xs text-zinc-400\"\n >\n <span>{{ formatSize(asset.size) }}</span>\n </div>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { computed } from 'vue'\n\nimport { formatSize, getFilenameDetails } from '@/utils/formatUtil'\n\nimport type { AssetMeta } from '../schemas/mediaAssetSchema'\nimport MediaTitle from './MediaTitle.vue'\n\nconst { asset } = defineProps<{\n asset: AssetMeta\n}>()\n\nconst fileName = computed(() => {\n return getFilenameDetails(asset.name).filename\n})\n</script>\n"],"names":["fileName","computed","getFilenameDetails","__props"],"mappings":"wkBAyBA,MAAMA,EAAWC,EAAS,IACjBC,EAAmBC,EAAA,MAAM,IAAI,EAAE,QACvC"}
|
comfyui_frontend_package/static/assets/{MediaImageBottom-OWiMf_6W.js → MediaImageBottom-B-9SOOhn.js}
RENAMED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{
|
|
2
|
-
//# sourceMappingURL=MediaImageBottom-
|
|
1
|
+
import{du as n}from"./index-CuKlxAeN.js";import{_ as m}from"./MediaTitle.vue_vue_type_script_setup_true_lang-DVzYM9UW.js";import{bx as r,E as c,c as s,d as t,z as l,e as d,q as p,u as a}from"./vendor-other-CSX7WseZ.js";import"./vendor-primevue-B6rcS73U.js";import"./vendor-vue-CXt3ZZQ3.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-29bN5sfh.js";import"./vendor-tiptap-BkFTmTb3.js";const f={class:"flex flex-col items-center gap-1"},_={class:"flex items-center text-xs text-zinc-400"},u={key:0},z=r({__name:"MediaImageBottom",props:{asset:{}},setup(o){const i=c(()=>n(o.asset.name).filename);return(e,h)=>(t(),s("div",f,[l(m,{"file-name":i.value},null,8,["file-name"]),d("div",_,[e.asset.dimensions?(t(),s("span",u,a(e.asset.dimensions?.width)+"x"+a(e.asset.dimensions?.height),1)):p("",!0)])]))}});export{z as default};
|
|
2
|
+
//# sourceMappingURL=MediaImageBottom-B-9SOOhn.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MediaImageBottom-
|
|
1
|
+
{"version":3,"file":"MediaImageBottom-B-9SOOhn.js","sources":["../../src/platform/assets/components/MediaImageBottom.vue"],"sourcesContent":["<template>\n <div class=\"flex flex-col items-center gap-1\">\n <MediaTitle :file-name=\"fileName\" />\n <div class=\"flex items-center text-xs text-zinc-400\">\n <span v-if=\"asset.dimensions\"\n >{{ asset.dimensions?.width }}x{{ asset.dimensions?.height }}</span\n >\n </div>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { computed } from 'vue'\n\nimport { getFilenameDetails } from '@/utils/formatUtil'\n\nimport type { AssetMeta } from '../schemas/mediaAssetSchema'\nimport MediaTitle from './MediaTitle.vue'\n\nconst { asset } = defineProps<{\n asset: AssetMeta\n}>()\n\nconst fileName = computed(() => {\n return getFilenameDetails(asset.name).filename\n})\n</script>\n"],"names":["fileName","computed","getFilenameDetails","__props"],"mappings":"sjBAuBA,MAAMA,EAAWC,EAAS,IACjBC,EAAmBC,EAAA,MAAM,IAAI,EAAE,QACvC"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{
|
|
2
|
-
//# sourceMappingURL=MediaTitle.vue_vue_type_script_setup_true_lang-
|
|
1
|
+
import{dv as l}from"./index-CuKlxAeN.js";import{bx as n,E as t,c as m,d as c,u as i}from"./vendor-other-CSX7WseZ.js";const r=["title"],_=n({__name:"MediaTitle",props:{fileName:{}},setup(a){const e=a,o=t(()=>e.fileName),s=t(()=>l(e.fileName));return(p,f)=>(c(),m("h3",{class:"m-0 line-clamp-1 text-sm font-bold text-base-foreground",title:o.value},i(s.value),9,r))}});export{_};
|
|
2
|
+
//# sourceMappingURL=MediaTitle.vue_vue_type_script_setup_true_lang-DVzYM9UW.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MediaTitle.vue_vue_type_script_setup_true_lang-
|
|
1
|
+
{"version":3,"file":"MediaTitle.vue_vue_type_script_setup_true_lang-DVzYM9UW.js","sources":["../../src/platform/assets/components/MediaTitle.vue"],"sourcesContent":["<template>\n <h3\n class=\"m-0 line-clamp-1 text-sm font-bold text-base-foreground\"\n :title=\"fullName\"\n >\n {{ displayName }}\n </h3>\n</template>\n\n<script setup lang=\"ts\">\nimport { computed } from 'vue'\n\nimport { truncateFilename } from '@/utils/formatUtil'\n\nconst props = defineProps<{\n fileName: string\n}>()\n\nconst fullName = computed(() => props.fileName)\nconst displayName = computed(() => truncateFilename(props.fileName))\n</script>\n"],"names":["props","__props","fullName","computed","displayName","truncateFilename"],"mappings":"6LAcA,MAAMA,EAAQC,EAIRC,EAAWC,EAAS,IAAMH,EAAM,QAAQ,EACxCI,EAAcD,EAAS,IAAME,EAAiBL,EAAM,QAAQ,CAAC"}
|
comfyui_frontend_package/static/assets/{MediaVideoBottom-OKuLWTbn.js → MediaVideoBottom-D6IR52ja.js}
RENAMED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{
|
|
2
|
-
//# sourceMappingURL=MediaVideoBottom-
|
|
1
|
+
import{du as i,dn as n}from"./index-CuKlxAeN.js";import{_ as m}from"./MediaTitle.vue_vue_type_script_setup_true_lang-DVzYM9UW.js";import{bx as r,E as l,c as t,d as s,z as c,q as p,e as f,u as d,by as u}from"./vendor-other-CSX7WseZ.js";import"./vendor-primevue-B6rcS73U.js";import"./vendor-vue-CXt3ZZQ3.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-29bN5sfh.js";import"./vendor-tiptap-BkFTmTb3.js";const _={class:"flex flex-col items-center gap-1"},x={key:0,class:"flex items-center text-xs text-zinc-400"},b=r({__name:"MediaVideoBottom",props:{asset:{}},setup(a){const o=l(()=>i(a.asset.name).filename);return(e,z)=>(s(),t("div",_,[c(m,{"file-name":o.value},null,8,["file-name"]),e.asset.size?(s(),t("div",x,[f("span",null,d(u(n)(e.asset.size)),1)])):p("",!0)]))}});export{b as default};
|
|
2
|
+
//# sourceMappingURL=MediaVideoBottom-D6IR52ja.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MediaVideoBottom-
|
|
1
|
+
{"version":3,"file":"MediaVideoBottom-D6IR52ja.js","sources":["../../src/platform/assets/components/MediaVideoBottom.vue"],"sourcesContent":["<template>\n <div class=\"flex flex-col items-center gap-1\">\n <MediaTitle :file-name=\"fileName\" />\n <!-- TBD: File size will be provided by backend history API -->\n <div v-if=\"asset.size\" class=\"flex items-center text-xs text-zinc-400\">\n <span>{{ formatSize(asset.size) }}</span>\n </div>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { computed } from 'vue'\n\nimport { formatSize, getFilenameDetails } from '@/utils/formatUtil'\n\nimport type { AssetMeta } from '../schemas/mediaAssetSchema'\nimport MediaTitle from './MediaTitle.vue'\n\nconst { asset } = defineProps<{\n asset: AssetMeta\n}>()\n\nconst fileName = computed(() => {\n return getFilenameDetails(asset.name).filename\n})\n</script>\n"],"names":["fileName","computed","getFilenameDetails","__props"],"mappings":"kkBAsBA,MAAMA,EAAWC,EAAS,IACjBC,EAAmBC,EAAA,MAAM,IAAI,EAAE,QACvC"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
var z=Object.defineProperty;var l=(h,f)=>z(h,"name",{value:f,configurable:!0});import{s as D,u as P}from"./vendor-vue-CXt3ZZQ3.js";import{q as E,s as x}from"./vendor-primevue-B6rcS73U.js";import{e as
|
|
2
|
-
//# sourceMappingURL=ServerConfigPanel-
|
|
1
|
+
var z=Object.defineProperty;var l=(h,f)=>z(h,"name",{value:f,configurable:!0});import{s as D,u as P}from"./vendor-vue-CXt3ZZQ3.js";import{q as E,s as x}from"./vendor-primevue-B6rcS73U.js";import{e as O,f as G,N as H,dt as J,_ as C,dq as K,bo as M}from"./index-CuKlxAeN.js";import{u as Q}from"./serverConfigStore-trwJaF_M.js";import{bx as W,w as b,df as X,j as m,d as t,k as a,c as u,F as y,y as _,by as o,q as S,e as r,u as n,z as v,A as V}from"./vendor-other-CSX7WseZ.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-29bN5sfh.js";import"./vendor-tiptap-BkFTmTb3.js";const Y={class:"flex flex-col gap-2"},Z={class:"flex justify-end gap-2"},ee={class:"flex items-center justify-between"},fe=W({__name:"ServerConfigPanel",setup(h){const f=O(),k=Q(),$=G(),{serverConfigsByCategory:A,serverConfigValues:T,launchArgs:B,commandLineArgs:p,modifiedConfigs:g}=D(k);let w=!1;const I=l(()=>{k.revertChanges()},"revertChanges"),q=l(async()=>{w=!0,await M().restartApp()},"restartApp");b(B,async e=>{await f.set("Comfy.Server.LaunchArgs",e)}),b(T,async e=>{await f.set("Comfy.Server.ServerConfigValues",e)});const{copyToClipboard:N}=H(),j=l(async()=>{await N(p.value)},"copyCommandLineArgs"),{t:d}=P();X(()=>{w||g.value.length!==0&&$.add({severity:"warn",summary:d("serverConfig.restartRequiredToastSummary"),detail:d("serverConfig.restartRequiredToastDetail"),life:1e4})});const L=l(e=>({...e,name:d(`serverConfigItems.${e.id}.name`,e.name),tooltip:e.tooltip?d(`serverConfigItems.${e.id}.tooltip`,e.tooltip):void 0}),"translateItem");return(e,c)=>(t(),m(K,{value:"Server-Config",class:"server-config-panel"},{header:a(()=>[r("div",Y,[o(g).length>0?(t(),m(o(x),{key:0,severity:"info","pt:text":"w-full"},{default:a(()=>[r("p",null,n(e.$t("serverConfig.modifiedConfigs")),1),r("ul",null,[(t(!0),u(y,null,_(o(g),s=>(t(),u("li",{key:s.id},n(s.name)+": "+n(s.initialValue)+" → "+n(s.value),1))),128))]),r("div",Z,[v(C,{variant:"secondary",onClick:I},{default:a(()=>[V(n(e.$t("serverConfig.revertChanges")),1)]),_:1}),v(C,{variant:"destructive",onClick:q},{default:a(()=>[V(n(e.$t("serverConfig.restart")),1)]),_:1})])]),_:1})):S("",!0),o(p)?(t(),m(o(x),{key:1,severity:"secondary","pt:text":"w-full"},{icon:a(()=>c[0]||(c[0]=[r("i",{class:"icon-[lucide--terminal] text-xl font-bold"},null,-1)])),default:a(()=>[r("div",ee,[r("p",null,n(o(p)),1),v(C,{size:"icon",variant:"muted-textonly",onClick:j},{default:a(()=>c[1]||(c[1]=[r("i",{class:"pi pi-clipboard"},null,-1)])),_:1})])]),_:1})):S("",!0)])]),default:a(()=>[(t(!0),u(y,null,_(Object.entries(o(A)),([s,F],R)=>(t(),u("div",{key:s},[R>0?(t(),m(o(E),{key:0})):S("",!0),r("h3",null,n(e.$t(`serverConfigCategories.${s}`,s)),1),(t(!0),u(y,null,_(F,i=>(t(),u("div",{key:i.name,class:"mb-4"},[v(J,{id:i.id,"form-value":i.value,"onUpdate:formValue":l(U=>i.value=U,"onUpdate:formValue"),item:L(i),"label-class":{"text-highlight":i.initialValue!==i.value}},null,8,["id","form-value","onUpdate:formValue","item","label-class"])]))),128))]))),128))]),_:1}))}});export{fe as default};
|
|
2
|
+
//# sourceMappingURL=ServerConfigPanel-BBWOQ7ej.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ServerConfigPanel-
|
|
1
|
+
{"version":3,"file":"ServerConfigPanel-BBWOQ7ej.js","sources":["../../src/platform/settings/components/ServerConfigPanel.vue"],"sourcesContent":["<template>\n <PanelTemplate value=\"Server-Config\" class=\"server-config-panel\">\n <template #header>\n <div class=\"flex flex-col gap-2\">\n <Message\n v-if=\"modifiedConfigs.length > 0\"\n severity=\"info\"\n pt:text=\"w-full\"\n >\n <p>\n {{ $t('serverConfig.modifiedConfigs') }}\n </p>\n <ul>\n <li v-for=\"config in modifiedConfigs\" :key=\"config.id\">\n {{ config.name }}: {{ config.initialValue }} → {{ config.value }}\n </li>\n </ul>\n <div class=\"flex justify-end gap-2\">\n <Button variant=\"secondary\" @click=\"revertChanges\">\n {{ $t('serverConfig.revertChanges') }}\n </Button>\n <Button variant=\"destructive\" @click=\"restartApp\">\n {{ $t('serverConfig.restart') }}\n </Button>\n </div>\n </Message>\n <Message v-if=\"commandLineArgs\" severity=\"secondary\" pt:text=\"w-full\">\n <template #icon>\n <i class=\"icon-[lucide--terminal] text-xl font-bold\" />\n </template>\n <div class=\"flex items-center justify-between\">\n <p>{{ commandLineArgs }}</p>\n <Button\n size=\"icon\"\n variant=\"muted-textonly\"\n @click=\"copyCommandLineArgs\"\n >\n <i class=\"pi pi-clipboard\" />\n </Button>\n </div>\n </Message>\n </div>\n </template>\n <div\n v-for=\"([label, items], i) in Object.entries(serverConfigsByCategory)\"\n :key=\"label\"\n >\n <Divider v-if=\"i > 0\" />\n <h3>{{ $t(`serverConfigCategories.${label}`, label) }}</h3>\n <div v-for=\"item in items\" :key=\"item.name\" class=\"mb-4\">\n <FormItem\n :id=\"item.id\"\n v-model:form-value=\"item.value\"\n :item=\"translateItem(item)\"\n :label-class=\"{\n 'text-highlight': item.initialValue !== item.value\n }\"\n />\n </div>\n </div>\n </PanelTemplate>\n</template>\n\n<script setup lang=\"ts\">\nimport { storeToRefs } from 'pinia'\nimport Divider from 'primevue/divider'\nimport Message from 'primevue/message'\nimport { onBeforeUnmount, watch } from 'vue'\nimport { useI18n } from 'vue-i18n'\n\nimport FormItem from '@/components/common/FormItem.vue'\nimport PanelTemplate from '@/components/dialog/content/setting/PanelTemplate.vue'\nimport Button from '@/components/ui/button/Button.vue'\nimport { useCopyToClipboard } from '@/composables/useCopyToClipboard'\nimport type { ServerConfig } from '@/constants/serverConfig'\nimport { useSettingStore } from '@/platform/settings/settingStore'\nimport type { FormItem as FormItemType } from '@/platform/settings/types'\nimport { useToastStore } from '@/platform/updates/common/toastStore'\nimport { useServerConfigStore } from '@/stores/serverConfigStore'\nimport { electronAPI } from '@/utils/envUtil'\n\nconst settingStore = useSettingStore()\nconst serverConfigStore = useServerConfigStore()\nconst toastStore = useToastStore()\nconst {\n serverConfigsByCategory,\n serverConfigValues,\n launchArgs,\n commandLineArgs,\n modifiedConfigs\n} = storeToRefs(serverConfigStore)\n\nlet restartTriggered = false\n\nconst revertChanges = () => {\n serverConfigStore.revertChanges()\n}\n\nconst restartApp = async () => {\n restartTriggered = true\n await electronAPI().restartApp()\n}\n\nwatch(launchArgs, async (newVal) => {\n await settingStore.set('Comfy.Server.LaunchArgs', newVal)\n})\n\nwatch(serverConfigValues, async (newVal) => {\n await settingStore.set('Comfy.Server.ServerConfigValues', newVal)\n})\n\nconst { copyToClipboard } = useCopyToClipboard()\nconst copyCommandLineArgs = async () => {\n await copyToClipboard(commandLineArgs.value)\n}\n\nconst { t } = useI18n()\n\nonBeforeUnmount(() => {\n if (restartTriggered) {\n return\n }\n\n if (modifiedConfigs.value.length === 0) {\n return\n }\n\n toastStore.add({\n severity: 'warn',\n summary: t('serverConfig.restartRequiredToastSummary'),\n detail: t('serverConfig.restartRequiredToastDetail'),\n life: 10_000\n })\n})\n\nconst translateItem = (item: ServerConfig<any>): FormItemType => {\n return {\n ...item,\n name: t(`serverConfigItems.${item.id}.name`, item.name),\n tooltip: item.tooltip\n ? t(`serverConfigItems.${item.id}.tooltip`, item.tooltip)\n : undefined\n }\n}\n</script>\n"],"names":["settingStore","useSettingStore","serverConfigStore","useServerConfigStore","toastStore","useToastStore","serverConfigsByCategory","serverConfigValues","launchArgs","commandLineArgs","modifiedConfigs","storeToRefs","restartTriggered","revertChanges","__name","restartApp","electronAPI","watch","newVal","copyToClipboard","useCopyToClipboard","copyCommandLineArgs","t","useI18n","onBeforeUnmount","translateItem","item"],"mappings":"quBAiFA,MAAMA,EAAeC,EAAA,EACfC,EAAoBC,EAAA,EACpBC,EAAaC,EAAA,EACb,CACJ,wBAAAC,EACA,mBAAAC,EACA,WAAAC,EACA,gBAAAC,EACA,gBAAAC,CAAA,EACEC,EAAYT,CAAiB,EAEjC,IAAIU,EAAmB,GAEvB,MAAMC,EAAgBC,EAAA,IAAM,CAC1BZ,EAAkB,cAAA,CACpB,EAFsB,iBAIhBa,EAAaD,EAAA,SAAY,CAC7BF,EAAmB,GACnB,MAAMI,EAAA,EAAc,WAAA,CACtB,EAHmB,cAKnBC,EAAMT,EAAY,MAAOU,GAAW,CAClC,MAAMlB,EAAa,IAAI,0BAA2BkB,CAAM,CAC1D,CAAC,EAEDD,EAAMV,EAAoB,MAAOW,GAAW,CAC1C,MAAMlB,EAAa,IAAI,kCAAmCkB,CAAM,CAClE,CAAC,EAED,KAAM,CAAE,gBAAAC,CAAA,EAAoBC,EAAA,EACtBC,EAAsBP,EAAA,SAAY,CACtC,MAAMK,EAAgBV,EAAgB,KAAK,CAC7C,EAF4B,uBAItB,CAAE,EAAAa,CAAA,EAAMC,EAAA,EAEdC,EAAgB,IAAM,CAChBZ,GAIAF,EAAgB,MAAM,SAAW,GAIrCN,EAAW,IAAI,CACb,SAAU,OACV,QAASkB,EAAE,0CAA0C,EACrD,OAAQA,EAAE,yCAAyC,EACnD,KAAM,GAAA,CACP,CACH,CAAC,EAED,MAAMG,EAAgBX,EAACY,IACd,CACL,GAAGA,EACH,KAAMJ,EAAE,qBAAqBI,EAAK,EAAE,QAASA,EAAK,IAAI,EACtD,QAASA,EAAK,QACVJ,EAAE,qBAAqBI,EAAK,EAAE,WAAYA,EAAK,OAAO,EACtD,MAAA,GANc"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
var G=Object.defineProperty;var a=(f,c)=>G(f,"name",{value:c,configurable:!0});import{t as s,dv as I,a2 as Q,l as V,a1 as X,V as J,dw as Z,c as M,_ as P,d as U,z as ee,b as te}from"./index-2-qFLlQP.js";import{_ as se,a as oe}from"./GraphView-CjDjhvN7.js";import{bx as j,E as T,j as ne,d as x,r as E,c as b,e,z as p,by as n,k as y,q as O,u as t,F as re,y as ae,s as z,l as le,A,v as ie,w as F,df as ce}from"./vendor-other-CSX7WseZ.js";import{v as de,p as ue}from"./vendor-primevue-B6rcS73U.js";import{u as pe}from"./vendor-vue-CXt3ZZQ3.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-BKWXAgVe.js";import"./vendor-tiptap-BkFTmTb3.js";import"./UserAvatar.vue_vue_type_script_setup_true_lang-ZL9faEyg.js";import"./index-_AAd9eTu.js";import"./LazyImage.vue_vue_type_script_setup_true_lang-CcI-aYhS.js";import"./keybindingService-CWbdWLPI.js";import"./serverConfigStore-trwJaF_M.js";import"./WidgetInputNumber.vue_vue_type_script_setup_true_lang-aeh2Ot2n.js";import"./widgetPropFilter-CygYoMQt.js";import"./WidgetLayoutField.vue_vue_type_script_setup_true_lang-Dps42A-g.js";import"./WidgetWithControl.vue_vue_type_script_setup_true_lang-COy_p9Eh.js";const fe=j({__name:"CloudBadge",props:{displayMode:{default:"full"},reverseOrder:{type:Boolean,default:!1},noPadding:{type:Boolean,default:!1},backgroundColor:{default:"var(--comfy-menu-bg)"}},setup(f){const c=T(()=>({label:s("g.beta"),text:"Comfy Cloud"}));return(m,v)=>(x(),ne(se,{badge:c.value,"display-mode":m.displayMode,"reverse-order":m.reverseOrder,"no-padding":m.noPadding,"background-color":m.backgroundColor},null,8,["badge","display-mode","reverse-order","no-padding","background-color"]))}}),me=""+new URL("images/cloud-subscription.webm",import.meta.url).href,xe=20,be=["yearly-pro","yearly-creator","yearly-standard","monthly-pro","monthly-creator","monthly-standard"];be.reduce((f,c,m)=>f.set(c,m),new Map);const ge={class:"flex flex-col gap-8"},_e={class:"flex justify-center"},ye={class:"flex items-center gap-2"},ve={key:0,class:"bg-primary-background text-white text-[11px] px-1 py-0.5 rounded-full flex items-center font-bold"},he={class:"flex flex-col xl:flex-row items-stretch gap-6"},we={class:"p-8 pb-0 flex flex-col gap-8"},ke={class:"flex flex-row items-center gap-2 justify-between"},$e={class:"font-inter text-base font-bold leading-normal text-base-foreground"},Ce={key:0,class:"rounded-full bg-base-foreground px-1.5 text-[11px] font-bold uppercase text-base-background h-5 tracking-tight flex items-center"},Pe={class:"flex flex-col"},Le={class:"flex flex-col gap-2"},Se={class:"flex flex-row items-baseline gap-2"},Ee={class:"font-inter text-[32px] font-semibold leading-normal text-base-foreground"},Te={class:"font-inter text-xl leading-normal text-base-foreground"},Ae={class:"flex items-center gap-2"},De={class:"text-sm text-muted-foreground"},Re={class:"flex flex-col gap-4 pb-0 flex-1"},Be={class:"flex flex-row items-center justify-between"},Ie={class:"font-inter text-sm font-normal leading-normal text-foreground"},je={class:"flex flex-row items-center gap-1"},Ne={class:"font-inter text-sm font-bold leading-normal text-base-foreground"},Me={class:"flex flex-row items-center justify-between"},Oe={class:"text-sm font-normal text-foreground"},ze={class:"font-inter text-sm font-bold leading-normal text-base-foreground"},Fe={class:"flex flex-row items-center justify-between"},Ve={class:"text-sm font-normal text-foreground"},Ue={class:"flex flex-row items-center justify-between"},Ye={class:"text-sm font-normal text-foreground"},qe={class:"flex flex-row items-center justify-between"},He={class:"text-sm font-normal text-foreground"},Ke={key:0,class:"pi pi-check text-xs text-success-foreground"},We={key:1,class:"pi pi-times text-xs text-foreground"},Ge={class:"flex flex-col gap-2"},Qe={class:"flex flex-row items-start justify-between"},Xe={class:"flex flex-col gap-2"},Je={class:"text-sm font-normal text-foreground"},Ze={class:"flex flex-row items-center gap-2 group pt-2"},et={class:"font-inter text-sm font-bold leading-normal text-base-foreground"},tt={class:"flex flex-col p-8"},st={class:"flex flex-col gap-2"},ot={class:"text-sm text-base-foreground"},nt={href:"https://cloud.comfy.org/?template=video_wan2_2_14B_fun_camera",target:"_blank",rel:"noopener noreferrer",class:"text-sm text-azure-600 hover:text-azure-400 underline"},rt=j({__name:"PricingTable",setup(f){const c=[{label:s("subscription.yearly"),value:"yearly"},{label:s("subscription.monthly"),value:"monthly"}],m=[{id:"STANDARD",key:"standard",name:s("subscription.tiers.standard.name"),pricing:I.standard,maxDuration:s("subscription.maxDuration.standard"),customLoRAs:!1,isPopular:!1},{id:"CREATOR",key:"creator",name:s("subscription.tiers.creator.name"),pricing:I.creator,maxDuration:s("subscription.maxDuration.creator"),customLoRAs:!0,isPopular:!0},{id:"PRO",key:"pro",name:s("subscription.tiers.pro.name"),pricing:I.pro,maxDuration:s("subscription.maxDuration.pro"),customLoRAs:!0,isPopular:!1}],{n:v}=pe(),{getAuthHeader:N}=Q(),{isActiveSubscription:D,subscriptionTier:L,isYearlySubscription:S}=V(),{accessBillingPortal:k,reportError:h}=X(),{wrapWithErrorHandlingAsync:$}=J(),g=E(!1),R=E(null),w=E(),u=E("yearly"),_=T(()=>L.value?Z[L.value]:null);T(()=>_.value?{tierKey:_.value,billingCycle:S.value?"yearly":"monthly"}:null);const C=a(r=>{if(!_.value)return!1;const i=u.value==="yearly";return _.value===r&&S.value===i},"isCurrentPlan"),B=a(r=>{w.value.toggle(r)},"togglePopover"),l=a(r=>{if(C(r.key))return s("subscription.currentPlan");const i=u.value==="yearly"?s("subscription.tierNameYearly",{name:r.name}):r.name;return D.value?s("subscription.changeTo",{plan:i}):s("subscription.subscribeTo",{plan:i})},"getButtonLabel"),d=a(r=>C(r.key)?"secondary":r.key==="creator"?"primary":"secondary","getButtonSeverity"),Y=a(r=>r.key==="creator"?"font-inter text-sm font-bold leading-normal text-base-background":"font-inter text-sm font-bold leading-normal text-primary-foreground","getButtonTextClass"),q=a(r=>r.pricing[u.value],"getPrice"),H=a(r=>r.pricing.yearly*12,"getAnnualTotal"),K=a(r=>r.pricing.credits*(u.value==="yearly"?12:1),"getCreditsDisplay"),W=$(async r=>{},h);return(r,i)=>(x(),b("div",ge,[e("div",_e,[p(n(de),{modelValue:u.value,"onUpdate:modelValue":i[0]||(i[0]=o=>u.value=o),options:c,"option-label":"label","option-value":"value","allow-empty":!1,unstyled:"",pt:{root:{class:"flex gap-1 bg-secondary-background rounded-lg p-1.5"},pcToggleButton:{root:a(({context:o})=>({class:["w-36 h-8 rounded-md transition-colors cursor-pointer border-none outline-none ring-0 text-sm font-medium flex items-center justify-center",o.active?"bg-base-foreground text-base-background":"bg-transparent text-muted-foreground hover:bg-secondary-background-hover"]}),"root"),label:{class:"flex items-center gap-2 "}}}},{option:y(({option:o})=>[e("div",ye,[e("span",null,t(o.label),1),o.value==="yearly"?(x(),b("div",ve," -20% ")):O("",!0)])]),_:1},8,["modelValue","pt"])]),e("div",he,[(x(),b(re,null,ae(m,o=>e("div",{key:o.id,class:z(n(M)("flex-1 flex flex-col rounded-2xl border border-border-default bg-base-background shadow-[0_0_12px_rgba(0,0,0,0.1)]",o.isPopular?"border-muted-foreground":""))},[e("div",we,[e("div",ke,[e("span",$e,t(o.name),1),o.isPopular?(x(),b("div",Ce,t(n(s)("subscription.mostPopular")),1)):O("",!0)]),e("div",Pe,[e("div",Le,[e("div",Se,[e("span",Ee,[le(e("span",{class:"line-through text-2xl text-muted-foreground"}," $"+t(o.pricing.monthly),513),[[ie,u.value==="yearly"]]),A(" $"+t(q(o)),1)]),e("span",Te,t(n(s)("subscription.usdPerMonth")),1)]),e("div",Ae,[e("span",De,t(u.value==="yearly"?n(s)("subscription.billedYearly",{total:`$${H(o)}`}):n(s)("subscription.billedMonthly")),1)])])]),e("div",Re,[e("div",Be,[e("span",Ie,t(u.value==="yearly"?n(s)("subscription.yearlyCreditsLabel"):n(s)("subscription.monthlyCreditsLabel")),1),e("div",je,[i[1]||(i[1]=e("i",{class:"icon-[lucide--component] text-amber-400 text-sm"},null,-1)),e("span",Ne,t(n(v)(K(o))),1)])]),e("div",Me,[e("span",Oe,t(n(s)("subscription.maxDurationLabel")),1),e("span",ze,t(o.maxDuration),1)]),e("div",Fe,[e("span",Ve,t(n(s)("subscription.gpuLabel")),1),i[2]||(i[2]=e("i",{class:"pi pi-check text-xs text-success-foreground"},null,-1))]),e("div",Ue,[e("span",Ye,t(n(s)("subscription.addCreditsLabel")),1),i[3]||(i[3]=e("i",{class:"pi pi-check text-xs text-success-foreground"},null,-1))]),e("div",qe,[e("span",He,t(n(s)("subscription.customLoRAsLabel")),1),o.customLoRAs?(x(),b("i",Ke)):(x(),b("i",We))]),e("div",Ge,[e("div",Qe,[e("div",Xe,[e("span",Je,t(n(s)("subscription.videoEstimateLabel")),1),e("div",Ze,[i[4]||(i[4]=e("i",{class:"pi pi-question-circle text-xs text-muted-foreground group-hover:text-base-foreground"},null,-1)),e("span",{class:"text-sm font-normal text-muted-foreground cursor-pointer group-hover:text-base-foreground",onClick:B},t(n(s)("subscription.videoEstimateHelp")),1)])]),e("span",et," ~"+t(n(v)(o.pricing.videoEstimate)),1)])])])]),e("div",tt,[p(P,{variant:d(o),disabled:g.value||C(o.key),loading:R.value===o.key,class:z(n(M)("h-10 w-full",Y(o),o.key==="creator"?"bg-base-foreground border-transparent hover:bg-inverted-background-hover":"bg-secondary-background border-transparent hover:bg-secondary-background-hover focus:bg-secondary-background-selected")),onClick:a(()=>n(W)(o.key),"onClick")},{default:y(()=>[A(t(l(o)),1)]),_:2},1032,["variant","disabled","loading","class","onClick"])])],2)),64))]),p(n(ue),{ref_key:"popover",ref:w,"append-to":"body","auto-z-index":!0,"base-z-index":1e3,dismissable:!0,"close-on-escape":!0,unstyled:"",pt:{root:{class:"rounded-lg border border-interface-stroke bg-interface-panel-surface shadow-lg p-4 max-w-xs"}}},{default:y(()=>[e("div",st,[e("p",ot,t(n(s)("subscription.videoEstimateExplanation")),1),e("a",nt,t(n(s)("subscription.videoEstimateTryTemplate")),1)])]),_:1},512)]))}}),at={},lt={class:"flex flex-col items-start gap-0 self-stretch"},it={class:"flex items-center gap-2 py-2"},ct={class:"text-sm text-text-primary"},dt={class:"flex items-center gap-2 py-2"},ut={class:"text-sm text-text-primary"};function pt(f,c){return x(),b("div",lt,[e("div",it,[c[0]||(c[0]=e("i",{class:"pi pi-check text-xs text-text-primary"},null,-1)),e("span",ct,t(f.$t("subscription.benefits.benefit1")),1)]),e("div",dt,[c[1]||(c[1]=e("i",{class:"pi pi-check text-xs text-text-primary"},null,-1)),e("span",ut,t(f.$t("subscription.benefits.benefit2")),1)])])}a(pt,"_sfc_render");const ft=U(at,[["render",pt]]),mt={key:0,class:"relative flex flex-col p-4 pt-8 md:p-16 !overflow-y-auto h-full gap-8"},xt={class:"text-center"},bt={class:"text-xl lg:text-2xl text-muted-foreground m-0"},gt={class:"flex flex-col items-center gap-2"},_t={class:"text-sm text-text-secondary m-0"},yt={class:"flex items-center gap-1.5"},vt={class:"text-sm text-text-secondary"},ht={key:1,class:"legacy-dialog relative grid h-full grid-cols-5"},wt={class:"col-span-3 flex flex-col justify-between p-8"},kt={class:"flex flex-col gap-6"},$t={class:"inline-flex items-center gap-2"},Ct={class:"text-sm text-text-primary"},Pt={class:"flex items-baseline gap-2"},Lt={class:"text-4xl font-bold"},St={class:"text-xl"},Et={class:"flex flex-col pt-8"},Tt=3e3,At=3,Dt=j({__name:"SubscriptionRequiredDialogContent",props:{onClose:{type:Function}},emits:["close"],setup(f,{emit:c}){const m=f,v=c,{fetchStatus:N,isActiveSubscription:D}=V(),L=new Intl.NumberFormat(navigator.language||"en-US",{style:"currency",currency:"USD",minimumFractionDigits:0,maximumFractionDigits:0}).format(xe),S=ee(),k=T(()=>te);let h=null,$=0;const g=a(()=>{h&&(clearInterval(h),h=null)},"stopPolling"),R=a(()=>{g(),$=0;const l=a(async()=>{try{await N(),$++,$>=At&&g()}catch(d){console.error("[SubscriptionDialog] Failed to poll subscription status",d),g()}},"poll");l(),h=window.setInterval(()=>{l()},Tt)},"startPolling"),w=a(()=>{k.value&&R()},"handleWindowFocus");F(k,l=>{l?window.addEventListener("focus",w):(window.removeEventListener("focus",w),g())},{immediate:!0}),F(()=>D.value,l=>{l&&k.value&&v("close",!0)});const u=a(()=>{v("close",!0)},"handleSubscribed"),_=a(()=>{g(),m.onClose()},"handleClose"),C=a(async()=>{await S.execute("Comfy.ContactSupport")},"handleContactUs"),B=a(()=>{window.open("https://www.comfy.org/cloud/enterprise","_blank")},"handleViewEnterprise");return ce(()=>{g(),window.removeEventListener("focus",w)}),(l,d)=>k.value?(x(),b("div",mt,[p(P,{size:"icon",variant:"muted-textonly",class:"rounded-full shrink-0 text-text-secondary hover:bg-white/10 absolute right-2.5 top-2.5","aria-label":l.$t("g.close"),onClick:_},{default:y(()=>d[0]||(d[0]=[e("i",{class:"pi pi-times text-xl"},null,-1)])),_:1},8,["aria-label"]),e("div",xt,[e("h2",bt,t(l.$t("subscription.description")),1)]),p(rt,{class:"flex-1"}),e("div",gt,[e("p",_t,t(l.$t("subscription.haveQuestions")),1),e("div",yt,[p(P,{variant:"muted-textonly",class:"h-6 p-1 text-sm text-text-secondary hover:text-base-foreground",onClick:C},{default:y(()=>[A(t(l.$t("subscription.contactUs"))+" ",1),d[1]||(d[1]=e("i",{class:"pi pi-comments"},null,-1))]),_:1}),e("span",vt,t(l.$t("g.or")),1),p(P,{variant:"muted-textonly",class:"h-6 p-1 text-sm text-text-secondary hover:text-base-foreground",onClick:B},{default:y(()=>[A(t(l.$t("subscription.viewEnterprise"))+" ",1),d[2]||(d[2]=e("i",{class:"pi pi-external-link"},null,-1))]),_:1})])])])):(x(),b("div",ht,[p(P,{size:"icon",variant:"muted-textonly",class:"rounded-full absolute top-2.5 right-2.5 z-10 h-8 w-8 p-0 text-white hover:bg-white/20","aria-label":l.$t("g.close"),onClick:_},{default:y(()=>d[3]||(d[3]=[e("i",{class:"pi pi-times"},null,-1)])),_:1},8,["aria-label"]),d[4]||(d[4]=e("div",{class:"relative col-span-2 flex items-center justify-center overflow-hidden rounded-sm"},[e("video",{autoplay:"",loop:"",muted:"",playsinline:"",class:"h-full min-w-[125%] object-cover p-0",style:{"margin-left":"-20%"}},[e("source",{src:me,type:"video/webm"})])],-1)),e("div",wt,[e("div",null,[e("div",kt,[e("div",$t,[e("div",Ct,t(l.$t("subscription.required.title")),1),p(fe,{"reverse-order":"","no-padding":"","background-color":"var(--p-dialog-background)","use-subscription":""})]),e("div",Pt,[e("span",Lt,t(n(L)),1),e("span",St,t(l.$t("subscription.perMonth")),1)])]),p(ft,{class:"mt-6 text-muted"})]),e("div",Et,[p(oe,{class:"py-2 px-4 rounded-lg",pt:{root:{style:"background: var(--color-accent-blue, #0B8CE9);"},label:{class:"font-inter font-[700] text-sm"}},onSubscribed:u})])])]))}}),Xt=U(Dt,[["__scopeId","data-v-44074ee0"]]);export{Xt as default};
|
|
2
|
-
//# sourceMappingURL=SubscriptionRequiredDialogContent-
|
|
1
|
+
var G=Object.defineProperty;var a=(f,c)=>G(f,"name",{value:c,configurable:!0});import{t as s,dw as I,a3 as Q,m as V,a2 as X,W as J,dx as Z,c as M,_ as P,d as U,A as ee,b as te}from"./index-CuKlxAeN.js";import{_ as se,a as oe}from"./GraphView-C_FQc1Au.js";import{bx as j,E as T,j as ne,d as x,r as E,c as b,e,z as p,by as n,k as y,q as O,u as t,F as re,y as ae,s as F,l as le,A,v as ie,w as z,df as ce}from"./vendor-other-CSX7WseZ.js";import{v as de,p as ue}from"./vendor-primevue-B6rcS73U.js";import{u as pe}from"./vendor-vue-CXt3ZZQ3.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-29bN5sfh.js";import"./vendor-tiptap-BkFTmTb3.js";import"./UserAvatar.vue_vue_type_script_setup_true_lang-ZL9faEyg.js";import"./index-DEqR9lwu.js";import"./LazyImage.vue_vue_type_script_setup_true_lang-DyOiHvnA.js";import"./keybindingService-O5KDQleT.js";import"./serverConfigStore-trwJaF_M.js";import"./WidgetInputNumber.vue_vue_type_script_setup_true_lang-XbRdxGIz.js";import"./widgetPropFilter-CygYoMQt.js";import"./WidgetLayoutField.vue_vue_type_script_setup_true_lang-CZj3E4v6.js";import"./WidgetWithControl.vue_vue_type_script_setup_true_lang-JSl33v3j.js";const fe=j({__name:"CloudBadge",props:{displayMode:{default:"full"},reverseOrder:{type:Boolean,default:!1},noPadding:{type:Boolean,default:!1},backgroundColor:{default:"var(--comfy-menu-bg)"}},setup(f){const c=T(()=>({label:s("g.beta"),text:"Comfy Cloud"}));return(m,v)=>(x(),ne(se,{badge:c.value,"display-mode":m.displayMode,"reverse-order":m.reverseOrder,"no-padding":m.noPadding,"background-color":m.backgroundColor},null,8,["badge","display-mode","reverse-order","no-padding","background-color"]))}}),me=""+new URL("images/cloud-subscription.webm",import.meta.url).href,xe=20,be=["yearly-pro","yearly-creator","yearly-standard","monthly-pro","monthly-creator","monthly-standard"];be.reduce((f,c,m)=>f.set(c,m),new Map);const ge={class:"flex flex-col gap-8"},_e={class:"flex justify-center"},ye={class:"flex items-center gap-2"},ve={key:0,class:"bg-primary-background text-white text-[11px] px-1 py-0.5 rounded-full flex items-center font-bold"},he={class:"flex flex-col xl:flex-row items-stretch gap-6"},we={class:"p-8 pb-0 flex flex-col gap-8"},ke={class:"flex flex-row items-center gap-2 justify-between"},$e={class:"font-inter text-base font-bold leading-normal text-base-foreground"},Ce={key:0,class:"rounded-full bg-base-foreground px-1.5 text-[11px] font-bold uppercase text-base-background h-5 tracking-tight flex items-center"},Pe={class:"flex flex-col"},Le={class:"flex flex-col gap-2"},Se={class:"flex flex-row items-baseline gap-2"},Ee={class:"font-inter text-[32px] font-semibold leading-normal text-base-foreground"},Te={class:"font-inter text-xl leading-normal text-base-foreground"},Ae={class:"flex items-center gap-2"},De={class:"text-sm text-muted-foreground"},Re={class:"flex flex-col gap-4 pb-0 flex-1"},Be={class:"flex flex-row items-center justify-between"},Ie={class:"font-inter text-sm font-normal leading-normal text-foreground"},je={class:"flex flex-row items-center gap-1"},Ne={class:"font-inter text-sm font-bold leading-normal text-base-foreground"},Me={class:"flex flex-row items-center justify-between"},Oe={class:"text-sm font-normal text-foreground"},Fe={class:"font-inter text-sm font-bold leading-normal text-base-foreground"},ze={class:"flex flex-row items-center justify-between"},Ve={class:"text-sm font-normal text-foreground"},Ue={class:"flex flex-row items-center justify-between"},Ye={class:"text-sm font-normal text-foreground"},qe={class:"flex flex-row items-center justify-between"},He={class:"text-sm font-normal text-foreground"},Ke={key:0,class:"pi pi-check text-xs text-success-foreground"},We={key:1,class:"pi pi-times text-xs text-foreground"},Ge={class:"flex flex-col gap-2"},Qe={class:"flex flex-row items-start justify-between"},Xe={class:"flex flex-col gap-2"},Je={class:"text-sm font-normal text-foreground"},Ze={class:"flex flex-row items-center gap-2 group pt-2"},et={class:"font-inter text-sm font-bold leading-normal text-base-foreground"},tt={class:"flex flex-col p-8"},st={class:"flex flex-col gap-2"},ot={class:"text-sm text-base-foreground"},nt={href:"https://cloud.comfy.org/?template=video_wan2_2_14B_fun_camera",target:"_blank",rel:"noopener noreferrer",class:"text-sm text-azure-600 hover:text-azure-400 underline"},rt=j({__name:"PricingTable",setup(f){const c=[{label:s("subscription.yearly"),value:"yearly"},{label:s("subscription.monthly"),value:"monthly"}],m=[{id:"STANDARD",key:"standard",name:s("subscription.tiers.standard.name"),pricing:I.standard,maxDuration:s("subscription.maxDuration.standard"),customLoRAs:!1,isPopular:!1},{id:"CREATOR",key:"creator",name:s("subscription.tiers.creator.name"),pricing:I.creator,maxDuration:s("subscription.maxDuration.creator"),customLoRAs:!0,isPopular:!0},{id:"PRO",key:"pro",name:s("subscription.tiers.pro.name"),pricing:I.pro,maxDuration:s("subscription.maxDuration.pro"),customLoRAs:!0,isPopular:!1}],{n:v}=pe(),{getAuthHeader:N}=Q(),{isActiveSubscription:D,subscriptionTier:L,isYearlySubscription:S}=V(),{accessBillingPortal:k,reportError:h}=X(),{wrapWithErrorHandlingAsync:$}=J(),g=E(!1),R=E(null),w=E(),u=E("yearly"),_=T(()=>L.value?Z[L.value]:null);T(()=>_.value?{tierKey:_.value,billingCycle:S.value?"yearly":"monthly"}:null);const C=a(r=>{if(!_.value)return!1;const i=u.value==="yearly";return _.value===r&&S.value===i},"isCurrentPlan"),B=a(r=>{w.value.toggle(r)},"togglePopover"),l=a(r=>{if(C(r.key))return s("subscription.currentPlan");const i=u.value==="yearly"?s("subscription.tierNameYearly",{name:r.name}):r.name;return D.value?s("subscription.changeTo",{plan:i}):s("subscription.subscribeTo",{plan:i})},"getButtonLabel"),d=a(r=>C(r.key)?"secondary":r.key==="creator"?"primary":"secondary","getButtonSeverity"),Y=a(r=>r.key==="creator"?"font-inter text-sm font-bold leading-normal text-base-background":"font-inter text-sm font-bold leading-normal text-primary-foreground","getButtonTextClass"),q=a(r=>r.pricing[u.value],"getPrice"),H=a(r=>r.pricing.yearly*12,"getAnnualTotal"),K=a(r=>r.pricing.credits*(u.value==="yearly"?12:1),"getCreditsDisplay"),W=$(async r=>{},h);return(r,i)=>(x(),b("div",ge,[e("div",_e,[p(n(de),{modelValue:u.value,"onUpdate:modelValue":i[0]||(i[0]=o=>u.value=o),options:c,"option-label":"label","option-value":"value","allow-empty":!1,unstyled:"",pt:{root:{class:"flex gap-1 bg-secondary-background rounded-lg p-1.5"},pcToggleButton:{root:a(({context:o})=>({class:["w-36 h-8 rounded-md transition-colors cursor-pointer border-none outline-none ring-0 text-sm font-medium flex items-center justify-center",o.active?"bg-base-foreground text-base-background":"bg-transparent text-muted-foreground hover:bg-secondary-background-hover"]}),"root"),label:{class:"flex items-center gap-2 "}}}},{option:y(({option:o})=>[e("div",ye,[e("span",null,t(o.label),1),o.value==="yearly"?(x(),b("div",ve," -20% ")):O("",!0)])]),_:1},8,["modelValue","pt"])]),e("div",he,[(x(),b(re,null,ae(m,o=>e("div",{key:o.id,class:F(n(M)("flex-1 flex flex-col rounded-2xl border border-border-default bg-base-background shadow-[0_0_12px_rgba(0,0,0,0.1)]",o.isPopular?"border-muted-foreground":""))},[e("div",we,[e("div",ke,[e("span",$e,t(o.name),1),o.isPopular?(x(),b("div",Ce,t(n(s)("subscription.mostPopular")),1)):O("",!0)]),e("div",Pe,[e("div",Le,[e("div",Se,[e("span",Ee,[le(e("span",{class:"line-through text-2xl text-muted-foreground"}," $"+t(o.pricing.monthly),513),[[ie,u.value==="yearly"]]),A(" $"+t(q(o)),1)]),e("span",Te,t(n(s)("subscription.usdPerMonth")),1)]),e("div",Ae,[e("span",De,t(u.value==="yearly"?n(s)("subscription.billedYearly",{total:`$${H(o)}`}):n(s)("subscription.billedMonthly")),1)])])]),e("div",Re,[e("div",Be,[e("span",Ie,t(u.value==="yearly"?n(s)("subscription.yearlyCreditsLabel"):n(s)("subscription.monthlyCreditsLabel")),1),e("div",je,[i[1]||(i[1]=e("i",{class:"icon-[lucide--component] text-amber-400 text-sm"},null,-1)),e("span",Ne,t(n(v)(K(o))),1)])]),e("div",Me,[e("span",Oe,t(n(s)("subscription.maxDurationLabel")),1),e("span",Fe,t(o.maxDuration),1)]),e("div",ze,[e("span",Ve,t(n(s)("subscription.gpuLabel")),1),i[2]||(i[2]=e("i",{class:"pi pi-check text-xs text-success-foreground"},null,-1))]),e("div",Ue,[e("span",Ye,t(n(s)("subscription.addCreditsLabel")),1),i[3]||(i[3]=e("i",{class:"pi pi-check text-xs text-success-foreground"},null,-1))]),e("div",qe,[e("span",He,t(n(s)("subscription.customLoRAsLabel")),1),o.customLoRAs?(x(),b("i",Ke)):(x(),b("i",We))]),e("div",Ge,[e("div",Qe,[e("div",Xe,[e("span",Je,t(n(s)("subscription.videoEstimateLabel")),1),e("div",Ze,[i[4]||(i[4]=e("i",{class:"pi pi-question-circle text-xs text-muted-foreground group-hover:text-base-foreground"},null,-1)),e("span",{class:"text-sm font-normal text-muted-foreground cursor-pointer group-hover:text-base-foreground",onClick:B},t(n(s)("subscription.videoEstimateHelp")),1)])]),e("span",et," ~"+t(n(v)(o.pricing.videoEstimate)),1)])])])]),e("div",tt,[p(P,{variant:d(o),disabled:g.value||C(o.key),loading:R.value===o.key,class:F(n(M)("h-10 w-full",Y(o),o.key==="creator"?"bg-base-foreground border-transparent hover:bg-inverted-background-hover":"bg-secondary-background border-transparent hover:bg-secondary-background-hover focus:bg-secondary-background-selected")),onClick:a(()=>n(W)(o.key),"onClick")},{default:y(()=>[A(t(l(o)),1)]),_:2},1032,["variant","disabled","loading","class","onClick"])])],2)),64))]),p(n(ue),{ref_key:"popover",ref:w,"append-to":"body","auto-z-index":!0,"base-z-index":1e3,dismissable:!0,"close-on-escape":!0,unstyled:"",pt:{root:{class:"rounded-lg border border-interface-stroke bg-interface-panel-surface shadow-lg p-4 max-w-xs"}}},{default:y(()=>[e("div",st,[e("p",ot,t(n(s)("subscription.videoEstimateExplanation")),1),e("a",nt,t(n(s)("subscription.videoEstimateTryTemplate")),1)])]),_:1},512)]))}}),at={},lt={class:"flex flex-col items-start gap-0 self-stretch"},it={class:"flex items-center gap-2 py-2"},ct={class:"text-sm text-text-primary"},dt={class:"flex items-center gap-2 py-2"},ut={class:"text-sm text-text-primary"};function pt(f,c){return x(),b("div",lt,[e("div",it,[c[0]||(c[0]=e("i",{class:"pi pi-check text-xs text-text-primary"},null,-1)),e("span",ct,t(f.$t("subscription.benefits.benefit1")),1)]),e("div",dt,[c[1]||(c[1]=e("i",{class:"pi pi-check text-xs text-text-primary"},null,-1)),e("span",ut,t(f.$t("subscription.benefits.benefit2")),1)])])}a(pt,"_sfc_render");const ft=U(at,[["render",pt]]),mt={key:0,class:"relative flex flex-col p-4 pt-8 md:p-16 !overflow-y-auto h-full gap-8"},xt={class:"text-center"},bt={class:"text-xl lg:text-2xl text-muted-foreground m-0"},gt={class:"flex flex-col items-center gap-2"},_t={class:"text-sm text-text-secondary m-0"},yt={class:"flex items-center gap-1.5"},vt={class:"text-sm text-text-secondary"},ht={key:1,class:"legacy-dialog relative grid h-full grid-cols-5"},wt={class:"col-span-3 flex flex-col justify-between p-8"},kt={class:"flex flex-col gap-6"},$t={class:"inline-flex items-center gap-2"},Ct={class:"text-sm text-text-primary"},Pt={class:"flex items-baseline gap-2"},Lt={class:"text-4xl font-bold"},St={class:"text-xl"},Et={class:"flex flex-col pt-8"},Tt=3e3,At=3,Dt=j({__name:"SubscriptionRequiredDialogContent",props:{onClose:{type:Function}},emits:["close"],setup(f,{emit:c}){const m=f,v=c,{fetchStatus:N,isActiveSubscription:D}=V(),L=new Intl.NumberFormat(navigator.language||"en-US",{style:"currency",currency:"USD",minimumFractionDigits:0,maximumFractionDigits:0}).format(xe),S=ee(),k=T(()=>te);let h=null,$=0;const g=a(()=>{h&&(clearInterval(h),h=null)},"stopPolling"),R=a(()=>{g(),$=0;const l=a(async()=>{try{await N(),$++,$>=At&&g()}catch(d){console.error("[SubscriptionDialog] Failed to poll subscription status",d),g()}},"poll");l(),h=window.setInterval(()=>{l()},Tt)},"startPolling"),w=a(()=>{k.value&&R()},"handleWindowFocus");z(k,l=>{l?window.addEventListener("focus",w):(window.removeEventListener("focus",w),g())},{immediate:!0}),z(()=>D.value,l=>{l&&k.value&&v("close",!0)});const u=a(()=>{v("close",!0)},"handleSubscribed"),_=a(()=>{g(),m.onClose()},"handleClose"),C=a(async()=>{await S.execute("Comfy.ContactSupport")},"handleContactUs"),B=a(()=>{window.open("https://www.comfy.org/cloud/enterprise","_blank")},"handleViewEnterprise");return ce(()=>{g(),window.removeEventListener("focus",w)}),(l,d)=>k.value?(x(),b("div",mt,[p(P,{size:"icon",variant:"muted-textonly",class:"rounded-full shrink-0 text-text-secondary hover:bg-white/10 absolute right-2.5 top-2.5","aria-label":l.$t("g.close"),onClick:_},{default:y(()=>d[0]||(d[0]=[e("i",{class:"pi pi-times text-xl"},null,-1)])),_:1},8,["aria-label"]),e("div",xt,[e("h2",bt,t(l.$t("subscription.description")),1)]),p(rt,{class:"flex-1"}),e("div",gt,[e("p",_t,t(l.$t("subscription.haveQuestions")),1),e("div",yt,[p(P,{variant:"muted-textonly",class:"h-6 p-1 text-sm text-text-secondary hover:text-base-foreground",onClick:C},{default:y(()=>[A(t(l.$t("subscription.contactUs"))+" ",1),d[1]||(d[1]=e("i",{class:"pi pi-comments"},null,-1))]),_:1}),e("span",vt,t(l.$t("g.or")),1),p(P,{variant:"muted-textonly",class:"h-6 p-1 text-sm text-text-secondary hover:text-base-foreground",onClick:B},{default:y(()=>[A(t(l.$t("subscription.viewEnterprise"))+" ",1),d[2]||(d[2]=e("i",{class:"pi pi-external-link"},null,-1))]),_:1})])])])):(x(),b("div",ht,[p(P,{size:"icon",variant:"muted-textonly",class:"rounded-full absolute top-2.5 right-2.5 z-10 h-8 w-8 p-0 text-white hover:bg-white/20","aria-label":l.$t("g.close"),onClick:_},{default:y(()=>d[3]||(d[3]=[e("i",{class:"pi pi-times"},null,-1)])),_:1},8,["aria-label"]),d[4]||(d[4]=e("div",{class:"relative col-span-2 flex items-center justify-center overflow-hidden rounded-sm"},[e("video",{autoplay:"",loop:"",muted:"",playsinline:"",class:"h-full min-w-[125%] object-cover p-0",style:{"margin-left":"-20%"}},[e("source",{src:me,type:"video/webm"})])],-1)),e("div",wt,[e("div",null,[e("div",kt,[e("div",$t,[e("div",Ct,t(l.$t("subscription.required.title")),1),p(fe,{"reverse-order":"","no-padding":"","background-color":"var(--p-dialog-background)","use-subscription":""})]),e("div",Pt,[e("span",Lt,t(n(L)),1),e("span",St,t(l.$t("subscription.perMonth")),1)])]),p(ft,{class:"mt-6 text-muted"})]),e("div",Et,[p(oe,{class:"py-2 px-4 rounded-lg",pt:{root:{style:"background: var(--color-accent-blue, #0B8CE9);"},label:{class:"font-inter font-[700] text-sm"}},onSubscribed:u})])])]))}}),Xt=U(Dt,[["__scopeId","data-v-44074ee0"]]);export{Xt as default};
|
|
2
|
+
//# sourceMappingURL=SubscriptionRequiredDialogContent-oUSDZGJZ.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"SubscriptionRequiredDialogContent-CtCWM_jj.js","sources":["../../src/components/topbar/CloudBadge.vue","../../../../../../../assets/images/cloud-subscription.webm","../../src/config/subscriptionPricesConfig.ts","../../src/platform/cloud/subscription/utils/subscriptionTierRank.ts","../../src/platform/cloud/subscription/components/PricingTable.vue","../../src/platform/cloud/subscription/components/SubscriptionBenefits.vue","../../src/platform/cloud/subscription/components/SubscriptionRequiredDialogContent.vue"],"sourcesContent":["<template>\n <TopbarBadge\n :badge=\"cloudBadge\"\n :display-mode=\"displayMode\"\n :reverse-order=\"reverseOrder\"\n :no-padding=\"noPadding\"\n :background-color=\"backgroundColor\"\n />\n</template>\n\n<script setup lang=\"ts\">\nimport { computed } from 'vue'\n\nimport { t } from '@/i18n'\nimport type { TopbarBadge as TopbarBadgeType } from '@/types/comfy'\n\nimport TopbarBadge from './TopbarBadge.vue'\n\nwithDefaults(\n defineProps<{\n displayMode?: 'full' | 'compact' | 'icon-only'\n reverseOrder?: boolean\n noPadding?: boolean\n backgroundColor?: string\n }>(),\n {\n displayMode: 'full',\n reverseOrder: false,\n noPadding: false,\n backgroundColor: 'var(--comfy-menu-bg)'\n }\n)\n\nconst cloudBadge = computed<TopbarBadgeType>(() => ({\n label: t('g.beta'),\n text: 'Comfy Cloud'\n}))\n</script>\n","export default \"__VITE_PUBLIC_ASSET__b4a125b1__\"","export const MONTHLY_SUBSCRIPTION_PRICE = 20\n","import type { TierKey } from '@/platform/cloud/subscription/constants/tierPricing'\n\nexport type BillingCycle = 'monthly' | 'yearly'\n\ntype RankedTierKey = Exclude<TierKey, 'founder'>\ntype RankedPlanKey = `${BillingCycle}-${RankedTierKey}`\n\ninterface PlanDescriptor {\n tierKey: TierKey\n billingCycle: BillingCycle\n}\n\nconst PLAN_ORDER: RankedPlanKey[] = [\n 'yearly-pro',\n 'yearly-creator',\n 'yearly-standard',\n 'monthly-pro',\n 'monthly-creator',\n 'monthly-standard'\n]\n\nconst PLAN_RANK = PLAN_ORDER.reduce<Map<RankedPlanKey, number>>(\n (acc, plan, index) => acc.set(plan, index),\n new Map()\n)\n\nconst toRankedPlanKey = (\n tierKey: TierKey,\n billingCycle: BillingCycle\n): RankedPlanKey | null => {\n if (tierKey === 'founder') return null\n return `${billingCycle}-${tierKey}` as RankedPlanKey\n}\n\nexport const getPlanRank = ({\n tierKey,\n billingCycle\n}: PlanDescriptor): number => {\n const planKey = toRankedPlanKey(tierKey, billingCycle)\n if (!planKey) return Number.POSITIVE_INFINITY\n\n return PLAN_RANK.get(planKey) ?? Number.POSITIVE_INFINITY\n}\n\ninterface DowngradeCheckParams {\n current: PlanDescriptor\n target: PlanDescriptor\n}\n\nexport const isPlanDowngrade = ({\n current,\n target\n}: DowngradeCheckParams): boolean => {\n const currentRank = getPlanRank(current)\n const targetRank = getPlanRank(target)\n\n return targetRank > currentRank\n}\n","<template>\n <div class=\"flex flex-col gap-8\">\n <div class=\"flex justify-center\">\n <SelectButton\n v-model=\"currentBillingCycle\"\n :options=\"billingCycleOptions\"\n option-label=\"label\"\n option-value=\"value\"\n :allow-empty=\"false\"\n unstyled\n :pt=\"{\n root: {\n class: 'flex gap-1 bg-secondary-background rounded-lg p-1.5'\n },\n pcToggleButton: {\n root: ({ context }: ToggleButtonPassThroughMethodOptions) => ({\n class: [\n 'w-36 h-8 rounded-md transition-colors cursor-pointer border-none outline-none ring-0 text-sm font-medium flex items-center justify-center',\n context.active\n ? 'bg-base-foreground text-base-background'\n : 'bg-transparent text-muted-foreground hover:bg-secondary-background-hover'\n ]\n }),\n label: { class: 'flex items-center gap-2 ' }\n }\n }\"\n >\n <template #option=\"{ option }\">\n <div class=\"flex items-center gap-2\">\n <span>{{ option.label }}</span>\n <div\n v-if=\"option.value === 'yearly'\"\n class=\"bg-primary-background text-white text-[11px] px-1 py-0.5 rounded-full flex items-center font-bold\"\n >\n -20%\n </div>\n </div>\n </template>\n </SelectButton>\n </div>\n <div class=\"flex flex-col xl:flex-row items-stretch gap-6\">\n <div\n v-for=\"tier in tiers\"\n :key=\"tier.id\"\n :class=\"\n cn(\n 'flex-1 flex flex-col rounded-2xl border border-border-default bg-base-background shadow-[0_0_12px_rgba(0,0,0,0.1)]',\n tier.isPopular ? 'border-muted-foreground' : ''\n )\n \"\n >\n <div class=\"p-8 pb-0 flex flex-col gap-8\">\n <div class=\"flex flex-row items-center gap-2 justify-between\">\n <span\n class=\"font-inter text-base font-bold leading-normal text-base-foreground\"\n >\n {{ tier.name }}\n </span>\n <div\n v-if=\"tier.isPopular\"\n class=\"rounded-full bg-base-foreground px-1.5 text-[11px] font-bold uppercase text-base-background h-5 tracking-tight flex items-center\"\n >\n {{ t('subscription.mostPopular') }}\n </div>\n </div>\n <div class=\"flex flex-col\">\n <div class=\"flex flex-col gap-2\">\n <div class=\"flex flex-row items-baseline gap-2\">\n <span\n class=\"font-inter text-[32px] font-semibold leading-normal text-base-foreground\"\n >\n <span\n v-show=\"currentBillingCycle === 'yearly'\"\n class=\"line-through text-2xl text-muted-foreground\"\n >\n ${{ tier.pricing.monthly }}\n </span>\n ${{ getPrice(tier) }}\n </span>\n <span\n class=\"font-inter text-xl leading-normal text-base-foreground\"\n >\n {{ t('subscription.usdPerMonth') }}\n </span>\n </div>\n <div class=\"flex items-center gap-2\">\n <span class=\"text-sm text-muted-foreground\">\n {{\n currentBillingCycle === 'yearly'\n ? t('subscription.billedYearly', {\n total: `$${getAnnualTotal(tier)}`\n })\n : t('subscription.billedMonthly')\n }}\n </span>\n </div>\n </div>\n </div>\n\n <div class=\"flex flex-col gap-4 pb-0 flex-1\">\n <div class=\"flex flex-row items-center justify-between\">\n <span\n class=\"font-inter text-sm font-normal leading-normal text-foreground\"\n >\n {{\n currentBillingCycle === 'yearly'\n ? t('subscription.yearlyCreditsLabel')\n : t('subscription.monthlyCreditsLabel')\n }}\n </span>\n <div class=\"flex flex-row items-center gap-1\">\n <i class=\"icon-[lucide--component] text-amber-400 text-sm\" />\n <span\n class=\"font-inter text-sm font-bold leading-normal text-base-foreground\"\n >\n {{ n(getCreditsDisplay(tier)) }}\n </span>\n </div>\n </div>\n\n <div class=\"flex flex-row items-center justify-between\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.maxDurationLabel') }}\n </span>\n <span\n class=\"font-inter text-sm font-bold leading-normal text-base-foreground\"\n >\n {{ tier.maxDuration }}\n </span>\n </div>\n\n <div class=\"flex flex-row items-center justify-between\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.gpuLabel') }}\n </span>\n <i class=\"pi pi-check text-xs text-success-foreground\" />\n </div>\n\n <div class=\"flex flex-row items-center justify-between\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.addCreditsLabel') }}\n </span>\n <i class=\"pi pi-check text-xs text-success-foreground\" />\n </div>\n\n <div class=\"flex flex-row items-center justify-between\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.customLoRAsLabel') }}\n </span>\n <i\n v-if=\"tier.customLoRAs\"\n class=\"pi pi-check text-xs text-success-foreground\"\n />\n <i v-else class=\"pi pi-times text-xs text-foreground\" />\n </div>\n\n <div class=\"flex flex-col gap-2\">\n <div class=\"flex flex-row items-start justify-between\">\n <div class=\"flex flex-col gap-2\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.videoEstimateLabel') }}\n </span>\n <div class=\"flex flex-row items-center gap-2 group pt-2\">\n <i\n class=\"pi pi-question-circle text-xs text-muted-foreground group-hover:text-base-foreground\"\n />\n <span\n class=\"text-sm font-normal text-muted-foreground cursor-pointer group-hover:text-base-foreground\"\n @click=\"togglePopover\"\n >\n {{ t('subscription.videoEstimateHelp') }}\n </span>\n </div>\n </div>\n <span\n class=\"font-inter text-sm font-bold leading-normal text-base-foreground\"\n >\n ~{{ n(tier.pricing.videoEstimate) }}\n </span>\n </div>\n </div>\n </div>\n </div>\n <div class=\"flex flex-col p-8\">\n <Button\n :variant=\"getButtonSeverity(tier)\"\n :disabled=\"isLoading || isCurrentPlan(tier.key)\"\n :loading=\"loadingTier === tier.key\"\n :class=\"\n cn(\n 'h-10 w-full',\n getButtonTextClass(tier),\n tier.key === 'creator'\n ? 'bg-base-foreground border-transparent hover:bg-inverted-background-hover'\n : 'bg-secondary-background border-transparent hover:bg-secondary-background-hover focus:bg-secondary-background-selected'\n )\n \"\n @click=\"() => handleSubscribe(tier.key)\"\n >\n {{ getButtonLabel(tier) }}\n </Button>\n </div>\n </div>\n </div>\n\n <!-- Video Estimate Help Popover -->\n <Popover\n ref=\"popover\"\n append-to=\"body\"\n :auto-z-index=\"true\"\n :base-z-index=\"1000\"\n :dismissable=\"true\"\n :close-on-escape=\"true\"\n unstyled\n :pt=\"{\n root: {\n class:\n 'rounded-lg border border-interface-stroke bg-interface-panel-surface shadow-lg p-4 max-w-xs'\n }\n }\"\n >\n <div class=\"flex flex-col gap-2\">\n <p class=\"text-sm text-base-foreground\">\n {{ t('subscription.videoEstimateExplanation') }}\n </p>\n <a\n href=\"https://cloud.comfy.org/?template=video_wan2_2_14B_fun_camera\"\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n class=\"text-sm text-azure-600 hover:text-azure-400 underline\"\n >\n {{ t('subscription.videoEstimateTryTemplate') }}\n </a>\n </div>\n </Popover>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { cn } from '@comfyorg/tailwind-utils'\nimport Popover from 'primevue/popover'\nimport SelectButton from 'primevue/selectbutton'\nimport type { ToggleButtonPassThroughMethodOptions } from 'primevue/togglebutton'\nimport { computed, ref } from 'vue'\nimport { useI18n } from 'vue-i18n'\n\nimport Button from '@/components/ui/button/Button.vue'\nimport { useFirebaseAuthActions } from '@/composables/auth/useFirebaseAuthActions'\nimport { useErrorHandling } from '@/composables/useErrorHandling'\nimport { getComfyApiBaseUrl } from '@/config/comfyApi'\nimport { t } from '@/i18n'\nimport { useSubscription } from '@/platform/cloud/subscription/composables/useSubscription'\nimport {\n TIER_PRICING,\n TIER_TO_KEY\n} from '@/platform/cloud/subscription/constants/tierPricing'\nimport type {\n TierKey,\n TierPricing\n} from '@/platform/cloud/subscription/constants/tierPricing'\nimport { isPlanDowngrade } from '@/platform/cloud/subscription/utils/subscriptionTierRank'\nimport type { BillingCycle } from '@/platform/cloud/subscription/utils/subscriptionTierRank'\nimport { isCloud } from '@/platform/distribution/types'\nimport {\n FirebaseAuthStoreError,\n useFirebaseAuthStore\n} from '@/stores/firebaseAuthStore'\nimport type { components } from '@/types/comfyRegistryTypes'\n\ntype SubscriptionTier = components['schemas']['SubscriptionTier']\ntype CheckoutTierKey = Exclude<TierKey, 'founder'>\ntype CheckoutTier = CheckoutTierKey | `${CheckoutTierKey}-yearly`\n\nconst getCheckoutTier = (\n tierKey: CheckoutTierKey,\n billingCycle: BillingCycle\n): CheckoutTier => (billingCycle === 'yearly' ? `${tierKey}-yearly` : tierKey)\n\ninterface BillingCycleOption {\n label: string\n value: BillingCycle\n}\n\ninterface PricingTierConfig {\n id: SubscriptionTier\n key: CheckoutTierKey\n name: string\n pricing: TierPricing\n maxDuration: string\n customLoRAs: boolean\n isPopular?: boolean\n}\n\nconst billingCycleOptions: BillingCycleOption[] = [\n { label: t('subscription.yearly'), value: 'yearly' },\n { label: t('subscription.monthly'), value: 'monthly' }\n]\n\nconst tiers: PricingTierConfig[] = [\n {\n id: 'STANDARD',\n key: 'standard',\n name: t('subscription.tiers.standard.name'),\n pricing: TIER_PRICING.standard,\n maxDuration: t('subscription.maxDuration.standard'),\n customLoRAs: false,\n isPopular: false\n },\n {\n id: 'CREATOR',\n key: 'creator',\n name: t('subscription.tiers.creator.name'),\n pricing: TIER_PRICING.creator,\n maxDuration: t('subscription.maxDuration.creator'),\n customLoRAs: true,\n isPopular: true\n },\n {\n id: 'PRO',\n key: 'pro',\n name: t('subscription.tiers.pro.name'),\n pricing: TIER_PRICING.pro,\n maxDuration: t('subscription.maxDuration.pro'),\n customLoRAs: true,\n isPopular: false\n }\n]\n\nconst { n } = useI18n()\nconst { getAuthHeader } = useFirebaseAuthStore()\nconst { isActiveSubscription, subscriptionTier, isYearlySubscription } =\n useSubscription()\nconst { accessBillingPortal, reportError } = useFirebaseAuthActions()\nconst { wrapWithErrorHandlingAsync } = useErrorHandling()\n\nconst isLoading = ref(false)\nconst loadingTier = ref<CheckoutTierKey | null>(null)\nconst popover = ref()\nconst currentBillingCycle = ref<BillingCycle>('yearly')\n\nconst currentTierKey = computed<TierKey | null>(() =>\n subscriptionTier.value ? TIER_TO_KEY[subscriptionTier.value] : null\n)\n\nconst currentPlanDescriptor = computed(() => {\n if (!currentTierKey.value) return null\n\n return {\n tierKey: currentTierKey.value,\n billingCycle: isYearlySubscription.value ? 'yearly' : 'monthly'\n } as const\n})\n\nconst isCurrentPlan = (tierKey: CheckoutTierKey): boolean => {\n if (!currentTierKey.value) return false\n\n const selectedIsYearly = currentBillingCycle.value === 'yearly'\n\n return (\n currentTierKey.value === tierKey &&\n isYearlySubscription.value === selectedIsYearly\n )\n}\n\nconst togglePopover = (event: Event) => {\n popover.value.toggle(event)\n}\n\nconst getButtonLabel = (tier: PricingTierConfig): string => {\n if (isCurrentPlan(tier.key)) return t('subscription.currentPlan')\n\n const planName =\n currentBillingCycle.value === 'yearly'\n ? t('subscription.tierNameYearly', { name: tier.name })\n : tier.name\n\n return isActiveSubscription.value\n ? t('subscription.changeTo', { plan: planName })\n : t('subscription.subscribeTo', { plan: planName })\n}\n\nconst getButtonSeverity = (tier: PricingTierConfig): 'primary' | 'secondary' =>\n isCurrentPlan(tier.key)\n ? 'secondary'\n : tier.key === 'creator'\n ? 'primary'\n : 'secondary'\n\nconst getButtonTextClass = (tier: PricingTierConfig): string =>\n tier.key === 'creator'\n ? 'font-inter text-sm font-bold leading-normal text-base-background'\n : 'font-inter text-sm font-bold leading-normal text-primary-foreground'\n\nconst getPrice = (tier: PricingTierConfig): number =>\n tier.pricing[currentBillingCycle.value]\n\nconst getAnnualTotal = (tier: PricingTierConfig): number =>\n tier.pricing.yearly * 12\n\nconst getCreditsDisplay = (tier: PricingTierConfig): number =>\n tier.pricing.credits * (currentBillingCycle.value === 'yearly' ? 12 : 1)\n\nconst initiateCheckout = async (tierKey: CheckoutTierKey) => {\n const authHeader = await getAuthHeader()\n if (!authHeader) {\n throw new FirebaseAuthStoreError(t('toastMessages.userNotAuthenticated'))\n }\n\n const checkoutTier = getCheckoutTier(tierKey, currentBillingCycle.value)\n const response = await fetch(\n `${getComfyApiBaseUrl()}/customers/cloud-subscription-checkout/${checkoutTier}`,\n {\n method: 'POST',\n headers: { ...authHeader, 'Content-Type': 'application/json' }\n }\n )\n\n if (!response.ok) {\n let errorMessage = 'Failed to initiate checkout'\n try {\n const errorData = await response.json()\n errorMessage = errorData.message || errorMessage\n } catch {\n // If JSON parsing fails, try to get text response or use HTTP status\n try {\n const errorText = await response.text()\n errorMessage =\n errorText || `HTTP ${response.status} ${response.statusText}`\n } catch {\n errorMessage = `HTTP ${response.status} ${response.statusText}`\n }\n }\n\n throw new FirebaseAuthStoreError(\n t('toastMessages.failedToInitiateSubscription', {\n error: errorMessage\n })\n )\n }\n\n return await response.json()\n}\n\nconst handleSubscribe = wrapWithErrorHandlingAsync(\n async (tierKey: CheckoutTierKey) => {\n if (!isCloud || isLoading.value || isCurrentPlan(tierKey)) return\n\n isLoading.value = true\n loadingTier.value = tierKey\n\n try {\n if (isActiveSubscription.value) {\n // Pass the target tier to create a deep link to subscription update confirmation\n const checkoutTier = getCheckoutTier(tierKey, currentBillingCycle.value)\n const targetPlan = {\n tierKey,\n billingCycle: currentBillingCycle.value\n }\n const downgrade =\n currentPlanDescriptor.value &&\n isPlanDowngrade({\n current: currentPlanDescriptor.value,\n target: targetPlan\n })\n\n if (downgrade) {\n // TODO(COMFY-StripeProration): Remove once backend checkout creation mirrors portal proration (\"change at billing end\")\n await accessBillingPortal()\n } else {\n await accessBillingPortal(checkoutTier)\n }\n } else {\n const response = await initiateCheckout(tierKey)\n if (response.checkout_url) {\n window.open(response.checkout_url, '_blank')\n }\n }\n } finally {\n isLoading.value = false\n loadingTier.value = null\n }\n },\n reportError\n)\n</script>\n","<template>\n <div class=\"flex flex-col items-start gap-0 self-stretch\">\n <div class=\"flex items-center gap-2 py-2\">\n <i class=\"pi pi-check text-xs text-text-primary\" />\n <span class=\"text-sm text-text-primary\">\n {{ $t('subscription.benefits.benefit1') }}\n </span>\n </div>\n\n <div class=\"flex items-center gap-2 py-2\">\n <i class=\"pi pi-check text-xs text-text-primary\" />\n <span class=\"text-sm text-text-primary\">\n {{ $t('subscription.benefits.benefit2') }}\n </span>\n </div>\n </div>\n</template>\n\n<script setup lang=\"ts\"></script>\n","<template>\n <div\n v-if=\"showCustomPricingTable\"\n class=\"relative flex flex-col p-4 pt-8 md:p-16 !overflow-y-auto h-full gap-8\"\n >\n <Button\n size=\"icon\"\n variant=\"muted-textonly\"\n class=\"rounded-full shrink-0 text-text-secondary hover:bg-white/10 absolute right-2.5 top-2.5\"\n :aria-label=\"$t('g.close')\"\n @click=\"handleClose\"\n >\n <i class=\"pi pi-times text-xl\" />\n </Button>\n <div class=\"text-center\">\n <h2 class=\"text-xl lg:text-2xl text-muted-foreground m-0\">\n {{ $t('subscription.description') }}\n </h2>\n </div>\n\n <PricingTable class=\"flex-1\" />\n\n <!-- Contact and Enterprise Links -->\n <div class=\"flex flex-col items-center gap-2\">\n <p class=\"text-sm text-text-secondary m-0\">\n {{ $t('subscription.haveQuestions') }}\n </p>\n <div class=\"flex items-center gap-1.5\">\n <Button\n variant=\"muted-textonly\"\n class=\"h-6 p-1 text-sm text-text-secondary hover:text-base-foreground\"\n @click=\"handleContactUs\"\n >\n {{ $t('subscription.contactUs') }}\n <i class=\"pi pi-comments\" />\n </Button>\n <span class=\"text-sm text-text-secondary\">{{ $t('g.or') }}</span>\n <Button\n variant=\"muted-textonly\"\n class=\"h-6 p-1 text-sm text-text-secondary hover:text-base-foreground\"\n @click=\"handleViewEnterprise\"\n >\n {{ $t('subscription.viewEnterprise') }}\n <i class=\"pi pi-external-link\" />\n </Button>\n </div>\n </div>\n </div>\n <div v-else class=\"legacy-dialog relative grid h-full grid-cols-5\">\n <!-- Custom close button -->\n <Button\n size=\"icon\"\n variant=\"muted-textonly\"\n class=\"rounded-full absolute top-2.5 right-2.5 z-10 h-8 w-8 p-0 text-white hover:bg-white/20\"\n :aria-label=\"$t('g.close')\"\n @click=\"handleClose\"\n >\n <i class=\"pi pi-times\" />\n </Button>\n\n <div\n class=\"relative col-span-2 flex items-center justify-center overflow-hidden rounded-sm\"\n >\n <video\n autoplay\n loop\n muted\n playsinline\n class=\"h-full min-w-[125%] object-cover p-0\"\n style=\"margin-left: -20%\"\n >\n <source\n src=\"/assets/images/cloud-subscription.webm\"\n type=\"video/webm\"\n />\n </video>\n </div>\n\n <div class=\"col-span-3 flex flex-col justify-between p-8\">\n <div>\n <div class=\"flex flex-col gap-6\">\n <div class=\"inline-flex items-center gap-2\">\n <div class=\"text-sm text-text-primary\">\n {{ $t('subscription.required.title') }}\n </div>\n <CloudBadge\n reverse-order\n no-padding\n background-color=\"var(--p-dialog-background)\"\n use-subscription\n />\n </div>\n\n <div class=\"flex items-baseline gap-2\">\n <span class=\"text-4xl font-bold\">{{ formattedMonthlyPrice }}</span>\n <span class=\"text-xl\">{{ $t('subscription.perMonth') }}</span>\n </div>\n </div>\n\n <SubscriptionBenefits class=\"mt-6 text-muted\" />\n </div>\n\n <div class=\"flex flex-col pt-8\">\n <SubscribeButton\n class=\"py-2 px-4 rounded-lg\"\n :pt=\"{\n root: {\n style: 'background: var(--color-accent-blue, #0B8CE9);'\n },\n label: {\n class: 'font-inter font-[700] text-sm'\n }\n }\"\n @subscribed=\"handleSubscribed\"\n />\n </div>\n </div>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { computed, onBeforeUnmount, watch } from 'vue'\n\nimport CloudBadge from '@/components/topbar/CloudBadge.vue'\nimport Button from '@/components/ui/button/Button.vue'\nimport { MONTHLY_SUBSCRIPTION_PRICE } from '@/config/subscriptionPricesConfig'\nimport PricingTable from '@/platform/cloud/subscription/components/PricingTable.vue'\nimport SubscribeButton from '@/platform/cloud/subscription/components/SubscribeButton.vue'\nimport SubscriptionBenefits from '@/platform/cloud/subscription/components/SubscriptionBenefits.vue'\nimport { useSubscription } from '@/platform/cloud/subscription/composables/useSubscription'\nimport { isCloud } from '@/platform/distribution/types'\nimport { useTelemetry } from '@/platform/telemetry'\nimport { useCommandStore } from '@/stores/commandStore'\n\nconst props = defineProps<{\n onClose: () => void\n}>()\n\nconst emit = defineEmits<{\n close: [subscribed: boolean]\n}>()\n\nconst { fetchStatus, isActiveSubscription } = useSubscription()\n\n// Legacy price for non-tier flow with locale-aware formatting\nconst formattedMonthlyPrice = new Intl.NumberFormat(\n navigator.language || 'en-US',\n {\n style: 'currency',\n currency: 'USD',\n minimumFractionDigits: 0,\n maximumFractionDigits: 0\n }\n).format(MONTHLY_SUBSCRIPTION_PRICE)\nconst commandStore = useCommandStore()\nconst telemetry = useTelemetry()\n\n// Always show custom pricing table for cloud subscriptions\nconst showCustomPricingTable = computed(\n () => isCloud && window.__CONFIG__?.subscription_required\n)\n\nconst POLL_INTERVAL_MS = 3000\nconst MAX_POLL_ATTEMPTS = 3\nlet pollInterval: number | null = null\nlet pollAttempts = 0\n\nconst stopPolling = () => {\n if (pollInterval) {\n clearInterval(pollInterval)\n pollInterval = null\n }\n}\n\nconst startPolling = () => {\n stopPolling()\n pollAttempts = 0\n\n const poll = async () => {\n try {\n await fetchStatus()\n pollAttempts++\n\n if (pollAttempts >= MAX_POLL_ATTEMPTS) {\n stopPolling()\n }\n } catch (error) {\n console.error(\n '[SubscriptionDialog] Failed to poll subscription status',\n error\n )\n stopPolling()\n }\n }\n\n void poll()\n pollInterval = window.setInterval(() => {\n void poll()\n }, POLL_INTERVAL_MS)\n}\n\nconst handleWindowFocus = () => {\n if (showCustomPricingTable.value) {\n startPolling()\n }\n}\n\nwatch(\n showCustomPricingTable,\n (enabled) => {\n if (enabled) {\n window.addEventListener('focus', handleWindowFocus)\n } else {\n window.removeEventListener('focus', handleWindowFocus)\n stopPolling()\n }\n },\n { immediate: true }\n)\n\nwatch(\n () => isActiveSubscription.value,\n (isActive) => {\n if (isActive && showCustomPricingTable.value) {\n emit('close', true)\n }\n }\n)\n\nconst handleSubscribed = () => {\n emit('close', true)\n}\n\nconst handleClose = () => {\n stopPolling()\n props.onClose()\n}\n\nconst handleContactUs = async () => {\n telemetry?.trackHelpResourceClicked({\n resource_type: 'help_feedback',\n is_external: true,\n source: 'subscription'\n })\n await commandStore.execute('Comfy.ContactSupport')\n}\n\nconst handleViewEnterprise = () => {\n telemetry?.trackHelpResourceClicked({\n resource_type: 'docs',\n is_external: true,\n source: 'subscription'\n })\n window.open('https://www.comfy.org/cloud/enterprise', '_blank')\n}\n\nonBeforeUnmount(() => {\n stopPolling()\n window.removeEventListener('focus', handleWindowFocus)\n})\n</script>\n\n<style scoped>\n.legacy-dialog :deep(.bg-comfy-menu-secondary) {\n background-color: transparent;\n}\n\n.legacy-dialog :deep(.p-button) {\n color: white;\n}\n</style>\n"],"names":["cloudBadge","computed","t","_imports_0","MONTHLY_SUBSCRIPTION_PRICE","PLAN_ORDER","acc","plan","index","billingCycleOptions","tiers","TIER_PRICING","n","useI18n","getAuthHeader","useFirebaseAuthStore","isActiveSubscription","subscriptionTier","isYearlySubscription","useSubscription","accessBillingPortal","reportError","useFirebaseAuthActions","wrapWithErrorHandlingAsync","useErrorHandling","isLoading","ref","loadingTier","popover","currentBillingCycle","currentTierKey","TIER_TO_KEY","isCurrentPlan","__name","tierKey","selectedIsYearly","togglePopover","event","getButtonLabel","tier","planName","getButtonSeverity","getButtonTextClass","getPrice","getAnnualTotal","getCreditsDisplay","handleSubscribe","_hoisted_1","_hoisted_2","_hoisted_3","_hoisted_4","_hoisted_5","_openBlock","_createElementBlock","_createElementVNode","_toDisplayString","_ctx","POLL_INTERVAL_MS","MAX_POLL_ATTEMPTS","props","__props","emit","__emit","fetchStatus","formattedMonthlyPrice","commandStore","useCommandStore","showCustomPricingTable","isCloud","pollInterval","pollAttempts","stopPolling","startPolling","poll","error","handleWindowFocus","watch","enabled","isActive","handleSubscribed","handleClose","handleContactUs","handleViewEnterprise","onBeforeUnmount"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"SubscriptionRequiredDialogContent-oUSDZGJZ.js","sources":["../../src/components/topbar/CloudBadge.vue","../../../../../../../assets/images/cloud-subscription.webm","../../src/config/subscriptionPricesConfig.ts","../../src/platform/cloud/subscription/utils/subscriptionTierRank.ts","../../src/platform/cloud/subscription/components/PricingTable.vue","../../src/platform/cloud/subscription/components/SubscriptionBenefits.vue","../../src/platform/cloud/subscription/components/SubscriptionRequiredDialogContent.vue"],"sourcesContent":["<template>\n <TopbarBadge\n :badge=\"cloudBadge\"\n :display-mode=\"displayMode\"\n :reverse-order=\"reverseOrder\"\n :no-padding=\"noPadding\"\n :background-color=\"backgroundColor\"\n />\n</template>\n\n<script setup lang=\"ts\">\nimport { computed } from 'vue'\n\nimport { t } from '@/i18n'\nimport type { TopbarBadge as TopbarBadgeType } from '@/types/comfy'\n\nimport TopbarBadge from './TopbarBadge.vue'\n\nwithDefaults(\n defineProps<{\n displayMode?: 'full' | 'compact' | 'icon-only'\n reverseOrder?: boolean\n noPadding?: boolean\n backgroundColor?: string\n }>(),\n {\n displayMode: 'full',\n reverseOrder: false,\n noPadding: false,\n backgroundColor: 'var(--comfy-menu-bg)'\n }\n)\n\nconst cloudBadge = computed<TopbarBadgeType>(() => ({\n label: t('g.beta'),\n text: 'Comfy Cloud'\n}))\n</script>\n","export default \"__VITE_PUBLIC_ASSET__b4a125b1__\"","export const MONTHLY_SUBSCRIPTION_PRICE = 20\n","import type { TierKey } from '@/platform/cloud/subscription/constants/tierPricing'\n\nexport type BillingCycle = 'monthly' | 'yearly'\n\ntype RankedTierKey = Exclude<TierKey, 'founder'>\ntype RankedPlanKey = `${BillingCycle}-${RankedTierKey}`\n\ninterface PlanDescriptor {\n tierKey: TierKey\n billingCycle: BillingCycle\n}\n\nconst PLAN_ORDER: RankedPlanKey[] = [\n 'yearly-pro',\n 'yearly-creator',\n 'yearly-standard',\n 'monthly-pro',\n 'monthly-creator',\n 'monthly-standard'\n]\n\nconst PLAN_RANK = PLAN_ORDER.reduce<Map<RankedPlanKey, number>>(\n (acc, plan, index) => acc.set(plan, index),\n new Map()\n)\n\nconst toRankedPlanKey = (\n tierKey: TierKey,\n billingCycle: BillingCycle\n): RankedPlanKey | null => {\n if (tierKey === 'founder') return null\n return `${billingCycle}-${tierKey}` as RankedPlanKey\n}\n\nexport const getPlanRank = ({\n tierKey,\n billingCycle\n}: PlanDescriptor): number => {\n const planKey = toRankedPlanKey(tierKey, billingCycle)\n if (!planKey) return Number.POSITIVE_INFINITY\n\n return PLAN_RANK.get(planKey) ?? Number.POSITIVE_INFINITY\n}\n\ninterface DowngradeCheckParams {\n current: PlanDescriptor\n target: PlanDescriptor\n}\n\nexport const isPlanDowngrade = ({\n current,\n target\n}: DowngradeCheckParams): boolean => {\n const currentRank = getPlanRank(current)\n const targetRank = getPlanRank(target)\n\n return targetRank > currentRank\n}\n","<template>\n <div class=\"flex flex-col gap-8\">\n <div class=\"flex justify-center\">\n <SelectButton\n v-model=\"currentBillingCycle\"\n :options=\"billingCycleOptions\"\n option-label=\"label\"\n option-value=\"value\"\n :allow-empty=\"false\"\n unstyled\n :pt=\"{\n root: {\n class: 'flex gap-1 bg-secondary-background rounded-lg p-1.5'\n },\n pcToggleButton: {\n root: ({ context }: ToggleButtonPassThroughMethodOptions) => ({\n class: [\n 'w-36 h-8 rounded-md transition-colors cursor-pointer border-none outline-none ring-0 text-sm font-medium flex items-center justify-center',\n context.active\n ? 'bg-base-foreground text-base-background'\n : 'bg-transparent text-muted-foreground hover:bg-secondary-background-hover'\n ]\n }),\n label: { class: 'flex items-center gap-2 ' }\n }\n }\"\n >\n <template #option=\"{ option }\">\n <div class=\"flex items-center gap-2\">\n <span>{{ option.label }}</span>\n <div\n v-if=\"option.value === 'yearly'\"\n class=\"bg-primary-background text-white text-[11px] px-1 py-0.5 rounded-full flex items-center font-bold\"\n >\n -20%\n </div>\n </div>\n </template>\n </SelectButton>\n </div>\n <div class=\"flex flex-col xl:flex-row items-stretch gap-6\">\n <div\n v-for=\"tier in tiers\"\n :key=\"tier.id\"\n :class=\"\n cn(\n 'flex-1 flex flex-col rounded-2xl border border-border-default bg-base-background shadow-[0_0_12px_rgba(0,0,0,0.1)]',\n tier.isPopular ? 'border-muted-foreground' : ''\n )\n \"\n >\n <div class=\"p-8 pb-0 flex flex-col gap-8\">\n <div class=\"flex flex-row items-center gap-2 justify-between\">\n <span\n class=\"font-inter text-base font-bold leading-normal text-base-foreground\"\n >\n {{ tier.name }}\n </span>\n <div\n v-if=\"tier.isPopular\"\n class=\"rounded-full bg-base-foreground px-1.5 text-[11px] font-bold uppercase text-base-background h-5 tracking-tight flex items-center\"\n >\n {{ t('subscription.mostPopular') }}\n </div>\n </div>\n <div class=\"flex flex-col\">\n <div class=\"flex flex-col gap-2\">\n <div class=\"flex flex-row items-baseline gap-2\">\n <span\n class=\"font-inter text-[32px] font-semibold leading-normal text-base-foreground\"\n >\n <span\n v-show=\"currentBillingCycle === 'yearly'\"\n class=\"line-through text-2xl text-muted-foreground\"\n >\n ${{ tier.pricing.monthly }}\n </span>\n ${{ getPrice(tier) }}\n </span>\n <span\n class=\"font-inter text-xl leading-normal text-base-foreground\"\n >\n {{ t('subscription.usdPerMonth') }}\n </span>\n </div>\n <div class=\"flex items-center gap-2\">\n <span class=\"text-sm text-muted-foreground\">\n {{\n currentBillingCycle === 'yearly'\n ? t('subscription.billedYearly', {\n total: `$${getAnnualTotal(tier)}`\n })\n : t('subscription.billedMonthly')\n }}\n </span>\n </div>\n </div>\n </div>\n\n <div class=\"flex flex-col gap-4 pb-0 flex-1\">\n <div class=\"flex flex-row items-center justify-between\">\n <span\n class=\"font-inter text-sm font-normal leading-normal text-foreground\"\n >\n {{\n currentBillingCycle === 'yearly'\n ? t('subscription.yearlyCreditsLabel')\n : t('subscription.monthlyCreditsLabel')\n }}\n </span>\n <div class=\"flex flex-row items-center gap-1\">\n <i class=\"icon-[lucide--component] text-amber-400 text-sm\" />\n <span\n class=\"font-inter text-sm font-bold leading-normal text-base-foreground\"\n >\n {{ n(getCreditsDisplay(tier)) }}\n </span>\n </div>\n </div>\n\n <div class=\"flex flex-row items-center justify-between\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.maxDurationLabel') }}\n </span>\n <span\n class=\"font-inter text-sm font-bold leading-normal text-base-foreground\"\n >\n {{ tier.maxDuration }}\n </span>\n </div>\n\n <div class=\"flex flex-row items-center justify-between\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.gpuLabel') }}\n </span>\n <i class=\"pi pi-check text-xs text-success-foreground\" />\n </div>\n\n <div class=\"flex flex-row items-center justify-between\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.addCreditsLabel') }}\n </span>\n <i class=\"pi pi-check text-xs text-success-foreground\" />\n </div>\n\n <div class=\"flex flex-row items-center justify-between\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.customLoRAsLabel') }}\n </span>\n <i\n v-if=\"tier.customLoRAs\"\n class=\"pi pi-check text-xs text-success-foreground\"\n />\n <i v-else class=\"pi pi-times text-xs text-foreground\" />\n </div>\n\n <div class=\"flex flex-col gap-2\">\n <div class=\"flex flex-row items-start justify-between\">\n <div class=\"flex flex-col gap-2\">\n <span class=\"text-sm font-normal text-foreground\">\n {{ t('subscription.videoEstimateLabel') }}\n </span>\n <div class=\"flex flex-row items-center gap-2 group pt-2\">\n <i\n class=\"pi pi-question-circle text-xs text-muted-foreground group-hover:text-base-foreground\"\n />\n <span\n class=\"text-sm font-normal text-muted-foreground cursor-pointer group-hover:text-base-foreground\"\n @click=\"togglePopover\"\n >\n {{ t('subscription.videoEstimateHelp') }}\n </span>\n </div>\n </div>\n <span\n class=\"font-inter text-sm font-bold leading-normal text-base-foreground\"\n >\n ~{{ n(tier.pricing.videoEstimate) }}\n </span>\n </div>\n </div>\n </div>\n </div>\n <div class=\"flex flex-col p-8\">\n <Button\n :variant=\"getButtonSeverity(tier)\"\n :disabled=\"isLoading || isCurrentPlan(tier.key)\"\n :loading=\"loadingTier === tier.key\"\n :class=\"\n cn(\n 'h-10 w-full',\n getButtonTextClass(tier),\n tier.key === 'creator'\n ? 'bg-base-foreground border-transparent hover:bg-inverted-background-hover'\n : 'bg-secondary-background border-transparent hover:bg-secondary-background-hover focus:bg-secondary-background-selected'\n )\n \"\n @click=\"() => handleSubscribe(tier.key)\"\n >\n {{ getButtonLabel(tier) }}\n </Button>\n </div>\n </div>\n </div>\n\n <!-- Video Estimate Help Popover -->\n <Popover\n ref=\"popover\"\n append-to=\"body\"\n :auto-z-index=\"true\"\n :base-z-index=\"1000\"\n :dismissable=\"true\"\n :close-on-escape=\"true\"\n unstyled\n :pt=\"{\n root: {\n class:\n 'rounded-lg border border-interface-stroke bg-interface-panel-surface shadow-lg p-4 max-w-xs'\n }\n }\"\n >\n <div class=\"flex flex-col gap-2\">\n <p class=\"text-sm text-base-foreground\">\n {{ t('subscription.videoEstimateExplanation') }}\n </p>\n <a\n href=\"https://cloud.comfy.org/?template=video_wan2_2_14B_fun_camera\"\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n class=\"text-sm text-azure-600 hover:text-azure-400 underline\"\n >\n {{ t('subscription.videoEstimateTryTemplate') }}\n </a>\n </div>\n </Popover>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { cn } from '@comfyorg/tailwind-utils'\nimport Popover from 'primevue/popover'\nimport SelectButton from 'primevue/selectbutton'\nimport type { ToggleButtonPassThroughMethodOptions } from 'primevue/togglebutton'\nimport { computed, ref } from 'vue'\nimport { useI18n } from 'vue-i18n'\n\nimport Button from '@/components/ui/button/Button.vue'\nimport { useFirebaseAuthActions } from '@/composables/auth/useFirebaseAuthActions'\nimport { useErrorHandling } from '@/composables/useErrorHandling'\nimport { getComfyApiBaseUrl } from '@/config/comfyApi'\nimport { t } from '@/i18n'\nimport { useSubscription } from '@/platform/cloud/subscription/composables/useSubscription'\nimport {\n TIER_PRICING,\n TIER_TO_KEY\n} from '@/platform/cloud/subscription/constants/tierPricing'\nimport type {\n TierKey,\n TierPricing\n} from '@/platform/cloud/subscription/constants/tierPricing'\nimport { isPlanDowngrade } from '@/platform/cloud/subscription/utils/subscriptionTierRank'\nimport type { BillingCycle } from '@/platform/cloud/subscription/utils/subscriptionTierRank'\nimport { isCloud } from '@/platform/distribution/types'\nimport {\n FirebaseAuthStoreError,\n useFirebaseAuthStore\n} from '@/stores/firebaseAuthStore'\nimport type { components } from '@/types/comfyRegistryTypes'\n\ntype SubscriptionTier = components['schemas']['SubscriptionTier']\ntype CheckoutTierKey = Exclude<TierKey, 'founder'>\ntype CheckoutTier = CheckoutTierKey | `${CheckoutTierKey}-yearly`\n\nconst getCheckoutTier = (\n tierKey: CheckoutTierKey,\n billingCycle: BillingCycle\n): CheckoutTier => (billingCycle === 'yearly' ? `${tierKey}-yearly` : tierKey)\n\ninterface BillingCycleOption {\n label: string\n value: BillingCycle\n}\n\ninterface PricingTierConfig {\n id: SubscriptionTier\n key: CheckoutTierKey\n name: string\n pricing: TierPricing\n maxDuration: string\n customLoRAs: boolean\n isPopular?: boolean\n}\n\nconst billingCycleOptions: BillingCycleOption[] = [\n { label: t('subscription.yearly'), value: 'yearly' },\n { label: t('subscription.monthly'), value: 'monthly' }\n]\n\nconst tiers: PricingTierConfig[] = [\n {\n id: 'STANDARD',\n key: 'standard',\n name: t('subscription.tiers.standard.name'),\n pricing: TIER_PRICING.standard,\n maxDuration: t('subscription.maxDuration.standard'),\n customLoRAs: false,\n isPopular: false\n },\n {\n id: 'CREATOR',\n key: 'creator',\n name: t('subscription.tiers.creator.name'),\n pricing: TIER_PRICING.creator,\n maxDuration: t('subscription.maxDuration.creator'),\n customLoRAs: true,\n isPopular: true\n },\n {\n id: 'PRO',\n key: 'pro',\n name: t('subscription.tiers.pro.name'),\n pricing: TIER_PRICING.pro,\n maxDuration: t('subscription.maxDuration.pro'),\n customLoRAs: true,\n isPopular: false\n }\n]\n\nconst { n } = useI18n()\nconst { getAuthHeader } = useFirebaseAuthStore()\nconst { isActiveSubscription, subscriptionTier, isYearlySubscription } =\n useSubscription()\nconst { accessBillingPortal, reportError } = useFirebaseAuthActions()\nconst { wrapWithErrorHandlingAsync } = useErrorHandling()\n\nconst isLoading = ref(false)\nconst loadingTier = ref<CheckoutTierKey | null>(null)\nconst popover = ref()\nconst currentBillingCycle = ref<BillingCycle>('yearly')\n\nconst currentTierKey = computed<TierKey | null>(() =>\n subscriptionTier.value ? TIER_TO_KEY[subscriptionTier.value] : null\n)\n\nconst currentPlanDescriptor = computed(() => {\n if (!currentTierKey.value) return null\n\n return {\n tierKey: currentTierKey.value,\n billingCycle: isYearlySubscription.value ? 'yearly' : 'monthly'\n } as const\n})\n\nconst isCurrentPlan = (tierKey: CheckoutTierKey): boolean => {\n if (!currentTierKey.value) return false\n\n const selectedIsYearly = currentBillingCycle.value === 'yearly'\n\n return (\n currentTierKey.value === tierKey &&\n isYearlySubscription.value === selectedIsYearly\n )\n}\n\nconst togglePopover = (event: Event) => {\n popover.value.toggle(event)\n}\n\nconst getButtonLabel = (tier: PricingTierConfig): string => {\n if (isCurrentPlan(tier.key)) return t('subscription.currentPlan')\n\n const planName =\n currentBillingCycle.value === 'yearly'\n ? t('subscription.tierNameYearly', { name: tier.name })\n : tier.name\n\n return isActiveSubscription.value\n ? t('subscription.changeTo', { plan: planName })\n : t('subscription.subscribeTo', { plan: planName })\n}\n\nconst getButtonSeverity = (tier: PricingTierConfig): 'primary' | 'secondary' =>\n isCurrentPlan(tier.key)\n ? 'secondary'\n : tier.key === 'creator'\n ? 'primary'\n : 'secondary'\n\nconst getButtonTextClass = (tier: PricingTierConfig): string =>\n tier.key === 'creator'\n ? 'font-inter text-sm font-bold leading-normal text-base-background'\n : 'font-inter text-sm font-bold leading-normal text-primary-foreground'\n\nconst getPrice = (tier: PricingTierConfig): number =>\n tier.pricing[currentBillingCycle.value]\n\nconst getAnnualTotal = (tier: PricingTierConfig): number =>\n tier.pricing.yearly * 12\n\nconst getCreditsDisplay = (tier: PricingTierConfig): number =>\n tier.pricing.credits * (currentBillingCycle.value === 'yearly' ? 12 : 1)\n\nconst initiateCheckout = async (tierKey: CheckoutTierKey) => {\n const authHeader = await getAuthHeader()\n if (!authHeader) {\n throw new FirebaseAuthStoreError(t('toastMessages.userNotAuthenticated'))\n }\n\n const checkoutTier = getCheckoutTier(tierKey, currentBillingCycle.value)\n const response = await fetch(\n `${getComfyApiBaseUrl()}/customers/cloud-subscription-checkout/${checkoutTier}`,\n {\n method: 'POST',\n headers: { ...authHeader, 'Content-Type': 'application/json' }\n }\n )\n\n if (!response.ok) {\n let errorMessage = 'Failed to initiate checkout'\n try {\n const errorData = await response.json()\n errorMessage = errorData.message || errorMessage\n } catch {\n // If JSON parsing fails, try to get text response or use HTTP status\n try {\n const errorText = await response.text()\n errorMessage =\n errorText || `HTTP ${response.status} ${response.statusText}`\n } catch {\n errorMessage = `HTTP ${response.status} ${response.statusText}`\n }\n }\n\n throw new FirebaseAuthStoreError(\n t('toastMessages.failedToInitiateSubscription', {\n error: errorMessage\n })\n )\n }\n\n return await response.json()\n}\n\nconst handleSubscribe = wrapWithErrorHandlingAsync(\n async (tierKey: CheckoutTierKey) => {\n if (!isCloud || isLoading.value || isCurrentPlan(tierKey)) return\n\n isLoading.value = true\n loadingTier.value = tierKey\n\n try {\n if (isActiveSubscription.value) {\n // Pass the target tier to create a deep link to subscription update confirmation\n const checkoutTier = getCheckoutTier(tierKey, currentBillingCycle.value)\n const targetPlan = {\n tierKey,\n billingCycle: currentBillingCycle.value\n }\n const downgrade =\n currentPlanDescriptor.value &&\n isPlanDowngrade({\n current: currentPlanDescriptor.value,\n target: targetPlan\n })\n\n if (downgrade) {\n // TODO(COMFY-StripeProration): Remove once backend checkout creation mirrors portal proration (\"change at billing end\")\n await accessBillingPortal()\n } else {\n await accessBillingPortal(checkoutTier)\n }\n } else {\n const response = await initiateCheckout(tierKey)\n if (response.checkout_url) {\n window.open(response.checkout_url, '_blank')\n }\n }\n } finally {\n isLoading.value = false\n loadingTier.value = null\n }\n },\n reportError\n)\n</script>\n","<template>\n <div class=\"flex flex-col items-start gap-0 self-stretch\">\n <div class=\"flex items-center gap-2 py-2\">\n <i class=\"pi pi-check text-xs text-text-primary\" />\n <span class=\"text-sm text-text-primary\">\n {{ $t('subscription.benefits.benefit1') }}\n </span>\n </div>\n\n <div class=\"flex items-center gap-2 py-2\">\n <i class=\"pi pi-check text-xs text-text-primary\" />\n <span class=\"text-sm text-text-primary\">\n {{ $t('subscription.benefits.benefit2') }}\n </span>\n </div>\n </div>\n</template>\n\n<script setup lang=\"ts\"></script>\n","<template>\n <div\n v-if=\"showCustomPricingTable\"\n class=\"relative flex flex-col p-4 pt-8 md:p-16 !overflow-y-auto h-full gap-8\"\n >\n <Button\n size=\"icon\"\n variant=\"muted-textonly\"\n class=\"rounded-full shrink-0 text-text-secondary hover:bg-white/10 absolute right-2.5 top-2.5\"\n :aria-label=\"$t('g.close')\"\n @click=\"handleClose\"\n >\n <i class=\"pi pi-times text-xl\" />\n </Button>\n <div class=\"text-center\">\n <h2 class=\"text-xl lg:text-2xl text-muted-foreground m-0\">\n {{ $t('subscription.description') }}\n </h2>\n </div>\n\n <PricingTable class=\"flex-1\" />\n\n <!-- Contact and Enterprise Links -->\n <div class=\"flex flex-col items-center gap-2\">\n <p class=\"text-sm text-text-secondary m-0\">\n {{ $t('subscription.haveQuestions') }}\n </p>\n <div class=\"flex items-center gap-1.5\">\n <Button\n variant=\"muted-textonly\"\n class=\"h-6 p-1 text-sm text-text-secondary hover:text-base-foreground\"\n @click=\"handleContactUs\"\n >\n {{ $t('subscription.contactUs') }}\n <i class=\"pi pi-comments\" />\n </Button>\n <span class=\"text-sm text-text-secondary\">{{ $t('g.or') }}</span>\n <Button\n variant=\"muted-textonly\"\n class=\"h-6 p-1 text-sm text-text-secondary hover:text-base-foreground\"\n @click=\"handleViewEnterprise\"\n >\n {{ $t('subscription.viewEnterprise') }}\n <i class=\"pi pi-external-link\" />\n </Button>\n </div>\n </div>\n </div>\n <div v-else class=\"legacy-dialog relative grid h-full grid-cols-5\">\n <!-- Custom close button -->\n <Button\n size=\"icon\"\n variant=\"muted-textonly\"\n class=\"rounded-full absolute top-2.5 right-2.5 z-10 h-8 w-8 p-0 text-white hover:bg-white/20\"\n :aria-label=\"$t('g.close')\"\n @click=\"handleClose\"\n >\n <i class=\"pi pi-times\" />\n </Button>\n\n <div\n class=\"relative col-span-2 flex items-center justify-center overflow-hidden rounded-sm\"\n >\n <video\n autoplay\n loop\n muted\n playsinline\n class=\"h-full min-w-[125%] object-cover p-0\"\n style=\"margin-left: -20%\"\n >\n <source\n src=\"/assets/images/cloud-subscription.webm\"\n type=\"video/webm\"\n />\n </video>\n </div>\n\n <div class=\"col-span-3 flex flex-col justify-between p-8\">\n <div>\n <div class=\"flex flex-col gap-6\">\n <div class=\"inline-flex items-center gap-2\">\n <div class=\"text-sm text-text-primary\">\n {{ $t('subscription.required.title') }}\n </div>\n <CloudBadge\n reverse-order\n no-padding\n background-color=\"var(--p-dialog-background)\"\n use-subscription\n />\n </div>\n\n <div class=\"flex items-baseline gap-2\">\n <span class=\"text-4xl font-bold\">{{ formattedMonthlyPrice }}</span>\n <span class=\"text-xl\">{{ $t('subscription.perMonth') }}</span>\n </div>\n </div>\n\n <SubscriptionBenefits class=\"mt-6 text-muted\" />\n </div>\n\n <div class=\"flex flex-col pt-8\">\n <SubscribeButton\n class=\"py-2 px-4 rounded-lg\"\n :pt=\"{\n root: {\n style: 'background: var(--color-accent-blue, #0B8CE9);'\n },\n label: {\n class: 'font-inter font-[700] text-sm'\n }\n }\"\n @subscribed=\"handleSubscribed\"\n />\n </div>\n </div>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { computed, onBeforeUnmount, watch } from 'vue'\n\nimport CloudBadge from '@/components/topbar/CloudBadge.vue'\nimport Button from '@/components/ui/button/Button.vue'\nimport { MONTHLY_SUBSCRIPTION_PRICE } from '@/config/subscriptionPricesConfig'\nimport PricingTable from '@/platform/cloud/subscription/components/PricingTable.vue'\nimport SubscribeButton from '@/platform/cloud/subscription/components/SubscribeButton.vue'\nimport SubscriptionBenefits from '@/platform/cloud/subscription/components/SubscriptionBenefits.vue'\nimport { useSubscription } from '@/platform/cloud/subscription/composables/useSubscription'\nimport { isCloud } from '@/platform/distribution/types'\nimport { useTelemetry } from '@/platform/telemetry'\nimport { useCommandStore } from '@/stores/commandStore'\n\nconst props = defineProps<{\n onClose: () => void\n}>()\n\nconst emit = defineEmits<{\n close: [subscribed: boolean]\n}>()\n\nconst { fetchStatus, isActiveSubscription } = useSubscription()\n\n// Legacy price for non-tier flow with locale-aware formatting\nconst formattedMonthlyPrice = new Intl.NumberFormat(\n navigator.language || 'en-US',\n {\n style: 'currency',\n currency: 'USD',\n minimumFractionDigits: 0,\n maximumFractionDigits: 0\n }\n).format(MONTHLY_SUBSCRIPTION_PRICE)\nconst commandStore = useCommandStore()\nconst telemetry = useTelemetry()\n\n// Always show custom pricing table for cloud subscriptions\nconst showCustomPricingTable = computed(\n () => isCloud && window.__CONFIG__?.subscription_required\n)\n\nconst POLL_INTERVAL_MS = 3000\nconst MAX_POLL_ATTEMPTS = 3\nlet pollInterval: number | null = null\nlet pollAttempts = 0\n\nconst stopPolling = () => {\n if (pollInterval) {\n clearInterval(pollInterval)\n pollInterval = null\n }\n}\n\nconst startPolling = () => {\n stopPolling()\n pollAttempts = 0\n\n const poll = async () => {\n try {\n await fetchStatus()\n pollAttempts++\n\n if (pollAttempts >= MAX_POLL_ATTEMPTS) {\n stopPolling()\n }\n } catch (error) {\n console.error(\n '[SubscriptionDialog] Failed to poll subscription status',\n error\n )\n stopPolling()\n }\n }\n\n void poll()\n pollInterval = window.setInterval(() => {\n void poll()\n }, POLL_INTERVAL_MS)\n}\n\nconst handleWindowFocus = () => {\n if (showCustomPricingTable.value) {\n startPolling()\n }\n}\n\nwatch(\n showCustomPricingTable,\n (enabled) => {\n if (enabled) {\n window.addEventListener('focus', handleWindowFocus)\n } else {\n window.removeEventListener('focus', handleWindowFocus)\n stopPolling()\n }\n },\n { immediate: true }\n)\n\nwatch(\n () => isActiveSubscription.value,\n (isActive) => {\n if (isActive && showCustomPricingTable.value) {\n emit('close', true)\n }\n }\n)\n\nconst handleSubscribed = () => {\n emit('close', true)\n}\n\nconst handleClose = () => {\n stopPolling()\n props.onClose()\n}\n\nconst handleContactUs = async () => {\n telemetry?.trackHelpResourceClicked({\n resource_type: 'help_feedback',\n is_external: true,\n source: 'subscription'\n })\n await commandStore.execute('Comfy.ContactSupport')\n}\n\nconst handleViewEnterprise = () => {\n telemetry?.trackHelpResourceClicked({\n resource_type: 'docs',\n is_external: true,\n source: 'subscription'\n })\n window.open('https://www.comfy.org/cloud/enterprise', '_blank')\n}\n\nonBeforeUnmount(() => {\n stopPolling()\n window.removeEventListener('focus', handleWindowFocus)\n})\n</script>\n\n<style scoped>\n.legacy-dialog :deep(.bg-comfy-menu-secondary) {\n background-color: transparent;\n}\n\n.legacy-dialog :deep(.p-button) {\n color: white;\n}\n</style>\n"],"names":["cloudBadge","computed","t","_imports_0","MONTHLY_SUBSCRIPTION_PRICE","PLAN_ORDER","acc","plan","index","billingCycleOptions","tiers","TIER_PRICING","n","useI18n","getAuthHeader","useFirebaseAuthStore","isActiveSubscription","subscriptionTier","isYearlySubscription","useSubscription","accessBillingPortal","reportError","useFirebaseAuthActions","wrapWithErrorHandlingAsync","useErrorHandling","isLoading","ref","loadingTier","popover","currentBillingCycle","currentTierKey","TIER_TO_KEY","isCurrentPlan","__name","tierKey","selectedIsYearly","togglePopover","event","getButtonLabel","tier","planName","getButtonSeverity","getButtonTextClass","getPrice","getAnnualTotal","getCreditsDisplay","handleSubscribe","_hoisted_1","_hoisted_2","_hoisted_3","_hoisted_4","_hoisted_5","_openBlock","_createElementBlock","_createElementVNode","_toDisplayString","_ctx","POLL_INTERVAL_MS","MAX_POLL_ATTEMPTS","props","__props","emit","__emit","fetchStatus","formattedMonthlyPrice","commandStore","useCommandStore","showCustomPricingTable","isCloud","pollInterval","pollAttempts","stopPolling","startPolling","poll","error","handleWindowFocus","watch","enabled","isActive","handleSubscribed","handleClose","handleContactUs","handleViewEnterprise","onBeforeUnmount"],"mappings":"+0CAiCA,MAAMA,EAAaC,EAA0B,KAAO,CAClD,MAAOC,EAAE,QAAQ,EACjB,KAAM,aAAA,EACN,yPCpCFC,GAAe,kECAFC,GAA6B,GCYpCC,GAA8B,CAClC,aACA,iBACA,kBACA,cACA,kBACA,kBACF,EAEkBA,GAAW,OAC3B,CAACC,EAAKC,EAAMC,IAAUF,EAAI,IAAIC,EAAMC,CAAK,MACrC,GACN,u8EC6QA,MAAMC,EAA4C,CAChD,CAAE,MAAOP,EAAE,qBAAqB,EAAG,MAAO,QAAA,EAC1C,CAAE,MAAOA,EAAE,sBAAsB,EAAG,MAAO,SAAA,CAAU,EAGjDQ,EAA6B,CACjC,CACE,GAAI,WACJ,IAAK,WACL,KAAMR,EAAE,kCAAkC,EAC1C,QAASS,EAAa,SACtB,YAAaT,EAAE,mCAAmC,EAClD,YAAa,GACb,UAAW,EAAA,EAEb,CACE,GAAI,UACJ,IAAK,UACL,KAAMA,EAAE,iCAAiC,EACzC,QAASS,EAAa,QACtB,YAAaT,EAAE,kCAAkC,EACjD,YAAa,GACb,UAAW,EAAA,EAEb,CACE,GAAI,MACJ,IAAK,MACL,KAAMA,EAAE,6BAA6B,EACrC,QAASS,EAAa,IACtB,YAAaT,EAAE,8BAA8B,EAC7C,YAAa,GACb,UAAW,EAAA,CACb,EAGI,CAAE,EAAAU,CAAA,EAAMC,GAAA,EACR,CAAE,cAAAC,CAAA,EAAkBC,EAAA,EACpB,CAAE,qBAAAC,EAAsB,iBAAAC,EAAkB,qBAAAC,CAAA,EAC9CC,EAAA,EACI,CAAE,oBAAAC,EAAqB,YAAAC,CAAA,EAAgBC,EAAA,EACvC,CAAE,2BAAAC,CAAA,EAA+BC,EAAA,EAEjCC,EAAYC,EAAI,EAAK,EACrBC,EAAcD,EAA4B,IAAI,EAC9CE,EAAUF,EAAA,EACVG,EAAsBH,EAAkB,QAAQ,EAEhDI,EAAiB7B,EAAyB,IAC9CgB,EAAiB,MAAQc,EAAYd,EAAiB,KAAK,EAAI,IAAA,EAGnChB,EAAS,IAChC6B,EAAe,MAEb,CACL,QAASA,EAAe,MACxB,aAAcZ,EAAqB,MAAQ,SAAW,SAAA,EAJtB,IAMnC,EAED,MAAMc,EAAgBC,EAACC,GAAsC,CAC3D,GAAI,CAACJ,EAAe,MAAO,MAAO,GAElC,MAAMK,EAAmBN,EAAoB,QAAU,SAEvD,OACEC,EAAe,QAAUI,GACzBhB,EAAqB,QAAUiB,CAEnC,EATsB,iBAWhBC,EAAgBH,EAACI,GAAiB,CACtCT,EAAQ,MAAM,OAAOS,CAAK,CAC5B,EAFsB,iBAIhBC,EAAiBL,EAACM,GAAoC,CAC1D,GAAIP,EAAcO,EAAK,GAAG,EAAG,OAAOrC,EAAE,0BAA0B,EAEhE,MAAMsC,EACJX,EAAoB,QAAU,SAC1B3B,EAAE,8BAA+B,CAAE,KAAMqC,EAAK,KAAM,EACpDA,EAAK,KAEX,OAAOvB,EAAqB,MACxBd,EAAE,wBAAyB,CAAE,KAAMsC,CAAA,CAAU,EAC7CtC,EAAE,2BAA4B,CAAE,KAAMsC,EAAU,CACtD,EAXuB,kBAajBC,EAAoBR,EAACM,GACzBP,EAAcO,EAAK,GAAG,EAClB,YACAA,EAAK,MAAQ,UACX,UACA,YALkB,qBAOpBG,EAAqBT,EAACM,GAC1BA,EAAK,MAAQ,UACT,mEACA,sEAHqB,sBAKrBI,EAAWV,EAACM,GAChBA,EAAK,QAAQV,EAAoB,KAAK,EADvB,YAGXe,EAAiBX,EAACM,GACtBA,EAAK,QAAQ,OAAS,GADD,kBAGjBM,EAAoBZ,EAACM,GACzBA,EAAK,QAAQ,SAAWV,EAAoB,QAAU,SAAW,GAAK,GAD9C,qBA4CpBiB,EAAkBvB,EACtB,MAAOW,GAA6B,CAqCpC,EACAb,CAAA,umHCjeK0B,GAAA,CAAA,MAAM,8CAA8C,EAClDC,GAAA,CAAA,MAAM,8BAA8B,EAEjCC,GAAA,CAAA,MAAM,2BAA2B,EAKpCC,GAAA,CAAA,MAAM,8BAA8B,EAEjCC,GAAA,CAAA,MAAM,2BAA2B,mBAV3C,OAAAC,EAAA,EAAAC,EAcM,MAdNN,GAcM,CAbJO,EAKM,MALNN,GAKM,aAJJM,EAAmD,IAAA,CAAhD,MAAM,uCAAuC,EAAA,KAAA,EAAA,GAChDA,EAEO,OAFPL,GAEOM,EADFC,EAAA,GAAE,gCAAA,CAAA,EAAA,CAAA,IAITF,EAKM,MALNJ,GAKM,aAJJI,EAAmD,IAAA,CAAhD,MAAM,uCAAuC,EAAA,KAAA,EAAA,GAChDA,EAEO,OAFPH,GAEOI,EADFC,EAAA,GAAE,gCAAA,CAAA,EAAA,CAAA,6vBCsJPC,GAAmB,IACnBC,GAAoB,qHA7B1B,MAAMC,EAAQC,EAIRC,EAAOC,EAIP,CAAE,YAAAC,EAAa,qBAAA/C,CAAA,EAAyBG,EAAA,EAGxC6C,EAAwB,IAAI,KAAK,aACrC,UAAU,UAAY,QACtB,CACE,MAAO,WACP,SAAU,MACV,sBAAuB,EACvB,sBAAuB,CAAA,CACzB,EACA,OAAO5D,EAA0B,EAC7B6D,EAAeC,GAAA,EAIfC,EAAyBlE,EAC7B,IAAMmE,EAA8B,EAKtC,IAAIC,EAA8B,KAC9BC,EAAe,EAEnB,MAAMC,EAActC,EAAA,IAAM,CACpBoC,IACF,cAAcA,CAAY,EAC1BA,EAAe,KAEnB,EALoB,eAOdG,EAAevC,EAAA,IAAM,CACzBsC,EAAA,EACAD,EAAe,EAEf,MAAMG,EAAOxC,EAAA,SAAY,CACvB,GAAI,CACF,MAAM8B,EAAA,EACNO,IAEIA,GAAgBZ,IAClBa,EAAA,CAEJ,OAASG,EAAO,CACd,QAAQ,MACN,0DACAA,CAAA,EAEFH,EAAA,CACF,CACF,EAfa,QAiBRE,EAAA,EACLJ,EAAe,OAAO,YAAY,IAAM,CACjCI,EAAA,CACP,EAAGhB,EAAgB,CACrB,EAzBqB,gBA2BfkB,EAAoB1C,EAAA,IAAM,CAC1BkC,EAAuB,OACzBK,EAAA,CAEJ,EAJ0B,qBAM1BI,EACET,EACCU,GAAY,CACPA,EACF,OAAO,iBAAiB,QAASF,CAAiB,GAElD,OAAO,oBAAoB,QAASA,CAAiB,EACrDJ,EAAA,EAEJ,EACA,CAAE,UAAW,EAAA,CAAK,EAGpBK,EACE,IAAM5D,EAAqB,MAC1B8D,GAAa,CACRA,GAAYX,EAAuB,OACrCN,EAAK,QAAS,EAAI,CAEtB,CAAA,EAGF,MAAMkB,EAAmB9C,EAAA,IAAM,CAC7B4B,EAAK,QAAS,EAAI,CACpB,EAFyB,oBAInBmB,EAAc/C,EAAA,IAAM,CACxBsC,EAAA,EACAZ,EAAM,QAAA,CACR,EAHoB,eAKdsB,EAAkBhD,EAAA,SAAY,CAMlC,MAAMgC,EAAa,QAAQ,sBAAsB,CACnD,EAPwB,mBASlBiB,EAAuBjD,EAAA,IAAM,CAMjC,OAAO,KAAK,yCAA0C,QAAQ,CAChE,EAP6B,wBAS7B,OAAAkD,GAAgB,IAAM,CACpBZ,EAAA,EACA,OAAO,oBAAoB,QAASI,CAAiB,CACvD,CAAC"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{q as N,g as U,G as b}from"./vendor-primevue-B6rcS73U.js";import{_ as A}from"./UserAvatar.vue_vue_type_script_setup_true_lang-ZL9faEyg.js";import{
|
|
2
|
-
//# sourceMappingURL=UserPanel-
|
|
1
|
+
import{q as N,g as U,G as b}from"./vendor-primevue-B6rcS73U.js";import{_ as A}from"./UserAvatar.vue_vue_type_script_setup_true_lang-ZL9faEyg.js";import{p as P,a1 as z,_ as r}from"./index-CuKlxAeN.js";import{bx as B,h as I,j as a,d as l,k as n,e as s,z as d,c as u,u as t,by as e,q as p,A as c,l as O,s as V}from"./vendor-other-CSX7WseZ.js";import"./vendor-vue-CXt3ZZQ3.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-29bN5sfh.js";import"./vendor-tiptap-BkFTmTb3.js";const q={class:"flex h-full flex-col"},E={class:"mb-2 text-2xl font-bold"},L={key:0,class:"flex flex-col gap-2"},j={class:"flex flex-col gap-0.5"},G={class:"font-medium"},K={class:"text-muted"},T={class:"flex flex-col gap-0.5"},F={class:"font-medium"},H={class:"text-muted"},J={class:"flex flex-col gap-0.5"},M={class:"font-medium"},Q={class:"flex items-center gap-1 text-muted"},R={key:2,class:"mt-4 flex flex-col gap-2"},W={key:1,class:"flex flex-col gap-4"},X={class:"text-smoke-600"},re=B({__name:"UserPanel",setup(Y){const g=P(),{loading:m,isLoggedIn:_,isApiKeyLogin:h,isEmailProvider:v,userDisplayName:k,userEmail:x,userPhotoUrl:f,providerName:y,providerIcon:$,handleSignOut:S,handleSignIn:C,handleDeleteAccount:w}=z();return(i,o)=>{const D=I("tooltip");return l(),a(e(b),{value:"User",class:"user-settings-container h-full"},{default:n(()=>[s("div",q,[s("h2",E,t(i.$t("userSettings.title")),1),d(e(N),{class:"mb-3"}),e(_)?(l(),u("div",L,[e(f)?(l(),a(A,{key:0,"photo-url":e(f),shape:"circle",size:"large"},null,8,["photo-url"])):p("",!0),s("div",j,[s("h3",G,t(i.$t("userSettings.name")),1),s("div",K,t(e(k)||i.$t("userSettings.notSet")),1)]),s("div",T,[s("h3",F,t(i.$t("userSettings.email")),1),s("span",H,t(e(x)),1)]),s("div",J,[s("h3",M,t(i.$t("userSettings.provider")),1),s("div",Q,[s("i",{class:V(e($))},null,2),c(" "+t(e(y))+" ",1),e(v)?O((l(),a(r,{key:0,variant:"muted-textonly",size:"icon-sm",onClick:o[0]||(o[0]=Z=>e(g).showUpdatePasswordDialog())},{default:n(()=>o[1]||(o[1]=[s("i",{class:"pi pi-pen-to-square"},null,-1)])),_:1})),[[D,{value:i.$t("userSettings.updatePassword"),showDelay:300}]]):p("",!0)])]),e(m)?(l(),a(e(U),{key:1,class:"mt-4 h-8 w-8",style:{"--pc-spinner-color":"#000"}})):(l(),u("div",R,[d(r,{class:"w-32",variant:"secondary",onClick:e(S)},{default:n(()=>[o[2]||(o[2]=s("i",{class:"pi pi-sign-out"},null,-1)),c(" "+t(i.$t("auth.signOut.signOut")),1)]),_:1},8,["onClick"]),e(h)?p("",!0):(l(),a(r,{key:0,class:"w-fit",variant:"destructive-textonly",onClick:e(w)},{default:n(()=>[c(t(i.$t("auth.deleteAccount.deleteAccount")),1)]),_:1},8,["onClick"]))]))])):(l(),u("div",W,[s("p",X,t(i.$t("auth.login.title")),1),d(r,{class:"w-52",variant:"primary",loading:e(m),onClick:e(C)},{default:n(()=>[o[3]||(o[3]=s("i",{class:"pi pi-user"},null,-1)),c(" "+t(i.$t("auth.login.signInOrSignUp")),1)]),_:1},8,["loading","onClick"])]))])]),_:1})}}});export{re as default};
|
|
2
|
+
//# sourceMappingURL=UserPanel-Do_alb49.js.map
|
comfyui_frontend_package/static/assets/{UserPanel-CrxHTRQZ.js.map → UserPanel-Do_alb49.js.map}
RENAMED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"UserPanel-
|
|
1
|
+
{"version":3,"file":"UserPanel-Do_alb49.js","sources":["../../src/components/dialog/content/setting/UserPanel.vue"],"sourcesContent":["<template>\n <TabPanel value=\"User\" class=\"user-settings-container h-full\">\n <div class=\"flex h-full flex-col\">\n <h2 class=\"mb-2 text-2xl font-bold\">{{ $t('userSettings.title') }}</h2>\n <Divider class=\"mb-3\" />\n\n <!-- Normal User Panel -->\n <div v-if=\"isLoggedIn\" class=\"flex flex-col gap-2\">\n <UserAvatar\n v-if=\"userPhotoUrl\"\n :photo-url=\"userPhotoUrl\"\n shape=\"circle\"\n size=\"large\"\n />\n\n <div class=\"flex flex-col gap-0.5\">\n <h3 class=\"font-medium\">\n {{ $t('userSettings.name') }}\n </h3>\n <div class=\"text-muted\">\n {{ userDisplayName || $t('userSettings.notSet') }}\n </div>\n </div>\n\n <div class=\"flex flex-col gap-0.5\">\n <h3 class=\"font-medium\">\n {{ $t('userSettings.email') }}\n </h3>\n <span class=\"text-muted\">\n {{ userEmail }}\n </span>\n </div>\n\n <div class=\"flex flex-col gap-0.5\">\n <h3 class=\"font-medium\">\n {{ $t('userSettings.provider') }}\n </h3>\n <div class=\"flex items-center gap-1 text-muted\">\n <i :class=\"providerIcon\" />\n {{ providerName }}\n <Button\n v-if=\"isEmailProvider\"\n v-tooltip=\"{\n value: $t('userSettings.updatePassword'),\n showDelay: 300\n }\"\n variant=\"muted-textonly\"\n size=\"icon-sm\"\n @click=\"dialogService.showUpdatePasswordDialog()\"\n >\n <i class=\"pi pi-pen-to-square\" />\n </Button>\n </div>\n </div>\n\n <ProgressSpinner\n v-if=\"loading\"\n class=\"mt-4 h-8 w-8\"\n style=\"--pc-spinner-color: #000\"\n />\n <div v-else class=\"mt-4 flex flex-col gap-2\">\n <Button class=\"w-32\" variant=\"secondary\" @click=\"handleSignOut\">\n <i class=\"pi pi-sign-out\" />\n {{ $t('auth.signOut.signOut') }}\n </Button>\n <Button\n v-if=\"!isApiKeyLogin\"\n class=\"w-fit\"\n variant=\"destructive-textonly\"\n @click=\"handleDeleteAccount\"\n >\n {{ $t('auth.deleteAccount.deleteAccount') }}\n </Button>\n </div>\n </div>\n\n <!-- Login Section -->\n <div v-else class=\"flex flex-col gap-4\">\n <p class=\"text-smoke-600\">\n {{ $t('auth.login.title') }}\n </p>\n\n <Button\n class=\"w-52\"\n variant=\"primary\"\n :loading=\"loading\"\n @click=\"handleSignIn\"\n >\n <i class=\"pi pi-user\" />\n {{ $t('auth.login.signInOrSignUp') }}\n </Button>\n </div>\n </div>\n </TabPanel>\n</template>\n\n<script setup lang=\"ts\">\nimport Divider from 'primevue/divider'\nimport ProgressSpinner from 'primevue/progressspinner'\nimport TabPanel from 'primevue/tabpanel'\n\nimport UserAvatar from '@/components/common/UserAvatar.vue'\nimport Button from '@/components/ui/button/Button.vue'\nimport { useCurrentUser } from '@/composables/auth/useCurrentUser'\nimport { useDialogService } from '@/services/dialogService'\n\nconst dialogService = useDialogService()\nconst {\n loading,\n isLoggedIn,\n isApiKeyLogin,\n isEmailProvider,\n userDisplayName,\n userEmail,\n userPhotoUrl,\n providerName,\n providerIcon,\n handleSignOut,\n handleSignIn,\n handleDeleteAccount\n} = useCurrentUser()\n</script>\n"],"names":["dialogService","useDialogService","loading","isLoggedIn","isApiKeyLogin","isEmailProvider","userDisplayName","userEmail","userPhotoUrl","providerName","providerIcon","handleSignOut","handleSignIn","handleDeleteAccount","useCurrentUser"],"mappings":"y+BA0GA,MAAMA,EAAgBC,EAAA,EAChB,CACJ,QAAAC,EACA,WAAAC,EACA,cAAAC,EACA,gBAAAC,EACA,gBAAAC,EACA,UAAAC,EACA,aAAAC,EACA,aAAAC,EACA,aAAAC,EACA,cAAAC,EACA,aAAAC,EACA,oBAAAC,CAAA,EACEC,EAAA"}
|
comfyui_frontend_package/static/assets/{UserSelectView-tu0lXAri.js → UserSelectView-DVJzD33o.js}
RENAMED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
var S=Object.defineProperty;var y=(n,s)=>S(n,"name",{value:s,configurable:!0});import{bx as k,r as c,o as U,n as V,c as C,d as v,l as E,e as t,v as N,by as o,p as B,s as T,E as p,j as b,k as h,z as i,u,J as z,q as R,A as x}from"./vendor-other-CSX7WseZ.js";import{e as M,q as j,i as q,s as A}from"./vendor-primevue-B6rcS73U.js";import{k as D}from"./vendor-vue-CXt3ZZQ3.js";import{
|
|
2
|
-
//# sourceMappingURL=UserSelectView-
|
|
1
|
+
var S=Object.defineProperty;var y=(n,s)=>S(n,"name",{value:s,configurable:!0});import{bx as k,r as c,o as U,n as V,c as C,d as v,l as E,e as t,v as N,by as o,p as B,s as T,E as p,j as b,k as h,z as i,u,J as z,q as R,A as x}from"./vendor-other-CSX7WseZ.js";import{e as M,q as j,i as q,s as A}from"./vendor-primevue-B6rcS73U.js";import{k as D}from"./vendor-vue-CXt3ZZQ3.js";import{a7 as I,bo as J,ce as K,bt as O,_ as P}from"./index-CuKlxAeN.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-29bN5sfh.js";import"./vendor-tiptap-BkFTmTb3.js";const W={class:"flex w-full grow items-center justify-center overflow-auto"},F=k({__name:"BaseViewTemplate",props:{dark:{type:Boolean,default:!1}},setup(n){const s={color:"rgba(0, 0, 0, 0)",symbolColor:"#d4d4d4"},d={color:"rgba(0, 0, 0, 0)",symbolColor:"#171717"},l=c(null);return U(async()=>{I()&&(await V(),J().changeTheme({...n.dark?s:d,height:l.value?.getBoundingClientRect().height??0}))}),(a,m)=>(v(),C("div",{class:T(["flex h-svh w-screen flex-col font-sans",[a.dark?"dark-theme bg-neutral-900 text-neutral-300":"bg-neutral-300 text-neutral-900"]])},[E(t("div",{ref_key:"topMenuRef",ref:l,class:"app-drag h-(--comfy-topbar-height) w-full"},null,512),[[N,o(K)()]]),t("div",W,[B(a.$slots,"default")])],2))}}),G={id:"comfy-user-selection",class:"relative min-w-84 rounded-lg bg-(--comfy-menu-bg) p-5 px-10 shadow-lg"},H={class:"flex w-full flex-col items-center"},L={class:"flex w-full flex-col gap-2"},Q={for:"new-user-input"},X={class:"flex w-full flex-col gap-2"},Y={for:"existing-user-select"},Z={class:"mt-5"},ie=k({__name:"UserSelectView",setup(n){const s=O(),d=D(),l=c(null),a=c(""),m=c(""),w=p(()=>a.value.trim()!==""),$=p(()=>s.users.find(e=>e.username===a.value)?`User "${a.value}" already exists`:""),g=p(()=>$.value||m.value),_=y(async()=>{try{const e=w.value?await s.createUser(a.value):l.value;if(!e)throw new Error("No user selected");await s.login(e),await d.push("/")}catch(e){m.value=e instanceof Error?e.message:JSON.stringify(e)}},"login");return U(async()=>{s.initialized||await s.initialize()}),(e,r)=>(v(),b(F,{dark:""},{default:h(()=>[t("main",G,[r[2]||(r[2]=t("h1",{class:"my-2.5 mb-7 font-normal"},"ComfyUI",-1)),t("div",H,[t("div",L,[t("label",Q,u(e.$t("userSelect.newUser"))+":",1),i(o(M),{id:"new-user-input",modelValue:a.value,"onUpdate:modelValue":r[0]||(r[0]=f=>a.value=f),placeholder:e.$t("userSelect.enterUsername"),onKeyup:z(_,["enter"])},null,8,["modelValue","placeholder"])]),i(o(j)),t("div",X,[t("label",Y,u(e.$t("userSelect.existingUser"))+":",1),i(o(q),{modelValue:l.value,"onUpdate:modelValue":r[1]||(r[1]=f=>l.value=f),class:"w-full","input-id":"existing-user-select",options:o(s).users,"option-label":"username",placeholder:e.$t("userSelect.selectUser"),disabled:w.value},null,8,["modelValue","options","placeholder","disabled"]),g.value?(v(),b(o(A),{key:0,severity:"error"},{default:h(()=>[x(u(g.value),1)]),_:1})):R("",!0)]),t("footer",Z,[i(P,{onClick:_},{default:h(()=>[x(u(e.$t("userSelect.next")),1)]),_:1})])])])]),_:1}))}});export{ie as default};
|
|
2
|
+
//# sourceMappingURL=UserSelectView-DVJzD33o.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"UserSelectView-
|
|
1
|
+
{"version":3,"file":"UserSelectView-DVJzD33o.js","sources":["../../src/views/templates/BaseViewTemplate.vue","../../src/views/UserSelectView.vue"],"sourcesContent":["<template>\n <div\n class=\"flex h-svh w-screen flex-col font-sans\"\n :class=\"[\n dark\n ? 'dark-theme bg-neutral-900 text-neutral-300'\n : 'bg-neutral-300 text-neutral-900'\n ]\"\n >\n <!-- Virtual top menu for native window (drag handle) -->\n <div\n v-show=\"isNativeWindow()\"\n ref=\"topMenuRef\"\n class=\"app-drag h-(--comfy-topbar-height) w-full\"\n />\n <div class=\"flex w-full grow items-center justify-center overflow-auto\">\n <slot />\n </div>\n </div>\n</template>\n\n<script setup lang=\"ts\">\nimport { nextTick, onMounted, ref } from 'vue'\n\nimport { electronAPI, isElectron, isNativeWindow } from '@/utils/envUtil'\n\nconst { dark = false } = defineProps<{\n dark?: boolean\n}>()\n\nconst darkTheme = {\n color: 'rgba(0, 0, 0, 0)',\n symbolColor: '#d4d4d4'\n}\n\nconst lightTheme = {\n color: 'rgba(0, 0, 0, 0)',\n symbolColor: '#171717'\n}\n\nconst topMenuRef = ref<HTMLDivElement | null>(null)\nonMounted(async () => {\n if (isElectron()) {\n await nextTick()\n\n electronAPI().changeTheme({\n ...(dark ? darkTheme : lightTheme),\n height: topMenuRef.value?.getBoundingClientRect().height ?? 0\n })\n }\n})\n</script>\n","<template>\n <BaseViewTemplate dark>\n <main\n id=\"comfy-user-selection\"\n class=\"relative min-w-84 rounded-lg bg-(--comfy-menu-bg) p-5 px-10 shadow-lg\"\n >\n <h1 class=\"my-2.5 mb-7 font-normal\">ComfyUI</h1>\n <div class=\"flex w-full flex-col items-center\">\n <div class=\"flex w-full flex-col gap-2\">\n <label for=\"new-user-input\">{{ $t('userSelect.newUser') }}:</label>\n <InputText\n id=\"new-user-input\"\n v-model=\"newUsername\"\n :placeholder=\"$t('userSelect.enterUsername')\"\n @keyup.enter=\"login\"\n />\n </div>\n <Divider />\n <div class=\"flex w-full flex-col gap-2\">\n <label for=\"existing-user-select\"\n >{{ $t('userSelect.existingUser') }}:</label\n >\n <Select\n v-model=\"selectedUser\"\n class=\"w-full\"\n input-id=\"existing-user-select\"\n :options=\"userStore.users\"\n option-label=\"username\"\n :placeholder=\"$t('userSelect.selectUser')\"\n :disabled=\"createNewUser\"\n />\n <Message v-if=\"error\" severity=\"error\">\n {{ error }}\n </Message>\n </div>\n <footer class=\"mt-5\">\n <Button @click=\"login\">{{ $t('userSelect.next') }}</Button>\n </footer>\n </div>\n </main>\n </BaseViewTemplate>\n</template>\n\n<script setup lang=\"ts\">\nimport Divider from 'primevue/divider'\nimport InputText from 'primevue/inputtext'\nimport Message from 'primevue/message'\nimport Select from 'primevue/select'\nimport { computed, onMounted, ref } from 'vue'\nimport { useRouter } from 'vue-router'\n\nimport Button from '@/components/ui/button/Button.vue'\nimport type { User } from '@/stores/userStore'\nimport { useUserStore } from '@/stores/userStore'\nimport BaseViewTemplate from '@/views/templates/BaseViewTemplate.vue'\n\nconst userStore = useUserStore()\nconst router = useRouter()\n\nconst selectedUser = ref<User | null>(null)\nconst newUsername = ref('')\nconst loginError = ref('')\n\nconst createNewUser = computed(() => newUsername.value.trim() !== '')\nconst newUserExistsError = computed(() => {\n return userStore.users.find((user) => user.username === newUsername.value)\n ? `User \"${newUsername.value}\" already exists`\n : ''\n})\nconst error = computed(() => newUserExistsError.value || loginError.value)\n\nconst login = async () => {\n try {\n const user = createNewUser.value\n ? await userStore.createUser(newUsername.value)\n : selectedUser.value\n\n if (!user) {\n throw new Error('No user selected')\n }\n\n await userStore.login(user)\n await router.push('/')\n } catch (err) {\n loginError.value = err instanceof Error ? err.message : JSON.stringify(err)\n }\n}\n\nonMounted(async () => {\n if (!userStore.initialized) {\n await userStore.initialize()\n }\n})\n</script>\n"],"names":["darkTheme","lightTheme","topMenuRef","ref","onMounted","isElectron","nextTick","electronAPI","__props","userStore","useUserStore","router","useRouter","selectedUser","newUsername","loginError","createNewUser","computed","newUserExistsError","user","error","login","__name","err"],"mappings":"ksBA8BA,MAAMA,EAAY,CAChB,MAAO,mBACP,YAAa,SAAA,EAGTC,EAAa,CACjB,MAAO,mBACP,YAAa,SAAA,EAGTC,EAAaC,EAA2B,IAAI,EAClD,OAAAC,EAAU,SAAY,CAChBC,MACF,MAAMC,EAAA,EAENC,EAAA,EAAc,YAAY,CACxB,GAAIC,OAAOR,EAAYC,EACvB,OAAQC,EAAW,OAAO,sBAAA,EAAwB,QAAU,CAAA,CAC7D,EAEL,CAAC,ypBCMD,MAAMO,EAAYC,EAAA,EACZC,EAASC,EAAA,EAETC,EAAeV,EAAiB,IAAI,EACpCW,EAAcX,EAAI,EAAE,EACpBY,EAAaZ,EAAI,EAAE,EAEnBa,EAAgBC,EAAS,IAAMH,EAAY,MAAM,KAAA,IAAW,EAAE,EAC9DI,EAAqBD,EAAS,IAC3BR,EAAU,MAAM,KAAMU,GAASA,EAAK,WAAaL,EAAY,KAAK,EACrE,SAASA,EAAY,KAAK,mBAC1B,EACL,EACKM,EAAQH,EAAS,IAAMC,EAAmB,OAASH,EAAW,KAAK,EAEnEM,EAAQC,EAAA,SAAY,CACxB,GAAI,CACF,MAAMH,EAAOH,EAAc,MACvB,MAAMP,EAAU,WAAWK,EAAY,KAAK,EAC5CD,EAAa,MAEjB,GAAI,CAACM,EACH,MAAM,IAAI,MAAM,kBAAkB,EAGpC,MAAMV,EAAU,MAAMU,CAAI,EAC1B,MAAMR,EAAO,KAAK,GAAG,CACvB,OAASY,EAAK,CACZR,EAAW,MAAQQ,aAAe,MAAQA,EAAI,QAAU,KAAK,UAAUA,CAAG,CAC5E,CACF,EAfc,SAiBd,OAAAnB,EAAU,SAAY,CACfK,EAAU,aACb,MAAMA,EAAU,WAAA,CAEpB,CAAC"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
var _=Object.defineProperty;var m=(n,a)=>_(n,"name",{value:a,configurable:!0});import{H as b,p as w}from"./vendor-primevue-B6rcS73U.js";import{e as y}from"./index-
|
|
2
|
-
//# sourceMappingURL=ValueControlPopover-
|
|
1
|
+
var _=Object.defineProperty;var m=(n,a)=>_(n,"name",{value:a,configurable:!0});import{H as b,p as w}from"./vendor-primevue-B6rcS73U.js";import{e as y}from"./index-CuKlxAeN.js";import{bx as C,r as k,E as V,cN as $,j as z,d as r,k as D,e,A as u,u as s,c as d,F as M,y as N,z as B,q as f,s as S,by as p}from"./vendor-other-CSX7WseZ.js";import"./vendor-vue-CXt3ZZQ3.js";import"./vendor-xterm-CWYFmgbN.js";import"./vendor-three-29bN5sfh.js";import"./vendor-tiptap-BkFTmTb3.js";const j={class:"w-113 max-w-md p-4 space-y-4"},E={class:"text-sm text-muted-foreground leading-tight"},F={class:"text-base-foreground font-medium"},q={class:"space-y-2"},A={class:"flex items-center gap-2 flex-1 min-w-0"},H={class:"flex items-center justify-center w-8 h-8 rounded-lg flex-shrink-0 bg-secondary-background border border-border-subtle"},L={key:1,class:"text-xs font-normal text-base-foreground"},O={class:"flex flex-col gap-0.5 min-w-0 flex-1"},P={class:"text-sm font-normal text-base-foreground leading-tight"},T={class:"text-sm font-normal text-muted-foreground leading-tight"},Y=C({__name:"ValueControlPopover",props:{modelValue:{},modelModifiers:{}},emits:["update:modelValue"],setup(n,{expose:a}){const l=k(),g=y();a({toggle:m(o=>{l.value.toggle(o)},"toggle")});const x=[{mode:"fixed",icon:"icon-[lucide--pencil-off]",title:"fixed",description:"fixedDesc"},{mode:"increment",text:"+1",title:"increment",description:"incrementDesc"},{mode:"decrement",text:"-1",title:"decrement",description:"decrementDesc"},{mode:"randomize",icon:"icon-[lucide--shuffle]",title:"randomize",description:"randomizeDesc"}],v=V(()=>g.get("Comfy.WidgetControlMode")),i=$(n,"modelValue");return(o,c)=>(r(),z(p(w),{ref_key:"popover",ref:l,class:"bg-interface-panel-surface border border-interface-stroke rounded-lg"},{default:D(()=>[e("div",j,[e("div",E,[u(s(o.$t("widgets.valueControl.header.prefix"))+" ",1),e("span",F,s(v.value==="before"?o.$t("widgets.valueControl.header.before"):o.$t("widgets.valueControl.header.after")),1),u(" "+s(o.$t("widgets.valueControl.header.postfix")),1)]),e("div",q,[(r(),d(M,null,N(x,t=>e("div",{key:t.mode,class:"flex items-center justify-between py-2 gap-7"},[e("div",A,[e("div",H,[t.icon?(r(),d("i",{key:0,class:S([t.icon,"text-base text-base-foreground"])},null,2)):f("",!0),t.text?(r(),d("span",L,s(t.text),1)):f("",!0)]),e("div",O,[e("div",P,[e("span",null,s(o.$t(`widgets.valueControl.${t.title}`)),1)]),e("div",T,s(o.$t(`widgets.valueControl.${t.description}`)),1)])]),B(p(b),{modelValue:i.value,"onUpdate:modelValue":c[0]||(c[0]=h=>i.value=h),class:"flex-shrink-0","input-id":t.mode,value:t.mode},null,8,["modelValue","input-id","value"])])),64))])])]),_:1},512))}});export{Y as default};
|
|
2
|
+
//# sourceMappingURL=ValueControlPopover-CZIsPw9J.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ValueControlPopover-
|
|
1
|
+
{"version":3,"file":"ValueControlPopover-CZIsPw9J.js","sources":["../../src/renderer/extensions/vueNodes/widgets/components/ValueControlPopover.vue"],"sourcesContent":["<script setup lang=\"ts\">\nimport Popover from 'primevue/popover'\nimport RadioButton from 'primevue/radiobutton'\nimport { computed, ref } from 'vue'\n\nimport { useSettingStore } from '@/platform/settings/settingStore'\nimport type { ControlOptions } from '@/types/simplifiedWidget'\n\ntype ControlOption = {\n description: string\n mode: ControlOptions\n icon?: string\n text?: string\n title: string\n}\n\nconst popover = ref()\nconst settingStore = useSettingStore()\n\nconst toggle = (event: Event) => {\n popover.value.toggle(event)\n}\ndefineExpose({ toggle })\n\nconst controlOptions: ControlOption[] = [\n {\n mode: 'fixed',\n icon: 'icon-[lucide--pencil-off]',\n title: 'fixed',\n description: 'fixedDesc'\n },\n {\n mode: 'increment',\n text: '+1',\n title: 'increment',\n description: 'incrementDesc'\n },\n {\n mode: 'decrement',\n text: '-1',\n title: 'decrement',\n description: 'decrementDesc'\n },\n {\n mode: 'randomize',\n icon: 'icon-[lucide--shuffle]',\n title: 'randomize',\n description: 'randomizeDesc'\n }\n]\n\nconst widgetControlMode = computed(() =>\n settingStore.get('Comfy.WidgetControlMode')\n)\n\nconst controlMode = defineModel<ControlOptions>()\n</script>\n\n<template>\n <Popover\n ref=\"popover\"\n class=\"bg-interface-panel-surface border border-interface-stroke rounded-lg\"\n >\n <div class=\"w-113 max-w-md p-4 space-y-4\">\n <div class=\"text-sm text-muted-foreground leading-tight\">\n {{ $t('widgets.valueControl.header.prefix') }}\n <span class=\"text-base-foreground font-medium\">\n {{\n widgetControlMode === 'before'\n ? $t('widgets.valueControl.header.before')\n : $t('widgets.valueControl.header.after')\n }}\n </span>\n {{ $t('widgets.valueControl.header.postfix') }}\n </div>\n\n <div class=\"space-y-2\">\n <div\n v-for=\"option in controlOptions\"\n :key=\"option.mode\"\n class=\"flex items-center justify-between py-2 gap-7\"\n >\n <div class=\"flex items-center gap-2 flex-1 min-w-0\">\n <div\n class=\"flex items-center justify-center w-8 h-8 rounded-lg flex-shrink-0 bg-secondary-background border border-border-subtle\"\n >\n <i\n v-if=\"option.icon\"\n :class=\"option.icon\"\n class=\"text-base text-base-foreground\"\n />\n <span\n v-if=\"option.text\"\n class=\"text-xs font-normal text-base-foreground\"\n >\n {{ option.text }}\n </span>\n </div>\n\n <div class=\"flex flex-col gap-0.5 min-w-0 flex-1\">\n <div\n class=\"text-sm font-normal text-base-foreground leading-tight\"\n >\n <span>\n {{ $t(`widgets.valueControl.${option.title}`) }}\n </span>\n </div>\n <div\n class=\"text-sm font-normal text-muted-foreground leading-tight\"\n >\n {{ $t(`widgets.valueControl.${option.description}`) }}\n </div>\n </div>\n </div>\n\n <RadioButton\n v-model=\"controlMode\"\n class=\"flex-shrink-0\"\n :input-id=\"option.mode\"\n :value=\"option.mode\"\n />\n </div>\n </div>\n </div>\n </Popover>\n</template>\n"],"names":["popover","ref","settingStore","useSettingStore","__expose","__name","event","controlOptions","widgetControlMode","computed","controlMode","_useModel","__props"],"mappings":"oqCAgBA,MAAMA,EAAUC,EAAA,EACVC,EAAeC,EAAA,EAKrBC,EAAa,CAAE,OAHAC,EAACC,GAAiB,CAC/BN,EAAQ,MAAM,OAAOM,CAAK,CAC5B,EAFe,UAGQ,EAEvB,MAAMC,EAAkC,CACtC,CACE,KAAM,QACN,KAAM,4BACN,MAAO,QACP,YAAa,WAAA,EAEf,CACE,KAAM,YACN,KAAM,KACN,MAAO,YACP,YAAa,eAAA,EAEf,CACE,KAAM,YACN,KAAM,KACN,MAAO,YACP,YAAa,eAAA,EAEf,CACE,KAAM,YACN,KAAM,yBACN,MAAO,YACP,YAAa,eAAA,CACf,EAGIC,EAAoBC,EAAS,IACjCP,EAAa,IAAI,yBAAyB,CAAA,EAGtCQ,EAAcC,EAA2BC,EAAA,YAAC"}
|