pilotswarm 0.5.47 → 0.5.49
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/mcp/dist/src/tools/providers.d.ts.map +1 -1
- package/mcp/dist/src/tools/providers.js +12 -0
- package/mcp/dist/src/tools/providers.js.map +1 -1
- package/package.json +2 -2
- package/tui/src/node-sdk-transport.js +5 -0
- package/ui/core/src/commands.js +1 -0
- package/ui/core/src/controller.js +85 -3
- package/ui/core/src/history.js +5 -37
- package/ui/core/src/index.js +1 -0
- package/ui/core/src/reducer.js +42 -0
- package/ui/core/src/selectors.js +153 -4
- package/ui/core/src/state.js +20 -0
- package/ui/core/src/table-layout.js +155 -0
- package/ui/react/src/web-app.js +479 -249
- package/web/dist/assets/{abnfDiagram-VRR7QNED-VPL8m_9W.js → abnfDiagram-VRR7QNED-CXF6f3n3.js} +1 -1
- package/web/dist/assets/{arc-T5I3-c1B.js → arc-MlDVINID.js} +1 -1
- package/web/dist/assets/{architectureDiagram-ZJ3FMSHR-DEP70bg6.js → architectureDiagram-ZJ3FMSHR-Bdz1J9H-.js} +1 -1
- package/web/dist/assets/{blockDiagram-677ZJIJ3-CvBu1MbO.js → blockDiagram-677ZJIJ3-tO706-rr.js} +1 -1
- package/web/dist/assets/{c4Diagram-LMCZKHZV-B5qwF4gm.js → c4Diagram-LMCZKHZV-BuZrMrYZ.js} +1 -1
- package/web/dist/assets/channel-moQWQGwr.js +1 -0
- package/web/dist/assets/{chunk-2Q5K7J3B-zVW8dS7X.js → chunk-2Q5K7J3B-BWWIPnCk.js} +1 -1
- package/web/dist/assets/{chunk-32BRIVSS-DWctxZZS.js → chunk-32BRIVSS-TyL8x2Q5.js} +1 -1
- package/web/dist/assets/{chunk-5VM5RSS4-Bq7_Vmf9.js → chunk-5VM5RSS4-ZTwZyN5B.js} +1 -1
- package/web/dist/assets/{chunk-EX3LRPZG-B8CFB3v-.js → chunk-EX3LRPZG-CjWsKz70.js} +1 -1
- package/web/dist/assets/{chunk-JWPE2WC7-B7gLPjgZ.js → chunk-JWPE2WC7-BNQrzsa3.js} +1 -1
- package/web/dist/assets/{chunk-MOJQB5TN-B2x6q12r.js → chunk-MOJQB5TN-B51xJi0l.js} +1 -1
- package/web/dist/assets/{chunk-RYQCIY6F-XorU9Stx.js → chunk-RYQCIY6F-BCdsh9nc.js} +1 -1
- package/web/dist/assets/{chunk-V7JOEXUC-CsLa6pw5.js → chunk-V7JOEXUC-C7FFxC7C.js} +1 -1
- package/web/dist/assets/{chunk-VR4S4FIN-BBv9mwmj.js → chunk-VR4S4FIN-DWoFV0Pb.js} +1 -1
- package/web/dist/assets/{chunk-XXDRQBXY-Cjm4mm6l.js → chunk-XXDRQBXY-plM48yQb.js} +1 -1
- package/web/dist/assets/classDiagram-OUVF2IWQ-33Sv-tmv.js +1 -0
- package/web/dist/assets/classDiagram-v2-EOCWNBFH-33Sv-tmv.js +1 -0
- package/web/dist/assets/{cose-bilkent-JH36ORCC-Zw9ZQbVl.js → cose-bilkent-JH36ORCC-cPPsd8jq.js} +1 -1
- package/web/dist/assets/{cynefin-VYW2F7L2-BYnR9YLM.js → cynefin-VYW2F7L2-DLoMRcB-.js} +1 -1
- package/web/dist/assets/{cynefinDiagram-TSTJHNR4-Cx8L0dOv.js → cynefinDiagram-TSTJHNR4-DbxB1EcR.js} +1 -1
- package/web/dist/assets/{dagre-VKFMJZFB-7GaqVcqz.js → dagre-VKFMJZFB-Cl5J3v7U.js} +1 -1
- package/web/dist/assets/{diagram-FQU43EPY-BWSRPJvU.js → diagram-FQU43EPY-C_5l69HJ.js} +1 -1
- package/web/dist/assets/{diagram-G47NLZAW-BELuAE1e.js → diagram-G47NLZAW-B_nxM69x.js} +1 -1
- package/web/dist/assets/{diagram-NH7WQ7WH-DGXhPpri.js → diagram-NH7WQ7WH-BogLLCcM.js} +1 -1
- package/web/dist/assets/{diagram-OA4YK3LP-DV8HqN0T.js → diagram-OA4YK3LP-1HZ1DJgO.js} +1 -1
- package/web/dist/assets/{diagram-WEI45ONY-Clv1X3ZL.js → diagram-WEI45ONY-CZ9akwtz.js} +1 -1
- package/web/dist/assets/{ebnfDiagram-CCIWWBDH-TpQx36oi.js → ebnfDiagram-CCIWWBDH-CCg2iaF2.js} +1 -1
- package/web/dist/assets/{erDiagram-Q63AITRT-DVVWd00c.js → erDiagram-Q63AITRT-BCYw6hLk.js} +1 -1
- package/web/dist/assets/{flowDiagram-23GEKE2U-Cdz_8_Dw.js → flowDiagram-23GEKE2U-B3O-UeAj.js} +1 -1
- package/web/dist/assets/{ganttDiagram-NO4QXBWP-zlco-o7u.js → ganttDiagram-NO4QXBWP-GJzz1tR4.js} +1 -1
- package/web/dist/assets/{gitGraphDiagram-IHSO6WYX-CfAZW1En.js → gitGraphDiagram-IHSO6WYX-Ch1cfaOe.js} +1 -1
- package/web/dist/assets/index-BUp5hFdX.css +1 -0
- package/web/dist/assets/{index-tQXCQojP.js → index-wYKm3Bnl.js} +6 -6
- package/web/dist/assets/{infoDiagram-FWYZ7A6U-0R-8efwI.js → infoDiagram-FWYZ7A6U-Bjo2ImAx.js} +1 -1
- package/web/dist/assets/{ishikawaDiagram-FXEZZL3T-lPpoXGlp.js → ishikawaDiagram-FXEZZL3T-Cknf936W.js} +1 -1
- package/web/dist/assets/{journeyDiagram-5HDEW3XC-D05vSVqu.js → journeyDiagram-5HDEW3XC-Chy2vDKP.js} +1 -1
- package/web/dist/assets/{kanban-definition-HUTT4EX6-ClaDdESv.js → kanban-definition-HUTT4EX6-BL4WMBwi.js} +1 -1
- package/web/dist/assets/{linear-CUnhHMvY.js → linear-B8XSGnZ8.js} +1 -1
- package/web/dist/assets/{mermaid.core-DaYS-X8Y.js → mermaid.core-CFdkmvEY.js} +4 -4
- package/web/dist/assets/{mindmap-definition-LN4V7U3C-N480VHds.js → mindmap-definition-LN4V7U3C-CHOBIkSR.js} +1 -1
- package/web/dist/assets/{papaparse.min-CNTcNgd8.js → papaparse.min-DnG1sqyK.js} +1 -1
- package/web/dist/assets/{pegDiagram-2B236MQR-CVWyJ5ck.js → pegDiagram-2B236MQR-VuMpZEdm.js} +1 -1
- package/web/dist/assets/{pieDiagram-ENE6RG2P-UR9uohPf.js → pieDiagram-ENE6RG2P-CkFTLWPp.js} +1 -1
- package/web/dist/assets/pilotswarm-CLJw14xm.js +97 -0
- package/web/dist/assets/{quadrantDiagram-ABIIQ3AL-D2SIOetn.js → quadrantDiagram-ABIIQ3AL-B74MHjsI.js} +1 -1
- package/web/dist/assets/{railroadDiagram-RFXS5EU6-OgN6qgOU.js → railroadDiagram-RFXS5EU6-CwcT-BI1.js} +1 -1
- package/web/dist/assets/{requirementDiagram-TGXJPOKE-BSUURBBz.js → requirementDiagram-TGXJPOKE-CfV8rmaQ.js} +1 -1
- package/web/dist/assets/{sankeyDiagram-HTMAVEWB-BBZhmSBZ.js → sankeyDiagram-HTMAVEWB-BECA4LLx.js} +1 -1
- package/web/dist/assets/{sequenceDiagram-DBY2YBRQ-C10IDNdW.js → sequenceDiagram-DBY2YBRQ-C80kbBkw.js} +1 -1
- package/web/dist/assets/{sizeCapture-X5ZJPWSS-B9787MHa.js → sizeCapture-X5ZJPWSS-BgdLZC94.js} +1 -1
- package/web/dist/assets/{stateDiagram-2N3HPSRC-BmSBo7es.js → stateDiagram-2N3HPSRC-DY_mnuOT.js} +1 -1
- package/web/dist/assets/stateDiagram-v2-6OUMAXLB-Dw3VhZ5V.js +1 -0
- package/web/dist/assets/{swimlanes-5IMT3BWC-DOXpv_KQ.js → swimlanes-5IMT3BWC-9m8kjDvw.js} +2 -2
- package/web/dist/assets/swimlanesDiagram-G3AALYLV-DoOI0AiK.js +8 -0
- package/web/dist/assets/{timeline-definition-FHXFAJF6-SjhGfPdI.js → timeline-definition-FHXFAJF6-CRDqu4Os.js} +1 -1
- package/web/dist/assets/{vennDiagram-L72KCM5P-BiujYen6.js → vennDiagram-L72KCM5P-B2KNeFvN.js} +1 -1
- package/web/dist/assets/{wardleyDiagram-EHGQE667-6nLXBvwc.js → wardleyDiagram-EHGQE667-DC0vN3Ub.js} +1 -1
- package/web/dist/assets/{xychartDiagram-FW5EYKEG-Di7ioTvW.js → xychartDiagram-FW5EYKEG-DOY6Rwu4.js} +1 -1
- package/web/dist/index.html +3 -3
- package/web/runtime.js +10 -0
- package/web/dist/assets/channel-D5LojeMw.js +0 -1
- package/web/dist/assets/classDiagram-OUVF2IWQ-C5edc5Or.js +0 -1
- package/web/dist/assets/classDiagram-v2-EOCWNBFH-C5edc5Or.js +0 -1
- package/web/dist/assets/index-CMtzFJre.css +0 -1
- package/web/dist/assets/pilotswarm-BG6hk0oE.js +0 -97
- package/web/dist/assets/stateDiagram-v2-6OUMAXLB-BqpsfoJI.js +0 -1
- package/web/dist/assets/swimlanesDiagram-G3AALYLV-k8WG_bWt.js +0 -8
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
// Column layout for fit-width markdown / chat tables. Lives in ui-core so
|
|
2
|
+
// the algorithm can be unit-tested without a DOM; web-app.js renders the
|
|
3
|
+
// result as a <colgroup> of percentages plus a min-width in ch.
|
|
4
|
+
//
|
|
5
|
+
// Terminology: the FLEX column is the one prose-like column that wraps to
|
|
6
|
+
// absorb overflow; every other column is RIGID and keeps its content width.
|
|
7
|
+
|
|
8
|
+
export function normalizeTableCellText(value = "") {
|
|
9
|
+
return String(value || "")
|
|
10
|
+
.replace(/\s+/g, " ")
|
|
11
|
+
.trim();
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
const FIT_WIDTH_FLEX_HEADER_KEYWORDS = [
|
|
15
|
+
"description",
|
|
16
|
+
"mechanism",
|
|
17
|
+
"details",
|
|
18
|
+
"notes",
|
|
19
|
+
"summary",
|
|
20
|
+
"message",
|
|
21
|
+
"comment",
|
|
22
|
+
"reason",
|
|
23
|
+
"body",
|
|
24
|
+
"content",
|
|
25
|
+
"explanation",
|
|
26
|
+
"rationale",
|
|
27
|
+
"one-liner",
|
|
28
|
+
];
|
|
29
|
+
|
|
30
|
+
const FIT_WIDTH_FLEX_MIN_MAX_LEN = 24;
|
|
31
|
+
const FIT_WIDTH_RIGID_CHAR_CAP = 32;
|
|
32
|
+
const FIT_WIDTH_MIN_RIGID_CHARS = 6;
|
|
33
|
+
const FIT_WIDTH_FLEX_MIN_CHARS = 30;
|
|
34
|
+
const FIT_WIDTH_FLEX_MAX_CHARS = 56;
|
|
35
|
+
const FIT_WIDTH_FLEX_MIN_FRACTION = 0.4;
|
|
36
|
+
const FIT_WIDTH_FLEX_TO_RIGID_RATIO = 1.4;
|
|
37
|
+
const FIT_WIDTH_MIN_EXTRA_CHARS = 2;
|
|
38
|
+
|
|
39
|
+
/**
|
|
40
|
+
* Compute per-column layout for a fit-width markdown / chat table.
|
|
41
|
+
*
|
|
42
|
+
* Strategy:
|
|
43
|
+
* 1. Measure max cell length and "wrappability" (cells with whitespace) per column.
|
|
44
|
+
* 2. Identify a single "flex" column — long, prose-like, ideally with a
|
|
45
|
+
* header keyword like Description / Mechanism / Notes. This column
|
|
46
|
+
* absorbs overflow by wrapping aggressively.
|
|
47
|
+
* 3. Give every other column a budget = clamp(maxLen + padding, MIN, RIGID_CAP),
|
|
48
|
+
* so rigid columns stay at their content-fit width even when one
|
|
49
|
+
* sibling column has hundreds of characters of prose.
|
|
50
|
+
* 4. Give the flex column a bounded share of the rigid-column budget. A
|
|
51
|
+
* very long cell should wrap; it should not steal so much percentage
|
|
52
|
+
* width that compact columns like Count / Status collapse on phones.
|
|
53
|
+
* 5. Return a minimum table width in ch so the wrapper can scroll
|
|
54
|
+
* horizontally rather than forcing all columns below readable size.
|
|
55
|
+
*
|
|
56
|
+
* Returns { widths: ["12.34%", ...], flexIndex: number, minWidth: "64ch" }
|
|
57
|
+
* when a flex column is identified — the table renderer then forces
|
|
58
|
+
* table-layout: fixed, adds an `is-flex-column` class to the chosen column,
|
|
59
|
+
* and gives the table a readable minimum width. Returns null when no flex
|
|
60
|
+
* column is found, in which case the renderer falls back to the browser's
|
|
61
|
+
* auto-table-layout (which is already good for short / uniform tables).
|
|
62
|
+
*
|
|
63
|
+
* Background: the previous behavior used the browser's auto-table-layout
|
|
64
|
+
* unconditionally. That works well when columns are uniform but is biased
|
|
65
|
+
* toward wide columns when one column has prose hundreds of characters
|
|
66
|
+
* long (e.g. a Mechanism / Description column) — auto-layout distributes
|
|
67
|
+
* width proportional to (max-content − min-content), which lets the prose
|
|
68
|
+
* column squeeze the rigid columns down to a few characters each.
|
|
69
|
+
*/
|
|
70
|
+
export function computeFitWidthColumnLayout(rows = []) {
|
|
71
|
+
const columnCount = Math.max(0, ...rows.map((row) => row.length));
|
|
72
|
+
if (columnCount <= 0) return null;
|
|
73
|
+
|
|
74
|
+
const headerRow = rows[0] || [];
|
|
75
|
+
const dataRowCount = Math.max(1, rows.length - 1);
|
|
76
|
+
|
|
77
|
+
const stats = Array.from({ length: columnCount }, () => ({
|
|
78
|
+
max: 0,
|
|
79
|
+
// Longest run without whitespace. A rigid column wraps at spaces
|
|
80
|
+
// only, so this is the narrowest it can be drawn without breaking
|
|
81
|
+
// a word — a 60-char CamelCase test name, a URL, a hash.
|
|
82
|
+
longestToken: 0,
|
|
83
|
+
spaceCells: 0,
|
|
84
|
+
}));
|
|
85
|
+
for (let rowIndex = 0; rowIndex < rows.length; rowIndex += 1) {
|
|
86
|
+
const row = rows[rowIndex];
|
|
87
|
+
for (let columnIndex = 0; columnIndex < columnCount; columnIndex += 1) {
|
|
88
|
+
const text = normalizeTableCellText(row[columnIndex] || "");
|
|
89
|
+
if (text.length > stats[columnIndex].max) stats[columnIndex].max = text.length;
|
|
90
|
+
if (rowIndex > 0 && /\s/.test(text)) stats[columnIndex].spaceCells += 1;
|
|
91
|
+
for (const token of text.split(/\s+/)) {
|
|
92
|
+
if (token.length > stats[columnIndex].longestToken) stats[columnIndex].longestToken = token.length;
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
let flexIndex = -1;
|
|
98
|
+
let flexScore = 0;
|
|
99
|
+
for (let columnIndex = 0; columnIndex < columnCount; columnIndex += 1) {
|
|
100
|
+
const stat = stats[columnIndex];
|
|
101
|
+
if (stat.max < FIT_WIDTH_FLEX_MIN_MAX_LEN) continue;
|
|
102
|
+
const spaceRatio = stat.spaceCells / dataRowCount;
|
|
103
|
+
if (spaceRatio < 0.4) continue;
|
|
104
|
+
const headerText = normalizeTableCellText(headerRow[columnIndex] || "").toLowerCase();
|
|
105
|
+
const headerBonus = FIT_WIDTH_FLEX_HEADER_KEYWORDS.some((keyword) => headerText.includes(keyword)) ? 60 : 0;
|
|
106
|
+
const score = stat.max + headerBonus;
|
|
107
|
+
if (score > flexScore) {
|
|
108
|
+
flexScore = score;
|
|
109
|
+
flexIndex = columnIndex;
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
if (flexIndex < 0) return null;
|
|
114
|
+
|
|
115
|
+
const rigidBudgets = stats.map((stat, columnIndex) => {
|
|
116
|
+
if (columnIndex === flexIndex) return 0;
|
|
117
|
+
// The cap keeps a column of many short words from hogging width; it
|
|
118
|
+
// must never cut a single word. Under the fixed layout a rigid cell
|
|
119
|
+
// wraps at spaces only, so a budget below the longest token painted
|
|
120
|
+
// that token across the next column. The floor makes the table's
|
|
121
|
+
// min-width grow instead — past the pane, the wrapper scrolls.
|
|
122
|
+
return Math.max(
|
|
123
|
+
FIT_WIDTH_MIN_RIGID_CHARS,
|
|
124
|
+
Math.min(stat.max + 2, FIT_WIDTH_RIGID_CHAR_CAP),
|
|
125
|
+
stat.longestToken + 2,
|
|
126
|
+
);
|
|
127
|
+
});
|
|
128
|
+
const sumRigid = rigidBudgets.reduce((sum, value) => sum + value, 0);
|
|
129
|
+
const flexStat = stats[flexIndex];
|
|
130
|
+
const flexBudget = Math.max(
|
|
131
|
+
FIT_WIDTH_FLEX_MIN_CHARS,
|
|
132
|
+
Math.min(
|
|
133
|
+
flexStat.max * 0.45,
|
|
134
|
+
FIT_WIDTH_FLEX_MAX_CHARS,
|
|
135
|
+
Math.max(FIT_WIDTH_FLEX_MIN_CHARS, sumRigid * FIT_WIDTH_FLEX_TO_RIGID_RATIO),
|
|
136
|
+
),
|
|
137
|
+
);
|
|
138
|
+
const budgets = rigidBudgets.map((value, columnIndex) => (
|
|
139
|
+
columnIndex === flexIndex ? flexBudget : value
|
|
140
|
+
));
|
|
141
|
+
|
|
142
|
+
const totalBudget = budgets.reduce((sum, value) => sum + value, 0);
|
|
143
|
+
if (totalBudget > 0 && budgets[flexIndex] / totalBudget < FIT_WIDTH_FLEX_MIN_FRACTION) {
|
|
144
|
+
const sumRigid = totalBudget - budgets[flexIndex];
|
|
145
|
+
budgets[flexIndex] = sumRigid * (FIT_WIDTH_FLEX_MIN_FRACTION / (1 - FIT_WIDTH_FLEX_MIN_FRACTION));
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
const finalTotal = budgets.reduce((sum, value) => sum + value, 0);
|
|
149
|
+
if (!(finalTotal > 0)) return null;
|
|
150
|
+
return {
|
|
151
|
+
widths: budgets.map((value) => `${((value / finalTotal) * 100).toFixed(2)}%`),
|
|
152
|
+
flexIndex,
|
|
153
|
+
minWidth: `${Math.ceil(finalTotal + FIT_WIDTH_MIN_EXTRA_CHARS)}ch`,
|
|
154
|
+
};
|
|
155
|
+
}
|