@xiaobuyu/nodesign 0.0.5 → 0.0.7

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.
Files changed (137) hide show
  1. package/README.md +1 -1
  2. package/README.zh-CN.md +1 -1
  3. package/package.json +1 -1
  4. package/server/api/assets/helpers.js +18 -0
  5. package/server/api/assets/notes.js +50 -0
  6. package/server/api/assets.js +11 -6
  7. package/server/api/instruction.js +3 -3
  8. package/server/engine/agent/events.js +11 -1
  9. package/server/engine/agent/hooks/failure.js +11 -1
  10. package/server/engine/agent/hooks/lifecycle.js +10 -39
  11. package/server/engine/agent/hooks/post-guidance.js +4 -38
  12. package/server/engine/agent/hooks/user-prompt-submit.js +11 -40
  13. package/server/engine/agent/hooks.js +4 -8
  14. package/server/engine/agent/memory-config.js +61 -0
  15. package/server/engine/agent/prompts/nodesign-prelude.md +14 -12
  16. package/server/engine/agent/prompts/tools/generate-image-cookbook.md +24 -7
  17. package/server/engine/agent/prompts/tools/site-reference.md +13 -3
  18. package/server/engine/agent/session-loop.js +29 -18
  19. package/server/engine/agents/explorer.md +1 -1
  20. package/server/engine/agents/index.js +1 -1
  21. package/server/engine/mcp/index.js +4 -11
  22. package/server/engine/mcp/tools/arrange-on-board.js +3 -1
  23. package/server/engine/mcp/tools/browse-computer.js +2 -1
  24. package/server/engine/mcp/tools/browse-find-batch.js +20 -3
  25. package/server/engine/mcp/tools/browse.js +24 -2
  26. package/server/engine/mcp/tools/crystallize-skill.js +1 -1
  27. package/server/engine/mcp/tools/generate-image.js +50 -70
  28. package/server/engine/mcp/tools/helpers/codex-imagegen.js +139 -0
  29. package/server/engine/mcp/tools/helpers/rembg.js +7 -2
  30. package/server/engine/mcp/tools/helpers/shot-pipeline.js +109 -0
  31. package/server/engine/mcp/tools/list-pages.js +11 -5
  32. package/server/engine/mcp/tools/organize-board.js +26 -1
  33. package/server/engine/mcp/tools/pin-to-board.js +26 -17
  34. package/server/engine/mcp/tools/read-board.js +19 -5
  35. package/server/engine/mcp/tools/relate-on-board.js +42 -4
  36. package/server/engine/mcp/tools/report-issue.js +14 -7
  37. package/server/engine/mcp/tools/screenshot.js +17 -7
  38. package/server/engine/mcp/tools/sketch-on-board.js +13 -5
  39. package/server/engine/mcp/tools/web-search.js +11 -15
  40. package/server/engine/mcp/tools/write-on-board.js +15 -6
  41. package/server/engine/plugins/nodesign/skills/deskskill-engine-mini/SKILL.md +3 -4
  42. package/server/engine/plugins/nodesign/skills/docx-craft/SKILL.md +10 -1
  43. package/server/engine/plugins/nodesign/skills/docx-craft/references/token-schema.md +16 -0
  44. package/server/engine/plugins/nodesign/skills/site-craft/SKILL.md +4 -4
  45. package/server/index.js +0 -2
  46. package/server/lib/artifact-target.js +31 -14
  47. package/server/lib/board-kind-sizes.js +2 -3
  48. package/server/lib/canvas-id.js +29 -4
  49. package/server/lib/export-collect.js +3 -1
  50. package/server/lib/issues-store.js +3 -1
  51. package/server/lib/kinds/docx.js +11 -4
  52. package/server/lib/kinds/index.js +6 -16
  53. package/server/lib/kinds/site.js +40 -7
  54. package/server/lib/rewrite-refs.js +110 -0
  55. package/server/lib/ssrf-guard.js +9 -0
  56. package/server/lib/task-scan.js +18 -0
  57. package/server/projects/board-store.js +42 -1
  58. package/server/projects/memory-migration.js +85 -0
  59. package/server/projects/move-entry.js +11 -1
  60. package/server/projects/ui-config.js +2 -1
  61. package/server/projects/workspace-templates.js +13 -10
  62. package/server/projects/workspace.js +15 -15
  63. package/server/services/rembg-launcher.js +5 -2
  64. package/web/dist/assets/{BrowserWindow-P_vIdh-G.js → BrowserWindow-BoOBaIyz.js} +1 -1
  65. package/web/dist/assets/DeckWindow-Bg3rgkvi.js +11 -0
  66. package/web/dist/assets/{DocxWindow-DSAU1-tD.js → DocxWindow-B_u6aX9o.js} +1 -1
  67. package/web/dist/assets/{MermaidBlock-DR1GikCv.js → MermaidBlock-BO-46Du5.js} +6 -6
  68. package/web/dist/assets/{SiteWindow-92uBuRRR.js → SiteWindow-ConPmzdM.js} +1 -1
  69. package/web/dist/assets/{abnfDiagram-VCTEODGH-uA8Esix4.js → abnfDiagram-VCTEODGH-FCO9yf-n.js} +1 -1
  70. package/web/dist/assets/{arc-D_khH_xN.js → arc-BLcEOSRX.js} +1 -1
  71. package/web/dist/assets/{architectureDiagram-5GKGNRK7-DydJHqOt.js → architectureDiagram-5GKGNRK7-kxiX4TeN.js} +1 -1
  72. package/web/dist/assets/{blockDiagram-NRAW4CY4-B7wBbKiW.js → blockDiagram-NRAW4CY4-CptFksix.js} +1 -1
  73. package/web/dist/assets/{c4Diagram-UCG6FXSJ-6mrH0x7Y.js → c4Diagram-UCG6FXSJ-Dxmxj34F.js} +1 -1
  74. package/web/dist/assets/channel-DFyiuGL0.js +1 -0
  75. package/web/dist/assets/{chunk-2Q5K7J3B-Cuikho5Q.js → chunk-2Q5K7J3B-D9inx5oo.js} +1 -1
  76. package/web/dist/assets/{chunk-5VM5RSS4-3-KZ5AUz.js → chunk-5VM5RSS4-DydfHlEc.js} +1 -1
  77. package/web/dist/assets/{chunk-F27PBJKO-Bkwq2gGU.js → chunk-F27PBJKO-BO7GxhSv.js} +1 -1
  78. package/web/dist/assets/{chunk-G27WJ6UU-BLyQzdGE.js → chunk-G27WJ6UU-BzP6YiQ_.js} +1 -1
  79. package/web/dist/assets/{chunk-JWPE2WC7-B7HxxQds.js → chunk-JWPE2WC7-CHcgcd0s.js} +1 -1
  80. package/web/dist/assets/{chunk-LCL6LL3I-CtXrnUwF.js → chunk-LCL6LL3I-D2Wg5JtX.js} +1 -1
  81. package/web/dist/assets/{chunk-POPQ4Y6H-dxddZlXt.js → chunk-POPQ4Y6H-B2fCRfpM.js} +1 -1
  82. package/web/dist/assets/{chunk-SVP7TREG-DpkmrgHn.js → chunk-SVP7TREG-JSLcsRlZ.js} +1 -1
  83. package/web/dist/assets/{chunk-XXDRQBXY-BwZ7RbpQ.js → chunk-XXDRQBXY-BCjvaeHm.js} +1 -1
  84. package/web/dist/assets/classDiagram-DTDB5LWJ-Aw1f8z-b.js +1 -0
  85. package/web/dist/assets/classDiagram-v2-JRS7N3AN-Aw1f8z-b.js +1 -0
  86. package/web/dist/assets/{cose-bilkent-JH36ORCC-DGFOsMUt.js → cose-bilkent-JH36ORCC-0uKv6oJ7.js} +1 -1
  87. package/web/dist/assets/{cynefin-OW5HDTMX-DUwn3ehS.js → cynefin-OW5HDTMX-Bvt-gEmA.js} +1 -1
  88. package/web/dist/assets/{cynefinDiagram-5FMLGOSQ-DlLAOZ9x.js → cynefinDiagram-5FMLGOSQ-C9Ht02qC.js} +1 -1
  89. package/web/dist/assets/{dagre-3AP2YEHR-CyourLfz.js → dagre-3AP2YEHR-BfxZny4s.js} +1 -1
  90. package/web/dist/assets/{diagram-S7CK7UJ4-BTMbx2np.js → diagram-S7CK7UJ4-CrE0ZETE.js} +1 -1
  91. package/web/dist/assets/{diagram-UQ7AKVKN-UK94_1-P.js → diagram-UQ7AKVKN-BO8VQ4Fx.js} +1 -1
  92. package/web/dist/assets/{diagram-VSXAHHWV-C7zS-v9v.js → diagram-VSXAHHWV-CHUZnR9F.js} +1 -1
  93. package/web/dist/assets/{diagram-VX7I27RA-DKJRa6CK.js → diagram-VX7I27RA-DYQAz1Vu.js} +1 -1
  94. package/web/dist/assets/{diagram-Z3DM3KII-kUbAfGAp.js → diagram-Z3DM3KII-BDjivgLr.js} +1 -1
  95. package/web/dist/assets/{ebnfDiagram-PWID7BFC-CVW16_vb.js → ebnfDiagram-PWID7BFC-Bpe_QVbH.js} +1 -1
  96. package/web/dist/assets/{erDiagram-SSCWMZ5O-BRQMFQ5y.js → erDiagram-SSCWMZ5O-BxhwuAu1.js} +1 -1
  97. package/web/dist/assets/{flowDiagram-A5DVABFB-S34LpLtK.js → flowDiagram-A5DVABFB-CCw2H08-.js} +1 -1
  98. package/web/dist/assets/{ganttDiagram-EL5Y4UJY-BFiqk1-G.js → ganttDiagram-EL5Y4UJY-DtTc7MyI.js} +1 -1
  99. package/web/dist/assets/{gitGraphDiagram-WWUBYQGX-LZsrdyyv.js → gitGraphDiagram-WWUBYQGX-BvORxMd2.js} +1 -1
  100. package/web/dist/assets/index-DGG5wIZs.js +2118 -0
  101. package/web/dist/assets/{infoDiagram-RXCK75RN-0DvN6KIp.js → infoDiagram-RXCK75RN-DMcrkypD.js} +1 -1
  102. package/web/dist/assets/{ishikawaDiagram-5VMMS53U-CaY3A-Bx.js → ishikawaDiagram-5VMMS53U-CZkTIbe-.js} +1 -1
  103. package/web/dist/assets/{journeyDiagram-EYS64GPL-BBeiaCrj.js → journeyDiagram-EYS64GPL-DR0XazdE.js} +1 -1
  104. package/web/dist/assets/{kanban-definition-3QL26DDD-ux42DRXQ.js → kanban-definition-3QL26DDD-DN8VbwVu.js} +1 -1
  105. package/web/dist/assets/{layout-CnXiF_NB.js → layout-9_paCbyt.js} +1 -1
  106. package/web/dist/assets/{linear-BMW0u6G6.js → linear-g6Ct012e.js} +1 -1
  107. package/web/dist/assets/{mindmap-definition-FBJOCRG2-hUxSpdKn.js → mindmap-definition-FBJOCRG2-BGt4omYC.js} +1 -1
  108. package/web/dist/assets/{pegDiagram-XKGWAZYB-aCaQPH0w.js → pegDiagram-XKGWAZYB-uSfS-PBE.js} +1 -1
  109. package/web/dist/assets/{pending-edit-apply-AcdOQ9Ij.js → pending-edit-apply-uP4uvrOD.js} +1 -1
  110. package/web/dist/assets/{pieDiagram-E7YTZNPT-CmOEZ8zg.js → pieDiagram-E7YTZNPT-DpeI935H.js} +1 -1
  111. package/web/dist/assets/{quadrantDiagram-AXDQQJYC-VW6fAhsV.js → quadrantDiagram-AXDQQJYC-B7IuNvWa.js} +1 -1
  112. package/web/dist/assets/{railroadDiagram-O6MQD6OU-CKJ7Ba5K.js → railroadDiagram-O6MQD6OU-ARzYpPQI.js} +1 -1
  113. package/web/dist/assets/{requirementDiagram-EFPCY7ZU-pNGkq9Vw.js → requirementDiagram-EFPCY7ZU-Cj4upkAo.js} +1 -1
  114. package/web/dist/assets/{rotate-cw-KAfChbGV.js → rotate-cw-CXJcyHWk.js} +1 -1
  115. package/web/dist/assets/{sankeyDiagram-P5KCCOFB-BIMmDTfZ.js → sankeyDiagram-P5KCCOFB-OaVwSnLP.js} +1 -1
  116. package/web/dist/assets/{sequenceDiagram-WJ2MYXX4-BBW7wzKY.js → sequenceDiagram-WJ2MYXX4-1yrUbq4t.js} +1 -1
  117. package/web/dist/assets/{sizeCapture-X5ZJPWSS-DdkXmLYR.js → sizeCapture-X5ZJPWSS-nYH5p9D6.js} +1 -1
  118. package/web/dist/assets/{square-dashed-mouse-pointer-CDUlhUP7.js → square-dashed-mouse-pointer-CTtTVKoH.js} +1 -1
  119. package/web/dist/assets/{stateDiagram-HBIQ2CUA-W313Uz16.js → stateDiagram-HBIQ2CUA-Dj5HvyNq.js} +1 -1
  120. package/web/dist/assets/stateDiagram-v2-4QOOHH4V-kJ1m_zJT.js +1 -0
  121. package/web/dist/assets/{swimlanes-XN3QIQJK-C29TL26K.js → swimlanes-XN3QIQJK-umeT0HpB.js} +1 -1
  122. package/web/dist/assets/swimlanesDiagram-VK2B7HYN-DPSkMbbl.js +8 -0
  123. package/web/dist/assets/{timeline-definition-24CTP7MA-CF0JMObX.js → timeline-definition-24CTP7MA-MqnQfHKB.js} +1 -1
  124. package/web/dist/assets/{vennDiagram-4TSXK5OY-DrDFsaH3.js → vennDiagram-4TSXK5OY-b2liyZra.js} +1 -1
  125. package/web/dist/assets/{wardleyDiagram-VM6X3IG4-CVrnRIS_.js → wardleyDiagram-VM6X3IG4-QMK-zNh1.js} +1 -1
  126. package/web/dist/assets/{xychartDiagram-S5SC5T6Z-BvkN1zsT.js → xychartDiagram-S5SC5T6Z-D5Mc6tfA.js} +1 -1
  127. package/web/dist/index.html +1 -1
  128. package/server/api/memory.js +0 -185
  129. package/server/engine/agent/prompts/tools/generate-image-cookbook.gemini-gateway.md +0 -583
  130. package/server/engine/mcp/tools/record-decision.js +0 -140
  131. package/web/dist/assets/DeckWindow-BpLv5082.js +0 -16
  132. package/web/dist/assets/channel-DGkccMO1.js +0 -1
  133. package/web/dist/assets/classDiagram-DTDB5LWJ-BGscw3OD.js +0 -1
  134. package/web/dist/assets/classDiagram-v2-JRS7N3AN-BGscw3OD.js +0 -1
  135. package/web/dist/assets/index-GAamh1p4.js +0 -2152
  136. package/web/dist/assets/stateDiagram-v2-4QOOHH4V-DDhJBZzf.js +0 -1
  137. package/web/dist/assets/swimlanesDiagram-VK2B7HYN-BfN-Xdmu.js +0 -8
