From d48bb1b052467859a158974249ade20c6f3af58b Mon Sep 17 00:00:00 2001 From: tolvitty Date: Fri, 13 Feb 2026 14:40:24 +0100 Subject: [PATCH] docs: add Phase 1 quick wins design document Covers new field types (slider, color, time), keyboard navigation, and form import/export. Co-Authored-By: Claude Opus 4.6 --- .../2026-02-13-phase1-quick-wins-design.md | 126 ++++++++++++++++++ 1 file changed, 126 insertions(+) create mode 100644 docs/plans/2026-02-13-phase1-quick-wins-design.md diff --git a/docs/plans/2026-02-13-phase1-quick-wins-design.md b/docs/plans/2026-02-13-phase1-quick-wins-design.md new file mode 100644 index 0000000..da50729 --- /dev/null +++ b/docs/plans/2026-02-13-phase1-quick-wins-design.md @@ -0,0 +1,126 @@ +# Phase 1 — Quick Wins Design + +**Status:** Approved +**Date:** 2026-02-13 +**Scope:** New field types, keyboard navigation, form import/export + +--- + +## Overview + +Phase 1 adds three categories of improvements to Formfire: +1. Three new field types (slider, color, time) +2. Keyboard navigation in the form modal +3. Form import/export via JSON files + +These features extend existing patterns with minimal architectural changes. + +--- + +## 1. New Field Types + +### Type System Changes (`types.ts`) + +Extend `FieldType` union with `'slider' | 'color' | 'time'`. + +Add optional properties to `FormField`: +- `min?: number` — slider minimum (default: 0) +- `max?: number` — slider maximum (default: 100) +- `step?: number` — slider step increment (default: 1) + +### Renderers (`field-renderers.ts`) + +| Type | HTML Element | getValue() | Notes | +|------|-------------|------------|-------| +| `slider` | `` + value label | `number` | Live value display, min/max/step from FormField | +| `color` | `` + hex label | `string` (#hex) | Default: `#000000` | +| `time` | `` | `string` (HH:MM) | Mirrors existing date renderer pattern | + +All three implement the standard `RenderedField` interface (getValue/setValue/setError). + +### Builder Changes (`form-builder.ts`) + +- Add `'slider'`, `'color'`, `'time'` to `FIELD_TYPES` array +- Show Min/Max/Step settings when field type is `slider` +- Placeholder support for `time` (same as date) + +### Validation (`validators.ts`) + +- Slider: validate value is within min/max range + +--- + +## 2. Keyboard Navigation + +### Form Modal (`form-modal.ts`) + +Single `keydown` listener on modal contentEl with event delegation: + +- **Ctrl+Enter** → Submit form (always) +- **Enter** on single-line inputs (text, number, date, time, color, dropdown) → Submit, unless a suggest dropdown is open +- **Enter** on textarea → normal line break (no submit) +- **Escape** → Close modal (already handled by Obsidian's Modal base class) + +### Field Renderer Accessibility (`field-renderers.ts`) + +- **Toggle**: Add `tabindex="0"`, Space/Enter to toggle +- **Rating**: Add `tabindex="0"`, Arrow Left/Right to change value, Enter to confirm +- **Tags**: Input already has focus handling, just needs tab-order + +Tab order follows field definition order naturally via DOM order. + +--- + +## 3. Form Import/Export + +### New Module: `src/utils/form-io.ts` + +Two pure functions: + +```typescript +exportForms(forms: FormDefinition[]): string +``` +Serializes to JSON with version wrapper: `{ version: 1, forms: [...] }`. + +```typescript +importForms(json: string): FormDefinition[] +``` +Parses JSON, validates structure (forms array, each form has id/name/fields), generates new UUIDs for imported forms to prevent ID collisions. + +### Settings Tab Changes (`settings-tab.ts`) + +New buttons below "New Form": +- **Export All** — Creates JSON blob, triggers browser download as `formfire-export.json` +- **Import** — Opens native file input (``), reads file, validates, adds forms to store + +Per-form **Export** button in the form list (alongside Edit/Duplicate/Delete). Exports single form. + +### Error Handling + +- Invalid JSON → `Notice("Invalid JSON file")` +- Missing required fields → `Notice("Invalid form format")` +- Success → `Notice("Imported X form(s)")` + +No import preview modal — validation is sufficient. YAGNI. + +--- + +## Files Changed + +| File | Change | +|------|--------| +| `src/types.ts` | Extend FieldType, add min/max/step to FormField | +| `src/ui/field-renderers.ts` | Add slider, color, time renderers; add tabindex/keyboard to toggle, rating | +| `src/ui/form-modal.ts` | Add keydown listener for Ctrl+Enter, Enter submit | +| `src/ui/form-builder.ts` | Extend FIELD_TYPES, add slider-specific settings | +| `src/utils/validators.ts` | Add slider range validation | +| `src/utils/form-io.ts` | **New** — exportForms, importForms | +| `src/ui/settings-tab.ts` | Add Export All, Import, per-form Export buttons | +| `styles.css` | Styles for slider, color, time fields | + +## Out of Scope + +- Import preview/diff modal +- Clipboard-based import/export +- Cloud sync or sharing +- Migration logic between form versions