Master the three pillars of user research — qualitative interviews, quantitative surveys, and behavioral analytics — and learn to synthesize findings into design decisions backed by evidence, not assumptions.
Every failed product has one thing in common: the team substituted their own opinions for user research. They built what they assumed users wanted, not what users actually needed. User research is the discipline that replaces assumption with evidence.
User research sits at the Empathize stage of the design process. Its goal is not to collect data — it is to develop genuine empathy for the humans who will use your product. The real output is understanding: why users behave the way they do, what goals they are trying to achieve, and where existing solutions are failing them.
This lesson covers the three primary research methods: qualitative interviews (understanding the 'why'), surveys (measuring the 'how many'), and analytics (observing the 'what'). Used together, they paint a complete picture of user needs that no single method can provide alone.
User interviews are the most powerful research tool available. A 30-minute conversation with five real users reveals more than six months of guessing. The goal is not to test your solution — it is to understand the user's world before you have a solution.
The TEDW Framework prevents leading questions that confirm existing assumptions:
Questions to avoid:
Interview structure for a 30-minute session:
Aim for 5-8 interviews per user segment. After 5 interviews you will hear the same themes repeating — this saturation signals you have enough data for this research round.
Practical rules: record with permission (frees you to listen, not transcribe); embrace 3-second silences before following up; never validate or reject answers; ask 'Why?' and 'Tell me more' relentlessly; follow surprising tangents — that is where unexpected insight lives.
Surveys answer: how many users experience X? They provide statistical confidence to patterns observed in interviews. A survey cannot explain why users do things, but it validates whether a pattern is widespread or limited to a few outliers.
Likert Scale Questions measure attitudes on a 5 or 7-point scale:
'How easy was it to find the course you were looking for?' (1 = Very difficult, 5 = Very easy)
The System Usability Scale (SUS) is the industry-standard 10-question usability survey. A SUS score above 68 is above average. Below 51 is an immediate usability red flag requiring intervention.
Survey design principles:
Common response biases to design around:
Survey data informs CSS decisions. If 68% of respondents report difficulty distinguishing course difficulty levels, the solution is a visible difficulty badge on course cards:
1/* Difficulty badge — designed from survey data showing users cannot distinguish levels */
2.difficulty-badge {
3 display: inline-flex;
4 align-items: center;
5 padding: 0.25rem 0.625rem;
6 border-radius: 9999px;
7 font-size: 0.6875rem;
8 font-weight: 600;
9 letter-spacing: 0.05em;
10 text-transform: uppercase;
11}
12.difficulty-badge[data-level="beginner"] { background: #dcfce7; color: #166534; }
13.difficulty-badge[data-level="intermediate"] { background: #fef3c7; color: #92400e; }
14.difficulty-badge[data-level="advanced"] { background: #fee2e2; color: #991b1b; }Analytics tell you what users actually do, not what they say they do. People are terrible at self-reporting their own behavior — they remember exceptions as typical and omit embarrassing steps. Analytics are honest because they record every action without interpretation.
Key metrics and their action thresholds:
Bounce rate: percentage who leave after one page. Above 70% indicates a landing page problem — mismatch between what the page promises and what it delivers.
Session duration: time spent per visit. A consistent drop signals an engagement problem — content is not meeting user expectations set by the entry point.
Funnel drop-off: the percentage of users who abandon at each step of a conversion flow. Above 50% drop-off at a single step is a clear friction signal that requires investigation.
Rage clicks: rapid repeated clicks on non-interactive elements. Any rage clicks indicate users expect something to be clickable that is not — a common UX failure when decorative elements look interactive.
Scroll depth: how far down a page users read. Below 50% scroll depth on content pages indicates above-the-fold content is not compelling enough to motivate continued reading.
Forming a research hypothesis from analytics:
The analytics plus interview loop is the core research cycle: analytics show where the problem is; interviews reveal why it exists. Neither method alone is sufficient for confident design decisions.
Implement analytics-informed components with data attributes for event tracking:
1<!-- Analytics identified rage clicks on this bookmark icon (it was a div, not a button) -->
2<!-- Fix: make it a focusable, interactive button element -->
3<button
4 type="button"
5 class="icon-btn"
6 aria-label="Save to reading list"
7 aria-pressed="false"
8 data-track="course-save"
9 data-course-id="react-hooks-deep-dive">
10 <svg aria-hidden="true" focusable="false" width="20" height="20">
11 <use href="#icon-bookmark"></use>
12 </svg>
13</button>1.icon-btn {
2 display: inline-flex;
3 align-items: center;
4 justify-content: center;
5 width: 2rem;
6 height: 2rem;
7 border-radius: 0.5rem;
8 border: none;
9 background: transparent;
10 color: #6b7280;
11 cursor: pointer;
12 transition: background-color 150ms ease, color 150ms ease;
13}
14.icon-btn:hover { background: #f3f4f6; color: #111827; }
15.icon-btn[aria-pressed="true"] { color: #2563eb; }
16.icon-btn:focus-visible { outline: 2px solid #2563eb; outline-offset: 2px; }Raw research data is not actionable. Synthesis converts raw data into design opportunities by finding patterns across multiple data sources and connecting them to specific implementation decisions.
Affinity Mapping process:
Insight statement structure:
'We noticed that [observation from research]. We believe this is because [interpretation]. This creates an opportunity to [specific design action].'
Example from a real synthesis:
'We noticed that 68% of survey respondents said finding the right course took over 10 minutes. Interviews revealed users could not distinguish beginner from intermediate content from the course card alone. This creates an opportunity to add a visible difficulty indicator directly on course cards — positioned on the thumbnail image so it is visible before the user reads any text.'
This connects: quantitative data (68% measurement) + qualitative data (interview explanation) + specific design action (course card badge position).
The CSS implementation that traces back to this specific research synthesis:
1/* Course card — thumbnail-positioned badge is the direct output of research synthesis */
2.course-card { position: relative; border-radius: 0.75rem; overflow: hidden;
3 border: 1px solid #e5e7eb; background: white; }
4.course-card-thumbnail { position: relative; aspect-ratio: 16/9; overflow: hidden; }
5.course-card-thumbnail img { width: 100%; height: 100%; object-fit: cover; }
6
7/* Badge on thumbnail — not in body — because research showed users decide on the thumbnail */
8.course-card .difficulty-badge {
9 position: absolute;
10 top: 0.75rem;
11 left: 0.75rem;
12 z-index: 1;
13}
14.course-card-body { padding: 1rem; }
15.course-card-title { font-size: 1rem; font-weight: 600; margin: 0 0 0.375rem; color: #111827; }
16.course-card-meta { font-size: 0.8125rem; color: #6b7280; }Translating analytics drop-off data and interview findings into an accessible CSS chip-based filter component that solves the discovered usability problem.
1<!-- BEFORE: three generic links flagged by analytics for high drop-off -->
2<!-- Analytics: 60% of users leave course listing without clicking a course -->
3<!-- Interviews: users feel overwhelmed — cannot filter 200 courses by level or topic -->
4<nav>
5 <a href="/courses">All Courses</a>
6 <a href="/courses/new">New</a>
7 <a href="/courses/popular">Popular</a>
8</nav>
9
10<!-- AFTER: research-informed filter component -->
11<!-- Research finding: users need to filter by (1) level, (2) duration, (3) topic -->
12<!-- Design decision: chip toggles (not dropdown) because <= 5 options per category -->
13<style>
14 .filter-bar {
15 display: flex;
16 gap: 0.75rem;
17 flex-wrap: wrap;
18 padding: 1rem 0;
19 border-bottom: 2px solid #f3f4f6;
20 margin-bottom: 2rem;
21 }
22 /* fieldset removes default browser border and padding */
23 .filter-group {
24 display: flex;
25 align-items: center;
26 gap: 0.375rem;
27 border: none;
28 padding: 0;
29 margin: 0;
30 }
31 .filter-group legend {
32 font-size: 0.6875rem;
33 font-weight: 700;
34 text-transform: uppercase;
35 letter-spacing: 0.08em;
36 color: #9ca3af;
37 padding-right: 0.5rem;
38 /* float trick to keep legend inline with buttons */
39 float: left;
40 width: auto;
41 }
42 .filter-chip {
43 padding: 0.375rem 0.875rem;
44 border: 1.5px solid #e5e7eb;
45 border-radius: 9999px;
46 background: white;
47 font-size: 0.875rem;
48 font-family: inherit;
49 color: #374151;
50 cursor: pointer;
51 transition: border-color 120ms ease, background-color 120ms ease, color 120ms ease;
52 line-height: 1.25;
53 }
54 .filter-chip:hover {
55 border-color: #93c5fd;
56 color: #1d4ed8;
57 background: #eff6ff;
58 }
59 /* aria-pressed="true" is the toggled/active state */
60 .filter-chip[aria-pressed="true"] {
61 background: #2563eb;
62 border-color: #2563eb;
63 color: white;
64 font-weight: 600;
65 }
66 .filter-chip:focus-visible {
67 outline: 2px solid #2563eb;
68 outline-offset: 2px;
69 }
70 /* Utility: visually hidden but accessible to screen readers */
71 .sr-only {
72 position: absolute;
73 width: 1px; height: 1px;
74 padding: 0; margin: -1px;
75 overflow: hidden;
76 clip: rect(0, 0, 0, 0);
77 white-space: nowrap;
78 border: 0;
79 }
80</style>
81
82<section aria-labelledby="filter-heading">
83 <h2 id="filter-heading" class="sr-only">Filter courses</h2>
84 <div class="filter-bar">
85 <!-- fieldset groups related filter options semantically -->
86 <fieldset class="filter-group">
87 <legend>Level</legend>
88 <button class="filter-chip" type="button" aria-pressed="false"
89 data-filter="level" data-value="beginner">Beginner</button>
90 <button class="filter-chip" type="button" aria-pressed="false"
91 data-filter="level" data-value="intermediate">Intermediate</button>
92 <button class="filter-chip" type="button" aria-pressed="false"
93 data-filter="level" data-value="advanced">Advanced</button>
94 </fieldset>
95 <fieldset class="filter-group">
96 <legend>Duration</legend>
97 <button class="filter-chip" type="button" aria-pressed="false"
98 data-filter="duration" data-value="short">Under 2h</button>
99 <button class="filter-chip" type="button" aria-pressed="false"
100 data-filter="duration" data-value="medium">2 to 8h</button>
101 <button class="filter-chip" type="button" aria-pressed="false"
102 data-filter="duration" data-value="long">8h or more</button>
103 </fieldset>
104 </div>
105 <!-- aria-live region announces filter state to screen reader users -->
106 <div id="filter-announcement" aria-live="polite" aria-atomic="true" class="sr-only"></div>
107</section>The BEFORE navigation had three generic links — analytics showed 60% of users left the listing page without clicking any course. Five interviews revealed users were overwhelmed by 200 undifferentiated courses and needed to filter by difficulty and duration before they could evaluate options. The AFTER component uses chip toggle buttons (research showed users prefer toggles over dropdowns for 5 or fewer options per category), fieldset and legend for semantic grouping visible to screen readers, aria-pressed for accessible toggle state, and an aria-live region that announces 'Showing 34 beginner courses' when filters are applied.
The next lesson covers Information Architecture — how to organize content so users find it without thinking, using card sorting to discover user mental models and tree testing to validate navigation before writing any code.
Your progress is saved in this browser, on this device only.