Files of Rules and state in microinteractions
wondelai/
Show the full text252 lines
Rules and State in Microinteractions
Rules are the invisible engine of a microinteraction. Once a trigger fires, rules determine what happens: what changes, in what order, with what constraints, and when the interaction ends. Users never see rules directly -- they experience their effects through feedback. But when rules are poorly designed, users feel it immediately: the toggle that does not remember its position, the slider that jumps to unexpected values, the form that erases their input on error.
What Rules Define
Every microinteraction's rules answer these questions:
| Question | What It Determines | Example |
|---|---|---|
| What happens first? | The initial response to the trigger | Button text changes to "Saving..." |
| What sequence follows? | Steps that occur in order | Validate input, send request, show result |
| What can the user do during? | Available actions while processing | Cancel button appears during upload |
| What can the user NOT do? | Constraints that prevent errors | Cannot submit form with empty required fields |
| What are the boundaries? | Minimum, maximum, and default values | Character limit: 280; volume: 0-100%; quantity: 1-99 |
| When does it end? | Completion condition | Request returns success; timer reaches zero |
| What if it fails? | Error handling behavior | Show error message, preserve input, suggest fix |
Defining Rules: The Goal-First Method
Start with the goal, not the interface. What is the user trying to accomplish? Derive every rule from that goal.
Process
- State the goal in one sentence: "The user wants to set their alarm time."
- Identify the minimum inputs: Time (hour, minute), AM/PM, days of week.
- Define the simplest path: Tap time, scroll to desired hour/minute, toggle AM/PM, select days, confirm.
- Add constraints: Cannot set alarm in the past (today). Maximum 20 alarms. Minimum interval between alarms: 1 minute.
- Handle failures: If alarm cannot be set (permission denied), show error with action to fix it.
- Define the end state: Alarm is set, confirmation shown, alarm appears in list.
Rule Complexity vs. Frequency
| Usage Frequency | Rule Complexity | Rationale | Example |
|---|---|---|---|
| Many times per day | Minimal rules, zero configuration | Must be instant and frictionless | Liking a post: one tap, done |
| Once per day | Simple rules, smart defaults | Allow some configuration | Setting an alarm: time + days |
| Once per week | Moderate rules, options available | Users can invest time | Scheduling a meeting: time, attendees, recurrence |
| Once ever | Full rule set, onboarding acceptable | First-time setup | Account creation: email, password, preferences |
State Management Within Microinteractions
Every microinteraction has state -- the current condition of the interaction at any given moment. Managing state well means users always know where they are, what happened, and what they can do next.
Core States of a Microinteraction
| State | Description | Visual Indicator | User Can... |
|---|---|---|---|
| Idle | Ready and waiting for trigger | Default appearance | Initiate the interaction |
| Active/In Progress | Processing or awaiting input | Loading spinner, active color | Cancel, wait, or provide input |
| Success | Completed successfully | Green checkmark, confirmation text | Move on, undo (if available) |
| Error | Failed to complete | Red indicator, error message | Retry, correct input, dismiss |
| Partial | Partially complete or partially loaded | Partial progress, skeleton | Continue, wait for more |
| Disabled | Cannot be initiated | Grayed out, reduced opacity | Nothing (show reason on hover/focus) |
State Transition Map
Map every possible transition between states to ensure no combination is overlooked:
┌─────────┐
trigger │ IDLE │ reset
┌─────────→│ │←──────────┐
│ └────┬────┘ │
│ │ trigger │
│ ▼ │
│ ┌──────────┐ │
│ │ ACTIVE │───────────┤
│ │ │ cancel │
│ └────┬─────┘ │
│ ┌──┴──┐ │
│ │ │ │
│ success fail │
│ │ │ │
│ ▼ ▼ │
│ ┌────────┐ ┌───────┐ │
│ │SUCCESS │ │ ERROR │ │
│ │ │ │ │──retry─┘
│ └───┬────┘ └───────┘
│ │ timeout/dismiss
└─────────┘
State Persistence
| Persistence Type | When to Use | Storage Method | Example |
|---|---|---|---|
| Ephemeral | Within a single session | Component state (React state, SwiftUI @State) | Hover state, dropdown open/closed |
| Session | Across page navigations, lost on close | Session storage, navigation state | Form progress, scroll position |
| Persistent | Across sessions, survives app close | Local storage, database, user preferences | Theme setting, notification preferences |
| Synced | Across devices | Cloud database, account-linked storage | Read/unread status, bookmarks |
Constraints and Limitations
Constraints are rules that prevent errors by limiting what users can do. Well-designed constraints feel natural -- users do not notice them because the wrong action was never possible.
Types of Constraints in Microinteractions
| Constraint Type | Mechanism | Example |
|---|---|---|
| Range | Limit input to min/max values | Volume slider: 0-100%, cannot exceed |
| Format | Enforce specific input patterns | Phone field: auto-formats as (555) 123-4567 |
| Type | Restrict input to valid characters | Numeric field: keyboard shows numbers only |
| Sequence | Enforce step order | Payment flow: shipping before payment before confirm |
| Dependency | One option enables/disables others | "Ship to different address" checkbox reveals address form |
| Capacity | Limit quantity or selection count | File upload: maximum 5 files, 10MB each |
| Temporal | Restrict timing of actions | "Undo send": available for 30 seconds only |
Implementing Constraints Gracefully
Prevent rather than punish. The best constraint is one users never encounter because the wrong action was impossible:
| Punishing (bad) | Preventing (good) |
|---|---|
| "Invalid date format" error after typing | Date picker control that only allows valid dates |
| "That username is taken" after submitting form | Real-time availability check as user types |
| "File too large" error after waiting for upload | Show size limit upfront; disable upload for oversized files |
| "Cannot select past dates" error message | Gray out and disable past dates in calendar |
Communicating Constraints
| Method | When to Use | Example |
|---|---|---|
| Disabled state | Action not available yet | Submit button grayed until form is valid |
| Counter | Approaching a limit | "23/280 characters" or "3 of 5 files uploaded" |
| Visual boundary | Range limits | Slider track shows min/max; cursor stops at edges |
| Inline hint | Format requirements | "Must be 8+ characters with one number" below password field |
| Progressive disclosure | Complex constraints | Advanced options hidden behind "Show more" |
Error States
Error states are what happens when rules are violated or when the system fails. Error handling is where most microinteractions fall apart -- and where thoughtful design has the most impact on user trust.
Error State Principles
1. Preserve the user's work. Never erase input on error. If a form fails validation, keep everything the user typed.
2. Explain in human language. Not "Error 422: Unprocessable Entity" but "That email address looks incomplete. Did you forget the domain (e.g., @gmail.com)?"
3. Point to the problem. Show the error next to the field that caused it, not in a banner at the top of the page.
4. Offer a path forward. Every error message should suggest a fix or offer an alternative.
5. Time it right. Validate on blur (when the user leaves the field) for format errors; validate on submit for cross-field errors.
Error State Taxonomy
| Error Type | Cause | Detection Timing | Display Strategy |
|---|---|---|---|
| Format error | Wrong input pattern (email, phone) | On blur or real-time | Inline message below field |
| Missing required | Required field left empty | On submit | Highlight field, inline message |
| Range error | Value outside allowed range | Real-time or on blur | Inline message with valid range |
| Conflict error | Input conflicts with existing data | On submit (requires server check) | Inline with suggestion |
| System error | Server failure, network issue | On submit | Banner or modal with retry option |
| Permission error | User lacks authorization | On trigger | Disable trigger or show explanation |
| Timeout error | Operation took too long | After threshold | Message with retry; preserve input |
Error Recovery Patterns
| Pattern | How It Works | Example |
|---|---|---|
| Inline correction | User fixes error in place | Red-bordered field; user retypes; border turns green |
| Undo | Reverse the action that caused the error | "Undo" link in error toast message |
| Retry | Attempt the same action again | "Retry" button after network timeout |
| Suggestion | System proposes a valid alternative | "Did you mean [email protected]?" |
| Fallback | System provides an alternative path | "Upload failed. Try a smaller file or paste a URL instead." |
| Graceful degradation | System completes partial operation | "3 of 5 files uploaded. Retry remaining?" |
Edge Cases
Edge cases are the boundary conditions where microinteractions often break. Designing for edge cases means asking "What happens when...?" for every unusual situation.
Essential Edge Cases to Design For
| Edge Case | Question | Design Response |
|---|---|---|
| Empty state | What if there is no data? | Show helpful empty state with CTA |
| Zero value | What if the count is zero? | "No notifications" not "Notifications (0)" |
| Maximum value | What if the limit is reached? | Disable further input; show "Maximum reached" |
| Rapid repeated trigger | What if user clicks 10 times fast? | Debounce; disable trigger during processing |
| Interruption | What if user navigates away mid-action? | Save progress or warn before leaving |
| Slow connection | What if the request takes 30 seconds? | Show progress; allow cancel |
| No connection | What if the user is offline? | Queue action; show "Will send when online" |
| Concurrent edit | What if two users edit the same thing? | Detect conflict; show merge options |
| Very long input | What if the user enters 10,000 characters? | Truncate display; show full on expand |
| Special characters | What if input contains emoji, HTML, or Unicode? | Sanitize and display correctly |
| Screen reader | What if the user cannot see the visual feedback? | Announce state changes via aria-live regions |
| Keyboard only | What if the user cannot use a mouse? | Ensure all triggers are focusable and operable via keyboard |
Edge Case Testing Methodology
- Boundary values: Test at 0, 1, max-1, max, and max+1 for any numeric input.
- Empty/full: Test with no data and with maximum data.
- Speed: Test with instant response, 3-second delay, and 30-second delay.
- Interruption: Test what happens when the user closes the browser, loses connection, or switches apps mid-action.
- Repetition: Test triggering the same action 10 times rapidly.
- Platform variety: Test on the slowest supported device and smallest supported screen.
What NOT to Allow
Deciding what NOT to allow is as important as deciding what to allow. Good rules prevent harmful, confusing, or destructive actions.
Actions to Prevent
| Action to Prevent | Why | How to Prevent |
|---|---|---|
| Double submission | Duplicates orders, messages, payments | Disable trigger on first click; debounce |
| Deleting without confirmation | Irreversible data loss | Confirmation dialog for destructive actions |
| Submitting invalid data | Creates bad records, user confusion | Client-side validation before submission |
| Exceeding rate limits | Overloads system, degrades experience | Throttle triggers; show "Try again in X seconds" |
| Conflicting selections | Logical impossibility (depart after arrive) | Disable impossible options based on other selections |
| Accidental mode entry | User does not realize they changed context | Require deliberate action (not hover) to enter modes |
The "Nothing Should Happen" Cases
Some trigger activations should produce no result -- and that is a deliberate rule:
| Situation | Rule | Feedback |
|---|---|---|
| Clicking a disabled button | No action | Show tooltip explaining why it is disabled |
| Submitting an empty required field | No submission | Highlight field; show "Required" |
| Dragging a non-draggable item | No movement | No cursor change; no visual response |
| Pressing a key outside valid range | No input | No character appears; optionally shake field |
| Tapping outside a modal | Close modal (if non-critical) or no action (if critical) | Modal dismisses or overlay flashes briefly |
State Design Checklist
- Have you defined every possible state (idle, active, success, error, disabled, partial)?
- Can users always tell which state the interaction is in?
- Have you mapped every state transition?
- Have you defined what is NOT allowed?
- Do constraints prevent errors instead of punishing them?
- Are error messages human-readable, specific, and actionable?
- Is user input preserved on error?
- Have you tested all edge cases (empty, max, rapid, offline, interrupted)?
- Is state persistence appropriate (ephemeral vs. session vs. permanent)?
- Can screen reader users perceive state changes?
| 1 | # Rules and State in Microinteractions |
| 2 | |
| 3 | Rules are the invisible engine of a microinteraction. Once a trigger fires, rules determine what happens: what changes, in what order, with what constraints, and when the interaction ends. Users never see rules directly -- they experience their effects through feedback. But when rules are poorly designed, users feel it immediately: the toggle that does not remember its position, the slider that jumps to unexpected values, the form that erases their input on error. |
| 4 | |
| 5 | ## What Rules Define |
| 6 | |
| 7 | Every microinteraction's rules answer these questions: |
| 8 | |
| 9 | | Question | What It Determines | Example | |
| 10 | |----------|-------------------|---------| |
| 11 | | What happens first? | The initial response to the trigger | Button text changes to "Saving..." | |
| 12 | | What sequence follows? | Steps that occur in order | Validate input, send request, show result | |
| 13 | | What can the user do during? | Available actions while processing | Cancel button appears during upload | |
| 14 | | What can the user NOT do? | Constraints that prevent errors | Cannot submit form with empty required fields | |
| 15 | | What are the boundaries? | Minimum, maximum, and default values | Character limit: 280; volume: 0-100%; quantity: 1-99 | |
| 16 | | When does it end? | Completion condition | Request returns success; timer reaches zero | |
| 17 | | What if it fails? | Error handling behavior | Show error message, preserve input, suggest fix | |
| 18 | |
| 19 | |
| 20 | |
| 21 | ## Defining Rules: The Goal-First Method |
| 22 | |
| 23 | Start with the goal, not the interface. What is the user trying to accomplish? Derive every rule from that goal. |
| 24 | |
| 25 | ### Process |
| 26 | |
| 27 | **State the goal in one sentence:** "The user wants to set their alarm time." |
| 28 | **Identify the minimum inputs:** Time (hour, minute), AM/PM, days of week. |
| 29 | **Define the simplest path:** Tap time, scroll to desired hour/minute, toggle AM/PM, select days, confirm. |
| 30 | **Add constraints:** Cannot set alarm in the past (today). Maximum 20 alarms. Minimum interval between alarms: 1 minute. |
| 31 | **Handle failures:** If alarm cannot be set (permission denied), show error with action to fix it. |
| 32 | **Define the end state:** Alarm is set, confirmation shown, alarm appears in list. |
| 33 | |
| 34 | ### Rule Complexity vs. Frequency |
| 35 | |
| 36 | | Usage Frequency | Rule Complexity | Rationale | Example | |
| 37 | |-----------------|-----------------|-----------|---------| |
| 38 | | **Many times per day** | Minimal rules, zero configuration | Must be instant and frictionless | Liking a post: one tap, done | |
| 39 | | **Once per day** | Simple rules, smart defaults | Allow some configuration | Setting an alarm: time + days | |
| 40 | | **Once per week** | Moderate rules, options available | Users can invest time | Scheduling a meeting: time, attendees, recurrence | |
| 41 | | **Once ever** | Full rule set, onboarding acceptable | First-time setup | Account creation: email, password, preferences | |
| 42 | |
| 43 | |
| 44 | |
| 45 | ## State Management Within Microinteractions |
| 46 | |
| 47 | Every microinteraction has state -- the current condition of the interaction at any given moment. Managing state well means users always know where they are, what happened, and what they can do next. |
| 48 | |
| 49 | ### Core States of a Microinteraction |
| 50 | |
| 51 | | State | Description | Visual Indicator | User Can... | |
| 52 | |-------|-------------|------------------|-------------| |
| 53 | | **Idle** | Ready and waiting for trigger | Default appearance | Initiate the interaction | |
| 54 | | **Active/In Progress** | Processing or awaiting input | Loading spinner, active color | Cancel, wait, or provide input | |
| 55 | | **Success** | Completed successfully | Green checkmark, confirmation text | Move on, undo (if available) | |
| 56 | | **Error** | Failed to complete | Red indicator, error message | Retry, correct input, dismiss | |
| 57 | | **Partial** | Partially complete or partially loaded | Partial progress, skeleton | Continue, wait for more | |
| 58 | | **Disabled** | Cannot be initiated | Grayed out, reduced opacity | Nothing (show reason on hover/focus) | |
| 59 | |
| 60 | ### State Transition Map |
| 61 | |
| 62 | Map every possible transition between states to ensure no combination is overlooked: |
| 63 | |
| 64 | |
| 65 | ┌─────────┐ |
| 66 | trigger │ IDLE │ reset |
| 67 | ┌─────────→│ │←──────────┐ |
| 68 | │ └────┬────┘ │ |
| 69 | │ │ trigger │ |
| 70 | │ ▼ │ |
| 71 | │ ┌──────────┐ │ |
| 72 | │ │ ACTIVE │───────────┤ |
| 73 | │ │ │ cancel │ |
| 74 | │ └────┬─────┘ │ |
| 75 | │ ┌──┴──┐ │ |
| 76 | │ │ │ │ |
| 77 | │ success fail │ |
| 78 | │ │ │ │ |
| 79 | │ ▼ ▼ │ |
| 80 | │ ┌────────┐ ┌───────┐ │ |
| 81 | │ │SUCCESS │ │ ERROR │ │ |
| 82 | │ │ │ │ │──retry─┘ |
| 83 | │ └───┬────┘ └───────┘ |
| 84 | │ │ timeout/dismiss |
| 85 | └─────────┘ |
| 86 | |
| 87 | |
| 88 | ### State Persistence |
| 89 | |
| 90 | | Persistence Type | When to Use | Storage Method | Example | |
| 91 | |-----------------|-------------|----------------|---------| |
| 92 | | **Ephemeral** | Within a single session | Component state (React state, SwiftUI @State) | Hover state, dropdown open/closed | |
| 93 | | **Session** | Across page navigations, lost on close | Session storage, navigation state | Form progress, scroll position | |
| 94 | | **Persistent** | Across sessions, survives app close | Local storage, database, user preferences | Theme setting, notification preferences | |
| 95 | | **Synced** | Across devices | Cloud database, account-linked storage | Read/unread status, bookmarks | |
| 96 | |
| 97 | |
| 98 | |
| 99 | ## Constraints and Limitations |
| 100 | |
| 101 | Constraints are rules that prevent errors by limiting what users can do. Well-designed constraints feel natural -- users do not notice them because the wrong action was never possible. |
| 102 | |
| 103 | ### Types of Constraints in Microinteractions |
| 104 | |
| 105 | | Constraint Type | Mechanism | Example | |
| 106 | |----------------|-----------|---------| |
| 107 | | **Range** | Limit input to min/max values | Volume slider: 0-100%, cannot exceed | |
| 108 | | **Format** | Enforce specific input patterns | Phone field: auto-formats as (555) 123-4567 | |
| 109 | | **Type** | Restrict input to valid characters | Numeric field: keyboard shows numbers only | |
| 110 | | **Sequence** | Enforce step order | Payment flow: shipping before payment before confirm | |
| 111 | | **Dependency** | One option enables/disables others | "Ship to different address" checkbox reveals address form | |
| 112 | | **Capacity** | Limit quantity or selection count | File upload: maximum 5 files, 10MB each | |
| 113 | | **Temporal** | Restrict timing of actions | "Undo send": available for 30 seconds only | |
| 114 | |
| 115 | ### Implementing Constraints Gracefully |
| 116 | |
| 117 | **Prevent rather than punish.** The best constraint is one users never encounter because the wrong action was impossible: |
| 118 | |
| 119 | | Punishing (bad) | Preventing (good) | |
| 120 | |----------------|-------------------| |
| 121 | | "Invalid date format" error after typing | Date picker control that only allows valid dates | |
| 122 | | "That username is taken" after submitting form | Real-time availability check as user types | |
| 123 | | "File too large" error after waiting for upload | Show size limit upfront; disable upload for oversized files | |
| 124 | | "Cannot select past dates" error message | Gray out and disable past dates in calendar | |
| 125 | |
| 126 | ### Communicating Constraints |
| 127 | |
| 128 | | Method | When to Use | Example | |
| 129 | |--------|-------------|---------| |
| 130 | | **Disabled state** | Action not available yet | Submit button grayed until form is valid | |
| 131 | | **Counter** | Approaching a limit | "23/280 characters" or "3 of 5 files uploaded" | |
| 132 | | **Visual boundary** | Range limits | Slider track shows min/max; cursor stops at edges | |
| 133 | | **Inline hint** | Format requirements | "Must be 8+ characters with one number" below password field | |
| 134 | | **Progressive disclosure** | Complex constraints | Advanced options hidden behind "Show more" | |
| 135 | |
| 136 | |
| 137 | |
| 138 | ## Error States |
| 139 | |
| 140 | Error states are what happens when rules are violated or when the system fails. Error handling is where most microinteractions fall apart -- and where thoughtful design has the most impact on user trust. |
| 141 | |
| 142 | ### Error State Principles |
| 143 | |
| 144 | **1. Preserve the user's work.** Never erase input on error. If a form fails validation, keep everything the user typed. |
| 145 | |
| 146 | **2. Explain in human language.** Not "Error 422: Unprocessable Entity" but "That email address looks incomplete. Did you forget the domain (e.g., @gmail.com)?" |
| 147 | |
| 148 | **3. Point to the problem.** Show the error next to the field that caused it, not in a banner at the top of the page. |
| 149 | |
| 150 | **4. Offer a path forward.** Every error message should suggest a fix or offer an alternative. |
| 151 | |
| 152 | **5. Time it right.** Validate on blur (when the user leaves the field) for format errors; validate on submit for cross-field errors. |
| 153 | |
| 154 | ### Error State Taxonomy |
| 155 | |
| 156 | | Error Type | Cause | Detection Timing | Display Strategy | |
| 157 | |-----------|-------|-------------------|------------------| |
| 158 | | **Format error** | Wrong input pattern (email, phone) | On blur or real-time | Inline message below field | |
| 159 | | **Missing required** | Required field left empty | On submit | Highlight field, inline message | |
| 160 | | **Range error** | Value outside allowed range | Real-time or on blur | Inline message with valid range | |
| 161 | | **Conflict error** | Input conflicts with existing data | On submit (requires server check) | Inline with suggestion | |
| 162 | | **System error** | Server failure, network issue | On submit | Banner or modal with retry option | |
| 163 | | **Permission error** | User lacks authorization | On trigger | Disable trigger or show explanation | |
| 164 | | **Timeout error** | Operation took too long | After threshold | Message with retry; preserve input | |
| 165 | |
| 166 | ### Error Recovery Patterns |
| 167 | |
| 168 | | Pattern | How It Works | Example | |
| 169 | |---------|-------------|---------| |
| 170 | | **Inline correction** | User fixes error in place | Red-bordered field; user retypes; border turns green | |
| 171 | | **Undo** | Reverse the action that caused the error | "Undo" link in error toast message | |
| 172 | | **Retry** | Attempt the same action again | "Retry" button after network timeout | |
| 173 | | **Suggestion** | System proposes a valid alternative | "Did you mean [email protected]?" | |
| 174 | | **Fallback** | System provides an alternative path | "Upload failed. Try a smaller file or paste a URL instead." | |
| 175 | | **Graceful degradation** | System completes partial operation | "3 of 5 files uploaded. Retry remaining?" | |
| 176 | |
| 177 | |
| 178 | |
| 179 | ## Edge Cases |
| 180 | |
| 181 | Edge cases are the boundary conditions where microinteractions often break. Designing for edge cases means asking "What happens when...?" for every unusual situation. |
| 182 | |
| 183 | ### Essential Edge Cases to Design For |
| 184 | |
| 185 | | Edge Case | Question | Design Response | |
| 186 | |-----------|----------|-----------------| |
| 187 | | **Empty state** | What if there is no data? | Show helpful empty state with CTA | |
| 188 | | **Zero value** | What if the count is zero? | "No notifications" not "Notifications (0)" | |
| 189 | | **Maximum value** | What if the limit is reached? | Disable further input; show "Maximum reached" | |
| 190 | | **Rapid repeated trigger** | What if user clicks 10 times fast? | Debounce; disable trigger during processing | |
| 191 | | **Interruption** | What if user navigates away mid-action? | Save progress or warn before leaving | |
| 192 | | **Slow connection** | What if the request takes 30 seconds? | Show progress; allow cancel | |
| 193 | | **No connection** | What if the user is offline? | Queue action; show "Will send when online" | |
| 194 | | **Concurrent edit** | What if two users edit the same thing? | Detect conflict; show merge options | |
| 195 | | **Very long input** | What if the user enters 10,000 characters? | Truncate display; show full on expand | |
| 196 | | **Special characters** | What if input contains emoji, HTML, or Unicode? | Sanitize and display correctly | |
| 197 | | **Screen reader** | What if the user cannot see the visual feedback? | Announce state changes via aria-live regions | |
| 198 | | **Keyboard only** | What if the user cannot use a mouse? | Ensure all triggers are focusable and operable via keyboard | |
| 199 | |
| 200 | ### Edge Case Testing Methodology |
| 201 | |
| 202 | **Boundary values:** Test at 0, 1, max-1, max, and max+1 for any numeric input. |
| 203 | **Empty/full:** Test with no data and with maximum data. |
| 204 | **Speed:** Test with instant response, 3-second delay, and 30-second delay. |
| 205 | **Interruption:** Test what happens when the user closes the browser, loses connection, or switches apps mid-action. |
| 206 | **Repetition:** Test triggering the same action 10 times rapidly. |
| 207 | **Platform variety:** Test on the slowest supported device and smallest supported screen. |
| 208 | |
| 209 | |
| 210 | |
| 211 | ## What NOT to Allow |
| 212 | |
| 213 | Deciding what NOT to allow is as important as deciding what to allow. Good rules prevent harmful, confusing, or destructive actions. |
| 214 | |
| 215 | ### Actions to Prevent |
| 216 | |
| 217 | | Action to Prevent | Why | How to Prevent | |
| 218 | |-------------------|-----|----------------| |
| 219 | | **Double submission** | Duplicates orders, messages, payments | Disable trigger on first click; debounce | |
| 220 | | **Deleting without confirmation** | Irreversible data loss | Confirmation dialog for destructive actions | |
| 221 | | **Submitting invalid data** | Creates bad records, user confusion | Client-side validation before submission | |
| 222 | | **Exceeding rate limits** | Overloads system, degrades experience | Throttle triggers; show "Try again in X seconds" | |
| 223 | | **Conflicting selections** | Logical impossibility (depart after arrive) | Disable impossible options based on other selections | |
| 224 | | **Accidental mode entry** | User does not realize they changed context | Require deliberate action (not hover) to enter modes | |
| 225 | |
| 226 | ### The "Nothing Should Happen" Cases |
| 227 | |
| 228 | Some trigger activations should produce no result -- and that is a deliberate rule: |
| 229 | |
| 230 | | Situation | Rule | Feedback | |
| 231 | |-----------|------|----------| |
| 232 | | Clicking a disabled button | No action | Show tooltip explaining why it is disabled | |
| 233 | | Submitting an empty required field | No submission | Highlight field; show "Required" | |
| 234 | | Dragging a non-draggable item | No movement | No cursor change; no visual response | |
| 235 | | Pressing a key outside valid range | No input | No character appears; optionally shake field | |
| 236 | | Tapping outside a modal | Close modal (if non-critical) or no action (if critical) | Modal dismisses or overlay flashes briefly | |
| 237 | |
| 238 | |
| 239 | |
| 240 | ## State Design Checklist |
| 241 | |
| 242 | [ ] Have you defined every possible state (idle, active, success, error, disabled, partial)? |
| 243 | [ ] Can users always tell which state the interaction is in? |
| 244 | [ ] Have you mapped every state transition? |
| 245 | [ ] Have you defined what is NOT allowed? |
| 246 | [ ] Do constraints prevent errors instead of punishing them? |
| 247 | [ ] Are error messages human-readable, specific, and actionable? |
| 248 | [ ] Is user input preserved on error? |
| 249 | [ ] Have you tested all edge cases (empty, max, rapid, offline, interrupted)? |
| 250 | [ ] Is state persistence appropriate (ephemeral vs. session vs. permanent)? |
| 251 | [ ] Can screen reader users perceive state changes? |
| 252 |
Discussion
Alternatives
Browse more free Claude skills or everything in Design.