Skip to content

Question patterns

The vocabulary used in the Type column throughout the questionnaire, plus the notation for conditional logic. Stick to this list — a new answer type means new handling in whatever tool eventually captures responses.

Answer types

Type Captures Use when Maps to
Short text One line, free form Names, places, short labels <input type="text">
Long text Paragraphs Anything you want the client to explain <textarea>
Number Integer or decimal Counts, durations, reps <input type="number">
Number + unit Value plus its unit Weights and lengths where kg/lb or cm/in both occur Number field + unit selector
Yes/No Binary Screening gates and simple facts Radio pair
Single choice Exactly one of N Mutually exclusive options Radio group or dropdown
Multi-select Zero or more of N Checklists — symptoms, equipment, obstacles Checkbox group
Scale 0–10 Integer 0–10 Pain, stress, confidence Slider or radio row
Scale 1–5 Integer 1–5 Quality and comfort ratings Radio row
Score 0–3 Integer 0–3 Coach-assigned movement screen scores Radio row
Date Calendar date Birth dates, targets, signatures <input type="date">, stored YYYY-MM-DD
Checkbox Single affirmation Consent statements that must be actively ticked <input type="checkbox">
Signature Drawn or typed mark Waiver sign-off Signature widget + timestamp
File upload Document or image Clearance letters, rehab sheets <input type="file">
Repeating group N copies of a sub-form Injury list, surgery list Repeatable fieldset
Matrix One answer per row, from a shared column set Digestive symptoms, food frequency, family history Grid of radio groups
Calculated Derived value BMI, waist-to-hip ratio Never entered by hand

Matrix questions

A matrix asks the same question of many items at once. It is the most efficient type on the form and the easiest to get wrong.

Define it with an explicit row list and column list:

health_family_matrix
  Columns: Diabetes | Heart disease | Stroke | High blood pressure | ...
  Rows:    Mother | Father | Sibling | Maternal grandparent | ...

Rules:

  • Columns must be exhaustive. Every row needs a truthful answer, including "normal" and "doesn't apply". Without them, clients leave rows blank and you cannot distinguish normal from skipped.
  • Rows must be independent. If answering one row changes what another means, they are not matrix rows.
  • Never put an urgent item in a matrix. A row that should trigger a referral gets skimmed past at the same rate as every other row. Pull it out into its own question — see sys_gi_urgent in section 3.5, which exists precisely because the source sheet had blood in stool sitting as row 12 of 19.
  • Cap it at about 20 rows. Past that, accuracy drops as clients start answering by pattern rather than by item. The food frequency grid in section 7.2 exceeds this deliberately and is the exception — it is grouped by food category so the client can move through it in chunks.
  • On mobile, a matrix must reflow into one question per row. A grid that scrolls sideways gets random answers.

Rules

Field IDs are permanent

Every question has a unique snake_case Field ID. Once a single response exists, the ID is frozen — reword the question all you like, but never reuse an ID for a different question and never renumber to tidy up. Prefix each section's IDs consistently (health_*, inj_*, goal_*, …).

Required means blocking

Yes — submission is blocked without it. Reserve this for safety-critical and legally necessary fields; every required field is a point where someone abandons the form. No — optional. Cond. — required only when its trigger fires.

Conditional logic

Written under the table it applies to, in this form:

child_field_id → if parent_field_id = Value
child_field_id → if parent_field_id includes Value
child_field_id → if parent_field_id is not Value

Where several children share one trigger, group them:

parq_1_detail, parq_1_controlled → if parq_1_heart = Yes

Rules:

  • A conditional question is hidden, not disabled, until its trigger fires.
  • Hidden questions never block submission, whatever their Req. says.
  • If a trigger is later unset, clear the child's stored answer — a stale follow-up attached to a retracted Yes is worse than no answer at all.
  • Don't nest more than two levels deep. If you need three, the section wants splitting.

Multi-select conventions

  • Always include an explicit escape option — None of these, Not currently, Prefer not to say. A blank multi-select is ambiguous: it can mean "none apply" or "I skipped this", and for screening questions that difference matters.
  • Escape options are mutually exclusive with every other option: selecting None of these clears the rest.
  • Where a list ends in Other, pair it with a conditional *_other short text field.

Sensitive questions

Questions touching disordered eating, mental health, pregnancy, substance use and body image follow extra rules:

  • Always offer Prefer not to say.
  • Never mark them required.
  • Never chain an interrogating follow-up inside the form — a positive answer is a prompt for a conversation or a referral, not for more questions.
  • Flag them in the page with a !!! danger admonition explaining the handling, as in section 7.7.

Writing the questions

  • One thing per question. "Do you have knee or hip pain?" cannot be answered by someone with only knee pain.
  • Plain language over clinical terms — "pain in your chest", not "angina".
  • Avoid leading wording. "How much do you drink?" beats "You don't drink much, do you?"
  • Give ranges rather than exact numbers where precision isn't real. Nobody knows their weekly step count to three digits.
  • Put the burden on the form, not the client: if you can derive it, calculate it instead of asking.