🏭 GooseFactory HITL Modals

Interactive MCP App modals for Human-in-the-Loop feedback collection.

What's Here

5 production-ready, self-contained HTML modals designed for sandboxed iframes inside AI chat interfaces:

Modal File Use Case Key Feature
🚦 Traffic Light src/traffic-light.html Pass/Polish/Rework decisions LED glow, tag pills, response time tracking
📋 Report Card src/report-card.html Multi-dimension grading (A-F) Bubble-fill animation, GPA auto-calc, grade change tracking
Speed Round src/speed-round.html Batch pass/fail (timed) 60s timer, streak counter, skip detection, full stats
⚔️ Side-by-Side Arena src/side-by-side.html A/B comparison Hover time tracking, per-dimension breakdown, winner celebration
🌡️ Thermometer src/thermometer.html Subjective quality (0-100) Draggable mercury, bg color transitions, particles, drag journey capture

Quick Start

# Serve the preview page
npx serve src/preview -p 3333

# Or serve all files for direct access
npx serve src -p 3334

Then open http://localhost:3333 for the interactive preview environment.

Architecture

Self-Contained

Each modal is a single HTML file with inline CSS and JS. No external dependencies. This is intentional — modals are served as MCP App resources inside sandboxed iframes.

Communication Protocol

Every modal follows the CONTRACTS.md §3 "Modal Data Contract":

Host → Modal:  window.__FACTORY_CONTEXT__  (injected before load)
Modal → Host:  window.parent.postMessage()

Message Types

Type Direction When
factory_modal_ready Modal → Host Modal loaded and interactive
factory_modal_response Modal → Host User submitted feedback
factory_modal_close Modal → Host Modal wants to close
factory_modal_resize Modal → Host Modal wants to change size
factory_modal_error Modal → Host Modal hit an error

Hidden Behavioral Metrics

Every modal automatically captures:

  • timeToFirstInteractionMs — How long before user engaged
  • timeToDecisionMs — Total time from open to submit
  • totalInteractions — Click/tap count
  • fieldsModified — Which inputs were changed
  • deviceType — Mobile vs desktop
  • viewportSize — Screen dimensions

Plus modal-specific metrics:

  • Traffic Light: responseTimeMs (fast = high confidence)
  • Report Card: gradeChanges (mind-change tracking)
  • Speed Round: Per-item timeMs, streaks, speed curve
  • Side-by-Side: hoverTimeA/B (attention distribution)
  • Thermometer: dragJourney (full temperature path during drag)

File Structure

packages/modals/
├── package.json
├── README.md                    ← You are here
├── src/
│   ├── traffic-light.html       ← 🚦 Pass/Polish/Rework
│   ├── report-card.html         ← 📋 A-F grading
│   ├── speed-round.html         ← ⚡ Timed batch review
│   ├── side-by-side.html        ← ⚔️ A/B comparison
│   ├── thermometer.html         ← 🌡️ Quality temperature
│   ├── shared/
│   │   └── modal-utils.js       ← Canonical utility functions
│   └── preview/
│       └── index.html           ← Dev preview page with mock context & console

Design Principles

  1. 3-Second Rule — Instantly obvious what to do
  2. Dopamine Design — Every interaction feels satisfying
  3. Data Density — Rich signal from every tap/drag/click
  4. Dark Mode First#111 background, designed for chat panels
  5. Touch-Friendly — 48px minimum tap targets
  6. 400-600px Width — Optimized for chat panel constraints

Integrating with GooseFactory

MCP App Host Usage

// In your MCP tool response:
const response = {
  _meta: {
    goose: {
      toolUI: {
        displayType: "inline",
        name: "Traffic Light Review",
        renderer: "mcp-ui",
      },
    },
  },
  content: [{
    uri: "ui://factory-modal",
    mimeType: "text/html",
    text: trafficLightHtml, // The full HTML file content
  }],
};

McpAppHost Component

The host component (React/Desktop) should:

  1. Create a sandboxed iframe with allow-scripts allow-forms
  2. Inject window.__FACTORY_CONTEXT__ before the modal HTML
  3. Listen for postMessage events
  4. Forward factory_modal_response to POST /v1/feedback
  5. Handle timeouts gracefully

See CONTRACTS.md §4.4 for the full McpAppHost component contract.

Preview Page

The preview page at src/preview/index.html provides:

  • Sidebar with all 5 modals
  • 500px-wide iframe with simulated device chrome
  • Mock context data (editable pipeline/item names)
  • Real-time postMessage console showing all events
  • Reload and new-window buttons for testing

Next Modals (Planned)

The design doc (design-hitl-modal-collection.md) defines 25 total modals. Next batch:

  • 🃏 Tinder Swipe — Batch card swiping
  • 🎯 Spotlight — Code annotation with attention heatmap
  • 🏆 Judge's Scorecard — Olympic-style weighted scoring
  • 🎲 Priority Poker — Fibonacci estimation cards
  • 🔫 Mission Briefing — High-stakes go/no-go with flight checks