@hank-warren/pi-ask-user-question 0.5.0 → 0.5.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.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,18 @@
1
1
  # @hank-warren/pi-ask-user-question
2
2
 
3
+ ## 0.5.1
4
+
5
+ ### Patch Changes
6
+
7
+ - 464fe1e: fix: pasting into the ask-user-question custom-answer field was silently dropped
8
+
9
+ pi-tui re-wraps pastes in bracketed-paste markers (`\x1b[200~ … \x1b[201~`) before they reach `handleInput`. The questionnaire dialog's free-text field only accepted printable chunks, so a paste — which contains ESC — fell through every key predicate into the inert branch and vanished. The note editor was unaffected because `handleCommentKey` buffers its own pastes.
10
+
11
+ The bracketed-paste state machine inside `handleCommentKey` is now extracted as a new shared export, `consumePasteChunk` (pi-permission-selector minor), and the custom-answer field routes input through it: single-chunk and chunk-spanning pastes insert, multi-line pastes flatten to one line, and input trailing the end marker is re-dispatched as ordinary keys.
12
+
13
+ - Updated dependencies [464fe1e]
14
+ - @hank-warren/pi-permission-selector@1.2.0
15
+
3
16
  ## 0.5.0
4
17
 
5
18
  ### Minor Changes
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hank-warren/pi-ask-user-question",
3
- "version": "0.5.0",
3
+ "version": "0.5.1",
4
4
  "description": "Structured questionnaire tool for Pi with numbered options, digit hotkeys and Tab-to-comment, composed from the shared permission-selector component.",
5
5
  "type": "module",
6
6
  "keywords": [
@@ -46,7 +46,7 @@
46
46
  "CHANGELOG.md"
47
47
  ],
48
48
  "dependencies": {
49
- "@hank-warren/pi-permission-selector": "^1.1.0"
49
+ "@hank-warren/pi-permission-selector": "^1.2.0"
50
50
  },
51
51
  "peerDependencies": {
52
52
  "@earendil-works/pi-coding-agent": "*",
package/view/dialog.ts CHANGED
@@ -39,6 +39,7 @@
39
39
  */
40
40
 
41
41
  import {
42
+ consumePasteChunk,
42
43
  isBackspaceKey,
43
44
  isCharKey,
44
45
  isEnterKey,
@@ -99,6 +100,14 @@ const PREVIEW_MAX_ROWS = 12;
99
100
  interface TabState {
100
101
  selector: OptionSelector;
101
102
  customText?: string;
103
+ /**
104
+ * In-progress bracketed paste aimed at the custom-answer field. pi-tui wraps
105
+ * pastes in `\x1b[200~ … \x1b[201~` and the markers can span input chunks;
106
+ * a paste chunk fails every key predicate, so without this buffer pasting
107
+ * into the field was silently dropped (the note editor was unaffected —
108
+ * handleCommentKey buffers its own pastes).
109
+ */
110
+ pasteBuffer?: string;
102
111
  pendingNotes?: string;
103
112
  /**
104
113
  * Labels checked alongside the sentinel row on a multi-select question, held
@@ -371,10 +380,26 @@ export class QuestionnaireDialog {
371
380
  // Free-text mode. Every check below MUST use a shared predicate — see
372
381
  // rule 1. Esc unwinds to the option list rather than cancelling the
373
382
  // dialog: one Esc never discards more than one layer.
383
+ //
384
+ // Bracketed pastes come first: a paste chunk contains ESC, so it would
385
+ // otherwise fall through every predicate into the inert branch and vanish.
386
+ const paste = consumePasteChunk(tab.pasteBuffer, keyData);
387
+ if (paste !== undefined) {
388
+ tab.pasteBuffer = paste.buffer;
389
+ if (paste.text !== undefined) {
390
+ tab.customText += paste.text;
391
+ this.repaint();
392
+ }
393
+ // Ordinary input after the end marker (e.g. a trailing Enter) goes back
394
+ // through normal key handling.
395
+ if (paste.rest) this.handleInput(paste.rest);
396
+ return;
397
+ }
374
398
  if (isEscapeKey(keyData)) {
375
399
  // Back to the option list. The selector still holds every tick, so a
376
400
  // multi-select question is exactly as the user left it.
377
401
  tab.customText = undefined;
402
+ tab.pasteBuffer = undefined;
378
403
  tab.pendingNotes = undefined;
379
404
  tab.pendingSelected = undefined;
380
405
  this.repaint();
@@ -394,6 +419,7 @@ export class QuestionnaireDialog {
394
419
  this.session.recordAnswer(text, { custom: true, notes: tab.pendingNotes });
395
420
  }
396
421
  tab.customText = undefined;
422
+ tab.pasteBuffer = undefined;
397
423
  tab.pendingNotes = undefined;
398
424
  tab.pendingSelected = undefined;
399
425
  this.afterAnswer();