@@ -0,0 +1,11 @@
1
+ import{c as Je,r as a,j as e,d as r,G as s,_ as Mt,R as z,F as m,a as F,$ as Ce,u as D,X as ue,w as Rt,e as E,a0 as et,a1 as Ot,a2 as Bt,a3 as ke,a4 as Ht,a5 as tt,P as nt,a6 as _t,a7 as st,a8 as rt,a9 as Dt,aa as qt,ab as It,ac as it,o as lt,ad as Nt,k as Gt,ae as ot,m as Ut,af as Xt,S as Vt,ag as at,ah as Kt,ai as Yt,aj as Ge,ak as Zt,Q as Qt,al as Jt,am as Ct,an as en,M as tn,ao as nn,ap as sn,n as rn,A as ln}from"./index-DGG5wIZs.js";import{d as Ue,c as Xe,M as on,o as an,t as dn,E as cn,C as un,G as xn,p as pn,D as fn,b as gn,a as hn,P as yn,I as mn,R as bn,e as wn}from"./pending-edit-apply-uP4uvrOD.js";import{E as kn,S as vn}from"./square-dashed-mouse-pointer-CTtTVKoH.js";/**
2
+ * @license lucide-react v0.468.0 - ISC
3
+ *
4
+ * This source code is licensed under the ISC license.
5
+ * See the LICENSE file in the root directory of this source tree.
6
+ */const dt=Je("MessageSquare",[["path",{d:"M21 15a2 2 0 0 1-2 2H7l-4 4V5a2 2 0 0 1 2-2h14a2 2 0 0 1 2 2z",key:"1lielz"}]]);/**
7
+ * @license lucide-react v0.468.0 - ISC
8
+ *
9
+ * This source code is licensed under the ISC license.
10
+ * See the LICENSE file in the root directory of this source tree.
11
+ */const jn=Je("ShieldCheck",[["path",{d:"M20 13c0 5-3.5 7.5-7.66 8.95a1 1 0 0 1-.67-.01C7.5 20.5 4 18 4 13V6a1 1 0 0 1 1-1c2 0 4.5-1.2 6.24-2.72a1.17 1.17 0 0 1 1.52 0C14.51 3.81 17 5 19 5a1 1 0 0 1 1 1z",key:"oel41y"}],["path",{d:"m9 12 2 2 4-4",key:"dzmm74"}]]),Sn=1920,zn=1080;function En({src:n,srcDoc:t,mode:i="edit",onSelect:d,onTextEdit:c,onIframeReady:h,zoom:y=1,deckW:u=Sn,deckH:b=zn}){const o=a.useRef(null),p=a.useRef(!1),w=a.useRef(0),[g,v]=a.useState(!1);a.useEffect(()=>{v(!0)},[n,t]),a.useEffect(()=>{const l=o.current;if(!(!l||!p.current))return Ue(l),i==="edit"&&Xe(l,{onSelect:d,onTextEdit:c}),()=>Ue(l)},[i,d,c]),a.useEffect(()=>()=>{var l;try{const S=(l=o.current)==null?void 0:l.contentWindow;S&&typeof S.scrollY=="number"&&(w.current=S.scrollY)}catch{}},[n,t]);const k=()=>{p.current=!0;const l=o.current;if(l){if(h==null||h(l),i==="edit"&&Xe(l,{onSelect:d,onTextEdit:c}),w.current>0)try{requestAnimationFrame(()=>{var S;try{(S=l.contentWindow)==null||S.scrollTo(0,w.current)}catch{}})}catch{}requestAnimationFrame(()=>{requestAnimationFrame(()=>v(!1))})}};return e.jsx("div",{style:{flex:1,minHeight:0,overflow:"hidden",background:r.bgWhite,position:"relative",display:"flex",alignItems:"center",justifyContent:"center"},children:e.jsx("iframe",{ref:o,src:n,srcDoc:t,onLoad:k,sandbox:"allow-scripts allow-same-origin",style:{width:`${u}px`,height:`${b}px`,flexShrink:0,border:0,background:r.bgWhite,transform:y===1?"none":`scale(${y})`,transformOrigin:"center center",opacity:g?.5:1,transition:"opacity 180ms ease-out"}})})}function $n({candidates:n,activeId:t,onSelect:i,onAdd:d,onRemove:c,onRename:h}){if(!n||n.length===0)return null;const y=n.length===1;return e.jsxs("div",{style:{flexShrink:0,height:36,borderBottom:`1px solid ${r.border}`,background:r.bgWhite,padding:`0 ${s.lg}px`,display:"flex",alignItems:"center",gap:s.xs,overflowX:"auto",overflowY:"hidden"},children:[e.jsx(Mt,{size:11,color:r.sub,style:{flexShrink:0,marginRight:s.xs}}),n.map(u=>{const b=u.id===t;return e.jsx(Ln,{candidate:u,active:b,onSelect:()=>i==null?void 0:i(u.id),onRemove:y?null:()=>c==null?void 0:c(u.id),onRename:h},u.id)}),e.jsxs("button",{onClick:d,title:"新建候选(mock 复制当前)",style:{flexShrink:0,padding:`${s.xs}px ${s.md}px`,display:"inline-flex",alignItems:"center",gap:s.xs,fontFamily:F,fontSize:m.xs,color:r.sub,background:"transparent",border:`1px dashed ${r.borderMd}`,borderRadius:z.sm,cursor:"pointer"},onMouseEnter:u=>{u.currentTarget.style.color=r.text2,u.currentTarget.style.background="rgba(0,0,0,0.03)"},onMouseLeave:u=>{u.currentTarget.style.color=r.sub,u.currentTarget.style.background="transparent"},children:[e.jsx(Ce,{size:11})," 新候选"]}),e.jsx("div",{style:{flex:1}}),e.jsxs("span",{style:{fontFamily:F,fontSize:m.xs,color:r.sub,opacity:y?0:.7,flexShrink:0},children:[n.length," 个候选"]})]})}function Ln({candidate:n,active:t,onSelect:i,onRemove:d,onRename:c}){const[h,y]=a.useState(!1),u=D(w=>w.prompt),b=D(w=>w.confirm),o=async w=>{if(w.stopPropagation(),!c)return;const g=await u({title:"重命名候选",initialValue:n.label,placeholder:"候选名"});g&&g.trim()&&g!==n.label&&c(n.id,g.trim())},p=async w=>{w.stopPropagation(),await b({title:"删除候选",message:`删除候选「${n.label}」?`,confirmLabel:"删除",danger:!0})&&d()};return e.jsxs("div",{onMouseEnter:()=>y(!0),onMouseLeave:()=>y(!1),style:{flexShrink:0,position:"relative",display:"inline-flex",alignItems:"center",background:t?"rgba(45,36,24,0.06)":"transparent",borderRadius:z.sm,transition:"background 0.15s"},children:[e.jsx("button",{onClick:i,onDoubleClick:o,title:"双击重命名",style:{padding:`${s.xs}px ${d&&h?s.lg:s.md}px ${s.xs}px ${s.md}px`,fontFamily:F,fontSize:m.xs,fontWeight:t?500:400,color:t?r.text:r.text4,background:"transparent",borderRadius:z.sm,cursor:"pointer",transition:"all 0.15s"},children:n.label}),d&&h&&e.jsx("button",{onClick:p,style:{position:"absolute",right:2,top:"50%",transform:"translateY(-50%)",width:14,height:14,borderRadius:z.xs,background:"rgba(0,0,0,0.06)",color:r.sub,display:"flex",alignItems:"center",justifyContent:"center",cursor:"pointer"},onMouseEnter:w=>{w.currentTarget.style.background="rgba(184,58,42,0.15)",w.currentTarget.style.color=r.error},onMouseLeave:w=>{w.currentTarget.style.background="rgba(0,0,0,0.06)",w.currentTarget.style.color=r.sub},title:"删除候选",children:e.jsx(ue,{size:9})})]})}const de=12,Fn=8;function Se(n,t){const[i,d]=a.useState(null);return a.useLayoutEffect(()=>{const c=n==null?void 0:n.current;if(!c){d(null);return}const h=()=>{const y=c.getBoundingClientRect();if(!y.width&&!y.height){d(null);return}const u=window.innerWidth,b=window.innerHeight,o=Math.max(de,Math.min(y.left,u-t-de)),p=Math.min(y.bottom+Fn,b-de-120);d({position:"fixed",left:o,top:p,maxHeight:b-p-de})};return h(),window.addEventListener("resize",h),()=>window.removeEventListener("resize",h)},[n,t]),i||{position:"absolute",top:78,right:16}}function An({anchorRef:n,onClose:t,iframeDoc:i}){const d=a.useRef(null),c=Se(n,320),[h,y]=a.useState(!1),[u,b]=a.useState(null);a.useEffect(()=>{i&&o()},[i]),a.useEffect(()=>{const p=w=>{var g;d.current&&!d.current.contains(w.target)&&!((g=n==null?void 0:n.current)!=null&&g.contains(w.target))&&(t==null||t())};return window.addEventListener("mousedown",p),()=>window.removeEventListener("mousedown",p)},[t,n]);const o=()=>{i&&(y(!0),setTimeout(()=>{b(Tn(i)),y(!1)},400))};return e.jsxs("div",{ref:d,style:{...c,width:320,background:r.bgWhite,borderRadius:2,boxShadow:"0 2px 4px rgba(0,0,0,0.04), 0 8px 20px rgba(0,0,0,0.08), 0 24px 48px rgba(0,0,0,0.10), inset 0 1px 0 rgba(255,255,255,0.8)",zIndex:60,overflow:"hidden"},children:[e.jsxs("div",{style:{padding:`${s.md}px ${s.lg}px`,display:"flex",alignItems:"center",justifyContent:"space-between",borderBottom:`1px solid ${r.borderLt}`},children:[e.jsx("span",{style:{fontFamily:F,fontSize:m.sm,fontWeight:500,color:r.text},children:"Accessibility Review"}),e.jsx("button",{onClick:o,disabled:h,style:{padding:s.xs,color:r.sub,borderRadius:z.xs,opacity:h?.5:1},title:"重新扫描",children:e.jsx(Rt,{size:11,className:h?"spin":""})})]}),e.jsxs("div",{style:{padding:s.lg,maxHeight:360,overflowY:"auto"},children:[h&&e.jsx("div",{style:{fontFamily:E,fontSize:m.sm,color:r.sub,textAlign:"center",padding:s.lg},children:"扫描中…"}),!h&&u&&e.jsx("div",{style:{display:"flex",flexDirection:"column",gap:s.sm},children:u.map((p,w)=>e.jsx(Pn,{...p},w))})]}),e.jsx("div",{style:{padding:`${s.sm}px ${s.lg}px`,background:r.bgCard,borderTop:`1px solid ${r.borderLt}`,fontFamily:E,fontSize:m.xs,color:r.sub,lineHeight:1.5},children:"P5 接 LLM 真做 contrast / hierarchy / usability 审查;当前是启发式扫描。"})]})}function Pn({kind:n,label:t,hint:i,count:d}){const c=n==="ok",h=n==="warn",y=c?et:h?Ot:ue,u=c?r.success:h?r.warn:r.error;return e.jsxs("div",{style:{display:"flex",alignItems:"flex-start",gap:s.sm,padding:`${s.xs}px ${s.sm}px`,background:c?"transparent":"rgba(0,0,0,0.02)",borderRadius:z.sm},children:[e.jsx(y,{size:12,color:u,style:{marginTop:s.xxs,flexShrink:0}}),e.jsxs("div",{style:{flex:1},children:[e.jsxs("div",{style:{fontFamily:E,fontSize:m.sm,color:r.text2,lineHeight:1.4},children:[t," ",d!=null&&e.jsxs("span",{style:{color:r.sub,fontSize:m.xs},children:["(",d,")"]})]}),i&&e.jsx("div",{style:{fontFamily:E,fontSize:m.xs,color:r.sub,marginTop:1,lineHeight:1.4},children:i})]})]})}function Tn(n){const t=[],i=Array.from(n.querySelectorAll("img")),d=i.filter(o=>!o.hasAttribute("alt"));i.length===0?t.push({kind:"ok",label:"无图片元素需要 alt",hint:"没有 <img> 标签"}):d.length===0?t.push({kind:"ok",label:"图片 alt 完整",count:i.length}):t.push({kind:"warn",label:"部分图片缺 alt",count:d.length,hint:"加 alt 才能让屏幕阅读器识别"});const c=n.querySelectorAll("h1").length,h=n.querySelectorAll("h2").length;c===0&&h===0?t.push({kind:"warn",label:"没有 h1/h2 标题",hint:"层级缺失,screen reader 难导航"}):c>5?t.push({kind:"warn",label:"h1 过多",count:c,hint:"一般每页只 1 个 h1(每 section 1 个也可)"}):t.push({kind:"ok",label:"标题层级合理",hint:`h1 × ${c}, h2 × ${h}`});const y=Array.from(n.querySelectorAll("button")),u=y.filter(o=>!(o.textContent||"").trim()&&!o.getAttribute("aria-label"));y.length===0?t.push({kind:"ok",label:"无 button 需要文本",hint:"页面没有 <button>"}):u.length===0?t.push({kind:"ok",label:"按钮文本完整",count:y.length}):t.push({kind:"warn",label:"部分按钮缺文本/aria-label",count:u.length});const b=n.documentElement;return b.hasAttribute("lang")?t.push({kind:"ok",label:`<html> 标记了 lang="${b.getAttribute("lang")}"`}):t.push({kind:"warn",label:"<html> 缺 lang 属性",hint:"影响 screen reader 发音"}),t.push({kind:"ok",label:"色彩对比度(抽样)",hint:"主色块 WCAG AA pass(mock)"}),t.push({kind:"ok",label:"焦点顺序(mock)",hint:"Tab 键 traversal — P5 真模拟"}),t}function Wn({project:n,deckSpec:t,projectId:i}){var H,I,N;const d=Bt(f=>{var P;return((P=f.contextByProject[i])==null?void 0:P.systemInfo)||null}),c=D(f=>f.showToast),h=D(f=>f.confirm),[y,u]=a.useState([]),[b,o]=a.useState(!1),[p,w]=a.useState(!1),g=a.useRef(null),v=a.useCallback(async()=>{if(i){o(!0);try{const{plugins:f}=await ke.listProject(i);u(f||[])}catch(f){console.error("[SystemTab] listProject plugins failed:",f)}finally{o(!1)}}},[i]);a.useEffect(()=>{v()},[v]);const k=a.useCallback(async(f,P=!1)=>{var T,ee,X,V,B;if(!(!f||!i)){w(!0);try{const L=await ke.installProject(i,f,{force:P}),G=(T=L==null?void 0:L.installed)==null?void 0:T.name;c(`已装 plugin \`${G}\`(新会话生效)`,"success"),(ee=L==null?void 0:L.warnings)!=null&&ee.length&&c(`警告:${L.warnings.join(";")}`,"warn"),await v()}catch(L){if(L.status===409&&((X=L.body)!=null&&X.existing)){await h({title:"覆盖已装 plugin?",message:`已装 \`${L.body.existing.name}@${L.body.existing.version}\`,将覆盖为 \`${L.body.incoming.name}@${L.body.incoming.version}\`。`,confirmLabel:"覆盖",cancelLabel:"取消",danger:!0})&&await k(f,!0);return}const G=(B=(V=L.body)==null?void 0:V.errors)!=null&&B.length?`:${L.body.errors.join(";")}`:"";c(`安装失败${G||`:${L.message}`}`,"error")}finally{w(!1),g.current&&(g.current.value="")}}},[i,v,c,h]),l=a.useCallback(async f=>{if(await h({title:"卸载 plugin?",message:`从 project 移除 \`${f}\`(新会话生效)。文件会被删除。`,confirmLabel:"卸载",cancelLabel:"取消",danger:!0}))try{await ke.removeProject(i,f),c(`已卸载 \`${f}\``,"success"),await v()}catch(T){c(`卸载失败:${T.message}`,"error")}},[i,v,c,h]),S=Array.isArray(d==null?void 0:d.skills)?d.skills.map(f=>typeof f=="string"?f:f.name||f.id).filter(Boolean):[],A=Array.isArray(d==null?void 0:d.plugins)?d.plugins.map(f=>typeof f=="string"?f:f.name||f.id).filter(Boolean):[];return e.jsxs("div",{style:{padding:s.lg,display:"flex",flexDirection:"column",gap:s.xl},children:[e.jsx(C,{label:"本会话的 Skills",children:S.length===0?e.jsx("span",{style:{fontFamily:E,fontSize:m.sm,color:r.sub},children:"(等会话起动后从 SDK system_init 拉取)"}):e.jsx("div",{style:{display:"flex",flexWrap:"wrap",gap:s.xs},children:S.map(f=>e.jsx(Ve,{icon:Ht,label:f},f))})}),e.jsx(C,{label:"本会话的 Plugins",children:A.length===0?e.jsx("span",{style:{fontFamily:E,fontSize:m.sm,color:r.sub},children:"—"}):e.jsx("div",{style:{display:"flex",flexWrap:"wrap",gap:s.xs},children:A.map(f=>e.jsx(Ve,{icon:tt,label:f},f))})}),e.jsxs(C,{label:"Project 级 Plugins",children:[e.jsx("div",{style:{display:"flex",flexDirection:"column",gap:s.xs,marginBottom:s.sm},children:b&&y.length===0?e.jsx("span",{style:{fontFamily:E,fontSize:m.sm,color:r.sub},children:"加载中…"}):y.length===0?e.jsx("span",{style:{fontFamily:E,fontSize:m.sm,color:r.sub},children:"暂无(上传 zip 安装到本 project)"}):y.map(f=>e.jsx(Mn,{plugin:f,onUninstall:()=>l(f.name)},f.name))}),e.jsx("input",{ref:g,type:"file",accept:".md,.zip,application/zip,text/markdown,text/plain",style:{display:"none"},onChange:f=>{var T;const P=(T=f.target.files)==null?void 0:T[0];P&&k(P)}}),e.jsxs("button",{onClick:()=>{var f;return(f=g.current)==null?void 0:f.click()},disabled:p,style:{display:"inline-flex",alignItems:"center",gap:s.xs,padding:`${s.xs+1}px ${s.md}px`,fontFamily:E,fontSize:m.xs,color:r.text2,background:r.bgWhite,boxShadow:nt.far,borderRadius:z.md,cursor:p?"not-allowed":"pointer",opacity:p?.6:1},children:[e.jsx(_t,{size:11})," ",p?"安装中…":"上传 skill / plugin"]}),e.jsx("div",{style:{marginTop:s.xs,fontFamily:E,fontSize:m.xs,color:r.sub,lineHeight:1.5},children:"支持单 .md / skill zip / 完整 plugin zip。仅装到本 project;全局可见的走右上角 Skill 页面。新会话生效。"})]}),e.jsxs(C,{label:"模型",children:[e.jsx(ce,{k:"LLM",v:(d==null?void 0:d.model)||"—"}),(d==null?void 0:d.cwd)&&e.jsx(ce,{k:"cwd",v:d.cwd})]}),t&&e.jsxs(C,{label:"设计意图(spec)",children:[e.jsx(ce,{k:"metaphor",v:((H=t.meta)==null?void 0:H.metaphor)||"—"}),e.jsx(ce,{k:"audience",v:((I=t.meta)==null?void 0:I.audience)||"—"}),((N=t.meta)==null?void 0:N.intent)&&e.jsx("div",{style:{marginTop:s.sm,padding:s.md,background:r.bgCard,border:`1px solid ${r.borderLt}`,borderRadius:z.md,fontFamily:E,fontSize:m.xs,color:r.text2,lineHeight:1.6},children:t.meta.intent}),t.outline&&t.outline.length>0&&e.jsxs(e.Fragment,{children:[e.jsxs("div",{style:{marginTop:s.lg,fontFamily:F,fontSize:m.xs,color:r.sub,textTransform:"uppercase",letterSpacing:"0.05em",marginBottom:s.sm},children:["页面 outline (",t.outline.length,")"]}),e.jsx("div",{style:{display:"flex",flexDirection:"column",gap:s.xs},children:t.outline.map(f=>e.jsxs("div",{style:{padding:`${s.xs+1}px ${s.md}px`,fontFamily:E,fontSize:m.xs,background:"rgba(43,33,23,0.025)",borderRadius:z.sm,display:"flex",gap:s.sm,alignItems:"baseline"},children:[e.jsx("span",{style:{fontFamily:F,color:r.sub,minWidth:24},children:String(f.index).padStart(2,"0")}),e.jsx("span",{style:{color:r.text3,minWidth:64,fontFamily:F,fontSize:m.xs,textTransform:"uppercase"},children:f.layout}),e.jsx("span",{style:{color:r.text2,flex:1,lineHeight:1.4},children:f.intent})]},f.id))})]})]})]})}function Mn({plugin:n,onUninstall:t}){var i;return e.jsxs("div",{style:{display:"flex",alignItems:"center",gap:s.sm,padding:`${s.xs+1}px ${s.sm}px`,background:"rgba(43,33,23,0.025)",borderRadius:z.sm},children:[e.jsx(tt,{size:11,color:r.text4}),e.jsxs("div",{style:{flex:1,minWidth:0},children:[e.jsxs("div",{style:{display:"flex",alignItems:"baseline",gap:s.xs},children:[e.jsx("span",{style:{fontFamily:F,fontSize:m.sm,color:r.text2},children:n.name}),e.jsx("span",{style:{fontFamily:F,fontSize:m.xs,color:r.sub},children:n.version}),e.jsxs("span",{style:{fontFamily:E,fontSize:m.xs,color:r.sub},children:["· ",((i=n.skills)==null?void 0:i.length)||0," skill"]})]}),n.description&&e.jsx("div",{style:{fontFamily:E,fontSize:m.xs,color:r.sub,lineHeight:1.4,marginTop:s.xxs,overflow:"hidden",textOverflow:"ellipsis",whiteSpace:"nowrap"},title:n.description,children:n.description})]}),e.jsx("button",{onClick:t,title:"卸载",style:{background:"transparent",border:"none",color:r.sub,cursor:"pointer",padding:s.xxs},children:e.jsx(st,{size:11})})]})}function Ve({icon:n,label:t}){return e.jsxs("span",{style:{display:"inline-flex",alignItems:"center",gap:s.xs,padding:`${s.xxs}px ${s.sm}px`,fontFamily:F,fontSize:m.xs,color:r.text2,background:"rgba(43,33,23,0.04)",borderRadius:z.pill},children:[e.jsx(n,{size:10,color:r.text4}),t]})}function C({label:n,children:t}){return e.jsxs("div",{children:[e.jsx("div",{style:{fontFamily:F,fontSize:m.xs,color:r.sub,textTransform:"uppercase",letterSpacing:"0.05em",marginBottom:s.sm},children:n}),e.jsx("div",{style:{display:"flex",flexDirection:"column",gap:s.xs},children:t})]})}function ce({k:n,v:t}){return e.jsxs("div",{style:{display:"flex",gap:s.md,fontFamily:E,fontSize:m.sm},children:[e.jsx("span",{style:{color:r.sub,minWidth:70},children:n}),e.jsx("span",{style:{color:r.text2,flex:1,wordBreak:"break-word"},children:t})]})}function Rn({anchorRef:n,onClose:t,project:i,deckSpec:d,projectId:c,sessionId:h,onA11yClick:y,tweaksEnabled:u=null,onTweaksEnabledChange:b=null}){const o=D(l=>l.canvasFont),p=D(l=>l.followAgent),w=D(l=>l.setFollowAgent),g=D(l=>l.setCanvasFont),v=a.useRef(null),k=Se(n,360);return a.useEffect(()=>{const l=S=>{var A;v.current&&!v.current.contains(S.target)&&!((A=n==null?void 0:n.current)!=null&&A.contains(S.target))&&(t==null||t())};return window.addEventListener("mousedown",l),()=>window.removeEventListener("mousedown",l)},[t,n]),a.useEffect(()=>{const l=S=>{S.key==="Escape"&&(t==null||t())};return window.addEventListener("keydown",l),()=>window.removeEventListener("keydown",l)},[t]),e.jsxs("div",{ref:v,style:{...k,width:360,background:r.bgWhite,borderRadius:2,boxShadow:"0 2px 4px rgba(0,0,0,0.04), 0 8px 20px rgba(0,0,0,0.08), 0 24px 48px rgba(0,0,0,0.10), inset 0 1px 0 rgba(255,255,255,0.8)",zIndex:60,display:"flex",flexDirection:"column",overflow:"hidden"},children:[e.jsxs("div",{style:{padding:`${s.md}px ${s.lg}px`,display:"flex",alignItems:"center",gap:s.sm,borderBottom:`1px solid ${r.borderLt}`,flexShrink:0},children:[e.jsx(rt,{size:12,color:r.text4}),e.jsx("span",{style:{fontFamily:F,fontSize:m.sm,fontWeight:500,color:r.text},children:"System"})]}),e.jsxs("div",{style:{flex:1,minHeight:0,overflowY:"auto"},children:[y&&e.jsxs("div",{style:{padding:`${s.md}px ${s.lg}px`,borderBottom:`1px solid ${r.borderLt}`,display:"flex",flexDirection:"column",gap:s.sm},children:[e.jsx("div",{style:{fontFamily:F,fontSize:m.xs,color:r.sub,textTransform:"uppercase",letterSpacing:"0.05em"},children:"Canvas 工具"}),e.jsx("div",{style:{display:"flex",gap:s.sm},children:e.jsxs("button",{onClick:()=>{y(),t==null||t()},style:On,title:"无障碍审查(mock)",children:[e.jsx(jn,{size:11})," A11y"]})})]}),b&&e.jsxs("div",{style:{padding:`${s.md}px ${s.lg}px`,borderBottom:`1px solid ${r.borderLt}`,display:"flex",alignItems:"center",gap:s.sm},children:[e.jsxs("div",{style:{flex:1,minWidth:0},children:[e.jsx("div",{style:{fontFamily:E,fontSize:m.sm,color:r.text},children:"Tweaks 模式"}),e.jsx("div",{style:{fontFamily:E,fontSize:m.xs,color:r.sub,marginTop:2,lineHeight:1.5},children:u?"开:agent 会主动把核心参数做成控件让你拖":"关:不暴露控件,改样式走对话"})]}),e.jsx(Ke,{checked:!!u,onChange:b})]}),e.jsxs("div",{style:{padding:`${s.md}px ${s.lg}px`,borderBottom:`1px solid ${r.borderLt}`,display:"flex",alignItems:"center",gap:s.sm},children:[e.jsxs("div",{style:{flex:1,minWidth:0},children:[e.jsx("div",{style:{fontFamily:E,fontSize:m.sm,color:r.text},children:"镜头跟随 agent"}),e.jsx("div",{style:{fontFamily:E,fontSize:m.xs,color:r.sub,marginTop:2,lineHeight:1.5},children:p?"开:agent 换到哪个产物,镜头就飞过去(你操作后 8 秒内不抢)":"关:镜头只听你的;agent 在动什么看光圈"})]}),e.jsx(Ke,{checked:p,onChange:w})]}),e.jsxs("div",{style:{padding:`${s.md}px ${s.lg}px`,borderBottom:`1px solid ${r.borderLt}`},children:[e.jsx("div",{style:{fontFamily:E,fontSize:m.sm,color:r.text},children:"画布手写字体"}),e.jsx("div",{style:{fontFamily:E,fontSize:m.xs,color:r.sub,marginTop:2,marginBottom:s.sm},children:"用「文字」工具(T)在画布上写字时用这个"}),e.jsx("div",{style:{display:"flex",gap:s.xs,flexWrap:"wrap"},children:Object.entries(Dt).map(([l,S])=>e.jsx("button",{onClick:()=>g({...o,font:l}),style:{padding:`${s.xs}px ${s.sm}px`,borderRadius:z.md,cursor:"pointer",fontFamily:qt[l],fontSize:m.sm,border:`1px solid ${o.font===l?r.text:r.borderLt}`,background:o.font===l?r.text:"transparent",color:o.font===l?r.bg:r.text2},children:S},l))}),e.jsx("div",{style:{display:"flex",gap:s.xs,marginTop:s.sm},children:Object.entries(It).map(([l,S])=>e.jsx("button",{onClick:()=>g({...o,size:l}),style:{padding:`${s.xs}px ${s.sm}px`,borderRadius:z.md,cursor:"pointer",fontFamily:E,fontSize:m.xs,border:`1px solid ${o.size===l?r.text:r.borderLt}`,background:o.size===l?r.text:"transparent",color:o.size===l?r.bg:r.text2},children:S},l))})]}),e.jsx(Wn,{project:i,deckSpec:d,projectId:c})]}),e.jsx("div",{style:{padding:`${s.sm}px ${s.lg}px`,background:r.bgCard,borderTop:`1px solid ${r.borderLt}`,fontFamily:E,fontSize:m.xs,color:r.sub,lineHeight:1.5,flexShrink:0},children:"spec 不可在此编辑 — 改 spec 跟 agent 说,触发新 run。"})]})}function Ke({checked:n,onChange:t,title:i}){return e.jsx("button",{onClick:()=>t==null?void 0:t(!n),title:i,style:{width:28,height:16,padding:0,border:"none",borderRadius:z.lg,background:n?r.text:"rgba(0,0,0,0.18)",position:"relative",cursor:"pointer",transition:"background 0.15s",flexShrink:0},children:e.jsx("span",{style:{position:"absolute",top:2,left:n?14:2,width:12,height:12,borderRadius:z.round,background:r.bgWhite,boxShadow:it.crispSm,transition:"left 0.15s"}})})}const On={padding:`${s.xs+1}px ${s.md}px`,fontFamily:F,fontSize:m.xs,color:r.text4,background:"rgba(0,0,0,0.04)",border:"none",borderRadius:z.sm,display:"inline-flex",alignItems:"center",gap:s.xs,cursor:"pointer"};function Bn({comments:n=[],iframeDoc:t,iframeRef:i,anchorRef:d,onClose:c,onResolveComment:h,onDeleteComment:y,onSelectAnchor:u}){const b=a.useRef(null),o=Se(d,380);a.useEffect(()=>{const g=v=>{var k;b.current&&!b.current.contains(v.target)&&!((k=d==null?void 0:d.current)!=null&&k.contains(v.target))&&(c==null||c())};return window.addEventListener("mousedown",g),()=>window.removeEventListener("mousedown",g)},[c,d]),a.useEffect(()=>{const g=v=>{v.key==="Escape"&&(c==null||c())};return window.addEventListener("keydown",g),()=>window.removeEventListener("keydown",g)},[c]);const p=a.useMemo(()=>{const g=new Map;for(const k of n){const l=t&&k.anchor?lt(k.anchor,t.body):null,S=l?Nt(l):null,A=(S==null?void 0:S.index)??null;g.has(A)||g.set(A,[]),g.get(A).push({comment:k,el:l})}return[...g.entries()].sort((k,l)=>k[0]===null?1:l[0]===null?-1:k[0]-l[0])},[n,t]),w=g=>{if(g.el)try{g.el.scrollIntoView({behavior:"smooth",block:"center"})}catch{}u&&u(g.comment.anchor)};return e.jsxs("div",{ref:b,style:{...o,width:380,background:r.bgWhite,borderRadius:2,boxShadow:"0 2px 4px rgba(0,0,0,0.04), 0 8px 20px rgba(0,0,0,0.08), 0 24px 48px rgba(0,0,0,0.10), inset 0 1px 0 rgba(255,255,255,0.8)",zIndex:60,display:"flex",flexDirection:"column",overflow:"hidden"},children:[e.jsxs("div",{style:{padding:`${s.md}px ${s.lg}px`,display:"flex",alignItems:"center",gap:s.sm,borderBottom:`1px solid ${r.borderLt}`,flexShrink:0},children:[e.jsx(dt,{size:12,color:r.text4}),e.jsxs("span",{style:{fontFamily:F,fontSize:m.sm,fontWeight:500,color:r.text,flex:1},children:["全部评论 ",n.length>0&&`(${n.length})`]}),e.jsx("button",{onClick:c,title:"关闭",style:{padding:s.xs,color:r.text5,borderRadius:z.xs,background:"transparent",border:"none",cursor:"pointer"},children:e.jsx(ue,{size:12})})]}),e.jsx("div",{style:{flex:1,minHeight:0,overflowY:"auto"},children:n.length===0?e.jsxs("div",{style:{padding:`${s.lg+s.md}px ${s.lg}px`,fontFamily:E,fontSize:m.sm,color:r.sub,textAlign:"center",lineHeight:1.6},children:["还没有评论。",e.jsx("br",{}),"点击画布上任意元素 → 在弹出的浮卡里写评论。"]}):p.map(([g,v])=>e.jsxs("div",{style:{padding:`${s.md}px ${s.lg}px`,borderBottom:`1px solid ${r.borderLt}`},children:[e.jsxs("div",{style:{fontFamily:F,fontSize:m.xs,color:r.sub,textTransform:"uppercase",letterSpacing:"0.05em",marginBottom:s.sm},children:[g===null?"未定位":`第 ${g+1} 页`," · ",v.length," 条"]}),e.jsx("div",{style:{display:"flex",flexDirection:"column",gap:s.xs},children:v.map(({comment:k,el:l})=>e.jsx(Hn,{comment:k,available:!!l,onClick:()=>w({comment:k,el:l}),onResolve:()=>h==null?void 0:h(k.id),onDelete:()=>y==null?void 0:y(k.id)},k.id))})]},g??"orphan"))}),e.jsx("div",{style:{padding:`${s.sm}px ${s.lg}px`,background:r.bgCard,borderTop:`1px solid ${r.borderLt}`,fontFamily:E,fontSize:m.xs,color:r.sub,lineHeight:1.5,flexShrink:0},children:"点击评论 → 跳到对应元素;evaluator 切到 edit 模式后可在浮卡续写。"})]})}function Hn({comment:n,available:t,onClick:i,onResolve:d,onDelete:c}){var y,u,b;const h=n.status==="resolved";return e.jsxs("div",{style:{padding:`${s.sm}px ${s.md}px`,background:r.bgWhite,boxShadow:nt.far,borderRadius:z.md,display:"flex",flexDirection:"column",gap:s.xs,opacity:h?.5:1,cursor:t?"pointer":"default",transition:"background 0.1s"},onClick:t?i:void 0,onMouseEnter:o=>{t&&(o.currentTarget.style.background="rgba(0,0,0,0.02)")},onMouseLeave:o=>{o.currentTarget.style.background=r.bgWhite},children:[e.jsx("div",{style:{fontFamily:E,fontSize:m.sm,color:r.text2,lineHeight:1.5,textDecoration:h?"line-through":"none",whiteSpace:"pre-wrap",wordBreak:"break-word"},children:n.text}),e.jsxs("div",{style:{display:"flex",alignItems:"center",gap:s.xs,fontFamily:F,fontSize:m.xs,color:r.sub},children:[t?e.jsxs(e.Fragment,{children:[e.jsx(on,{size:9}),e.jsx("span",{children:((y=n.anchor)==null?void 0:y.dataId)||((b=(u=n.anchor)==null?void 0:u.path)==null?void 0:b.split(">").pop())||"元素"})]}):e.jsx("span",{style:{fontStyle:"italic"},children:"元素已不在"}),e.jsx("span",{style:{flex:1}}),e.jsx("button",{onClick:o=>{o.stopPropagation(),d()},title:h?"取消解决":"标记解决",style:{padding:s.xxs,color:r.sub,borderRadius:z.xs,background:"transparent",border:"none",cursor:"pointer"},children:e.jsx(et,{size:11})}),e.jsx("button",{onClick:o=>{o.stopPropagation(),c()},title:"删除",style:{padding:s.xxs,color:r.sub,borderRadius:z.xs,background:"transparent",border:"none",cursor:"pointer"},children:e.jsx(st,{size:11})})]})]})}function _n({iframeDoc:n,active:t}){const[i,d]=a.useState([]),[c,h]=a.useState(0);a.useEffect(()=>{if(!t||!n){d([]);return}let u=null;const b=()=>{const p=Array.from(n.querySelectorAll("section[data-page]"));if(d(p),u&&u.disconnect(),!!p.length)try{u=new(n.defaultView||window).IntersectionObserver(w=>{const g=w.filter(k=>k.isIntersecting).sort((k,l)=>l.intersectionRatio-k.intersectionRatio)[0];if(!g)return;const v=p.indexOf(g.target);v>=0&&h(v)},{threshold:[.35,.6]}),p.forEach(w=>u.observe(w))}catch{}};b();let o=null;try{o=new(n.defaultView||window).MutationObserver(()=>b()),n.body&&o.observe(n.body,{childList:!0,subtree:!0})}catch{}return()=>{u==null||u.disconnect(),o==null||o.disconnect()}},[n,t]);const y=a.useCallback(u=>{h(b=>{const o=Math.max(0,Math.min(i.length-1,b+u)),p=i[o];if(p)try{p.scrollIntoView({behavior:"smooth",block:"start"})}catch{}return o})},[i]);return a.useEffect(()=>{if(!t||i.length<2)return;const u=o=>{if(o.key!=="ArrowLeft"&&o.key!=="ArrowRight")return;const p=o.target;p&&(p.tagName==="INPUT"||p.tagName==="TEXTAREA"||p.isContentEditable)||(o.preventDefault(),y(o.key==="ArrowRight"?1:-1))};window.addEventListener("keydown",u);let b=null;try{b=n,b==null||b.addEventListener("keydown",u)}catch{}return()=>{window.removeEventListener("keydown",u);try{b==null||b.removeEventListener("keydown",u)}catch{}}},[t,i.length,y,n]),!t||i.length<2?null:e.jsxs("div",{style:{position:"absolute",bottom:16,left:"50%",transform:"translateX(-50%)",display:"flex",alignItems:"center",gap:s.xxs,background:"rgba(28,24,18,0.86)",borderRadius:z.pill,padding:s.xs,boxShadow:"0 6px 22px rgba(0,0,0,0.22)",zIndex:30,backdropFilter:"blur(6px)"},children:[e.jsx(Ye,{onClick:()=>y(-1),disabled:c===0,icon:Gt,title:"上一页(←)"}),e.jsxs("span",{style:{fontFamily:F,fontSize:m.sm,color:ot.ink,padding:`0 ${s.md}px`,minWidth:52,textAlign:"center",userSelect:"none"},children:[c+1," / ",i.length]}),e.jsx(Ye,{onClick:()=>y(1),disabled:c===i.length-1,icon:Ut,title:"下一页(→)"})]})}function Ye({onClick:n,disabled:t,icon:i,title:d}){return e.jsx("button",{onClick:n,disabled:t,title:d,style:{display:"flex",alignItems:"center",justifyContent:"center",width:26,height:26,borderRadius:z.round,border:"none",background:"transparent",color:t?"rgba(232,226,210,0.3)":ot.ink,cursor:t?"default":"pointer",transition:"background 0.15s"},onMouseEnter:c=>{t||(c.currentTarget.style.background="rgba(255,255,255,0.12)")},onMouseLeave:c=>{c.currentTarget.style.background="transparent"},children:e.jsx(i,{size:15})})}function Dn({edits:n=[],onApply:t,onUndo:i,onClearAll:d,canUndo:c=!1,isRunning:h=!1}){const y=n.length;if(y===0)return null;const u=qn(n);return e.jsxs("div",{style:{position:"absolute",bottom:16,left:"50%",transform:"translateX(-50%)",background:"rgba(45, 36, 24, 0.94)",color:r.btnText,borderRadius:z.lg,padding:`${s.sm}px ${s.lg}px`,display:"flex",alignItems:"center",gap:s.md,fontFamily:F,fontSize:m.xs,boxShadow:"0 8px 32px rgba(0,0,0,0.25), 0 2px 8px rgba(0,0,0,0.18)",zIndex:50,backdropFilter:"blur(8px)",WebkitBackdropFilter:"blur(8px)"},children:[e.jsx("span",{style:{padding:`${s.xxs}px ${s.md}px`,background:"rgba(245, 240, 232, 0.15)",borderRadius:z.xl,fontWeight:600,minWidth:22,textAlign:"center"},children:y}),e.jsxs("span",{style:{color:"#dfd6c6"},children:[u," 待应用"]}),e.jsx("div",{style:{width:1,height:18,background:"rgba(245,240,232,0.2)"}}),e.jsxs("button",{onClick:i,disabled:!c,title:c?"撤销最近一次 (Cmd+Z)":"无可撤销操作",style:{...Ze,opacity:c?1:.4,cursor:c?"pointer":"not-allowed"},children:[e.jsx(Xt,{size:11})," 撤销"]}),e.jsxs("button",{onClick:d,title:"全部撤销 — 把所有 pending 编辑清掉",style:Ze,children:[e.jsx(ue,{size:11})," 全部撤销"]}),e.jsxs("button",{onClick:t,disabled:h,title:h?"agent 正在跑,等当前 run 结束":"让 agent 把这些调整落到源代码",style:{...In,opacity:h?.6:1,cursor:h?"wait":"pointer"},children:[e.jsx(Vt,{size:11})," 应用"]})]})}function qn(n){const t={move:0,style:0,dup:0,del:0};for(const d of n)d.kind==="pending-move"?t.move++:d.kind==="pending-style"?t.style++:d.kind==="pending-duplicate"?t.dup++:d.kind==="pending-delete"&&t.del++;const i=[];return t.move&&i.push(`${t.move} 拖动`),t.dup&&i.push(`${t.dup} 复制`),t.style&&i.push(`${t.style} 样式`),t.del&&i.push(`${t.del} 删除`),i.join(" · ")||"调整"}const Ze={display:"inline-flex",alignItems:"center",gap:s.xs,padding:`${s.xs}px ${s.base}px`,fontFamily:"inherit",fontSize:m.xs,color:r.btnText,background:"transparent",border:"1px solid rgba(245,240,232,0.25)",borderRadius:z.sm},In={display:"inline-flex",alignItems:"center",gap:s.xs,padding:"5px 14px",fontFamily:"inherit",fontSize:m.xs,fontWeight:600,color:r.btn,background:r.btnText,border:"none",borderRadius:z.sm,boxShadow:"0 1px 2px rgba(0,0,0,0.15)"},Qe=at.purple,Nn=Kt(at.purple,.18);function Gn({edits:n=[],iframeRef:t,zoom:i=1}){const[,d]=a.useState(0);a.useEffect(()=>{if(n.length===0)return;const g=t==null?void 0:t.current;if(!g)return;const v=g.contentWindow;if(!v)return;let k=null;const l=()=>{k||(k=requestAnimationFrame(()=>{k=null,d(S=>S+1)}))};try{v.addEventListener("scroll",l,{passive:!0,capture:!0}),v.addEventListener("resize",l),window.addEventListener("resize",l)}catch{}return()=>{try{v.removeEventListener("scroll",l,{capture:!0}),v.removeEventListener("resize",l),window.removeEventListener("resize",l)}catch{}k&&cancelAnimationFrame(k)}},[n.length,t]);const c=a.useMemo(()=>n.filter(g=>(g.kind==="pending-move"||g.kind==="pending-duplicate")&&g.reactMount===!0),[n]);if(c.length===0||!(t!=null&&t.current))return null;const h=t.current,y=h.contentDocument;if(!y)return null;const u=h.getBoundingClientRect(),b=an(h);if(!b)return null;const o=h.contentWindow,p=(o==null?void 0:o.innerWidth)??u.width/i,w=(o==null?void 0:o.innerHeight)??u.height/i;return e.jsx(e.Fragment,{children:c.map((g,v)=>{var f;const k=lt(g.anchor,y.body);if(!k)return null;const l=k.getBoundingClientRect();if(l.bottom<=0||l.top>=w||l.right<=0||l.left>=p)return null;const{top:S,left:A}=dn(b,l.left,l.top,i),H=l.width*i,I=l.height*i,N=(f=g.aiContext)!=null&&f.targetContainerTag?`${g.aiContext.targetContainerTag}`:"目标容器";return e.jsxs("div",{style:{position:"absolute",top:0,left:0,pointerEvents:"none"},children:[e.jsx("div",{style:{position:"absolute",pointerEvents:"none",top:S-3,left:A-3,width:H+6,height:I+6,border:`2px dashed ${Qe}`,borderRadius:z.sm,boxShadow:`0 0 0 3px ${Nn}`,zIndex:9}}),e.jsxs("div",{style:{position:"absolute",pointerEvents:"none",top:S-12,left:A+H-8,transform:"translateX(-100%)",padding:`${s.xxs}px ${s.sm}px`,fontFamily:F,fontSize:m.xs,lineHeight:"14px",fontWeight:500,color:r.bgWhite,background:Qe,borderRadius:z.xs,whiteSpace:"nowrap",boxShadow:it.crisp,zIndex:11,maxWidth:Math.max(120,H),overflow:"hidden",textOverflow:"ellipsis"},children:[g.kind==="pending-duplicate"?"复制到":"移到"," <",N,">"]})]},v)})})}const ve={"16:9":{w:1920,h:1080},"16:10":{w:1920,h:1200},"9:16":{w:1080,h:1920},"4:3":{w:1440,h:1080}},je="16:9";function Un(n){if(!n||typeof n!="string")return je;const t=n.match(/<div\b[^>]*class\s*=\s*['"][^'"]*__nd-deck-wrap[^'"]*['"][^>]*data-deck-aspect\s*=\s*['"]([^'"]+)['"]/i)||n.match(/<div\b[^>]*data-deck-aspect\s*=\s*['"]([^'"]+)['"][^>]*class\s*=\s*['"][^'"]*__nd-deck-wrap[^'"]*['"]/i);return t&&ve[t[1]]?t[1]:je}function Yn({tab:n,onTabChange:t,onClose:i,artifactExports:d=null,onExport:c=null,onToolbarGroups:h=null,title:y="幻灯",htmlSrc:u,htmlContent:b,selectedAnchor:o,onSelectChange:p,onTextEdit:w,onIframeReady:g,candidates:v,activeCandidateId:k,onSelectCandidate:l,onAddCandidate:S,onRemoveCandidate:A,onRenameCandidate:H,project:I,deckSpec:N,projectId:f,sessionId:P,comments:T=[],onAddComment:ee,onResolveComment:X,onDeleteComment:V,onRegionComment:B=null,tweaksAvailable:L=!1,pendingEdits:G=[],onCommitMove:q,onCommitFreePosition:xe,onSubmitDragNote:ct,lastPendingEditId:ut=null,onApplyPendingEdits:xt,onUndoPending:pt,onClearAllPending:ft,canUndoPending:gt=!1,isStreaming:U=!1}){var We,Me,Re,Oe,Be,He,_e,De,qe,Ie;const{panels:pe,setPanelVisible:ht}=Yt(),fe=!!((We=pe==null?void 0:pe.tweaks)!=null&&We.visible),yt=()=>ht("tweaks",!fe),[K,ze]=a.useState(!1);a.useEffect(()=>{U&&n==="drag"&&(t==null||t("edit"))},[U,n,t]);const mt=a.useRef(null),[ge,bt]=a.useState(!1),[Ee,wt]=a.useState(null),[kt,$e]=a.useState(!1),[Y,te]=a.useState("fit"),[Z,vt]=a.useState({width:0,height:0}),[Le,jt]=a.useState(0),[he,ne]=a.useState(""),[ye,se]=a.useState(!1),[_,Fe]=a.useState(null),[me,re]=a.useState(!1),[Q,ie]=a.useState(!1),[J,le]=a.useState(!1),[oe,Ae]=a.useState(!0),O=a.useRef(null),be=a.useRef(null),Pe=a.useRef(null);a.useEffect(()=>{if(!f||!P)return;let x=!1;return Ge.read(f).then(({config:j})=>{x||j&&typeof j.tweaks_mode_enabled=="boolean"&&Ae(j.tweaks_mode_enabled)}).catch(()=>{}),()=>{x=!0}},[f,P]);const St=a.useCallback(x=>{Ae(x),!(!f||!P)&&Ge.patch(f,{tweaks_mode_enabled:x}).catch(()=>{})},[f,P]);a.useEffect(()=>{const x=O.current;if(!x)return;const j=()=>{const M=x.getBoundingClientRect();vt(R=>R.width===M.width&&R.height===M.height?R:{width:M.width,height:M.height})};j();let $=null;try{$=new ResizeObserver(j),$.observe(x)}catch{}return window.addEventListener("resize",j),()=>{$&&$.disconnect(),window.removeEventListener("resize",j)}},[n]);const Te=Un(he),ae=ve[Te]||ve[je],W=Y==="fit"?Z.width>0&&Z.height>0?Math.min(Z.width/ae.w,Z.height/ae.h):1:Y,zt=v&&v.length>=1;a.useEffect(()=>{se(!1),Fe(null)},[k]),a.useEffect(()=>{const x=$=>{var R;if($.key!=="Escape")return;const M=$.target;((R=M==null?void 0:M.getAttribute)==null?void 0:R.call(M,"contenteditable"))!=="true"&&(Q||me||J||(o?p==null||p(null):i==null||i()))};window.addEventListener("keydown",x);let j=null;try{j=_,j==null||j.addEventListener("keydown",x)}catch{}return()=>{window.removeEventListener("keydown",x);try{j==null||j.removeEventListener("keydown",x)}catch{}}},[o,_,p,i,Q,me,J]),a.useEffect(()=>{const x=j=>{const $=j==null?void 0:j.data;if(!(!$||typeof $!="object")&&$.type==="canvas-page-change"&&Number.isFinite($.page))try{window.dispatchEvent(new CustomEvent("nd-canvas-page-change",{detail:{page:$.page}}))}catch{}};return window.addEventListener("message",x),()=>window.removeEventListener("message",x)},[]),a.useEffect(()=>{if(!u){ne(b||""),se(!1);return}fetch(u).then(x=>x.text()).then(x=>{ne(x),se(!1)}).catch(()=>ne("<!-- 无法加载源码 -->"))},[u,b,Le]);const Et=x=>{p==null||p((x==null?void 0:x.anchor)||null)},$t=x=>{w==null||w(x),console.log("[direct edit]",x)},Lt=a.useCallback(x=>{ne(x),se(!0)},[]),Ft=a.useCallback(x=>{try{Fe(x.contentDocument)}catch{}g==null||g(x)},[g]),At=()=>{jt(x=>x+1),p==null||p(null)},Pt=()=>{re(!1),ie(!1),le(x=>!x)},Tt=()=>{re(!1),le(!1),ie(x=>!x)},we=Array.isArray(T)?T.filter(x=>x.status!=="resolved").length:0,Wt=a.useMemo(()=>[rn({kind:"deck",exports:d,onExport:c}),{id:"mode",type:"mode",value:n,onChange:x=>{t==null||t(x),p==null||p(null)},items:[{id:"preview",icon:kn,label:"预览",title:"看成品(左右键翻页)"},{id:"edit",icon:Zt,label:"编辑",title:"双击文字直接改 · 单击元素弹评论卡"},{id:"drag",icon:Qt,label:"拖拽",disabled:U,title:U?"agent 正在跑,拖拽暂停以免和它抢同一份源码":"拖动元素调布局"},{id:"region",icon:vn,label:"圈选",disabled:!B,title:B?"框一块地方说事 —— 框住谁、当时长什么样、你想说什么,一起交给 agent":"要先开一个会话才能把圈选交给 agent"},{id:"code",icon:Jt,label:"源码",title:"看/改这一份 HTML"}]},n==="drag"&&{id:"dragmode",items:[{id:"free",icon:Ct,label:K?"自由":"嵌入",active:K,title:K?"自由摆放 · 松手落到像素位置(P 切回嵌入)":"嵌入 · 松手按 DOM 树插进容器(P 切自由摆放)",onClick:()=>ze(x=>!x)}]},n!=="code"&&{id:"zoom",items:[{id:"zoomOut",icon:en,title:"缩小",onClick:()=>te(Math.max(.25,W-.1))},{id:"zoomLevel",label:`${Math.round(W*100)}%`,active:Y==="fit",title:Y==="fit"?"当前自适应窗口":"点一下自适应窗口",onClick:()=>te("fit")},{id:"zoomIn",icon:Ce,title:"放大",onClick:()=>te(Math.min(3,W+.1))},{id:"fit",icon:tn,title:"自适应窗口",onClick:()=>te("fit")}]},{id:"actions",items:[{id:"tweaks",icon:nn,active:fe,disabled:!oe,title:oe?L?"Tweaks:拖控件实时改样式":"Tweaks(agent 还没暴露参数 — 跟它说一句让它 expose_tweaks)":"Tweaks 模式已关(在 System 里开)",onClick:yt},{id:"comment",icon:dt,label:we>0?String(we):void 0,active:J,btnRef:Pe,title:"这一份上已有的评论",onClick:Pt},{id:"reload",icon:sn,title:"重载(agent 改完没刷新时用)",onClick:At},{id:"system",icon:rt,active:Q,btnRef:be,title:"System:项目档案 / Tweaks 模式 / A11y",onClick:Tt}]}].filter(Boolean),[n,U,K,Y,W,fe,oe,L,J,Q,we,B,d,c]);return e.jsxs(ln,{kind:"deck",title:y,subtitle:Te,onClose:i,escToClose:!1,groups:Wt,onToolbarGroups:h,headerExtra:zt?e.jsx($n,{candidates:v,activeId:k,onSelect:l,onAdd:S,onRemove:A,onRename:H}):null,children:[(n==="edit"||n==="preview"||n==="drag"||n==="region")&&e.jsxs("div",{ref:O,style:{flex:1,minHeight:0,position:"relative",display:"flex",flexDirection:"column"},children:[e.jsx(En,{src:ye?void 0:u,srcDoc:ye?he:u?void 0:b,mode:n==="drag"||n==="region"?"preview":n,onSelect:Et,onTextEdit:$t,onIframeReady:Ft,zoom:W,deckW:ae.w,deckH:ae.h},`${k||"default"}-${Le}-${ye?"doc":"src"}`),n==="edit"&&o&&e.jsx(cn,{selectedAnchor:o,iframeRef:{current:(Me=O.current)==null?void 0:Me.querySelector("iframe")},zoom:W}),e.jsx(un,{comments:T,iframeRef:{current:(Re=O.current)==null?void 0:Re.querySelector("iframe")},zoom:W,onSelectAnchor:x=>{n!=="edit"&&(t==null||t("edit")),p==null||p(x)}}),e.jsx(Gn,{edits:G,iframeRef:{current:(Oe=O.current)==null?void 0:Oe.querySelector("iframe")},zoom:W}),e.jsx(_n,{iframeDoc:_,active:n==="preview"}),e.jsx(xn,{active:n==="drag"&&!ge,iframeRef:{current:(Be=O.current)==null?void 0:Be.querySelector("iframe")},zoom:W,pickDragSource:pn,isDragging:ge}),e.jsx(fn,{active:n==="drag",iframeRef:{current:(He=O.current)==null?void 0:He.querySelector("iframe")},zoom:W,freeMode:K,onFreeModeChange:ze,apiRef:mt,onDraggingChange:bt,onSelectionChange:x=>{wt(x),x&&$e(!0)},onCommitMove:(x,j)=>{var M;if(j.duplicate){const R=(M=j.sourceEl)==null?void 0:M.cloneNode(!0);let Ne=()=>{};if(R&&j.targetContainer){try{R.removeAttribute("data-anchor")}catch{}j.beforeEl&&j.beforeEl.parentNode===j.targetContainer?j.targetContainer.insertBefore(R,j.beforeEl):j.targetContainer.appendChild(R),Ne=()=>{try{R.remove()}catch{}}}q==null||q(x,Ne);return}const $=hn({iframeDoc:_,sourceEl:j.sourceEl,targetContainer:j.targetContainer,beforeEl:j.beforeEl});q==null||q(x,$==null?void 0:$.revert)},onCommitFreePosition:(x,j)=>{const $=gn({sourceEl:j.sourceEl,parentEl:j.parentEl,styleDelta:x.styleDelta,runtimeLocks:x.runtimeLocks,parentNeedsRelative:x.parentNeedsRelative});xe==null||xe(x,$==null?void 0:$.revert)}}),e.jsx(yn,{active:n==="drag"&&kt&&!ge&&!!Ee,iframeRef:{current:(_e=O.current)==null?void 0:_e.querySelector("iframe")},zoom:W,sourceEl:Ee,hasPendingEditId:!!ut,onSubmit:ct,onDismiss:()=>$e(!1)}),n==="edit"&&o&&_&&e.jsx(mn,{selectedAnchor:o,iframeDoc:_,iframeRef:{current:(De=O.current)==null?void 0:De.querySelector("iframe")},iframeRect:Z,zoom:W,comments:T,onClose:()=>p==null?void 0:p(null),onAddComment:ee,onResolveComment:X,onDeleteComment:V}),e.jsx(bn,{active:n==="region"&&!!B,iframeRef:{current:(qe=O.current)==null?void 0:qe.querySelector("iframe")},zoom:W,onSubmit:x=>B==null?void 0:B(x),onExit:()=>t==null?void 0:t("preview")}),e.jsx(Dn,{edits:G,onApply:xt,onUndo:pt,onClearAll:ft,canUndo:gt,isRunning:U})]}),n==="code"&&e.jsx(wn,{value:he,onChange:Lt,readOnly:!1}),me&&e.jsx(An,{anchorRef:be,onClose:()=>re(!1),iframeDoc:_}),Q&&e.jsx(Rn,{anchorRef:be,onClose:()=>ie(!1),project:I,deckSpec:N,projectId:f,sessionId:P,onA11yClick:()=>{ie(!1),re(!0)},tweaksEnabled:oe,onTweaksEnabledChange:St}),J&&e.jsx(Bn,{comments:T,iframeDoc:_,iframeRef:{current:(Ie=O.current)==null?void 0:Ie.querySelector("iframe")},anchorRef:Pe,onClose:()=>le(!1),onResolveComment:X,onDeleteComment:V,onSelectAnchor:x=>{le(!1),n!=="edit"&&(t==null||t("edit")),p==null||p(x)}})]})}export{Yn as default};
@@ -1,4 +1,4 @@
1
- import{c as q,r as n,j as e,R as N,d as c,G as g,P as Q,F as k,e as L,L as tt,S as ct,X as dt,a as K,v as ut,h as _,M as ht,I as G,T as pt,i as J,k as ft,l as xt,m as gt,n as yt,A as bt,C as vt}from"./index-GAamh1p4.js";import{S as wt,E as kt}from"./square-dashed-mouse-pointer-CDUlhUP7.js";/**
1
+ import{c as q,r as n,j as e,R as N,d as c,G as g,P as Q,F as k,e as L,L as tt,S as ct,X as dt,a as K,v as ut,h as _,M as ht,I as G,T as pt,i as J,k as ft,l as xt,m as gt,n as yt,A as bt,C as vt}from"./index-DGG5wIZs.js";import{S as wt,E as kt}from"./square-dashed-mouse-pointer-CTtTVKoH.js";/**
2
2
  * @license lucide-react v0.468.0 - ISC
3
3
  *
4
4
  * This source code is licensed under the ISC license.