@lamemind/loom-deck 0.27.0 → 0.27.1

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 (2) hide show
  1. package/dist/cli.js +24 -4
  2. package/package.json +1 -1
package/dist/cli.js CHANGED
@@ -680,7 +680,11 @@ function Deck({ cwd, tasksPath, tasksDir }) {
680
680
  for (const r of sessionRows) {
681
681
  if (r.kind === 'separator')
682
682
  continue;
683
- if (isAll) {
683
+ // La colonna serve dove l'appartenenza NON è già scritta altrove sullo
684
+ // schermo: nella vista "tutte" (ogni riga ha un binding proprio) e su
685
+ // OGNI riga pinnata, in qualunque vista — una pinnata è sganciata dal
686
+ // parent selezionato, quindi l'header del pane non parla per lei.
687
+ if (isAll || r.kind === 'pinned') {
684
688
  const b = bindings.get(r.sessionId);
685
689
  if (b)
686
690
  task = Math.max(task, termWidth(b));
@@ -2059,8 +2063,17 @@ function SessionsPane({ parentLabel, isSpot, isAll, bindings, taskW, ageW, rows,
2059
2063
  // riga oltre il bordo, e a ripararla arrivava `cli-truncate` (che
2060
2064
  // sfora di una colonna per emoji e mangia il bordo stesso).
2061
2065
  const staleNote = sessionNotes.get(row.sessionId);
2062
- const staleW = Math.max(0, paneTextWidth(columns) - (2 /* caret */ + termWidth(`${WARN} pin stale `) + SID_CHARS + 3 /* spazio + caporali */));
2063
- return (_jsxs(Text, { inverse: sel && focused, bold: sel && !focused, dimColor: true, wrap: "truncate-end", children: [sel ? CARET : CARET_OFF, _jsx(Text, { color: "yellow", children: WARN }), " pin stale", ' ', _jsx(Text, { dimColor: true, children: row.sessionId.slice(0, SID_CHARS) }), staleNote ? _jsxs(Text, { color: "yellow", children: [" \u00AB", cut(staleNote, staleW), "\u00BB"] }) : null] }, row.sessionId));
2066
+ // La riga stale è libera (niente colonne: non ha titolo
2067
+ // data), ma il binding va detto lo stesso è una pinnata, quindi
2068
+ // l'header del pane non ne dice l'appartenenza.
2069
+ const staleTask = bindings.get(row.sessionId) ?? null;
2070
+ const staleW = Math.max(0, paneTextWidth(columns) -
2071
+ (2 /* caret */ +
2072
+ termWidth(`${WARN} pin stale `) +
2073
+ SID_CHARS +
2074
+ (staleTask ? termWidth(staleTask) + 1 : 0) +
2075
+ 3 /* spazio + caporali */));
2076
+ return (_jsxs(Text, { inverse: sel && focused, bold: sel && !focused, dimColor: true, wrap: "truncate-end", children: [sel ? CARET : CARET_OFF, _jsx(Text, { color: "yellow", children: WARN }), " pin stale", ' ', _jsx(Text, { dimColor: true, children: row.sessionId.slice(0, SID_CHARS) }), staleTask ? _jsxs(Text, { color: "green", children: [" ", staleTask] }) : null, staleNote ? _jsxs(Text, { color: "yellow", children: [" \u00AB", cut(staleNote, staleW), "\u00BB"] }) : null] }, row.sessionId));
2064
2077
  }
2065
2078
  const s = row.session; // non-stale → session presente
2066
2079
  const isPinnedRow = row.kind === 'pinned';
@@ -2076,6 +2089,13 @@ function SessionsPane({ parentLabel, isSpot, isAll, bindings, taskW, ageW, rows,
2076
2089
  // task accanto, che esiste solo in questa vista.
2077
2090
  const bound = bindings.get(s.sessionId) ?? null;
2078
2091
  const linked = isAll ? Boolean(bound) : !isSpot;
2092
+ // Stesso motivo per cui la colonna esiste: una pinnata resta in lista
2093
+ // qualunque sia il parent selezionato, quindi l'header non ne dice
2094
+ // l'appartenenza e la cella va riempita anche fuori dalla vista
2095
+ // "tutte". Sulle contestuali, dove l'header parla già, resta vuota —
2096
+ // ma la cella è comunque larga `taskW`, o le colonne a destra
2097
+ // slitterebbero riga per riga.
2098
+ const taskCell = isAll || isPinnedRow ? (bound ?? TASK_EMPTY) : '';
2079
2099
  // T60 — colonne VERE: ogni cella fissa è larga esattamente quanto
2080
2100
  // dichiara, riempita di spazi con `pad` (che misura in colonne, non in
2081
2101
  // caratteri). Il marker va portato a 2 anche quando è `○`, largo 1:
@@ -2109,7 +2129,7 @@ function SessionsPane({ parentLabel, isSpot, isAll, bindings, taskW, ageW, rows,
2109
2129
  const used = (label.note ? termWidth(label.note) + 2 : 0) +
2110
2130
  (label.note && label.rest ? 1 : 0) +
2111
2131
  termWidth(label.rest);
2112
- return (_jsxs(Text, { inverse: sel && focused, bold: sel && !focused, wrap: "truncate-end", children: [sel ? CARET : CARET_OFF, isPinnedRow ? (_jsx(Text, { color: "yellow", children: pad('📌', 2) })) : linked ? (_jsx(Text, { color: "green", children: pad('🔗', 2) })) : (_jsx(Text, { dimColor: true, children: pad('○', 2) })), ' ', _jsx(Text, { color: "cyan", children: s.sessionId.slice(0, SID_CHARS) }), ' ', taskW > 0 ? (_jsxs(_Fragment, { children: [_jsx(Text, { color: bound ? 'green' : undefined, dimColor: !bound, children: pad(bound ?? TASK_EMPTY, taskW) }), ' '] })) : null, forkMark ? _jsx(Text, { color: "magenta", children: forkMark }) : null, label.note ? (_jsxs(Text, { color: "yellow", bold: true, children: ["\u00AB", label.note, "\u00BB"] })) : null, label.note && label.rest ? ' ' : null, label.rest ? _jsx(Text, { dimColor: Boolean(label.note), children: label.rest }) : null, ' '.repeat(Math.max(0, inner - used)), ' ', _jsx(Text, { dimColor: true, children: pad(age, ageW, 'right') })] }, s.sessionId));
2132
+ return (_jsxs(Text, { inverse: sel && focused, bold: sel && !focused, wrap: "truncate-end", children: [sel ? CARET : CARET_OFF, isPinnedRow ? (_jsx(Text, { color: "yellow", children: pad('📌', 2) })) : linked ? (_jsx(Text, { color: "green", children: pad('🔗', 2) })) : (_jsx(Text, { dimColor: true, children: pad('○', 2) })), ' ', _jsx(Text, { color: "cyan", children: s.sessionId.slice(0, SID_CHARS) }), ' ', taskW > 0 ? (_jsxs(_Fragment, { children: [_jsx(Text, { color: bound && taskCell ? 'green' : undefined, dimColor: !bound, children: pad(taskCell, taskW) }), ' '] })) : null, forkMark ? _jsx(Text, { color: "magenta", children: forkMark }) : null, label.note ? (_jsxs(Text, { color: "yellow", bold: true, children: ["\u00AB", label.note, "\u00BB"] })) : null, label.note && label.rest ? ' ' : null, label.rest ? _jsx(Text, { dimColor: Boolean(label.note), children: label.rest }) : null, ' '.repeat(Math.max(0, inner - used)), ' ', _jsx(Text, { dimColor: true, children: pad(age, ageW, 'right') })] }, s.sessionId));
2113
2133
  })), detail ? (_jsx(SessionDetailPane, { s: detail, firstLines: firstLines, lastLines: lastLines, columns: columns, origin: forkOf.get(detail.sessionId) ?? null, note: sessionNotes.get(detail.sessionId) ?? '' })) : null] }));
2114
2134
  }
2115
2135
  // T49 — detail pane della sessione selezionata (hover), gemello del DetailPane
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lamemind/loom-deck",
3
- "version": "0.27.0",
3
+ "version": "0.27.1",
4
4
  "description": "Deck TUI Ink per-progetto della famiglia loom: legge tasks.md e spawna sessioni Claude Code bound via LOOM_TASK",
5
5
  "type": "module",
6
6
  "bin": {