fix(widgets): mark TextInput dirty after state mutations#677
Conversation
📝 WalkthroughWalkthrough
ChangesTextInput dirty state tracking
Estimated code review effort🎯 2 (Simple) | ⏱️ ~8 minutes Poem
🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Comment |
There was a problem hiding this comment.
🧹 Nitpick comments (1)
packages/widgets/src/input/TextInput.ts (1)
94-105: 💤 Low valueConsider guarding markDirty() calls for consistency.
The cursor movement methods call
markDirty()unconditionally, even when the cursor position doesn't actually change (e.g., moving left when already at position 0). This differs fromdeleteBackanddeleteForward, which only callmarkDirty()when state actually changes.While the current implementation is functionally correct (markDirty() is idempotent and cheap), aligning these methods with the conditional pattern would improve consistency.
♻️ Optional refactor for consistency
-moveCursorLeft(): void { this._cursorPos = Math.max(0, this._cursorPos - 1); - this.markDirty(); -} -moveCursorRight(): void { this._cursorPos = Math.min(this._value.length, this._cursorPos + 1); - this.markDirty(); -} -moveCursorHome(): void { this._cursorPos = 0; - this.markDirty(); -} -moveCursorEnd(): void { this._cursorPos = this._value.length; - this.markDirty(); - } +moveCursorLeft(): void { + const newPos = Math.max(0, this._cursorPos - 1); + if (newPos !== this._cursorPos) { + this._cursorPos = newPos; + this.markDirty(); + } +} +moveCursorRight(): void { + const newPos = Math.min(this._value.length, this._cursorPos + 1); + if (newPos !== this._cursorPos) { + this._cursorPos = newPos; + this.markDirty(); + } +} +moveCursorHome(): void { + if (this._cursorPos !== 0) { + this._cursorPos = 0; + this.markDirty(); + } +} +moveCursorEnd(): void { + if (this._cursorPos !== this._value.length) { + this._cursorPos = this._value.length; + this.markDirty(); + } +}🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@packages/widgets/src/input/TextInput.ts` around lines 94 - 105, The cursor movement methods (moveCursorLeft, moveCursorRight, moveCursorHome, moveCursorEnd) call markDirty() unconditionally; change each to compute the new position first, compare it against this._cursorPos, update this._cursorPos and call this.markDirty() only when the position actually changed so behavior matches deleteBack/deleteForward's conditional dirty-marking.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Nitpick comments:
In `@packages/widgets/src/input/TextInput.ts`:
- Around line 94-105: The cursor movement methods (moveCursorLeft,
moveCursorRight, moveCursorHome, moveCursorEnd) call markDirty()
unconditionally; change each to compute the new position first, compare it
against this._cursorPos, update this._cursorPos and call this.markDirty() only
when the position actually changed so behavior matches
deleteBack/deleteForward's conditional dirty-marking.
ℹ️ Review info
⚙️ Run configuration
Configuration used: defaults
Review profile: CHILL
Plan: Pro Plus
Run ID: 08f39626-f885-47c0-bacd-40eb5fec80dd
📒 Files selected for processing (1)
packages/widgets/src/input/TextInput.ts
Description
This PR fixes a rendering issue in the TextInput widget where several state-mutating methods updated internal state without calling markDirty().
Added markDirty() calls to all methods that modify rendered state (value setter, text insertion/deletion, cursor movement, and clear operation) so programmatic updates trigger immediate re-rendering.
Related Issue
Closes #675
Which package(s)?
@termuijs/widgets
Type of Change
type:bug)type:feature)type:docs)type:testing)type:refactor)type:design)type:accessibility)type:performance)type:devops)type:security)Checklist
needs-starcheck blocks your merge otherwise.bun vitest runbun run buildbun run typecheckCONTRIBUTING.md.type: short description.markDirty()(if your change affects rendering).anytypes without an inline comment explaining why.GSSoC 2026 Participation
https://gssoc.girlscript.org/profile/a80c7e63-fb5a-4d58-aec9-115f9a2798b7Screenshots / Recordings (UI changes)
N/A
Notes for the Reviewer
This change is intentionally limited to TextInput state-mutating methods and does not modify rendering logic or widget behavior beyond ensuring proper dirty-state propagation after updates.
Validation completed:
Summary by CodeRabbit