Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
01c1d2e
Add action-tracker input schema definition
luanzeba Jan 24, 2026
1f1ea76
Add ActionTrackerInput component (MVP)
luanzeba Jan 24, 2026
7adaedb
Register ActionTrackerInput in ConfigurableInput
luanzeba Jan 24, 2026
cf38349
Update store to handle action-tracker dynamic fields
luanzeba Jan 24, 2026
15fee35
Add example action-tracker inputs for Auto and Teleop phases
luanzeba Jan 24, 2026
bda9b6e
Regenerate JSON schema with action-tracker type
luanzeba Jan 24, 2026
91be629
Fix Copy Column Names to use fieldValues codes for action-tracker sup…
luanzeba Jan 24, 2026
a5cee22
Delete .claude/settings.local.json
luanzeba Jan 25, 2026
6a30283
Delete CLAUDE.md
luanzeba Jan 25, 2026
50e45ef
Fix Copy Column Names to expand action-tracker with human-friendly names
luanzeba Jan 26, 2026
9ce9f91
Add optional icon property to action schema
luanzeba Jan 26, 2026
12277e6
Add DynamicIcon component for lazy-loaded Lucide icons in action buttons
luanzeba Jan 26, 2026
b1bed3c
Regenerate JSON schema with icon property in action definition
luanzeba Jan 26, 2026
f0c915d
Add example Lucide icons to action-tracker buttons in sample config
luanzeba Jan 26, 2026
467ff9c
fix: use min-height for action buttons to accommodate icons and wrapp…
luanzeba Jan 26, 2026
67064a6
perf: lazy-load DynamicIcon module to reduce main bundle size
luanzeba Jan 26, 2026
f91fb0a
fix: use h-auto on action buttons to prevent icon overflow
luanzeba Jan 26, 2026
1059bcc
feat: add mode option (tap/hold) to action-tracker schema
luanzeba Jan 28, 2026
db6cb2d
feat: implement hold mode for action-tracker with multi-touch support
luanzeba Jan 28, 2026
3752bcc
chore: add mode: hold to test config action-trackers
luanzeba Jan 28, 2026
f9dda07
fix: improve touch handling with intent delay and scroll detection
luanzeba Jan 28, 2026
5d07b55
Merge main into add-timed-action-input
luanzeba Feb 5, 2026
302e391
docs: add action-tracker documentation, remove example config
luanzeba Feb 5, 2026
0b99e17
docs: update README action-tracker example and clean up comment
luanzeba Feb 5, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
99 changes: 98 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ A QR Code-based scouting system for FRC
- [Using Multi-Select Input](#using-multi-select-input)
- [Using Image Input](#using-image-input)
- [Using Timer Input](#using-timer-input)
- [Using Action Tracker Input](#using-action-tracker-input)
- [Using The Blue Alliance (TBA) Integration](#using-the-blue-alliance-tba-integration)

## Getting started

Expand Down Expand Up @@ -98,7 +100,7 @@ The basic structure of the config.json file is as follows:

`title`: The name of this field

`type`: One of "text", "number", "boolean", "range", "select", "counter", "timer", "multi-select", "image", "TBA-team-and-robot", or "TBA-match-number". Describes the type of input this is.
`type`: One of "text", "number", "boolean", "range", "select", "counter", "timer", "multi-select", "image", "action-tracker", "TBA-team-and-robot", or "TBA-match-number". Describes the type of input this is.

`required`: a boolean indicating if this must be filled out before the QRCode is generated. If any field with this set to true is not filled out, QRScout will not generate a QRCode when the commit button is pressed.

Expand Down Expand Up @@ -369,6 +371,101 @@ This allows scouts to accurately measure and compare the efficiency of different
4. **Backup Method**: Have a secondary way to record time in case of user error
5. **Practice Before Competition**: Make sure scouts are comfortable using the timer function before actual matches

### Using Action Tracker Input

The action tracker input type allows scouts to record timestamped robot actions during a match. Rather than just counting events, scouts can tap or hold action buttons as they happen, building a timeline of what the robot did and when. This enables analysis of cycle times, action sequences, and phase-specific performance.

#### Configuration in config.json

```json
{
"title": "Auto Actions",
"type": "action-tracker",
"required": false,
"code": "autoAction",
"description": "Track robot actions during autonomous",
"formResetBehavior": "reset",
"mode": "hold",
"timerDuration": 15,
"actions": [
{ "label": "Scored", "code": "score", "icon": "target" },
{ "label": "Picked Up", "code": "pickup", "icon": "package" },
{ "label": "Missed", "code": "miss", "icon": "x" }
]
}
```

#### Action Tracker Properties

- **actions**: An array of action objects, each with:
- `label`: Display text for the button
- `code`: Unique identifier for this action (used in field names)
- `icon` (optional): A [Lucide icon](https://lucide.dev/icons) name to display on the button
- **mode**: Determines how actions are recorded:
- `"tap"`: Records an instant timestamp when the button is tapped. Best for discrete events like scoring or picking up game pieces.
- `"hold"`: Records both start and end timestamps while the button is held down. Best for continuous actions like playing defense or climbing. Supports multi-touch for tracking overlapping actions.
- **timerDuration** (optional): Expected duration in seconds (e.g., 15 for auto, 135 for teleop). Used as a UI reference.

#### Using Action Tracker in the Form

The action tracker provides a timer and a grid of action buttons:

1. **Timer**: Starts automatically when the first action is recorded, or can be started manually
2. **Action Buttons**: Tap (or hold, depending on mode) to record actions with timestamps
3. **Undo Button**: Removes the most recent action if recorded in error
4. **Action Log**: Shows recent actions with their timestamps

#### Data Format

Each action in an action-tracker generates two output columns:

- `{code}_{actionCode}_count`: Integer count of how many times this action occurred
- `{code}_{actionCode}_times`: Comma-separated timestamps in seconds

For example, an auto tracker with code `autoAct` and a "score" action produces:
- `autoAct_score_count`: `3`
- `autoAct_score_times`: `2.1,8.4,12.7`

In hold mode, timestamps are recorded as `start-end` pairs (e.g., `2.1-4.5,8.4-10.2`).

When copying column names, action-tracker fields expand into human-friendly headers like "Scored in Auto (count)" and "Scored in Auto (timestamps)".

#### FRC Scouting Examples

Action trackers are particularly useful for:

- **Scoring Timeline**: Track when and how often a robot scores during each phase
- **Cycle Time Analysis**: Calculate average time between actions
- **Defense Tracking**: Record when a robot starts and stops playing defense (using hold mode)
- **Autonomous Paths**: Understand the sequence of actions during auto
- **Endgame Timing**: Track climb attempts and timing

For example, to track scoring actions during teleop:

```json
{
"title": "Teleop Scoring",
"type": "action-tracker",
"required": false,
"code": "teleopScore",
"mode": "tap",
"timerDuration": 135,
"actions": [
{ "label": "Speaker", "code": "speaker", "icon": "volume-2" },
{ "label": "Amp", "code": "amp", "icon": "zap" },
{ "label": "Missed", "code": "miss", "icon": "x" }
]
}
```

#### Best Practices for Action Tracker

1. **Choose the Right Mode**: Use `tap` for instant events (scoring, intake), use `hold` for duration-based actions (defense, climbing)
2. **Keep Actions Focused**: Limit each tracker to 4-6 related actions to avoid overwhelming scouts
3. **Separate Phases**: Use distinct action-trackers for Auto and Teleop to keep data organized
4. **Use Icons**: Icons help scouts quickly identify buttons during fast-paced matches
5. **Practice Before Competition**: Ensure scouts are comfortable with the tap/hold interaction before actual matches

### Using The Blue Alliance (TBA) Integration

QRScout includes specialized input types that integrate with The Blue Alliance API to automatically populate match and team data. This integration provides seamless data prefilling for official FRC events.
Expand Down
26 changes: 24 additions & 2 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

84 changes: 83 additions & 1 deletion public/schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,12 @@
"description": "Code of the form field to get this value from"
}
},
"description": "Whether or not to always show the selected team number at the top of the screen"
"required": [
"show",
"codeValue"
],
"additionalProperties": false,
"description": "Optional floating text box at the tob of the screen to show things like the team number. May be useful on small screens"
},
"theme": {
"type": "object",
Expand Down Expand Up @@ -662,6 +667,83 @@
"code"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"title": {
"$ref": "#/properties/sections/items/properties/fields/items/anyOf/0/properties/title"
},
"description": {
"$ref": "#/properties/sections/items/properties/fields/items/anyOf/0/properties/description"
},
"type": {
"type": "string",
"const": "action-tracker"
},
"required": {
"$ref": "#/properties/sections/items/properties/fields/items/anyOf/0/properties/required"
},
"code": {
"$ref": "#/properties/sections/items/properties/fields/items/anyOf/0/properties/code"
},
"disabled": {
"$ref": "#/properties/sections/items/properties/fields/items/anyOf/0/properties/disabled"
},
"formResetBehavior": {
"$ref": "#/properties/sections/items/properties/fields/items/anyOf/0/properties/formResetBehavior"
},
"defaultValue": {
"type": "null",
"default": null,
"description": "Default value (null, as this input generates multiple fields)"
},
"actions": {
"type": "array",
"items": {
"type": "object",
"properties": {
"label": {
"type": "string",
"description": "The display label for this action button"
},
"code": {
"type": "string",
"description": "A unique code for this action (used in field names)"
},
"icon": {
"type": "string",
"description": "Optional Lucide icon name (e.g., \"fuel\", \"target\"). See https://lucide.dev/icons"
}
},
"required": [
"label",
"code"
],
"additionalProperties": false
},
"minItems": 1,
"description": "The actions to track. Each action becomes a tappable button."
},
"timerDuration": {
"type": "number",
"description": "Expected duration in seconds (for UI reference, e.g., 15 for auto, 135 for teleop)"
},
"mode": {
"type": "string",
"enum": ["tap", "hold"],
"default": "hold",
"description": "Recording mode: 'tap' records instant timestamps on click, 'hold' records duration while button is pressed (default: 'hold')"
}
},
"required": [
"title",
"type",
"required",
"code",
"actions"
],
"additionalProperties": false
}
]
}
Expand Down
Loading