@profpowell/vb-project-planning 0.2.1 → 0.2.3

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 (66) hide show
  1. package/README.md +10 -5
  2. package/dist/vb-project-planning.css +69 -3
  3. package/dist/vb-project-planning.js +3191 -2544
  4. package/dist/vb-project-planning.min.css +1 -1
  5. package/dist/vb-project-planning.min.js +221 -197
  6. package/package.json +7 -4
  7. package/src/lib/board-surface.js +158 -0
  8. package/src/lib/bundle-registry.js +2 -75
  9. package/src/lib/dates.js +125 -0
  10. package/src/lib/escape.js +34 -0
  11. package/src/lib/hash.js +16 -0
  12. package/src/lib/portrait-url.js +3 -29
  13. package/src/lib/src-loader.js +78 -0
  14. package/src/lib/vb-view-transition.js +7 -1
  15. package/src/utils/copy-init.js +56 -17
  16. package/src/web-components/_ux-base.js +409 -24
  17. package/src/web-components/adr-wc/README.md +18 -16
  18. package/src/web-components/adr-wc/api.json +7 -5
  19. package/src/web-components/adr-wc/logic.js +50 -136
  20. package/src/web-components/burndown-chart/api.json +8 -6
  21. package/src/web-components/burndown-chart/logic.js +75 -39
  22. package/src/web-components/empathy-map/api.json +13 -13
  23. package/src/web-components/empathy-map/logic.js +161 -168
  24. package/src/web-components/empathy-map/static.html +3 -3
  25. package/src/web-components/empathy-map/styles.js +1 -0
  26. package/src/web-components/gantt-chart/README.md +12 -6
  27. package/src/web-components/gantt-chart/api.json +23 -7
  28. package/src/web-components/gantt-chart/logic.js +456 -431
  29. package/src/web-components/gantt-chart/styles.css +14 -1
  30. package/src/web-components/impact-effort/api.json +9 -7
  31. package/src/web-components/impact-effort/logic.js +238 -209
  32. package/src/web-components/impact-effort/static.html +12 -4
  33. package/src/web-components/iron-triangle/_capacity.js +0 -18
  34. package/src/web-components/kanban-board/api.json +8 -6
  35. package/src/web-components/kanban-board/logic.js +289 -333
  36. package/src/web-components/product-roadmap/api.json +14 -13
  37. package/src/web-components/product-roadmap/logic.js +393 -246
  38. package/src/web-components/product-roadmap/styles.css +40 -0
  39. package/src/web-components/quadrant-grid/api.json +9 -4
  40. package/src/web-components/quadrant-grid/logic.js +80 -12
  41. package/src/web-components/quadrant-grid/styles.css +7 -0
  42. package/src/web-components/quality-target/_quality-utils.js +2 -46
  43. package/src/web-components/review-surface/README.md +9 -5
  44. package/src/web-components/review-surface/api.json +10 -8
  45. package/src/web-components/review-surface/logic.js +349 -218
  46. package/src/web-components/risk-register/api.json +1 -6
  47. package/src/web-components/risk-register/logic.js +71 -24
  48. package/src/web-components/risk-register/styles.css +9 -1
  49. package/src/web-components/story-map/api.json +8 -6
  50. package/src/web-components/story-map/logic.js +280 -281
  51. package/src/web-components/story-map/static.html +15 -5
  52. package/src/web-components/traceability-matrix/api.json +10 -3
  53. package/src/web-components/traceability-matrix/logic.js +112 -63
  54. package/src/web-components/traceability-matrix/styles.css +22 -1
  55. package/src/web-components/user-journey/api.json +25 -24
  56. package/src/web-components/user-journey/logic.js +76 -127
  57. package/src/web-components/user-journey/static.html +2 -2
  58. package/src/web-components/user-persona/api.json +15 -14
  59. package/src/web-components/user-persona/logic.js +71 -117
  60. package/src/web-components/user-persona/styles.js +1 -0
  61. package/src/web-components/user-story/api.json +13 -11
  62. package/src/web-components/user-story/logic.js +164 -195
  63. package/src/web-components/user-story/styles.js +28 -1
  64. package/src/web-components/work-item/README.md +3 -3
  65. package/src/web-components/work-item/api.json +13 -11
  66. package/src/web-components/work-item/logic.js +58 -154
@@ -1,4 +1,4 @@
1
- var re=`
1
+ var ze=`
2
2
  :host {
3
3
  display: block;
4
4
  font-family: var(--user-persona-font, var(--font-sans, system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif));
@@ -247,6 +247,7 @@ var re=`
247
247
  }
248
248
 
249
249
  .section-title {
250
+ margin: 0;
250
251
  font-size: var(--_font-sm);
251
252
  font-weight: 600;
252
253
  color: var(--_text);
@@ -294,55 +295,55 @@ var re=`
294
295
  transition: none !important;
295
296
  }
296
297
  }
297
- `;var Ns=window.matchMedia("(prefers-reduced-motion: reduce)");var ae=new Map;function w(n,t,e={}){let s=e.priority??10,r={impl:t,bundle:e.bundle,contract:e.contract,priority:s},a=ae.get(n);if(customElements.get(n)){if(!a||a.priority>=s){a&&a.priority===s&&a.impl!==t&&console.warn(`[VB Bundle] Tag <${n}> already registered by "${a.bundle}" (priority ${a.priority}). Skipping "${e.bundle}".`);return}console.warn(`[VB Bundle] Tag <${n}> defined by "${a.bundle}" cannot be replaced (customElements.define is permanent). "${e.bundle}" has higher priority but arrived late.`);return}if(a&&a.priority>=s){a.priority===s&&console.warn(`[VB Bundle] Tag <${n}> already registered by "${a.bundle}". Skipping "${e.bundle}" (first wins at equal priority).`);return}ae.set(n,r),customElements.define(n,t)}function m(n){return String(n).replace(/&/g,"&amp;").replace(/</g,"&lt;").replace(/>/g,"&gt;").replace(/"/g,"&quot;")}function O(n){return n.split(" ").map(t=>t[0]).join("").toUpperCase().slice(0,2)}function B(n){let t=0;for(let s=0;s<n.length;s++)t=n.charCodeAt(s)+((t<<5)-t);return`hsl(${(t%360+360)%360}, 65%, 55%)`}function k(n){return`<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true">${n}</svg>`}var E={user:'<path d="M19 21v-2a4 4 0 0 0-4-4H9a4 4 0 0 0-4 4v2"/><circle cx="12" cy="7" r="4"/>',pencil:'<path d="M21.174 6.812a1 1 0 0 0-3.986-3.987L3.842 16.174a2 2 0 0 0-.5.83l-1.321 4.352a.5.5 0 0 0 .623.622l4.353-1.32a2 2 0 0 0 .83-.497z"/><path d="m15 5 4 4"/>',check:'<path d="M20 6 9 17l-5-5"/>',target:'<circle cx="12" cy="12" r="10"/><circle cx="12" cy="12" r="6"/><circle cx="12" cy="12" r="2"/>',alertTriangle:'<path d="m21.73 18-8-14a2 2 0 0 0-3.48 0l-8 14A2 2 0 0 0 4 21h16a2 2 0 0 0 1.73-3"/><path d="M12 9v4"/><path d="M12 17h.01"/>',messageCircle:'<path d="M2.992 16.342a2 2 0 0 1 .094 1.167l-1.065 3.29a1 1 0 0 0 1.236 1.168l3.413-.998a2 2 0 0 1 1.099.092 10 10 0 1 0-4.777-4.719"/>',lightbulb:'<path d="M15 14c.2-1 .7-1.7 1.5-2.5 1-.9 1.5-2.2 1.5-3.5A6 6 0 0 0 6 8c0 1 .2 2.2 1.5 3.5.7.7 1.3 1.5 1.5 2.5"/><path d="M9 18h6"/><path d="M10 22h4"/>',wrench:'<path d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.106-3.105c.32-.322.863-.22.983.218a6 6 0 0 1-8.259 7.057l-7.91 7.91a1 1 0 0 1-2.999-3l7.91-7.91a6 6 0 0 1 7.057-8.259c.438.12.54.662.219.984z"/>',heart:'<path d="M2 9.5a5.5 5.5 0 0 1 9.591-3.676.56.56 0 0 0 .818 0A5.49 5.49 0 0 1 22 9.5c0 2.29-1.5 4-3 5.5l-5.492 5.313a2 2 0 0 1-3 .019L5 15c-1.5-1.5-3-3.2-3-5.5"/>',mapPin:'<path d="M20 10c0 4.993-5.539 10.193-7.399 11.799a1 1 0 0 1-1.202 0C9.539 20.193 4 14.993 4 10a8 8 0 0 1 16 0"/><circle cx="12" cy="10" r="3"/>',checkCircle:'<path d="M22 11.08V12a10 10 0 1 1-5.93-9.14"/><path d="m9 11 3 3L22 4"/>',x:'<path d="M18 6 6 18"/><path d="m6 6 12 12"/>',download:'<path d="M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4"/><polyline points="7 10 12 15 17 10"/><line x1="12" x2="12" y1="15" y2="3"/>',send:'<path d="M14.536 21.686a.5.5 0 0 0 .937-.024l6.5-19a.496.496 0 0 0-.635-.635l-19 6.5a.5.5 0 0 0-.024.937l7.93 3.18a2 2 0 0 1 1.112 1.11z"/><path d="m21.854 2.147-10.94 10.939"/>'},ft={says:{label:"Says",icon:E.messageCircle,color:"#3b82f6"},thinks:{label:"Thinks",icon:E.lightbulb,color:"#8b5cf6"},does:{label:"Does",icon:E.wrench,color:"#f59e0b"},feels:{label:"Feels",icon:E.heart,color:"#ef4444"}},R={delighted:{emoji:"\u{1F604}",score:.95,color:"#16a34a"},satisfied:{emoji:"\u{1F60A}",score:.8,color:"#22c55e"},hopeful:{emoji:"\u{1F642}",score:.68,color:"#84cc16"},curious:{emoji:"\u{1F914}",score:.55,color:"#eab308"},neutral:{emoji:"\u{1F610}",score:.5,color:"#94a3b8"},uncertain:{emoji:"\u{1F615}",score:.4,color:"#f97316"},confused:{emoji:"\u{1F635}",score:.3,color:"#fb923c"},frustrated:{emoji:"\u{1F624}",score:.18,color:"#ef4444"},angry:{emoji:"\u{1F620}",score:.05,color:"#dc2626"}};var Re="https://cdn.jsdelivr.net/gh/faker-js/assets-person-portrait",Z=[32,64,128,256,512];function je(n){let t=0;for(let e=0;e<n.length;e++)t=n.charCodeAt(e)+((t<<5)-t);return t}function De(n){let t=Z[0],e=Math.abs(n-t);for(let s=1;s<Z.length;s++){let r=Math.abs(n-Z[s]);r<e&&(t=Z[s],e=r)}return t}function ie(n,t=128){let e=je(String(n)),s=(e%100+100)%100,r=(e>>>16&1)===0?"female":"male",a=De(t);return`${Re}/${r}/${a}/${s}.jpg`}function bt(n){let t=0;for(let e=0;e<n.length;e++)t=n.charCodeAt(e)+((t<<5)-t);return t}var Fe=["Sarah Chen","Marcus Johnson","Aisha Patel","James O'Brien","Yuki Tanaka","Elena Rodriguez","David Kim","Fatima Al-Hassan","Lucas Silva","Priya Sharma","Noah Williams","Mei Lin","Carlos Mendez","Amara Osei","Henrik Larsson","Zara Ahmed"],Oe=["Product Manager","UX Designer","Frontend Developer","Data Analyst","Marketing Lead","QA Engineer","DevOps Lead","Content Strategist","Startup Founder","IT Director","Customer Success Lead","Research Scientist"],Be=["San Francisco, CA","Austin, TX","London, UK","Toronto, CA","Berlin, DE","Tokyo, JP","Sydney, AU","S\xE3o Paulo, BR"],He=["I need tools that help me stay organized without slowing me down.","The dashboard is where I live \u2014 it has to be fast and reliable.","I want to understand the data, not fight the interface.","If it takes more than two clicks, I\u2019ll find another way.","Collaboration shouldn\u2019t mean endless notification noise.","I just want it to work the way I expect it to.","Give me the big picture first, then let me drill into details.","Accessibility isn\u2019t a nice-to-have \u2014 it\u2019s how I use the web."],Ue=["Streamline daily workflows","Reduce context-switching","Stay aligned with the team","Make data-driven decisions quickly","Ship features on a predictable cadence","Automate repetitive tasks","Improve onboarding experience","Keep documentation up to date"],Ve=["Too many disconnected tools","Slow page loads break focus","Unclear ownership of tasks","Settings that reset unexpectedly","Notifications that bury important updates","Poor mobile experience","Inconsistent design across features","No offline support"],We=["Checks dashboards every morning","Prefers keyboard shortcuts over mouse","Skims docs, reads deeply only when stuck","Shares screenshots in Slack","Batches email to twice a day","Tests features in incognito first","Bookmarks frequently used reports","Uses dark mode exclusively"],gt=class extends HTMLElement{static get observedAttributes(){return["role","age","location","avatar","compact","src","data-list-stories","id"]}#e=new Map;#t=null;constructor(){super(),this.attachShadow({mode:"open"})}relatedStories(){if(!this.id)return[];let t=this.getRootNode(),e=t.querySelectorAll?t:document;return Array.from(e.querySelectorAll(`user-story[persona-id="${Qe(this.id)}"]:not([data-detail-clone])`))}#s(){for(let t of[...this.children]){let e=t.getAttribute("slot");e&&!this.getAttribute(e)&&this.#e.set(e,t.textContent.trim())}}_resolve(t){return this.getAttribute(t)||this.#e.get(t)||""}get data(){return{name:this.personaName,role:this.personaRole||void 0,age:this.age||void 0,location:this.location||void 0,avatar:this.avatar||void 0,quote:this.quote||void 0,bio:this.#e.get("bio")||void 0,goals:this.#e.get("goals")||void 0,frustrations:this.#e.get("frustrations")||void 0,behaviors:this.#e.get("behaviors")||void 0}}set data(t){!t||typeof t!="object"||(this._applyData(t),this.shadowRoot&&this.#o(),this.dispatchEvent(new CustomEvent("user-persona:data-changed",{detail:{data:this.data,source:"property"},bubbles:!0,composed:!0})))}_applyData(t){for(let e of["role","age","location","avatar"])t[e]&&this.setAttribute(e,String(t[e]));if(t.name&&!this.querySelector('[slot="name"]')){let e=document.createElement("h2");e.slot="name",e.textContent=String(t.name),this.appendChild(e)}if(t.quote&&!this.querySelector('[slot="quote"]')){let e=document.createElement("p");e.slot="quote",e.textContent=String(t.quote),this.appendChild(e)}for(let e of["bio","goals","frustrations","behaviors"])t[e]&&this.#e.set(e,String(t[e]))}async _loadSrc(t){if(t)try{let e=await fetch(t);if(!e.ok)throw new Error(`HTTP ${e.status}`);let s=await e.json();this._applyData(s),this.#o()}catch(e){console.warn(`[user-persona] Failed to load src="${t}":`,e)}}connectedCallback(){this.#s(),this.hasAttribute("data-mock")?this.#a():this.hasAttribute("src")&&this._loadSrc(this.getAttribute("src")),this.#o(),this.#i(),this.setAttribute("data-upgraded",""),this.dispatchEvent(new CustomEvent("persona-ready",{bubbles:!0,composed:!0,detail:{name:this.personaName,role:this.personaRole}}))}disconnectedCallback(){this.removeAttribute("data-upgraded"),this.#t?.disconnect(),this.#t=null}#i(){if(!this.hasAttribute("data-list-stories")||!this.id){this.#t?.disconnect(),this.#t=null;return}this.#t||(this.#t=new MutationObserver(()=>this.#r()),this.#t.observe(document.body,{childList:!0,subtree:!0,attributes:!0,attributeFilter:["persona-id"]}))}#r(){if(!this.shadowRoot)return;let t=this.shadowRoot.querySelector("[data-stories-section]");t&&(t.outerHTML=this.#n())}#n(){if(!this.hasAttribute("data-list-stories")||!this.id)return"";let t=this.relatedStories();return`
298
+ `;var Re=new Map;function A(i,t,e={}){let r=e.priority??10,s={impl:t,bundle:e.bundle,contract:e.contract,priority:r},a=Re.get(i);if(customElements.get(i)){if(!a||a.priority>=r){a&&a.priority===r&&a.impl!==t&&console.warn(`[VB Bundle] Tag <${i}> already registered by "${a.bundle}" (priority ${a.priority}). Skipping "${e.bundle}".`);return}console.warn(`[VB Bundle] Tag <${i}> defined by "${a.bundle}" cannot be replaced (customElements.define is permanent). "${e.bundle}" has higher priority but arrived late.`);return}if(a&&a.priority>=r){a.priority===r&&console.warn(`[VB Bundle] Tag <${i}> already registered by "${a.bundle}". Skipping "${e.bundle}" (first wins at equal priority).`);return}Re.set(i,s),customElements.define(i,t)}function p(i){return String(i??"").replace(/[&<>"']/g,t=>_r[t])}var _r={"&":"&amp;","<":"&lt;",">":"&gt;",'"':"&quot;","'":"&#39;"};function Pe(i){let t=String(i??"").trim();if(!t||/^[a-z][a-z0-9+.-]*:/i.test(t)&&!/^(https?:|data:image\/)/i.test(t))return"none";let e=t.replace(/["\\\n\r\f]/g,r=>`\\${r.charCodeAt(0).toString(16)} `);return p(`url("${e}")`)}function Z(i){let t=0,e=String(i??"");for(let r=0;r<e.length;r++)t=e.charCodeAt(r)+((t<<5)-t);return t}var z=class{#e=null;url=null;#t=!1;get pending(){return this.#t}start(t){this.#e?.abort();let e=new AbortController;return this.#e=e,this.#t=!1,this.url=t,{signal:e.signal,isCurrent:()=>this.#e===e&&!e.signal.aborted}}cancel(){let t=this.pending;return this.#e?.abort(),this.#e=null,this.#t=!1,this.url=null,t}async fetchJson(t){let{signal:e,isCurrent:r}=this.start(t);this.#t=!0;try{let s=await fetch(t,{signal:e});if(!s.ok)throw new Error(`HTTP ${s.status}`);let a=await s.json();return r()?(this.#t=!1,{data:a,isCurrent:r}):void 0}catch(s){if(s?.name==="AbortError"||!r())return;throw this.#t=!1,this.url=null,s}}};function at(i){return i.split(" ").map(t=>t[0]).join("").toUpperCase().slice(0,2)}function it(i){return`hsl(${(Z(i)%360+360)%360}, 65%, 55%)`}function S(i){return`<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true">${i}</svg>`}var q={user:'<path d="M19 21v-2a4 4 0 0 0-4-4H9a4 4 0 0 0-4 4v2"/><circle cx="12" cy="7" r="4"/>',pencil:'<path d="M21.174 6.812a1 1 0 0 0-3.986-3.987L3.842 16.174a2 2 0 0 0-.5.83l-1.321 4.352a.5.5 0 0 0 .623.622l4.353-1.32a2 2 0 0 0 .83-.497z"/><path d="m15 5 4 4"/>',check:'<path d="M20 6 9 17l-5-5"/>',target:'<circle cx="12" cy="12" r="10"/><circle cx="12" cy="12" r="6"/><circle cx="12" cy="12" r="2"/>',alertTriangle:'<path d="m21.73 18-8-14a2 2 0 0 0-3.48 0l-8 14A2 2 0 0 0 4 21h16a2 2 0 0 0 1.73-3"/><path d="M12 9v4"/><path d="M12 17h.01"/>',messageCircle:'<path d="M2.992 16.342a2 2 0 0 1 .094 1.167l-1.065 3.29a1 1 0 0 0 1.236 1.168l3.413-.998a2 2 0 0 1 1.099.092 10 10 0 1 0-4.777-4.719"/>',lightbulb:'<path d="M15 14c.2-1 .7-1.7 1.5-2.5 1-.9 1.5-2.2 1.5-3.5A6 6 0 0 0 6 8c0 1 .2 2.2 1.5 3.5.7.7 1.3 1.5 1.5 2.5"/><path d="M9 18h6"/><path d="M10 22h4"/>',wrench:'<path d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.106-3.105c.32-.322.863-.22.983.218a6 6 0 0 1-8.259 7.057l-7.91 7.91a1 1 0 0 1-2.999-3l7.91-7.91a6 6 0 0 1 7.057-8.259c.438.12.54.662.219.984z"/>',heart:'<path d="M2 9.5a5.5 5.5 0 0 1 9.591-3.676.56.56 0 0 0 .818 0A5.49 5.49 0 0 1 22 9.5c0 2.29-1.5 4-3 5.5l-5.492 5.313a2 2 0 0 1-3 .019L5 15c-1.5-1.5-3-3.2-3-5.5"/>',mapPin:'<path d="M20 10c0 4.993-5.539 10.193-7.399 11.799a1 1 0 0 1-1.202 0C9.539 20.193 4 14.993 4 10a8 8 0 0 1 16 0"/><circle cx="12" cy="10" r="3"/>',checkCircle:'<path d="M22 11.08V12a10 10 0 1 1-5.93-9.14"/><path d="m9 11 3 3L22 4"/>',x:'<path d="M18 6 6 18"/><path d="m6 6 12 12"/>',download:'<path d="M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4"/><polyline points="7 10 12 15 17 10"/><line x1="12" x2="12" y1="15" y2="3"/>',send:'<path d="M14.536 21.686a.5.5 0 0 0 .937-.024l6.5-19a.496.496 0 0 0-.635-.635l-19 6.5a.5.5 0 0 0-.024.937l7.93 3.18a2 2 0 0 1 1.112 1.11z"/><path d="m21.854 2.147-10.94 10.939"/>'},Wt={says:{label:"Says",icon:q.messageCircle,color:"#3b82f6"},thinks:{label:"Thinks",icon:q.lightbulb,color:"#8b5cf6"},does:{label:"Does",icon:q.wrench,color:"#f59e0b"},feels:{label:"Feels",icon:q.heart,color:"#ef4444"}},Ct={delighted:{emoji:"\u{1F604}",score:.95,color:"#16a34a"},satisfied:{emoji:"\u{1F60A}",score:.8,color:"#22c55e"},hopeful:{emoji:"\u{1F642}",score:.68,color:"#84cc16"},curious:{emoji:"\u{1F914}",score:.55,color:"#eab308"},neutral:{emoji:"\u{1F610}",score:.5,color:"#94a3b8"},uncertain:{emoji:"\u{1F615}",score:.4,color:"#f97316"},confused:{emoji:"\u{1F635}",score:.3,color:"#fb923c"},frustrated:{emoji:"\u{1F624}",score:.18,color:"#ef4444"},angry:{emoji:"\u{1F620}",score:.05,color:"#dc2626"}};function pt(i){let t=String(i??"").toLowerCase().trim();return Object.hasOwn(Ct,t)?Ct[t]:Ct.neutral}function De(i){return Object.hasOwn(Ct,String(i??"").toLowerCase().trim())}var nt=Object.freeze({critical:{label:"Critical",color:"#dc2626",bg:"rgba(220, 38, 38, 0.1)"},high:{label:"High",color:"#ea580c",bg:"rgba(234, 88, 12, 0.1)"},medium:{label:"Medium",color:"#ca8a04",bg:"rgba(202, 138, 4, 0.1)"},low:{label:"Low",color:"#16a34a",bg:"rgba(22, 163, 74, 0.1)"}}),ht=Object.freeze({backlog:{label:"Backlog",color:"#6b7280",bg:"rgba(107, 114, 128, 0.1)"},"to-do":{label:"To Do",color:"#3b82f6",bg:"rgba(59, 130, 246, 0.1)"},"in-progress":{label:"In Progress",color:"#8b5cf6",bg:"rgba(139, 92, 246, 0.1)"},review:{label:"Review",color:"#f59e0b",bg:"rgba(245, 158, 11, 0.1)"},done:{label:"Done",color:"#22c55e",bg:"rgba(34, 197, 94, 0.1)"}});function J(i,t,e){return Object.hasOwn(i,t)?i[t]:i[e]}function $t(i){return p(`#${encodeURIComponent(String(i??""))}`)}function ot(i){return i?i.split(",").map(t=>t.trim()).filter(Boolean):[]}function qt(i){return Array.isArray(i)?i.map(t=>String(t??"")):i==null||i===""?[]:[String(i)]}function I(i,t){return[...i.children].find(e=>e.getAttribute("slot")===t)}function E(i,t,e,{tag:r="p",list:s=!1,replace:a=!1}={}){if(e==null||e==="")return;let n=I(i,t);if(n&&!a)return;let o=s||Array.isArray(e),l=c=>c.tagName==="UL"||c.tagName==="OL",d=n;if(!d||o!==l(d)){let c=document.createElement(o?"ul":r);c.slot=t,d?d.replaceWith(c):i.appendChild(c),d=c}o?d.replaceChildren(...qt(e).map(c=>{let u=document.createElement("li");return u.textContent=c,u})):d.textContent=String(e)}function wt(i,t){let e=I(i,t);if(e){if(e.tagName==="UL"||e.tagName==="OL"){let r=[...e.querySelectorAll("li")].map(s=>s.textContent?.trim()??"").filter(Boolean);return r.length?r:void 0}return e.textContent?.trim()||void 0}}function mt(i){return i.getAttribute("detail")||(i.hasAttribute("compact")?"compact":"full")}function ft(i,t){for(let e of i.querySelectorAll(t)){let r=e.querySelector("slot");r&&r.assignedNodes().length===0&&e.setAttribute("data-empty","")}}var P=class extends HTMLElement{static readyEvent="";_slotCache=new Map;#e=!1;#t=!1;#r=new z;#a=0;#s=new Set;constructor(){super(),this.attachShadow({mode:"open"})}get _isSetUp(){return this.#e}connectedCallback(){if(this.#e){this._connect();return}this.#e=!0,this._cacheSlotValues(),this._setup();let t=this.getAttribute("src");t?this._loadSrc(t):(this._render(),this._fireReady()),this._connect(),this.setAttribute("data-upgraded",""),queueMicrotask(()=>{this.dispatchEvent(new CustomEvent(`${this.localName}:upgraded`,{bubbles:!0}))})}disconnectedCallback(){this._disconnect()}attributeChangedCallback(t,e,r){if(!(!this.#e||e===r)){if(this.#a){t!=="src"&&this.#s.add(t);return}if(t==="src"){this._loadSrc(r);return}this._attributeEffects(t),this._attributeChanged(t)}}_setup(){}_connect(){}_disconnect(){}_attributeEffects(t){}_attributeChanged(t){this._render()}_render(){}_readyDetail(){return{}}_applyData(t){}_renderLoading(){this._render()}_renderError(t){console.warn(`[${this.localName}] Failed to load src="${this.getAttribute("src")}":`,t)}_cacheSlotValues(){for(let t of this.children){let e=t.getAttribute("slot");e&&this._slotCache.set(e,t.textContent?.trim()??"")}}_slotText(t){return I(this,t)?.textContent?.trim()||this._slotCache.get(t)||""}_quietly(t){this.#a++;try{t()}finally{this.#a--}if(this.#a===0&&this.#s.size){let e=[...this.#s];this.#s.clear();for(let r of e)this._attributeEffects(r)}}_setData(t){!t||typeof t!="object"||(this._quietly(()=>this._applyData(t)),this._cacheSlotValues(),this._render(),this.dispatchEvent(new CustomEvent(`${this.localName}:data-changed`,{detail:{data:this.data,source:"property"},bubbles:!0,composed:!0})))}_fireReady(){if(this.#t)return;let t=this.constructor.readyEvent;t&&(this.#t=!0,this.dispatchEvent(new CustomEvent(t,{detail:this._readyDetail(),bubbles:!0,composed:!0})))}async _loadSrc(t){if(!t){this.#r.cancel(),this._render(),this._fireReady();return}this._renderLoading();let e;try{e=await this.#r.fetchJson(t)}catch(s){this._renderError(s instanceof Error?s:new Error(String(s)));return}if(!e)return;let{data:r}=e;this._quietly(()=>this._applyData(r&&typeof r=="object"?r:{})),this._cacheSlotValues(),this._render(),this._fireReady()}};var wr="https://cdn.jsdelivr.net/gh/faker-js/assets-person-portrait",It=[32,64,128,256,512];function Ar(i){let t=It[0],e=Math.abs(i-t);for(let r=1;r<It.length;r++){let s=Math.abs(i-It[r]);s<e&&(t=It[r],e=s)}return t}function Oe(i,t=128){let e=Z(String(i)),r=(e%100+100)%100,s=(e>>>16&1)===0?"female":"male",a=Ar(t);return`${wr}/${s}/${a}/${r}.jpg`}var kr=["Sarah Chen","Marcus Johnson","Aisha Patel","James O'Brien","Yuki Tanaka","Elena Rodriguez","David Kim","Fatima Al-Hassan","Lucas Silva","Priya Sharma","Noah Williams","Mei Lin","Carlos Mendez","Amara Osei","Henrik Larsson","Zara Ahmed"],Sr=["Product Manager","UX Designer","Frontend Developer","Data Analyst","Marketing Lead","QA Engineer","DevOps Lead","Content Strategist","Startup Founder","IT Director","Customer Success Lead","Research Scientist"],Er=["San Francisco, CA","Austin, TX","London, UK","Toronto, CA","Berlin, DE","Tokyo, JP","Sydney, AU","S\xE3o Paulo, BR"],Cr=["I need tools that help me stay organized without slowing me down.","The dashboard is where I live \u2014 it has to be fast and reliable.","I want to understand the data, not fight the interface.","If it takes more than two clicks, I\u2019ll find another way.","Collaboration shouldn\u2019t mean endless notification noise.","I just want it to work the way I expect it to.","Give me the big picture first, then let me drill into details.","Accessibility isn\u2019t a nice-to-have \u2014 it\u2019s how I use the web."],$r=["Streamline daily workflows","Reduce context-switching","Stay aligned with the team","Make data-driven decisions quickly","Ship features on a predictable cadence","Automate repetitive tasks","Improve onboarding experience","Keep documentation up to date"],qr=["Too many disconnected tools","Slow page loads break focus","Unclear ownership of tasks","Settings that reset unexpectedly","Notifications that bury important updates","Poor mobile experience","Inconsistent design across features","No offline support"],Ir=["Checks dashboards every morning","Prefers keyboard shortcuts over mouse","Skims docs, reads deeply only when stuck","Shares screenshots in Slack","Batches email to twice a day","Tests features in incognito first","Bookmarks frequently used reports","Uses dark mode exclusively"],Nr=["bio","goals","frustrations","behaviors"],Qt=class extends P{static readyEvent="persona-ready";static get observedAttributes(){return["name","role","age","location","avatar","quote","compact","src","data-list-stories","id"]}#e=null;relatedStories(){if(!this.id)return[];let t=this.getRootNode(),e=t.querySelectorAll?t:document;return Array.from(e.querySelectorAll(`user-story[persona-id="${Tr(this.id)}"]:not([data-detail-clone])`))}get data(){return{name:this.personaName,role:this.personaRole||void 0,age:this.age||void 0,location:this.location||void 0,avatar:this.avatar||void 0,quote:this.quote||void 0,bio:wt(this,"bio"),goals:wt(this,"goals"),frustrations:wt(this,"frustrations"),behaviors:wt(this,"behaviors")}}set data(t){this._setData(t)}_applyData(t){for(let e of["role","age","location","avatar"])t[e]!=null&&t[e]!==""&&this.setAttribute(e,String(t[e]));E(this,"name",t.name,{tag:"h2",replace:!0}),E(this,"quote",t.quote,{tag:"p",replace:!0});for(let e of Nr)E(this,e,t[e],{tag:"p",replace:!0})}_setup(){this.hasAttribute("data-mock")&&this.#s()}_connect(){this.#t(),this.#r()}_disconnect(){this.#e?.disconnect(),this.#e=null}_attributeEffects(t){(t==="data-list-stories"||t==="id")&&this.#t()}_readyDetail(){return{name:this.personaName,role:this.personaRole}}#t(){if(!this.hasAttribute("data-list-stories")||!this.id){this.#e?.disconnect(),this.#e=null;return}this.#e||(this.#e=new MutationObserver(()=>this.#r()),this.#e.observe(document.body,{childList:!0,subtree:!0,attributes:!0,attributeFilter:["persona-id"]}))}#r(){if(!this.shadowRoot)return;let t=this.shadowRoot.querySelector("[data-stories-section]");t&&(t.outerHTML=this.#a())}#a(){if(!this.hasAttribute("data-list-stories")||!this.id)return"";let t=this.relatedStories();return`
298
299
  <section class="section" part="section-stories" data-stories-section>
299
300
  <div class="section-header">
300
301
  <div class="section-icon stories" aria-hidden="true">
301
302
  <svg viewBox="0 0 24 24"><path d="M14 2H6c-1.1 0-1.99.9-1.99 2L4 20c0 1.1.89 2 1.99 2H18c1.1 0 2-.9 2-2V8l-6-6zm2 16H8v-2h8v2zm0-4H8v-2h8v2zm-3-5V3.5L18.5 9H13z"/></svg>
302
303
  </div>
303
- <span class="section-title">Stories <span class="section-count">${t.length}</span></span>
304
+ <h3 class="section-title">Stories <span class="section-count">${t.length}</span></h3>
304
305
  </div>
305
306
  <div class="section-content">
306
- ${t.length===0?'<p class="empty-stories">No user stories reference this persona yet.</p>':`<ul class="story-list">${t.map(e=>{let s=e.id||e.getAttribute("story-id")||"",r=e.querySelector('[slot="action"]')?.textContent?.trim()||e.getAttribute("action")||e.id||"untitled",a=e.getAttribute("priority")||"",i=e.getAttribute("status")||"";return`<li class="story-item" data-priority="${m(a)}" data-status="${m(i)}">${s?`<a href="#${m(s)}">${m(r)}</a>`:`<span>${m(r)}</span>`}${a?`<span class="story-meta">${m(a)}</span>`:""}${i?`<span class="story-meta">${m(i)}</span>`:""}</li>`}).join("")}</ul>`}
307
+ ${t.length===0?'<p class="empty-stories">No user stories reference this persona yet.</p>':`<ul class="story-list">${t.map(e=>{let r=e.id||e.getAttribute("story-id")||"",s=e.querySelector('[slot="action"]')?.textContent?.trim()||e.getAttribute("action")||e.id||"untitled",a=e.getAttribute("priority")||"",n=e.getAttribute("status")||"";return`<li class="story-item" data-priority="${p(a)}" data-status="${p(n)}">${r?`<a href="#${p(r)}">${p(s)}</a>`:`<span>${p(s)}</span>`}${a?`<span class="story-meta">${p(a)}</span>`:""}${n?`<span class="story-meta">${p(n)}</span>`:""}</li>`}).join("")}</ul>`}
307
308
  </div>
308
309
  </section>
309
- `}attributeChangedCallback(t,e,s){if(!(e===s||!this.shadowRoot)){if(t==="src"&&this.isConnected){this._loadSrc(s);return}(t==="data-list-stories"||t==="id")&&this.#i(),this.#o()}}get personaName(){return this.querySelector('[slot="name"]')?.textContent?.trim()||this.#e.get("name")||"Unnamed Persona"}get personaRole(){return this.getAttribute("role")||""}get age(){return this.getAttribute("age")||""}get location(){return this.getAttribute("location")||""}get avatar(){return this.getAttribute("avatar")||""}get quote(){return this.querySelector('[slot="quote"]')?.textContent?.trim()||this.#e.get("quote")||""}get compact(){return this.hasAttribute("compact")}#a(){let t=this.dataset.seed||this.dataset.mock||String(Date.now()),e=a=>a[(bt(t+a.length)%a.length+a.length)%a.length],s=(a,i)=>{let o=[];for(let c=0;c<i;c++)o.push(a[(bt(t+c+a.length)%a.length+a.length)%a.length]);return[...new Set(o)]};if(!this.querySelector('[slot="name"]')){let a=document.createElement("h2");a.slot="name",a.textContent=e(Fe),this.appendChild(a)}if(this.getAttribute("role")||this.setAttribute("role",e(Oe)),this.getAttribute("age")||this.setAttribute("age",String(25+(bt(t)%30+30)%30)),this.getAttribute("location")||this.setAttribute("location",e(Be)),!this.getAttribute("avatar")){let a=this.querySelector('[slot="name"]')?.textContent?.trim()||"Persona";this.setAttribute("avatar",ie(a,256))}if(!this.querySelector('[slot="quote"]')){let a=document.createElement("p");a.slot="quote",a.textContent=e(He),this.appendChild(a)}let r=(a,i)=>{if(this.querySelector(`[slot="${a}"]`))return;let o=document.createElement("ul");o.setAttribute("slot",a);for(let c of i){let d=document.createElement("li");d.textContent=c,o.appendChild(d)}this.appendChild(o)};r("goals",s(Ue,3)),r("frustrations",s(Ve,3)),r("behaviors",s(We,3))}#o(){let t=this.personaName,e=this.personaRole,s=this.age,r=this.location,a=this.avatar,i=this.quote,o=B(t),c=a?`background:url(${m(a)}) center/cover`:`background:${o}`;this.shadowRoot.innerHTML=`
310
- <style>${re}</style>
310
+ `}get personaName(){return this._slotText("name")||this.getAttribute("name")?.trim()||"Unnamed Persona"}get personaRole(){return this.getAttribute("role")||""}get age(){return this.getAttribute("age")||""}get location(){return this.getAttribute("location")||""}get avatar(){return this.getAttribute("avatar")||""}get quote(){return this._slotText("quote")||this.getAttribute("quote")?.trim()||""}get compact(){return this.hasAttribute("compact")}#s(){let t=this.dataset.seed||this.dataset.mock||String(Date.now()),e=a=>a[(Z(t+a.length)%a.length+a.length)%a.length],r=(a,n)=>{let o=[];for(let l=0;l<n;l++)o.push(a[(Z(t+l+a.length)%a.length+a.length)%a.length]);return[...new Set(o)]};if(!I(this,"name")&&!this.getAttribute("name")){let a=document.createElement("h2");a.slot="name",a.textContent=e(kr),this.appendChild(a)}if(this.getAttribute("role")||this.setAttribute("role",e(Sr)),this.getAttribute("age")||this.setAttribute("age",String(25+(Z(t)%30+30)%30)),this.getAttribute("location")||this.setAttribute("location",e(Er)),!this.getAttribute("avatar")){let a=this.personaName;this.setAttribute("avatar",Oe(a,256))}if(!I(this,"quote")&&!this.getAttribute("quote")){let a=document.createElement("p");a.slot="quote",a.textContent=e(Cr),this.appendChild(a)}let s=(a,n)=>{if(I(this,a))return;let o=document.createElement("ul");o.setAttribute("slot",a);for(let l of n){let d=document.createElement("li");d.textContent=l,o.appendChild(d)}this.appendChild(o)};s("goals",r($r,3)),s("frustrations",r(qr,3)),s("behaviors",r(Ir,3))}_render(){let t=this.personaName,e=this.personaRole,r=this.age,s=this.location,a=this.avatar,n=this.quote,o=it(t),l=a?`background:${Pe(a)} center/cover`:`background:${o}`;this.shadowRoot.innerHTML=`
311
+ <style>${ze}</style>
311
312
 
312
313
  <article class="persona-card" part="card" role="article"
313
- aria-label="User persona: ${m(t)}">
314
+ aria-label="User persona: ${p(t)}">
314
315
 
315
316
  <header class="persona-header" part="header">
316
- <div class="avatar" part="avatar" style="${c}"
317
- role="img" aria-label="Avatar for ${m(t)}">
318
- ${a?"":m(O(t))}
317
+ <div class="avatar" part="avatar" style="${l}"
318
+ role="img" aria-label="Avatar for ${p(t)}">
319
+ ${a?"":p(at(t))}
319
320
  </div>
320
321
  <div class="header-info">
321
322
  <div class="persona-name-wrap" part="name">
322
- <slot name="name"><h2 class="persona-name-fallback">${m(t)}</h2></slot>
323
+ <slot name="name"><h2 class="persona-name-fallback">${p(t)}</h2></slot>
323
324
  </div>
324
- ${e?`<p class="persona-role" part="role">${m(e)}</p>`:""}
325
+ ${e?`<p class="persona-role" part="role">${p(e)}</p>`:""}
325
326
  <div class="persona-meta" part="meta">
326
- ${s?`
327
+ ${r?`
327
328
  <span class="meta-item">
328
329
  <svg viewBox="0 0 24 24" aria-hidden="true"><path d="M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm0 3c1.66 0 3 1.34 3 3s-1.34 3-3 3-3-1.34-3-3 1.34-3 3-3zm0 14.2c-2.5 0-4.71-1.28-6-3.22.03-1.99 4-3.08 6-3.08 1.99 0 5.97 1.09 6 3.08-1.29 1.94-3.5 3.22-6 3.22z"/></svg>
329
- ${m(s)} years old
330
+ ${p(r)} years old
330
331
  </span>
331
332
  `:""}
332
- ${r?`
333
+ ${s?`
333
334
  <span class="meta-item">
334
335
  <svg viewBox="0 0 24 24" aria-hidden="true"><path d="M12 2C8.13 2 5 5.13 5 9c0 5.25 7 13 7 13s7-7.75 7-13c0-3.87-3.13-7-7-7zm0 9.5c-1.38 0-2.5-1.12-2.5-2.5s1.12-2.5 2.5-2.5 2.5 1.12 2.5 2.5-1.12 2.5-2.5 2.5z"/></svg>
335
- ${m(r)}
336
+ ${p(s)}
336
337
  </span>
337
338
  `:""}
338
339
  </div>
339
340
  </div>
340
341
  </header>
341
342
 
342
- ${i||this.querySelector('[slot="quote"]')?`
343
+ ${n||I(this,"quote")?`
343
344
  <div class="persona-quote" part="quote">
344
345
  <span class="quote-mark" aria-hidden="true">&ldquo;</span>
345
- <div class="quote-text-wrap"><slot name="quote"><p class="quote-text">${m(i)}</p></slot></div>
346
+ <div class="quote-text-wrap"><slot name="quote"><p class="quote-text">${p(n)}</p></slot></div>
346
347
  </div>
347
348
  `:""}
348
349
 
@@ -352,7 +353,7 @@ var re=`
352
353
  <div class="section-icon bio" aria-hidden="true">
353
354
  <svg viewBox="0 0 24 24"><path d="M12 12c2.21 0 4-1.79 4-4s-1.79-4-4-4-4 1.79-4 4 1.79 4 4 4zm0 2c-2.67 0-8 1.34-8 4v2h16v-2c0-2.66-5.33-4-8-4z"/></svg>
354
355
  </div>
355
- <span class="section-title">Background</span>
356
+ <h3 class="section-title">Background</h3>
356
357
  </div>
357
358
  <div class="section-content">
358
359
  <slot name="bio">No background information provided.</slot>
@@ -364,7 +365,7 @@ var re=`
364
365
  <div class="section-icon goals" aria-hidden="true">
365
366
  <svg viewBox="0 0 24 24"><path d="M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm-2 15l-5-5 1.41-1.41L10 14.17l7.59-7.59L19 8l-9 9z"/></svg>
366
367
  </div>
367
- <span class="section-title">Goals</span>
368
+ <h3 class="section-title">Goals</h3>
368
369
  </div>
369
370
  <div class="section-content">
370
371
  <slot name="goals">No goals specified.</slot>
@@ -376,7 +377,7 @@ var re=`
376
377
  <div class="section-icon frustrations" aria-hidden="true">
377
378
  <svg viewBox="0 0 24 24"><path d="M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm1 15h-2v-2h2v2zm0-4h-2V7h2v6z"/></svg>
378
379
  </div>
379
- <span class="section-title">Frustrations</span>
380
+ <h3 class="section-title">Frustrations</h3>
380
381
  </div>
381
382
  <div class="section-content">
382
383
  <slot name="frustrations">No frustrations listed.</slot>
@@ -388,17 +389,17 @@ var re=`
388
389
  <div class="section-icon behaviors" aria-hidden="true">
389
390
  <svg viewBox="0 0 24 24"><path d="M19 3H5c-1.1 0-2 .9-2 2v14c0 1.1.9 2 2 2h14c1.1 0 2-.9 2-2V5c0-1.1-.9-2-2-2zm-5 14H7v-2h7v2zm3-4H7v-2h10v2zm0-4H7V7h10v2z"/></svg>
390
391
  </div>
391
- <span class="section-title">Behaviors</span>
392
+ <h3 class="section-title">Behaviors</h3>
392
393
  </div>
393
394
  <div class="section-content">
394
395
  <slot name="behaviors">No behaviors documented.</slot>
395
396
  </div>
396
397
  </div>
397
398
 
398
- ${this.#n()}
399
+ ${this.#a()}
399
400
  </div>
400
401
  </article>
401
- `}};function Qe(n){return typeof CSS<"u"&&CSS.escape?CSS.escape(String(n)):String(n).replace(/["\\]/g,"\\$&")}w("user-persona",gt);var vt=`
402
+ `}};function Tr(i){return typeof CSS<"u"&&CSS.escape?CSS.escape(String(i)):String(i).replace(/["\\]/g,"\\$&")}A("user-persona",Qt);var Yt=`
402
403
  :host {
403
404
  --_bg: var(--user-story-bg, var(--color-surface, #ffffff));
404
405
  --_text: var(--user-story-text, var(--color-text, #1a1a1a));
@@ -604,6 +605,7 @@ var re=`
604
605
  .section-icon.tasks { background: var(--color-accent, #8b5cf6); }
605
606
 
606
607
  .section-title {
608
+ margin: 0;
607
609
  font-size: var(--_font-xs);
608
610
  font-weight: 600;
609
611
  color: var(--_muted);
@@ -668,13 +670,39 @@ var re=`
668
670
  margin: 0 !important;
669
671
  }
670
672
 
673
+ .visually-hidden {
674
+ position: absolute;
675
+ inline-size: 1px;
676
+ block-size: 1px;
677
+ padding: 0;
678
+ margin: -1px;
679
+ overflow: hidden;
680
+ clip-path: inset(50%);
681
+ white-space: nowrap;
682
+ border: 0;
683
+ }
684
+
671
685
  .story-title-fallback {
672
686
  font-size: var(--_font-sm);
673
687
  font-weight: 600;
674
688
  color: var(--_text);
675
689
  }
676
690
 
677
- /* Minimal detail level */
691
+ /* Minimal detail level \u2014 the card is a <button> that opens the detail dialog */
692
+ button.story-card--minimal {
693
+ display: block;
694
+ inline-size: 100%;
695
+ margin: 0;
696
+ font: inherit;
697
+ color: inherit;
698
+ text-align: start;
699
+ }
700
+
701
+ .story-card--minimal .story-body,
702
+ .story-card--minimal .story-title-wrap {
703
+ display: block;
704
+ }
705
+
678
706
  :host([detail="minimal"]) .story-card {
679
707
  padding: var(--_space-xs);
680
708
  }
@@ -721,43 +749,43 @@ var re=`
721
749
  :host([detail="compact"]) .slot-fallback {
722
750
  display: none;
723
751
  }
724
- `;var yt=class n extends HTMLElement{static get observedAttributes(){return["persona-id","priority","points","status","epic","story-id","compact","detail","src"]}static PRIORITIES={critical:{label:"Critical",color:"#dc2626",bg:"rgba(220, 38, 38, 0.1)"},high:{label:"High",color:"#ea580c",bg:"rgba(234, 88, 12, 0.1)"},medium:{label:"Medium",color:"#ca8a04",bg:"rgba(202, 138, 4, 0.1)"},low:{label:"Low",color:"#16a34a",bg:"rgba(22, 163, 74, 0.1)"}};static STATUSES={backlog:{label:"Backlog",color:"#6b7280",bg:"rgba(107, 114, 128, 0.1)"},"to-do":{label:"To Do",color:"#3b82f6",bg:"rgba(59, 130, 246, 0.1)"},"in-progress":{label:"In Progress",color:"#8b5cf6",bg:"rgba(139, 92, 246, 0.1)"},review:{label:"Review",color:"#f59e0b",bg:"rgba(245, 158, 11, 0.1)"},done:{label:"Done",color:"#22c55e",bg:"rgba(34, 197, 94, 0.1)"}};#e=new Map;#t=null;constructor(){super(),this.attachShadow({mode:"open"})}#s(){for(let t of[...this.children]){let e=t.getAttribute("slot");e&&this.#e.set(e,t.textContent.trim())}}_resolve(t){return this.getAttribute(t)||this.#e.get(t)||""}get data(){return{storyId:this.storyId||void 0,personaId:this.personaId||void 0,priority:this.priority,status:this.status,points:this.points||void 0,epic:this.epic||void 0,detail:this.getAttribute("detail")||void 0,persona:this.persona||void 0,action:this.action||void 0,benefit:this.benefit||void 0,title:this.storyTitle||void 0}}set data(t){!t||typeof t!="object"||(this._applyData(t),this.#s(),this.shadowRoot&&this.#o(),this.dispatchEvent(new CustomEvent("user-story:data-changed",{detail:{data:this.data,source:"property"},bubbles:!0,composed:!0})))}_applyData(t){for(let[e,s]of[["storyId","story-id"],["personaId","persona-id"],["priority","priority"],["status","status"],["points","points"],["epic","epic"],["detail","detail"]])t[e]!=null&&this.setAttribute(s,String(t[e]));if(t.persona&&!this.querySelector('[slot="persona"]')){let e=document.createElement("span");e.slot="persona",e.textContent=String(t.persona),this.appendChild(e)}if(t.action&&!this.querySelector('[slot="action"]')){let e=document.createElement("span");e.slot="action",e.textContent=String(t.action),this.appendChild(e)}if(t.benefit&&!this.querySelector('[slot="benefit"]')){let e=document.createElement("span");e.slot="benefit",e.textContent=String(t.benefit),this.appendChild(e)}if(t.title&&!this.querySelector('[slot="title"]')){let e=document.createElement("h3");e.slot="title",e.textContent=String(t.title),this.appendChild(e)}for(let e of["acceptance-criteria","tasks","notes"]){let s=e==="acceptance-criteria"?"acceptanceCriteria":e;if(t[s]&&!this.querySelector(`[slot="${e}"]`))if(Array.isArray(t[s])){let r=document.createElement("ul");r.slot=e;for(let a of t[s]){let i=document.createElement("li");i.textContent=String(a),r.appendChild(i)}this.appendChild(r)}else{let r=document.createElement("p");r.slot=e,r.textContent=String(t[s]),this.appendChild(r)}}}async _loadSrc(t){if(t)try{let e=await fetch(t);if(!e.ok)throw new Error(`HTTP ${e.status}`);let s=await e.json();this._applyData(s),this.#s(),this.#o()}catch(e){console.warn(`[user-story] Failed to load src="${t}":`,e)}}connectedCallback(){this.#s(),this.storyId&&!this.id&&!this.hasAttribute("data-detail-clone")&&(this.id=this.storyId),this.hasAttribute("src")&&this._loadSrc(this.getAttribute("src")),this.#o(),this.#i(),this.setAttribute("data-upgraded","")}disconnectedCallback(){this.removeAttribute("data-upgraded"),this.#t?.disconnect(),this.#t=null}attributeChangedCallback(t,e,s){e!==s&&this.shadowRoot&&(t==="src"&&this.isConnected?this._loadSrc(s):(this.#o(),t==="persona-id"&&this.#i()))}#i(){if(this.#t?.disconnect(),this.#t=null,!this.personaId||this.#r())return;let t=this.getRootNode(),s=(t&&typeof t.getElementById=="function"?t:document).getElementById(this.personaId);!s||s.tagName!=="USER-PERSONA"||(this.#t=new MutationObserver(()=>this.#o()),this.#t.observe(s,{attributes:!0,attributeFilter:["role"]}))}get persona(){return this.#r()||this.#n()||"user"}get personaId(){return this.getAttribute("persona-id")||""}#r(){return this.querySelector('[slot="persona"]')?.textContent?.trim()||this.#e.get("persona")||""}#n(){if(!this.personaId)return"";let t=this.getRootNode(),s=(t&&typeof t.getElementById=="function"?t:document).getElementById(this.personaId);return!s||s.tagName!=="USER-PERSONA"?"":s.getAttribute("role")?.trim()||""}#a(){return/^[aeio]/i.test(this.persona.trim())?"an":"a"}get action(){return this.querySelector('[slot="action"]')?.textContent?.trim()||this.#e.get("action")||""}get benefit(){return this.querySelector('[slot="benefit"]')?.textContent?.trim()||this.#e.get("benefit")||""}get priority(){return this.getAttribute("priority")||"medium"}get points(){return this.getAttribute("points")||""}get status(){return this.getAttribute("status")||"backlog"}get epic(){return this.getAttribute("epic")||""}get storyId(){return this.getAttribute("story-id")||""}get storyTitle(){return this.querySelector('[slot="title"]')?.textContent?.trim()||this.#e.get("title")||""}get _minimalLabel(){if(this.storyTitle)return this.storyTitle;let t=this.action;return t.length>40?t.slice(0,40)+"\u2026":t}get compact(){return this.hasAttribute("compact")}get _detailLevel(){return this.getAttribute("detail")?this.getAttribute("detail"):this.hasAttribute("compact")?"compact":"full"}updateStatus(t){n.STATUSES[t]&&(this.setAttribute("status",t),this.dispatchEvent(new CustomEvent("status-changed",{detail:{status:t,storyId:this.storyId},bubbles:!0,composed:!0})))}updatePriority(t){n.PRIORITIES[t]&&(this.setAttribute("priority",t),this.dispatchEvent(new CustomEvent("priority-changed",{detail:{priority:t,storyId:this.storyId},bubbles:!0,composed:!0})))}showDetail(){let t=`story-dialog-${this.storyId||this.id||"detail"}`,e=document.getElementById(t);e||(e=document.createElement("dialog"),e.id=t,e.setAttribute("data-size","l"),document.body.appendChild(e));let s=document.createElement("form");s.method="dialog";let r=document.createElement("header"),a=document.createElement("h3");a.textContent=this.storyTitle||this.storyId||"Story Detail";let i=document.createElement("button");i.type="submit",i.setAttribute("aria-label","Close"),i.textContent="\xD7",r.appendChild(a),r.appendChild(i);let o=document.createElement("section"),c=document.createElement("user-story");for(let l of this.getAttributeNames())l==="detail"||l==="compact"||l==="data-upgraded"||l==="draggable"||l==="data-id"||l==="data-quadrant"||c.setAttribute(l,this.getAttribute(l)??"");let d=[...this.children].some(l=>l.getAttribute("slot")&&l.tagName!=="DIALOG");c.setAttribute("detail",d?"full":"compact"),c.removeAttribute("id"),c.setAttribute("data-detail-clone","");for(let l of[...this.children])l.tagName!=="DIALOG"&&c.appendChild(l.cloneNode(!0));o.appendChild(c),s.appendChild(r),s.appendChild(o),e.innerHTML="",e.appendChild(s),e.addEventListener("close",()=>{e.innerHTML=""},{once:!0}),e.showModal()}#o(){let t=n.PRIORITIES[this.priority]||n.PRIORITIES.medium,e=n.STATUSES[this.status]||n.STATUSES.backlog,s=this._detailLevel,r=this.storyId?`User story: ${m(this.storyId)}`:"User story";if(this.shadowRoot){if(s==="minimal"){this.shadowRoot.innerHTML=`
725
- <style>${vt}</style>
726
- <article class="story-card story-card--minimal" role="article" aria-label="${r}"
727
- tabindex="0">
728
- <div class="story-body">
729
- ${this.storyId?`<span class="story-id">${m(this.storyId)}</span>`:""}
730
- <div class="story-title-wrap">
731
- <slot name="title"><span class="story-title-fallback">${m(this._minimalLabel||"[describe the action]")}</span></slot>
732
- </div>
733
- </div>
734
- </article>
735
- `;let a=this.shadowRoot.querySelector(".story-card--minimal");if(!a)return;a.addEventListener("click",()=>this.showDetail()),a.addEventListener("keydown",i=>{let o=i;(o.key==="Enter"||o.key===" ")&&(o.preventDefault(),this.showDetail())})}else this.shadowRoot.innerHTML=`
736
- <style>${vt}</style>
737
-
738
- <article class="story-card story-card--${s}" part="card" role="article" aria-label="${r}">
752
+ `;var Lr=0,Xt=class extends P{static readyEvent="story-ready";static get observedAttributes(){return["persona-id","priority","points","status","epic","story-id","compact","detail","src"]}static PRIORITIES=nt;static STATUSES=ht;#e=null;#t=null;constructor(){super(),this.addEventListener("keydown",this.#l)}get data(){return{storyId:this.storyId||void 0,personaId:this.personaId||void 0,priority:this.priority,status:this.status,points:this.points||void 0,epic:this.epic||void 0,detail:this.getAttribute("detail")||void 0,persona:this.persona||void 0,action:this.action||void 0,benefit:this.benefit||void 0,title:this.storyTitle||void 0}}set data(t){this._setData(t)}_applyData(t){for(let[e,r]of[["storyId","story-id"],["personaId","persona-id"],["priority","priority"],["status","status"],["points","points"],["epic","epic"],["detail","detail"]])t[e]!=null&&this.setAttribute(r,String(t[e]));E(this,"persona",t.persona,{tag:"span"}),E(this,"action",t.action,{tag:"span"}),E(this,"benefit",t.benefit,{tag:"span"}),E(this,"title",t.title,{tag:"h3"}),E(this,"acceptance-criteria",t.acceptanceCriteria),E(this,"tasks",t.tasks),E(this,"notes",t.notes)}_setup(){this.storyId&&!this.id&&!this.hasAttribute("data-detail-clone")&&(this.id=this.storyId)}_connect(){this.#r(),this.#o()}_disconnect(){this.#e?.disconnect(),this.#e=null,queueMicrotask(()=>{this.isConnected||this.#n()})}_attributeEffects(t){t==="persona-id"&&this.#r()}_readyDetail(){return{id:this.storyId,persona:this.persona,action:this.action,benefit:this.benefit,priority:this.priority,status:this.status,points:this.points}}#r(){if(this.#e?.disconnect(),this.#e=null,!this.personaId||this.#a())return;let t=this.getRootNode(),r=(t&&typeof t.getElementById=="function"?t:document).getElementById(this.personaId);!r||r.tagName!=="USER-PERSONA"||(this.#e=new MutationObserver(()=>this._render()),this.#e.observe(r,{attributes:!0,attributeFilter:["role"]}))}get persona(){return this.#a()||this.#s()||"user"}get personaId(){return this.getAttribute("persona-id")||""}#a(){return this._slotText("persona")}#s(){if(!this.personaId)return"";let t=this.getRootNode(),r=(t&&typeof t.getElementById=="function"?t:document).getElementById(this.personaId);return!r||r.tagName!=="USER-PERSONA"?"":r.getAttribute("role")?.trim()||""}#i(){return/^[aeio]/i.test(this.persona.trim())?"an":"a"}get action(){return this._slotText("action")}get benefit(){return this._slotText("benefit")}get priority(){return this.getAttribute("priority")||"medium"}get points(){return this.getAttribute("points")||""}get status(){return this.getAttribute("status")||"backlog"}get epic(){return this.getAttribute("epic")||""}get storyId(){return this.getAttribute("story-id")||""}get storyTitle(){return this._slotText("title")}get _minimalLabel(){if(this.storyTitle)return this.storyTitle;let t=this.action;return t.length>40?t.slice(0,40)+"\u2026":t}get compact(){return this.hasAttribute("compact")}get _detailLevel(){return mt(this)}updateStatus(t){Object.hasOwn(ht,t)&&(this.setAttribute("status",t),this.dispatchEvent(new CustomEvent("status-changed",{detail:{status:t,storyId:this.storyId},bubbles:!0,composed:!0})))}updatePriority(t){Object.hasOwn(nt,t)&&(this.setAttribute("priority",t),this.dispatchEvent(new CustomEvent("priority-changed",{detail:{priority:t,storyId:this.storyId},bubbles:!0,composed:!0})))}showDetail(){this.#n();let t=document.createElement("dialog");t.id=this.#c(),t.setAttribute("data-size","l");let e=document.createElement("form");e.method="dialog";let r=document.createElement("header"),s=document.createElement("h2");s.id=`${t.id}-title`,s.textContent=this.storyTitle||this.storyId||"Story Detail",t.setAttribute("aria-labelledby",s.id);let a=document.createElement("button");a.type="submit",a.setAttribute("aria-label","Close"),a.textContent="\xD7",r.appendChild(s),r.appendChild(a);let n=document.createElement("section"),o=document.createElement("user-story");for(let d of this.getAttributeNames())d==="detail"||d==="compact"||d==="data-upgraded"||d==="draggable"||d==="data-id"||d==="data-quadrant"||o.setAttribute(d,this.getAttribute(d)??"");let l=[...this.children].some(d=>d.getAttribute("slot"));o.setAttribute("detail",l?"full":"compact"),o.removeAttribute("id"),o.setAttribute("data-detail-clone","");for(let d of[...this.children])o.appendChild(d.cloneNode(!0));n.appendChild(o),e.appendChild(r),e.appendChild(n),t.appendChild(e),t.addEventListener("close",()=>{this.#t===t&&(this.#t=null),t.remove()},{once:!0}),document.body.appendChild(t),this.#t=t,t.showModal()}#c(){let t=`story-dialog-${this.storyId||this.id||"story"}`,e=t;for(;document.getElementById(e);)e=`${t}-${++Lr}`;return e}#n(){let t=this.#t;t&&(this.#t=null,t.open&&t.close(),t.remove())}get#d(){return this.parentElement?.localName==="drag-surface"}#o(){let t=this.shadowRoot?.querySelector(".story-card--minimal");t&&(t.tabIndex=this.#d?-1:0)}#l=t=>{t.key!=="Enter"||t.defaultPrevented||!this.#d||this._detailLevel!=="minimal"||this.getAttribute("aria-grabbed")==="true"||this.shadowRoot?.querySelector(".story-card--minimal")&&(t.preventDefault(),t.stopPropagation(),this.showDetail())};_render(){let t=J(nt,this.priority,"medium"),e=J(ht,this.status,"backlog"),r=this._detailLevel,s=this.storyId?`User story: ${p(this.storyId)}`:"User story";if(this.shadowRoot)if(r==="minimal"){let a=this._minimalLabel||"Untitled story",n=this.storyId?`${this.storyId}: ${a}`:a;this.shadowRoot.innerHTML=`
753
+ <style>${Yt}</style>
754
+ <button type="button" class="story-card story-card--minimal" part="card"
755
+ aria-haspopup="dialog" aria-label="${p(n)}">
756
+ <span class="story-body">
757
+ ${this.storyId?`<span class="story-id">${p(this.storyId)}</span>`:""}
758
+ <span class="story-title-wrap">
759
+ <slot name="title"><span class="story-title-fallback">${p(this._minimalLabel||"[describe the action]")}</span></slot>
760
+ </span>
761
+ </span>
762
+ </button>
763
+ `,this.shadowRoot.querySelector(".story-card--minimal")?.addEventListener("click",()=>this.showDetail()),this.#o()}else this.shadowRoot.innerHTML=`
764
+ <style>${Yt}</style>
765
+
766
+ <article class="story-card story-card--${r}" part="card" role="article" aria-label="${s}">
739
767
  <header class="story-header" part="header">
740
768
  <div class="story-meta">
741
- ${this.storyId?`<span class="story-id" part="id">${m(this.storyId)}</span>`:""}
742
- ${this.epic?`<span class="epic-badge" part="epic">${m(this.epic)}</span>`:""}
769
+ ${this.storyId?`<span class="story-id" part="id">${p(this.storyId)}</span>`:""}
770
+ ${this.epic?`<span class="epic-badge" part="epic">${p(this.epic)}</span>`:""}
743
771
  </div>
744
772
  <div class="story-badges">
745
773
  <span class="priority-badge" part="priority"
746
774
  style="color: ${t.color}; background: ${t.bg};"
747
- >${m(t.label)}</span>
775
+ >${p(t.label)}</span>
748
776
  <span class="status-badge" part="status"
749
777
  style="color: ${e.color}; background: ${e.bg};"
750
- >${m(e.label)}</span>
751
- ${this.points?`<span class="points-badge" part="points">${m(this.points)}</span>`:""}
778
+ >${p(e.label)}</span>
779
+ ${this.points?`<span class="points-badge" part="points">${p(this.points)}<span class="visually-hidden"> story points</span></span>`:""}
752
780
  </div>
753
781
  </header>
754
782
 
755
783
  <div class="story-body" part="body">
756
784
  <p class="story-statement" part="statement">
757
- <span class="keyword">As ${this.#a()}</span>
758
- ${this.personaId?`<a class="persona-text persona-text--link" href="#${m(this.personaId)}">${k(E.user)} <slot name="persona"><span>${m(this.#n()||"user")}</span></slot></a>`:'<span class="persona-text"><slot name="persona"><span>user</span></slot></span>'},
785
+ <span class="keyword">As ${this.#i()}</span>
786
+ ${this.personaId?`<a class="persona-text persona-text--link" href="#${p(this.personaId)}">${S(q.user)} <slot name="persona"><span>${p(this.#s()||"user")}</span></slot></a>`:'<span class="persona-text"><slot name="persona"><span>user</span></slot></span>'},
759
787
  <span class="keyword">I want</span>
760
- <span class="action-text"><slot name="action"><span>[describe the action]</span></slot></span>${this.benefit||this.querySelector('[slot="benefit"]')?`
788
+ <span class="action-text"><slot name="action"><span>[describe the action]</span></slot></span>${this.benefit||I(this,"benefit")?`
761
789
  <span class="keyword">so that</span>
762
790
  <span class="benefit-text"><slot name="benefit"></slot></span>`:""}
763
791
  </p>
@@ -769,7 +797,7 @@ var re=`
769
797
  <div class="section-icon acceptance">
770
798
  <svg viewBox="0 0 24 24"><path d="M9 16.17L4.83 12l-1.42 1.41L9 19 21 7l-1.41-1.41z"/></svg>
771
799
  </div>
772
- <span class="section-title">Acceptance Criteria</span>
800
+ <h3 class="section-title">Acceptance Criteria</h3>
773
801
  </div>
774
802
  <div class="section-content">
775
803
  <slot name="acceptance-criteria">
@@ -783,7 +811,7 @@ var re=`
783
811
  <div class="section-icon tasks">
784
812
  <svg viewBox="0 0 24 24"><path d="M19 3H5c-1.1 0-2 .9-2 2v14c0 1.1.9 2 2 2h14c1.1 0 2-.9 2-2V5c0-1.1-.9-2-2-2zm-5 14H7v-2h7v2zm3-4H7v-2h10v2zm0-4H7V7h10v2z"/></svg>
785
813
  </div>
786
- <span class="section-title">Tasks</span>
814
+ <h3 class="section-title">Tasks</h3>
787
815
  </div>
788
816
  <div class="section-content">
789
817
  <slot name="tasks">
@@ -797,7 +825,7 @@ var re=`
797
825
  <div class="section-icon notes">
798
826
  <svg viewBox="0 0 24 24"><path d="M3 17.25V21h3.75L17.81 9.94l-3.75-3.75L3 17.25zM20.71 7.04c.39-.39.39-1.02 0-1.41l-2.34-2.34c-.39-.39-1.02-.39-1.41 0l-1.83 1.83 3.75 3.75 1.83-1.83z"/></svg>
799
827
  </div>
800
- <span class="section-title">Notes</span>
828
+ <h3 class="section-title">Notes</h3>
801
829
  </div>
802
830
  <div class="section-content">
803
831
  <slot name="notes">
@@ -807,7 +835,7 @@ var re=`
807
835
  </div>
808
836
  </div>
809
837
  </article>
810
- `,s==="compact"&&this.shadowRoot.querySelectorAll(".section").forEach(i=>{let o=i.querySelector("slot");o&&o.assignedNodes().length===0&&i.setAttribute("data-empty","")});this.dispatchEvent(new CustomEvent("story-ready",{detail:{id:this.storyId,persona:this.persona,action:this.action,benefit:this.benefit,priority:this.priority,status:this.status,points:this.points},bubbles:!0,composed:!0}))}}};w("user-story",yt);var tt=`
838
+ `,r==="compact"&&ft(this.shadowRoot,".section")}};A("user-story",Xt);var Nt=`
811
839
  :host {
812
840
  display: block;
813
841
  font-family: var(--_font-sans);
@@ -1105,35 +1133,35 @@ var re=`
1105
1133
  .journey__grid-wrap { overflow: visible; }
1106
1134
  .row-label, .corner { position: relative; }
1107
1135
  }
1108
- `;var Xe=0;function M(n,t,e="vb-vt"){if(!n?.isConnected||typeof document>"u"||!("startViewTransition"in document)||matchMedia("(prefers-reduced-motion: reduce)").matches)return t(),null;let s=`${e}-${++Xe}`;n.style.viewTransitionName=s;let r=document.startViewTransition(t);return r.finished.finally(()=>{n.style.viewTransitionName===s&&(n.style.viewTransitionName="")}),r}var Ye=[{key:"actions",label:"Actions"},{key:"thoughts",label:"Thoughts"},{key:"touchpoints",label:"Touchpoints"},{key:"painPoints",label:"Pain Points"},{key:"opportunities",label:"Opportunities"}],xt=class extends HTMLElement{static get observedAttributes(){return["src","persona","persona-id","story-ids","compact"]}#e=new Map;constructor(){super(),this.attachShadow({mode:"open"}),this.__phases=null}get phases(){return this.__phases}set phases(t){this.__phases!==t&&(this.__phases=t,this.isConnected&&this._render(),this.dispatchEvent(new CustomEvent("user-journey:phases-changed",{detail:{phases:t,source:"property"},bubbles:!0,composed:!0})))}get data(){return{persona:this.getAttribute("persona")||void 0,personaId:this.getAttribute("persona-id")||void 0,title:this.querySelector('[slot="title"]')?.textContent?.trim()||void 0,summary:this.querySelector('[slot="summary"]')?.textContent?.trim()||void 0,phases:this.__phases||void 0}}set data(t){if(!(!t||typeof t!="object")){if(t.persona&&this.setAttribute("persona",String(t.persona)),t.personaId&&this.setAttribute("persona-id",String(t.personaId)),t.title&&!this.querySelector('[slot="title"]')){let e=document.createElement("h2");e.slot="title",e.textContent=t.title,this.appendChild(e)}if(t.summary&&!this.querySelector('[slot="summary"]')){let e=document.createElement("p");e.slot="summary",e.textContent=t.summary,this.appendChild(e)}t.phases!=null&&(this.__phases=t.phases),this.isConnected&&this._render(),this.dispatchEvent(new CustomEvent("user-journey:data-changed",{detail:{data:this.data,source:"property"},bubbles:!0,composed:!0}))}}#t(){for(let t of this.children){let e=t.getAttribute("slot");e&&this.#e.set(e,t.textContent.trim())}}_resolve(t){return this.getAttribute(t)||this.#e.get(t)||""}connectedCallback(){this.#t(),this.setAttribute("data-upgraded",""),this.hasAttribute("src")?this._loadSrc(this.getAttribute("src")):this._render()}disconnectedCallback(){this.removeAttribute("data-upgraded")}attributeChangedCallback(t){this.isConnected&&(t==="src"?this._loadSrc(this.getAttribute("src")):this._render())}async _loadSrc(t){if(!t)return;let e=this.shadowRoot;e.innerHTML=`<style>${tt}</style><div class="state-msg">Loading\u2026</div>`;try{let s=await fetch(t);if(!s.ok)throw new Error(`HTTP ${s.status}`);let r=await s.json();if(r.persona&&this.setAttribute("persona",r.persona),r.personaId&&this.setAttribute("persona-id",r.personaId),r.title&&!this.querySelector('[slot="title"]')){let a=document.createElement("h2");a.slot="title",a.textContent=r.title,this.appendChild(a)}if(r.summary&&!this.querySelector('[slot="summary"]')){let a=document.createElement("p");a.slot="summary",a.textContent=r.summary,this.appendChild(a)}this.__phases=r.phases||[],this._render()}catch(s){e.innerHTML=`<style>${tt}</style><div class="state-msg state-msg--error">Could not load journey: ${m(s.message)}</div>`}}_render(){let t=this._resolve("persona")||"",e=this._resolve("persona-id")||"",s=(this.getAttribute("story-ids")||"").split(",").map(u=>u.trim()).filter(Boolean),r=this.hasAttribute("compact"),a=this.__phases,i=!!this.querySelector('[slot="summary"]')||this.#e.has("summary"),o=this.querySelector('[slot="title"]')?.textContent?.trim()||this.#e.get("title")||"",c=`<style>${tt}</style>
1109
- <article class="journey${r?" journey--compact":""}">
1136
+ `;var Mr=0;function D(i,t,e="vb-vt"){if(!i?.isConnected||typeof document>"u"||!("startViewTransition"in document)||matchMedia("(prefers-reduced-motion: reduce)").matches)return t(),null;let r=`${e}-${++Mr}`;i.style.viewTransitionName=r;let s=document.startViewTransition(t);return s.ready.catch(()=>{}),s.finished.catch(()=>{}).finally(()=>{i.style.viewTransitionName===r&&(i.style.viewTransitionName="")}),s}var zr=[{key:"actions",label:"Actions"},{key:"thoughts",label:"Thoughts"},{key:"touchpoints",label:"Touchpoints"},{key:"painPoints",label:"Pain Points"},{key:"opportunities",label:"Opportunities"}],Jt=class extends P{static readyEvent="journey-ready";static get observedAttributes(){return["src","persona","persona-id","story-ids","compact"]}__phases=null;get phases(){return this.__phases}set phases(t){this.__phases!==t&&(this.__phases=t,this._isSetUp&&this._render(),this.dispatchEvent(new CustomEvent("user-journey:phases-changed",{detail:{phases:t,source:"property"},bubbles:!0,composed:!0})))}get data(){return{persona:this.getAttribute("persona")||void 0,personaId:this.getAttribute("persona-id")||void 0,title:I(this,"title")?.textContent?.trim()||void 0,summary:I(this,"summary")?.textContent?.trim()||void 0,phases:this.__phases||void 0}}set data(t){this._setData(t)}_applyData(t){t.persona&&this.setAttribute("persona",String(t.persona)),t.personaId&&this.setAttribute("persona-id",String(t.personaId)),E(this,"title",t.title,{tag:"h2"}),E(this,"summary",t.summary),t.phases!=null&&(this.__phases=t.phases)}_readyDetail(){let t=this.__phases;return{title:this._slotText("title"),persona:this._resolve("persona"),phaseCount:Array.isArray(t)?t.length:0}}_resolve(t){return this.getAttribute(t)||this._slotCache.get(t)||""}#e(){return this._slotText("title")||"User Journey"}_renderLoading(){this.shadowRoot.innerHTML=`<style>${Nt}</style><div class="state-msg">Loading\u2026</div>`}_renderError(t){this.shadowRoot.innerHTML=`<style>${Nt}</style><div class="state-msg state-msg--error">Could not load journey: ${p(t.message)}</div>`}_render(){let t=this._resolve("persona")||"",e=this._resolve("persona-id")||"",r=ot(this.getAttribute("story-ids")),s=this.hasAttribute("compact"),a=Array.isArray(this.__phases)?this.__phases:null,n=!!I(this,"summary")||this._slotCache.has("summary"),o=`<style>${Nt}</style>
1137
+ <article class="journey${s?" journey--compact":""}">
1110
1138
 
1111
1139
  <header class="journey__header">
1112
1140
  <div class="journey__header-top">
1113
1141
  <div class="journey__chips">
1114
1142
  <span class="chip chip--type">Journey Map</span>
1115
- ${s.map(u=>`<a class="chip chip--story" href="#${u}">${this._label(u)}</a>`).join("")}
1143
+ ${r.map(c=>`<a class="chip chip--story" href="${$t(c)}">${p(this._label(c))}</a>`).join("")}
1116
1144
  </div>
1117
1145
  ${t?`
1118
1146
  <div class="journey__persona">
1119
- ${e?`<a class="persona-ref" href="#${e}">${k(E.user)} ${m(t)}</a>`:`<span class="persona-ref">${k(E.user)} ${m(t)}</span>`}
1147
+ ${e?`<a class="persona-ref" href="${$t(e)}">${S(q.user)} ${p(t)}</a>`:`<span class="persona-ref">${S(q.user)} ${p(t)}</span>`}
1120
1148
  </div>`:""}
1121
1149
  </div>
1122
1150
  <div class="journey__title-wrap">
1123
1151
  <slot name="title"><h2 class="journey__title">User Journey</h2></slot>
1124
1152
  </div>
1125
- ${i?'<div class="journey__summary-wrap"><slot name="summary"></slot></div>':""}
1153
+ ${n?'<div class="journey__summary-wrap"><slot name="summary"></slot></div>':""}
1126
1154
  </header>
1127
1155
 
1128
1156
  ${a&&a.length?this._curve(a)+this._grid(a):`<div class="journey__placeholder">
1129
1157
  <p>Add phase data via <code>src</code> (JSON) or set <code>.phases</code> programmatically.</p>
1130
1158
  </div>`}
1131
1159
 
1132
- </article>`,d=this.shadowRoot,l=()=>{d.innerHTML=c};d.querySelector("article")?M(this,l,"uj-vt"):l(),this.dispatchEvent(new CustomEvent("journey-ready",{bubbles:!0,composed:!0,detail:{title:o,persona:t,phaseCount:a?a.length:0}}))}_curve(t){let c=t.length,d=b=>28+(c<2?944/2:b/(c-1)*944),l=b=>14+(1-(R[b.emotion]||R.neutral).score)*72,u=t.map((b,v)=>({x:d(v),y:l(b),ph:b})),p=`M ${u[0].x},${u[0].y}`;for(let b=1;b<u.length;b++){let v=u[b-1],x=u[b],_=(v.x+x.x)/2;p+=` C ${_},${v.y} ${_},${x.y} ${x.x},${x.y}`}let h=`uj-${Math.random().toString(36).slice(2,8)}`,f=u.at(-1);return`
1160
+ </article>`,l=this.shadowRoot,d=()=>{l.innerHTML=o};l.querySelector("article")?D(this,d,"uj-vt"):d()}_curve(t){let l=t.length,d=b=>28+(l<2?944/2:b/(l-1)*944),c=b=>14+(1-pt(b?.emotion).score)*72,u=t.map((b,g)=>({x:d(g),y:c(b),ph:b})),m=`M ${u[0].x},${u[0].y}`;for(let b=1;b<u.length;b++){let g=u[b-1],w=u[b],v=(g.x+w.x)/2;m+=` C ${v},${g.y} ${v},${w.y} ${w.x},${w.y}`}let f=`uj-${Math.random().toString(36).slice(2,8)}`,h=u.at(-1);return`
1133
1161
  <div class="journey__curve" aria-hidden="true">
1134
1162
  <svg viewBox="0 0 1000 100" preserveAspectRatio="none" class="curve-svg">
1135
1163
  <defs>
1136
- <linearGradient id="${h}" x1="0" y1="0" x2="0" y2="1">
1164
+ <linearGradient id="${f}" x1="0" y1="0" x2="0" y2="1">
1137
1165
  <stop offset="0%" stop-color="#6366f1" stop-opacity="0.22"/>
1138
1166
  <stop offset="100%" stop-color="#6366f1" stop-opacity="0"/>
1139
1167
  </linearGradient>
@@ -1142,36 +1170,36 @@ var re=`
1142
1170
  <rect x="0" y="${100*.4}" width="1000" height="${100*.2}" class="zone zone--neu"/>
1143
1171
  <rect x="0" y="${100*.6}" width="1000" height="${100*.4}" class="zone zone--neg"/>
1144
1172
  ${u.map(({x:b})=>`<line x1="${b}" y1="0" x2="${b}" y2="100" class="vline"/>`).join("")}
1145
- <path d="${p} L ${f.x},100 L ${u[0].x},100 Z" fill="url(#${h})"/>
1146
- <path d="${p}" fill="none" class="curve-line"/>
1147
- ${u.map(({x:b,y:v,ph:x})=>{let _=R[x.emotion]||R.neutral;return`<circle cx="${b}" cy="${v}" r="5" class="dot" style="fill:${_.color}"/>`}).join("")}
1173
+ <path d="${m} L ${h.x},100 L ${u[0].x},100 Z" fill="url(#${f})"/>
1174
+ <path d="${m}" fill="none" class="curve-line"/>
1175
+ ${u.map(({x:b,y:g,ph:w})=>`<circle cx="${b}" cy="${g}" r="5" class="dot" style="fill:${pt(w?.emotion).color}"/>`).join("")}
1148
1176
  </svg>
1149
- </div>`}_grid(t){let e=t.map((r,a)=>{let i=R[r.emotion]||R.neutral,o=r.storyIds||[];return`
1150
- <th class="phase-head" data-emotion="${r.emotion||"neutral"}"
1151
- style="--ec:${i.color}">
1177
+ </div>`}_grid(t){let e=t.map((s,a)=>{let n=pt(s?.emotion),o=String(s?.emotion||"neutral"),l=qt(s?.storyIds);return`
1178
+ <th class="phase-head" data-emotion="${p(o)}"
1179
+ style="--ec:${n.color}">
1152
1180
  <span class="ph-num">${a+1}</span>
1153
- <span class="ph-name">${m(r.name||"")}</span>
1154
- <span class="ph-emoji" title="${r.emotion||"neutral"}"><span role="img" aria-label="${m(r.emotion||"neutral")}">${i.emoji}</span></span>
1155
- ${o.length?`<div class="ph-stories">${o.map(c=>`<a class="chip chip--story" href="#${c}">${this._label(c)}</a>`).join("")}</div>`:""}
1156
- </th>`}).join(""),s=Ye.map(({key:r,label:a})=>{let i=t.map(o=>{let c=o[r]||[];return c.length?`<td class="data-cell data-cell--${r.toLowerCase()}">
1157
- ${c.map(d=>`<p>${m(d)}</p>`).join("")}
1181
+ <span class="ph-name">${p(s?.name||"")}</span>
1182
+ <span class="ph-emoji" title="${p(o)}"><span role="img" aria-label="${p(o)}">${n.emoji}</span></span>
1183
+ ${l.length?`<div class="ph-stories">${l.map(d=>`<a class="chip chip--story" href="${$t(d)}">${p(this._label(d))}</a>`).join("")}</div>`:""}
1184
+ </th>`}).join(""),r=zr.map(({key:s,label:a})=>{let n=t.map(o=>{let l=qt(o?.[s]);return l.length?`<td class="data-cell data-cell--${s.toLowerCase()}">
1185
+ ${l.map(d=>`<p>${p(d)}</p>`).join("")}
1158
1186
  </td>`:'<td class="data-cell data-cell--empty">\u2014</td>'}).join("");return`
1159
- <tr class="grid-row grid-row--${r.toLowerCase()}">
1187
+ <tr class="grid-row grid-row--${s.toLowerCase()}">
1160
1188
  <th class="row-label">${a}</th>
1161
- ${i}
1189
+ ${n}
1162
1190
  </tr>`}).join("");return`
1163
1191
  <div class="journey__grid-wrap">
1164
1192
  <table class="journey__grid"
1165
- aria-label="${m(this.getAttribute("title")||"User Journey")} \u2014 phase breakdown">
1193
+ aria-label="${p(this.#e())} \u2014 phase breakdown">
1166
1194
  <thead>
1167
1195
  <tr>
1168
1196
  <th class="corner">Stage</th>
1169
1197
  ${e}
1170
1198
  </tr>
1171
1199
  </thead>
1172
- <tbody>${s}</tbody>
1200
+ <tbody>${r}</tbody>
1173
1201
  </table>
1174
- </div>`}_label(t){return t.replace(/^(activity|persona|journey|story|user)-/,"").replace(/-/g," ").replace(/\b\w/g,e=>e.toUpperCase())}};w("user-journey",xt);var et=`
1202
+ </div>`}_label(t){return String(t).replace(/^(activity|persona|journey|story|user)-/,"").replace(/-/g," ").replace(/\b\w/g,e=>e.toUpperCase())}};A("user-journey",Jt);var Tt=`
1175
1203
  :host {
1176
1204
  display: block;
1177
1205
  font-family: var(--_font-sans);
@@ -1389,6 +1417,7 @@ var re=`
1389
1417
  .quadrant--feels .quadrant__icon { background: var(--_feels-bg); color: var(--_feels); }
1390
1418
 
1391
1419
  .quadrant__label {
1420
+ margin: 0;
1392
1421
  font-size: 13px;
1393
1422
  font-weight: 700;
1394
1423
  text-transform: uppercase;
@@ -1684,8 +1713,8 @@ var re=`
1684
1713
  .state-msg { padding: var(--_space-l); font-size: var(--_font-sm); color: var(--_muted); font-style: italic; }
1685
1714
  .state-msg--error { color: var(--color-error-text, var(--color-error, #dc2626)); }
1686
1715
  code { font-family: var(--font-mono, Monaco, Menlo, monospace); font-size: 0.88em; }
1687
- `;var _t=["says","thinks","does","feels"],wt=class extends HTMLElement{static get observedAttributes(){return["persona","persona-id","src","editable","compact"]}#e=new Map;constructor(){super(),this.attachShadow({mode:"open"}),this.__quadrants=null,this.__goals=null,this.__painPoints=null,this._editingQuadrants=new Set}get quadrants(){return this.__quadrants}set quadrants(t){this.__quadrants=t,this.isConnected&&this._render()}get goals(){return this.__goals}set goals(t){this.__goals=t,this.isConnected&&this._render()}get painPoints(){return this.__painPoints}set painPoints(t){this.__painPoints=t,this.isConnected&&this._render()}#t(){for(let t of this.children){let e=t.getAttribute("slot");e&&this.#e.set(e,t.textContent.trim())}}_resolve(t){return this.getAttribute(t)||this.#e.get(t)||""}connectedCallback(){this.#t(),this.setAttribute("data-upgraded",""),this.hasAttribute("src")?this._loadSrc(this.getAttribute("src")):this._render()}disconnectedCallback(){this.removeAttribute("data-upgraded")}attributeChangedCallback(t){this.isConnected&&(t==="src"?this._loadSrc(this.getAttribute("src")):this._render())}get data(){let t=this.querySelector('[slot="title"]'),e=this.querySelector('[slot="summary"]');return{persona:this.getAttribute("persona")||void 0,personaId:this.getAttribute("persona-id")||void 0,title:t?.textContent?.trim()||void 0,summary:e?.textContent?.trim()||void 0,quadrants:this.__quadrants||void 0,goals:this.__goals||void 0,painPoints:this.__painPoints||void 0}}set data(t){if(!(!t||typeof t!="object")){if(t.persona&&this.setAttribute("persona",String(t.persona)),t.personaId&&this.setAttribute("persona-id",String(t.personaId)),t.title&&!this.querySelector('[slot="title"]')){let e=document.createElement("h2");e.slot="title",e.textContent=t.title,this.appendChild(e)}if(t.summary&&!this.querySelector('[slot="summary"]')){let e=document.createElement("p");e.slot="summary",e.textContent=t.summary,this.appendChild(e)}t.quadrants!=null&&(this.__quadrants=t.quadrants),t.goals!=null&&(this.__goals=t.goals),t.painPoints!=null&&(this.__painPoints=t.painPoints),this.isConnected&&this._render(),this.dispatchEvent(new CustomEvent("empathy-map:data-changed",{detail:{data:this.data,source:"property"},bubbles:!0,composed:!0}))}}editQuadrant(t){_t.includes(t)&&this.hasAttribute("editable")&&this._openEdit(t)}closeQuadrant(t){_t.includes(t)&&this._closeEdit(t)}async _loadSrc(t){if(!(!t||!this.shadowRoot)){this.shadowRoot.innerHTML=`<style>${et}</style><div class="state-msg">Loading\u2026</div>`;try{let e=await fetch(t);if(!e.ok)throw new Error(`HTTP ${e.status}`);let s=await e.json();if(s.persona&&this.setAttribute("persona",s.persona),s.personaId&&this.setAttribute("persona-id",s.personaId),s.title&&!this.querySelector('[slot="title"]')){let r=document.createElement("h2");r.slot="title",r.textContent=s.title,this.appendChild(r)}if(s.summary&&!this.querySelector('[slot="summary"]')){let r=document.createElement("p");r.slot="summary",r.textContent=s.summary,this.appendChild(r)}this.__quadrants=s.quadrants||null,this.__goals=s.goals||null,this.__painPoints=s.painPoints||null,this._render()}catch(e){if(!this.shadowRoot)return;let s=e instanceof Error?e.message:String(e);this.shadowRoot.innerHTML=`<style>${et}</style><div class="state-msg state-msg--error">Could not load empathy map: ${m(s)}</div>`}}}_render(){let t=this._resolve("persona")||"",e=this._resolve("persona-id")||"",s=this.hasAttribute("compact"),r=this.hasAttribute("editable"),a=!!this.querySelector('[slot="title"]')||this.#e.has("title"),i=!!this.querySelector('[slot="summary"]')||this.#e.has("summary"),o=this.__goals?.length||this.querySelector('[slot="goals"]'),c=this.__painPoints?.length||this.querySelector('[slot="pain-points"]'),d=`<style>${et}</style>
1688
- <article class="empathy-map${s?" empathy-map--compact":""}">
1716
+ `;var Kt=["says","thinks","does","feels"],Gt=class extends P{static readyEvent="empathy-map:ready";static get observedAttributes(){return["persona","persona-id","src","editable","compact"]}__quadrants=null;__goals=null;__painPoints=null;_editingQuadrants=new Set;_editedQuadrants=new Set;get quadrants(){return this.__quadrants}set quadrants(t){this.__quadrants=t,this._isSetUp&&this._render()}get goals(){return this.__goals}set goals(t){this.__goals=t,this._isSetUp&&this._render()}get painPoints(){return this.__painPoints}set painPoints(t){this.__painPoints=t,this._isSetUp&&this._render()}_resolve(t){return this.getAttribute(t)||this._slotCache.get(t)||""}_readyDetail(){return{title:this._slotText("title")||"Empathy Map",persona:this._resolve("persona")}}get data(){let t=I(this,"title"),e=I(this,"summary");return{persona:this.getAttribute("persona")||void 0,personaId:this.getAttribute("persona-id")||void 0,title:t?.textContent?.trim()||void 0,summary:e?.textContent?.trim()||void 0,quadrants:this.__quadrants||void 0,goals:this.__goals||void 0,painPoints:this.__painPoints||void 0}}set data(t){this._setData(t)}_applyData(t){t.persona&&this.setAttribute("persona",String(t.persona)),t.personaId&&this.setAttribute("persona-id",String(t.personaId)),E(this,"title",t.title,{tag:"h2"}),E(this,"summary",t.summary),t.quadrants!=null&&(this.__quadrants=t.quadrants),t.goals!=null&&(this.__goals=t.goals),t.painPoints!=null&&(this.__painPoints=t.painPoints)}editQuadrant(t){Kt.includes(t)&&this.hasAttribute("editable")&&this._openEdit(t)}closeQuadrant(t){Kt.includes(t)&&this._closeEdit(t)}_renderLoading(){this.shadowRoot.innerHTML=`<style>${Tt}</style><div class="state-msg">Loading\u2026</div>`}_renderError(t){this.shadowRoot.innerHTML=`<style>${Tt}</style><div class="state-msg state-msg--error">Could not load empathy map: ${p(t.message)}</div>`}_render(){let t=this._resolve("persona")||"",e=this._resolve("persona-id")||"",r=this.hasAttribute("compact"),s=this.hasAttribute("editable"),a=!!I(this,"summary")||this._slotCache.has("summary"),n=this.__goals?.length||I(this,"goals"),o=this.__painPoints?.length||I(this,"pain-points"),l=`<style>${Tt}</style>
1717
+ <article class="empathy-map${r?" empathy-map--compact":""}">
1689
1718
 
1690
1719
  <header class="empathy-map__header">
1691
1720
  <div class="empathy-map__header-top">
@@ -1694,90 +1723,88 @@ var re=`
1694
1723
  </div>
1695
1724
  ${t?`
1696
1725
  <div class="empathy-map__persona">
1697
- ${e?`<a class="persona-ref" href="#${m(e)}">${k(E.user)} ${m(t)}</a>`:`<span class="persona-ref">${k(E.user)} ${m(t)}</span>`}
1726
+ ${e?`<a class="persona-ref" href="#${p(e)}">${S(q.user)} ${p(t)}</a>`:`<span class="persona-ref">${S(q.user)} ${p(t)}</span>`}
1698
1727
  </div>`:""}
1699
1728
  </div>
1700
1729
  <div class="empathy-map__title-wrap">
1701
1730
  <slot name="title"><h2 class="empathy-map__title">Empathy Map</h2></slot>
1702
1731
  </div>
1703
- ${i?'<div class="empathy-map__summary-wrap"><slot name="summary"></slot></div>':""}
1732
+ ${a?'<div class="empathy-map__summary-wrap"><slot name="summary"></slot></div>':""}
1704
1733
  </header>
1705
1734
 
1706
1735
  <div class="empathy-map__grid">
1707
- ${_t.map(u=>this._renderQuadrant(u,r)).join("")}
1736
+ ${Kt.map(c=>this._renderQuadrant(c,s)).join("")}
1708
1737
  </div>
1709
1738
 
1710
- ${o||c?`
1739
+ ${n||o?`
1711
1740
  <footer class="empathy-map__footer">
1712
- ${this._renderSummaryRow("goals",k(E.target),"Goals")}
1713
- ${this._renderSummaryRow("pain-points",k(E.alertTriangle),"Pain Points")}
1741
+ ${this._renderSummaryRow("goals",S(q.target),"Goals")}
1742
+ ${this._renderSummaryRow("pain-points",S(q.alertTriangle),"Pain Points")}
1714
1743
  </footer>
1715
1744
  `:""}
1716
1745
 
1717
- </article>`,l=()=>{this.shadowRoot&&(this.shadowRoot.innerHTML=d,r&&this._bindEditListeners())};this.shadowRoot?.querySelector("article")?M(this,l,"em-vt"):l(),this.dispatchEvent(new CustomEvent("empathy-map:ready",{bubbles:!0,composed:!0,detail:{title:this.querySelector('[slot="title"]')?.textContent?.trim()||"Empathy Map",persona:t}}))}_renderQuadrant(t,e){let s=ft[t],r=this.__quadrants?.[t],a=this._editingQuadrants.has(t),i=r&&r.length?t==="feels"?r.map(c=>this._renderEmotion(c)).join(""):r.map(c=>`<p>${m(c)}</p>`).join(""):`<slot name="${t}"><p class="placeholder">Add ${s.label.toLowerCase()} items\u2026</p></slot>`,o=r?.length?r.join(`
1718
- `):"";return`
1746
+ </article>`,d=()=>{if(!this.shadowRoot)return;let c=this.#t();this.shadowRoot.innerHTML=l,s&&(this._bindEditListeners(),this.#r(c))};this.shadowRoot?.querySelector("article")?D(this,d,"em-vt"):d()}_renderQuadrant(t,e){let r=Wt[t],s=this.__quadrants?.[t],a=this._editingQuadrants.has(t),n=s&&s.length||this._editedQuadrants.has(t)?this._quadrantItemsHtml(t):`<slot name="${t}"><p class="placeholder">Add ${r.label.toLowerCase()} items\u2026</p></slot>`,o=this.#e(t);return`
1719
1747
  <section class="quadrant quadrant--${t}"${a?" data-editing":""}>
1720
1748
  <div class="quadrant__inner">
1721
1749
  <div class="quadrant__header">
1722
- <div class="quadrant__icon" aria-hidden="true">${k(s.icon)}</div>
1723
- <span class="quadrant__label">${s.label}</span>
1750
+ <div class="quadrant__icon" aria-hidden="true">${S(r.icon)}</div>
1751
+ <h3 class="quadrant__label">${r.label}</h3>
1724
1752
  ${e?`<button class="quadrant__edit-btn" data-quadrant="${t}"
1725
- aria-label="Edit ${s.label}" title="Edit ${s.label}">${k(E.pencil)}</button>`:""}
1753
+ aria-label="Edit ${r.label}" title="Edit ${r.label}">${S(q.pencil)}</button>`:""}
1726
1754
  </div>
1727
1755
  <div class="quadrant__faces">
1728
1756
  <div class="quadrant__face quadrant__face--front"${a?" inert":""}>
1729
1757
  <div class="quadrant__content">
1730
- ${i}
1758
+ ${n}
1731
1759
  </div>
1732
1760
  </div>
1733
1761
  ${e?`
1734
1762
  <div class="quadrant__face quadrant__face--back"${a?"":" inert"}>
1735
1763
  <textarea class="quadrant__editor" data-quadrant="${t}"
1736
1764
  placeholder="One item per line\u2026"
1737
- aria-label="Edit ${s.label} items">${m(o)}</textarea>
1765
+ aria-label="Edit ${r.label} items">${p(o)}</textarea>
1738
1766
  <button class="quadrant__done-btn" data-quadrant="${t}"
1739
- aria-label="Done editing ${s.label}">${k(E.check)} Done</button>
1767
+ aria-label="Done editing ${r.label}">${S(q.check)} Done</button>
1740
1768
  </div>
1741
1769
  `:""}
1742
1770
  </div>
1743
1771
  </div>
1744
- </section>`}_renderEmotion(t){let e=t.toLowerCase().trim(),s=R[e];return s?`<span class="emotion-tag" style="--ec:${s.color}"><span role="img" aria-label="${m(t)}">${s.emoji}</span> ${m(t)}</span>`:`<p>${m(t)}</p>`}_renderSummaryRow(t,e,s){let a=(t==="pain-points"?"painPoints":t)==="painPoints"?this.__painPoints:this.__goals,i=a?.length?a.map(o=>`<p>${m(o)}</p>`).join(""):`<slot name="${t}"><p class="placeholder">No ${s.toLowerCase()} specified.</p></slot>`;return`
1772
+ </section>`}_quadrantItemsHtml(t){let e=this.__quadrants?.[t]||[];return e.length?t==="feels"?e.map(r=>this._renderEmotion(r)).join(""):e.map(r=>`<p>${p(r)}</p>`).join(""):`<p class="placeholder">Add ${Wt[t].label.toLowerCase()} items\u2026</p>`}_renderEmotion(t){if(De(t)){let e=pt(t);return`<span class="emotion-tag" style="--ec:${e.color}"><span role="img" aria-label="${p(t)}">${e.emoji}</span> ${p(t)}</span>`}return`<p>${p(t)}</p>`}_renderSummaryRow(t,e,r){let a=(t==="pain-points"?"painPoints":t)==="painPoints"?this.__painPoints:this.__goals,n=a?.length?a.map(o=>`<p>${p(o)}</p>`).join(""):`<slot name="${t}"><p class="placeholder">No ${r.toLowerCase()} specified.</p></slot>`;return`
1745
1773
  <div class="summary-row">
1746
1774
  <span class="summary-row__icon" aria-hidden="true">${e}</span>
1747
1775
  <div class="summary-row__body">
1748
- <div class="summary-row__label">${s}</div>
1749
- <div class="summary-row__content">${i}</div>
1776
+ <div class="summary-row__label">${r}</div>
1777
+ <div class="summary-row__content">${n}</div>
1750
1778
  </div>
1751
- </div>`}_bindEditListeners(){let t=this.shadowRoot;t&&(t.querySelectorAll(".quadrant__edit-btn").forEach(e=>{e.addEventListener("click",()=>{let s=e.dataset.quadrant;s&&this._openEdit(s)})}),t.querySelectorAll(".quadrant__done-btn").forEach(e=>{e.addEventListener("click",()=>{let s=e.dataset.quadrant;s&&this._closeEdit(s)})}),t.querySelectorAll(".quadrant__editor").forEach(e=>{let s=e;s.addEventListener("keydown",r=>{let a=r;if(a.key==="Escape"){a.preventDefault();let i=s.dataset.quadrant;i&&this._closeEdit(i)}})}))}_openEdit(t){this._editingQuadrants.add(t);let e=this.shadowRoot?.querySelector(`.quadrant--${t}`);if(!e)return;e.setAttribute("data-editing","");let s=e.querySelector(".quadrant__face--front"),r=e.querySelector(".quadrant__face--back");s&&s.setAttribute("inert",""),r&&r.removeAttribute("inert");let a=e.querySelector(".quadrant__editor");if(a){let i=this.__quadrants?.[t];if(i?.length)a.value=i.join(`
1752
- `);else{let o=e.querySelector(`slot[name="${t}"]`);if(o){let c=o.assignedElements();if(c.length){let d=[];c.forEach(l=>{let u=l.querySelectorAll("li");u.length?u.forEach(p=>d.push(p.textContent?.trim()??"")):d.push(l.textContent?.trim()??"")}),a.value=d.filter(Boolean).join(`
1753
- `)}}}a.focus()}}_closeEdit(t){let e=this.shadowRoot?.querySelector(`.quadrant--${t}`);if(!e)return;let s=e.querySelector(".quadrant__editor");if(s){let i=s.value.split(`
1754
- `).map(c=>c.trim()).filter(Boolean);this.__quadrants||(this.__quadrants={}),this.__quadrants[t]=i;let o=e.querySelector(".quadrant__content");if(o)if(i.length)o.innerHTML=t==="feels"?i.map(c=>this._renderEmotion(c)).join(""):i.map(c=>`<p>${m(c)}</p>`).join("");else{let c=ft[t];o.innerHTML=`<p class="placeholder">Add ${c.label.toLowerCase()} items\u2026</p>`}}this._editingQuadrants.delete(t),e.removeAttribute("data-editing");let r=e.querySelector(".quadrant__face--front"),a=e.querySelector(".quadrant__face--back");r&&r.removeAttribute("inert"),a&&a.setAttribute("inert",""),this.dispatchEvent(new CustomEvent("empathy-map:update",{bubbles:!0,composed:!0,detail:{quadrant:t,items:this.__quadrants?.[t]||[]}}))}};w("empathy-map",wt);var C=class extends HTMLElement{#e=[];#t;connectedCallback(){this.hasAttribute("data-upgraded")||this.setup()!==!1&&(this.setAttribute("data-upgraded",""),queueMicrotask(()=>{this.dispatchEvent(new CustomEvent(`${this.localName}:upgraded`,{bubbles:!0}))}))}disconnectedCallback(){for(let t of this.#e)t();this.#e=[],this.removeAttribute("data-upgraded"),this.teardown()}listen(t,e,s,r){t.addEventListener(e,s,r),this.#e.push(()=>t.removeEventListener(e,s,r))}setup(){}teardown(){}setState(t,e){this.#t||(this.#t=this.attachInternals());let s=this.#t.states;try{e?s.add(t):s.delete(t)}catch{let r=`--${t}`;e?s.add(r):s.delete(r)}}_adoptInternals(t){this.#t||(this.#t=t)}};function st({newItems:n,nodes:t,keyOf:e,renderItem:s,containerFor:r}){let a=[],i=[],o=[],c=new Set;for(let l of n)c.add(e(l));for(let[l,u]of[...t])c.has(l)||(u.remove(),t.delete(l),o.push(l));let d=new Map;for(let l of n){let u=e(l),p=t.get(u)||null,h=r(l,p);d.has(h)||d.set(h,[]),d.get(h)?.push({item:l,key:u,existing:p})}for(let[l,u]of d)for(let p=0;p<u.length;p++){let{item:h,key:f,existing:b}=u[p],v=b;v?(v.parentElement!==l||l.children[p]!==v)&&i.push(f):(v=s(h),t.set(f,v),a.push(f));let x=l.children[p];x!==v&&l.insertBefore(v,x||null)}return{added:a,moved:i,removed:o}}var At=class n extends C{static QUADRANTS=["quick-wins","big-bets","fill-ins","money-pit"];static LABELS={"quick-wins":"Quick Wins","big-bets":"Big Bets","fill-ins":"Fill-Ins","money-pit":"Money Pit"};static DESCRIPTIONS={"quick-wins":"High impact \xB7 Low effort","big-bets":"High impact \xB7 High effort","fill-ins":"Low impact \xB7 Low effort","money-pit":"Low impact \xB7 High effort"};static#e=0;static get observedAttributes(){return["src","compact","title"]}#t=null;#s={};#i=null;#r="";#n=null;setup(){this.#r=`ie-${++n.#e}`;let t=[...this.querySelectorAll(":scope > [data-quadrant], :scope > [draggable]")],e=document.createElement("div");e.className="ie-wrapper";let s=document.createElement("div");s.className="ie-y-label",s.setAttribute("aria-hidden","true"),s.textContent="Impact \u2191";let r=document.createElement("div");r.style.cssText="display:flex;flex-direction:column;flex:1;min-width:0;";let a=document.createElement("div");a.className="ie-grid",a.setAttribute("role","region"),a.setAttribute("aria-label","Impact-Effort prioritization matrix");let i=document.createElement("div");i.className="ie-x-label",i.setAttribute("aria-hidden","true"),i.textContent="Effort \u2192";for(let l of n.QUADRANTS){let u=document.createElement("section");u.className="ie-quadrant",u.dataset.quadrantZone=l,u.setAttribute("aria-label",`${n.LABELS[l]}: ${n.DESCRIPTIONS[l]}`);let p=document.createElement("header");p.className="ie-quadrant-label",p.innerHTML=`${n.LABELS[l]}<br><span class="ie-quadrant-desc">${n.DESCRIPTIONS[l]}</span>`;let h=document.createElement("drag-surface");h.setAttribute("group",this.#r),h.setAttribute("aria-label",n.LABELS[l]),h.setAttribute("data-layout","stack"),h.setAttribute("data-layout-gap","xs"),u.appendChild(p),u.appendChild(h),a.appendChild(u),this.#s[l]=h}t.forEach((l,u)=>{let p=l,h=p.getAttribute("data-quadrant")||"quick-wins",f=this.#s[h]||this.#s["quick-wins"];p.hasAttribute("draggable")||p.setAttribute("draggable","true"),p.hasAttribute("data-id")||(p.dataset.id=`ie-item-${u}`),f.appendChild(p)});let o=document.createElement("div");o.className="ie-live-region",o.setAttribute("role","status"),o.setAttribute("aria-live","polite"),o.setAttribute("aria-atomic","true");let c=this.getAttribute("title");if(c){let l=document.createElement("h3");l.className="ie-title",l.textContent=c,this.prepend(l)}r.appendChild(a),r.appendChild(i),e.appendChild(s),e.appendChild(r),this.appendChild(e),this.appendChild(o),this.#t=a,this.#i=o,this.#n=e,this.listen(this,"drag-surface:transfer",l=>{let{item:u,fromSurface:p,toSurface:h}=l.detail,f=this.#p(p),b=this.#p(h);!f||!b||(u.setAttribute("data-quadrant",b),this.#l(`Moved ${this.#u(u)} to ${n.LABELS[b]}`),this.dispatchEvent(new CustomEvent("impact-effort:move",{bubbles:!0,detail:{itemId:u.dataset.id,from:f,to:b,item:u}})))});let d=this.getAttribute("src");d&&this.#c(d),this.#m()}teardown(){this.#n&&(this.#n.remove(),this.#n=null),this.#i&&(this.#i.remove(),this.#i=null),this.#t=null,this.#s={},this.#o.clear(),this.#a=[]}#a=[];#o=new Map;get items(){if(this.#a.length)return this.#a;let t=[];for(let[e,s]of Object.entries(this.#s))for(let r of s.querySelectorAll(':scope > [draggable="true"]'))t.push({id:r.getAttribute("data-id")||void 0,quadrant:e,text:r.textContent?.trim()||void 0});return t}set items(t){if(!this.#t)return;let e=Array.isArray(t)?t:[];st({newItems:e,nodes:this.#o,keyOf:s=>s.id??`${s.quadrant}:${s.text}`,renderItem:s=>{let r=this;if(typeof r.renderItem=="function"){let i=r.renderItem(s);if(i instanceof Element)return i.hasAttribute("draggable")||i.setAttribute("draggable","true"),i.hasAttribute("data-id")||i.setAttribute("data-id",String(s.id??"")),i}let a=document.createElement("article");return a.className="ie-card",a.setAttribute("draggable","true"),s.id&&a.setAttribute("data-id",String(s.id)),a.textContent=s.text||s.id||"",a},containerFor:s=>this.#s[s.quadrant]||this.#s["quick-wins"]}),this.#a=e,this.dispatchEvent(new CustomEvent("impact-effort:items-changed",{detail:{items:e,source:"property"},bubbles:!0}))}attributeChangedCallback(t,e,s){this.hasAttribute("data-upgraded")&&t==="src"&&s&&s!==e&&this.#c(s)}async#c(t){try{let e=await fetch(t);if(!e.ok)throw new Error(`HTTP ${e.status}`);let s=await e.json();if(!Array.isArray(s))return;let r=()=>{for(let a of n.QUADRANTS){let i=this.#s[a];if(i)for(let o of[...i.querySelectorAll("[draggable]")])o.remove()}s.forEach((a,i)=>{let o=a.quadrant||"quick-wins",c=a.id||`ie-item-${i}`,d;a.persona||a.action||a.storyId?(d=document.createElement("user-story"),d.setAttribute("detail","minimal"),a.storyId&&d.setAttribute("story-id",a.storyId),a.persona&&d.setAttribute("persona",a.persona),a.action&&d.setAttribute("action",a.action),a.benefit&&d.setAttribute("benefit",a.benefit),a.priority&&d.setAttribute("priority",a.priority),a.status&&d.setAttribute("status",a.status),a.points&&d.setAttribute("points",String(a.points))):(d=document.createElement("article"),d.textContent=a.label||a.text||""),d.setAttribute("draggable","true"),d.dataset.id=c,d.dataset.quadrant=o,(this.#s[o]||this.#s["quick-wins"]).appendChild(d)})};this.hasAttribute("data-upgraded")&&this.#t?M(this,r,"ie-vt"):r(),this.#m()}catch(e){console.warn(`[impact-effort] Failed to load src="${t}":`,e)}}#p(t){for(let[e,s]of Object.entries(this.#s))if(s===t)return e;return null}#l(t){let e=this.#i;e&&(e.textContent="",requestAnimationFrame(()=>{e.textContent=t}))}#u(t){return t.dataset.id||t.textContent.trim().slice(0,40)}#m(){let t={};for(let e of n.QUADRANTS){let s=this.#s[e];t[e]=s?s.querySelectorAll('[draggable="true"]').length:0}this.dispatchEvent(new CustomEvent("impact-effort:ready",{bubbles:!0,detail:{quadrantCounts:t}}))}};w("impact-effort",At);var kt=class n extends C{static#e=0;setup(){this.#u=`qg-${++n.#e}`;let t=this.getAttribute("x-label")||"",e=this.getAttribute("y-label")||"",s=this.getAttribute("x-low")||"Low",r=this.getAttribute("x-high")||"High",a=this.getAttribute("y-low")||"Low",i=this.getAttribute("y-high")||"High",o=[this.getAttribute("q1-label")||"Q1",this.getAttribute("q2-label")||"Q2",this.getAttribute("q3-label")||"Q3",this.getAttribute("q4-label")||"Q4"],c=this.hasAttribute("draggable"),d=[...this.querySelectorAll(":scope > [data-quadrant], :scope > [data-x][data-y]")],l=document.createElement("section");l.className="qg-wrapper",l.setAttribute("role","region"),l.setAttribute("aria-label",`${e} \xD7 ${t} quadrant grid`);let u=document.createElement("header");u.className="qg-y-label",u.setAttribute("aria-hidden","true"),u.textContent=`\u2191 ${e}`;let p=document.createElement("aside");p.className="qg-y-scale",p.setAttribute("aria-hidden","true"),p.innerHTML=`<span>${i}</span><span>${a}</span>`;let h=document.createElement("div");h.className="qg-grid";let f=document.createElement("aside");f.className="qg-x-scale",f.setAttribute("aria-hidden","true"),f.innerHTML=`<span>${s}</span><span>${r}</span>`;let b=document.createElement("footer");b.className="qg-x-label",b.setAttribute("aria-hidden","true"),b.textContent=`${t} \u2192`;for(let x=0;x<4;x++){let _=document.createElement("section");_.className="qg-quadrant",_.dataset.quadrantZone=String(x),_.setAttribute("aria-label",o[x]);let g=document.createElement("header");if(g.className="qg-quadrant-label",g.textContent=o[x],_.appendChild(g),c){let y=document.createElement("drag-surface");y.setAttribute("group",this.#u),y.setAttribute("aria-label",o[x]),y.setAttribute("data-layout","stack"),y.setAttribute("data-layout-gap","xs"),_.appendChild(y),this.#m[x]=y}else{let y=document.createElement("ul");y.className="qg-items",_.appendChild(y),this.#g[x]=y}h.appendChild(_),this.#b[x]=_}d.forEach((x,_)=>{let g=x,y=this.#o(g),A=c?this.#m[y]:this.#g[y];if(c&&(g.hasAttribute("draggable")||g.setAttribute("draggable","true")),g.hasAttribute("data-id")||(g.dataset.id=`qg-item-${_}`),g.hasAttribute("data-x")&&g.hasAttribute("data-y")){let S=parseFloat(g.getAttribute("data-x")??""),$=parseFloat(g.getAttribute("data-y")??"");if(Number.isFinite(S)&&Number.isFinite($)){let T=y===0||y===3?(S-.5)*2:S*2,z=y===0||y===1?($-.5)*2:$*2;if(g.style.setProperty("--qg-local-x",T.toFixed(4)),g.style.setProperty("--qg-local-y",z.toFixed(4)),g.classList.add("qg-pinned"),!g.style.getPropertyValue("--qg-pin-hue")){let N=g.dataset.id||(g.textContent||"").trim();g.style.setProperty("--qg-pin-hue",`${n.#n(N)}deg`)}}}if(c)A.appendChild(g);else{let S=document.createElement("li");S.appendChild(g),A.appendChild(S)}});let v=document.createElement("div");v.className="qg-live-region visually-hidden",v.setAttribute("role","status"),v.setAttribute("aria-live","polite"),l.appendChild(u),l.appendChild(p),l.appendChild(h),l.appendChild(f),l.appendChild(b),this.appendChild(l),this.appendChild(v),this.#v=h,this.#d=v,this.#h=o,c&&this.listen(this,"drag-surface:transfer",this.#a),this.#t()}#t(){if(typeof ResizeObserver>"u")return;let t=e=>{let s=e.offsetWidth,r=e.offsetHeight;s>0&&e.style.setProperty("--qg-pin-half-w",`${s/2}px`),r>0&&e.style.setProperty("--qg-pin-half-h",`${r/2}px`)};this.#y=new ResizeObserver(e=>{for(let s of e)t(s.target);this.#s()});for(let e of this.querySelectorAll(".qg-pinned"))this.#y.observe(e);this.#s()}#s(){this.#f||(this.#f=requestAnimationFrame(()=>{this.#f=0,this.#i()}))}#i(){for(let e of this.querySelectorAll(".qg-pinned")){let s=e;s.classList.remove("qg-clustered"),s.style.removeProperty("--qg-cluster-i"),s.style.removeProperty("--qg-cluster-n"),delete s.dataset.cluster,s.dataset.qgTabbed!==void 0&&(s.removeAttribute("tabindex"),delete s.dataset.qgTabbed)}let t=0;for(let e=0;e<4;e++){let s=this.#b[e];if(!s)continue;let r=[...s.querySelectorAll(".qg-pinned")];if(r.length<2)continue;let a=r.map(l=>l.getBoundingClientRect()),i=Array.from({length:r.length},(l,u)=>u),o=l=>i[l]===l?l:i[l]=o(i[l]),c=(l,u)=>{let p=o(l),h=o(u);p!==h&&(i[p]=h)};for(let l=0;l<r.length;l++)for(let u=l+1;u<r.length;u++)n.#r(a[l],a[u])&&c(l,u);let d=new Map;for(let l=0;l<r.length;l++){let u=o(l);d.has(u)||d.set(u,[]),d.get(u)?.push(l)}for(let l of d.values()){if(l.length<2)continue;let u=`c${++t}`;l.forEach((p,h)=>{let f=r[p];f.classList.add("qg-clustered"),f.dataset.cluster=u,f.style.setProperty("--qg-cluster-i",String(h)),f.style.setProperty("--qg-cluster-n",String(l.length)),!f.hasAttribute("tabindex")&&!f.matches("a, button, [contenteditable]")&&(f.setAttribute("tabindex","0"),f.dataset.qgTabbed="")})}}}teardown(){this.#y?.disconnect(),this.#y=null,this.#f&&cancelAnimationFrame(this.#f),this.#f=0}static#r(t,e){return!(t.right<=e.left||e.right<=t.left||t.bottom<=e.top||e.bottom<=t.top)}static#n(t){let e=5381;for(let s=0;s<t.length;s++)e=(e<<5)+e+t.charCodeAt(s)|0;return(e%360+360)%360}#a=t=>{let{item:e,fromSurface:s,toSurface:r}=t.detail,a=this.#c(s),i=this.#c(r);a==null||i==null||(e.setAttribute("data-quadrant",String(i)),this.#l(`Moved ${this.#p(e)} to ${this.#h[i]}`),this.dispatchEvent(new CustomEvent("quadrant-grid:move",{bubbles:!0,detail:{item:e,itemId:e.dataset.id,from:a,to:i}})))};#o(t){let e=parseInt(t.getAttribute("data-quadrant"),10);if(e>=0&&e<=3)return e;if(t.hasAttribute("data-x")&&t.hasAttribute("data-y")){let s=parseFloat(t.getAttribute("data-x")),r=parseFloat(t.getAttribute("data-y"));return n.quadrantFor(s,r)}return 0}static quadrantFor(t,e){let s=t>=.5,r=e>=.5;return r&&s?0:r&&!s?1:!r&&!s?2:3}#c(t){for(let e=0;e<4;e++)if(this.#m[e]===t)return e;return null}#p(t){return(t.textContent||"").trim().split(`
1755
- `)[0]||"item"}#l(t){this.#d&&(this.#d.textContent=t)}#u="";#m={};#g={};#b={};#v=null;#d=null;#h=[];#y=null;#f=0};w("quadrant-grid",kt);var ne=5,Ct=class n extends C{setup(){let t=this.querySelector(":scope > template"),e=t?n.#t(t):[];if(this.hasAttribute("src")){this.#e(this.getAttribute("src"));return}this.#s(e)}async#e(t){try{let s=await(await fetch(t)).json();this.#s(Array.isArray(s)?s:[])}catch(e){console.warn("risk-register: failed to load src",t,e),this.#s([])}}static#t(t){let e=[],s=t.content.querySelectorAll("tr");for(let r of s){let a=[...r.children],i=a[0]?.textContent?.trim()||"",o=r.getAttribute("data-id")||i.toLowerCase().replace(/\s+/g,"-")||`risk-${e.length}`;e.push({id:o,title:i,likelihood:parseInt(a[1]?.textContent??"",10)||0,impact:parseInt(a[2]?.textContent??"",10)||0,owner:a[3]?.textContent?.trim()||"",mitigation:a[4]?.textContent?.trim()||""})}return e}#s(t){this.#a=t,[...this.children].forEach(r=>{r.tagName!=="TEMPLATE"&&r.remove()});let e=this.getAttribute("label");if(e){let r=document.createElement("header");r.className="rr-label",r.textContent=e,this.appendChild(r)}let s=document.createElement("div");s.className="rr-layout",s.appendChild(this.#i(t)),s.appendChild(this.#r(t)),this.appendChild(s),queueMicrotask(()=>{this.dispatchEvent(new CustomEvent("risk-register:ready",{bubbles:!0,detail:{count:t.length}}))})}#i(t){let e=document.createElement("data-table"),s=document.createElement("table");return s.innerHTML=`
1779
+ </div>`}_bindEditListeners(){let t=this.shadowRoot;t&&(t.querySelectorAll(".quadrant__edit-btn").forEach(e=>{e.addEventListener("click",()=>{let r=e.dataset.quadrant;r&&this._openEdit(r)})}),t.querySelectorAll(".quadrant__done-btn").forEach(e=>{e.addEventListener("click",()=>{let r=e.dataset.quadrant;r&&this._closeEdit(r)})}),t.querySelectorAll(".quadrant__editor").forEach(e=>{let r=e;r.addEventListener("keydown",s=>{let a=s;if(a.key==="Escape"){a.preventDefault();let n=r.dataset.quadrant;n&&this._closeEdit(n)}})}))}_openEdit(t){let e=this.shadowRoot?.querySelector(`.quadrant--${t}`);if(!e)return;this._editingQuadrants.add(t),e.setAttribute("data-editing","");let r=e.querySelector(".quadrant__face--front"),s=e.querySelector(".quadrant__face--back");r&&r.setAttribute("inert",""),s&&s.removeAttribute("inert");let a=e.querySelector(".quadrant__editor");a&&(a.value=this.#e(t),a.focus())}#e(t){let e=this.__quadrants?.[t];if(e?.length)return e.join(`
1780
+ `);if(this._editedQuadrants.has(t))return"";let r=[];for(let s of this.children){if(s.getAttribute("slot")!==t)continue;let a=s.querySelectorAll("li");a.length?a.forEach(n=>r.push(n.textContent?.trim()??"")):r.push(s.textContent?.trim()??"")}return r.filter(Boolean).join(`
1781
+ `)}#t(){let t=new Map,e=this.shadowRoot;if(!e)return t;for(let r of this._editingQuadrants){let s=e.querySelector(`.quadrant__editor[data-quadrant="${r}"]`);s&&t.set(r,{value:s.value,start:s.selectionStart,end:s.selectionEnd,focused:e.activeElement===s})}return t}#r(t){let e=this.shadowRoot;if(e)for(let[r,s]of t){let a=e.querySelector(`.quadrant__editor[data-quadrant="${r}"]`);a&&(a.value=s.value,a.setSelectionRange(s.start,s.end),s.focused&&a.focus())}}_closeEdit(t){if(!this._editingQuadrants.has(t))return;let e=this.shadowRoot?.querySelector(`.quadrant--${t}`);if(!e)return;let r=e.querySelector(".quadrant__editor");if(r){let o=r.value.split(`
1782
+ `).map(d=>d.trim()).filter(Boolean);this.__quadrants||(this.__quadrants={}),this.__quadrants[t]=o,this._editedQuadrants.add(t);let l=e.querySelector(".quadrant__content");l&&(l.innerHTML=this._quadrantItemsHtml(t))}this._editingQuadrants.delete(t),e.removeAttribute("data-editing");let s=e.querySelector(".quadrant__face--front"),a=e.querySelector(".quadrant__face--back"),n=this.shadowRoot?.activeElement;a&&n&&a.contains(n)&&e.querySelector(".quadrant__edit-btn")?.focus(),s&&s.removeAttribute("inert"),a&&a.setAttribute("inert",""),this.dispatchEvent(new CustomEvent("empathy-map:update",{bubbles:!0,composed:!0,detail:{quadrant:t,items:this.__quadrants?.[t]||[]}}))}};A("empathy-map",Gt);var C=class extends HTMLElement{#e=[];#t;connectedCallback(){this.hasAttribute("data-upgraded")||this.setup()!==!1&&(this.setAttribute("data-upgraded",""),queueMicrotask(()=>{this.dispatchEvent(new CustomEvent(`${this.localName}:upgraded`,{bubbles:!0}))}))}disconnectedCallback(){for(let t of this.#e)t();this.#e=[],this.removeAttribute("data-upgraded"),this.teardown()}listen(t,e,r,s){t.addEventListener(e,r,s),this.#e.push(()=>t.removeEventListener(e,r,s))}setup(){}teardown(){}setState(t,e){this.#t||(this.#t=this.attachInternals());let r=this.#t.states;try{e?r.add(t):r.delete(t)}catch{let s=`--${t}`;e?r.add(s):r.delete(s)}}_adoptInternals(t){this.#t||(this.#t=t)}};function Lt({newItems:i,nodes:t,keyOf:e,renderItem:r,containerFor:s}){let a=[],n=[],o=[],l=new Set;for(let c of i)l.add(e(c));for(let[c,u]of[...t])l.has(c)||(u.remove(),t.delete(c),o.push(c));let d=new Map;for(let c of i){let u=e(c),m=t.get(u)||null,f=s(c,m);d.has(f)||d.set(f,[]),d.get(f)?.push({item:c,key:u,existing:m})}for(let[c,u]of d)for(let m=0;m<u.length;m++){let{item:f,key:h,existing:b}=u[m],g=b;g?(g.parentElement!==c||c.children[m]!==g)&&n.push(h):(g=r(f),t.set(h,g),a.push(h));let w=c.children[m];w!==g&&c.insertBefore(g,w||null)}return{added:a,moved:n,removed:o}}function Y(i){return String(i??"").replace(/[-_]/g," ").replace(/\b\w/g,t=>t.toUpperCase())}function ct(i){let t=document.createElement("div");return t.className=i,t.setAttribute("role","status"),t.setAttribute("aria-live","polite"),t.setAttribute("aria-atomic","true"),t}function bt(i,t){i&&(i.textContent="",requestAnimationFrame(()=>{i.textContent=t}))}function lt(i){if(!i)return"item";let t=a=>(a||"").replace(/\s+/g," ").trim(),e=t(i.querySelector(':scope > [slot="title"]')?.textContent)||t(i.querySelector(':scope > [slot="action"]')?.textContent);if(e)return Zt(e);let r=t(i.getAttribute("aria-label"));if(r)return Zt(r);let s=t(i.textContent);return s?Zt(s):i.getAttribute("story-id")||i.getAttribute("data-id")||"item"}function Zt(i){return i.length>60?`${i.slice(0,59).trimEnd()}\u2026`:i}function tt(i,t,e){let r=!!i.querySelector(':scope > [draggable="true"]'),s=i.querySelector(`:scope > .${t}`);if(!r&&!s){let a=document.createElement("p");a.className=t,a.textContent=e,i.appendChild(a)}else r&&s&&s.remove()}function Mt(i){return!!(i&&(i.persona||i.action||i.benefit||i.storyId))}function gt(i,t){let e=document.createElement("user-story"),r=[["storyId","story-id"],["personaId","persona-id"],["priority","priority"],["status","status"],["points","points"],["epic","epic"]];for(let[a,n]of r)i[a]!=null&&i[a]!==""&&e.setAttribute(n,String(i[a]));let s=i.detail||t;s&&e.setAttribute("detail",String(s));for(let a of["persona","action","benefit"])i[a]&&e.appendChild(te("span",a,i[a]));i.title&&e.appendChild(te("h3","title",i.title));for(let[a,n]of[["acceptanceCriteria","acceptance-criteria"],["tasks","tasks"],["notes","notes"]]){let o=i[a];if(o)if(Array.isArray(o)){let l=document.createElement("ul");l.slot=n;for(let d of o){let c=document.createElement("li");c.textContent=String(d),l.appendChild(c)}e.appendChild(l)}else e.appendChild(te("p",n,o))}return e}function te(i,t,e){let r=document.createElement(i);return r.slot=t,r.textContent=String(e),r}var ee=class i extends C{static QUADRANTS=["quick-wins","big-bets","fill-ins","money-pit"];static LABELS={"quick-wins":"Quick Wins","big-bets":"Big Bets","fill-ins":"Fill-Ins","money-pit":"Money Pit"};static DESCRIPTIONS={"quick-wins":"High impact \xB7 Low effort","big-bets":"High impact \xB7 High effort","fill-ins":"Low impact \xB7 Low effort","money-pit":"Low impact \xB7 High effort"};static#e=0;static get observedAttributes(){return["src","compact","title"]}#t={};#r=null;#a=null;#s="";#i=!1;#c=!1;#n=!1;#d=new z;#o=null;#l=new Map;#u=new Map;setup(){if(this.#s||(this.#s=`ie-${++i.#e}`),!this.#i&&(this.#i=!0,this.#y(),this.#o)){let e=this.#o;this.#o=null,this.items=e}this.#c||(this.#c=!0,this.listen(this,"drag-surface:transfer",this.#b));let t=this.getAttribute("src");if(t){t!==this.#d.url&&this.#w(t);return}this.#n||this.#v()}teardown(){this.#c=!1}#y(){let t=[...this.querySelectorAll(":scope > [data-quadrant], :scope > [draggable]")],e=document.createElement("div");e.className="ie-wrapper";let r=document.createElement("div");r.className="ie-y-label",r.setAttribute("aria-hidden","true"),r.textContent="Impact \u2191";let s=document.createElement("div");s.style.cssText="display:flex;flex-direction:column;flex:1;min-width:0;";let a=document.createElement("div");a.className="ie-grid",a.setAttribute("role","region"),a.setAttribute("aria-label","Impact-Effort prioritization matrix");let n=document.createElement("div");n.className="ie-x-label",n.setAttribute("aria-hidden","true"),n.textContent="Effort \u2192";for(let o of i.QUADRANTS){let l=document.createElement("section");l.className="ie-quadrant",l.dataset.quadrantZone=o,l.setAttribute("aria-label",`${i.LABELS[o]}: ${i.DESCRIPTIONS[o]}`);let d=document.createElement("header");d.className="ie-quadrant-label";let c=document.createElement("span");c.className="ie-quadrant-desc",c.textContent=i.DESCRIPTIONS[o],d.append(i.LABELS[o],document.createElement("br"),c);let u=document.createElement("drag-surface");u.setAttribute("group",this.#s),u.setAttribute("aria-label",i.LABELS[o]),u.setAttribute("data-layout","stack"),u.setAttribute("data-layout-gap","xs"),l.appendChild(d),l.appendChild(u),a.appendChild(l),this.#t[o]=u}t.forEach((o,l)=>{let d=o,c=this.#t[d.getAttribute("data-quadrant")||""]?d.getAttribute("data-quadrant"):"quick-wins";d.setAttribute("data-quadrant",c),d.hasAttribute("draggable")||d.setAttribute("draggable","true"),d.hasAttribute("data-id")||(d.dataset.id=`ie-item-${l}`),this.#t[c].appendChild(d),this.#l.set(d.dataset.id,d)}),this.#r=ct("ie-live-region"),this.#E(),s.appendChild(a),s.appendChild(n),e.appendChild(r),e.appendChild(s),this.append(e,this.#r)}#E(){let t=this.getAttribute("title");t?(this.#a||(this.#a=document.createElement("h3"),this.#a.className="ie-title",this.prepend(this.#a)),this.#a.textContent=t):this.#a&&(this.#a.remove(),this.#a=null)}#b=t=>{let{item:e,fromSurface:r,toSurface:s}=t.detail,a=this.#A(r),n=this.#A(s);!a||!n||(e.setAttribute("data-quadrant",n),bt(this.#r,`Moved ${lt(e)} to ${i.LABELS[n]}`),this.dispatchEvent(new CustomEvent("impact-effort:move",{bubbles:!0,detail:{itemId:e.dataset.id,from:a,to:n,item:e}})))};get items(){let t=[];for(let[e,r]of Object.entries(this.#t))for(let s of r.querySelectorAll(':scope > [draggable="true"]')){let a=s.getAttribute("data-id")||void 0,n=this.#h(s),o=n!==void 0?this.#u.get(n):void 0;o?t.push({...o,quadrant:e}):t.push({id:a,quadrant:e,label:lt(s)})}return t}set items(t){let e=Array.isArray(t)?t:[];if(!this.#i){this.#o=e;return}this.#x(e),this.dispatchEvent(new CustomEvent("impact-effort:items-changed",{detail:{items:e,source:"property"},bubbles:!0}))}static#g(t){let e=new Map,r=new Map;for(let s of t){if(s.id!=null){r.set(s,s.id);continue}let a=String(s.label??s.text??""),n=e.get(a)??0;e.set(a,n+1),r.set(s,n?`label:${a}#${n}`:`label:${a}`)}return r}#h(t){for(let[e,r]of this.#l)if(r===t)return e}#x(t){let e=i.#g(t);Lt({newItems:t,nodes:this.#l,keyOf:r=>e.get(r),renderItem:r=>this.#_(r),containerFor:r=>this.#t[r.quadrant]||this.#t["quick-wins"]}),this.#u.clear();for(let r of t){let s=e.get(r);this.#u.set(s,r),this.#l.get(s)?.setAttribute("data-quadrant",this.#t[r.quadrant]?r.quadrant:"quick-wins")}}#_(t){let e=this,r;if(typeof e.renderItem=="function"){let s=e.renderItem(t);s instanceof Element&&(r=s)}return!r&&Mt(t)&&(r=gt(t,"minimal")),r||(r=document.createElement("article"),r.className="ie-card",r.textContent=t.label??t.text??t.id??""),r.hasAttribute("draggable")||r.setAttribute("draggable","true"),t.id!=null&&!r.hasAttribute("data-id")&&r.setAttribute("data-id",String(t.id)),r}attributeChangedCallback(t,e,r){e===r||!this.#i||(t==="src"&&r&&r!==this.#d.url&&this.#w(r),t==="src"&&!r&&this.#d.cancel(),t==="title"&&this.#E())}async#w(t){try{let e=await this.#d.fetchJson(t);if(!e)return;let{data:r,isCurrent:s}=e;if(!Array.isArray(r))return;let a=r.map((o,l)=>({...o,id:o.id??o.storyId??`ie-item-${l}`})),n=D(this,()=>this.#x(a),"ie-vt");if(n&&await n.updateCallbackDone,!s())return;this.dispatchEvent(new CustomEvent("impact-effort:items-changed",{detail:{items:this.items,source:"src"},bubbles:!0})),this.#n||this.#v()}catch(e){console.warn(`[impact-effort] Failed to load src="${t}":`,e)}}#A(t){for(let[e,r]of Object.entries(this.#t))if(r===t)return e;return null}#v(){this.#n=!0;let t={};for(let e of i.QUADRANTS){let r=this.#t[e];t[e]=r?r.querySelectorAll(':scope > [draggable="true"]').length:0}this.dispatchEvent(new CustomEvent("impact-effort:ready",{bubbles:!0,detail:{quadrantCounts:t}}))}};A("impact-effort",ee);var re=class i extends C{static#e=0;static VISUAL_ORDER=[1,0,2,3];setup(){if(this.#b||(this.#b=`qg-${++i.#e}`),this.#g){this.#t();return}this.#g=!0;let t=this.getAttribute("x-label")||"",e=this.getAttribute("y-label")||"",r=this.getAttribute("x-low")||"Low",s=this.getAttribute("x-high")||"High",a=this.getAttribute("y-low")||"Low",n=this.getAttribute("y-high")||"High",o=[this.getAttribute("q1-label")||"Q1",this.getAttribute("q2-label")||"Q2",this.getAttribute("q3-label")||"Q3",this.getAttribute("q4-label")||"Q4"],l=this.hasAttribute("draggable"),d=[...this.querySelectorAll(":scope > [data-quadrant], :scope > [data-x][data-y]")],c=document.createElement("section");c.className="qg-wrapper",c.setAttribute("role","region"),c.setAttribute("aria-label",`${e} \xD7 ${t} quadrant grid`);let u=document.createElement("header");u.className="qg-y-label",u.setAttribute("aria-hidden","true"),u.textContent=`\u2191 ${e}`;let m=document.createElement("aside");m.className="qg-y-scale",m.setAttribute("aria-hidden","true"),m.append(i.#r(n),i.#r(a));let f=document.createElement("div");f.className="qg-grid";let h=document.createElement("aside");h.className="qg-x-scale",h.setAttribute("aria-hidden","true"),h.append(i.#r(r),i.#r(s));let b=document.createElement("footer");b.className="qg-x-label",b.setAttribute("aria-hidden","true"),b.textContent=`${t} \u2192`;for(let w of i.VISUAL_ORDER){let v=document.createElement("section");v.className="qg-quadrant",v.dataset.quadrantZone=String(w),v.setAttribute("aria-label",o[w]);let y=document.createElement("header");if(y.className="qg-quadrant-label",y.textContent=o[w],v.appendChild(y),l){let x=document.createElement("drag-surface");x.setAttribute("group",this.#b),x.setAttribute("aria-label",o[w]),x.setAttribute("data-layout","stack"),x.setAttribute("data-layout-gap","xs"),v.appendChild(x),this.#_[w]=x}else{let x=document.createElement("ul");x.className="qg-items",v.appendChild(x),this.#w[w]=x}f.appendChild(v),this.#A[w]=v}d.forEach((w,v)=>{let y=w,x=this.#l(y),k=l?this.#_[x]:this.#w[x];if(l&&(y.hasAttribute("draggable")||y.setAttribute("draggable","true")),y.hasAttribute("data-id")||(y.dataset.id=`qg-item-${v}`),y.hasAttribute("data-x")&&y.hasAttribute("data-y")){let _=parseFloat(y.getAttribute("data-x")??""),$=parseFloat(y.getAttribute("data-y")??"");if(Number.isFinite(_)&&Number.isFinite($)){let N=x===0||x===3?(_-.5)*2:_*2,F=x===0||x===1?($-.5)*2:$*2;if(y.style.setProperty("--qg-local-x",N.toFixed(4)),y.style.setProperty("--qg-local-y",F.toFixed(4)),y.classList.add("qg-pinned"),!y.style.getPropertyValue("--qg-pin-hue")){let L=y.dataset.id||(y.textContent||"").trim();y.style.setProperty("--qg-pin-hue",`${i.#n(L)}deg`)}}}if(l)k.appendChild(y);else{let _=document.createElement("li");y.classList.contains("qg-pinned")&&(_.className="qg-pin-item"),_.appendChild(y),k.appendChild(_)}});let g=document.createElement("div");g.className="qg-live-region visually-hidden",g.setAttribute("role","status"),g.setAttribute("aria-live","polite"),c.appendChild(u),c.appendChild(m),c.appendChild(f),c.appendChild(h),c.appendChild(b),this.appendChild(c),this.appendChild(g),this.#v=g,this.#m=o,this.#x=l,this.#t()}#t(){this.#h||(this.#h=!0,this.#x&&this.listen(this,"drag-surface:transfer",this.#d),this.#a())}static#r(t){let e=document.createElement("span");return e.textContent=t,e}#a(){if(typeof ResizeObserver>"u")return;let t=e=>{let r=e.offsetWidth,s=e.offsetHeight;r>0&&e.style.setProperty("--qg-pin-half-w",`${r/2}px`),s>0&&e.style.setProperty("--qg-pin-half-h",`${s/2}px`)};this.#p=new ResizeObserver(e=>{for(let r of e)t(r.target);this.#s()});for(let e of this.querySelectorAll(".qg-pinned"))this.#p.observe(e);this.#s()}#s(){this.#f||(this.#f=requestAnimationFrame(()=>{this.#f=0,this.#i()}))}#i(){for(let e of this.querySelectorAll(".qg-pinned")){let r=e;r.classList.remove("qg-clustered"),r.style.removeProperty("--qg-cluster-i"),r.style.removeProperty("--qg-cluster-n"),delete r.dataset.cluster,r.dataset.qgTabbed!==void 0&&(r.removeAttribute("tabindex"),delete r.dataset.qgTabbed),r.dataset.qgRole!==void 0&&(r.removeAttribute("role"),delete r.dataset.qgRole)}let t=0;for(let e=0;e<4;e++){let r=this.#A[e];if(!r)continue;let s=[...r.querySelectorAll(".qg-pinned")];if(s.length<2)continue;let a=s.map(c=>c.getBoundingClientRect()),n=Array.from({length:s.length},(c,u)=>u),o=c=>n[c]===c?c:n[c]=o(n[c]),l=(c,u)=>{let m=o(c),f=o(u);m!==f&&(n[m]=f)};for(let c=0;c<s.length;c++)for(let u=c+1;u<s.length;u++)i.#c(a[c],a[u])&&l(c,u);let d=new Map;for(let c=0;c<s.length;c++){let u=o(c);d.has(u)||d.set(u,[]),d.get(u)?.push(c)}for(let c of d.values()){if(c.length<2)continue;let u=`c${++t}`;c.forEach((m,f)=>{let h=s[m];h.classList.add("qg-clustered"),h.dataset.cluster=u,h.style.setProperty("--qg-cluster-i",String(f)),h.style.setProperty("--qg-cluster-n",String(c.length)),!h.hasAttribute("tabindex")&&!h.matches("a, button, [contenteditable]")&&(h.setAttribute("tabindex","0"),h.dataset.qgTabbed="",h.hasAttribute("role")||(h.setAttribute("role","group"),h.dataset.qgRole=""))})}}}teardown(){this.#h=!1,this.#p?.disconnect(),this.#p=null,this.#f&&cancelAnimationFrame(this.#f),this.#f=0}static#c(t,e){return!(t.right<=e.left||e.right<=t.left||t.bottom<=e.top||e.bottom<=t.top)}static#n(t){let e=5381;for(let r=0;r<t.length;r++)e=(e<<5)+e+t.charCodeAt(r)|0;return(e%360+360)%360}#d=t=>{let{item:e,fromSurface:r,toSurface:s}=t.detail,a=this.#u(r),n=this.#u(s);a==null||n==null||(e.setAttribute("data-quadrant",String(n)),e.classList.contains("qg-pinned")&&this.#o(e),this.#s(),this.#E(`Moved ${this.#y(e)} to ${this.#m[n]}`),this.dispatchEvent(new CustomEvent("quadrant-grid:move",{bubbles:!0,detail:{item:e,itemId:e.dataset.id,from:a,to:n}})))};#o(t){this.#p?.unobserve(t),t.removeAttribute("data-x"),t.removeAttribute("data-y"),t.classList.remove("qg-pinned","qg-clustered");for(let e of["--qg-local-x","--qg-local-y","--qg-pin-half-w","--qg-pin-half-h","--qg-cluster-i","--qg-cluster-n"])t.style.removeProperty(e);delete t.dataset.cluster,t.dataset.qgTabbed!==void 0&&(t.removeAttribute("tabindex"),delete t.dataset.qgTabbed),t.dataset.qgRole!==void 0&&(t.removeAttribute("role"),delete t.dataset.qgRole)}#l(t){let e=parseInt(t.getAttribute("data-quadrant"),10);if(e>=0&&e<=3)return e;if(t.hasAttribute("data-x")&&t.hasAttribute("data-y")){let r=parseFloat(t.getAttribute("data-x")),s=parseFloat(t.getAttribute("data-y"));return i.quadrantFor(r,s)}return 0}static quadrantFor(t,e){let r=t>=.5,s=e>=.5;return s&&r?0:s&&!r?1:!s&&!r?2:3}#u(t){for(let e=0;e<4;e++)if(this.#_[e]===t)return e;return null}#y(t){return(t.textContent||"").trim().split(`
1783
+ `)[0]||"item"}#E(t){this.#v&&(this.#v.textContent=t)}#b="";#g=!1;#h=!1;#x=!1;#_={};#w={};#A={};#v=null;#m=[];#p=null;#f=0};A("quadrant-grid",re);var ae=5,je=(ae+1)/2;function zt(i){let t=parseInt(String(i??""),10);return!Number.isFinite(t)||t<1?0:Math.min(ae,t)}var Fe=i=>(i-1)/(ae-1);function Rr(i,t){let e=i>je;return t>je?e?0:1:e?3:2}var se=class i extends C{setup(){let t=this.querySelector(":scope > template"),e=t?i.#t(t):[];if(this.hasAttribute("src")){this.#e(this.getAttribute("src"));return}this.#r(e)}async#e(t){try{let r=await(await fetch(t)).json();this.#r(Array.isArray(r)?r:[])}catch(e){console.warn("risk-register: failed to load src",t,e),this.#r([])}}static#t(t){let e=[],r=t.content.querySelectorAll("tr");for(let s of r){let a=[...s.children],n=a[0]?.textContent?.trim()||"",o=s.getAttribute("data-id")||n.toLowerCase().replace(/\s+/g,"-")||`risk-${e.length}`;e.push({id:o,title:n,likelihood:zt(a[1]?.textContent),impact:zt(a[2]?.textContent),owner:a[3]?.textContent?.trim()||"",mitigation:a[4]?.textContent?.trim()||""})}return e}#r(t){this.#i=t.map(s=>({...s,likelihood:zt(s?.likelihood),impact:zt(s?.impact)})),t=this.#i,[...this.children].forEach(s=>{s.tagName!=="TEMPLATE"&&s.remove()});let e=this.getAttribute("label");if(e){let s=document.createElement("header");s.className="rr-label",s.textContent=e,this.appendChild(s)}let r=document.createElement("div");r.className="rr-layout",r.appendChild(this.#a(t)),r.appendChild(this.#s(t)),this.appendChild(r),queueMicrotask(()=>{this.dispatchEvent(new CustomEvent("risk-register:ready",{bubbles:!0,detail:{count:t.length}}))})}#a(t){let e=document.createElement("data-table"),r=document.createElement("table");return r.innerHTML=`
1756
1784
  <thead>
1757
1785
  <tr>
1758
1786
  <th data-sort="string">Title</th>
1759
1787
  <th data-sort="number">Likelihood</th>
1760
1788
  <th data-sort="number">Impact</th>
1761
- <th data-sort="number" data-rollup="product" data-heatmap="low-good">Severity</th>
1789
+ <th data-sort="number" data-severity data-heatmap="low-good">Severity</th>
1762
1790
  <th data-sort="string">Owner</th>
1763
1791
  <th data-sort="string">Mitigation</th>
1764
1792
  </tr>
1765
1793
  </thead>
1766
1794
  <tbody>
1767
- ${t.map(r=>`
1768
- <tr data-id="${n.#n(r.id)}">
1769
- <td>${n.#n(r.title)}</td>
1770
- <td>${r.likelihood||""}</td>
1771
- <td>${r.impact||""}</td>
1772
- <td></td>
1773
- <td>${n.#n(r.owner)}</td>
1774
- <td>${n.#n(r.mitigation)}</td>
1775
- </tr>
1776
- `).join("")}
1795
+ ${t.map(s=>{let a=s.likelihood&&s.impact?s.likelihood*s.impact:null;return`
1796
+ <tr data-id="${p(s.id)}">
1797
+ <td>${p(s.title)}</td>
1798
+ <td>${s.likelihood||""}</td>
1799
+ <td>${s.impact||""}</td>
1800
+ <td${a===null?"":` data-sort-value="${a}"`}>${a??""}</td>
1801
+ <td>${p(s.owner)}</td>
1802
+ <td>${p(s.mitigation)}</td>
1803
+ </tr>`}).join("")}
1777
1804
  </tbody>
1778
- `,e.appendChild(s),e}#r(t){let e=document.createElement("quadrant-grid");e.setAttribute("x-label","Likelihood"),e.setAttribute("y-label","Impact"),e.setAttribute("x-low","Rare"),e.setAttribute("x-high","Likely"),e.setAttribute("y-low","Minor"),e.setAttribute("y-high","Severe"),e.setAttribute("q1-label","Avoid"),e.setAttribute("q2-label","Plan"),e.setAttribute("q3-label","Accept"),e.setAttribute("q4-label","Mitigate");for(let s of t){if(!s.likelihood||!s.impact)continue;let r=document.createElement("span"),a=Math.min(1,Math.max(0,s.likelihood/ne)),i=Math.min(1,Math.max(0,s.impact/ne));r.setAttribute("data-x",a.toFixed(3)),r.setAttribute("data-y",i.toFixed(3)),r.setAttribute("data-id",s.id),r.setAttribute("title",`${s.title} \u2014 likelihood ${s.likelihood}, impact ${s.impact}`),r.textContent=s.title,e.appendChild(r)}return e}static#n(t){return String(t??"").replace(/[&<>"']/g,e=>({"&":"&amp;","<":"&lt;",">":"&gt;",'"':"&quot;","'":"&#39;"})[e])}#a=[];get rows(){return[...this.#a]}set rows(t){this.#s(Array.isArray(t)?t:[])}};w("risk-register",Ct);var Et=class n extends C{setup(){let t=this.getAttribute("rows"),e=this.getAttribute("cols"),s=this.getAttribute("link-attr");return!t||!e||!s?(console.warn("traceability-matrix: requires rows, cols, and link-attr attributes"),!1):(queueMicrotask(()=>this.#e(t,e,s)),!0)}#e(t,e,s){let r=[...document.querySelectorAll(t)].filter(g=>g!==this&&!this.contains(g)),a=[...document.querySelectorAll(e)].filter(g=>g!==this&&!this.contains(g));if(!r.length||!a.length){this.#i();return}let i=this.getAttribute("row-label")||"",o=this.getAttribute("cell-mark")||"\u2713",c=this.hasAttribute("flag-orphans"),d=[],l=new WeakMap,u=new WeakMap;for(let g of r){let y=n.#r(g.getAttribute(s));for(let A of y){let S=a.find($=>$.id===A);S&&(d.push({rowEl:g,colEl:S}),l.set(g,(l.get(g)||0)+1),u.set(S,(u.get(S)||0)+1))}}let p=document.createElement("data-table"),h=document.createElement("table"),f=document.createElement("thead"),b=document.createElement("tr"),v=document.createElement("th");v.setAttribute("data-sort","string"),v.textContent=i,b.appendChild(v);for(let g of a){let y=document.createElement("th");y.setAttribute("data-sort","number"),y.textContent=n.#n(g),y.dataset.colId=g.id||"",c&&!u.get(g)&&(y.dataset.orphan=""),b.appendChild(y)}f.appendChild(b),h.appendChild(f);let x=document.createElement("tbody");for(let g of r){let y=document.createElement("tr");y.dataset.rowId=g.id||"",c&&!l.get(g)&&(y.dataset.orphan="");let A=document.createElement("th");A.scope="row",A.textContent=n.#n(g),y.appendChild(A);let S=n.#r(g.getAttribute(s));for(let $ of a){let T=document.createElement("td"),z=S.includes($.id);T.setAttribute("data-sort-value",z?"1":"0"),z?(T.dataset.linked="",T.textContent=o,T.setAttribute("aria-label","linked")):T.setAttribute("aria-label","not linked"),T.dataset.colId=$.id||"",y.appendChild(T)}x.appendChild(y)}h.appendChild(x),p.appendChild(h),[...this.children].forEach(g=>{g.tagName!=="TEMPLATE"&&g.remove()});let _=this.getAttribute("label");if(_){let g=document.createElement("header");g.className="tm-label",g.textContent=_,this.appendChild(g)}this.appendChild(p),this.#a=p,this.#o=new Map(r.map(g=>[g.id,g])),this.#c=new Map(a.map(g=>[g.id,g])),this.listen(p,"click",this.#t),queueMicrotask(()=>{this.dispatchEvent(new CustomEvent("traceability-matrix:ready",{bubbles:!0,detail:{rowCount:r.length,colCount:a.length,linkCount:d.length}}))})}#t=t=>{let e=t.target.closest('td, th[scope="row"]');if(!e)return;let s=e.closest("tr");if(!s)return;let r=s.dataset.rowId,a=e.dataset.colId,i=r?this.#o.get(r):null,o=a?this.#c.get(a):null,c=e.hasAttribute("data-state-highlighted");if(this.#s(),c){this.dispatchEvent(new CustomEvent("traceability-matrix:highlight",{bubbles:!0,detail:{rowEl:i,colEl:o,on:!1}}));return}e.setAttribute("data-state-highlighted",""),i&&i.setAttribute("data-state-highlighted",""),o&&o!==i&&o.setAttribute("data-state-highlighted",""),s.setAttribute("data-state-highlighted",""),this.dispatchEvent(new CustomEvent("traceability-matrix:highlight",{bubbles:!0,detail:{rowEl:i,colEl:o,on:!0}}))};#s(){this.#a&&(this.#a.querySelectorAll("[data-state-highlighted]").forEach(t=>t.removeAttribute("data-state-highlighted")),document.querySelectorAll("[data-state-highlighted]").forEach(t=>{(this.#o.has(t.id)||this.#c.has(t.id))&&t.removeAttribute("data-state-highlighted")}))}#i(){[...this.children].forEach(e=>{e.tagName!=="TEMPLATE"&&e.remove()});let t=document.createElement("p");t.className="tm-empty",t.textContent="No matching elements found for this matrix.",this.appendChild(t)}static#r(t){return t?t.split(",").map(e=>e.trim()).filter(Boolean):[]}static#n(t){return t.getAttribute("data-matrix-label")||t.id||(t.textContent||"").trim().split(`
1779
- `)[0].slice(0,60)||"(unnamed)"}#a=null;#o=new Map;#c=new Map};w("traceability-matrix",Et);var Ke=864e5,St=class n extends C{setup(){let t=this.getAttribute("start"),e=this.getAttribute("end"),s=parseFloat(this.getAttribute("total")||"");if(!t||!e||!Number.isFinite(s))return console.warn("burndown-chart: requires start, end, and total attributes"),!1;let r=n.#s(t),a=n.#s(e);if(!r||!a||a<r)return console.warn("burndown-chart: start/end dates invalid",t,e),!1;let i=(this.getAttribute("weekends")||"include")!=="exclude",o=this.getAttribute("unit")||"points",c=this.getAttribute("label")||"",d=this.querySelector(":scope > template"),l=d?n.#t(d):[],u=l.filter(b=>b.delta!==0),p=n.#r(r,a),h=n.#n(p,s,i),f=n.#a(p,l);return this.#e({label:c,unit:o,dayLabels:p,actual:f,ideal:h,scopeChanges:u}),queueMicrotask(()=>{this.dispatchEvent(new CustomEvent("burndown-chart:ready",{bubbles:!0,detail:{dayCount:p.length,total:s,scopeChanges:u.length}}))}),!0}#e({label:t,unit:e,dayLabels:s,actual:r,ideal:a,scopeChanges:i}){if([...this.children].forEach(u=>{u.tagName!=="TEMPLATE"&&u.remove()}),t){let u=document.createElement("header");u.className="bdc-label",u.textContent=t,this.appendChild(u)}let o=document.createElement("chart-wc");o.setAttribute("data-type","line"),o.setAttribute("data-legend",""),o.setAttribute("data-tooltip",""),o.setAttribute("data-label-x","Day"),o.setAttribute("data-label-y",e);let c={},d={};s.forEach((u,p)=>{c[u]=a[p],r[p]!==null&&(d[u]=r[p])});let l=[{name:"Actual",values:d},{name:"Ideal",values:c}];if(o.setAttribute("data-values",JSON.stringify(l)),this.appendChild(o),i.length){let u=document.createElement("aside");u.className="bdc-scope-changes";let p=document.createElement("h4");p.textContent="Scope changes",u.appendChild(p);let h=document.createElement("ul");for(let f of i){let b=document.createElement("li"),v=f.delta>0?"+":"";b.innerHTML=`<time datetime="${f.date}">${f.date}</time>: <strong>${v}${f.delta} ${e}</strong>`,h.appendChild(b)}u.appendChild(h),this.appendChild(u)}}static#t(t){let e=[],s=t.content.querySelectorAll("tr");for(let r of s){let a=[...r.children],i=a[0]?.textContent?.trim(),o=parseFloat(a[1]?.textContent??""),c=parseFloat(a[2]?.textContent??"0")||0;!i||!Number.isFinite(o)||e.push({date:i,remaining:o,delta:c})}return e}static#s(t){let e=String(t).match(/^(\d{4})-(\d{2})-(\d{2})/);return e?new Date(Number(e[1]),Number(e[2])-1,Number(e[3])):null}static#i(t){let e=String(t.getMonth()+1).padStart(2,"0"),s=String(t.getDate()).padStart(2,"0");return`${t.getFullYear()}-${e}-${s}`}static#r(t,e){let s=[];for(let r=t.getTime();r<=e.getTime();r+=Ke)s.push(n.#i(new Date(r)));return s}static#n(t,e,s){let r=l=>{let u=n.#s(l);if(!u)return!1;let p=u.getDay();return p===0||p===6},a=t.map((l,u)=>({d:l,i:u,weekend:r(l)})).filter(l=>s||!l.weekend),i=a.length>1?e/(a.length-1):0,o=new Array(t.length).fill(null),c=e,d=0;for(let l=0;l<t.length;l++){let u=r(t[l]);s||!u?(o[l]=Math.max(0,e-i*d),d++,c=o[l]):o[l]=c}return o}static#a(t,e){let s=new Map(e.map(r=>[r.date,r.remaining]));return t.map(r=>s.has(r)?s.get(r):null)}};w("burndown-chart",St);var $t=class n extends C{static get observedAttributes(){return["start","end","view","editable","today-marker"]}setup(){if(!this.#e())return!1;let t=[...this.querySelectorAll(":scope > section[data-lane]")];return t.length?(this.#x=t,this.#t(),!0):(console.warn("product-roadmap: no <section data-lane> children found"),!1)}#e(){let t=this.getAttribute("start"),e=this.getAttribute("end");if(!t||!e)return console.warn("product-roadmap: start and end attributes required"),!1;let s=n.#b(t,"start"),r=n.#b(e,"end");return!s||!r||r<=s?(console.warn("product-roadmap: invalid start/end",t,e),!1):(this.#d=s,this.#h=r,this.#y=r.getTime()-s.getTime(),this.#f=this.getAttribute("view")==="month"?"month":"quarter",this.#w=this.hasAttribute("editable"),!0)}attributeChangedCallback(t,e,s){e!==s&&(!this.isConnected||!this.#x.length||this.#e()&&this.#t())}#t(){[...this.children].forEach(r=>{this.#x.includes(r)||r.remove()}),this.#x.forEach(r=>{r.hidden=!0});let t=document.createElement("div");t.className="rm-wrapper";let e=this.#s();t.appendChild(e);let s=document.createElement("div");s.className="rm-lanes";for(let r of this.#x){let a=r.getAttribute("data-lane")||"",i=document.createElement("section");i.className="rm-lane",i.dataset.lane=a;let o=document.createElement("header");o.className="rm-lane-label",o.textContent=a,i.appendChild(o);let c=document.createElement("div");c.className="rm-track",c.dataset.lane=a;let d=[...r.querySelectorAll(":scope > article[data-start][data-end]")];for(let l of d){let u=this.#i(l,a);u&&c.appendChild(u)}this.#w&&(c.addEventListener("dragover",this.#c),c.addEventListener("drop",this.#p)),i.appendChild(c),s.appendChild(i)}if(t.appendChild(s),this.hasAttribute("today-marker")&&this.#d&&this.#h){let r=new Date;if(r>=this.#d&&r<=this.#h){let a=document.createElement("div");a.className="rm-today",a.style.setProperty("--rm-x",this.#l(r).toFixed(4)),a.title=`Today: ${n.#v(r)}`,s.appendChild(a)}}this.appendChild(t),this.#_=t}#s(){let t=document.createElement("header");t.className="rm-axis";let e=this.#g();for(let s of e){let r=document.createElement("div");r.className="rm-tick",r.style.setProperty("--rm-x",s.startFraction.toFixed(4)),r.style.setProperty("--rm-w",(s.endFraction-s.startFraction).toFixed(4)),r.textContent=s.label,t.appendChild(r)}return t}#i(t,e){let s=n.#b(t.getAttribute("data-start"),"start"),r=n.#b(t.getAttribute("data-end"),"end");if(!s||!r||!this.#d||!this.#h)return null;let a=s<this.#d?this.#d:s,i=r>this.#h?this.#h:r;if(a>=i)return null;let o=this.#l(a),c=this.#l(i)-o,d=document.createElement("article");d.className="rm-bar",d.style.setProperty("--rm-x",o.toFixed(4)),d.style.setProperty("--rm-w",c.toFixed(4)),d.dataset.lane=e,d.dataset.start=n.#v(s),d.dataset.end=n.#v(r),t.dataset.status&&(d.dataset.status=t.dataset.status),t.id&&(d.dataset.sourceId=t.id),this.#w&&d.setAttribute("draggable","true");let l=t.querySelector("h1, h2, h3, h4, h5, h6"),u=document.createElement("span");if(u.className="rm-bar-title",u.textContent=l?l.textContent.trim():(t.textContent||"").trim().split(`
1780
- `)[0],d.appendChild(u),d.setAttribute("aria-label",`${u.textContent} \u2014 ${d.dataset.start} to ${d.dataset.end} in ${e}`),d.addEventListener("click",p=>{this.#A||this.dispatchEvent(new CustomEvent("product-roadmap:select",{bubbles:!0,detail:{initiative:t,lane:e,start:d.dataset.start,end:d.dataset.end,status:d.dataset.status||null}}))}),this.#w){let p=document.createElement("span");p.className="rm-bar-handle",p.setAttribute("aria-label","Resize end date"),d.appendChild(p),p.addEventListener("pointerdown",h=>this.#n(h,d,t)),d.addEventListener("pointerdown",h=>{h.target!==p&&this.#r(h,d,t)}),d.addEventListener("dragstart",h=>{h.dataTransfer&&(h.dataTransfer.effectAllowed="move",h.dataTransfer.setData("text/plain",t.id||d.dataset.sourceId||"")),this.#k=t,this.#C=e}),d.addEventListener("dragend",()=>{this.#k=null,this.#C=null})}return d}#r(t,e,s){if(t.button!==0)return;t.preventDefault();let r=e.parentElement.getBoundingClientRect(),a=t.clientX,i=parseFloat(e.style.getPropertyValue("--rm-x"))||0,o=parseFloat(e.style.getPropertyValue("--rm-w"))||0;this.#A={kind:"move",bar:e,initiative:s,trackRect:r,startX:a,startFraction:i,widthFraction:o},e.setPointerCapture(t.pointerId),e.addEventListener("pointermove",this.#a),e.addEventListener("pointerup",this.#o),e.addEventListener("pointercancel",this.#o)}#n(t,e,s){if(t.button!==0)return;t.preventDefault(),t.stopPropagation();let r=e.parentElement.getBoundingClientRect(),a=t.clientX,i=parseFloat(e.style.getPropertyValue("--rm-x"))||0,o=parseFloat(e.style.getPropertyValue("--rm-w"))||0;this.#A={kind:"resize",bar:e,initiative:s,trackRect:r,startX:a,startFraction:i,widthFraction:o},e.setPointerCapture(t.pointerId),e.addEventListener("pointermove",this.#a),e.addEventListener("pointerup",this.#o),e.addEventListener("pointercancel",this.#o)}#a=t=>{if(!this.#A)return;let{kind:e,bar:s,trackRect:r,startX:a,startFraction:i,widthFraction:o}=this.#A,c=(t.clientX-a)/r.width;if(e==="move"){let d=Math.max(0,Math.min(1-o,i+c));s.style.setProperty("--rm-x",d.toFixed(4))}else if(e==="resize"){let d=Math.max(.02,Math.min(1-i,o+c));s.style.setProperty("--rm-w",d.toFixed(4))}};#o=t=>{if(!this.#A)return;let{kind:e,bar:s,initiative:r}=this.#A;s.releasePointerCapture(t.pointerId),s.removeEventListener("pointermove",this.#a),s.removeEventListener("pointerup",this.#o),s.removeEventListener("pointercancel",this.#o);let a=parseFloat(s.style.getPropertyValue("--rm-x"))||0,i=parseFloat(s.style.getPropertyValue("--rm-w"))||0,o=this.#m(this.#u(a)),c=this.#m(this.#u(a+i));s.dataset.start=n.#v(o),s.dataset.end=n.#v(c);let d=this.#l(o),l=this.#l(c)-d;s.style.setProperty("--rm-x",d.toFixed(4)),s.style.setProperty("--rm-w",l.toFixed(4)),r&&(r.setAttribute("data-start",s.dataset.start??""),r.setAttribute("data-end",s.dataset.end??"")),this.dispatchEvent(new CustomEvent(e==="move"?"product-roadmap:reschedule":"product-roadmap:resize",{bubbles:!0,detail:{initiative:r,lane:s.dataset.lane,start:s.dataset.start,end:s.dataset.end}})),setTimeout(()=>{this.#A=null},0)};#c=t=>{this.#k&&(t.preventDefault(),t.dataTransfer.dropEffect="move")};#p=t=>{if(!this.#k)return;t.preventDefault();let e=t.currentTarget.dataset.lane,s=this.#k,r=this.#C;if(e===r)return;let a=this.#x.find(i=>i.getAttribute("data-lane")===e);a&&a.appendChild(s),this.dispatchEvent(new CustomEvent("product-roadmap:move",{bubbles:!0,detail:{initiative:s,fromLane:r,toLane:e,start:s.getAttribute("data-start"),end:s.getAttribute("data-end")}})),this.#t()};#l(t){if(!this.#d)return 0;let e=t.getTime()-this.#d.getTime();return Math.max(0,Math.min(1,e/this.#y))}#u(t){let e=this.#d??new Date;return new Date(e.getTime()+t*this.#y)}#m(t){if(this.#f==="month")return new Date(t.getFullYear(),t.getMonth(),1);let e=t.getMonth(),s=Math.floor(e/3)*3;return new Date(t.getFullYear(),s,1)}#g(){let t=[],e=this.#d,s=this.#h;if(!e||!s)return t;if(this.#f==="quarter"){let r=this.#m(e);for(;r<s;){let a=new Date(r.getFullYear(),r.getMonth()+3,1),i=this.#l(r<e?e:r),o=this.#l(a>s?s:a),c=Math.floor(r.getMonth()/3)+1;t.push({startFraction:i,endFraction:o,label:`Q${c} ${r.getFullYear()}`}),r=a}}else{let r=new Date(e.getFullYear(),e.getMonth(),1);for(;r<s;){let a=new Date(r.getFullYear(),r.getMonth()+1,1),i=this.#l(r<e?e:r),o=this.#l(a>s?s:a),c=r.toLocaleString(void 0,{month:"short"});t.push({startFraction:i,endFraction:o,label:`${c} ${r.getFullYear()}`}),r=a}}return t}static#b(t,e){if(!t)return null;let s=String(t).match(/^(\d{4})-Q([1-4])$/i);if(s){let i=Number(s[1]),c=(Number(s[2])-1)*3;return e==="end"?new Date(i,c+3,0):new Date(i,c,1)}let r=String(t).match(/^(\d{4})-(\d{2})-(\d{2})/);if(r)return new Date(Number(r[1]),Number(r[2])-1,Number(r[3]));let a=new Date(t);return isNaN(a.getTime())?null:a}static#v(t){let e=String(t.getMonth()+1).padStart(2,"0"),s=String(t.getDate()).padStart(2,"0");return`${t.getFullYear()}-${e}-${s}`}#d=null;#h=null;#y=0;#f="quarter";#w=!1;#x=[];#_=null;#A=null;#k=null;#C=null};w("product-roadmap",$t);function oe(n){let t=n;return class extends t{static keyOf(e){return e.id}#e=[];#t=new Map;get items(){return this.#e}set items(e){let s=e||[],r=st({newItems:s,nodes:this.#t,keyOf:this.constructor.keyOf,renderItem:a=>this._renderItem(a),containerFor:(a,i)=>this._containerFor(a,i)});this.#e=s,this._postRender({...r,items:s}),this._emit("items-changed",{items:s},"api")}_renderItem(e){throw new Error(`${this.constructor.name}: must implement _renderItem(item)`)}_containerFor(e,s){return this}_postRender(e){}_emit(e,s,r="api"){this.dispatchEvent(new CustomEvent(`${this.localName}:${e}`,{detail:{...s,source:r},bubbles:!0}))}_nodeFor(e){return this.#t.get(e)||null}_seedCollection(e,s){this.#e=e,this.#t.clear();for(let[r,a]of s)this.#t.set(r,a)}_setItemsSilently(e){this.#e=e}}}var qt=class n extends oe(C){static get observedAttributes(){return["src","compact","title"]}static keyOf(t){return t.id??t.storyId}static#e=0;#t=null;#s={};#i={};#r=null;#n="";#a=[];#o=null;setup(){this.#n=`kb-${++n.#e}`;let t=[...this.querySelectorAll(":scope > section[data-column]")];this.#a=t.map(a=>{let i=a.getAttribute("data-column")||"",c=a.getAttribute("data-column-label")||""||this.#h(i),d=a.getAttribute("data-wip"),l=d?parseInt(d,10):null,u=a.getAttribute("data-column-color")||null,p=[...a.children];return{id:i,label:c,wip:l,color:u,children:p}});for(let a of t)a.remove();this.#t=document.createElement("div"),this.#t.className="kb-columns",this.#t.setAttribute("role","region"),this.#t.setAttribute("aria-label","Kanban board");let e=0;for(let a of this.#a){let i=document.createElement("section");i.className="kb-column",i.setAttribute("data-column-id",a.id),a.color&&i.setAttribute("data-column-tint",a.color);let o=document.createElement("header");o.className="kb-column-header";let c=document.createElement("h3");c.textContent=a.label;let d=document.createElement("output");if(d.className="kb-count",d.textContent=String(a.children.length),c.appendChild(d),a.wip!==null&&!isNaN(a.wip)){let u=document.createElement("span");u.className="kb-wip",u.textContent=`/ ${a.wip}`,u.setAttribute("aria-label",`WIP limit ${a.wip}`),c.appendChild(u)}o.appendChild(c),i.appendChild(o);let l=document.createElement("drag-surface");if(l.setAttribute("group",this.#n),l.setAttribute("aria-label",`${a.label} items`),l.setAttribute("data-layout","stack"),l.setAttribute("data-layout-gap","xs"),a.children.length>0){for(let u of a.children)u.hasAttribute("draggable")||u.setAttribute("draggable","true"),u.hasAttribute("data-id")||(u.dataset.id=`kb-item-${e}`),l.appendChild(u);e+=a.children.length}else{let u=document.createElement("p");u.className="kb-empty",u.textContent="No items",l.appendChild(u)}i.appendChild(l),this.#t.appendChild(i),this.#s[a.id]=l,this.#i[a.id]=i,a.wip!==null&&a.children.length>a.wip&&i.setAttribute("data-wip-exceeded","")}let s=this.getAttribute("title");if(s){let a=document.createElement("h2");a.className="kb-title",a.textContent=s,this.appendChild(a)}this.appendChild(this.#t),this.#r=document.createElement("div"),this.#r.className="kb-live-region",this.#r.setAttribute("role","status"),this.#r.setAttribute("aria-live","polite"),this.#r.setAttribute("aria-atomic","true"),this.appendChild(this.#r),this.listen(this,"drag-surface:reorder",a=>{let i=a.detail,o=a.target.closest("drag-surface"),c=this.#m(o);c&&(this.#g(c),this.#p("drag"),this.dispatchEvent(new CustomEvent("kanban-board:reorder",{bubbles:!0,detail:{itemId:i.itemId,column:c,oldIndex:i.oldIndex,newIndex:i.newIndex}})))}),this.listen(this,"drag-surface:transfer",a=>{let i=a.detail,o=i.fromSurface,c=i.toSurface,d=this.#m(o),l=this.#m(c);if(!d||!l)return;i.item&&i.item.setAttribute("data-column",l),this.#g(d),this.#g(l);let u=c.querySelector(".kb-empty");if(u&&u.remove(),o.querySelectorAll(':scope > [draggable="true"]').length===0&&!o.querySelector(".kb-empty")){let _=document.createElement("p");_.className="kb-empty",_.textContent="No items",o.appendChild(_)}let h=this.#d(i.item),f=this.#b(d),b=this.#b(l);this.#v(`${h} moved from ${f} to ${b}`),this.#p("drag"),this.dispatchEvent(new CustomEvent("kanban-board:transfer",{bubbles:!0,detail:{itemId:i.itemId,fromColumn:d,toColumn:l,newIndex:i.newIndex,item:i.item}}));let v=c.querySelectorAll(':scope > [draggable="true"]').length,x=this.#a.find(_=>_.id===l);x?.wip!==null&&x?.wip!==void 0&&v>x.wip&&this.dispatchEvent(new CustomEvent("kanban-board:wip-exceeded",{bubbles:!0,detail:{column:l,limit:x.wip,count:v}}))}),this.#c();let r=this.getAttribute("src");if(r){this._loadSrc(r);return}this.dispatchEvent(new CustomEvent("kanban-board:ready",{bubbles:!0,detail:{columnCount:this.#a.length,itemCount:e}}))}#c(){let t=[],e=new Map;for(let[s,r]of Object.entries(this.#s)){let a=r.querySelectorAll(':scope > [draggable="true"]');for(let i of a){let o=i.getAttribute("data-id");o&&(t.push({id:o,column:s}),e.set(o,i))}}this._seedCollection(t,e)}#p(t){let e=[],s=new Map;for(let r of this.items){let a=String(r.id??r.storyId??"");a&&s.set(a,r)}for(let[r,a]of Object.entries(this.#s)){let i=a.querySelectorAll(':scope > [draggable="true"]');for(let o of i){let c=o.getAttribute("data-id");if(!c)continue;let d=s.get(c);e.push(d?{...d,column:r}:{id:c,column:r})}}this._setItemsSilently(e),this._emit("items-changed",{items:e},t)}teardown(){let t=this.querySelector(".kb-title");t&&t.remove(),this.#t&&(this.#t.remove(),this.#t=null),this.#r&&(this.#r.remove(),this.#r=null),this.#s={},this.#i={},this.#a=[]}get columns(){return this.#a.map(t=>({id:t.id,label:t.label,wip:t.wip??void 0,color:t.color??void 0}))}set columns(t){let e=(t||[]).map(i=>({id:i.id,label:i.label||this.#h(i.id),wip:i.wip??null,color:i.color??null,children:[]})),s=this.#t;this.#s={},this.#i={},this.#a=e;let r=this.#u();this.#t=r;let a=()=>{s&&s.remove(),this.appendChild(r)};this.hasAttribute("data-upgraded")&&s?M(this,a,"kb-vt"):a()}get renderItem(){return this.#o}set renderItem(t){this.#o=typeof t=="function"?t:null}_renderItem(t){let e;if(this.#o){let s=this.#o(t);if(!(s instanceof Element))throw new Error("kanban-board: renderItem must return an Element");e=s}else e=this.#l(t);return e.hasAttribute("draggable")||e.setAttribute("draggable","true"),e.hasAttribute("data-id")||e.setAttribute("data-id",String(n.keyOf(t))),e}_containerFor(t,e){let s=this.#s[t.column];if(!s)throw new Error(`kanban-board: no column "${t.column}" \u2014 set .columns first or include item.column matching an existing column id`);let r=s.querySelector(":scope > .kb-empty");return r&&r.remove(),s}_postRender(){for(let t of Object.keys(this.#s)){this.#g(t);let e=this.#s[t],s=e.querySelectorAll(':scope > [draggable="true"]'),r=e.querySelector(":scope > .kb-empty");if(s.length===0&&!r){let a=document.createElement("p");a.className="kb-empty",a.textContent="No items",e.appendChild(a)}else s.length>0&&r&&r.remove()}}#l(t){let e=customElements.get("work-item")?"work-item":"article",s=document.createElement(e);return e==="work-item"?s.data={itemId:t.id??t.storyId,type:t.type,priority:t.priority,status:t.status,estimate:t.estimate!=null?String(t.estimate):void 0,assignee:t.assignee,title:t.title,description:t.description,checklist:t.checklist,notes:t.notes,detail:t.detail}:(s.className="kb-card",s.textContent=t.title||t.label||t.id),s}#u(){let t=document.createElement("div");t.className="kb-columns",t.setAttribute("role","region"),t.setAttribute("aria-label","Kanban board");for(let e of this.#a){let s=document.createElement("section");s.className="kb-column",s.setAttribute("data-column-id",e.id),e.color&&s.setAttribute("data-column-tint",e.color);let r=document.createElement("header");r.className="kb-column-header";let a=document.createElement("h3");a.textContent=e.label;let i=document.createElement("output");if(i.className="kb-count",i.textContent="0",a.appendChild(i),e.wip!=null&&!isNaN(e.wip)){let d=document.createElement("span");d.className="kb-wip",d.textContent=`/ ${e.wip}`,d.setAttribute("aria-label",`WIP limit ${e.wip}`),a.appendChild(d)}r.appendChild(a),s.appendChild(r);let o=document.createElement("drag-surface");o.setAttribute("group",this.#n),o.setAttribute("aria-label",`${e.label} items`),o.setAttribute("data-layout","stack"),o.setAttribute("data-layout-gap","xs");let c=document.createElement("p");c.className="kb-empty",c.textContent="No items",o.appendChild(c),s.appendChild(o),t.appendChild(s),this.#s[e.id]=o,this.#i[e.id]=s}return t}attributeChangedCallback(t,e,s){e===s||!this.isConnected||t==="src"&&this._loadSrc(s)}async _loadSrc(t){if(t)try{let e=await fetch(t);if(!e.ok)throw new Error(`HTTP ${e.status}`);let s=await e.json();for(;this.firstChild;)this.firstChild.remove();for(let a of s.columns||[]){let i=document.createElement("section");i.setAttribute("data-column",a.id),a.label&&i.setAttribute("data-column-label",a.label),a.wip!=null&&i.setAttribute("data-wip",String(a.wip)),a.color&&i.setAttribute("data-column-color",a.color);for(let o of a.items||[]){let c;o.persona||o.action||o.storyId?(c=document.createElement("user-story"),c.setAttribute("detail",o.detail||"minimal"),o.storyId&&c.setAttribute("story-id",o.storyId),o.persona&&c.setAttribute("persona",o.persona),o.action&&c.setAttribute("action",o.action),o.benefit&&c.setAttribute("benefit",o.benefit),o.priority&&c.setAttribute("priority",o.priority),o.status&&c.setAttribute("status",o.status),o.points&&c.setAttribute("points",String(o.points))):(c=document.createElement("article"),c.className="kb-card",c.textContent=o.text||o.label||""),c.setAttribute("draggable","true"),c.dataset.id=o.id||o.storyId||"",i.appendChild(c)}this.appendChild(i)}let r=()=>{this.teardown(),this.removeAttribute("data-upgraded"),this.setup()};this.hasAttribute("data-upgraded")&&this.#t?M(this,r,"kb-vt"):r()}catch(e){console.warn(`[kanban-board] Failed to load src="${t}":`,e)}}#m(t){if(!t)return null;for(let[e,s]of Object.entries(this.#s))if(s===t)return e;return null}#g(t){let e=this.#s[t],s=this.#i[t];if(!e||!s)return;let r=e.querySelectorAll(':scope > [draggable="true"]').length,a=s.querySelector(".kb-count");a&&(a.textContent=String(r));let i=this.#a.find(o=>o.id===t);i?.wip!==null&&i?.wip!==void 0&&(r>i.wip?s.setAttribute("data-wip-exceeded",""):s.removeAttribute("data-wip-exceeded"))}#b(t){return this.#a.find(s=>s.id===t)?.label||this.#h(t)}#v(t){this.#r&&(this.#r.textContent="",requestAnimationFrame(()=>{this.#r&&(this.#r.textContent=t)}))}#d(t){return t.getAttribute("story-id")||t.getAttribute("data-id")||t.textContent?.trim().slice(0,40)||"item"}#h(t){return t.replace(/[-_]/g," ").replace(/\b\w/g,e=>e.toUpperCase())}};w("kanban-board",qt);var It=class n extends C{static get observedAttributes(){return["src","compact","title"]}static#e=0;#t=null;#s=null;#i={};#r=null;#n="";#a=[];setup(){this.#n=`sm-${++n.#e}`;let t=[...this.querySelectorAll(":scope > section[data-activity]")];this.#a=t.map(a=>{let i=a.getAttribute("data-activity")||"",c=a.getAttribute("data-activity-label")||""||this.#u(i),d=a.getAttribute("data-journey-phase")||null,l=[...a.children];return{id:i,label:c,journeyPhase:d,children:l}});for(let a of t)a.remove();this.#t=document.createElement("div"),this.#t.className="sm-scroll",this.#t.setAttribute("role","region"),this.#t.setAttribute("aria-label","Story map"),this.#t.setAttribute("tabindex","0"),this.#s=document.createElement("div"),this.#s.className="sm-columns";let e=0;for(let a of this.#a){let i=document.createElement("section");i.className="sm-column",i.setAttribute("data-activity-column",a.id);let o=document.createElement("header");o.className="sm-activity-header";let c=document.createElement("h3");c.textContent=a.label;let d=document.createElement("span");d.className="sm-activity-count",d.textContent=String(a.children.length),c.appendChild(d),o.appendChild(c),i.appendChild(o);let l=document.createElement("drag-surface");if(l.setAttribute("group",this.#n),l.setAttribute("aria-label",`${a.label} stories`),l.setAttribute("data-layout","stack"),l.setAttribute("data-layout-gap","xs"),a.children.length>0){for(let u of a.children)l.appendChild(u);e+=a.children.length}else{let u=document.createElement("p");u.className="sm-empty",u.textContent="No stories yet",l.appendChild(u)}i.appendChild(l),this.#s.appendChild(i),this.#i[a.id]=l}let s=this.getAttribute("title");if(s){let a=document.createElement("h2");a.className="sm-title",a.textContent=s,this.appendChild(a)}this.#t.appendChild(this.#s),this.appendChild(this.#t),this.#r=document.createElement("div"),this.#r.className="sm-live-region",this.#r.setAttribute("role","status"),this.#r.setAttribute("aria-live","polite"),this.#r.setAttribute("aria-atomic","true"),this.appendChild(this.#r),this.listen(this,"drag-surface:reorder",a=>{let i=a.detail,o=a.target.closest("drag-surface"),c=this.#o(o);c&&(this.#c(c),this.dispatchEvent(new CustomEvent("story-map:reorder",{bubbles:!0,detail:{itemId:i.itemId,activity:c,oldIndex:i.oldIndex,newIndex:i.newIndex}})))}),this.listen(this,"drag-surface:transfer",a=>{let i=a.detail,o=i.fromSurface,c=i.toSurface,d=this.#o(o),l=this.#o(c);if(!d||!l)return;this.#c(d),this.#c(l);let u=c.querySelector(".sm-empty");if(u&&u.remove(),o.querySelectorAll(':scope > [draggable="true"]').length===0&&!o.querySelector(".sm-empty")){let f=document.createElement("p");f.className="sm-empty",f.textContent="No stories yet",o.appendChild(f)}let h=this.#l(i.item);this.#p(`${h} moved from ${d} to ${l}`),this.dispatchEvent(new CustomEvent("story-map:transfer",{bubbles:!0,detail:{itemId:i.itemId,fromActivity:d,toActivity:l,newIndex:i.newIndex}}))});let r=this.getAttribute("src");if(r){this._loadSrc(r);return}this.dispatchEvent(new CustomEvent("story-map:ready",{bubbles:!0,detail:{activityCount:this.#a.length,storyCount:e}}))}teardown(){this.#t&&(this.#t.remove(),this.#t=null),this.#r&&(this.#r.remove(),this.#r=null),this.#s=null,this.#i={},this.#a=[]}get activities(){return this.#a.map(t=>({id:t.id,label:t.label,journeyPhase:t.journeyPhase||void 0,stories:[...this.#i[t.id]?.querySelectorAll(':scope > [draggable="true"]')||[]].map(e=>({id:e.getAttribute("data-id")||void 0,storyId:e.getAttribute("story-id")||void 0,title:e.querySelector('[slot="title"]')?.textContent?.trim()||void 0}))}))}set activities(t){let e=Array.isArray(t)?t:[];for(;this.firstChild;)this.firstChild.remove();for(let r of e){let a=document.createElement("section");a.setAttribute("data-activity",r.id||""),r.label&&a.setAttribute("data-activity-label",r.label),r.journeyPhase&&a.setAttribute("data-journey-phase",r.journeyPhase);for(let i of r.stories||[]){let o,c=this;if(typeof c.renderStory=="function"){let d=c.renderStory(i);o=d instanceof Element?d:null}o||(customElements.get("user-story")?(o=document.createElement("user-story"),o.data=i):(o=document.createElement("article"),o.className="sm-card",o.textContent=i.title||i.id||"")),o.hasAttribute("draggable")||o.setAttribute("draggable","true"),i.id&&!o.hasAttribute("data-id")&&o.setAttribute("data-id",String(i.id)),a.appendChild(o)}this.appendChild(a)}let s=()=>{this.teardown(),this.removeAttribute("data-upgraded"),this.setup()};this.hasAttribute("data-upgraded")&&this.#t?M(this,s,"sm-vt"):s(),this.dispatchEvent(new CustomEvent("story-map:activities-changed",{detail:{activities:e,source:"property"},bubbles:!0}))}attributeChangedCallback(t,e,s){e===s||!this.isConnected||t==="src"&&this._loadSrc(s)}async _loadSrc(t){if(t)try{let e=await fetch(t);if(!e.ok)throw new Error(`HTTP ${e.status}`);let s=await e.json();for(;this.firstChild;)this.firstChild.remove();for(let a of s.activities||[]){let i=document.createElement("section");i.setAttribute("data-activity",a.id),i.setAttribute("data-activity-label",a.label||a.id),a.journeyPhase&&i.setAttribute("data-journey-phase",a.journeyPhase);for(let o of a.stories||[]){let c=document.createElement("user-story");c.setAttribute("draggable","true"),c.dataset.id=o.id||o.storyId,(o.storyId||o.id)&&c.setAttribute("story-id",o.storyId||o.id),o.title&&c.setAttribute("title",o.title),o.persona&&c.setAttribute("persona",o.persona),o.action&&c.setAttribute("action",o.action),o.benefit&&c.setAttribute("benefit",o.benefit),o.priority&&c.setAttribute("priority",o.priority),o.status&&c.setAttribute("status",o.status),o.points&&c.setAttribute("points",String(o.points)),c.setAttribute("detail",o.detail||"compact"),i.appendChild(c)}this.appendChild(i)}let r=()=>{this.teardown(),this.removeAttribute("data-upgraded"),this.setup()};this.hasAttribute("data-upgraded")&&this.#t?M(this,r,"sm-vt"):r()}catch(e){console.warn(`[story-map] Failed to load src="${t}":`,e)}}#o(t){if(!t)return null;for(let[e,s]of Object.entries(this.#i))if(s===t)return e;return null}#c(t){let e=this.#i[t];if(!e)return;let s=e.querySelectorAll(':scope > [draggable="true"]').length,r=e.closest("[data-activity-column]");if(!r)return;let a=r.querySelector(".sm-activity-count");a&&(a.textContent=String(s))}#p(t){this.#r&&(this.#r.textContent="",requestAnimationFrame(()=>{this.#r&&(this.#r.textContent=t)}))}#l(t){return t.getAttribute("story-id")||t.getAttribute("data-id")||t.textContent?.trim().slice(0,40)||"item"}#u(t){return t.replace(/[-_]/g," ").replace(/\b\w/g,e=>e.toUpperCase())}};w("story-map",It);var rt=`
1805
+ `,e.appendChild(r),e}#s(t){let e=document.createElement("quadrant-grid");e.setAttribute("x-label","Likelihood"),e.setAttribute("y-label","Impact"),e.setAttribute("x-low","Rare"),e.setAttribute("x-high","Likely"),e.setAttribute("y-low","Minor"),e.setAttribute("y-high","Severe"),e.setAttribute("q1-label","Avoid"),e.setAttribute("q2-label","Plan"),e.setAttribute("q3-label","Accept"),e.setAttribute("q4-label","Mitigate");for(let r of t){if(!r.likelihood||!r.impact)continue;let s=document.createElement("span");s.setAttribute("data-x",Fe(r.likelihood).toFixed(3)),s.setAttribute("data-y",Fe(r.impact).toFixed(3)),s.setAttribute("data-quadrant",String(Rr(r.likelihood,r.impact))),s.setAttribute("data-id",r.id),s.setAttribute("title",`${r.title} \u2014 likelihood ${r.likelihood}, impact ${r.impact}, severity ${r.likelihood*r.impact}`),s.textContent=r.title,e.appendChild(s)}return e}#i=[];get rows(){return[...this.#i]}set rows(t){this.#r(Array.isArray(t)?t:[])}};A("risk-register",se);var Pr=["id","story-id","item-id"],ie=class i extends C{setup(){let t=this.getAttribute("rows"),e=this.getAttribute("cols"),r=this.getAttribute("link-attr");return!t||!e||!r?(console.warn("traceability-matrix: requires rows, cols, and link-attr attributes"),!1):(queueMicrotask(()=>{this.isConnected&&this.#t(t,e,r)}),!0)}teardown(){this.#s()}#e(t){let e=this.getAttribute("match-attr");return(e?[e]:Pr).map(s=>(t.getAttribute(s)||"").trim()).filter(Boolean)}#t(t,e,r){let s=[...document.querySelectorAll(t)].filter(_=>_!==this&&!this.contains(_)),a=[...document.querySelectorAll(e)].filter(_=>_!==this&&!this.contains(_));if(!s.length||!a.length){this.#i();return}let n=this.getAttribute("row-label")||"",o=this.getAttribute("cell-mark")||"\u2713",l=this.hasAttribute("flag-orphans"),d=a.map(_=>new Set(this.#e(_))),c=s.map(_=>{let $=i.#c(_.getAttribute(r));return d.map(N=>$.some(F=>N.has(F)))}),u=c.map(_=>_.filter(Boolean).length),m=a.map((_,$)=>c.filter(N=>N[$]).length),f=u.reduce((_,$)=>_+$,0),h=document.createElement("data-table"),b=document.createElement("table"),g=document.createElement("thead"),w=document.createElement("tr"),v=document.createElement("th");v.setAttribute("data-sort","string"),v.textContent=n,w.appendChild(v);let y=a.map(_=>i.#n(_));a.forEach((_,$)=>{let N=document.createElement("th");N.setAttribute("data-sort","number"),N.textContent=y[$],N.dataset.colId=_.id||this.#e(_)[0]||"",N.dataset.colIndex=String($),l&&!m[$]&&(N.dataset.orphan=""),w.appendChild(N)}),g.appendChild(w),b.appendChild(g);let x=document.createElement("tbody");s.forEach((_,$)=>{let N=document.createElement("tr");N.dataset.rowId=_.id||"",N.dataset.rowIndex=String($),l&&!u[$]&&(N.dataset.orphan="");let F=i.#n(_),L=document.createElement("th");L.scope="row",L.appendChild(i.#r(F,`Highlight ${F}`)),N.appendChild(L),a.forEach((Q,rt)=>{let V=document.createElement("td"),G=c[$][rt];V.setAttribute("data-sort-value",G?"1":"0"),G&&(V.dataset.linked=""),V.setAttribute("aria-label",G?"linked":"not linked"),V.dataset.colId=Q.id||this.#e(Q)[0]||"",V.dataset.colIndex=String(rt),V.appendChild(i.#r(G?o:"",`${F} \xD7 ${y[rt]}: ${G?"linked":"not linked"}`)),N.appendChild(V)}),x.appendChild(N)}),b.appendChild(x),h.appendChild(b),this.#s(),[...this.children].forEach(_=>{_.tagName!=="TEMPLATE"&&_.remove()});let k=this.getAttribute("label");if(k){let _=document.createElement("header");_.className="tm-label",_.textContent=k,this.appendChild(_)}this.appendChild(h),this.#d=s,this.#o=a,this.listen(h,"click",this.#a),queueMicrotask(()=>{this.dispatchEvent(new CustomEvent("traceability-matrix:ready",{bubbles:!0,detail:{rowCount:s.length,colCount:a.length,linkCount:f}}))})}static#r(t,e){let r=document.createElement("button");return r.type="button",r.className="tm-cell-btn",r.textContent=t,r.setAttribute("aria-label",e),r.setAttribute("aria-pressed","false"),r}#a=t=>{let e=t.target.closest('td, th[scope="row"]');if(!e)return;let r=e.closest("tr");if(!r)return;let s=r.dataset.rowIndex,a=e.dataset.colIndex,n=s!==void 0?this.#d[Number(s)]??null:null,o=a!==void 0?this.#o[Number(a)]??null:null,l=e.hasAttribute("data-state-highlighted");if(this.#s(),l){this.dispatchEvent(new CustomEvent("traceability-matrix:highlight",{bubbles:!0,detail:{rowEl:n,colEl:o,on:!1}}));return}e.setAttribute("data-state-highlighted",""),e.querySelector(".tm-cell-btn")?.setAttribute("aria-pressed","true"),r.setAttribute("data-state-highlighted","");for(let d of[n,o])d&&!this.#l.includes(d)&&(d.setAttribute("data-state-highlighted",""),this.#l.push(d));this.dispatchEvent(new CustomEvent("traceability-matrix:highlight",{bubbles:!0,detail:{rowEl:n,colEl:o,on:!0}}))};#s(){this.querySelectorAll("[data-state-highlighted]").forEach(t=>t.removeAttribute("data-state-highlighted")),this.querySelectorAll('.tm-cell-btn[aria-pressed="true"]').forEach(t=>t.setAttribute("aria-pressed","false"));for(let t of this.#l)t.removeAttribute("data-state-highlighted");this.#l=[]}#i(){this.#s(),[...this.children].forEach(e=>{e.tagName!=="TEMPLATE"&&e.remove()});let t=document.createElement("p");t.className="tm-empty",t.textContent="No matching elements found for this matrix.",this.appendChild(t)}static#c(t){return t?t.split(",").map(e=>e.trim()).filter(Boolean):[]}static#n(t){return t.getAttribute("data-matrix-label")||t.id||(t.textContent||"").trim().split(`
1806
+ `)[0].slice(0,60)||"(unnamed)"}#d=[];#o=[];#l=[]};A("traceability-matrix",ie);var Dr=/^(\d{4})-(\d{2})-(\d{2})(?![\d:T])/,Or=/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}/;function T(i){if(i==null||i==="")return null;if(i instanceof Date)return Number.isNaN(i.getTime())?null:et(i);if(typeof i=="number")return Number.isFinite(i)?et(new Date(i)):null;let t=String(i).trim(),e=t.match(Dr);if(e){let s=new Date(Number(e[1]),Number(e[2])-1,Number(e[3]));return s.getMonth()!==Number(e[2])-1||s.getDate()!==Number(e[3])?null:s}if(!Or.test(t))return null;let r=new Date(t);return Number.isNaN(r.getTime())?null:et(r)}function et(i){return new Date(i.getFullYear(),i.getMonth(),i.getDate())}function R(i){let t=String(i.getMonth()+1).padStart(2,"0"),e=String(i.getDate()).padStart(2,"0");return`${i.getFullYear()}-${t}-${e}`}function M(i,t){let e=et(i);return e.setDate(e.getDate()+t),e}function W(i,t){let e=Date.UTC(i.getFullYear(),i.getMonth(),i.getDate()),r=Date.UTC(t.getFullYear(),t.getMonth(),t.getDate());return Math.round((r-e)/864e5)}function Be(i,t){let e=[];for(let r=et(i);r<=t;r=M(r,1))e.push(R(r));return e}function Rt(i){return new Date(i.getFullYear(),i.getMonth(),1)}function jr(i){return new Date(i.getFullYear(),i.getMonth()+1,0)}function Pt(i){return new Date(i.getFullYear(),Math.floor(i.getMonth()/3)*3,1)}function B(i,t){let e=new Date(i.getFullYear(),i.getMonth()+t,1),r=jr(e).getDate();return new Date(e.getFullYear(),e.getMonth(),Math.min(i.getDate(),r))}function H(i,t={year:"numeric",month:"long",day:"numeric"},e=void 0){return i.toLocaleDateString(e,t)}var ne=class i extends C{static get observedAttributes(){return["start","end","total","unit","label","weekends"]}#e=!1;connectedCallback(){this.#e=!0,super.connectedCallback()}disconnectedCallback(){this.#e=!1,super.disconnectedCallback()}attributeChangedCallback(t,e,r){e===r||!this.#e||(this.hasAttribute("data-upgraded")?this.#a()||this.#r():super.connectedCallback())}setup(){if(!this.#a())return!1;let{dayCount:t,total:e,scopeChanges:r}=this.#t;return queueMicrotask(()=>{this.dispatchEvent(new CustomEvent("burndown-chart:ready",{bubbles:!0,detail:{dayCount:t,total:e,scopeChanges:r}}))}),!0}#t={dayCount:0,total:0,scopeChanges:0};#r(){[...this.children].forEach(t=>{t.tagName!=="TEMPLATE"&&t.remove()})}#a(){let t=this.getAttribute("start"),e=this.getAttribute("end"),r=parseFloat(this.getAttribute("total")||"");if(!t||!e||!Number.isFinite(r))return console.warn("burndown-chart: requires start, end, and total attributes"),!1;let s=T(t),a=T(e);if(!s||!a||a<s)return console.warn("burndown-chart: start/end dates invalid",t,e),!1;let n=(this.getAttribute("weekends")||"include")!=="exclude",o=this.getAttribute("unit")||"points",l=this.getAttribute("label")||"",d=this.querySelector(":scope > template"),c=d?i.#i(d):[],u=c.filter(b=>b.delta!==0),m=Be(s,a),f=i.#c(m,r,n),h=i.#n(m,c);return this.#s({label:l,unit:o,dayLabels:m,actual:h,ideal:f,scopeChanges:u}),this.#t={dayCount:m.length,total:r,scopeChanges:u.length},!0}#s({label:t,unit:e,dayLabels:r,actual:s,ideal:a,scopeChanges:n}){if(this.#r(),t){let u=document.createElement("header");u.className="bdc-label",u.textContent=t,this.appendChild(u)}let o=document.createElement("chart-wc");o.setAttribute("data-type","line"),o.setAttribute("data-legend",""),o.setAttribute("data-tooltip",""),o.setAttribute("data-label-x","Day"),o.setAttribute("data-label-y",e);let l={},d={};r.forEach((u,m)=>{l[u]=a[m],s[m]!==null&&(d[u]=s[m])});let c=[{name:"Actual",values:d},{name:"Ideal",values:l}];if(o.setAttribute("data-values",JSON.stringify(c)),this.appendChild(o),n.length){let u=document.createElement("aside");u.className="bdc-scope-changes";let m=document.createElement("h4");m.textContent="Scope changes",u.appendChild(m);let f=document.createElement("ul");for(let h of n){let b=document.createElement("li"),g=h.delta>0?"+":"",w=document.createElement("time");w.setAttribute("datetime",h.date),w.textContent=h.date;let v=document.createElement("strong");v.textContent=`${g}${h.delta} ${e}`,b.append(w,": ",v),f.appendChild(b)}u.appendChild(f),this.appendChild(u)}}static#i(t){let e=[],r=t.content.querySelectorAll("tr");for(let s of r){let a=[...s.children],n=a[0]?.textContent?.trim(),o=parseFloat(a[1]?.textContent??""),l=parseFloat(a[2]?.textContent??"0")||0;if(!n||!Number.isFinite(o))continue;let d=/^\d{4}-\d{2}-\d{2}/.test(n)?T(n):null,c=d?R(d):n;e.push({date:c,remaining:o,delta:l})}return e}static#c(t,e,r){let s=c=>{let u=T(c);if(!u)return!1;let m=u.getDay();return m===0||m===6},a=t.map((c,u)=>({d:c,i:u,weekend:s(c)})).filter(c=>r||!c.weekend),n=a.length>1?e/(a.length-1):0,o=new Array(t.length).fill(null),l=e,d=0;for(let c=0;c<t.length;c++){let u=s(t[c]);r||!u?(o[c]=Math.max(0,e-n*d),d++,l=o[c]):o[c]=l}return o}static#n(t,e){let r=new Map(e.map(s=>[s.date,s.remaining]));return t.map(s=>r.has(s)?r.get(s):null)}};A("burndown-chart",ne);var He=4,Fr={planned:"Planned","in-progress":"In progress","at-risk":"At risk",shipped:"Shipped",blocked:"Blocked"};function Ue(i){return Fr[i]||(i.charAt(0).toUpperCase()+i.slice(1)).replace(/-/g," ")}var Br=0,oe=class i extends C{static get observedAttributes(){return["start","end","view","editable","today-marker"]}#e=`rm-${++Br}`;setup(){if(!this.#t())return!1;let t=[...this.querySelectorAll(":scope > section[data-lane]")];return t.length?(this.#q=t,this.listen(this,"click",this.#d),this.listen(this,"keydown",this.#o),this.listen(this,"pointerdown",this.#l),this.listen(this,"pointermove",this.#u),this.listen(this,"pointerup",this.#y),this.listen(this,"pointercancel",this.#E),this.#a(),!0):(console.warn("product-roadmap: no <section data-lane> children found"),!1)}teardown(){this.#N=null}#t(){let t=this.getAttribute("start"),e=this.getAttribute("end");if(!t||!e)return console.warn("product-roadmap: start and end attributes required"),!1;let r=i.#m(t,"start"),s=i.#m(e,"end");return!r||!s||s<r?(console.warn("product-roadmap: invalid start/end",t,e),!1):(this.#p=r,this.#f=M(s,1),this.#S=W(r,this.#f),this.#k=this.getAttribute("view")==="month"?"month":"quarter",this.#$=this.hasAttribute("editable"),!0)}attributeChangedCallback(t,e,r){e!==r&&(!this.isConnected||!this.hasAttribute("data-upgraded")||this.#t()&&this.#a())}get#r(){return this.#k==="month"?1:3}#a(){let t=this.querySelector(".rm-bar:focus"),e=t?this.#I.get(t):null;[...this.children].forEach(o=>{this.#q.includes(o)||o.remove()}),this.#q.forEach(o=>{o.hidden=!0}),this.#I=new WeakMap;let r=document.createElement("div");r.className="rm-wrapper",r.appendChild(this.#s());let s=document.createElement("div");s.className="rm-lanes";let a=null;for(let o of this.#q){let l=o.getAttribute("data-lane")||"",d=document.createElement("section");d.className="rm-lane",d.dataset.lane=l;let c=document.createElement("header");c.className="rm-lane-label",c.textContent=l,d.appendChild(c);let u=document.createElement("div");u.className="rm-track",u.dataset.lane=l;let m=[...o.querySelectorAll(":scope > article[data-start][data-end]")];for(let f of m){let h=this.#i(f,l);h&&(u.appendChild(h),f===e&&(a=h))}d.appendChild(u),s.appendChild(d)}if(r.appendChild(s),this.hasAttribute("today-marker")&&this.#p&&this.#f){let o=T(new Date);if(o>=this.#p&&o<this.#f){let l=document.createElement("div");l.className="rm-today",l.style.setProperty("--rm-x",this.#h(o).toFixed(4)),l.title=`Today: ${R(o)}`,s.appendChild(l)}}if(this.#$){let o=document.createElement("p");o.id=`${this.#e}-help`,o.className="rm-sr-only";let l=this.#k==="month"?"month":"quarter";o.textContent=`Arrow keys move by one ${l}. Shift plus arrow keys change the end date. Alt plus up or down arrow moves to another lane.`,r.appendChild(o)}let n=document.createElement("div");n.className="rm-sr-only",n.setAttribute("role","status"),n.setAttribute("aria-live","polite"),r.appendChild(n),this.#T=n,this.appendChild(r),a&&a.focus()}#s(){let t=document.createElement("header");t.className="rm-axis";for(let e of this.#v()){let r=document.createElement("div");r.className="rm-tick",r.style.setProperty("--rm-x",e.startFraction.toFixed(4)),r.style.setProperty("--rm-w",(e.endFraction-e.startFraction).toFixed(4)),r.textContent=e.label,t.appendChild(r)}return t}#i(t,e){let r=i.#m(t.getAttribute("data-start"),"start"),s=i.#m(t.getAttribute("data-end"),"end");if(!r||!s||s<r||!this.#p||!this.#f)return null;let a=M(s,1),n=r<this.#p?this.#p:r,o=a>this.#f?this.#f:a;if(n>=o)return null;let l=this.#h(n),d=this.#h(o)-l,c=document.createElement("article");c.className="rm-bar",c.style.setProperty("--rm-x",l.toFixed(4)),c.style.setProperty("--rm-w",d.toFixed(4)),c.dataset.lane=e,c.dataset.start=R(r),c.dataset.end=R(s);let u=t.dataset.status||"";u&&(c.dataset.status=u),t.id&&(c.dataset.sourceId=t.id),c.tabIndex=0,c.setAttribute("role","button"),this.#I.set(c,t);let m=t.querySelector("h1, h2, h3, h4, h5, h6"),f=document.createElement("span");if(f.className="rm-bar-title",f.textContent=m?m.textContent.trim():(t.textContent||"").trim().split(`
1807
+ `)[0],c.appendChild(f),u){let h=document.createElement("span");h.className="rm-bar-status",h.textContent=Ue(u),c.appendChild(h)}if(c.setAttribute("aria-label",`${f.textContent} \u2014 ${H(r)} to ${H(s)} in ${e}`+(u?`, status: ${Ue(u).toLowerCase()}`:"")),this.#$){c.setAttribute("aria-describedby",`${this.#e}-help`);let h=document.createElement("span");h.className="rm-bar-handle",h.setAttribute("aria-hidden","true"),h.title="Drag to change the end date",c.appendChild(h)}return c}#c(t){let e=this.#I.get(t);e&&this.dispatchEvent(new CustomEvent("product-roadmap:select",{bubbles:!0,detail:{initiative:e,lane:t.dataset.lane,start:t.dataset.start,end:t.dataset.end,status:t.dataset.status||null}}))}#n(t){let r=t.target?.closest?.(".rm-bar");return r&&this.contains(r)?r:null}#d=t=>{let e=this.#n(t);e&&(this.#C||this.#c(e))};#o=t=>{let e=t,r=this.#n(e);if(!r||e.target!==r)return;if(e.key==="Enter"||e.key===" "){e.preventDefault(),this.#c(r);return}if(!this.#$)return;let s=this.#I.get(r);if(!s)return;let a=this.#r;if(e.altKey&&(e.key==="ArrowUp"||e.key==="ArrowDown")){e.preventDefault();let d=this.#q.map(m=>m.getAttribute("data-lane")||""),c=d.indexOf(r.dataset.lane||""),u=d[c+(e.key==="ArrowUp"?-1:1)];if(c===-1||u===void 0)return;this.#b(s,r.dataset.lane||"",u,null,null,"move");return}if(e.key!=="ArrowLeft"&&e.key!=="ArrowRight")return;e.preventDefault();let n=e.key==="ArrowLeft"?-1:1,o=T(r.dataset.start),l=M(T(r.dataset.end),1);if(e.shiftKey){if(n>0&&l>=this.#f)return;let d=B(l,n*a);if(d<=o)return;this.#b(s,r.dataset.lane||"",null,o,M(d,-1),"resize")}else{if(n<0&&o<=this.#p||n>0&&l>=this.#f)return;let d=B(o,n*a),c=B(l,n*a);this.#b(s,r.dataset.lane||"",null,d,M(c,-1),"reschedule")}};#l=t=>{let e=t;if(!this.#$||e.button!==0)return;let r=this.#n(e);if(!r)return;let s=r.parentElement;if(!s)return;let a=e.target.classList?.contains("rm-bar-handle");this.#N={kind:a?"resize":"move",pointerId:e.pointerId,bar:r,trackRect:s.getBoundingClientRect(),startX:e.clientX,startY:e.clientY,startFraction:parseFloat(r.style.getPropertyValue("--rm-x"))||0,widthFraction:parseFloat(r.style.getPropertyValue("--rm-w"))||0,moved:!1,targetLane:r.dataset.lane||""}};#u=t=>{let e=t,r=this.#N;if(!r||e.pointerId!==r.pointerId)return;let s=e.clientX-r.startX,a=e.clientY-r.startY;if(!r.moved){if(Math.abs(s)<He&&Math.abs(a)<He)return;r.moved=!0,r.bar.setAttribute("data-dragging","");try{r.bar.setPointerCapture(e.pointerId)}catch{}}let n=s/r.trackRect.width;if(r.kind==="move"){let o=Math.max(0,Math.min(1-r.widthFraction,r.startFraction+n));r.bar.style.setProperty("--rm-x",o.toFixed(4));let l=r.bar.dataset.lane||"";for(let d of this.querySelectorAll(".rm-track")){let c=d.getBoundingClientRect();e.clientY>=c.top&&e.clientY<=c.bottom&&(l=d.dataset.lane||""),d.toggleAttribute("data-drop-target",!1)}r.targetLane=l,l!==r.bar.dataset.lane&&this.querySelector(`.rm-track[data-lane="${CSS.escape(l)}"]`)?.setAttribute("data-drop-target","")}else{let o=Math.max(.01,Math.min(1-r.startFraction,r.widthFraction+n));r.bar.style.setProperty("--rm-w",o.toFixed(4))}};#y=t=>{let e=t,r=this.#N;if(!r||e.pointerId!==r.pointerId||(this.#N=null,!r.moved))return;this.#C=!0,setTimeout(()=>{this.#C=!1},0);let s=this.#I.get(r.bar);if(!s)return;let a=parseFloat(r.bar.style.getPropertyValue("--rm-x"))||0,n=parseFloat(r.bar.style.getPropertyValue("--rm-w"))||0,o=T(r.bar.dataset.start),l=M(T(r.bar.dataset.end),1);if(r.kind==="move"){let u=a-r.startFraction;o=this.#A(this.#_(this.#x(o)+u)),l=this.#A(this.#_(this.#x(l)+u))}else{let u=n-r.widthFraction;l=this.#A(this.#_(this.#x(l)+u))}l<=o&&(l=B(o,this.#r));let d=r.bar.dataset.lane||"",c=r.kind==="move"&&r.targetLane!==d?r.targetLane:null;this.#b(s,d,c,o,M(l,-1),r.kind==="move"?"reschedule":"resize")};#E=t=>{let e=t;!this.#N||e.pointerId!==this.#N.pointerId||(this.#N=null,this.#a())};#b(t,e,r,s,a,n){let o=R(i.#m(t.getAttribute("data-start"),"start")),l=R(i.#m(t.getAttribute("data-end"),"end")),d=s?R(s):o,c=a?R(a):l,u=d!==o||c!==l,m=r!==null&&r!==e?this.#q.find(g=>g.getAttribute("data-lane")===r):null,f=!!m;if(u&&(t.setAttribute("data-start",d),t.setAttribute("data-end",c)),m&&m.appendChild(t),this.#a(),!u&&!f)return;let h=f?r:e,b=t.querySelector("h1, h2, h3, h4, h5, h6")?.textContent?.trim()||"Initiative";this.#g(`${b}: ${H(T(d))} to ${H(T(c))} in ${h}`),u&&n!=="move"&&this.dispatchEvent(new CustomEvent(`product-roadmap:${n}`,{bubbles:!0,detail:{initiative:t,lane:h,start:d,end:c}})),f&&this.dispatchEvent(new CustomEvent("product-roadmap:move",{bubbles:!0,detail:{initiative:t,fromLane:e,toLane:r,start:d,end:c}}))}#g(t){this.#T&&(this.#T.textContent=t)}#h(t){return!this.#p||!this.#S?0:Math.max(0,Math.min(1,W(this.#p,t)/this.#S))}#x(t){return!this.#p||!this.#S?0:W(this.#p,t)/this.#S}#_(t){return M(this.#p??new Date,Math.round(t*this.#S))}#w(t){return this.#k==="month"?Rt(t):Pt(t)}#A(t){let e=this.#w(t),r=B(e,this.#r);return W(e,t)<=W(t,r)?e:r}#v(){let t=[],e=this.#p,r=this.#f;if(!e||!r)return t;let s=this.#r;for(let a=this.#w(e);a<r;a=B(a,s)){let n=B(a,s),o=this.#h(a<e?e:a),l=this.#h(n>r?r:n),d=this.#k==="quarter"?`Q${Math.floor(a.getMonth()/3)+1} ${a.getFullYear()}`:`${a.toLocaleString(void 0,{month:"short"})} ${a.getFullYear()}`;t.push({startFraction:o,endFraction:l,label:d})}return t}static#m(t,e){if(!t)return null;let r=String(t).trim().match(/^(\d{4})-Q([1-4])$/i);if(r){let s=Number(r[1]),a=(Number(r[2])-1)*3;return e==="end"?new Date(s,a+3,0):new Date(s,a,1)}return T(t)}#p=null;#f=null;#S=0;#k="quarter";#$=!1;#C=!1;#q=[];#I=new WeakMap;#T=null;#N=null};A("product-roadmap",oe);function Ve(i){let t=i;return class extends t{static keyOf(e){return e.id}#e=[];#t=new Map;get items(){return this.#e}set items(e){let r=e||[],s=Lt({newItems:r,nodes:this.#t,keyOf:this.constructor.keyOf,renderItem:a=>this._renderItem(a),containerFor:(a,n)=>this._containerFor(a,n)});this.#e=r,this._postRender({...s,items:r}),this._emit("items-changed",{items:r},"api")}_renderItem(e){throw new Error(`${this.constructor.name}: must implement _renderItem(item)`)}_containerFor(e,r){return this}_postRender(e){}_emit(e,r,s="api"){this.dispatchEvent(new CustomEvent(`${this.localName}:${e}`,{detail:{...r,source:s},bubbles:!0}))}_nodeFor(e){return this.#t.get(e)||null}_seedCollection(e,r){this.#e=e,this.#t.clear();for(let[s,a]of r)this.#t.set(s,a)}_setItemsSilently(e){this.#e=e}}}var ce=class i extends Ve(C){static get observedAttributes(){return["src","compact","title"]}static keyOf(t){return t.id??t.storyId}static#e=0;#t=null;#r={};#a={};#s=null;#i=null;#c="";#n=[];#d=null;#o=!1;#l=!1;#u=!1;#y=new z;setup(){this.#f(),this.#o||(this.#o=!0,this.#E()),this.#l||(this.#l=!0,this.listen(this,"drag-surface:reorder",this.#x),this.listen(this,"drag-surface:transfer",this.#_));let t=this.getAttribute("src");if(t){t!==this.#y.url&&this._loadSrc(t);return}this.#u||this.#h()}#E(){let t=[...this.querySelectorAll(":scope > section[data-column]")],e=t.map(r=>this.#b(r));for(let r of t)r.remove();this.#g(),this.#s=ct("kb-live-region"),this.#n=e.map(r=>r.meta),this.#t=this.#m(e.map(r=>r.children)),this.append(this.#t,this.#s),this._postRender(),this.#w()}#b(t){let e=t.getAttribute("data-column")||"",r=t.getAttribute("data-column-label")||Y(e),s=t.getAttribute("data-wip"),a=s?parseInt(s,10):null,n=t.getAttribute("data-column-color")||null,o=[...t.children];return{meta:{id:e,label:r,wip:a!==null&&isNaN(a)?null:a,color:n},children:o}}#g(){let t=this.getAttribute("title");t?(this.#i||(this.#i=document.createElement("h2"),this.#i.className="kb-title",this.prepend(this.#i)),this.#i.textContent=t):this.#i&&(this.#i.remove(),this.#i=null),this.#t?.setAttribute("aria-label",t||"Kanban board")}#h(){this.#u=!0,this.dispatchEvent(new CustomEvent("kanban-board:ready",{bubbles:!0,detail:{columnCount:this.#n.length,itemCount:this.items.length}}))}#x=t=>{let e=t.detail,r=t.target.closest("drag-surface"),s=this.#k(r);s&&(this.#$(s),this.#A("drag"),this.dispatchEvent(new CustomEvent("kanban-board:reorder",{bubbles:!0,detail:{itemId:e.itemId,column:s,oldIndex:e.oldIndex,newIndex:e.newIndex}})))};#_=t=>{let e=t.detail,r=e.fromSurface,s=e.toSurface,a=this.#k(r),n=this.#k(s);if(!a||!n)return;e.item&&e.item.setAttribute("data-column",n),this.#$(a),this.#$(n),tt(s,"kb-empty","No items"),tt(r,"kb-empty","No items"),bt(this.#s,`${lt(e.item)} moved from ${this.#C(a)} to ${this.#C(n)}`),this.#A("drag"),this.dispatchEvent(new CustomEvent("kanban-board:transfer",{bubbles:!0,detail:{itemId:e.itemId,fromColumn:a,toColumn:n,newIndex:e.newIndex,item:e.item}}));let o=s.querySelectorAll(':scope > [draggable="true"]').length,l=this.#n.find(d=>d.id===n);l&&l.wip!=null&&o>l.wip&&this.dispatchEvent(new CustomEvent("kanban-board:wip-exceeded",{bubbles:!0,detail:{column:n,limit:l.wip,count:o}}))};#w(){let t=[],e=new Map;for(let[r,s]of Object.entries(this.#r)){let a=s.querySelectorAll(':scope > [draggable="true"]');for(let n of a){let o=n.getAttribute("data-id");o&&(t.push({id:o,column:r}),e.set(o,n))}}this._seedCollection(t,e)}#A(t){let e=[],r=new Map;for(let s of this.items){let a=String(s.id??s.storyId??"");a&&r.set(a,s)}for(let[s,a]of Object.entries(this.#r)){let n=a.querySelectorAll(':scope > [draggable="true"]');for(let o of n){let l=o.getAttribute("data-id");if(!l)continue;let d=r.get(l);e.push(d?{...d,column:s}:{id:l,column:s})}}this._setItemsSilently(e),this._emit("items-changed",{items:e},t)}teardown(){this.#l=!1}get columns(){return this.#n.map(t=>({id:t.id,label:t.label,wip:t.wip??void 0,color:t.color??void 0}))}set columns(t){let e=(t||[]).map(c=>({id:c.id,label:c.label||Y(c.id),wip:c.wip??null,color:c.color??null}));this.#o||(this.#o=!0,this.#s=ct("kb-live-region"),this.appendChild(this.#s));let r=this.#t;this.#n=e;let s=this.#m();this.#t=s,this.#g();let a=this.items,n=[],o=new Map;for(let c of a){let u=i.keyOf(c),m=this._nodeFor(u),f=this.#r[c.column];m&&(f?(f.appendChild(m),n.push(c),o.set(u,m)):m.remove())}let l=new Map(e.map((c,u)=>[c.id,u]));n.sort((c,u)=>(l.get(c.column)??0)-(l.get(u.column)??0)),this._seedCollection(n,o),this._postRender(),n.length!==a.length&&this._emit("items-changed",{items:n},"api");let d=()=>{r&&r.remove(),this.#S(s)};this.hasAttribute("data-upgraded")&&r?D(this,d,"kb-vt"):d()}get renderItem(){return this.#d}set renderItem(t){this.#d=typeof t=="function"?t:null}_renderItem(t){let e;if(this.#d){let r=this.#d(t);if(!(r instanceof Element))throw new Error("kanban-board: renderItem must return an Element");e=r}else e=this.#v(t);return e.hasAttribute("draggable")||e.setAttribute("draggable","true"),e.hasAttribute("data-id")||e.setAttribute("data-id",String(i.keyOf(t))),e}_containerFor(t,e){let r=this.#r[t.column];if(!r)throw new Error(`kanban-board: no column "${t.column}" \u2014 set .columns first or include item.column matching an existing column id`);let s=r.querySelector(":scope > .kb-empty");return s&&s.remove(),r}_postRender(){for(let[t,e]of Object.entries(this.#r))this.#$(t),tt(e,"kb-empty","No items")}#v(t){let e=customElements.get("work-item")?"work-item":"article",r=document.createElement(e);return e==="work-item"?r.data={itemId:t.id??t.storyId,type:t.type,priority:t.priority,status:t.status,estimate:t.estimate!=null?String(t.estimate):void 0,assignee:t.assignee,title:t.title,description:t.description,checklist:t.checklist,notes:t.notes,detail:t.detail}:(r.className="kb-card",r.textContent=t.title||t.label||t.id),r}#m(t=[]){this.#f(),this.#r={},this.#a={};let e=document.createElement("div");e.className="kb-columns",e.setAttribute("role","region"),e.setAttribute("aria-label",this.getAttribute("title")||"Kanban board");let r=0;return this.#n.forEach((s,a)=>{let n=document.createElement("section");n.className="kb-column",n.setAttribute("data-column-id",s.id),s.color&&n.setAttribute("data-column-tint",s.color);let o=document.createElement("header");o.className="kb-column-header";let l=document.createElement("h3");l.textContent=s.label;let d=document.createElement("output");if(d.className="kb-count",d.textContent="0",l.appendChild(d),s.wip!=null){let u=document.createElement("span");u.className="kb-wip",u.textContent=`/ ${s.wip}`,u.setAttribute("aria-label",`WIP limit ${s.wip}`),l.appendChild(u)}o.appendChild(l),n.appendChild(o);let c=document.createElement("drag-surface");c.setAttribute("group",this.#c),c.setAttribute("aria-label",`${s.label} items`),c.setAttribute("data-layout","stack"),c.setAttribute("data-layout-gap","xs");for(let u of t[a]||[])u.hasAttribute("draggable")||u.setAttribute("draggable","true"),u.hasAttribute("data-id")||(u.dataset.id=`kb-item-${r}`),r+=1,c.appendChild(u);n.appendChild(c),e.appendChild(n),this.#r[s.id]=c,this.#a[s.id]=n}),e}attributeChangedCallback(t,e,r){e===r||!this.#o||(t==="src"&&r&&r!==this.#y.url&&this._loadSrc(r),t==="src"&&!r&&this.#y.cancel(),t==="title"&&this.#g())}async _loadSrc(t){if(t)try{let e=await this.#y.fetchJson(t);if(!e)return;let{data:r,isCurrent:s}=e,a=[],n=(r.columns||[]).map(d=>{a.push((d.items||[]).map(u=>this.#p(u)));let c=d.wip!=null?parseInt(String(d.wip),10):null;return{id:String(d.id??""),label:d.label||Y(String(d.id??"")),wip:c!==null&&isNaN(c)?null:c,color:d.color||null}}),l=D(this,()=>{this.#t?.remove(),this.#n=n,this.#t=this.#m(a),this.#S(this.#t),this._postRender(),this.#w()},"kb-vt");if(l&&await l.updateCallbackDone,!s())return;this._emit("items-changed",{items:this.items},"src"),this.#u||this.#h()}catch(e){console.warn(`[kanban-board] Failed to load src="${t}":`,e)}}#p(t){let e;Mt(t)?e=gt(t,"minimal"):(e=document.createElement("article"),e.className="kb-card",e.textContent=t.text||t.label||t.title||""),e.setAttribute("draggable","true");let r=t.id||t.storyId;return r&&(e.dataset.id=String(r)),e}#f(){this.#c||(this.#c=`kb-${++i.#e}`)}#S(t){let e=this.#s;this.insertBefore(t,e?.parentNode?e:null)}#k(t){if(!t)return null;for(let[e,r]of Object.entries(this.#r))if(r===t)return e;return null}#$(t){let e=this.#r[t],r=this.#a[t];if(!e||!r)return;let s=e.querySelectorAll(':scope > [draggable="true"]').length,a=r.querySelector(".kb-count");a&&(a.textContent=String(s));let n=this.#n.find(o=>o.id===t);n?.wip!==null&&n?.wip!==void 0&&(s>n.wip?r.setAttribute("data-wip-exceeded",""):r.removeAttribute("data-wip-exceeded"))}#C(t){return this.#n.find(r=>r.id===t)?.label||Y(t)}};A("kanban-board",ce);var le=class i extends C{static get observedAttributes(){return["src","compact","title"]}static#e=0;#t=null;#r=null;#a={};#s=null;#i=null;#c="";#n=[];#d=new Map;#o=!1;#l=!1;#u=!1;#y=new z;setup(){if(this.#c||(this.#c=`sm-${++i.#e}`),!this.#o){this.#o=!0;let e=[...this.querySelectorAll(":scope > section[data-activity]")],r=e.map(s=>i.#E(s));for(let s of e)s.remove();this.#g(),this.#t=document.createElement("div"),this.#t.className="sm-scroll",this.#t.setAttribute("role","region"),this.#t.setAttribute("tabindex","0"),this.#s=ct("sm-live-region"),this.#b(r.map(s=>s.meta),r.map(s=>s.children)),this.append(this.#t,this.#s)}this.#l||(this.#l=!0,this.listen(this,"drag-surface:reorder",this.#x),this.listen(this,"drag-surface:transfer",this.#_));let t=this.getAttribute("src");if(t){t!==this.#y.url&&this._loadSrc(t);return}this.#u||this.#h()}teardown(){this.#l=!1}static#E(t){let e=t.getAttribute("data-activity")||"",r=t.getAttribute("data-activity-label")||Y(e),s=t.getAttribute("data-journey-phase")||null,a=[...t.children];return{meta:{id:e,label:r,journeyPhase:s},children:a}}#b(t,e){this.#n=t,this.#a={};let r=document.createElement("div");r.className="sm-columns",t.forEach((s,a)=>{let n=document.createElement("section");n.className="sm-column",n.setAttribute("data-activity-column",s.id);let o=document.createElement("header");o.className="sm-activity-header";let l=document.createElement("h3");l.textContent=s.label;let d=document.createElement("span");d.className="sm-activity-count",l.appendChild(d),o.appendChild(l),n.appendChild(o);let c=document.createElement("drag-surface");c.setAttribute("group",this.#c),c.setAttribute("aria-label",`${s.label} stories`),c.setAttribute("data-layout","stack"),c.setAttribute("data-layout-gap","xs");for(let u of e[a]||[])c.appendChild(u);n.appendChild(c),r.appendChild(n),this.#a[s.id]=c,this.#p(s.id),tt(c,"sm-empty","No stories yet")}),this.#r?.remove(),this.#r=r,this.#t?.appendChild(r),this.#t?.setAttribute("aria-label",this.getAttribute("title")||"Story map")}#g(){let t=this.getAttribute("title");t?(this.#i||(this.#i=document.createElement("h2"),this.#i.className="sm-title",this.prepend(this.#i)),this.#i.textContent=t):this.#i&&(this.#i.remove(),this.#i=null),this.#t?.setAttribute("aria-label",t||"Story map")}#h(){this.#u=!0;let t=0;for(let e of Object.values(this.#a))t+=e.querySelectorAll(':scope > [draggable="true"]').length;this.dispatchEvent(new CustomEvent("story-map:ready",{bubbles:!0,detail:{activityCount:this.#n.length,storyCount:t}}))}#x=t=>{let e=t.detail,r=t.target.closest("drag-surface"),s=this.#v(r);s&&(this.#p(s),this.dispatchEvent(new CustomEvent("story-map:reorder",{bubbles:!0,detail:{itemId:e.itemId,activity:s,oldIndex:e.oldIndex,newIndex:e.newIndex}})))};#_=t=>{let e=t.detail,r=e.fromSurface,s=e.toSurface,a=this.#v(r),n=this.#v(s);!a||!n||(this.#p(a),this.#p(n),tt(s,"sm-empty","No stories yet"),tt(r,"sm-empty","No stories yet"),bt(this.#s,`${lt(e.item)} moved from ${this.#m(a)} to ${this.#m(n)}`),this.dispatchEvent(new CustomEvent("story-map:transfer",{bubbles:!0,detail:{itemId:e.itemId,fromActivity:a,toActivity:n,newIndex:e.newIndex}})))};get activities(){return this.#n.map(t=>({id:t.id,label:t.label,journeyPhase:t.journeyPhase||void 0,stories:[...this.#a[t.id]?.querySelectorAll(':scope > [draggable="true"]')||[]].map(e=>this.#A(e))}))}set activities(t){let e=Array.isArray(t)?t:[];this.#d.clear();let r=[],s=e.map(a=>{let n=String(a.id??"");return r.push((a.stories||[]).map(o=>this.#w(o,void 0))),{id:n,label:a.label||Y(n),journeyPhase:a.journeyPhase||null}});if(this.#o)D(this,()=>this.#b(s,r),"sm-vt");else{for(let a of this.querySelectorAll(":scope > section[data-activity]"))a.remove();s.forEach((a,n)=>{let o=document.createElement("section");o.setAttribute("data-activity",a.id),o.setAttribute("data-activity-label",a.label),a.journeyPhase&&o.setAttribute("data-journey-phase",a.journeyPhase),o.append(...r[n]),this.appendChild(o)})}this.dispatchEvent(new CustomEvent("story-map:activities-changed",{detail:{activities:e,source:"property"},bubbles:!0}))}#w(t,e){let r=null,s=this;if(typeof s.renderStory=="function"){let l=s.renderStory(t);r=l instanceof Element?l:null}r||(r=gt(t,e));let a=r;a.hasAttribute("draggable")||a.setAttribute("draggable","true");let n=t.id??t.storyId;n!=null&&!a.hasAttribute("data-id")&&a.setAttribute("data-id",String(n));let o=a.getAttribute("data-id");return o&&this.#d.set(o,t),a}#A(t){let e=t.getAttribute("data-id")||void 0,r=e?this.#d.get(e):void 0;if(r)return{...r,id:r.id??e};let s=t.data;if(t.localName==="user-story"&&s&&typeof s=="object"){let a={id:e};for(let[n,o]of Object.entries(s))o!==void 0&&(a[n]=o);return a}return{id:e,storyId:t.getAttribute("story-id")||void 0,title:(t.querySelector('[slot="title"]')?.textContent||t.textContent||"").replace(/\s+/g," ").trim()||void 0}}attributeChangedCallback(t,e,r){e===r||!this.#o||(t==="src"&&r&&r!==this.#y.url&&this._loadSrc(r),t==="src"&&!r&&this.#y.cancel(),t==="title"&&this.#g())}async _loadSrc(t){if(t)try{let e=await this.#y.fetchJson(t);if(!e)return;let{data:r,isCurrent:s}=e;this.#d.clear();let a=[],n=(r.activities||[]).map(l=>{let d=String(l.id??"");return a.push((l.stories||[]).map(c=>this.#w(c,"compact"))),{id:d,label:l.label||Y(d),journeyPhase:l.journeyPhase||null}}),o=D(this,()=>this.#b(n,a),"sm-vt");if(o&&await o.updateCallbackDone,!s())return;this.dispatchEvent(new CustomEvent("story-map:activities-changed",{detail:{activities:this.activities,source:"src"},bubbles:!0})),this.#u||this.#h()}catch(e){console.warn(`[story-map] Failed to load src="${t}":`,e)}}#v(t){if(!t)return null;for(let[e,r]of Object.entries(this.#a))if(r===t)return e;return null}#m(t){return this.#n.find(e=>e.id===t)?.label||Y(t)}#p(t){let e=this.#a[t];if(!e)return;let r=e.querySelectorAll(':scope > [draggable="true"]').length,a=e.closest("[data-activity-column]")?.querySelector(".sm-activity-count");a&&(a.textContent=String(r))}};A("story-map",le);var We=`
1781
1808
  :host {
1782
1809
  display: block;
1783
1810
  position: relative;
@@ -2225,68 +2252,67 @@ var re=`
2225
2252
  /* \u2500\u2500 Utility \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500 */
2226
2253
  .state-msg { padding: var(--_space-l); font-size: var(--_font-sm); color: var(--_muted); font-style: italic; }
2227
2254
  .state-msg--error { color: var(--color-error-text, var(--color-error, #dc2626)); }
2228
- `;function Je(){let n=globalThis.localStorage;if(!n)throw new Error("VBStore: localStorage is not available in this environment");return{async getRaw(t){return n.getItem(t)},async setRaw(t,e){n.setItem(t,e)},async removeRaw(t){n.removeItem(t)},async keys(t){let e=[];for(let s=0;s<n.length;s++){let r=n.key(s);r&&r.startsWith(t)&&e.push(r)}return e}}}var at=null;function j(){return at||(at=Je()),at}function Nt(n,t){if(typeof n!="string"||!n)throw new TypeError("VBStore: namespace must be a non-empty string");if(typeof t!="string"||!t)throw new TypeError("VBStore: key must be a non-empty string");return`vb:${n}:${t}`}function ce(n){if(typeof n!="string"||!n)throw new TypeError("VBStore: namespace must be a non-empty string");return`vb:${n}:`}function le(n){try{let t=JSON.parse(n);if(t&&typeof t=="object"&&typeof t.timestamp=="number")return t}catch{}return null}var it={configure(n={}){at=n.backend??null},async set(n,t,e){let s={data:e,timestamp:Date.now()};await j().setRaw(Nt(n,t),JSON.stringify(s))},async get(n,t,e){let s=await j().getRaw(Nt(n,t));if(s==null)return null;let r=le(s);return!r||e?.maxAge!=null&&Date.now()-r.timestamp>e.maxAge?null:r.data},async remove(n,t){await j().removeRaw(Nt(n,t))},async list(n){let t=ce(n),e=await j().keys(t),s=[];for(let r of e){let a=await j().getRaw(r);if(a==null)continue;let i=le(a);i&&s.push({key:r.slice(t.length),data:i.data,timestamp:i.timestamp})}return s},async clear(n){let t=ce(n),e=await j().keys(t);for(let s of e)await j().removeRaw(s)},async clearAll(){let n=await j().keys("vb:");for(let t of n)await j().removeRaw(t)},async setMany(n,t){for(let[e,s]of t)await it.set(n,e,s)}};var Mt="[data-copy], [data-copy-target], [data-paste-target]",Ge="Copied to clipboard",Ze="Pasted from clipboard",Tt=new WeakMap;async function zt(n,t={}){if(n==null||n==="")return!1;let{button:e,announceMessage:s=Ge,duration:r=1500}=t;try{await navigator.clipboard.writeText(n)}catch{return!1}return ue({button:e,duration:r,announceMessage:s,eventDetail:{text:n}}),!0}function ue({button:n,duration:t,announceMessage:e,eventDetail:s,state:r="copied",eventName:a="copy"}){if(n){n.dataset.state=r;let i=Tt.get(n);i&&clearTimeout(i),Tt.set(n,setTimeout(()=>{delete n.dataset.state,Tt.delete(n)},t)),n.dispatchEvent(new CustomEvent(a,{bubbles:!0,detail:s}))}ss(e,n??document.body)}async function ts(n,t={}){let{button:e,announceMessage:s=Ze,duration:r=1500}=t,a;try{a=await navigator.clipboard.readText()}catch{return null}return n&&("value"in n&&(n instanceof HTMLInputElement||n instanceof HTMLTextAreaElement||n instanceof HTMLSelectElement)?n.value=a:n.textContent=a,n.dispatchEvent(new Event("input",{bubbles:!0}))),ue({button:e,duration:r,announceMessage:s,eventDetail:{text:a},state:"pasted",eventName:"paste"}),a}function de(n=document){n.querySelectorAll(Mt).forEach(Lt)}function Lt(n){n.hasAttribute("data-copy-init")||(n.setAttribute("data-copy-init",""),n.addEventListener("click",()=>{if(n.dataset.pasteTarget){let e=document.querySelector(n.dataset.pasteTarget);if(!e)return;ts(e,{button:n});return}let t=es(n);t&&zt(t,{button:n})}))}function es(n){if(n.dataset.copy)return n.dataset.copy;if(n.dataset.copyTarget){let t=document.querySelector(n.dataset.copyTarget);if(!t)return"";let e=n.dataset.copyAttr;return e?t.getAttribute(e)??"":t.textContent??""}return""}function ss(n,t){let e=document.createElement("div");e.setAttribute("role","status"),e.setAttribute("aria-live","polite"),e.className="visually-hidden",e.textContent=n,t.appendChild(e),setTimeout(()=>e.remove(),1e3)}document.readyState==="loading"?document.addEventListener("DOMContentLoaded",()=>de()):de();var rs=new MutationObserver(n=>{for(let t of n)for(let e of t.addedNodes){if(e.nodeType!==Node.ELEMENT_NODE)continue;let s=e;s.matches(Mt)&&Lt(s),s.querySelectorAll(Mt).forEach(r=>Lt(r))}});rs.observe(document.documentElement,{childList:!0,subtree:!0});var X=class{#e=new Map;async load(){return[...this.#e.values()]}async save(t){return t.id||(t.id=crypto.randomUUID()),this.#e.set(t.id,t),t}async update(t,e){let s=this.#e.get(t);if(!s)throw new Error(`Pin ${t} not found`);return Object.assign(s,e),s}async remove(t){this.#e.delete(t)}},nt=class{#e;constructor(t="default"){this.#e=t}async#t(){let t=await it.get("reviews",this.#e);return Array.isArray(t)?t:[]}async#s(t){await it.set("reviews",this.#e,t)}async load(){return this.#t()}async save(t){t.id||(t.id=crypto.randomUUID());let e=await this.#t();return e.push(t),await this.#s(e),t}async update(t,e){let s=await this.#t(),r=s.findIndex(a=>a.id===t);if(r===-1)throw new Error(`Pin ${t} not found`);return Object.assign(s[r],e),await this.#s(s),s[r]}async remove(t){let e=(await this.#t()).filter(s=>s.id!==t);await this.#s(e)}},ot=class{#e;constructor(t){if(!t)throw new Error("RestAdapter requires an endpoint URL");this.#e=t.replace(/\/$/,"")}async load(){let t=await fetch(this.#e);if(!t.ok)throw new Error(`HTTP ${t.status}`);let e=await t.json();return Array.isArray(e)?e:e.pins||[]}async save(t){let e=await fetch(this.#e,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify(t)});if(!e.ok)throw new Error(`HTTP ${e.status}`);return e.json()}async update(t,e){let s=await fetch(`${this.#e}/${encodeURIComponent(t)}`,{method:"PATCH",headers:{"Content-Type":"application/json"},body:JSON.stringify(e)});if(!s.ok)throw new Error(`HTTP ${s.status}`);return s.json()}async remove(t){let e=await fetch(`${this.#e}/${encodeURIComponent(t)}`,{method:"DELETE"});if(!e.ok)throw new Error(`HTTP ${e.status}`)}},Pt=class extends HTMLElement{static get observedAttributes(){return["src","editable","adapter","endpoint","storage-key","author","compact","show-resolved"]}#e=new Map;constructor(){super(),this.attachShadow({mode:"open"}),this.__pins=[],this.__adapter=null,this._activePin=null,this._annotating=!1}get pins(){return this.__pins}set pins(t){let e=Array.isArray(t)?t:[];this.__pins!==e&&(this.__pins=e,this.isConnected&&this._render(),this.dispatchEvent(new CustomEvent("review-surface:pins-changed",{detail:{pins:e,source:"property"},bubbles:!0,composed:!0})))}get adapter(){return this.__adapter}set adapter(t){this.__adapter=t,this.isConnected&&this._loadFromAdapter()}#t(){for(let t of this.children){let e=t.getAttribute("slot");e&&this.#e.set(e,t.textContent.trim())}}_resolve(t){return this.getAttribute(t)||this.#e.get(t)||""}connectedCallback(){this.#t(),this.setAttribute("data-upgraded",""),this.#s(),this.hasAttribute("src")?this._loadSrc(this.getAttribute("src")):this._loadFromAdapter()}disconnectedCallback(){this.removeAttribute("data-upgraded"),this.removeAttribute("data-annotating")}attributeChangedCallback(t){this.isConnected&&(t==="src"?this._loadSrc(this.getAttribute("src")):t==="adapter"||t==="endpoint"||t==="storage-key"?(this.#s(),this._loadFromAdapter()):this._render())}#s(){if(this.__adapter&&!(this.__adapter instanceof X)&&!(this.__adapter instanceof nt)&&!(this.__adapter instanceof ot))return;switch(this.getAttribute("adapter")||"memory"){case"local":this.__adapter=new nt(this.getAttribute("storage-key")||"default");break;case"rest":try{this.__adapter=new ot(this.getAttribute("endpoint")??"")}catch{this.__adapter=new X}break;default:this.__adapter=new X}}async _loadSrc(t){if(!(!t||!this.shadowRoot)){this.shadowRoot.innerHTML=`<style>${rt}</style><div class="state-msg">Loading\u2026</div>`;try{let e=await fetch(t);if(!e.ok)throw new Error(`HTTP ${e.status}`);let s=await e.json();this.__pins=Array.isArray(s)?s:s.pins||[],this._render()}catch(e){let s=e instanceof Error?e.message:String(e);this.shadowRoot.innerHTML=`<style>${rt}</style><div class="state-msg state-msg--error">Could not load pins: ${m(s)}</div>`}}}async _loadFromAdapter(){if(this.__adapter){try{this.__pins=await this.__adapter.load()}catch{this.__pins=[]}this._render()}}async addPin(t){let e={id:crypto.randomUUID(),x:Math.max(0,Math.min(100,t.x)),y:Math.max(0,Math.min(100,t.y)),text:t.text||"",author:t.author||this.getAttribute("author")||"Anonymous",createdAt:new Date().toISOString(),resolved:!1,resolvedBy:null,resolvedAt:null,replies:[]};return this.__adapter&&await this.__adapter.save(e),this.__pins.push(e),this._render(),this.#c(`Pin ${this.#i().length} added`),this.dispatchEvent(new CustomEvent("review-surface:add",{bubbles:!0,composed:!0,detail:{pin:e}})),e}async removePin(t){let e=this.__pins.find(s=>s.id===t);e&&(this.__adapter&&await this.__adapter.remove(t),this.__pins=this.__pins.filter(s=>s.id!==t),this._activePin===t&&(this._activePin=null),this._render(),this.#c("Pin removed"),this.dispatchEvent(new CustomEvent("review-surface:remove",{bubbles:!0,composed:!0,detail:{pin:e}})))}async resolvePin(t){let e=this.__pins.find(r=>r.id===t);if(!e)return;let s={resolved:!0,resolvedBy:this.getAttribute("author")||"Anonymous",resolvedAt:new Date().toISOString()};this.__adapter&&await this.__adapter.update(t,s),Object.assign(e,s),this._render(),this.#c("Pin resolved"),this.dispatchEvent(new CustomEvent("review-surface:resolve",{bubbles:!0,composed:!0,detail:{pin:e}}))}async unresolvePin(t){let e=this.__pins.find(r=>r.id===t);if(!e)return;let s={resolved:!1,resolvedBy:null,resolvedAt:null};this.__adapter&&await this.__adapter.update(t,s),Object.assign(e,s),this._render(),this.#c("Pin re-opened"),this.dispatchEvent(new CustomEvent("review-surface:update",{bubbles:!0,composed:!0,detail:{pin:e,changes:s}}))}exportPins(){return structuredClone(this.__pins)}importPins(t){this.__pins=Array.isArray(t)?structuredClone(t):[],this._activePin=null,this._render()}#i(){let t=this.hasAttribute("show-resolved");return this.__pins.filter(e=>t||!e.resolved).sort((e,s)=>new Date(e.createdAt??0).getTime()-new Date(s.createdAt??0).getTime())}_render(){if(!this.shadowRoot)return;let t=this.hasAttribute("editable"),e=this.#i(),s=this._activePin?this.__pins.find(r=>r.id===this._activePin):null;this.setAttribute("pin-count",String(e.length)),this.shadowRoot.innerHTML=`<style>${rt}</style>
2255
+ `;function Hr(){let i=globalThis.localStorage;if(!i)throw new Error("VBStore: localStorage is not available in this environment");return{async getRaw(t){return i.getItem(t)},async setRaw(t,e){i.setItem(t,e)},async removeRaw(t){i.removeItem(t)},async keys(t){let e=[];for(let r=0;r<i.length;r++){let s=i.key(r);s&&s.startsWith(t)&&e.push(s)}return e}}}var Dt=null;function K(){return Dt||(Dt=Hr()),Dt}function de(i,t){if(typeof i!="string"||!i)throw new TypeError("VBStore: namespace must be a non-empty string");if(typeof t!="string"||!t)throw new TypeError("VBStore: key must be a non-empty string");return`vb:${i}:${t}`}function Qe(i){if(typeof i!="string"||!i)throw new TypeError("VBStore: namespace must be a non-empty string");return`vb:${i}:`}function Ye(i){try{let t=JSON.parse(i);if(t&&typeof t=="object"&&typeof t.timestamp=="number")return t}catch{}return null}var Ot={configure(i={}){Dt=i.backend??null},async set(i,t,e){let r={data:e,timestamp:Date.now()};await K().setRaw(de(i,t),JSON.stringify(r))},async get(i,t,e){let r=await K().getRaw(de(i,t));if(r==null)return null;let s=Ye(r);return!s||e?.maxAge!=null&&Date.now()-s.timestamp>e.maxAge?null:s.data},async remove(i,t){await K().removeRaw(de(i,t))},async list(i){let t=Qe(i),e=await K().keys(t),r=[];for(let s of e){let a=await K().getRaw(s);if(a==null)continue;let n=Ye(a);n&&r.push({key:s.slice(t.length),data:n.data,timestamp:n.timestamp})}return r},async clear(i){let t=Qe(i),e=await K().keys(t);for(let r of e)await K().removeRaw(r)},async clearAll(){let i=await K().keys("vb:");for(let t of i)await K().removeRaw(t)},async setMany(i,t){for(let[e,r]of t)await Ot.set(i,e,r)}};var Ur="vb:copy",Vr="vb:paste",pe="[data-copy], [data-copy-target], [data-paste-target]",Wr="Copied to clipboard",Qr="Pasted from clipboard",ue=new WeakMap;async function me(i,t={}){if(i==null||i==="")return!1;let{button:e,announceMessage:r=Wr,duration:s=1500}=t;try{await navigator.clipboard.writeText(i)}catch{return!1}return Ke({button:e,duration:s,announceMessage:r,eventDetail:{text:i}}),!0}function Ke({button:i,duration:t,announceMessage:e,eventDetail:r,state:s="copied",eventName:a=Ur}){if(i){i.dataset.state=s;let n=ue.get(i);n&&clearTimeout(n),ue.set(i,setTimeout(()=>{delete i.dataset.state,ue.delete(i)},t)),i.dispatchEvent(new CustomEvent(a,{bubbles:!0,detail:r}))}Kr(e)}async function Yr(i,t={}){let{button:e,announceMessage:r=Qr,duration:s=1500}=t,a;try{a=await navigator.clipboard.readText()}catch{return null}return i&&("value"in i&&(i instanceof HTMLInputElement||i instanceof HTMLTextAreaElement||i instanceof HTMLSelectElement)?i.value=a:i.textContent=a,i.dispatchEvent(new Event("input",{bubbles:!0}))),Ke({button:e,duration:s,announceMessage:r,eventDetail:{text:a},state:"pasted",eventName:Vr}),a}function Xe(i=document){i.querySelectorAll(pe).forEach(he)}function he(i){i.hasAttribute("data-copy-init")||(i.setAttribute("data-copy-init",""),i.addEventListener("click",()=>{if(i.dataset.pasteTarget){let e=document.querySelector(i.dataset.pasteTarget);if(!e)return;Yr(e,{button:i});return}let t=Xr(i);t&&me(t,{button:i})}))}function Xr(i){if(i.dataset.copy)return i.dataset.copy;if(i.dataset.copyTarget){let t=document.querySelector(i.dataset.copyTarget);if(!t)return"";let e=i.dataset.copyAttr;return e?t.getAttribute(e)??"":t.textContent??""}return""}var Je;function Jr(){let i=document.querySelector("body > [data-vb-clipboard-status]");return i||(i=document.createElement("div"),i.setAttribute("data-vb-clipboard-status",""),i.setAttribute("role","status"),i.setAttribute("aria-live","polite"),i.setAttribute("aria-atomic","true"),i.style.cssText="position:absolute;inline-size:1px;block-size:1px;margin:-1px;padding:0;overflow:hidden;clip-path:inset(50%);white-space:nowrap;border:0;",document.body.appendChild(i),i)}function Kr(i){if(!document.body)return;let t=Jr();t.textContent="",requestAnimationFrame(()=>{t.textContent=i,clearTimeout(Je),Je=setTimeout(()=>{t.textContent===i&&(t.textContent="")},5e3)})}document.readyState==="loading"?document.addEventListener("DOMContentLoaded",()=>Xe()):Xe();var Gr=new MutationObserver(i=>{for(let t of i)for(let e of t.addedNodes){if(e.nodeType!==Node.ELEMENT_NODE)continue;let r=e;r.matches(pe)&&he(r),r.querySelectorAll(pe).forEach(s=>he(s))}});Gr.observe(document.documentElement,{childList:!0,subtree:!0});var At=class{#e=new Map;async load(){return[...this.#e.values()]}async save(t){return t.id||(t.id=crypto.randomUUID()),this.#e.set(t.id,t),t}async update(t,e,r){let s=this.#e.get(t)??{...r??{},id:t};return Object.assign(s,e),this.#e.set(t,s),s}async remove(t){this.#e.delete(t)}},jt=class{#e;constructor(t="default"){this.#e=t}async#t(){let t=await Ot.get("reviews",this.#e);return Array.isArray(t)?t:[]}async#r(t){await Ot.set("reviews",this.#e,t)}async load(){return this.#t()}async save(t){t.id||(t.id=crypto.randomUUID());let e=await this.#t();return e.push(t),await this.#r(e),t}async update(t,e,r){let s=await this.#t(),a=s.findIndex(n=>n.id===t);return a===-1&&(a=s.push({...r??{},id:t})-1),Object.assign(s[a],e),await this.#r(s),s[a]}async remove(t){let e=(await this.#t()).filter(r=>r.id!==t);await this.#r(e)}},Ft=class{#e;constructor(t){if(!t)throw new Error("RestAdapter requires an endpoint URL");this.#e=t.replace(/\/$/,"")}async load(){let t=await fetch(this.#e);if(!t.ok)throw new Error(`HTTP ${t.status}`);let e=await t.json();return Array.isArray(e)?e:e.pins||[]}async save(t){let e=await fetch(this.#e,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify(t)});if(!e.ok)throw new Error(`HTTP ${e.status}`);return e.json()}async update(t,e){let r=await fetch(`${this.#e}/${encodeURIComponent(t)}`,{method:"PATCH",headers:{"Content-Type":"application/json"},body:JSON.stringify(e)});if(!r.ok)throw new Error(`HTTP ${r.status}`);return r.json()}async remove(t){let e=await fetch(`${this.#e}/${encodeURIComponent(t)}`,{method:"DELETE"});if(!e.ok)throw new Error(`HTTP ${e.status}`)}},vt=i=>{let t=Number(i);return Number.isFinite(t)?Math.max(0,Math.min(100,t)):0},fe=class extends HTMLElement{static get observedAttributes(){return["src","editable","adapter","endpoint","storage-key","author","compact","show-resolved"]}#e=!1;#t=!1;#r=!1;#a=!1;#s=0;#i=new z;#c;#n;#d;#o;#l;constructor(){super();let t=this.attachShadow({mode:"open"});t.innerHTML=`<style>${We}</style>
2256
+ <div class="rs-status state-msg" hidden></div>
2229
2257
  <div class="rs-container">
2230
2258
  <slot></slot>
2231
- <div class="rs-overlay" role="img" aria-label="Review annotation surface">
2232
- ${e.map((r,a)=>this._renderPin(r,a+1)).join("")}
2233
- </div>
2234
- ${s?this._renderPopover(s,t):""}
2259
+ <div class="rs-overlay" role="group" aria-label="Review pins"></div>
2260
+ <div class="rs-popover-host" style="display:contents"></div>
2235
2261
  </div>
2236
- ${t?this._renderToolbar(e.length):""}
2237
- <div class="rs-live" aria-live="polite" aria-atomic="true"></div>`,this._bindListeners(t),this.dispatchEvent(new CustomEvent("review-surface:ready",{bubbles:!0,composed:!0,detail:{pinCount:e.length}}))}_renderPin(t,e){let s=t.text?t.text.slice(0,50):"Empty pin";return`<button class="rs-pin"
2238
- data-pin-id="${m(t.id)}"
2262
+ <div class="rs-toolbar-host" style="display:contents"></div>
2263
+ <div class="rs-live" role="status" aria-live="polite" aria-atomic="true"></div>`;let e=r=>t.querySelector(r);this.#o=e(".rs-status"),this.#c=e(".rs-overlay"),this.#n=e(".rs-popover-host"),this.#d=e(".rs-toolbar-host"),this.#l=e(".rs-live"),t.addEventListener("click",r=>this.#w(r)),t.addEventListener("keydown",r=>this.#A(r)),this.__pins=[],this.__adapter=null,this._activePin=null,this._annotating=!1}get pins(){return this.__pins}set pins(t){let e=Array.isArray(t)?t:[];this.__pins!==e&&(this.__pins=e,this.#a=!0,this.#i.cancel(),this.#s++,this.#t=!0,this.#e&&this._render(),this.dispatchEvent(new CustomEvent("review-surface:pins-changed",{detail:{pins:e,source:"property"},bubbles:!0,composed:!0})))}get adapter(){return this.__adapter}set adapter(t){this.__adapter=t,this.#e&&this.isConnected&&this._loadFromAdapter()}connectedCallback(){if(this.setAttribute("data-upgraded",""),this.#e){this._render();return}this.#e=!0,this.__adapter||this.#u(),this.dispatchEvent(new CustomEvent("review-surface:upgraded",{bubbles:!0,composed:!0})),this.#a?(this.#t=!0,this._render()):this.hasAttribute("src")?this._loadSrc(this.getAttribute("src")):this._loadFromAdapter()}disconnectedCallback(){this.removeAttribute("data-upgraded"),this.removeAttribute("data-annotating"),this._annotating=!1}attributeChangedCallback(t){if(!(!this.#e||!this.isConnected))if(t==="src"){let e=this.getAttribute("src");e?this._loadSrc(e):this.#i.cancel()&&this._loadFromAdapter()}else t==="adapter"||t==="endpoint"||t==="storage-key"?(this.#u(),this._loadFromAdapter()):this._render()}#u(){if(this.__adapter&&!(this.__adapter instanceof At)&&!(this.__adapter instanceof jt)&&!(this.__adapter instanceof Ft))return;switch(this.getAttribute("adapter")||"memory"){case"local":this.__adapter=new jt(this.getAttribute("storage-key")||"default");break;case"rest":try{this.__adapter=new Ft(this.getAttribute("endpoint")??"")}catch{this.__adapter=new At}break;default:this.__adapter=new At}}async _loadSrc(t){if(!t)return;this.#s++,this.#y("Loading\u2026");let e;try{e=await this.#i.fetchJson(t)}catch(s){let a=s instanceof Error?s.message:String(s);this.#y(`Could not load pins: ${a}`,!0);return}if(!e)return;let{data:r}=e;this.__pins=Array.isArray(r)?r:r?.pins||[],this.#t=!0,this._render()}async _loadFromAdapter(){if(!this.__adapter)return;this.#i.cancel();let t=++this.#s,e;try{e=await this.__adapter.load()}catch{e=[]}t===this.#s&&(this.__pins=Array.isArray(e)?e:[],this.#t=!0,this._render())}#y(t,e=!1){this.#o.textContent=t,this.#o.classList.toggle("state-msg--error",e),this.#o.hidden=!1}async addPin(t){let e={id:crypto.randomUUID(),x:vt(t.x),y:vt(t.y),text:t.text||"",author:t.author||this.getAttribute("author")||"Anonymous",createdAt:new Date().toISOString(),resolved:!1,resolvedBy:null,resolvedAt:null,replies:[]};return this.__adapter&&await this.__adapter.save(e),this.__pins.push(e),this._render(),this.#k(`Pin ${this.#E().length} added`),this.dispatchEvent(new CustomEvent("review-surface:add",{bubbles:!0,composed:!0,detail:{pin:e}})),e}async removePin(t){let e=this.__pins.find(r=>r.id===t);e&&(this.__adapter&&await this.__adapter.remove(t),this.__pins=this.__pins.filter(r=>r.id!==t),this._activePin===t&&(this._activePin=null),this._render(),this.#k("Pin removed"),this.dispatchEvent(new CustomEvent("review-surface:remove",{bubbles:!0,composed:!0,detail:{pin:e}})))}async resolvePin(t){let e=this.__pins.find(s=>s.id===t);if(!e)return;let r={resolved:!0,resolvedBy:this.getAttribute("author")||"Anonymous",resolvedAt:new Date().toISOString()};this.__adapter&&await this.__adapter.update(t,r,e),Object.assign(e,r),this._render(),this.#k("Pin resolved"),this.dispatchEvent(new CustomEvent("review-surface:resolve",{bubbles:!0,composed:!0,detail:{pin:e}}))}async unresolvePin(t){let e=this.__pins.find(s=>s.id===t);if(!e)return;let r={resolved:!1,resolvedBy:null,resolvedAt:null};this.__adapter&&await this.__adapter.update(t,r,e),Object.assign(e,r),this._render(),this.#k("Pin re-opened"),this.dispatchEvent(new CustomEvent("review-surface:update",{bubbles:!0,composed:!0,detail:{pin:e,changes:r}}))}exportPins(){return structuredClone(this.__pins)}importPins(t){this.__pins=Array.isArray(t)?structuredClone(t):[],this.#i.cancel(),this.#s++,this.#t=!0,this._activePin=null,this._render()}#E(){let t=this.hasAttribute("show-resolved");return this.__pins.filter(e=>t||!e.resolved).sort((e,r)=>new Date(e.createdAt??0).getTime()-new Date(r.createdAt??0).getTime())}_render(){let t=this.hasAttribute("editable"),e=this.#E(),r=this._activePin?this.__pins.find(a=>a.id===this._activePin):null;this._activePin&&!r&&(this._activePin=null),this.setAttribute("pin-count",String(e.length));let s=this.#b();this.#o.hidden=!0,this.#c.innerHTML=e.map((a,n)=>this._renderPin(a,n+1)).join(""),this.#n.innerHTML=r?this._renderPopover(r,t):"",this.#d.innerHTML=t?this._renderToolbar(e.length):"",this.#g(s),this.#t&&!this.#r&&(this.#r=!0,this.dispatchEvent(new CustomEvent("review-surface:ready",{bubbles:!0,composed:!0,detail:{pinCount:e.length}})))}#b(){let t=this.shadowRoot?.activeElement??null;if(!t)return null;let e=!!t.closest(".rs-popover"),r="";t.classList.contains("rs-pin")?r=`.rs-pin[data-pin-id="${CSS.escape(t.dataset.pinId??"")}"]`:t.dataset.action?r=`[data-action="${CSS.escape(t.dataset.action)}"]`:t.classList.contains("rs-input__field")?r=".rs-input__field":t.classList.contains("rs-popover")&&(r=".rs-popover");let s=t instanceof HTMLTextAreaElement?t.value:void 0;return{selector:r,value:s,inPopover:e}}#g(t){if(!t)return;let e=this.shadowRoot,r=t.selector?e.querySelector(t.selector):null;r instanceof HTMLTextAreaElement&&t.value!==void 0&&(r.value=t.value),!r&&t.inPopover&&(r=e.querySelector(".rs-popover")),r||(r=this.#h(this._activePin)??e.querySelector('[data-action="toggle-mode"]')),r?.focus()}#h(t){return t?this.shadowRoot?.querySelector(`.rs-pin[data-pin-id="${CSS.escape(t)}"]`)??null:null}#x(t){this._activePin=t,this._render(),(this.shadowRoot?.querySelector(".rs-popover")??null)?.focus(),this.dispatchEvent(new CustomEvent("review-surface:select",{bubbles:!0,composed:!0,detail:{pin:this.__pins.find(e=>e.id===t)}}))}#_(){let t=this._activePin;this._activePin=null,this._render(),this.#h(t)?.focus()}_renderPin(t,e){let r=t.text?String(t.text).slice(0,50):"Empty pin";return`<button type="button" class="rs-pin"
2264
+ data-pin-id="${p(t.id)}"
2239
2265
  ${t.resolved?"data-resolved":""}
2240
2266
  ${this._activePin===t.id?"data-active":""}
2241
- style="left:${t.x}%;top:${t.y}%"
2242
- aria-label="Pin ${e}: ${m(s)}"
2267
+ style="left:${vt(t.x)}%;top:${vt(t.y)}%"
2268
+ aria-label="Pin ${e}: ${p(r)}"
2243
2269
  aria-expanded="${this._activePin===t.id}"
2244
2270
  aria-haspopup="dialog">
2245
2271
  <span class="rs-pin__number">${e}</span>
2246
- </button>`}_renderPopover(t,e){let s=this.#i().findIndex(r=>r.id===t.id)+1;return`<div class="rs-popover" data-open
2247
- style="left:${Math.min(t.x,70)}%;top:${t.y}%"
2272
+ </button>`}_renderPopover(t,e){let r=this.#E().findIndex(a=>a.id===t.id)+1,s=r>0?`Pin ${r}`:"Pin";return`<div class="rs-popover" data-open tabindex="-1"
2273
+ style="left:${Math.min(vt(t.x),70)}%;top:${vt(t.y)}%"
2248
2274
  role="dialog"
2249
- aria-labelledby="rs-popover-title-${m(t.id)}">
2275
+ aria-labelledby="rs-popover-title-${p(t.id)}">
2250
2276
 
2251
2277
  <div class="rs-popover__header">
2252
- <span class="rs-popover__title" id="rs-popover-title-${m(t.id)}">
2253
- Pin ${s}
2254
- ${t.resolved?`<span class="rs-resolved-badge">${k(E.checkCircle)} Resolved</span>`:""}
2278
+ <span class="rs-popover__title" id="rs-popover-title-${p(t.id)}">
2279
+ ${s}
2280
+ ${t.resolved?`<span class="rs-resolved-badge">${S(q.checkCircle)} Resolved</span>`:""}
2255
2281
  </span>
2256
2282
  <div class="rs-popover__actions">
2257
2283
  ${e&&!t.resolved?`
2258
- <button class="rs-popover__btn rs-popover__btn--resolve" data-action="resolve" data-pin-id="${m(t.id)}"
2259
- aria-label="Resolve pin" title="Resolve">${k(E.checkCircle)}</button>`:""}
2284
+ <button type="button" class="rs-popover__btn rs-popover__btn--resolve" data-action="resolve" data-pin-id="${p(t.id)}"
2285
+ aria-label="Resolve pin" title="Resolve">${S(q.checkCircle)}</button>`:""}
2260
2286
  ${e&&t.resolved?`
2261
- <button class="rs-popover__btn" data-action="unresolve" data-pin-id="${m(t.id)}"
2262
- aria-label="Re-open pin" title="Re-open">${k(E.messageCircle)}</button>`:""}
2287
+ <button type="button" class="rs-popover__btn" data-action="unresolve" data-pin-id="${p(t.id)}"
2288
+ aria-label="Re-open pin" title="Re-open">${S(q.messageCircle)}</button>`:""}
2263
2289
  ${e?`
2264
- <button class="rs-popover__btn rs-popover__btn--delete" data-action="delete" data-pin-id="${m(t.id)}"
2265
- aria-label="Delete pin" title="Delete">${k(E.x)}</button>`:""}
2266
- <button class="rs-popover__btn" data-action="close"
2267
- aria-label="Close">${k(E.x)}</button>
2290
+ <button type="button" class="rs-popover__btn rs-popover__btn--delete" data-action="delete" data-pin-id="${p(t.id)}"
2291
+ aria-label="Delete pin" title="Delete">${S(q.x)}</button>`:""}
2292
+ <button type="button" class="rs-popover__btn" data-action="close"
2293
+ aria-label="Close">${S(q.x)}</button>
2268
2294
  </div>
2269
2295
  </div>
2270
2296
 
2271
2297
  <div class="rs-comment">
2272
2298
  <div class="rs-comment__meta">
2273
- <span class="rs-comment__avatar" style="background:${B(t.author||"Anonymous")}">${O(t.author||"Anonymous")}</span>
2274
- <span class="rs-comment__author">${m(t.author||"Anonymous")}</span>
2275
- <span class="rs-comment__time">${this.#o(t.createdAt)}</span>
2299
+ <span class="rs-comment__avatar" style="background:${it(t.author||"Anonymous")}">${p(at(t.author||"Anonymous"))}</span>
2300
+ <span class="rs-comment__author">${p(t.author||"Anonymous")}</span>
2301
+ <span class="rs-comment__time">${p(this.#S(t.createdAt))}</span>
2276
2302
  </div>
2277
- <div class="rs-comment__text">${m(t.text)}</div>
2303
+ <div class="rs-comment__text">${p(t.text)}</div>
2278
2304
  </div>
2279
2305
 
2280
2306
  ${t.replies?.length?`
2281
2307
  <div class="rs-replies">
2282
- ${t.replies.map(r=>`
2308
+ ${t.replies.map(a=>`
2283
2309
  <div class="rs-reply">
2284
2310
  <div class="rs-comment__meta">
2285
- <span class="rs-comment__avatar" style="background:${B(r.author||"Anonymous")}">${O(r.author||"Anonymous")}</span>
2286
- <span class="rs-comment__author">${m(r.author||"Anonymous")}</span>
2287
- <span class="rs-comment__time">${this.#o(r.createdAt)}</span>
2311
+ <span class="rs-comment__avatar" style="background:${it(a.author||"Anonymous")}">${p(at(a.author||"Anonymous"))}</span>
2312
+ <span class="rs-comment__author">${p(a.author||"Anonymous")}</span>
2313
+ <span class="rs-comment__time">${p(this.#S(a.createdAt))}</span>
2288
2314
  </div>
2289
- <div class="rs-comment__text">${m(r.text)}</div>
2315
+ <div class="rs-comment__text">${p(a.text)}</div>
2290
2316
  </div>
2291
2317
  `).join("")}
2292
2318
  </div>`:""}
@@ -2294,23 +2320,23 @@ var re=`
2294
2320
  ${e?`
2295
2321
  <div class="rs-input">
2296
2322
  <textarea class="rs-input__field" placeholder="Reply\u2026" rows="1"
2297
- aria-label="Reply to pin ${s}"></textarea>
2298
- <button class="rs-input__submit" data-action="reply" data-pin-id="${m(t.id)}"
2299
- aria-label="Send reply">${k(E.send)}</button>
2323
+ aria-label="Reply to ${s.toLowerCase()}"></textarea>
2324
+ <button type="button" class="rs-input__submit" data-action="reply" data-pin-id="${p(t.id)}"
2325
+ aria-label="Send reply">${S(q.send)}</button>
2300
2326
  </div>`:""}
2301
2327
 
2302
2328
  </div>`}_renderToolbar(t){return`<div class="rs-toolbar" role="toolbar" aria-label="Review tools">
2303
- <button class="rs-toolbar__btn" data-action="toggle-mode"
2329
+ <button type="button" class="rs-toolbar__btn" data-action="toggle-mode"
2304
2330
  aria-pressed="${this._annotating}"
2305
2331
  title="Toggle annotate mode">
2306
- ${k(E.mapPin)} Annotate
2332
+ ${S(q.mapPin)} Annotate
2307
2333
  </button>
2308
- <button class="rs-toolbar__btn" data-action="export"
2334
+ <button type="button" class="rs-toolbar__btn" data-action="export"
2309
2335
  title="Export pins as JSON">
2310
- ${k(E.download)} Export
2336
+ ${S(q.download)} Export
2311
2337
  </button>
2312
2338
  <output class="rs-toolbar__count">${t} pin${t!==1?"s":""}</output>
2313
- </div>`}_bindListeners(t){let e=this.shadowRoot;if(!e)return;e.querySelectorAll(".rs-pin").forEach(a=>{a.addEventListener("click",i=>{i.stopPropagation();let o=a.dataset.pinId??null;this._activePin=this._activePin===o?null:o,this._render(),this._activePin&&this.dispatchEvent(new CustomEvent("review-surface:select",{bubbles:!0,composed:!0,detail:{pin:this.__pins.find(c=>c.id===o)}}))})});let s=e.querySelector(".rs-overlay");s&&t&&s.addEventListener("click",a=>{if(!this._annotating)return;let i=a;if(i.target?.closest(".rs-pin"))return;let c=s.getBoundingClientRect(),d=(i.clientX-c.left)/c.width*100,l=(i.clientY-c.top)/c.height*100;this.#r(d,l)}),e.querySelectorAll("[data-action]").forEach(a=>{a.addEventListener("click",i=>{i.stopPropagation();let o=a.dataset.action,c=a.dataset.pinId;switch(o){case"close":this._activePin=null,this._render();break;case"resolve":c&&this.resolvePin(c);break;case"unresolve":c&&this.unresolvePin(c);break;case"delete":c&&this.removePin(c);break;case"toggle-mode":this._annotating=!this._annotating,this._annotating?this.setAttribute("data-annotating",""):this.removeAttribute("data-annotating"),this._render(),this.dispatchEvent(new CustomEvent("review-surface:mode",{bubbles:!0,composed:!0,detail:{mode:this._annotating?"annotate":"view"}}));break;case"export":this.#a();break;case"reply":this.#n(c);break}})});let r=e.querySelector(".rs-input__field");r&&r.addEventListener("keydown",a=>{let i=a;if(i.key==="Enter"&&!i.shiftKey){i.preventDefault();let c=e.querySelector('[data-action="reply"]')?.dataset.pinId;c&&this.#n(c)}}),e.addEventListener("keydown",a=>{a.key==="Escape"&&(this._activePin?(this._activePin=null,this._render()):this._annotating&&(this._annotating=!1,this.removeAttribute("data-annotating"),this._render(),this.dispatchEvent(new CustomEvent("review-surface:mode",{bubbles:!0,composed:!0,detail:{mode:"view"}}))))})}async#r(t,e){let s=this.getAttribute("author")||"Anonymous",r=await this.addPin({x:t,y:e,text:"",author:s});this._activePin=r.id,this._render(),requestAnimationFrame(()=>{(this.shadowRoot?.querySelector(".rs-input__field")??null)?.focus()})}async#n(t){let e=this.shadowRoot?.querySelector(".rs-input__field")??null;if(!e)return;let s=e.value.trim();if(!s)return;let r=this.__pins.find(i=>i.id===t);if(!r)return;let a={id:crypto.randomUUID(),text:s,author:this.getAttribute("author")||"Anonymous",createdAt:new Date().toISOString()};r.replies||(r.replies=[]),r.text?(r.replies.push(a),this.__adapter&&await this.__adapter.update(t,{replies:r.replies})):(r.text=s,this.__adapter&&await this.__adapter.update(t,{text:s})),this._render(),this.#c("Reply added"),requestAnimationFrame(()=>{(this.shadowRoot?.querySelector(".rs-input__field")??null)?.focus()}),this.dispatchEvent(new CustomEvent("review-surface:update",{bubbles:!0,composed:!0,detail:{pin:r,changes:{replies:r.replies}}}))}async#a(){let t=JSON.stringify(this.exportPins(),null,2);if(await zt(t,{announceMessage:"Pins copied to clipboard"}))return;let s=new Blob([t],{type:"application/json"}),r=URL.createObjectURL(s),a=document.createElement("a");a.href=r,a.download="review-pins.json",a.click(),URL.revokeObjectURL(r),this.#c("Pins exported as file")}#o(t){if(!t)return"";try{let e=new Date(t),r=new Date().getTime()-e.getTime(),a=Math.floor(r/6e4);if(a<1)return"just now";if(a<60)return`${a}m ago`;let i=Math.floor(a/60);if(i<24)return`${i}h ago`;let o=Math.floor(i/24);return o<7?`${o}d ago`:e.toLocaleDateString()}catch{return""}}#c(t){let e=this.shadowRoot?.querySelector(".rs-live");e&&(e.textContent=t)}};w("review-surface",Pt);var H=864e5,jt=H*7,ct=H*30,as=H*91,he=H*365;function Y(n){return typeof n=="number"?n:new Date(n).getTime()}function is(n){return n<=jt*3?t=>t.toLocaleDateString(void 0,{month:"short",day:"numeric"}):n<=ct*3?t=>t.toLocaleDateString(void 0,{month:"short",day:"numeric"}):n<=he?t=>t.toLocaleDateString(void 0,{month:"short",year:"2-digit"}):t=>t.toLocaleDateString(void 0,{year:"numeric"})}function ns(n){return n<=jt*3?"day":n<=ct*3?"week":n<=he?"month":"quarter"}function pe(n){return String(n).replace(/&/g,"&amp;").replace(/</g,"&lt;").replace(/>/g,"&gt;").replace(/"/g,"&quot;")}var Rt=class n extends C{static get observedAttributes(){return["src","title","view","show-today","show-progress","show-dependencies","compact"]}#e=null;#t=null;#s=null;#i=[];#r=0;#n=0;#a=0;setup(){let t=this.querySelector(":scope > table");return!t||(this.#i=this.#p(t),this.#i.length===0)?!1:(this.#r=Math.min(...this.#i.map(e=>e.start)),this.#n=Math.max(...this.#i.map(e=>e.end)),this.#a=this.#n-this.#r,this.#a<=0&&(this.#a=H),this.#l(t),this.dispatchEvent(new CustomEvent("gantt-chart:ready",{bubbles:!0,detail:{taskCount:this.#i.length,dateRange:{start:new Date(this.#r).toISOString(),end:new Date(this.#n).toISOString()}}})),!0)}teardown(){this.#s&&(this.#s.remove(),this.#s=null),this.#e&&(this.#e.remove(),this.#e=null),this.#t&&(this.#t.remove(),this.#t=null);let t=this.querySelector("table.gc-sr-only");t&&t.classList.remove("gc-sr-only"),this.#i=[]}static#o=0;attributeChangedCallback(t,e,s){e===s||!this.isConnected||(t==="src"?this._loadSrc(s):this.hasAttribute("data-upgraded")&&this.#c())}#c(){let t=()=>{this.teardown(),this.removeAttribute("data-upgraded"),this.setup()};if(this.hasAttribute("data-upgraded")&&"startViewTransition"in document&&!matchMedia("(prefers-reduced-motion: reduce)").matches){let e=`gc-vt-${++n.#o}`;this.style.viewTransitionName=e,document.startViewTransition(t).finished.finally(()=>{this.style.viewTransitionName=""})}else t()}get tasks(){return this.#i}set tasks(t){let e=(t||[]).map((s,r)=>({id:s.id??`gc-task-${r}`,name:s.name??`Task ${r+1}`,start:typeof s.start=="number"?s.start:Y(s.start),end:typeof s.end=="number"?s.end:s.end!=null?Y(s.end):typeof s.start=="number"?s.start:Y(s.start),progress:s.progress??0,group:s.group??null,depends:Array.isArray(s.depends)?s.depends:s.depends?String(s.depends).split(",").map(a=>a.trim()):[],status:s.status??null,assignee:s.assignee??null,milestone:!!s.milestone,color:s.color??null,storyIds:s.storyIds??[],itemIds:s.itemIds??[]}));if((this.#e||this.#s||this.#t)&&(this.#s&&(this.#s.remove(),this.#s=null),this.#e&&(this.#e.remove(),this.#e=null),this.#t&&(this.#t.remove(),this.#t=null)),this.#i=e,e.length>0){this.#r=Math.min(...e.map(r=>r.start)),this.#n=Math.max(...e.map(r=>r.end)),this.#a=this.#n-this.#r,this.#a<=0&&(this.#a=H);let s=this.querySelector(":scope > table");s||(s=document.createElement("table"),s.classList.add("gc-sr-only"),this.appendChild(s)),this.#l(s)}this.dispatchEvent(new CustomEvent("gantt-chart:tasks-changed",{detail:{tasks:e,source:"property"},bubbles:!0}))}#p(t){let e=t.querySelectorAll("tbody tr"),s=[];for(let r=0;r<e.length;r++){let a=e[r],i=a.querySelectorAll("time[datetime]");if(i.length<2&&!a.hasAttribute("data-milestone"))continue;let o=i[0]?.getAttribute("datetime"),c=i.length>1?i[1].getAttribute("datetime"):o;if(!o)continue;let d=a.querySelector("progress"),l=d?d.value/(d.max||100):0,u=a.cells[0]?.textContent?.trim()||`Task ${r+1}`;s.push({id:a.dataset.taskId||`gc-task-${r}`,name:u,start:Y(o),end:Y(c),progress:l,group:a.dataset.group||null,depends:a.dataset.depends?a.dataset.depends.split(",").map(p=>p.trim()):[],status:a.dataset.status||null,assignee:a.dataset.assignee||null,milestone:a.hasAttribute("data-milestone"),color:a.dataset.color||null,storyIds:a.dataset.storyIds?a.dataset.storyIds.split(",").map(p=>p.trim()):[],itemIds:a.dataset.itemIds?a.dataset.itemIds.split(",").map(p=>p.trim()):[]})}return s}#l(t){let e=this.getAttribute("title"),s=this.hasAttribute("show-today"),r=this.hasAttribute("show-progress"),a=this.hasAttribute("show-dependencies");e&&(this.#s=document.createElement("h2"),this.#s.className="gc-title",this.#s.textContent=e,this.insertBefore(this.#s,t)),this.#e=document.createElement("div"),this.#e.className="gc-container",this.#e.setAttribute("role","region"),this.#e.setAttribute("aria-label",`Gantt chart${e?": "+e:""}`);let i=this.#u();this.#e.appendChild(i);let o=document.createElement("div");o.className="gc-body";let c=document.createElement("div");c.className="gc-task-list";let d=document.createElement("div");d.className="gc-bars";let l=this.#g();d.appendChild(l);let u=this.#b();for(let[p,h]of u){if(u.size>1&&p){let f=document.createElement("div");f.className="gc-group-header";let b=document.createElement("span");b.className="gc-group-label",b.textContent=p,f.appendChild(b),c.appendChild(f);let v=document.createElement("div");v.className="gc-group-spacer",d.appendChild(v)}for(let f of h){let b=document.createElement("div");b.className="gc-task-row",b.setAttribute("data-task-id",f.id);let v=document.createElement("span");v.className="gc-task-name",v.textContent=f.name,b.appendChild(v);let x=document.createElement("span");x.className="gc-task-dates",x.textContent=`${new Date(f.start).toLocaleDateString()} to ${new Date(f.end).toLocaleDateString()}`,b.appendChild(x),c.appendChild(b);let _=document.createElement("div");_.className="gc-bar-row",f.milestone?_.appendChild(this.#d(f)):_.appendChild(this.#v(f,r)),d.appendChild(_)}}if(s){let p=this.#h();p&&d.appendChild(p)}a&&requestAnimationFrame(()=>{let p=this.#y(d);p&&d.appendChild(p)}),o.appendChild(c),o.appendChild(d),this.#e.appendChild(o),this.insertBefore(this.#e,t),t.classList.add("gc-sr-only"),this.#t=document.createElement("div"),this.#t.className="gc-sr-only",this.#t.setAttribute("role","status"),this.#t.setAttribute("aria-live","polite"),this.#t.setAttribute("aria-atomic","true"),this.appendChild(this.#t),this.listen(this.#e,"click",p=>{let h=p.target.closest(".gc-bar, .gc-milestone");if(!h)return;let f=h.dataset.taskId,b=this.#i.find(v=>v.id===f);b&&(this.#w(`Selected: ${b.name}`),this.dispatchEvent(new CustomEvent("gantt-chart:task-click",{bubbles:!0,detail:{task:b}})))}),this.listen(this.#e,"keydown",p=>{let h=p;if(h.key==="Enter"||h.key===" "){let f=h.target.closest(".gc-bar, .gc-milestone");f&&(h.preventDefault(),f.click())}})}#u(){let t=document.createElement("div");t.className="gc-timeline-header";let e=document.createElement("div");e.className="gc-timeline-spacer",t.appendChild(e);let s=document.createElement("div");s.className="gc-timeline-dates";let r=this.#m();for(let{position:a,text:i}of r){let o=document.createElement("span");o.className="gc-date-label",o.style.left=`${a}%`,o.textContent=i,s.appendChild(o)}return t.appendChild(s),t}#m(){let t=this.getAttribute("view")||"auto",e=t==="auto"?ns(this.#a):t,s=is(this.#a),r=[],a;switch(e){case"day":a=H;break;case"week":a=jt;break;case"month":a=ct;break;case"quarter":a=as;break;default:a=ct}let i=new Date(this.#r);if(e==="week"){let d=i.getDay(),l=d===0?1:d===1?0:8-d;i.setDate(i.getDate()+l)}else if(e==="month")i.setDate(1),i.getTime()<this.#r&&i.setMonth(i.getMonth()+1);else if(e==="quarter"){let d=i.getMonth(),l=Math.ceil((d+1)/3)*3;i.setMonth(l),i.setDate(1)}let o=i.getTime();o>this.#r+a*.5&&r.push({position:0,text:s(new Date(this.#r))});let c=o;for(;c<=this.#n;){let d=(c-this.#r)/this.#a*100;if(d>=0&&d<=100&&r.push({position:d,text:s(new Date(c))}),e==="month"){let l=new Date(c);l.setMonth(l.getMonth()+1),c=l.getTime()}else if(e==="quarter"){let l=new Date(c);l.setMonth(l.getMonth()+3),c=l.getTime()}else c+=a}return r}#g(){let t=document.createElement("div");t.className="gc-grid-lines";let e=this.#m();for(let{position:s}of e){if(s<=0)continue;let r=document.createElement("div");r.className="gc-grid-line",r.style.left=`${s}%`,t.appendChild(r)}return t}#b(){let t=new Map;for(let e of this.#i){let s=e.group||"";t.has(s)||t.set(s,[]),t.get(s)?.push(e)}return t}#v(t,e){let s=(t.start-this.#r)/this.#a*100,r=(t.end-t.start)/this.#a*100,a=document.createElement("div");if(a.className="gc-bar",a.setAttribute("data-task-id",t.id),a.setAttribute("role","img"),a.setAttribute("tabindex","0"),a.setAttribute("aria-label",`${pe(t.name)}: ${new Date(t.start).toLocaleDateString()} to ${new Date(t.end).toLocaleDateString()}`+(t.progress>0?`, ${Math.round(t.progress*100)}% complete`:"")),a.style.left=`${s}%`,a.style.width=`${Math.max(r,.5)}%`,t.status&&a.setAttribute("data-status",t.status),t.color&&a.style.setProperty("--gc-bar-color",t.color),e&&t.progress>0){let i=document.createElement("div");i.className="gc-bar-fill",i.style.width=`${Math.round(t.progress*100)}%`,a.appendChild(i)}if(r>8){let i=document.createElement("span");i.className="gc-bar-label",i.textContent=t.name,a.appendChild(i)}return a}#d(t){let e=(t.start-this.#r)/this.#a*100,s=document.createElement("div");return s.className="gc-milestone",s.setAttribute("data-task-id",t.id),s.setAttribute("role","img"),s.setAttribute("tabindex","0"),s.setAttribute("aria-label",`Milestone: ${pe(t.name)}, ${new Date(t.start).toLocaleDateString()}`),s.style.left=`${e}%`,t.status&&s.setAttribute("data-status",t.status),t.color&&s.style.setProperty("--gc-bar-color",t.color),s}#h(){let t=Date.now();if(t<this.#r||t>this.#n)return null;let e=(t-this.#r)/this.#a*100,s=document.createElement("div");s.className="gc-today-line",s.style.left=`${e}%`;let r=document.createElement("span");return r.className="gc-today-label",r.textContent="Today",s.appendChild(r),s}#y(t){if(!this.#i.some(l=>l.depends.length>0))return null;let s="http://www.w3.org/2000/svg",r=36,a=t.querySelectorAll(".gc-bar-row").length,i=document.createElementNS(s,"svg");i.setAttribute("class","gc-deps"),i.setAttribute("viewBox",`0 0 100 ${a*r}`),i.setAttribute("preserveAspectRatio","none"),i.style.width="100%",i.style.height="100%";let o=document.createElementNS(s,"defs"),c=document.createElementNS(s,"marker");c.setAttribute("id","gc-arrowhead"),c.setAttribute("markerWidth","8"),c.setAttribute("markerHeight","6"),c.setAttribute("refX","8"),c.setAttribute("refY","3"),c.setAttribute("orient","auto");let d=document.createElementNS(s,"polygon");d.setAttribute("points","0 0, 8 3, 0 6"),d.setAttribute("fill","var(--color-text-muted, #666666)"),c.appendChild(d),o.appendChild(c),i.appendChild(o);for(let l of this.#i)for(let u of l.depends){let p=this.#i.find(A=>A.id===u);if(!p)continue;let h=(p.end-this.#r)/this.#a*100,f=(l.start-this.#r)/this.#a*100,b=this.#f(p.id,t),v=this.#f(l.id,t);if(b===-1||v===-1)continue;let x=b*r+r/2,_=v*r+r/2,g=document.createElementNS(s,"path"),y=h+(f-h)/2;g.setAttribute("d",`M ${h} ${x} C ${y} ${x}, ${y} ${_}, ${f} ${_}`),g.setAttribute("class","gc-dep-line"),g.setAttribute("vector-effect","non-scaling-stroke"),i.appendChild(g)}return i}#f(t,e){let s=e.querySelectorAll(".gc-bar-row");for(let r=0;r<s.length;r++){let a=s[r].querySelector("[data-task-id]");if(a&&a.dataset.taskId===t)return r}return-1}async _loadSrc(t){if(t)try{let e=await fetch(t);if(!e.ok)throw new Error(`HTTP ${e.status}`);let s=await e.json();for(;this.firstChild;)this.firstChild.remove();let r=document.createElement("table"),a=document.createElement("thead"),i=document.createElement("tr");for(let c of["Task","Start","End","Progress"]){let d=document.createElement("th");d.textContent=c,i.appendChild(d)}a.appendChild(i),r.appendChild(a);let o=document.createElement("tbody");for(let c of s.tasks||[]){let d=document.createElement("tr");c.id&&(d.dataset.taskId=c.id),c.group&&(d.dataset.group=c.group),c.depends&&(d.dataset.depends=Array.isArray(c.depends)?c.depends.join(","):c.depends),c.status&&(d.dataset.status=c.status),c.assignee&&(d.dataset.assignee=c.assignee),c.milestone&&d.setAttribute("data-milestone",""),c.color&&(d.dataset.color=c.color),c.storyIds&&(d.dataset.storyIds=Array.isArray(c.storyIds)?c.storyIds.join(","):c.storyIds),c.itemIds&&(d.dataset.itemIds=Array.isArray(c.itemIds)?c.itemIds.join(","):c.itemIds);let l=document.createElement("td");l.textContent=c.name||"",d.appendChild(l);let u=document.createElement("td"),p=document.createElement("time");p.setAttribute("datetime",c.start),p.textContent=new Date(c.start).toLocaleDateString(void 0,{month:"short",day:"numeric"}),u.appendChild(p),d.appendChild(u);let h=document.createElement("td"),f=document.createElement("time");f.setAttribute("datetime",c.end||c.start),f.textContent=new Date(c.end||c.start).toLocaleDateString(void 0,{month:"short",day:"numeric"}),h.appendChild(f),d.appendChild(h);let b=document.createElement("td"),v=document.createElement("progress");v.value=c.progress||0,v.max=100,v.textContent=`${c.progress||0}%`,b.appendChild(v),d.appendChild(b),o.appendChild(d)}r.appendChild(o),this.appendChild(r),s.title&&this.setAttribute("title",s.title),this.#c()}catch(e){console.warn(`[gantt-chart] Failed to load src="${t}":`,e)}}#w(t){this.#t&&(this.#t.textContent="",requestAnimationFrame(()=>{this.#t&&(this.#t.textContent=t)}))}};w("gantt-chart",Rt);var K=`
2339
+ </div>`}#w(t){let e=t.target;if(!(e instanceof Element))return;let r=e.closest(".rs-pin");if(r){t.stopPropagation();let a=r.dataset.pinId??null;this._activePin===a?this.#_():a&&this.#x(a);return}let s=e.closest("[data-action]");if(s){t.stopPropagation();let a=s.dataset.pinId;switch(s.dataset.action){case"close":this.#_();break;case"resolve":a&&this.resolvePin(a);break;case"unresolve":a&&this.unresolvePin(a);break;case"delete":a&&this.removePin(a);break;case"toggle-mode":this.#v(!this._annotating);break;case"export":this.#f();break;case"reply":a&&this.#p(a);break}return}if(e===this.#c&&this._annotating&&this.hasAttribute("editable")){let a=t,n=this.#c.getBoundingClientRect(),o=(a.clientX-n.left)/n.width*100,l=(a.clientY-n.top)/n.height*100;this.#m(o,l)}}#A(t){let e=t.target;if(t.key==="Enter"&&!t.shiftKey&&e instanceof Element&&e.matches(".rs-input__field")){t.preventDefault();let r=(this.shadowRoot?.querySelector('[data-action="reply"]')??null)?.dataset.pinId;r&&this.#p(r);return}t.key==="Escape"&&(this._activePin?(t.stopPropagation(),this.#_()):this._annotating&&(t.stopPropagation(),this.#v(!1)))}#v(t){this._annotating=t,this.toggleAttribute("data-annotating",t),this._render(),this.dispatchEvent(new CustomEvent("review-surface:mode",{bubbles:!0,composed:!0,detail:{mode:t?"annotate":"view"}}))}async#m(t,e){let r=this.getAttribute("author")||"Anonymous",s=await this.addPin({x:t,y:e,text:"",author:r});this._activePin=s.id,this._render(),(this.shadowRoot?.querySelector(".rs-input__field")??null)?.focus()}async#p(t){let e=this.shadowRoot?.querySelector(".rs-input__field")??null;if(!e)return;let r=e.value.trim();if(!r)return;let s=this.__pins.find(o=>o.id===t);if(!s)return;let a={id:crypto.randomUUID(),text:r,author:this.getAttribute("author")||"Anonymous",createdAt:new Date().toISOString()},n=s.text?{replies:[...s.replies??[],a]}:{text:r};this.__adapter&&await this.__adapter.update(t,n,s),Object.assign(s,n),s.replies||(s.replies=[]),e.value="",this._render(),this.#k("Reply added"),(this.shadowRoot?.querySelector(".rs-input__field")??null)?.focus(),this.dispatchEvent(new CustomEvent("review-surface:update",{bubbles:!0,composed:!0,detail:{pin:s,changes:n}}))}async#f(){let t=JSON.stringify(this.exportPins(),null,2);if(await me(t,{announceMessage:"Pins copied to clipboard"}))return;let r=new Blob([t],{type:"application/json"}),s=URL.createObjectURL(r),a=document.createElement("a");a.href=s,a.download="review-pins.json",a.click(),URL.revokeObjectURL(s),this.#k("Pins exported as file")}#S(t){if(!t)return"";try{let e=new Date(t);if(Number.isNaN(e.getTime()))return"";let s=new Date().getTime()-e.getTime(),a=Math.floor(s/6e4);if(a<1)return"just now";if(a<60)return`${a}m ago`;let n=Math.floor(a/60);if(n<24)return`${n}h ago`;let o=Math.floor(n/24);return o<7?`${o}d ago`:e.toLocaleDateString()}catch{return""}}#k(t){this.#l.textContent=t}};A("review-surface",fe);function Zr(i){return i<=90?t=>H(t,{month:"short",day:"numeric"}):i<=365?t=>H(t,{month:"short",year:"2-digit"}):t=>H(t,{year:"numeric"})}function ts(i){return i<=21?"day":i<=90?"week":i<=365?"month":"quarter"}var Ge={day:1,week:7,month:30,quarter:91};function dt(i){return H(new Date(i),{year:"numeric",month:"short",day:"numeric"})}var es={"not-started":"Not started","in-progress":"In progress",done:"Done",blocked:"Blocked"};function be(i){return es[i]||(i.charAt(0).toUpperCase()+i.slice(1)).replace(/-/g," ")}function ge(i){return Array.isArray(i)?i.map(String):i==null||i===""?[]:String(i).split(",").map(t=>t.trim()).filter(Boolean)}function rs(i){let t=Number(i);return!Number.isFinite(t)||t<=0?0:Math.min(1,t>1?t/100:t)}function ve(i){let t=[];return(i||[]).forEach((e,r)=>{let s=T(e?.start);if(!s)return;let a=T(e.end)??s;t.push({id:e.id!=null&&e.id!==""?String(e.id):`gc-task-${r}`,name:e.name??`Task ${r+1}`,start:s.getTime(),end:Math.max(a.getTime(),s.getTime()),progress:rs(e.progress),group:e.group||null,depends:ge(e.depends),status:e.status||null,assignee:e.assignee||null,milestone:!!e.milestone,color:e.color||null,storyIds:ge(e.storyIds),itemIds:ge(e.itemIds)})}),t}var ss=0,ye=class extends C{static get observedAttributes(){return["src","title","view","show-today","show-progress","show-dependencies","compact"]}#e=`gc-${++ss}`;#t=null;#r=null;#a=null;#s=[];#i="table";#c=new z;#n=!1;#d=!1;#o=new Date(0);#l=1;constructor(){if(super(),Object.prototype.hasOwnProperty.call(this,"tasks")){let t=this.tasks;delete this.tasks,this.tasks=t}}setup(){if(this.listen(this,"click",this.#q),this.listen(this,"keydown",this.#I),this.#i==="table"){let e=this.querySelector(":scope > table");this.#s=e?this.#u(e):[]}this.#b(),this.#s.length&&this.#h();let t=this.getAttribute("src");return t&&this.#i!=="property"&&t!==this.#c.url&&this.#T(t),!0}teardown(){this.#y();let t=this.querySelector(":scope > table.gc-sr-only");t&&!t.hasAttribute("data-gc-generated")&&t.classList.remove("gc-sr-only")}attributeChangedCallback(t,e,r){if(!(e===r||this.#d)&&!(!this.isConnected||!this.hasAttribute("data-upgraded"))){if(t==="src"){r?this.#T(r):this.#c.cancel();return}D(this,()=>this.#b(),"gc-vt")}}get tasks(){return this.#s}set tasks(t){this.#c.cancel(),this.#s=ve(t),this.#i="property",this.hasAttribute("data-upgraded")&&this.#b(),this.dispatchEvent(new CustomEvent("gantt-chart:tasks-changed",{detail:{tasks:this.#s,source:"property"},bubbles:!0}))}#u(t){let e=t.querySelectorAll("tbody tr"),r=[];for(let s=0;s<e.length;s++){let a=e[s],n=a.querySelectorAll("time[datetime]");if(n.length<2&&!a.hasAttribute("data-milestone"))continue;let o=n[0]?.getAttribute("datetime");if(!o)continue;let l=a.querySelector("progress");r.push({id:a.dataset.taskId||`gc-task-${s}`,name:a.cells[0]?.textContent?.trim()||`Task ${s+1}`,start:o,end:n.length>1?n[1].getAttribute("datetime"):o,progress:l?l.value/(l.max||1):0,group:a.dataset.group,depends:a.dataset.depends,status:a.dataset.status,assignee:a.dataset.assignee,milestone:a.hasAttribute("data-milestone"),color:a.dataset.color,storyIds:a.dataset.storyIds,itemIds:a.dataset.itemIds})}return ve(r)}#y(){this.#a?.remove(),this.#a=null,this.#t?.remove(),this.#t=null,this.#r?.remove(),this.#r=null}#E(){if(this.#i==="table")return this.querySelector(":scope > table");if(this.querySelectorAll(":scope > table").forEach(e=>e.remove()),!this.#s.length)return null;let t=this.#_();return this.appendChild(t),t}#b(){this.#y();let t=this.#E();if(!this.#s.length)return;let e=this.#s.map(s=>s.start),r=this.#s.map(s=>s.end);this.#o=new Date(Math.min(...e)),this.#l=Math.max(1,W(this.#o,new Date(Math.max(...r)))),this.#x(t)}#g(t){let e=typeof t=="number"?new Date(t):t;return W(this.#o,e)/this.#l*100}#h(){this.#n||(this.#n=!0,this.dispatchEvent(new CustomEvent("gantt-chart:ready",{bubbles:!0,detail:{taskCount:this.#s.length,dateRange:{start:R(this.#o),end:R(M(this.#o,this.#l))}}})))}#x(t){let e=this.getAttribute("title"),r=this.hasAttribute("show-today"),s=this.hasAttribute("show-progress"),a=this.hasAttribute("show-dependencies"),n=t&&t.parentNode===this?t:null;e&&(this.#a=document.createElement("h2"),this.#a.className="gc-title",this.#a.textContent=e,this.insertBefore(this.#a,n)),this.#t=document.createElement("div"),this.#t.className="gc-container",this.#t.setAttribute("role","region"),this.#t.setAttribute("aria-label",`Gantt chart${e?": "+e:""}`);let o=this.#A();this.#t.appendChild(this.#w(o));let l=document.createElement("div");l.className="gc-body";let d=document.createElement("div");d.className="gc-task-list";let c=document.createElement("div");c.className="gc-bars",c.appendChild(this.#v(o));let u=this.#m();for(let[m,f]of u){if(u.size>1&&m){let h=document.createElement("div");h.className="gc-group-header";let b=document.createElement("span");b.className="gc-group-label",b.textContent=m,h.appendChild(b),d.appendChild(h);let g=document.createElement("div");g.className="gc-group-spacer",c.appendChild(g)}for(let h of f){let b=document.createElement("div");b.className="gc-task-row",b.setAttribute("data-task-id",h.id);let g=document.createElement("span");if(g.className="gc-task-name",g.textContent=h.name,b.appendChild(g),h.status){let y=document.createElement("span");y.className="gc-task-status",y.setAttribute("data-status",h.status),y.textContent=be(h.status),b.appendChild(y)}let w=document.createElement("span");w.className="gc-task-dates",w.textContent=h.milestone?dt(h.start):`${dt(h.start)} to ${dt(h.end)}`,b.appendChild(w),d.appendChild(b);let v=document.createElement("div");v.className="gc-bar-row",v.setAttribute("data-task-id",h.id),v.appendChild(h.milestone?this.#S(h):this.#f(h,s)),c.appendChild(v)}}if(r){let m=this.#k();m&&c.appendChild(m)}l.appendChild(d),l.appendChild(c),this.#t.appendChild(l),this.insertBefore(this.#t,n),t&&t.classList.add("gc-sr-only"),this.#r=document.createElement("div"),this.#r.className="gc-sr-only",this.#r.setAttribute("role","status"),this.#r.setAttribute("aria-live","polite"),this.#r.setAttribute("aria-atomic","true"),this.appendChild(this.#r),a&&requestAnimationFrame(()=>{if(!c.isConnected)return;let m=this.#$(c);m&&c.appendChild(m)})}#_(){let t=document.createElement("table");t.setAttribute("data-gc-generated","");let e=document.createElement("thead"),r=document.createElement("tr");for(let a of["Task","Start","End","Progress","Status"]){let n=document.createElement("th");n.scope="col",n.textContent=a,r.appendChild(n)}e.appendChild(r),t.appendChild(e);let s=document.createElement("tbody");for(let a of this.#s){let n=document.createElement("tr");n.dataset.taskId=a.id;let o=document.createElement("td");o.textContent=a.name,n.appendChild(o);for(let m of[a.start,a.end]){let f=document.createElement("td"),h=document.createElement("time");h.setAttribute("datetime",R(new Date(m))),h.textContent=dt(m),f.appendChild(h),n.appendChild(f)}let l=document.createElement("td"),d=document.createElement("progress"),c=Math.round(a.progress*100);d.max=100,d.value=c,d.textContent=`${c}%`,l.appendChild(d),n.appendChild(l);let u=document.createElement("td");u.textContent=a.status?be(a.status):"",n.appendChild(u),s.appendChild(n)}return t.appendChild(s),t}#w(t){let e=document.createElement("div");e.className="gc-timeline-header";let r=document.createElement("div");r.className="gc-timeline-spacer",e.appendChild(r);let s=document.createElement("div");s.className="gc-timeline-dates";for(let{position:a,text:n}of t){let o=document.createElement("span");o.className="gc-date-label",o.style.left=`${a}%`,o.textContent=n,s.appendChild(o)}return e.appendChild(s),e}#A(){let t=this.getAttribute("view")||"auto",e=Ge[t]?t:ts(this.#l),r=Zr(this.#l),s=this.#o,a=M(s,this.#l),n=[],o,l;if(e==="week"){let d=s.getDay();l=M(s,(8-d)%7),o=c=>M(c,7)}else e==="month"?(l=Rt(s),l<s&&(l=B(l,1)),o=d=>B(d,1)):e==="quarter"?(l=Pt(s),l<s&&(l=B(l,3)),o=d=>B(d,3)):(l=et(s),o=d=>M(d,1));W(s,l)>Ge[e]*.5&&n.push({position:0,text:r(s)});for(let d=l;d<=a;d=o(d)){let c=this.#g(d);c>=0&&c<=100&&n.push({position:c,text:r(d)})}return n}#v(t){let e=document.createElement("div");e.className="gc-grid-lines";for(let{position:r}of t){if(r<=0)continue;let s=document.createElement("div");s.className="gc-grid-line",s.style.left=`${r}%`,e.appendChild(s)}return e}#m(){let t=new Map;for(let e of this.#s){let r=e.group||"";t.has(r)||t.set(r,[]),t.get(r)?.push(e)}return t}#p(t){let e=[t.milestone?`Milestone: ${t.name}, ${dt(t.start)}`:`${t.name}: ${dt(t.start)} to ${dt(t.end)}`];return t.status&&e.push(`status: ${be(t.status).toLowerCase()}`),!t.milestone&&t.progress>0&&e.push(`${Math.round(t.progress*100)}% complete`),t.assignee&&e.push(`assigned to ${t.assignee}`),e.join(", ")}#f(t,e){let r=this.#g(t.start),s=this.#g(t.end)-r,a=document.createElement("div");if(a.className="gc-bar",a.setAttribute("data-task-id",t.id),a.setAttribute("role","button"),a.setAttribute("tabindex","0"),a.setAttribute("aria-label",this.#p(t)),a.style.left=`${r}%`,a.style.width=`${Math.max(s,.5)}%`,t.status&&a.setAttribute("data-status",t.status),t.color&&a.style.setProperty("--gc-bar-color",t.color),e&&t.progress>0){let n=document.createElement("div");n.className="gc-bar-fill",n.style.width=`${Math.round(t.progress*100)}%`,a.appendChild(n)}if(s>8){let n=document.createElement("span");n.className="gc-bar-label",n.setAttribute("aria-hidden","true"),n.textContent=t.name,a.appendChild(n)}return a}#S(t){let e=document.createElement("div");return e.className="gc-milestone",e.setAttribute("data-task-id",t.id),e.setAttribute("role","button"),e.setAttribute("tabindex","0"),e.setAttribute("aria-label",this.#p(t)),e.style.left=`${this.#g(t.start)}%`,t.status&&e.setAttribute("data-status",t.status),t.color&&e.style.setProperty("--gc-bar-color",t.color),e}#k(){let t=new Date,e=(t.getTime()-et(t).getTime())/864e5,r=W(this.#o,t)+e;if(r<0||r>this.#l)return null;let s=document.createElement("div");s.className="gc-today-line",s.style.left=`${r/this.#l*100}%`;let a=document.createElement("span");return a.className="gc-today-label",a.textContent="Today",s.appendChild(a),s}#$(t){if(!this.#s.some(c=>c.depends.length>0))return null;let e=new Map;for(let c of t.querySelectorAll(":scope > .gc-bar-row"))e.set(c.dataset.taskId||"",c.offsetTop+c.offsetHeight/2);let r=Math.max(1,Math.round(t.scrollHeight)),s="http://www.w3.org/2000/svg",a=document.createElementNS(s,"svg");a.setAttribute("class","gc-deps"),a.setAttribute("aria-hidden","true"),a.setAttribute("viewBox",`0 0 100 ${r}`),a.setAttribute("preserveAspectRatio","none"),a.style.width="100%",a.style.height=`${r}px`;let n=`${this.#e}-arrowhead`,o=document.createElementNS(s,"defs"),l=document.createElementNS(s,"marker");l.setAttribute("id",n),l.setAttribute("markerWidth","8"),l.setAttribute("markerHeight","6"),l.setAttribute("refX","8"),l.setAttribute("refY","3"),l.setAttribute("orient","auto");let d=document.createElementNS(s,"polygon");d.setAttribute("points","0 0, 8 3, 0 6"),d.setAttribute("fill","var(--color-text-muted, #666666)"),l.appendChild(d),o.appendChild(l),a.appendChild(o);for(let c of this.#s)for(let u of c.depends){let m=this.#s.find(y=>y.id===u);if(!m)continue;let f=e.get(m.id),h=e.get(c.id);if(f===void 0||h===void 0)continue;let b=this.#g(m.end),g=this.#g(c.start),w=b+(g-b)/2,v=document.createElementNS(s,"path");v.setAttribute("d",`M ${b} ${f} C ${w} ${f}, ${w} ${h}, ${g} ${h}`),v.setAttribute("class","gc-dep-line"),v.setAttribute("data-from",m.id),v.setAttribute("data-to",c.id),v.setAttribute("marker-end",`url(#${n})`),v.setAttribute("vector-effect","non-scaling-stroke"),a.appendChild(v)}return a}#C(t){let r=t.target?.closest?.(".gc-bar, .gc-milestone");return r&&this.#t?.contains(r)?r:null}#q=t=>{let e=this.#C(t);if(!e)return;let r=this.#s.find(s=>s.id===e.dataset.taskId);r&&(this.#N(`Selected: ${r.name}`),this.dispatchEvent(new CustomEvent("gantt-chart:task-click",{bubbles:!0,detail:{task:r}})))};#I=t=>{let e=t;if(e.key!=="Enter"&&e.key!==" ")return;let r=this.#C(e);r&&(e.preventDefault(),r.click())};async#T(t){let e;try{e=await this.#c.fetchJson(t)}catch(s){console.warn(`[gantt-chart] Failed to load src="${t}":`,s);return}if(!e)return;let{data:r}=e;this.#s=ve(r?.tasks||[]),this.#i="src",r?.title&&r.title!==this.getAttribute("title")&&(this.#d=!0,this.setAttribute("title",r.title),this.#d=!1),this.hasAttribute("data-upgraded")&&(this.#b(),this.#h()),this.dispatchEvent(new CustomEvent("gantt-chart:tasks-changed",{detail:{tasks:this.#s,source:"src"},bubbles:!0}))}#N(t){this.#r&&(this.#r.textContent="",requestAnimationFrame(()=>{this.#r&&(this.#r.textContent=t)}))}};A("gantt-chart",ye);var kt=`
2314
2340
  :host {
2315
2341
  --_bg: var(--work-item-bg, var(--color-surface, #ffffff));
2316
2342
  --_text: var(--work-item-text, var(--color-text, #1a1a1a));
@@ -2673,30 +2699,29 @@ var re=`
2673
2699
 
2674
2700
  .state-msg { padding: var(--_space-m); font-size: var(--_font-sm); color: var(--_muted); font-style: italic; }
2675
2701
  .state-msg--error { color: var(--color-error-text, var(--color-error, #dc2626)); }
2676
- `;var me={task:'<rect x="3" y="3" width="18" height="18" rx="2"/><path d="m9 12 2 2 4-4"/>',bug:'<path d="m8 2 1.88 1.88"/><path d="M14.12 3.88 16 2"/><path d="M9 7.13v-1a3.003 3.003 0 1 1 6 0v1"/><path d="M12 20c-3.3 0-6-2.7-6-6v-3a4 4 0 0 1 4-4h4a4 4 0 0 1 4 4v3c0 3.3-2.7 6-6 6"/><path d="M12 20v-9"/><path d="M6.53 9C4.6 8.8 3 7.1 3 5"/><path d="M6 13H2"/><path d="M3 21c0-2.1 1.7-3.9 3.8-4"/><path d="M20.97 5c0 2.1-1.6 3.8-3.5 4"/><path d="M22 13h-4"/><path d="M17.2 17c2.1.1 3.8 1.9 3.8 4"/>',chore:'<path d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.106-3.105c.32-.322.863-.22.983.218a6 6 0 0 1-8.259 7.057l-7.91 7.91a1 1 0 0 1-2.999-3l7.91-7.91a6 6 0 0 1 7.057-8.259c.438.12.54.662.219.984z"/>',spike:'<path d="M15 14c.2-1 .7-1.7 1.5-2.5 1-.9 1.5-2.2 1.5-3.5A6 6 0 0 0 6 8c0 1 .2 2.2 1.5 3.5.7.7 1.3 1.5 1.5 2.5"/><path d="M9 18h6"/><path d="M10 22h4"/>',feature:'<circle cx="12" cy="12" r="10"/><path d="m9 12 2 2 4-4"/>'},Dt={critical:{label:"Critical",color:"#dc2626",bg:"rgba(220, 38, 38, 0.1)"},high:{label:"High",color:"#ea580c",bg:"rgba(234, 88, 12, 0.1)"},medium:{label:"Medium",color:"#ca8a04",bg:"rgba(202, 138, 4, 0.1)"},low:{label:"Low",color:"#16a34a",bg:"rgba(22, 163, 74, 0.1)"}},Ft={backlog:{label:"Backlog",color:"#6b7280",bg:"rgba(107, 114, 128, 0.1)"},"to-do":{label:"To Do",color:"#3b82f6",bg:"rgba(59, 130, 246, 0.1)"},"in-progress":{label:"In Progress",color:"#8b5cf6",bg:"rgba(139, 92, 246, 0.1)"},review:{label:"Review",color:"#f59e0b",bg:"rgba(245, 158, 11, 0.1)"},done:{label:"Done",color:"#22c55e",bg:"rgba(34, 197, 94, 0.1)"},blocked:{label:"Blocked",color:"#dc2626",bg:"rgba(220, 38, 38, 0.1)"}},Ot=class extends HTMLElement{static get observedAttributes(){return["item-id","type","priority","status","estimate","assignee","story-ids","detail","compact","src"]}#e=new Map;constructor(){super(),this.attachShadow({mode:"open"})}#t(){for(let t of[...this.children]){let e=t.getAttribute("slot");e&&this.#e.set(e,t.textContent.trim())}}_resolve(t){return this.getAttribute(t)||this.#e.get(t)||""}connectedCallback(){this.#t(),this.itemId&&!this.id&&(this.id=this.itemId),this.hasAttribute("src")&&this._loadSrc(this.getAttribute("src")),this.#s(),this.setAttribute("data-upgraded","")}disconnectedCallback(){this.removeAttribute("data-upgraded")}attributeChangedCallback(t,e,s){e!==s&&this.shadowRoot&&(t==="src"&&this.isConnected?this._loadSrc(s):this.#s())}get itemId(){return this.getAttribute("item-id")||""}get itemTitle(){return this.querySelector('[slot="title"]')?.textContent?.trim()||this.#e.get("title")||""}get itemType(){return this.getAttribute("type")||"task"}get priority(){return this.getAttribute("priority")||"medium"}get status(){return this.getAttribute("status")||"backlog"}get estimate(){return this.getAttribute("estimate")||""}get assignee(){return this.getAttribute("assignee")||""}get storyIds(){let t=this.getAttribute("story-ids")||"";return t?t.split(",").map(e=>e.trim()).filter(Boolean):[]}get _detailLevel(){return this.getAttribute("detail")?this.getAttribute("detail"):this.hasAttribute("compact")?"compact":"full"}get _minimalLabel(){return this.itemTitle||this.itemId||"Work item"}updateStatus(t){Ft[t]&&(this.setAttribute("status",t),this.dispatchEvent(new CustomEvent("work-item:status",{detail:{status:t,itemId:this.itemId},bubbles:!0,composed:!0})))}updatePriority(t){Dt[t]&&(this.setAttribute("priority",t),this.dispatchEvent(new CustomEvent("work-item:priority",{detail:{priority:t,itemId:this.itemId},bubbles:!0,composed:!0})))}get data(){return{itemId:this.itemId||void 0,type:this.itemType,priority:this.priority,status:this.status,estimate:this.estimate||void 0,assignee:this.assignee||void 0,storyIds:this.storyIds.length?this.storyIds:void 0,detail:this.getAttribute("detail")||void 0,title:this.itemTitle||void 0}}set data(t){!t||typeof t!="object"||(this._applyData(t),this.shadowRoot&&this.#s(),this.dispatchEvent(new CustomEvent("work-item:data-changed",{detail:{data:this.data,source:"property"},bubbles:!0,composed:!0})))}_applyData(t){for(let[e,s]of[["itemId","item-id"],["type","type"],["priority","priority"],["status","status"],["estimate","estimate"],["assignee","assignee"],["detail","detail"]])t[e]!=null&&this.setAttribute(s,String(t[e]));if(t.storyIds&&this.setAttribute("story-ids",Array.isArray(t.storyIds)?t.storyIds.join(","):String(t.storyIds)),t.title&&!this.querySelector('[slot="title"]')){let e=document.createElement("h3");e.slot="title",e.textContent=String(t.title),this.appendChild(e)}for(let e of["description","notes"])if(t[e]&&!this.querySelector(`[slot="${e}"]`)){let s=document.createElement("p");s.slot=e,s.textContent=String(t[e]),this.appendChild(s)}if(t.checklist&&!this.querySelector('[slot="checklist"]')){let e=document.createElement("ul");e.slot="checklist";let s=Array.isArray(t.checklist)?t.checklist:[t.checklist];for(let r of s){let a=document.createElement("li");a.textContent=String(r),e.appendChild(a)}this.appendChild(e)}}async _loadSrc(t){if(!t)return;let e=this.shadowRoot;e.innerHTML=`<style>${K}</style><div class="state-msg">Loading\u2026</div>`;try{let s=await fetch(t);if(!s.ok)throw new Error(`HTTP ${s.status}`);let r=await s.json();this._applyData(r),this.#s()}catch(s){e.innerHTML=`<style>${K}</style><div class="state-msg state-msg--error">Could not load: ${m(s.message)}</div>`}}#s(){let t=this.shadowRoot,e=Dt[this.priority]||Dt.medium,s=Ft[this.status]||Ft.backlog,r=this.itemType,a=me[r]||me.task,i=this._detailLevel,o=this.itemId?`Work item: ${m(this.itemId)}`:"Work item";if(i==="minimal"){t.innerHTML=`<style>${K}</style>
2677
- <article class="wi-card wi-card--minimal" role="article" aria-label="${o}"
2678
- tabindex="0">
2702
+ `;var as={task:'<rect x="3" y="3" width="18" height="18" rx="2"/><path d="m9 12 2 2 4-4"/>',bug:'<path d="m8 2 1.88 1.88"/><path d="M14.12 3.88 16 2"/><path d="M9 7.13v-1a3.003 3.003 0 1 1 6 0v1"/><path d="M12 20c-3.3 0-6-2.7-6-6v-3a4 4 0 0 1 4-4h4a4 4 0 0 1 4 4v3c0 3.3-2.7 6-6 6"/><path d="M12 20v-9"/><path d="M6.53 9C4.6 8.8 3 7.1 3 5"/><path d="M6 13H2"/><path d="M3 21c0-2.1 1.7-3.9 3.8-4"/><path d="M20.97 5c0 2.1-1.6 3.8-3.5 4"/><path d="M22 13h-4"/><path d="M17.2 17c2.1.1 3.8 1.9 3.8 4"/>',chore:'<path d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.106-3.105c.32-.322.863-.22.983.218a6 6 0 0 1-8.259 7.057l-7.91 7.91a1 1 0 0 1-2.999-3l7.91-7.91a6 6 0 0 1 7.057-8.259c.438.12.54.662.219.984z"/>',spike:'<path d="M15 14c.2-1 .7-1.7 1.5-2.5 1-.9 1.5-2.2 1.5-3.5A6 6 0 0 0 6 8c0 1 .2 2.2 1.5 3.5.7.7 1.3 1.5 1.5 2.5"/><path d="M9 18h6"/><path d="M10 22h4"/>',feature:'<circle cx="12" cy="12" r="10"/><path d="m9 12 2 2 4-4"/>'},Ze=Object.freeze({...ht,blocked:{label:"Blocked",color:"#dc2626",bg:"rgba(220, 38, 38, 0.1)"}}),xe=class extends P{static readyEvent="work-item:ready";static get observedAttributes(){return["item-id","type","priority","status","estimate","assignee","story-ids","detail","compact","src"]}_setup(){this.itemId&&!this.id&&(this.id=this.itemId)}_readyDetail(){return{itemId:this.itemId,title:this.itemTitle,type:this.itemType,priority:this.priority,status:this.status}}get itemId(){return this.getAttribute("item-id")||""}get itemTitle(){return this._slotText("title")}get itemType(){return this.getAttribute("type")||"task"}get priority(){return this.getAttribute("priority")||"medium"}get status(){return this.getAttribute("status")||"backlog"}get estimate(){return this.getAttribute("estimate")||""}get assignee(){return this.getAttribute("assignee")||""}get storyIds(){return ot(this.getAttribute("story-ids"))}get _detailLevel(){return mt(this)}get _minimalLabel(){return this.itemTitle||this.itemId||"Work item"}updateStatus(t){Object.hasOwn(Ze,t)&&(this.setAttribute("status",t),this.dispatchEvent(new CustomEvent("work-item:status",{detail:{status:t,itemId:this.itemId},bubbles:!0,composed:!0})))}updatePriority(t){Object.hasOwn(nt,t)&&(this.setAttribute("priority",t),this.dispatchEvent(new CustomEvent("work-item:priority",{detail:{priority:t,itemId:this.itemId},bubbles:!0,composed:!0})))}get data(){return{itemId:this.itemId||void 0,type:this.itemType,priority:this.priority,status:this.status,estimate:this.estimate||void 0,assignee:this.assignee||void 0,storyIds:this.storyIds.length?this.storyIds:void 0,detail:this.getAttribute("detail")||void 0,title:this.itemTitle||void 0}}set data(t){this._setData(t)}_applyData(t){for(let[e,r]of[["itemId","item-id"],["type","type"],["priority","priority"],["status","status"],["estimate","estimate"],["assignee","assignee"],["detail","detail"]])t[e]!=null&&this.setAttribute(r,String(t[e]));t.storyIds&&this.setAttribute("story-ids",Array.isArray(t.storyIds)?t.storyIds.join(","):String(t.storyIds)),E(this,"title",t.title,{tag:"h3"}),E(this,"description",t.description),E(this,"notes",t.notes),E(this,"checklist",t.checklist,{list:!0})}_renderLoading(){this.shadowRoot.innerHTML=`<style>${kt}</style><div class="state-msg">Loading\u2026</div>`}_renderError(t){this.shadowRoot.innerHTML=`<style>${kt}</style><div class="state-msg state-msg--error">Could not load: ${p(t.message)}</div>`}_render(){let t=this.shadowRoot,e=J(nt,this.priority,"medium"),r=J(Ze,this.status,"backlog"),s=this.itemType,a=J(as,s,"task"),n=this._detailLevel,o=this.itemId?`Work item: ${p(this.itemId)}`:"Work item";if(n==="minimal"){t.innerHTML=`<style>${kt}</style>
2703
+ <article class="wi-card wi-card--minimal" role="article" aria-label="${o}">
2679
2704
  <div class="wi-body">
2680
2705
  <div class="wi-meta">
2681
- ${this.itemId?`<span class="wi-id">${m(this.itemId)}</span>`:""}
2682
- <span class="wi-type" data-type="${m(r)}">${k(a)} ${m(r)}</span>
2706
+ ${this.itemId?`<span class="wi-id">${p(this.itemId)}</span>`:""}
2707
+ <span class="wi-type" data-type="${p(s)}">${S(a)} ${p(s)}</span>
2683
2708
  </div>
2684
2709
  <div class="wi-title-wrap">
2685
- <slot name="title"><span class="wi-title-fallback">${m(this._minimalLabel)}</span></slot>
2710
+ <slot name="title"><span class="wi-title-fallback">${p(this._minimalLabel)}</span></slot>
2686
2711
  </div>
2687
2712
  </div>
2688
- </article>`;return}if(t.innerHTML=`<style>${K}</style>
2689
- <article class="wi-card wi-card--${i}" role="article" aria-label="${o}">
2713
+ </article>`;return}t.innerHTML=`<style>${kt}</style>
2714
+ <article class="wi-card wi-card--${n}" role="article" aria-label="${o}">
2690
2715
 
2691
2716
  <header class="wi-header">
2692
2717
  <div class="wi-meta">
2693
- ${this.itemId?`<span class="wi-id">${m(this.itemId)}</span>`:""}
2694
- <span class="wi-type" data-type="${m(r)}">${k(a)} ${m(r)}</span>
2718
+ ${this.itemId?`<span class="wi-id">${p(this.itemId)}</span>`:""}
2719
+ <span class="wi-type" data-type="${p(s)}">${S(a)} ${p(s)}</span>
2695
2720
  </div>
2696
2721
  <div class="wi-badges">
2697
- <span class="wi-priority" style="color:${e.color};background:${e.bg}">${m(e.label)}</span>
2698
- <span class="wi-status" style="color:${s.color};background:${s.bg}">${m(s.label)}</span>
2699
- ${this.estimate?`<span class="wi-estimate" title="Estimate">${m(this.estimate)}</span>`:""}
2722
+ <span class="wi-priority" style="color:${e.color};background:${e.bg}">${p(e.label)}</span>
2723
+ <span class="wi-status" style="color:${r.color};background:${r.bg}">${p(r.label)}</span>
2724
+ ${this.estimate?`<span class="wi-estimate" title="Estimate">${p(this.estimate)}</span>`:""}
2700
2725
  </div>
2701
2726
  </header>
2702
2727
 
@@ -2707,13 +2732,13 @@ var re=`
2707
2732
 
2708
2733
  ${this.assignee?`
2709
2734
  <div class="wi-assignee">
2710
- <span class="wi-assignee__avatar" style="background:${B(this.assignee)}">${O(this.assignee)}</span>
2711
- ${m(this.assignee)}
2735
+ <span class="wi-assignee__avatar" style="background:${it(this.assignee)}">${p(at(this.assignee))}</span>
2736
+ ${p(this.assignee)}
2712
2737
  </div>`:""}
2713
2738
 
2714
2739
  ${this.storyIds.length?`
2715
2740
  <div class="wi-links">
2716
- ${this.storyIds.map(c=>`<a class="wi-link" href="#${m(c)}">${k('<rect x="3" y="3" width="18" height="18" rx="2"/><path d="M7 7h10"/><path d="M7 12h10"/><path d="M7 17h10"/>')} ${m(c)}</a>`).join("")}
2741
+ ${this.storyIds.map(l=>`<a class="wi-link" href="#${p(l)}">${S('<rect x="3" y="3" width="18" height="18" rx="2"/><path d="M7 7h10"/><path d="M7 12h10"/><path d="M7 17h10"/>')} ${p(l)}</a>`).join("")}
2717
2742
  </div>`:""}
2718
2743
  </div>
2719
2744
 
@@ -2755,7 +2780,7 @@ var re=`
2755
2780
  </div>
2756
2781
  </div>
2757
2782
 
2758
- </article>`,i==="compact")for(let c of t.querySelectorAll(".wi-section")){let d=c.querySelector("slot");d&&d.assignedNodes().length===0&&c.setAttribute("data-empty","")}this.dispatchEvent(new CustomEvent("work-item:ready",{detail:{itemId:this.itemId,title:this.itemTitle,type:r,priority:this.priority,status:this.status},bubbles:!0,composed:!0}))}};w("work-item",Ot);var J=`
2783
+ </article>`,n==="compact"&&ft(t,".wi-section")}};A("work-item",xe);var St=`
2759
2784
  :host {
2760
2785
  --_bg: var(--adr-wc-bg, var(--color-surface, #ffffff));
2761
2786
  --_text: var(--adr-wc-text, var(--color-text, #1a1a1a));
@@ -3081,28 +3106,27 @@ var re=`
3081
3106
 
3082
3107
  .state-msg { padding: var(--_space-m); font-size: var(--_font-sm); color: var(--_muted); font-style: italic; }
3083
3108
  .state-msg--error { color: var(--color-error-text, var(--color-error, #dc2626)); }
3084
- `;var fe={proposed:{label:"Proposed",color:"#3b82f6",bg:"rgba(59, 130, 246, 0.1)"},accepted:{label:"Accepted",color:"#22c55e",bg:"rgba(34, 197, 94, 0.1)"},deprecated:{label:"Deprecated",color:"#f59e0b",bg:"rgba(245, 158, 11, 0.1)"},superseded:{label:"Superseded",color:"#6b7280",bg:"rgba(107, 114, 128, 0.1)"}},V={calendar:'<rect width="18" height="18" x="3" y="4" rx="2" ry="2"/><line x1="16" x2="16" y1="2" y2="6"/><line x1="8" x2="8" y1="2" y2="6"/><line x1="3" x2="21" y1="10" y2="10"/>',context:'<path d="M14 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V8z"/><polyline points="14 2 14 8 20 8"/><line x1="16" x2="8" y1="13" y2="13"/><line x1="16" x2="8" y1="17" y2="17"/><line x1="10" x2="8" y1="9" y2="9"/>',decision:'<path d="M22 11.08V12a10 10 0 1 1-5.93-9.14"/><path d="m9 11 3 3L22 4"/>',consequences:'<path d="m16 16 3-8 3 8c-.87.65-1.92 1-3 1s-2.13-.35-3-1Z"/><path d="m2 16 3-8 3 8c-.87.65-1.92 1-3 1s-2.13-.35-3-1Z"/><path d="M7 21h10"/><path d="M12 3v18"/><path d="M3 7h2c2 0 5-1 7-2 2 1 5 2 7 2h2"/>',arrowRight:'<path d="M5 12h14"/><path d="m12 5 7 7-7 7"/>'},Bt=class extends HTMLElement{static get observedAttributes(){return["adr-id","status","supersedes","superseded-by","detail","compact","src"]}#e=new Map;constructor(){super(),this.attachShadow({mode:"open"})}#t(){for(let t of[...this.children]){let e=t.getAttribute("slot");e&&this.#e.set(e,t.textContent.trim())}}connectedCallback(){this.#t(),this.adrId&&!this.id&&(this.id=this.adrId),this.hasAttribute("src")&&this._loadSrc(this.getAttribute("src")),this.#s(),this.setAttribute("data-upgraded","")}disconnectedCallback(){this.removeAttribute("data-upgraded")}attributeChangedCallback(t,e,s){e!==s&&this.shadowRoot&&(t==="src"&&this.isConnected?this._loadSrc(s):this.#s())}get adrId(){return this.getAttribute("adr-id")||""}get status(){return this.getAttribute("status")||"proposed"}get adrTitle(){return this.querySelector('[slot="title"]')?.textContent?.trim()||this.#e.get("title")||""}get adrDate(){let t=this.querySelector('[slot="date"]');return t?.getAttribute("datetime")||t?.textContent?.trim()||this.#e.get("date")||""}get supersedes(){let t=this.getAttribute("supersedes")||"";return t?t.split(",").map(e=>e.trim()).filter(Boolean):[]}get supersededBy(){let t=this.getAttribute("superseded-by")||"";return t?t.split(",").map(e=>e.trim()).filter(Boolean):[]}get _detailLevel(){return this.getAttribute("detail")?this.getAttribute("detail"):this.hasAttribute("compact")?"compact":"full"}get _minimalLabel(){return this.adrTitle||this.adrId||"ADR"}get data(){return{adrId:this.adrId||void 0,status:this.status,detail:this.getAttribute("detail")||void 0,supersedes:this.supersedes.length?this.supersedes:void 0,supersededBy:this.supersededBy.length?this.supersededBy:void 0,title:this.adrTitle||void 0,date:this.adrDate||void 0}}set data(t){!t||typeof t!="object"||(this._applyData(t),this.#t(),this.shadowRoot&&this.#s(),this.dispatchEvent(new CustomEvent("adr-wc:data-changed",{detail:{data:this.data,source:"property"},bubbles:!0,composed:!0})))}_applyData(t){if(t.adrId!=null&&this.setAttribute("adr-id",String(t.adrId)),t.status!=null&&this.setAttribute("status",String(t.status)),t.detail!=null&&this.setAttribute("detail",String(t.detail)),t.supersedes&&this.setAttribute("supersedes",Array.isArray(t.supersedes)?t.supersedes.join(","):String(t.supersedes)),t.supersededBy&&this.setAttribute("superseded-by",Array.isArray(t.supersededBy)?t.supersededBy.join(","):String(t.supersededBy)),t.title&&!this.querySelector('[slot="title"]')){let e=document.createElement("h3");e.slot="title",e.textContent=String(t.title),this.appendChild(e)}if(t.date&&!this.querySelector('[slot="date"]')){let e=document.createElement("time");e.slot="date",e.setAttribute("datetime",String(t.date)),e.textContent=new Date(String(t.date)).toLocaleDateString(void 0,{year:"numeric",month:"long",day:"numeric"}),this.appendChild(e)}for(let e of["context","decision"])if(t[e]&&!this.querySelector(`[slot="${e}"]`)){let s=document.createElement("p");s.slot=e,s.textContent=String(t[e]),this.appendChild(s)}if(t.consequences&&!this.querySelector('[slot="consequences"]')){let e=document.createElement("ul");e.slot="consequences";let s=Array.isArray(t.consequences)?t.consequences:[t.consequences];for(let r of s){let a=document.createElement("li");a.textContent=String(r),e.appendChild(a)}this.appendChild(e)}}async _loadSrc(t){if(!t)return;let e=this.shadowRoot;e.innerHTML=`<style>${J}</style><div class="state-msg">Loading\u2026</div>`;try{let s=await fetch(t);if(!s.ok)throw new Error(`HTTP ${s.status}`);let r=await s.json();this._applyData(r),this.#t(),this.#s()}catch(s){e.innerHTML=`<style>${J}</style><div class="state-msg state-msg--error">Could not load: ${m(s.message)}</div>`}}#s(){let t=this.shadowRoot,e=fe[this.status]||fe.proposed,s=this._detailLevel,r=this.adrId?`ADR: ${m(this.adrId)}`:"Architectural Decision Record",a=!!this.querySelector('[slot="date"]')||this.#e.has("date");if(s==="minimal"){t.innerHTML=`<style>${J}</style>
3085
- <article class="adr-card adr-card--minimal" role="article" aria-label="${r}"
3086
- tabindex="0">
3109
+ `;var is={proposed:{label:"Proposed",color:"#3b82f6",bg:"rgba(59, 130, 246, 0.1)"},accepted:{label:"Accepted",color:"#22c55e",bg:"rgba(34, 197, 94, 0.1)"},deprecated:{label:"Deprecated",color:"#f59e0b",bg:"rgba(245, 158, 11, 0.1)"},superseded:{label:"Superseded",color:"#6b7280",bg:"rgba(107, 114, 128, 0.1)"}},yt={calendar:'<rect width="18" height="18" x="3" y="4" rx="2" ry="2"/><line x1="16" x2="16" y1="2" y2="6"/><line x1="8" x2="8" y1="2" y2="6"/><line x1="3" x2="21" y1="10" y2="10"/>',context:'<path d="M14 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V8z"/><polyline points="14 2 14 8 20 8"/><line x1="16" x2="8" y1="13" y2="13"/><line x1="16" x2="8" y1="17" y2="17"/><line x1="10" x2="8" y1="9" y2="9"/>',decision:'<path d="M22 11.08V12a10 10 0 1 1-5.93-9.14"/><path d="m9 11 3 3L22 4"/>',consequences:'<path d="m16 16 3-8 3 8c-.87.65-1.92 1-3 1s-2.13-.35-3-1Z"/><path d="m2 16 3-8 3 8c-.87.65-1.92 1-3 1s-2.13-.35-3-1Z"/><path d="M7 21h10"/><path d="M12 3v18"/><path d="M3 7h2c2 0 5-1 7-2 2 1 5 2 7 2h2"/>',arrowRight:'<path d="M5 12h14"/><path d="m12 5 7 7-7 7"/>'},_e=class extends P{static readyEvent="adr-wc:ready";static get observedAttributes(){return["adr-id","status","supersedes","superseded-by","detail","compact","src"]}_setup(){this.adrId&&!this.id&&(this.id=this.adrId)}_readyDetail(){return{adrId:this.adrId,title:this.adrTitle,status:this.status}}get adrId(){return this.getAttribute("adr-id")||""}get status(){return this.getAttribute("status")||"proposed"}get adrTitle(){return this._slotText("title")}get adrDate(){return I(this,"date")?.getAttribute("datetime")||this._slotText("date")}get supersedes(){return ot(this.getAttribute("supersedes"))}get supersededBy(){return ot(this.getAttribute("superseded-by"))}get _detailLevel(){return mt(this)}get _minimalLabel(){return this.adrTitle||this.adrId||"ADR"}get data(){return{adrId:this.adrId||void 0,status:this.status,detail:this.getAttribute("detail")||void 0,supersedes:this.supersedes.length?this.supersedes:void 0,supersededBy:this.supersededBy.length?this.supersededBy:void 0,title:this.adrTitle||void 0,date:this.adrDate||void 0}}set data(t){this._setData(t)}_applyData(t){if(t.adrId!=null&&this.setAttribute("adr-id",String(t.adrId)),t.status!=null&&this.setAttribute("status",String(t.status)),t.detail!=null&&this.setAttribute("detail",String(t.detail)),t.supersedes&&this.setAttribute("supersedes",Array.isArray(t.supersedes)?t.supersedes.join(","):String(t.supersedes)),t.supersededBy&&this.setAttribute("superseded-by",Array.isArray(t.supersededBy)?t.supersededBy.join(","):String(t.supersededBy)),E(this,"title",t.title,{tag:"h3"}),t.date&&!I(this,"date")){let e=String(t.date),r=T(e),s=document.createElement("time");s.slot="date",s.setAttribute("datetime",e),s.textContent=r?H(r):e,this.appendChild(s)}E(this,"context",t.context),E(this,"decision",t.decision),E(this,"consequences",t.consequences,{list:!0})}_renderLoading(){this.shadowRoot.innerHTML=`<style>${St}</style><div class="state-msg">Loading\u2026</div>`}_renderError(t){this.shadowRoot.innerHTML=`<style>${St}</style><div class="state-msg state-msg--error">Could not load: ${p(t.message)}</div>`}_render(){let t=this.shadowRoot,e=J(is,this.status,"proposed"),r=this._detailLevel,s=this.adrId?`ADR: ${p(this.adrId)}`:"Architectural Decision Record",a=!!I(this,"date")||this._slotCache.has("date");if(r==="minimal"){t.innerHTML=`<style>${St}</style>
3110
+ <article class="adr-card adr-card--minimal" role="article" aria-label="${s}">
3087
3111
  <div class="adr-body">
3088
3112
  <div class="adr-meta">
3089
- ${this.adrId?`<span class="adr-id">${m(this.adrId)}</span>`:""}
3090
- <span class="adr-status" style="color:${e.color};background:${e.bg}">${m(e.label)}</span>
3113
+ ${this.adrId?`<span class="adr-id">${p(this.adrId)}</span>`:""}
3114
+ <span class="adr-status" style="color:${e.color};background:${e.bg}">${p(e.label)}</span>
3091
3115
  </div>
3092
3116
  <div class="adr-title-wrap">
3093
- <slot name="title"><span class="adr-title-fallback">${m(this._minimalLabel)}</span></slot>
3117
+ <slot name="title"><span class="adr-title-fallback">${p(this._minimalLabel)}</span></slot>
3094
3118
  </div>
3095
3119
  </div>
3096
- </article>`;return}if(t.innerHTML=`<style>${J}</style>
3097
- <article class="adr-card adr-card--${s}" role="article" aria-label="${r}">
3120
+ </article>`;return}t.innerHTML=`<style>${St}</style>
3121
+ <article class="adr-card adr-card--${r}" role="article" aria-label="${s}">
3098
3122
 
3099
3123
  <header class="adr-header">
3100
3124
  <div class="adr-meta">
3101
- ${this.adrId?`<span class="adr-id">${m(this.adrId)}</span>`:""}
3102
- ${a?`<span class="adr-date-wrap">${k(V.calendar)} <slot name="date"></slot></span>`:""}
3125
+ ${this.adrId?`<span class="adr-id">${p(this.adrId)}</span>`:""}
3126
+ ${a?`<span class="adr-date-wrap">${S(yt.calendar)} <slot name="date"></slot></span>`:""}
3103
3127
  </div>
3104
3128
  <div class="adr-badges">
3105
- <span class="adr-status" style="color:${e.color};background:${e.bg}">${m(e.label)}</span>
3129
+ <span class="adr-status" style="color:${e.color};background:${e.bg}">${p(e.label)}</span>
3106
3130
  </div>
3107
3131
  </header>
3108
3132
 
@@ -3114,20 +3138,20 @@ var re=`
3114
3138
  ${this.supersedes.length?`
3115
3139
  <div class="adr-links">
3116
3140
  <span class="adr-links-label">Supersedes</span>
3117
- ${this.supersedes.map(i=>`<a class="adr-link" href="#${m(i)}">${k(V.arrowRight)} ${m(i)}</a>`).join("")}
3141
+ ${this.supersedes.map(n=>`<a class="adr-link" href="#${p(n)}">${S(yt.arrowRight)} ${p(n)}</a>`).join("")}
3118
3142
  </div>`:""}
3119
3143
 
3120
3144
  ${this.supersededBy.length?`
3121
3145
  <div class="adr-links">
3122
3146
  <span class="adr-links-label">Superseded by</span>
3123
- ${this.supersededBy.map(i=>`<a class="adr-link" href="#${m(i)}">${k(V.arrowRight)} ${m(i)}</a>`).join("")}
3147
+ ${this.supersededBy.map(n=>`<a class="adr-link" href="#${p(n)}">${S(yt.arrowRight)} ${p(n)}</a>`).join("")}
3124
3148
  </div>`:""}
3125
3149
  </div>
3126
3150
 
3127
3151
  <div class="adr-sections">
3128
3152
  <div class="adr-section">
3129
3153
  <div class="adr-section-header">
3130
- <div class="adr-section-icon context">${k(V.context)}</div>
3154
+ <div class="adr-section-icon context">${S(yt.context)}</div>
3131
3155
  <span class="adr-section-title">Context</span>
3132
3156
  </div>
3133
3157
  <div class="adr-section-content">
@@ -3137,7 +3161,7 @@ var re=`
3137
3161
 
3138
3162
  <div class="adr-section">
3139
3163
  <div class="adr-section-header">
3140
- <div class="adr-section-icon decision">${k(V.decision)}</div>
3164
+ <div class="adr-section-icon decision">${S(yt.decision)}</div>
3141
3165
  <span class="adr-section-title">Decision</span>
3142
3166
  </div>
3143
3167
  <div class="adr-section-content">
@@ -3147,7 +3171,7 @@ var re=`
3147
3171
 
3148
3172
  <div class="adr-section">
3149
3173
  <div class="adr-section-header">
3150
- <div class="adr-section-icon consequences">${k(V.consequences)}</div>
3174
+ <div class="adr-section-icon consequences">${S(yt.consequences)}</div>
3151
3175
  <span class="adr-section-title">Consequences</span>
3152
3176
  </div>
3153
3177
  <div class="adr-section-content">
@@ -3156,11 +3180,11 @@ var re=`
3156
3180
  </div>
3157
3181
  </div>
3158
3182
 
3159
- </article>`,s==="compact")for(let i of t.querySelectorAll(".adr-section")){let o=i.querySelector("slot");o&&o.assignedNodes().length===0&&i.setAttribute("data-empty","")}this.dispatchEvent(new CustomEvent("adr-wc:ready",{detail:{adrId:this.adrId,title:this.adrTitle,status:this.status},bubbles:!0,composed:!0}))}};w("adr-wc",Bt);function be(n,t,e){let s=W(n?.sprintCount)>0?W(n.sprintCount)*(W(n.sprintWeeks)||1):W(n?.sprintWeeks),r=W(t?.teamFTE),a=cs(W(e),0,1);return!(s>0)||!(r>0)||!(a>0)?0:Math.ceil(s*r*a)}function os(n){let t=2166136261;for(let e=0;e<n.length;e++)t^=n.charCodeAt(e),t=Math.imul(t,16777619);return(t>>>0).toString(36)}function Ht(n){return n===null||typeof n!="object"?JSON.stringify(n):Array.isArray(n)?"["+n.map(Ht).join(",")+"]":"{"+Object.keys(n).sort().map(e=>JSON.stringify(e)+":"+Ht(n[e])).join(",")+"}"}function ge({time:n,cost:t,scope:e}){return os(Ht({time:n||{},cost:t||{},scope:e||{}}))}function W(n){if(n===""||n==null)return 0;let t=Number(n);return Number.isFinite(t)?t:0}function cs(n,t,e){return Math.max(t,Math.min(e,n))}function ls({time:n={},cost:t={},scope:e={}}={}){return{t:P(n.sprintCount,1)*P(n.sprintWeeks,1),c:P(t.teamFTE,0)*P(t.hoursPerWeek,40),s:P(e.mustHaveCount,0)+.5*P(e.shouldHaveCount,0)}}function ds(n){let t=[n.t,n.c,n.s].filter(r=>r>0);if(t.length===0)return{time:1,cost:1,scope:1};let e=Math.max(...t),s=r=>r<=0?.55:.55+(1.45-.55)*(r/e);return{time:s(n.t),cost:s(n.c),scope:s(n.s)}}function Ut(n,t=80){let e={scope:-Math.PI/2,time:5*Math.PI/6,cost:Math.PI/6},s=ds(ls(n)),r=a=>({x:Math.cos(e[a])*t*s[a],y:Math.sin(e[a])*t*s[a],factor:s[a]});return{scope:r("scope"),time:r("time"),cost:r("cost")}}function us(n={}){let t=P(n.sprintCount,0),e=P(n.sprintWeeks,0);if(t>0&&e>0){let s=t*e;return t>1?`${s} weeks (${t} \xD7 ${e}wk)`:`${s} week${s===1?"":"s"}`}return e>0?`${e} week${e===1?"":"s"}`:n.deadline?`until ${n.deadline}`:"TBD"}function ps(n={}){let t=Number(n.teamFTE),e=n.budgetTier,s=[];return Number.isFinite(t)&&t>0&&s.push(`${t} FTE`),e&&e!=="unset"&&s.push(e),s.length>0?s.join(" \xB7 "):"TBD"}function hs(n={}){let t=P(n.mustHaveCount,0),e=P(n.shouldHaveCount,0);return t>0&&e>0?`${t} must \xB7 ${e} should`:t>0?`${t} must-have`:e>0?`${e} should-have`:"TBD"}function ve(n){return typeof n=="string"&&n.trim().length>0?n:"TBD \u2014 click to set"}var q="http://www.w3.org/2000/svg",ms={scope:{dx:0,dy:-22,anchor:"middle"},time:{dx:-10,dy:14,anchor:"end"},cost:{dx:10,dy:14,anchor:"start"}},fs={scope:{dx:0,dy:-8,anchor:"middle"},time:{dx:-10,dy:28,anchor:"end"},cost:{dx:10,dy:28,anchor:"start"}},bs={scope:{name:"Scope",unit:"# features / story points"},time:{name:"Time",unit:"hours / days / weeks"},cost:{name:"Cost",unit:"FTE / $"}};function ye({value:n={},vertices:t,capacityPoints:e=0,capacitySource:s="formula",qualitySummary:r=""}={}){let a=t||Ut(n),i=document.createElementNS(q,"svg");i.setAttribute("viewBox","-220 -170 440 340"),i.setAttribute("role","group"),i.setAttribute("aria-label",`Project shape: ${e||0} capacity points. Click each corner to edit, or the center to open the quality compass.`);let o=document.createElementNS(q,"polygon");o.setAttribute("class","triangle"),o.setAttribute("points",[`${L(a.scope.x)},${L(a.scope.y)}`,`${L(a.time.x)},${L(a.time.y)}`,`${L(a.cost.x)},${L(a.cost.y)}`].join(" ")),i.append(o);let c=document.createElementNS(q,"g");c.setAttribute("class","center"),c.setAttribute("data-target","quality"),c.setAttribute("tabindex","0"),c.setAttribute("role","button"),c.setAttribute("aria-label",`Quality \u2014 ${ve(r)}. Activate to open the quality decision.`);let d=document.createElementNS(q,"circle");d.setAttribute("class","capacity-backdrop"),d.setAttribute("cx","0"),d.setAttribute("cy","4"),d.setAttribute("r","32"),c.append(d);let l=document.createElementNS(q,"rect");l.setAttribute("class","hit"),l.setAttribute("x","-36"),l.setAttribute("y","-30"),l.setAttribute("width","72"),l.setAttribute("height","68"),l.setAttribute("rx","34"),c.append(l);let u=document.createElementNS(q,"text");u.setAttribute("class","quality-label"),u.setAttribute("x","0"),u.setAttribute("y","-15"),u.setAttribute("text-anchor","middle"),u.textContent="Quality",c.append(u);let p=document.createElementNS(q,"text");p.setAttribute("class","capacity"),p.setAttribute("x","0"),p.setAttribute("y","7"),p.setAttribute("text-anchor","middle"),p.setAttribute("dominant-baseline","middle"),p.textContent=e>0?String(e):"\u2014",c.append(p);let h=document.createElementNS(q,"text");h.setAttribute("class","capacity-unit"),h.setAttribute("x","0"),h.setAttribute("y","26"),h.setAttribute("text-anchor","middle"),h.textContent=s==="manual"?"pts (manual)":"pts",c.append(h);let f=document.createElementNS(q,"title");f.textContent=ve(r),c.append(f),i.append(c);for(let b of["scope","time","cost"])i.append(gs(b,a[b],n));return i}function gs(n,t,e){let s=ms[n],r=fs[n],a=bs[n],i=n==="scope"?hs(e.scope):n==="cost"?ps(e.cost):us(e.time),o=document.createElementNS(q,"g");o.setAttribute("class","vertex"),o.setAttribute("data-axis",n),o.setAttribute("tabindex","0"),o.setAttribute("role","button"),o.setAttribute("aria-label",`${a.name} \u2014 ${i}. Activate to edit.`);let c=document.createElementNS(q,"rect");c.setAttribute("class","hit");let d=160,l=50,u;s.anchor==="end"?u=t.x-d+6:s.anchor==="start"?u=t.x-6:u=t.x-d/2;let p=n==="scope"?t.y-l+6:t.y-6;c.setAttribute("x",String(L(u))),c.setAttribute("y",String(L(p))),c.setAttribute("width",String(d)),c.setAttribute("height",String(l)),c.setAttribute("rx","6"),o.append(c);let h=document.createElementNS(q,"text");h.setAttribute("class","vertex-name"),h.setAttribute("x",String(L(t.x+s.dx))),h.setAttribute("y",String(L(t.y+s.dy))),h.setAttribute("text-anchor",s.anchor),h.textContent=a.name,o.append(h);let f=document.createElementNS(q,"text");f.setAttribute("class","vertex-summary"),f.setAttribute("x",String(L(t.x+r.dx))),f.setAttribute("y",String(L(t.y+r.dy))),f.setAttribute("text-anchor",r.anchor),f.textContent=i,o.append(f);let b=document.createElementNS(q,"title");return b.textContent=`${a.name}: ${i} \u2014 ${a.unit}`,o.append(b),o}function P(n,t){if(n===""||n==null)return t;let e=Number(n);return Number.isFinite(e)&&e>0?e:t}function L(n){return Math.round(n*100)/100}var lt=["time","cost","scope"],dt={time:[{key:"sprintWeeks",label:"Sprint length (weeks)",type:"number",min:1,step:1,value:2,width:"6rem"},{key:"sprintCount",label:"Number of sprints",type:"number",min:1,step:1,value:3,width:"6rem"},{key:"hoursPerWeek",label:"Hours per week (per FTE)",type:"number",min:1,max:168,step:1,value:40,width:"6rem"},{key:"deadline",label:"Deadline (optional)",type:"date",width:"12rem"}],cost:[{key:"teamFTE",label:"Team size (FTE)",type:"number",min:0,step:.5,value:1,width:"6rem"},{key:"budgetTier",label:"Budget tier",type:"select",options:[["solo","Solo"],["small","Small (2-5)"],["medium","Medium (6-15)"],["large","Large (16+)"]],value:"solo",width:"14rem"},{key:"contractorBudget",label:"Contractor budget ($, optional)",type:"number",min:0,step:100,width:"10rem"}],scope:[{key:"mustHaveCount",label:"Must-have feature count",type:"number",min:0,step:1,width:"6rem"},{key:"shouldHaveCount",label:"Should-have feature count",type:"number",min:0,step:1,width:"6rem"},{key:"scopeNotes",label:"Notes",type:"textarea",rows:3,maxlength:2e3}]},xe={scope:"Scope",time:"Time",cost:"Cost"},Vt=class extends C{static formAssociated=!0;static get observedAttributes(){return["data-focus-factor","data-min-capacity","data-quality-href","data-quality-summary","disabled","locked"]}#e;#t={time:{},cost:{},scope:{},capacityPoints:0,capacitySource:"formula",hash:""};#s=null;#i=[];#r="";#n={};#a=null;#o=null;#c=null;constructor(){super(),this.#e=this.attachInternals(),this._adoptInternals(this.#e)}setup(){this.#r=this.getAttribute("data-quality-summary")||"",this.#v(),this.#A(),this.#h(),this.#k(),this.listen(this,"click",t=>this.#p(t)),this.listen(this,"keydown",t=>this.#l(t))}attributeChangedCallback(t){this.isConnected&&(t==="data-focus-factor"||t==="data-min-capacity"?this.#d({source:"attribute"}):t==="data-quality-summary"?(this.#r=this.getAttribute("data-quality-summary")||"",this.#h()):(t==="disabled"||t==="locked")&&this.#x())}get value(){return JSON.parse(JSON.stringify({...this.#t,revisionLog:this.#i}))}set value(t){if(!(!t||typeof t!="object")){for(let e of lt)t[e]&&typeof t[e]=="object"&&(this.#t[e]={...t[e]});t.capacitySource==="manual"&&Number.isFinite(t.capacityPoints)?(this.#s=t.capacityPoints,this.#t.capacitySource="manual"):(this.#s=null,this.#t.capacitySource="formula"),Array.isArray(t.revisionLog)&&(this.#i=[...t.revisionLog]),this.#b(),this.#d({source:"property"})}}get capacityPoints(){return this.#t.capacityPoints}get capacitySource(){return this.#t.capacitySource}get hash(){return this.#t.hash}get revisionLog(){return JSON.parse(JSON.stringify(this.#i))}get qualitySummary(){return this.#r}set qualitySummary(t){this.#r=String(t??""),this.#h()}openEditor(t){if(!lt.includes(t)||this.#w)return;let e=this.#m(t);typeof e.showModal=="function"?e.showModal():e.setAttribute("open","")}revise(t,e,s){if(!t||typeof s!="string"||s.length<10)throw new Error("iron-triangle: revise() requires field and a reason of at least 10 characters");let r=this.#N(t);this.#E(t,e);let a={field:t,from:r,to:e,reason:s};this.#i.push({revisedAt:new Date().toISOString(),changes:[a]}),this.dispatchEvent(new CustomEvent("iron-triangle:revise",{bubbles:!0,composed:!0,detail:a})),this.#b(),this.#d({source:"revise"})}setManual(t){let e=Math.max(1,Math.floor(Number(t)||0));this.#s=e;let s=this.#t.capacitySource;this.#t.capacitySource="manual",s!=="manual"&&this.dispatchEvent(new CustomEvent("iron-triangle:mode",{bubbles:!0,composed:!0,detail:{from:s,to:"manual"}})),this.setState("manual",!0),this.setState("formula",!1),this.#d({source:"manual"})}setFormula(){this.#s=null;let t=this.#t.capacitySource;this.#t.capacitySource="formula",t!=="formula"&&this.dispatchEvent(new CustomEvent("iron-triangle:mode",{bubbles:!0,composed:!0,detail:{from:t,to:"formula"}})),this.setState("manual",!1),this.setState("formula",!0),this.#d({source:"formula"})}recalc(){this.#d({source:"recalc"})}#p(t){let e=t.target.closest?.(".vertex[data-axis]");if(e&&this.contains(e)){t.preventDefault(),this.openEditor(e.dataset.axis);return}let s=t.target.closest?.('.center[data-target="quality"]');s&&this.contains(s)&&(t.preventDefault(),this.hasAttribute("disabled")||this.#u())}#l(t){if(t.key!=="Enter"&&t.key!==" ")return;let e=t.target.closest?.(".vertex[data-axis]");if(e&&this.contains(e)){t.preventDefault(),this.openEditor(e.dataset.axis);return}let s=t.target.closest?.('.center[data-target="quality"]');s&&this.contains(s)&&(t.preventDefault(),this.hasAttribute("disabled")||this.#u())}#u(){let t=new CustomEvent("iron-triangle:open-quality",{bubbles:!0,composed:!0,cancelable:!0,detail:{qualitySummary:this.#r,capacityPoints:this.#t.capacityPoints}});if(this.dispatchEvent(t)){let s=this.getAttribute("data-quality-href");s&&window.location.assign(s)}}#m(t){if(this.#n[t])return this.#n[t];let e=document.createElement("dialog");e.className=`iron-triangle-dialog iron-triangle-dialog--${t}`,e.setAttribute("aria-label",`${xe[t]} \u2014 edit`);let s=document.createElement("form");s.method="dialog",s.setAttribute("data-layout","stack"),s.setAttribute("data-layout-gap","m");let r=document.createElement("h3");r.textContent=xe[t],s.append(r);for(let c of dt[t])s.append(_e(t,c,this.#t[t]?.[c.key]));let a=document.createElement("div");a.setAttribute("data-layout","cluster"),a.setAttribute("data-layout-gap","s"),a.setAttribute("data-layout-justify","end");let i=document.createElement("button");i.type="button",i.value="cancel",i.textContent="Cancel",i.addEventListener("click",()=>e.close("cancel"));let o=document.createElement("button");return o.type="submit",o.value="save",o.textContent="Save",a.append(i,o),s.append(a),e.append(s),this.append(e),this.#n[t]=e,s.addEventListener("submit",c=>{c.preventDefault(),this.#g(t,s),e.close("save"),this.#d({source:"dialog",field:t})}),this.#x(),e}#g(t,e){let s={};for(let r of dt[t]){let a=e.querySelector(`[name="${t}.${r.key}"]`);if(!a)continue;let i=a.type==="checkbox"?a.checked:a.value;if(!(i===""||i==null))if(r.type==="number"){let o=Number(i);Number.isFinite(o)&&(s[r.key]=o)}else s[r.key]=i}this.#t[t]=s}#b(){for(let t of lt){let e=this.#n[t];if(e)for(let s of dt[t]){let r=e.querySelector(`[name="${t}.${s.key}"]`);if(!r)continue;let a=this.#t[t]?.[s.key];r.value=a==null?"":String(a)}}}#v(){for(let t of lt)for(let e of dt[t])e.value!==void 0&&this.#t[t][e.key]===void 0&&(this.#t[t][e.key]=e.value);this.#d({source:"init"})}#d({source:t,field:e}={}){let s=Number(this.dataset.focusFactor??.6),r=Number(this.dataset.minCapacity??1),a;this.#t.capacitySource==="manual"&&this.#s!=null?a=this.#s:a=be(this.#t.time,this.#t.cost,s),Number.isFinite(r)&&a>0&&a<r&&(a=r),this.#t.capacityPoints=a,this.#t.hash=ge(this.#t),this.#h(),this.#y(),this.#k(),this.#f(),this.dispatchEvent(new CustomEvent("iron-triangle:change",{bubbles:!0,composed:!0,detail:{...this.value,source:t,field:e}}))}#h(){let t=ye({value:this.#t,vertices:Ut(this.#t),capacityPoints:this.#t.capacityPoints,capacitySource:this.#t.capacitySource,qualitySummary:this.#r}),e=this.querySelector(":scope > svg");e?e.replaceWith(t):this.prepend(t),this.#_(),this.dataset.capacityPoints=String(this.#t.capacityPoints),this.dataset.capacitySource=this.#t.capacitySource}#y(){this.setState("formula",this.#t.capacitySource==="formula"),this.setState("manual",this.#t.capacitySource==="manual"),this.setState("unbudgeted",!(this.#t.capacityPoints>0));let t=this.#t.time?.deadline,e=!1;if(t){let s=new Date(t).getTime();Number.isFinite(s)&&(e=s<Date.now())}this.setState("over-deadline",e)}#f(){try{this.#e.setFormValue(JSON.stringify(this.value))}catch{}}get#w(){return this.hasAttribute("disabled")||this.hasAttribute("locked")}#x(){let t=this.#w;this.#o&&(this.#o.disabled=t);for(let e of Object.values(this.#n))for(let s of e.querySelectorAll("input, select, textarea, button"))s.disabled=t;this.#_()}#_(){let t=this.#w,e=this.hasAttribute("disabled");for(let s of this.querySelectorAll(':scope > svg [role="button"][tabindex]')){let r=s.matches('.center[data-target="quality"]')?e:t;s.setAttribute("tabindex",r?"-1":"0"),r?s.setAttribute("aria-disabled","true"):s.removeAttribute("aria-disabled")}}#A(){if(this.querySelector(":scope > .iron-triangle-status"))return;let t=document.createElement("div");t.className="iron-triangle-status";let e=document.createElement("output");e.className="iron-triangle-readout",e.setAttribute("aria-live","polite"),e.setAttribute("aria-atomic","true");let s=document.createElement("button");s.type="button",s.className="iron-triangle-mode ghost",s.setAttribute("aria-pressed","false"),s.textContent="Manual capacity",s.addEventListener("click",()=>this.#C());let r=document.createElement("p");r.className="iron-triangle-warning",r.setAttribute("data-warning","over-deadline"),r.hidden=!0,t.append(e,s,r);let a=this.querySelector(":scope > svg");a?a.after(t):this.prepend(t),this.#a=e,this.#o=s,this.#c=r,this.#x()}#k(){if(!this.#a)return;let{capacityPoints:t,capacitySource:e}=this.#t,s=e==="manual",r=this.#t.time?.deadline,a=this.matches(":state(over-deadline)"),i=[];i.push(t>0?`Capacity: ${t} points (${s?"manual":"formula"}).`:"Capacity: not yet budgeted."),a&&i.push(`Deadline has passed (${r}).`);let o=i.join(" ");if(this.#a.textContent!==o&&(this.#a.textContent=o),this.#o){this.#o.setAttribute("aria-pressed",s?"true":"false");let c=s&&t>0?`Manual capacity: ${t} pts`:"Manual capacity";this.#o.textContent!==c&&(this.#o.textContent=c),this.#o.setAttribute("aria-label",s?`${c}. Activate to edit or return to the formula.`:`${c}. Activate to override the formula with a fixed number.`)}this.#c&&(this.#c.textContent=a?`Deadline has passed (${r})`:"",this.#c.hidden=!a)}#C(){let t=this.#T(),e=t.querySelector('[name="capacity.points"]');e.value=String(this.#t.capacityPoints>0?this.#t.capacityPoints:1);let s=t.querySelector('button[value="formula"]');s.hidden=this.#t.capacitySource!=="manual",typeof t.showModal=="function"?t.showModal():t.setAttribute("open","")}#T(){if(this.#n.capacity)return this.#n.capacity;let t=document.createElement("dialog");t.className="iron-triangle-dialog iron-triangle-dialog--capacity",t.setAttribute("aria-label","Capacity \u2014 manual override");let e=document.createElement("form");e.method="dialog",e.setAttribute("data-layout","stack"),e.setAttribute("data-layout-gap","m");let s=document.createElement("h3");s.textContent="Manual capacity",e.append(s);let r=document.createElement("p");r.className="iron-triangle-dialog__hint",r.textContent="Fix the capacity to a number the team committed to. The Time / Cost / Scope inputs stay saved but stop driving the readout.",e.append(r),e.append(_e("capacity",{key:"points",label:"Capacity (points)",type:"number",min:1,step:1,width:"6rem"},this.#t.capacityPoints));let a=document.createElement("div");a.setAttribute("data-layout","cluster"),a.setAttribute("data-layout-gap","s"),a.setAttribute("data-layout-justify","end");let i=document.createElement("button");i.type="button",i.value="formula",i.textContent="Use formula",i.addEventListener("click",()=>{t.close("formula"),this.setFormula()});let o=document.createElement("button");o.type="button",o.value="cancel",o.textContent="Cancel",o.addEventListener("click",()=>t.close("cancel"));let c=document.createElement("button");return c.type="submit",c.value="save",c.textContent="Save",a.append(i,o,c),e.append(a),t.append(e),this.append(t),this.#n.capacity=t,e.addEventListener("submit",d=>{d.preventDefault();let l=e.querySelector('[name="capacity.points"]'),u=Number(l.value);t.close("save"),Number.isFinite(u)&&u>0&&this.setManual(u)}),this.#x(),t}#N(t){if(t==="capacityPoints")return this.#t.capacityPoints;let[e,s]=t.split(".");return e&&s?this.#t[e]?.[s]:void 0}#E(t,e){if(t==="capacityPoints"){this.setManual(e);return}let[s,r]=t.split(".");!s||!r||(this.#t[s]||(this.#t[s]={}),this.#t[s][r]=e)}};function _e(n,t,e){let s=document.createElement("form-field"),r=`${n}-${t.key}`,a=document.createElement("label");a.setAttribute("for",r),a.textContent=t.label,s.append(a);let i;if(t.type==="select"){i=document.createElement("select");for(let[o,c]of t.options){let d=document.createElement("option");d.value=o,d.textContent=c,(e===o||e==null&&t.value===o)&&(d.selected=!0),i.append(d)}}else t.type==="textarea"?(i=document.createElement("textarea"),t.rows&&(i.rows=t.rows),t.maxlength&&(i.maxLength=t.maxlength),e!=null&&(i.value=String(e))):(i=document.createElement("input"),i.type=t.type,t.min!=null&&(i.min=String(t.min)),t.max!=null&&(i.max=String(t.max)),t.step!=null&&(i.step=String(t.step)),e!=null?i.value=String(e):t.value!=null&&(i.value=String(t.value)));return i.id=r,i.name=`${n}.${t.key}`,t.width&&(i.style.inlineSize=t.width),s.append(i),s}w("iron-triangle",Vt);function vs(n){if(!n)return 0;let t=n.dataset?.capacityCost??n.getAttribute?.("data-capacity-cost"),e=Number(t);return Number.isFinite(e)&&e>0?e:0}function we(n){let t=0;for(let e of n||[])t+=vs(e);return t}function Wt({capacityPoints:n,qualitySum:t,featureSum:e}){let s=Number.isFinite(n)?n:1/0,r=Math.max(0,Number(t)||0),a=Math.max(0,Number(e)||0),i=Number.isFinite(s)?s-r-a:1/0;return{capacity:s,quality:r,features:a,slack:i}}function Ae({capacity:n,quality:t,features:e}){if(!Number.isFinite(n)||n<=0){let a=t+e;return a<=0?{quality:0,features:0,slack:100}:{quality:t/a*100,features:e/a*100,slack:0}}let s=t+e,r=Math.max(n,s);return{quality:t/r*100,features:e/r*100,slack:Math.max(0,(n-s)/r*100)}}var Qt=class extends C{static get observedAttributes(){return["data-bind-triangle","data-bind-quality"]}#e=null;#t=null;#s=null;#i=null;#r=!1;setup(){this.#a(),this.#o(),this.#c(),this.#u()}teardown(){this.#e?.(),this.#t?.(),this.#s?.disconnect(),this.#e=null,this.#t=null,this.#s=null}attributeChangedCallback(t){this.isConnected&&(t==="data-bind-triangle"?(this.#a(),this.#u()):t==="data-bind-quality"&&(this.#o(),this.#u()))}get capacityPoints(){return this.#p()}get qualitySum(){return this.#l()}get featureSum(){return this.#i!=null?this.#i:we(this.querySelectorAll("[data-capacity-cost]"))}set featureSum(t){this.#i=Number.isFinite(+t)?+t:null,this.#u()}get slack(){return Wt({capacityPoints:this.#p(),qualitySum:this.#l(),featureSum:this.featureSum}).slack}#n(t){if(!t)return null;let e=this.getRootNode();return e.getElementById?e.getElementById(t):document.getElementById(t)}#a(){this.#e?.(),this.#e=null;let t=this.#n(this.dataset.bindTriangle);if(!t||t.localName!=="iron-triangle")return;let e=()=>this.#u();t.addEventListener("iron-triangle:change",e),this.#e=()=>t.removeEventListener("iron-triangle:change",e)}#o(){this.#t?.(),this.#t=null;let t=this.#n(this.dataset.bindQuality);if(!t||t.localName!=="quality-target")return;let e=()=>this.#u();t.addEventListener("quality-target:change",e),this.#t=()=>t.removeEventListener("quality-target:change",e)}#c(){this.#s||(this.#s=new MutationObserver(t=>{t.some(s=>!s.target.closest?.("[data-capacity-table]"))&&this.#u()}),this.#s.observe(this,{childList:!0,subtree:!0,attributes:!0,attributeFilter:["data-capacity-cost"]}))}#p(){let t=this.#n(this.dataset.bindTriangle);if(!t||t.localName!=="iron-triangle")return 1/0;let e=t.capacityPoints;return Number.isFinite(e)&&e>0?e:1/0}#l(){let t=this.#n(this.dataset.bindQuality);return!t||t.localName!=="quality-target"?0:Number(t.criticalSum)||0}#u(){let t=Wt({capacityPoints:this.#p(),qualitySum:this.#l(),featureSum:this.featureSum}),e=Ae(t),s=this.querySelector(":scope > [data-capacity-table]");s||(s=document.createElement("section"),s.dataset.capacityTable="",this.prepend(s));let r=ys(t.capacity),a=t.quality>0?`\u2212${t.quality} pts`:"0 pts",i=t.features>0?`\u2212${t.features} pts`:"0 pts",o=xs(t.slack);s.innerHTML=`
3183
+ </article>`,r==="compact"&&ft(t,".adr-section")}};A("adr-wc",_e);function tr(i,t,e){let r=xt(i?.sprintCount)>0?xt(i.sprintCount)*(xt(i.sprintWeeks)||1):xt(i?.sprintWeeks),s=xt(t?.teamFTE),a=os(xt(e),0,1);return!(r>0)||!(s>0)||!(a>0)?0:Math.ceil(r*s*a)}function ns(i){let t=2166136261;for(let e=0;e<i.length;e++)t^=i.charCodeAt(e),t=Math.imul(t,16777619);return(t>>>0).toString(36)}function we(i){return i===null||typeof i!="object"?JSON.stringify(i):Array.isArray(i)?"["+i.map(we).join(",")+"]":"{"+Object.keys(i).sort().map(e=>JSON.stringify(e)+":"+we(i[e])).join(",")+"}"}function er({time:i,cost:t,scope:e}){return ns(we({time:i||{},cost:t||{},scope:e||{}}))}function xt(i){if(i===""||i==null)return 0;let t=Number(i);return Number.isFinite(t)?t:0}function os(i,t,e){return Math.max(t,Math.min(e,i))}function cs({time:i={},cost:t={},scope:e={}}={}){return{t:X(i.sprintCount,1)*X(i.sprintWeeks,1),c:X(t.teamFTE,0)*X(t.hoursPerWeek,40),s:X(e.mustHaveCount,0)+.5*X(e.shouldHaveCount,0)}}function ls(i){let t=[i.t,i.c,i.s].filter(s=>s>0);if(t.length===0)return{time:1,cost:1,scope:1};let e=Math.max(...t),r=s=>s<=0?.55:.55+(1.45-.55)*(s/e);return{time:r(i.t),cost:r(i.c),scope:r(i.s)}}function Ae(i,t=80){let e={scope:-Math.PI/2,time:5*Math.PI/6,cost:Math.PI/6},r=ls(cs(i)),s=a=>({x:Math.cos(e[a])*t*r[a],y:Math.sin(e[a])*t*r[a],factor:r[a]});return{scope:s("scope"),time:s("time"),cost:s("cost")}}function ds(i={}){let t=X(i.sprintCount,0),e=X(i.sprintWeeks,0);if(t>0&&e>0){let r=t*e;return t>1?`${r} weeks (${t} \xD7 ${e}wk)`:`${r} week${r===1?"":"s"}`}return e>0?`${e} week${e===1?"":"s"}`:i.deadline?`until ${i.deadline}`:"TBD"}function us(i={}){let t=Number(i.teamFTE),e=i.budgetTier,r=[];return Number.isFinite(t)&&t>0&&r.push(`${t} FTE`),e&&e!=="unset"&&r.push(e),r.length>0?r.join(" \xB7 "):"TBD"}function ps(i={}){let t=X(i.mustHaveCount,0),e=X(i.shouldHaveCount,0);return t>0&&e>0?`${t} must \xB7 ${e} should`:t>0?`${t} must-have`:e>0?`${e} should-have`:"TBD"}function rr(i){return typeof i=="string"&&i.trim().length>0?i:"TBD \u2014 click to set"}var O="http://www.w3.org/2000/svg",hs={scope:{dx:0,dy:-22,anchor:"middle"},time:{dx:-10,dy:14,anchor:"end"},cost:{dx:10,dy:14,anchor:"start"}},ms={scope:{dx:0,dy:-8,anchor:"middle"},time:{dx:-10,dy:28,anchor:"end"},cost:{dx:10,dy:28,anchor:"start"}},fs={scope:{name:"Scope",unit:"# features / story points"},time:{name:"Time",unit:"hours / days / weeks"},cost:{name:"Cost",unit:"FTE / $"}};function sr({value:i={},vertices:t,capacityPoints:e=0,capacitySource:r="formula",qualitySummary:s=""}={}){let a=t||Ae(i),n=document.createElementNS(O,"svg");n.setAttribute("viewBox","-220 -170 440 340"),n.setAttribute("role","group"),n.setAttribute("aria-label",`Project shape: ${e||0} capacity points. Click each corner to edit, or the center to open the quality compass.`);let o=document.createElementNS(O,"polygon");o.setAttribute("class","triangle"),o.setAttribute("points",[`${U(a.scope.x)},${U(a.scope.y)}`,`${U(a.time.x)},${U(a.time.y)}`,`${U(a.cost.x)},${U(a.cost.y)}`].join(" ")),n.append(o);let l=document.createElementNS(O,"g");l.setAttribute("class","center"),l.setAttribute("data-target","quality"),l.setAttribute("tabindex","0"),l.setAttribute("role","button"),l.setAttribute("aria-label",`Quality \u2014 ${rr(s)}. Activate to open the quality decision.`);let d=document.createElementNS(O,"circle");d.setAttribute("class","capacity-backdrop"),d.setAttribute("cx","0"),d.setAttribute("cy","4"),d.setAttribute("r","32"),l.append(d);let c=document.createElementNS(O,"rect");c.setAttribute("class","hit"),c.setAttribute("x","-36"),c.setAttribute("y","-30"),c.setAttribute("width","72"),c.setAttribute("height","68"),c.setAttribute("rx","34"),l.append(c);let u=document.createElementNS(O,"text");u.setAttribute("class","quality-label"),u.setAttribute("x","0"),u.setAttribute("y","-15"),u.setAttribute("text-anchor","middle"),u.textContent="Quality",l.append(u);let m=document.createElementNS(O,"text");m.setAttribute("class","capacity"),m.setAttribute("x","0"),m.setAttribute("y","7"),m.setAttribute("text-anchor","middle"),m.setAttribute("dominant-baseline","middle"),m.textContent=e>0?String(e):"\u2014",l.append(m);let f=document.createElementNS(O,"text");f.setAttribute("class","capacity-unit"),f.setAttribute("x","0"),f.setAttribute("y","26"),f.setAttribute("text-anchor","middle"),f.textContent=r==="manual"?"pts (manual)":"pts",l.append(f);let h=document.createElementNS(O,"title");h.textContent=rr(s),l.append(h),n.append(l);for(let b of["scope","time","cost"])n.append(bs(b,a[b],i));return n}function bs(i,t,e){let r=hs[i],s=ms[i],a=fs[i],n=i==="scope"?ps(e.scope):i==="cost"?us(e.cost):ds(e.time),o=document.createElementNS(O,"g");o.setAttribute("class","vertex"),o.setAttribute("data-axis",i),o.setAttribute("tabindex","0"),o.setAttribute("role","button"),o.setAttribute("aria-label",`${a.name} \u2014 ${n}. Activate to edit.`);let l=document.createElementNS(O,"rect");l.setAttribute("class","hit");let d=160,c=50,u;r.anchor==="end"?u=t.x-d+6:r.anchor==="start"?u=t.x-6:u=t.x-d/2;let m=i==="scope"?t.y-c+6:t.y-6;l.setAttribute("x",String(U(u))),l.setAttribute("y",String(U(m))),l.setAttribute("width",String(d)),l.setAttribute("height",String(c)),l.setAttribute("rx","6"),o.append(l);let f=document.createElementNS(O,"text");f.setAttribute("class","vertex-name"),f.setAttribute("x",String(U(t.x+r.dx))),f.setAttribute("y",String(U(t.y+r.dy))),f.setAttribute("text-anchor",r.anchor),f.textContent=a.name,o.append(f);let h=document.createElementNS(O,"text");h.setAttribute("class","vertex-summary"),h.setAttribute("x",String(U(t.x+s.dx))),h.setAttribute("y",String(U(t.y+s.dy))),h.setAttribute("text-anchor",s.anchor),h.textContent=n,o.append(h);let b=document.createElementNS(O,"title");return b.textContent=`${a.name}: ${n} \u2014 ${a.unit}`,o.append(b),o}function X(i,t){if(i===""||i==null)return t;let e=Number(i);return Number.isFinite(e)&&e>0?e:t}function U(i){return Math.round(i*100)/100}var Bt=["time","cost","scope"],Ht={time:[{key:"sprintWeeks",label:"Sprint length (weeks)",type:"number",min:1,step:1,value:2,width:"6rem"},{key:"sprintCount",label:"Number of sprints",type:"number",min:1,step:1,value:3,width:"6rem"},{key:"hoursPerWeek",label:"Hours per week (per FTE)",type:"number",min:1,max:168,step:1,value:40,width:"6rem"},{key:"deadline",label:"Deadline (optional)",type:"date",width:"12rem"}],cost:[{key:"teamFTE",label:"Team size (FTE)",type:"number",min:0,step:.5,value:1,width:"6rem"},{key:"budgetTier",label:"Budget tier",type:"select",options:[["solo","Solo"],["small","Small (2-5)"],["medium","Medium (6-15)"],["large","Large (16+)"]],value:"solo",width:"14rem"},{key:"contractorBudget",label:"Contractor budget ($, optional)",type:"number",min:0,step:100,width:"10rem"}],scope:[{key:"mustHaveCount",label:"Must-have feature count",type:"number",min:0,step:1,width:"6rem"},{key:"shouldHaveCount",label:"Should-have feature count",type:"number",min:0,step:1,width:"6rem"},{key:"scopeNotes",label:"Notes",type:"textarea",rows:3,maxlength:2e3}]},ar={scope:"Scope",time:"Time",cost:"Cost"},ke=class extends C{static formAssociated=!0;static get observedAttributes(){return["data-focus-factor","data-min-capacity","data-quality-href","data-quality-summary","disabled","locked"]}#e;#t={time:{},cost:{},scope:{},capacityPoints:0,capacitySource:"formula",hash:""};#r=null;#a=[];#s="";#i={};#c=null;#n=null;#d=null;constructor(){super(),this.#e=this.attachInternals(),this._adoptInternals(this.#e)}setup(){this.#s=this.getAttribute("data-quality-summary")||"",this.#g(),this.#p(),this.#x(),this.#f(),this.listen(this,"click",t=>this.#o(t)),this.listen(this,"keydown",t=>this.#l(t))}attributeChangedCallback(t){this.isConnected&&(t==="data-focus-factor"||t==="data-min-capacity"?this.#h({source:"attribute"}):t==="data-quality-summary"?(this.#s=this.getAttribute("data-quality-summary")||"",this.#x()):(t==="disabled"||t==="locked")&&this.#v())}get value(){return JSON.parse(JSON.stringify({...this.#t,revisionLog:this.#a}))}set value(t){if(!(!t||typeof t!="object")){for(let e of Bt)t[e]&&typeof t[e]=="object"&&(this.#t[e]={...t[e]});t.capacitySource==="manual"&&Number.isFinite(t.capacityPoints)?(this.#r=t.capacityPoints,this.#t.capacitySource="manual"):(this.#r=null,this.#t.capacitySource="formula"),Array.isArray(t.revisionLog)&&(this.#a=[...t.revisionLog]),this.#b(),this.#h({source:"property"})}}get capacityPoints(){return this.#t.capacityPoints}get capacitySource(){return this.#t.capacitySource}get hash(){return this.#t.hash}get revisionLog(){return JSON.parse(JSON.stringify(this.#a))}get qualitySummary(){return this.#s}set qualitySummary(t){this.#s=String(t??""),this.#x()}openEditor(t){if(!Bt.includes(t)||this.#A)return;let e=this.#y(t);typeof e.showModal=="function"?e.showModal():e.setAttribute("open","")}revise(t,e,r){if(!t||typeof r!="string"||r.length<10)throw new Error("iron-triangle: revise() requires field and a reason of at least 10 characters");let s=this.#$(t);this.#C(t,e);let a={field:t,from:s,to:e,reason:r};this.#a.push({revisedAt:new Date().toISOString(),changes:[a]}),this.dispatchEvent(new CustomEvent("iron-triangle:revise",{bubbles:!0,composed:!0,detail:a})),this.#b(),this.#h({source:"revise"})}setManual(t){let e=Math.max(1,Math.floor(Number(t)||0));this.#r=e;let r=this.#t.capacitySource;this.#t.capacitySource="manual",r!=="manual"&&this.dispatchEvent(new CustomEvent("iron-triangle:mode",{bubbles:!0,composed:!0,detail:{from:r,to:"manual"}})),this.setState("manual",!0),this.setState("formula",!1),this.#h({source:"manual"})}setFormula(){this.#r=null;let t=this.#t.capacitySource;this.#t.capacitySource="formula",t!=="formula"&&this.dispatchEvent(new CustomEvent("iron-triangle:mode",{bubbles:!0,composed:!0,detail:{from:t,to:"formula"}})),this.setState("manual",!1),this.setState("formula",!0),this.#h({source:"formula"})}recalc(){this.#h({source:"recalc"})}#o(t){let e=t.target.closest?.(".vertex[data-axis]");if(e&&this.contains(e)){t.preventDefault(),this.openEditor(e.dataset.axis);return}let r=t.target.closest?.('.center[data-target="quality"]');r&&this.contains(r)&&(t.preventDefault(),this.hasAttribute("disabled")||this.#u())}#l(t){if(t.key!=="Enter"&&t.key!==" ")return;let e=t.target.closest?.(".vertex[data-axis]");if(e&&this.contains(e)){t.preventDefault(),this.openEditor(e.dataset.axis);return}let r=t.target.closest?.('.center[data-target="quality"]');r&&this.contains(r)&&(t.preventDefault(),this.hasAttribute("disabled")||this.#u())}#u(){let t=new CustomEvent("iron-triangle:open-quality",{bubbles:!0,composed:!0,cancelable:!0,detail:{qualitySummary:this.#s,capacityPoints:this.#t.capacityPoints}});if(this.dispatchEvent(t)){let r=this.getAttribute("data-quality-href");r&&window.location.assign(r)}}#y(t){if(this.#i[t])return this.#i[t];let e=document.createElement("dialog");e.className=`iron-triangle-dialog iron-triangle-dialog--${t}`,e.setAttribute("aria-label",`${ar[t]} \u2014 edit`);let r=document.createElement("form");r.method="dialog",r.setAttribute("data-layout","stack"),r.setAttribute("data-layout-gap","m");let s=document.createElement("h3");s.textContent=ar[t],r.append(s);for(let l of Ht[t])r.append(ir(t,l,this.#t[t]?.[l.key]));let a=document.createElement("div");a.setAttribute("data-layout","cluster"),a.setAttribute("data-layout-gap","s"),a.setAttribute("data-layout-justify","end");let n=document.createElement("button");n.type="button",n.value="cancel",n.textContent="Cancel",n.addEventListener("click",()=>e.close("cancel"));let o=document.createElement("button");return o.type="submit",o.value="save",o.textContent="Save",a.append(n,o),r.append(a),e.append(r),this.append(e),this.#i[t]=e,r.addEventListener("submit",l=>{l.preventDefault(),this.#E(t,r),e.close("save"),this.#h({source:"dialog",field:t})}),this.#v(),e}#E(t,e){let r={};for(let s of Ht[t]){let a=e.querySelector(`[name="${t}.${s.key}"]`);if(!a)continue;let n=a.type==="checkbox"?a.checked:a.value;if(!(n===""||n==null))if(s.type==="number"){let o=Number(n);Number.isFinite(o)&&(r[s.key]=o)}else r[s.key]=n}this.#t[t]=r}#b(){for(let t of Bt){let e=this.#i[t];if(e)for(let r of Ht[t]){let s=e.querySelector(`[name="${t}.${r.key}"]`);if(!s)continue;let a=this.#t[t]?.[r.key];s.value=a==null?"":String(a)}}}#g(){for(let t of Bt)for(let e of Ht[t])e.value!==void 0&&this.#t[t][e.key]===void 0&&(this.#t[t][e.key]=e.value);this.#h({source:"init"})}#h({source:t,field:e}={}){let r=Number(this.dataset.focusFactor??.6),s=Number(this.dataset.minCapacity??1),a;this.#t.capacitySource==="manual"&&this.#r!=null?a=this.#r:a=tr(this.#t.time,this.#t.cost,r),Number.isFinite(s)&&a>0&&a<s&&(a=s),this.#t.capacityPoints=a,this.#t.hash=er(this.#t),this.#x(),this.#_(),this.#f(),this.#w(),this.dispatchEvent(new CustomEvent("iron-triangle:change",{bubbles:!0,composed:!0,detail:{...this.value,source:t,field:e}}))}#x(){let t=sr({value:this.#t,vertices:Ae(this.#t),capacityPoints:this.#t.capacityPoints,capacitySource:this.#t.capacitySource,qualitySummary:this.#s}),e=this.querySelector(":scope > svg");e?e.replaceWith(t):this.prepend(t),this.#m(),this.dataset.capacityPoints=String(this.#t.capacityPoints),this.dataset.capacitySource=this.#t.capacitySource}#_(){this.setState("formula",this.#t.capacitySource==="formula"),this.setState("manual",this.#t.capacitySource==="manual"),this.setState("unbudgeted",!(this.#t.capacityPoints>0));let t=this.#t.time?.deadline,e=!1;if(t){let r=new Date(t).getTime();Number.isFinite(r)&&(e=r<Date.now())}this.setState("over-deadline",e)}#w(){try{this.#e.setFormValue(JSON.stringify(this.value))}catch{}}get#A(){return this.hasAttribute("disabled")||this.hasAttribute("locked")}#v(){let t=this.#A;this.#n&&(this.#n.disabled=t);for(let e of Object.values(this.#i))for(let r of e.querySelectorAll("input, select, textarea, button"))r.disabled=t;this.#m()}#m(){let t=this.#A,e=this.hasAttribute("disabled");for(let r of this.querySelectorAll(':scope > svg [role="button"][tabindex]')){let s=r.matches('.center[data-target="quality"]')?e:t;r.setAttribute("tabindex",s?"-1":"0"),s?r.setAttribute("aria-disabled","true"):r.removeAttribute("aria-disabled")}}#p(){if(this.querySelector(":scope > .iron-triangle-status"))return;let t=document.createElement("div");t.className="iron-triangle-status";let e=document.createElement("output");e.className="iron-triangle-readout",e.setAttribute("aria-live","polite"),e.setAttribute("aria-atomic","true");let r=document.createElement("button");r.type="button",r.className="iron-triangle-mode ghost",r.setAttribute("aria-pressed","false"),r.textContent="Manual capacity",r.addEventListener("click",()=>this.#S());let s=document.createElement("p");s.className="iron-triangle-warning",s.setAttribute("data-warning","over-deadline"),s.hidden=!0,t.append(e,r,s);let a=this.querySelector(":scope > svg");a?a.after(t):this.prepend(t),this.#c=e,this.#n=r,this.#d=s,this.#v()}#f(){if(!this.#c)return;let{capacityPoints:t,capacitySource:e}=this.#t,r=e==="manual",s=this.#t.time?.deadline,a=this.matches(":state(over-deadline)"),n=[];n.push(t>0?`Capacity: ${t} points (${r?"manual":"formula"}).`:"Capacity: not yet budgeted."),a&&n.push(`Deadline has passed (${s}).`);let o=n.join(" ");if(this.#c.textContent!==o&&(this.#c.textContent=o),this.#n){this.#n.setAttribute("aria-pressed",r?"true":"false");let l=r&&t>0?`Manual capacity: ${t} pts`:"Manual capacity";this.#n.textContent!==l&&(this.#n.textContent=l),this.#n.setAttribute("aria-label",r?`${l}. Activate to edit or return to the formula.`:`${l}. Activate to override the formula with a fixed number.`)}this.#d&&(this.#d.textContent=a?`Deadline has passed (${s})`:"",this.#d.hidden=!a)}#S(){let t=this.#k(),e=t.querySelector('[name="capacity.points"]');e.value=String(this.#t.capacityPoints>0?this.#t.capacityPoints:1);let r=t.querySelector('button[value="formula"]');r.hidden=this.#t.capacitySource!=="manual",typeof t.showModal=="function"?t.showModal():t.setAttribute("open","")}#k(){if(this.#i.capacity)return this.#i.capacity;let t=document.createElement("dialog");t.className="iron-triangle-dialog iron-triangle-dialog--capacity",t.setAttribute("aria-label","Capacity \u2014 manual override");let e=document.createElement("form");e.method="dialog",e.setAttribute("data-layout","stack"),e.setAttribute("data-layout-gap","m");let r=document.createElement("h3");r.textContent="Manual capacity",e.append(r);let s=document.createElement("p");s.className="iron-triangle-dialog__hint",s.textContent="Fix the capacity to a number the team committed to. The Time / Cost / Scope inputs stay saved but stop driving the readout.",e.append(s),e.append(ir("capacity",{key:"points",label:"Capacity (points)",type:"number",min:1,step:1,width:"6rem"},this.#t.capacityPoints));let a=document.createElement("div");a.setAttribute("data-layout","cluster"),a.setAttribute("data-layout-gap","s"),a.setAttribute("data-layout-justify","end");let n=document.createElement("button");n.type="button",n.value="formula",n.textContent="Use formula",n.addEventListener("click",()=>{t.close("formula"),this.setFormula()});let o=document.createElement("button");o.type="button",o.value="cancel",o.textContent="Cancel",o.addEventListener("click",()=>t.close("cancel"));let l=document.createElement("button");return l.type="submit",l.value="save",l.textContent="Save",a.append(n,o,l),e.append(a),t.append(e),this.append(t),this.#i.capacity=t,e.addEventListener("submit",d=>{d.preventDefault();let c=e.querySelector('[name="capacity.points"]'),u=Number(c.value);t.close("save"),Number.isFinite(u)&&u>0&&this.setManual(u)}),this.#v(),t}#$(t){if(t==="capacityPoints")return this.#t.capacityPoints;let[e,r]=t.split(".");return e&&r?this.#t[e]?.[r]:void 0}#C(t,e){if(t==="capacityPoints"){this.setManual(e);return}let[r,s]=t.split(".");!r||!s||(this.#t[r]||(this.#t[r]={}),this.#t[r][s]=e)}};function ir(i,t,e){let r=document.createElement("form-field"),s=`${i}-${t.key}`,a=document.createElement("label");a.setAttribute("for",s),a.textContent=t.label,r.append(a);let n;if(t.type==="select"){n=document.createElement("select");for(let[o,l]of t.options){let d=document.createElement("option");d.value=o,d.textContent=l,(e===o||e==null&&t.value===o)&&(d.selected=!0),n.append(d)}}else t.type==="textarea"?(n=document.createElement("textarea"),t.rows&&(n.rows=t.rows),t.maxlength&&(n.maxLength=t.maxlength),e!=null&&(n.value=String(e))):(n=document.createElement("input"),n.type=t.type,t.min!=null&&(n.min=String(t.min)),t.max!=null&&(n.max=String(t.max)),t.step!=null&&(n.step=String(t.step)),e!=null?n.value=String(e):t.value!=null&&(n.value=String(t.value)));return n.id=s,n.name=`${i}.${t.key}`,t.width&&(n.style.inlineSize=t.width),r.append(n),r}A("iron-triangle",ke);function gs(i){if(!i)return 0;let t=i.dataset?.capacityCost??i.getAttribute?.("data-capacity-cost"),e=Number(t);return Number.isFinite(e)&&e>0?e:0}function nr(i){let t=0;for(let e of i||[])t+=gs(e);return t}function Se({capacityPoints:i,qualitySum:t,featureSum:e}){let r=Number.isFinite(i)?i:1/0,s=Math.max(0,Number(t)||0),a=Math.max(0,Number(e)||0),n=Number.isFinite(r)?r-s-a:1/0;return{capacity:r,quality:s,features:a,slack:n}}function or({capacity:i,quality:t,features:e}){if(!Number.isFinite(i)||i<=0){let a=t+e;return a<=0?{quality:0,features:0,slack:100}:{quality:t/a*100,features:e/a*100,slack:0}}let r=t+e,s=Math.max(i,r);return{quality:t/s*100,features:e/s*100,slack:Math.max(0,(i-r)/s*100)}}var Ee=class extends C{static get observedAttributes(){return["data-bind-triangle","data-bind-quality"]}#e=null;#t=null;#r=null;#a=null;#s=!1;setup(){this.#c(),this.#n(),this.#d(),this.#u()}teardown(){this.#e?.(),this.#t?.(),this.#r?.disconnect(),this.#e=null,this.#t=null,this.#r=null}attributeChangedCallback(t){this.isConnected&&(t==="data-bind-triangle"?(this.#c(),this.#u()):t==="data-bind-quality"&&(this.#n(),this.#u()))}get capacityPoints(){return this.#o()}get qualitySum(){return this.#l()}get featureSum(){return this.#a!=null?this.#a:nr(this.querySelectorAll("[data-capacity-cost]"))}set featureSum(t){this.#a=Number.isFinite(+t)?+t:null,this.#u()}get slack(){return Se({capacityPoints:this.#o(),qualitySum:this.#l(),featureSum:this.featureSum}).slack}#i(t){if(!t)return null;let e=this.getRootNode();return e.getElementById?e.getElementById(t):document.getElementById(t)}#c(){this.#e?.(),this.#e=null;let t=this.#i(this.dataset.bindTriangle);if(!t||t.localName!=="iron-triangle")return;let e=()=>this.#u();t.addEventListener("iron-triangle:change",e),this.#e=()=>t.removeEventListener("iron-triangle:change",e)}#n(){this.#t?.(),this.#t=null;let t=this.#i(this.dataset.bindQuality);if(!t||t.localName!=="quality-target")return;let e=()=>this.#u();t.addEventListener("quality-target:change",e),this.#t=()=>t.removeEventListener("quality-target:change",e)}#d(){this.#r||(this.#r=new MutationObserver(t=>{t.some(r=>!r.target.closest?.("[data-capacity-table]"))&&this.#u()}),this.#r.observe(this,{childList:!0,subtree:!0,attributes:!0,attributeFilter:["data-capacity-cost"]}))}#o(){let t=this.#i(this.dataset.bindTriangle);if(!t||t.localName!=="iron-triangle")return 1/0;let e=t.capacityPoints;return Number.isFinite(e)&&e>0?e:1/0}#l(){let t=this.#i(this.dataset.bindQuality);return!t||t.localName!=="quality-target"?0:Number(t.criticalSum)||0}#u(){let t=Se({capacityPoints:this.#o(),qualitySum:this.#l(),featureSum:this.featureSum}),e=or(t),r=this.querySelector(":scope > [data-capacity-table]");r||(r=document.createElement("section"),r.dataset.capacityTable="",this.prepend(r));let s=vs(t.capacity),a=t.quality>0?`\u2212${t.quality} pts`:"0 pts",n=t.features>0?`\u2212${t.features} pts`:"0 pts",o=ys(t.slack);r.innerHTML=`
3160
3184
  <dl data-layout="grid" class="capacity-ledger" aria-label="Capacity ledger">
3161
3185
  <div data-row="capacity">
3162
3186
  <dt>Capacity</dt>
3163
- <dd class="num">${r}</dd>
3187
+ <dd class="num">${s}</dd>
3164
3188
  <dd class="bar"><span class="bar-track"><span class="bar-fill bar-capacity" style="--w:100%"></span></span></dd>
3165
3189
  </div>
3166
3190
  <div data-row="quality">
@@ -3170,7 +3194,7 @@ var re=`
3170
3194
  </div>
3171
3195
  <div data-row="features">
3172
3196
  <dt>Features</dt>
3173
- <dd class="num">${i}</dd>
3197
+ <dd class="num">${n}</dd>
3174
3198
  <dd class="bar"><span class="bar-track"><span class="bar-fill bar-features" style="--w:${e.features.toFixed(1)}%"></span></span></dd>
3175
3199
  </div>
3176
3200
  <div data-row="slack" data-state="${t.slack<0?"over":"under"}">
@@ -3179,17 +3203,17 @@ var re=`
3179
3203
  <dd class="bar"><span class="bar-track"><span class="bar-fill bar-slack" style="--w:${e.slack.toFixed(1)}%"></span></span></dd>
3180
3204
  </div>
3181
3205
  </dl>
3182
- `,this.setState("overdrawn",t.slack<0);let c=t.slack<0;c!==this.#r&&(this.dispatchEvent(new CustomEvent("capacity-plan:overdrawn",{bubbles:!0,composed:!0,detail:{ledger:t,source:"render"}})),this.#r=c)}};function ys(n){return Number.isFinite(n)?`${n} pts`:"\u221E"}function xs(n){return Number.isFinite(n)?n===0?"0 pts":n>0?`+${n} pts`:`${n} pts`:"\u221E"}w("capacity-plan",Qt);var Yt=Object.freeze(["performance","accessibility","security","reliability","maintainability","observability","compatibility","scalability","portability","internationalization","privacy"]),ut=Object.freeze(["critical","important","acceptable","not-relevant"]),Kt=Object.freeze({critical:"Critical",important:"Important",acceptable:"Acceptable","not-relevant":"Not relevant"}),ke=Object.freeze({accessibility:3,performance:5,security:5,reliability:4,observability:3,internationalization:4,compatibility:2,portability:3,privacy:4,scalability:5,maintainability:2}),Ce=Object.freeze({performance:"Performance",accessibility:"Accessibility",security:"Security",reliability:"Reliability",maintainability:"Maintainability",observability:"Observability",compatibility:"Compatibility",scalability:"Scalability",portability:"Portability",internationalization:"Internationalization",privacy:"Privacy"}),ya=Object.freeze({accessibility:"a11y",internationalization:"i18n",maintainability:"maint",observability:"obs",compatibility:"compat",portability:"porta",performance:"perf",reliability:"rely",scalability:"scale",security:"sec",privacy:"priv"}),_s=Object.freeze({critical:1,important:.6,acceptable:.3,"not-relevant":0});function G(n){return Ce[n]?Ce[n]:String(n).replace(/[-_]/g," ").replace(/\b\w/g,t=>t.toUpperCase())}function Jt(n,t={}){let e={};for(let s of n)Object.prototype.hasOwnProperty.call(t,s)&&Number.isFinite(Number(t[s]))?e[s]=Math.max(0,Math.floor(Number(t[s]))):Object.prototype.hasOwnProperty.call(ke,s)?e[s]=ke[s]:e[s]=1;return Object.freeze(e)}function pt(n,t){let e=0;for(let[s,r]of Object.entries(n||{}))r==="critical"&&(e+=Number(t?.[s]??0));return e}function Se(n){return Object.keys(n||{}).filter(t=>n[t]==="critical")}function Gt(n){let{vector:t={},rationales:e={},costWeights:s={},capacityPoints:r=1/0,overrunRationale:a="",minRationale:i=10,minOverrunRationale:o=10}=n||{},c=[],d=Se(t);for(let u of d){let p=e[u];(typeof p!="string"||p.trim().length<i)&&c.push(`Critical "${u}" needs a rationale of at least ${i} characters.`)}let l=pt(t,s);return Number.isFinite(r)&&l>r&&(typeof a!="string"||a.trim().length<o)&&c.push(`Over budget by ${l-r} points (${l}/${r}); overrunRationale of at least ${o} characters required.`),{valid:c.length===0,errors:c,criticalSum:l}}function $e({level:n,rationale:t,minRationale:e=10}){return ut.includes(n)?n==="critical"&&(typeof t!="string"||t.trim().length<e)?{ok:!1,reason:"rationale-too-short"}:{ok:!0}:{ok:!1,reason:"pick-level"}}function Ee({ility:n,level:t,costWeight:e}){let s=G(n),r=t?Kt[t]||t:"unset",a=Number(e),i=Number.isFinite(a)?`${a} pts`:"? pts";return`${s} \u2014 ${r} \xB7 ${i}`}function qe(n){if(!n||typeof n!="string")return{};try{let t=JSON.parse(n);return t&&typeof t=="object"&&!Array.isArray(t)?t:{}}catch{return{}}}function Ie(n){let t=[];for(let e=0;e<n;e++)t.push(-Math.PI/2+2*Math.PI*e/n);return t}function ws({ilities:n,vector:t={},radius:e}){let s=Ie(n.length);return n.map((r,a)=>{let i=t[r]||null,o=_s[i]??0;return{ility:r,level:i,x:U(Math.cos(s[a])*e*o),y:U(Math.sin(s[a])*e*o)}})}function Xt({ilities:n,radius:t}){let e=Ie(n.length);return n.map((s,r)=>({ility:s,x:U(Math.cos(e[r])*t),y:U(Math.sin(e[r])*t)}))}var I="http://www.w3.org/2000/svg",As=Object.freeze([{ratio:1,label:"Critical",className:"ring-critical"},{ratio:.6,label:"Important",className:"ring-important"},{ratio:.3,label:"Acceptable",className:"ring-acceptable"}]),ks=.22;function Ne({ilities:n=[],vector:t={},costWeights:e={},capacityPoints:s=0,radius:r=100}={}){let a=document.createElementNS(I,"svg"),i=r+14,o=i+140,c=i+30;a.setAttribute("viewBox",`${-o} ${-c} ${o*2} ${c*2}`),a.setAttribute("role","group"),a.setAttribute("aria-label",`Quality target. ${Se(t||{}).length} critical of ${n.length} ilities. Click any axis to edit.`);for(let y of As){let A=document.createElementNS(I,"polygon");A.setAttribute("class",`ring ${y.className}`);let S=Xt({ilities:n,radius:r*y.ratio});A.setAttribute("points",S.map($=>`${$.x},${$.y}`).join(" ")),a.append(A)}let d=Xt({ilities:n,radius:r});for(let y of d){let A=document.createElementNS(I,"line");A.setAttribute("class","spoke"),A.setAttribute("x1","0"),A.setAttribute("y1","0"),A.setAttribute("x2",String(y.x)),A.setAttribute("y2",String(y.y)),a.append(A)}let l=ws({ilities:n,vector:t,radius:r}),u=l.filter(y=>Math.hypot(y.x,y.y)>.5);if(u.length>=3){let y=document.createElementNS(I,"polygon");y.setAttribute("class","vector"),y.setAttribute("points",u.map(A=>`${A.x},${A.y}`).join(" ")),a.append(y)}else if(u.length>0)for(let y of u){let A=document.createElementNS(I,"line");A.setAttribute("class","vector-spoke"),A.setAttribute("x1","0"),A.setAttribute("y1","0"),A.setAttribute("x2",String(y.x)),A.setAttribute("y2",String(y.y)),a.append(A)}let p=Xt({ilities:n,radius:i});for(let y=0;y<n.length;y++){let A=n[y],S=l[y],$=p[y],T=Number(e?.[A]??0),z=t?.[A]??null,N=document.createElementNS(I,"g");N.setAttribute("class","axis"),N.setAttribute("data-ility",A),z&&N.setAttribute("data-level",String(z)),N.setAttribute("tabindex","0"),N.setAttribute("role","button"),N.setAttribute("aria-label",`${Ee({ility:A,level:z,costWeight:T})}. Activate to edit.`);let D=document.createElementNS(I,"rect");D.setAttribute("class","hit");let ht=Cs($),mt=100,ee=22,ze=$.x+(ht==="end"?-mt:ht==="start"?0:-mt/2),Pe=$.y-ee/2;if(D.setAttribute("x",String(U(ze))),D.setAttribute("y",String(U(Pe))),D.setAttribute("width",String(mt)),D.setAttribute("height",String(ee)),D.setAttribute("rx","4"),N.append(D),z){let Q=document.createElementNS(I,"circle");Q.setAttribute("class","marker"),Q.setAttribute("cx",String(S.x)),Q.setAttribute("cy",String(S.y)),Q.setAttribute("r","4"),N.append(Q)}let F=document.createElementNS(I,"text");F.setAttribute("class","axis-label"),F.setAttribute("x",String($.x)),F.setAttribute("y",String($.y)),F.setAttribute("text-anchor",ht),F.setAttribute("dominant-baseline","middle"),F.textContent=G(A),N.append(F);let se=document.createElementNS(I,"title");se.textContent=Ee({ility:A,level:z,costWeight:T}),N.append(se),a.append(N)}let h=document.createElementNS(I,"g");h.setAttribute("class","center");let f=pt(t,e);Number.isFinite(s)&&f>s&&h.setAttribute("data-over","");let v=r*ks,x=document.createElementNS(I,"circle");x.setAttribute("class","capacity-backdrop"),x.setAttribute("cx","0"),x.setAttribute("cy","0"),x.setAttribute("r",String(U(v))),h.append(x);let _=document.createElementNS(I,"text");_.setAttribute("class","capacity-sum"),_.setAttribute("x","0"),_.setAttribute("y","-3"),_.setAttribute("text-anchor","middle"),_.setAttribute("dominant-baseline","middle"),_.textContent=String(f),h.append(_);let g=document.createElementNS(I,"text");return g.setAttribute("class","capacity-denom"),g.setAttribute("x","0"),g.setAttribute("y","11"),g.setAttribute("text-anchor","middle"),g.textContent=Number.isFinite(s)?`of ${s}`:"unbounded",h.append(g),a.append(h),a}function U(n){return Math.round(n*100)/100}function Cs(n){return Math.abs(n.x)<4?"middle":n.x>0?"start":"end"}var Es=0,Zt=class extends C{static formAssociated=!0;static get observedAttributes(){return["data-bind-to","data-capacity-points","data-cost-weights","data-radius","data-min-rationale","data-max-rationale","data-min-overrun-rationale","data-max-overrun-rationale","disabled","locked"]}#e;#t=[...Yt];#s={};#i={};#r=Jt(Yt);#n="";#a=!1;#o=null;#c=null;#p={};#l=null;#u=`quality-target-${++Es}`;constructor(){super(),this.#e=this.attachInternals(),this._adoptInternals(this.#e)}setup(){this.#f(),this.#N(),this.#E(),this.#h(),this.#q(),this.listen(this,"click",t=>this.#m(t)),this.listen(this,"keydown",t=>this.#g(t)),this.listen(this,"input",t=>this.#b(t))}teardown(){this.#o?.(),this.#o=null}attributeChangedCallback(t){this.isConnected&&(t==="data-bind-to"?(this.#N(),this.#E()):t==="data-capacity-points"?this.#E():t==="data-cost-weights"?(this.#f(),this.#E()):t==="data-radius"?this.#E():t==="data-min-overrun-rationale"||t==="data-max-overrun-rationale"?(this.#y(),this.#q()):(t==="disabled"||t==="locked")&&this.#L())}get vector(){return{...this.#s}}set vector(t){this.#w(t),this.#S("property")}get rationales(){return{...this.#i}}set rationales(t){this.#x(t),this.#S("property")}get costWeights(){return{...this.#r}}get capacityPoints(){return this.#_()}set capacityPoints(t){this.#c=Number.isFinite(+t)?+t:null,this.#S("property")}get criticalSum(){return pt(this.#s,this.#r)}get overBudget(){let t=this.#_();return Number.isFinite(t)&&this.criticalSum>t}get overrunRationale(){return this.#n}set overrunRationale(t){this.#n=String(t??"");let e=this.querySelector("[data-quality-overrun] textarea");e&&(e.value=this.#n),this.#q()}get ilities(){return[...this.#t]}set ilities(t){!Array.isArray(t)||t.length===0||(this.#t=[...t],this.#f(),this.#S("property"))}get value(){return{vector:{...this.#s},rationales:{...this.#i},costWeights:{...this.#r},capacityPoints:this.#A(),capacitySource:this.#k(),criticalSum:this.criticalSum,overrunRationale:this.#n||void 0,ironTriangleHash:this.#T()}}openEditor(t){if(!this.#t.includes(t)||this.#M)return;let e=this.#v(t);typeof e.showModal=="function"?e.showModal():e.setAttribute("open","")}checkValidity(){let{valid:t,errors:e}=Gt({vector:this.#s,rationales:this.#i,costWeights:this.#r,capacityPoints:this.#_(),overrunRationale:this.#n,minRationale:this.#$(),minOverrunRationale:this.#I()});this.setState("missing-rationale",!t);let s=this.querySelector("[data-quality-errors]");return s&&(s.textContent=e.join(" ")),t}#m(t){let e=t.target.closest?.(".axis[data-ility]");e&&this.contains(e)&&(t.preventDefault(),this.openEditor(e.dataset.ility))}#g(t){if(t.key!=="Enter"&&t.key!==" ")return;let e=t.target.closest?.(".axis[data-ility]");e&&this.contains(e)&&(t.preventDefault(),this.openEditor(e.dataset.ility))}#b(t){let e=t.target;e?.matches?.("[data-quality-overrun] textarea")&&(this.#n=e.value,this.checkValidity(),this.#q())}#v(t){if(this.#p[t])return this.#d(t),this.#p[t];let e=document.createElement("dialog");e.className=`quality-dialog quality-dialog--${t}`,e.setAttribute("aria-label",`${G(t)} \u2014 edit priority`);let s=document.createElement("form");s.method="dialog",s.setAttribute("data-layout","stack"),s.setAttribute("data-layout-gap","m");let r=document.createElement("h3");r.textContent=G(t),s.append(r);let a=document.createElement("fieldset");a.setAttribute("data-layout","stack"),a.setAttribute("data-layout-gap","2xs");let i=document.createElement("legend");i.textContent="Priority",a.append(i);for(let f of ut){let b=document.createElement("label"),v=document.createElement("input");v.type="radio",v.name="level",v.value=f,b.append(v,document.createTextNode(" "+Kt[f])),a.append(b)}s.append(a);let o=document.createElement("form-field"),c=document.createElement("label");c.setAttribute("for",`${this.#u}-${t}-rationale`),c.textContent="Rationale (required when Critical)";let d=document.createElement("textarea");d.id=`${this.#u}-${t}-rationale`,d.name="rationale",d.rows=3,d.minLength=this.#$(),d.maxLength=this.#j(),d.placeholder=`Why \u2265 ${this.#$()} chars`,o.append(c,d),s.append(o);let l=document.createElement("p");l.className="message message-error",l.dataset.dialogError="",l.hidden=!0,s.append(l);let u=document.createElement("div");u.setAttribute("data-layout","cluster"),u.setAttribute("data-layout-gap","s"),u.setAttribute("data-layout-justify","end");let p=document.createElement("button");p.type="button",p.textContent="Cancel",p.addEventListener("click",()=>e.close("cancel"));let h=document.createElement("button");return h.type="submit",h.textContent="Save",u.append(p,h),s.append(u),e.append(s),this.append(e),this.#p[t]=e,s.addEventListener("submit",f=>{f.preventDefault();let v=s.querySelector('input[name="level"]:checked')?.value,_=s.querySelector('textarea[name="rationale"]')?.value??"",g=$e({level:v,rationale:_,minRationale:this.#$()});if(!g.ok){l.hidden=!1,l.textContent=g.reason==="pick-level"?"Pick a priority level.":`Rationale must be at least ${this.#$()} characters.`;return}this.#s[t]=v??"",v==="critical"?this.#i[t]=_.trim():delete this.#i[t],e.close("save"),this.#S("dialog",t)}),this.#d(t),this.#L(),e}#d(t){let e=this.#p[t];if(!e)return;let s=this.#s[t];for(let i of e.querySelectorAll('input[name="level"]')){let o=i;o.checked=o.value===s}let r=e.querySelector('textarea[name="rationale"]');r&&(r.value=this.#i[t]||"");let a=e.querySelector("[data-dialog-error]");a&&(a.hidden=!0,a.textContent="")}#h(){if(this.#l)return;let t=document.createElement("section");t.className="quality-footer",t.dataset.qualityFooter="",t.setAttribute("data-layout","stack"),t.setAttribute("data-layout-gap","s");let e=document.createElement("section");e.dataset.qualityOverrun="",e.hidden=!0,e.innerHTML=`
3206
+ `,this.setState("overdrawn",t.slack<0);let l=t.slack<0;l!==this.#s&&(this.dispatchEvent(new CustomEvent("capacity-plan:overdrawn",{bubbles:!0,composed:!0,detail:{ledger:t,source:"render"}})),this.#s=l)}};function vs(i){return Number.isFinite(i)?`${i} pts`:"\u221E"}function ys(i){return Number.isFinite(i)?i===0?"0 pts":i>0?`+${i} pts`:`${i} pts`:"\u221E"}A("capacity-plan",Ee);var $e=Object.freeze(["performance","accessibility","security","reliability","maintainability","observability","compatibility","scalability","portability","internationalization","privacy"]),Ut=Object.freeze(["critical","important","acceptable","not-relevant"]),qe=Object.freeze({critical:"Critical",important:"Important",acceptable:"Acceptable","not-relevant":"Not relevant"}),cr=Object.freeze({accessibility:3,performance:5,security:5,reliability:4,observability:3,internationalization:4,compatibility:2,portability:3,privacy:4,scalability:5,maintainability:2}),lr=Object.freeze({performance:"Performance",accessibility:"Accessibility",security:"Security",reliability:"Reliability",maintainability:"Maintainability",observability:"Observability",compatibility:"Compatibility",scalability:"Scalability",portability:"Portability",internationalization:"Internationalization",privacy:"Privacy"}),xs=Object.freeze({critical:1,important:.6,acceptable:.3,"not-relevant":0});function Et(i){return lr[i]?lr[i]:String(i).replace(/[-_]/g," ").replace(/\b\w/g,t=>t.toUpperCase())}function Ie(i,t={}){let e={};for(let r of i)Object.prototype.hasOwnProperty.call(t,r)&&Number.isFinite(Number(t[r]))?e[r]=Math.max(0,Math.floor(Number(t[r]))):Object.prototype.hasOwnProperty.call(cr,r)?e[r]=cr[r]:e[r]=1;return Object.freeze(e)}function Vt(i,t){let e=0;for(let[r,s]of Object.entries(i||{}))s==="critical"&&(e+=Number(t?.[r]??0));return e}function ur(i){return Object.keys(i||{}).filter(t=>i[t]==="critical")}function Ne(i){let{vector:t={},rationales:e={},costWeights:r={},capacityPoints:s=1/0,overrunRationale:a="",minRationale:n=10,minOverrunRationale:o=10}=i||{},l=[],d=ur(t);for(let u of d){let m=e[u];(typeof m!="string"||m.trim().length<n)&&l.push(`Critical "${u}" needs a rationale of at least ${n} characters.`)}let c=Vt(t,r);return Number.isFinite(s)&&c>s&&(typeof a!="string"||a.trim().length<o)&&l.push(`Over budget by ${c-s} points (${c}/${s}); overrunRationale of at least ${o} characters required.`),{valid:l.length===0,errors:l,criticalSum:c}}function pr({level:i,rationale:t,minRationale:e=10}){return Ut.includes(i)?i==="critical"&&(typeof t!="string"||t.trim().length<e)?{ok:!1,reason:"rationale-too-short"}:{ok:!0}:{ok:!1,reason:"pick-level"}}function dr({ility:i,level:t,costWeight:e}){let r=Et(i),s=t?qe[t]||t:"unset",a=Number(e),n=Number.isFinite(a)?`${a} pts`:"? pts";return`${r} \u2014 ${s} \xB7 ${n}`}function hr(i){if(!i||typeof i!="string")return{};try{let t=JSON.parse(i);return t&&typeof t=="object"&&!Array.isArray(t)?t:{}}catch{return{}}}function mr(i){let t=[];for(let e=0;e<i;e++)t.push(-Math.PI/2+2*Math.PI*e/i);return t}function _s({ilities:i,vector:t={},radius:e}){let r=mr(i.length);return i.map((s,a)=>{let n=t[s]||null,o=xs[n]??0;return{ility:s,level:n,x:ut(Math.cos(r[a])*e*o),y:ut(Math.sin(r[a])*e*o)}})}function Ce({ilities:i,radius:t}){let e=mr(i.length);return i.map((r,s)=>({ility:r,x:ut(Math.cos(e[s])*t),y:ut(Math.sin(e[s])*t)}))}var j="http://www.w3.org/2000/svg",ws=Object.freeze([{ratio:1,label:"Critical",className:"ring-critical"},{ratio:.6,label:"Important",className:"ring-important"},{ratio:.3,label:"Acceptable",className:"ring-acceptable"}]),As=.22;function fr({ilities:i=[],vector:t={},costWeights:e={},capacityPoints:r=0,radius:s=100}={}){let a=document.createElementNS(j,"svg"),n=s+14,o=n+140,l=n+30;a.setAttribute("viewBox",`${-o} ${-l} ${o*2} ${l*2}`),a.setAttribute("role","group"),a.setAttribute("aria-label",`Quality target. ${ur(t||{}).length} critical of ${i.length} ilities. Click any axis to edit.`);for(let x of ws){let k=document.createElementNS(j,"polygon");k.setAttribute("class",`ring ${x.className}`);let _=Ce({ilities:i,radius:s*x.ratio});k.setAttribute("points",_.map($=>`${$.x},${$.y}`).join(" ")),a.append(k)}let d=Ce({ilities:i,radius:s});for(let x of d){let k=document.createElementNS(j,"line");k.setAttribute("class","spoke"),k.setAttribute("x1","0"),k.setAttribute("y1","0"),k.setAttribute("x2",String(x.x)),k.setAttribute("y2",String(x.y)),a.append(k)}let c=_s({ilities:i,vector:t,radius:s}),u=c.filter(x=>Math.hypot(x.x,x.y)>.5);if(u.length>=3){let x=document.createElementNS(j,"polygon");x.setAttribute("class","vector"),x.setAttribute("points",u.map(k=>`${k.x},${k.y}`).join(" ")),a.append(x)}else if(u.length>0)for(let x of u){let k=document.createElementNS(j,"line");k.setAttribute("class","vector-spoke"),k.setAttribute("x1","0"),k.setAttribute("y1","0"),k.setAttribute("x2",String(x.x)),k.setAttribute("y2",String(x.y)),a.append(k)}let m=Ce({ilities:i,radius:n});for(let x=0;x<i.length;x++){let k=i[x],_=c[x],$=m[x],N=Number(e?.[k]??0),F=t?.[k]??null,L=document.createElementNS(j,"g");L.setAttribute("class","axis"),L.setAttribute("data-ility",k),F&&L.setAttribute("data-level",String(F)),L.setAttribute("tabindex","0"),L.setAttribute("role","button"),L.setAttribute("aria-label",`${dr({ility:k,level:F,costWeight:N})}. Activate to edit.`);let Q=document.createElementNS(j,"rect");Q.setAttribute("class","hit");let rt=ks($),V=100,G=22,yr=$.x+(rt==="end"?-V:rt==="start"?0:-V/2),xr=$.y-G/2;if(Q.setAttribute("x",String(ut(yr))),Q.setAttribute("y",String(ut(xr))),Q.setAttribute("width",String(V)),Q.setAttribute("height",String(G)),Q.setAttribute("rx","4"),L.append(Q),F){let _t=document.createElementNS(j,"circle");_t.setAttribute("class","marker"),_t.setAttribute("cx",String(_.x)),_t.setAttribute("cy",String(_.y)),_t.setAttribute("r","4"),L.append(_t)}let st=document.createElementNS(j,"text");st.setAttribute("class","axis-label"),st.setAttribute("x",String($.x)),st.setAttribute("y",String($.y)),st.setAttribute("text-anchor",rt),st.setAttribute("dominant-baseline","middle"),st.textContent=Et(k),L.append(st);let Me=document.createElementNS(j,"title");Me.textContent=dr({ility:k,level:F,costWeight:N}),L.append(Me),a.append(L)}let f=document.createElementNS(j,"g");f.setAttribute("class","center");let h=Vt(t,e);Number.isFinite(r)&&h>r&&f.setAttribute("data-over","");let g=s*As,w=document.createElementNS(j,"circle");w.setAttribute("class","capacity-backdrop"),w.setAttribute("cx","0"),w.setAttribute("cy","0"),w.setAttribute("r",String(ut(g))),f.append(w);let v=document.createElementNS(j,"text");v.setAttribute("class","capacity-sum"),v.setAttribute("x","0"),v.setAttribute("y","-3"),v.setAttribute("text-anchor","middle"),v.setAttribute("dominant-baseline","middle"),v.textContent=String(h),f.append(v);let y=document.createElementNS(j,"text");return y.setAttribute("class","capacity-denom"),y.setAttribute("x","0"),y.setAttribute("y","11"),y.setAttribute("text-anchor","middle"),y.textContent=Number.isFinite(r)?`of ${r}`:"unbounded",f.append(y),a.append(f),a}function ut(i){return Math.round(i*100)/100}function ks(i){return Math.abs(i.x)<4?"middle":i.x>0?"start":"end"}var Ss=0,Te=class extends C{static formAssociated=!0;static get observedAttributes(){return["data-bind-to","data-capacity-points","data-cost-weights","data-radius","data-min-rationale","data-max-rationale","data-min-overrun-rationale","data-max-overrun-rationale","disabled","locked"]}#e;#t=[...$e];#r={};#a={};#s=Ie($e);#i="";#c=!1;#n=null;#d=null;#o={};#l=null;#u=`quality-target-${++Ss}`;constructor(){super(),this.#e=this.attachInternals(),this._adoptInternals(this.#e)}setup(){this.#w(),this.#$(),this.#C(),this.#x(),this.#I(),this.listen(this,"click",t=>this.#y(t)),this.listen(this,"keydown",t=>this.#E(t)),this.listen(this,"input",t=>this.#b(t))}teardown(){this.#n?.(),this.#n=null}attributeChangedCallback(t){this.isConnected&&(t==="data-bind-to"?(this.#$(),this.#C()):t==="data-capacity-points"?this.#C():t==="data-cost-weights"?(this.#w(),this.#C()):t==="data-radius"?this.#C():t==="data-min-overrun-rationale"||t==="data-max-overrun-rationale"?(this.#_(),this.#I()):(t==="disabled"||t==="locked")&&this.#z())}get vector(){return{...this.#r}}set vector(t){this.#A(t),this.#q("property")}get rationales(){return{...this.#a}}set rationales(t){this.#v(t),this.#q("property")}get costWeights(){return{...this.#s}}get capacityPoints(){return this.#m()}set capacityPoints(t){this.#d=Number.isFinite(+t)?+t:null,this.#q("property")}get criticalSum(){return Vt(this.#r,this.#s)}get overBudget(){let t=this.#m();return Number.isFinite(t)&&this.criticalSum>t}get overrunRationale(){return this.#i}set overrunRationale(t){this.#i=String(t??"");let e=this.querySelector("[data-quality-overrun] textarea");e&&(e.value=this.#i),this.#I()}get ilities(){return[...this.#t]}set ilities(t){!Array.isArray(t)||t.length===0||(this.#t=[...t],this.#w(),this.#q("property"))}get value(){return{vector:{...this.#r},rationales:{...this.#a},costWeights:{...this.#s},capacityPoints:this.#p(),capacitySource:this.#f(),criticalSum:this.criticalSum,overrunRationale:this.#i||void 0,ironTriangleHash:this.#k()}}openEditor(t){if(!this.#t.includes(t)||this.#N)return;let e=this.#g(t);typeof e.showModal=="function"?e.showModal():e.setAttribute("open","")}checkValidity(){let{valid:t,errors:e}=Ne({vector:this.#r,rationales:this.#a,costWeights:this.#s,capacityPoints:this.#m(),overrunRationale:this.#i,minRationale:this.#L(),minOverrunRationale:this.#M()});this.setState("missing-rationale",!t);let r=this.querySelector("[data-quality-errors]");return r&&(r.textContent=e.join(" ")),t}#y(t){let e=t.target.closest?.(".axis[data-ility]");e&&this.contains(e)&&(t.preventDefault(),this.openEditor(e.dataset.ility))}#E(t){if(t.key!=="Enter"&&t.key!==" ")return;let e=t.target.closest?.(".axis[data-ility]");e&&this.contains(e)&&(t.preventDefault(),this.openEditor(e.dataset.ility))}#b(t){let e=t.target;e?.matches?.("[data-quality-overrun] textarea")&&(this.#i=e.value,this.checkValidity(),this.#I())}#g(t){if(this.#o[t])return this.#h(t),this.#o[t];let e=document.createElement("dialog");e.className=`quality-dialog quality-dialog--${t}`,e.setAttribute("aria-label",`${Et(t)} \u2014 edit priority`);let r=document.createElement("form");r.method="dialog",r.setAttribute("data-layout","stack"),r.setAttribute("data-layout-gap","m");let s=document.createElement("h3");s.textContent=Et(t),r.append(s);let a=document.createElement("fieldset");a.setAttribute("data-layout","stack"),a.setAttribute("data-layout-gap","2xs");let n=document.createElement("legend");n.textContent="Priority",a.append(n);for(let h of Ut){let b=document.createElement("label"),g=document.createElement("input");g.type="radio",g.name="level",g.value=h,b.append(g,document.createTextNode(" "+qe[h])),a.append(b)}r.append(a);let o=document.createElement("form-field"),l=document.createElement("label");l.setAttribute("for",`${this.#u}-${t}-rationale`),l.textContent="Rationale (required when Critical)";let d=document.createElement("textarea");d.id=`${this.#u}-${t}-rationale`,d.name="rationale",d.rows=3,d.minLength=this.#L(),d.maxLength=this.#D(),d.placeholder=`Why \u2265 ${this.#L()} chars`,o.append(l,d),r.append(o);let c=document.createElement("p");c.className="message message-error",c.dataset.dialogError="",c.hidden=!0,r.append(c);let u=document.createElement("div");u.setAttribute("data-layout","cluster"),u.setAttribute("data-layout-gap","s"),u.setAttribute("data-layout-justify","end");let m=document.createElement("button");m.type="button",m.textContent="Cancel",m.addEventListener("click",()=>e.close("cancel"));let f=document.createElement("button");return f.type="submit",f.textContent="Save",u.append(m,f),r.append(u),e.append(r),this.append(e),this.#o[t]=e,r.addEventListener("submit",h=>{h.preventDefault();let g=r.querySelector('input[name="level"]:checked')?.value,v=r.querySelector('textarea[name="rationale"]')?.value??"",y=pr({level:g,rationale:v,minRationale:this.#L()});if(!y.ok){c.hidden=!1,c.textContent=y.reason==="pick-level"?"Pick a priority level.":`Rationale must be at least ${this.#L()} characters.`;return}this.#r[t]=g??"",g==="critical"?this.#a[t]=v.trim():delete this.#a[t],e.close("save"),this.#q("dialog",t)}),this.#h(t),this.#z(),e}#h(t){let e=this.#o[t];if(!e)return;let r=this.#r[t];for(let n of e.querySelectorAll('input[name="level"]')){let o=n;o.checked=o.value===r}let s=e.querySelector('textarea[name="rationale"]');s&&(s.value=this.#a[t]||"");let a=e.querySelector("[data-dialog-error]");a&&(a.hidden=!0,a.textContent="")}#x(){if(this.#l)return;let t=document.createElement("section");t.className="quality-footer",t.dataset.qualityFooter="",t.setAttribute("data-layout","stack"),t.setAttribute("data-layout-gap","s");let e=document.createElement("section");e.dataset.qualityOverrun="",e.hidden=!0,e.innerHTML=`
3183
3207
  <strong>Over budget \u2014 explain why.</strong>
3184
3208
  <small data-overrun-prompt></small>
3185
3209
  <form-field>
3186
- <label for="${this.#u}-overrun">Overrun rationale (\u2265 ${this.#I()} chars)</label>
3210
+ <label for="${this.#u}-overrun">Overrun rationale (\u2265 ${this.#M()} chars)</label>
3187
3211
  <textarea id="${this.#u}-overrun" name="overrunRationale"
3188
- minlength="${this.#I()}"
3212
+ minlength="${this.#M()}"
3189
3213
  maxlength="${this.#P()}"
3190
3214
  rows="3"></textarea>
3191
3215
  </form-field>
3192
- `,t.append(e);let s=document.createElement("p");s.dataset.qualityErrors="",s.className="message message-error",s.setAttribute("role","alert"),t.append(s),this.append(t),this.#l=t,this.#L()}#y(){if(!this.#l)return;let t=this.#_(),e=this.criticalSum,s=Number.isFinite(t)&&e>t,r=this.#l.querySelector("[data-quality-overrun]");if(r){r.hidden=!s;let a=r.querySelector("[data-overrun-prompt]");if(a){let d=e-t;a.textContent=s?`You're over budget by ${d} ${d===1?"point":"points"} (${e}/${t}).`:""}let i=this.#I(),o=r.querySelector("label");o&&(o.textContent=`Overrun rationale (\u2265 ${i} chars)`);let c=r.querySelector("textarea");c&&(c.minLength=i,c.maxLength=this.#P())}}#f(){let t=qe(this.getAttribute("data-cost-weights")||"");this.#r=Jt(this.#t,t)}#w(t){if(!(!t||typeof t!="object"))for(let[e,s]of Object.entries(t))ut.includes(s)&&(this.#s[e]=s)}#x(t){if(!(!t||typeof t!="object"))for(let[e,s]of Object.entries(t))this.#i[e]=String(s??"")}#_(){let t=this.#C();if(t&&Number.isFinite(t.capacityPoints)&&t.capacityPoints>0)return t.capacityPoints;let e=Number(this.getAttribute("data-capacity-points"));if(Number.isFinite(e)&&e>0)return e;let s=this.#c;return s!==null&&Number.isFinite(s)&&s>0?s:1/0}#A(){let t=this.#_();return Number.isFinite(t)?t:null}#k(){let t=this.#C();return t?.capacitySource==="manual"?"manual":t?"formula":(this.getAttribute("data-capacity-points"),"manual")}#C(){let t=this.getAttribute("data-bind-to");if(!t)return null;let e=this.getRootNode(),s=e.getElementById?e.getElementById(t):document.getElementById(t);return s&&s.localName==="iron-triangle"?s:null}#T(){return this.#C()?.hash||null}#N(){this.#o?.(),this.#o=null;let t=this.#C();if(!t)return;let e=()=>this.#S("iron-triangle");t.addEventListener("iron-triangle:change",e),this.#o=()=>t.removeEventListener("iron-triangle:change",e)}#E(){let t=Ss(Number(this.dataset.radius??100),30,400),e=this.#_(),s=Ne({ilities:this.#t,vector:this.#s,costWeights:this.#r,capacityPoints:e,radius:t}),r=this.querySelector(":scope > svg");r?r.replaceWith(s):this.prepend(s),this.#z()}#S(t,e){this.#E(),this.#y();let s=this.#_(),r=this.criticalSum,a=Number.isFinite(s)&&r>s;if(this.setState("over-budget",a),this.#q(),a!==this.#a){let i=a?"quality-target:over-budget":"quality-target:under-budget",o=a?{delta:r-s,criticalSum:r,capacityPoints:s}:{slack:s-r,criticalSum:r,capacityPoints:s};this.dispatchEvent(new CustomEvent(i,{bubbles:!0,composed:!0,detail:o})),this.#a=a}this.dispatchEvent(new CustomEvent("quality-target:change",{bubbles:!0,composed:!0,detail:{...this.value,source:t,field:e}}))}#q(){try{this.#e.setFormValue(JSON.stringify(this.value))}catch{}this.#R()}#R(){if(typeof this.#e.setValidity!="function")return;let{valid:t,errors:e}=Gt({vector:this.#s,rationales:this.#i,costWeights:this.#r,capacityPoints:this.#_(),overrunRationale:this.#n,minRationale:this.#$(),minOverrunRationale:this.#I()});if(t){this.#e.setValidity({});return}let s=this.overBudget?this.querySelector("[data-quality-overrun] textarea"):null;try{this.#e.setValidity({customError:!0},e.join(" "),s??void 0)}catch{this.#e.setValidity({customError:!0},e.join(" "))}}get#M(){return this.hasAttribute("disabled")||this.hasAttribute("locked")}#L(){let t=this.#M;for(let e of Object.values(this.#p))for(let s of e.querySelectorAll("input, textarea, select, button"))s.disabled=t;for(let e of this.#l?.querySelectorAll("textarea")??[])e.disabled=t;this.#z()}#z(){let t=this.#M;for(let e of this.querySelectorAll(":scope > svg .axis[data-ility]"))e.setAttribute("tabindex",t?"-1":"0"),t?e.setAttribute("aria-disabled","true"):e.removeAttribute("aria-disabled")}#$(){return Math.max(0,parseInt(this.dataset.minRationale??"10",10)||10)}#j(){return Math.max(10,parseInt(this.dataset.maxRationale??"200",10)||200)}#I(){return Math.max(0,parseInt(this.dataset.minOverrunRationale??"10",10)||10)}#P(){return Math.max(10,parseInt(this.dataset.maxOverrunRationale??"400",10)||400)}};function Ss(n,t,e){return Math.max(t,Math.min(e,n))}w("quality-target",Zt);var Te=`
3216
+ `,t.append(e);let r=document.createElement("p");r.dataset.qualityErrors="",r.className="message message-error",r.setAttribute("role","alert"),t.append(r),this.append(t),this.#l=t,this.#z()}#_(){if(!this.#l)return;let t=this.#m(),e=this.criticalSum,r=Number.isFinite(t)&&e>t,s=this.#l.querySelector("[data-quality-overrun]");if(s){s.hidden=!r;let a=s.querySelector("[data-overrun-prompt]");if(a){let d=e-t;a.textContent=r?`You're over budget by ${d} ${d===1?"point":"points"} (${e}/${t}).`:""}let n=this.#M(),o=s.querySelector("label");o&&(o.textContent=`Overrun rationale (\u2265 ${n} chars)`);let l=s.querySelector("textarea");l&&(l.minLength=n,l.maxLength=this.#P())}}#w(){let t=hr(this.getAttribute("data-cost-weights")||"");this.#s=Ie(this.#t,t)}#A(t){if(!(!t||typeof t!="object"))for(let[e,r]of Object.entries(t))Ut.includes(r)&&(this.#r[e]=r)}#v(t){if(!(!t||typeof t!="object"))for(let[e,r]of Object.entries(t))this.#a[e]=String(r??"")}#m(){let t=this.#S();if(t&&Number.isFinite(t.capacityPoints)&&t.capacityPoints>0)return t.capacityPoints;let e=Number(this.getAttribute("data-capacity-points"));if(Number.isFinite(e)&&e>0)return e;let r=this.#d;return r!==null&&Number.isFinite(r)&&r>0?r:1/0}#p(){let t=this.#m();return Number.isFinite(t)?t:null}#f(){let t=this.#S();return t?.capacitySource==="manual"?"manual":t?"formula":(this.getAttribute("data-capacity-points"),"manual")}#S(){let t=this.getAttribute("data-bind-to");if(!t)return null;let e=this.getRootNode(),r=e.getElementById?e.getElementById(t):document.getElementById(t);return r&&r.localName==="iron-triangle"?r:null}#k(){return this.#S()?.hash||null}#$(){this.#n?.(),this.#n=null;let t=this.#S();if(!t)return;let e=()=>this.#q("iron-triangle");t.addEventListener("iron-triangle:change",e),this.#n=()=>t.removeEventListener("iron-triangle:change",e)}#C(){let t=Es(Number(this.dataset.radius??100),30,400),e=this.#m(),r=fr({ilities:this.#t,vector:this.#r,costWeights:this.#s,capacityPoints:e,radius:t}),s=this.querySelector(":scope > svg");s?s.replaceWith(r):this.prepend(r),this.#R()}#q(t,e){this.#C(),this.#_();let r=this.#m(),s=this.criticalSum,a=Number.isFinite(r)&&s>r;if(this.setState("over-budget",a),this.#I(),a!==this.#c){let n=a?"quality-target:over-budget":"quality-target:under-budget",o=a?{delta:s-r,criticalSum:s,capacityPoints:r}:{slack:r-s,criticalSum:s,capacityPoints:r};this.dispatchEvent(new CustomEvent(n,{bubbles:!0,composed:!0,detail:o})),this.#c=a}this.dispatchEvent(new CustomEvent("quality-target:change",{bubbles:!0,composed:!0,detail:{...this.value,source:t,field:e}}))}#I(){try{this.#e.setFormValue(JSON.stringify(this.value))}catch{}this.#T()}#T(){if(typeof this.#e.setValidity!="function")return;let{valid:t,errors:e}=Ne({vector:this.#r,rationales:this.#a,costWeights:this.#s,capacityPoints:this.#m(),overrunRationale:this.#i,minRationale:this.#L(),minOverrunRationale:this.#M()});if(t){this.#e.setValidity({});return}let r=this.overBudget?this.querySelector("[data-quality-overrun] textarea"):null;try{this.#e.setValidity({customError:!0},e.join(" "),r??void 0)}catch{this.#e.setValidity({customError:!0},e.join(" "))}}get#N(){return this.hasAttribute("disabled")||this.hasAttribute("locked")}#z(){let t=this.#N;for(let e of Object.values(this.#o))for(let r of e.querySelectorAll("input, textarea, select, button"))r.disabled=t;for(let e of this.#l?.querySelectorAll("textarea")??[])e.disabled=t;this.#R()}#R(){let t=this.#N;for(let e of this.querySelectorAll(":scope > svg .axis[data-ility]"))e.setAttribute("tabindex",t?"-1":"0"),t?e.setAttribute("aria-disabled","true"):e.removeAttribute("aria-disabled")}#L(){return Math.max(0,parseInt(this.dataset.minRationale??"10",10)||10)}#D(){return Math.max(10,parseInt(this.dataset.maxRationale??"200",10)||200)}#M(){return Math.max(0,parseInt(this.dataset.minOverrunRationale??"10",10)||10)}#P(){return Math.max(10,parseInt(this.dataset.maxOverrunRationale??"400",10)||400)}};function Es(i,t,e){return Math.max(t,Math.min(e,i))}A("quality-target",Te);var br=`
3193
3217
  :host {
3194
3218
  --_padding: var(--requirement-card-padding, var(--size-m, 1rem));
3195
3219
  --_radius: var(--requirement-card-radius, var(--radius-m, 0.5rem));
@@ -3296,8 +3320,8 @@ var re=`
3296
3320
  outline: 2px solid var(--color-focus-ring, var(--color-interactive, currentColor));
3297
3321
  outline-offset: 2px;
3298
3322
  }
3299
- `;var Me=Object.freeze(["critical","important","acceptable","not-relevant"]),$s=Object.freeze({critical:"Critical",important:"Important",acceptable:"Acceptable","not-relevant":"Not relevant"}),Le=["badge","priority-pill","rationale","conflicts"],qs=`
3300
- <style>${Te}</style>
3323
+ `;var gr=Object.freeze(["critical","important","acceptable","not-relevant"]),Cs=Object.freeze({critical:"Critical",important:"Important",acceptable:"Acceptable","not-relevant":"Not relevant"}),vr=["badge","priority-pill","rationale","conflicts"],$s=`
3324
+ <style>${br}</style>
3301
3325
  <article class="card" part="card">
3302
3326
  <header class="head" part="head">
3303
3327
  <span class="name" part="name"><slot name="name"></slot></span>
@@ -3309,4 +3333,4 @@ var re=`
3309
3333
  <p class="rationale" part="rationale"><slot name="rationale"></slot></p>
3310
3334
  <p class="conflicts" part="conflicts"><slot name="conflicts"></slot></p>
3311
3335
  </article>
3312
- `,te=class extends C{#e=!1;static get observedAttributes(){return["data-priority","data-conflict","tabindex"]}setup(){if(this.shadowRoot)for(let e of Le){let s=this.shadowRoot.querySelector(`slot[name="${e}"]`);this.#s(e,s)}else{let e=this.attachShadow({mode:"open"});e.innerHTML=qs;for(let s of Le){let r=e.querySelector(`slot[name="${s}"]`);r?.addEventListener("slotchange",()=>this.#s(s,r)),this.#s(s,r)}}this.#i(),this.#r(),this.#n(),this.listen(this,"click",e=>this.#a(e));let t=this.closest("a[href], button");t&&this.listen(t,"click",e=>{this.contains(e.target)||this.#a(e)}),this.listen(this,"keydown",e=>{let s=e;(s.key==="Enter"||s.key===" ")&&this.#t&&(s.preventDefault(),this.#a(s))})}attributeChangedCallback(t){this.isConnected&&(t==="data-priority"?(this.#i(),this.#r()):t==="data-conflict"||t==="tabindex"&&this.#n())}get priority(){return(this.dataset.priority||"").toLowerCase()}set priority(t){let e=String(t||"").toLowerCase();Me.includes(e)?this.dataset.priority=e:delete this.dataset.priority}get hasConflict(){return this.hasAttribute("data-conflict")}set hasConflict(t){t?this.setAttribute("data-conflict",""):this.removeAttribute("data-conflict")}get#t(){return this.hasAttribute("tabindex")||this.closest("a[href], button")}#s(t,e){let s=!!e&&e.assignedNodes().some(r=>r.nodeType===Node.ELEMENT_NODE||r.nodeType===Node.TEXT_NODE&&r.textContent.trim().length>0);this.setState(`has-${t}`,s)}#i(){let t=(this.dataset.priority||"").toLowerCase();for(let e of Me)this.setState(`priority-${e}`,e===t)}#r(){let t=(this.dataset.priority||"").toLowerCase(),e=this.shadowRoot?.querySelector("[data-priority-default]");e&&(e.textContent=$s[t]||"")}#n(){this.setState("interactive",!!this.#t);let t=this.hasAttribute("tabindex")&&!this.closest("a[href], button");t&&!this.hasAttribute("role")?(this.setAttribute("role","button"),this.#e=!0):!t&&this.#e&&(this.removeAttribute("role"),this.#e=!1)}#a(t){this.#t&&this.dispatchEvent(new CustomEvent("requirement-card:click",{bubbles:!0,composed:!0,detail:{priority:this.priority||null,hasConflict:this.hasConflict,originalEvent:t}}))}};w("requirement-card",te);
3336
+ `,Le=class extends C{#e=!1;static get observedAttributes(){return["data-priority","data-conflict","tabindex"]}setup(){if(this.shadowRoot)for(let e of vr){let r=this.shadowRoot.querySelector(`slot[name="${e}"]`);this.#r(e,r)}else{let e=this.attachShadow({mode:"open"});e.innerHTML=$s;for(let r of vr){let s=e.querySelector(`slot[name="${r}"]`);s?.addEventListener("slotchange",()=>this.#r(r,s)),this.#r(r,s)}}this.#a(),this.#s(),this.#i(),this.listen(this,"click",e=>this.#c(e));let t=this.closest("a[href], button");t&&this.listen(t,"click",e=>{this.contains(e.target)||this.#c(e)}),this.listen(this,"keydown",e=>{let r=e;(r.key==="Enter"||r.key===" ")&&this.#t&&(r.preventDefault(),this.#c(r))})}attributeChangedCallback(t){this.isConnected&&(t==="data-priority"?(this.#a(),this.#s()):t==="data-conflict"||t==="tabindex"&&this.#i())}get priority(){return(this.dataset.priority||"").toLowerCase()}set priority(t){let e=String(t||"").toLowerCase();gr.includes(e)?this.dataset.priority=e:delete this.dataset.priority}get hasConflict(){return this.hasAttribute("data-conflict")}set hasConflict(t){t?this.setAttribute("data-conflict",""):this.removeAttribute("data-conflict")}get#t(){return this.hasAttribute("tabindex")||this.closest("a[href], button")}#r(t,e){let r=!!e&&e.assignedNodes().some(s=>s.nodeType===Node.ELEMENT_NODE||s.nodeType===Node.TEXT_NODE&&s.textContent.trim().length>0);this.setState(`has-${t}`,r)}#a(){let t=(this.dataset.priority||"").toLowerCase();for(let e of gr)this.setState(`priority-${e}`,e===t)}#s(){let t=(this.dataset.priority||"").toLowerCase(),e=this.shadowRoot?.querySelector("[data-priority-default]");e&&(e.textContent=Cs[t]||"")}#i(){this.setState("interactive",!!this.#t);let t=this.hasAttribute("tabindex")&&!this.closest("a[href], button");t&&!this.hasAttribute("role")?(this.setAttribute("role","button"),this.#e=!0):!t&&this.#e&&(this.removeAttribute("role"),this.#e=!1)}#c(t){this.#t&&this.dispatchEvent(new CustomEvent("requirement-card:click",{bubbles:!0,composed:!0,detail:{priority:this.priority||null,hasConflict:this.hasConflict,originalEvent:t}}))}};A("requirement-card",Le);