Feed

Molecule
Vertical activity streams with icons and timestamps. Used for audit logs, change history, and notification lists.

Playground

Every control sets a real prop of FeedProps. The JSX below updates as you go.
  • Rachel Chen approved the request
    2 hours ago
  • Ada Lovelace merged release/4.2
    5 hours ago
  • System created the project
    3 days ago
Props
Lead
pick one
compact
boolean
JSX · FeedProps
<Feed activity />

Variants

4 examples from src/molecules/feeds/feeds.md, each rendered live from its own JSX.
  • 2m
    Scout completed discovery
  • 18m
    Ranger restored the deployment
Activity
<Feed activity label="Recent activity" items={[{ time: "2m", action: "Scout completed discovery" }, { time: "18m", action: "Ranger restored the deployment" }]} />
  • 00:00
    Context Loaded the work item
  • 01:05
    Eval Checks passed
Trace
<Feed trace label="Latest trace" items={[{ time: "00:00", kind: "Context", action: "Loaded the work item" }, { time: "01:05", kind: "Eval", action: "Checks passed" }]} />
  • System rotated the signing key
    12 minutes ago
  • Rachel Chen invited a teammate
    2 hours ago
  • Ada Lovelace merged a release
    1 day ago
Icon lead
An item may name a kit glyph ({ icon }) for the connector node, which suits an audit or automation stream where a glyph reads the kind of event faster than a dot. Node content resolves in one order: the glyph on its disc, then a dot, the first event's in the accent. The avatar lead ignores icon and keeps leading with the person's 28px avatar on the same connector.
<Feed
items={[
{ icon: "shieldCheck", actor: "System", action: "rotated the signing key", time: "12 minutes ago" },
{ icon: "userPlus", actor: "Rachel Chen", action: "invited a teammate", time: "2 hours ago" },
{ icon: "gitMerge", actor: "Ada Lovelace", action: "merged a release", time: "1 day ago" }
]}
/>
  • RC
    Rachel Chen commented on the pull request
    2 hours ago
  • AL
    Ada Lovelace pushed 3 commits
    5 hours ago
  • KT
    Kevin Turner opened the pull request
    1 day ago
Avatar
<Feed
avatar
items={[
{ actor: "Rachel Chen", action: "commented on the pull request", time: "2 hours ago" },
{ actor: "Ada Lovelace", action: "pushed 3 commits", time: "5 hours ago" },
{ actor: "Kevin Turner", action: "opened the pull request", time: "1 day ago" }
]}
/>

Anatomy

  • Rachel Chen approved the request
    2 hours ago
  • Ada Lovelace merged release/4.2
    5 hours ago
  • System created the project
    3 days ago
1
Feed
2
Lead
3
Connector
4
Event
5
Timestamp
Dimmed parts appear only in some states or variants.

Props

11 props on FeedProps, grouped as they are declared in source. Required props are marked *.
Prop
Type
Default
Description
Props
1 prop
items
FeedItem[]
–
Events to render, top to bottom.
Lead axis
pick one
4 props
activity
boolean
false
trace
boolean
false
connector
boolean
false
avatar
boolean
false
Density modifier
6 props
compact
boolean
false
onItemPress
(index: number) => void
–
When set, each event row is pressable, reporting the row index.
label
string
–
The feed's accessible name (e.g. "Recent activity"): a screen reader announces it with the list of events. A virtualized feed needs one: on the web its scroller is a keyboard stop while the events overflow, and Chromium names an unnamed stop from the text of every event it has rendered.
virtualized
boolean
false
Render the rows through a windowed FlatList instead of mounting every row up front, for large lists. Give the list a bounded height (via style, e.g. { maxHeight: 400 }) so it can scroll; without one it warns and renders eagerly anyway. Default (omitted) mounts all rows, unchanged. On the web, while the rows overflow, the windowed list is a keyboard tab stop the keyboard can scroll, and the feed's card draws the focus ring while it has keyboard focus.
testID
string
–
E2E hook forwarded to the root element.
style
LayoutStyle
–
Composition within a parent only, never a restyle hook and never a width: the parent layout container provides the bounds.

Accessibility and keyboard

Keyboard
Not focusable. It has no interaction of its own and takes the semantics of what it wraps.
Semantics
Roles
button
From the docs
The events are a list, as in Tailwind UI, and each event is one of its items: a screen reader announces the list with its number of events and moves through it event by event. A pressable event is a button inside its item. The label prop names the list (for example "Recent activity").
A virtualized feed with a bounded height scrolls its events in a list of its own. On the web, while those events overflow, that list is a keyboard tab stop (before the rows themselves when onItemPress makes them buttons), the keyboard can scroll it, and while it has keyboard focus the feed's card draws the theme's focus ring. Only the events near its viewport are mounted, and each says where it sits in the whole feed, so a screen reader still counts every event. Give a windowed feed a label: focused, a list w

Platform skins

The playground's props on each platform: same tree, native shapes, type and touch sizes.
  • 00:00
    Context Loaded the work item
  • 01:05
    Eval Checks passed
Web
control 10 · field 10 · card 16 · Instrument Sans
  • 00:00
    Context Loaded the work item
  • 01:05
    Eval Checks passed
iOS
capsule controls · field 8 · card 12 · SF Pro · 44 pt
  • 00:00
    Context Loaded the work item
  • 01:05
    Eval Checks passed
Android
Material 3 stadium · field 4 · card 12 · Roboto · 48 dp

Usage

<Feed
items={[
{ actor: "Rachel Chen", action: "approved the request", time: "2 hours ago" },
{ actor: "Ada Lovelace", action: "merged", target: "release/4.2", time: "5 hours ago" },
{ actor: "System", action: "created the project", time: "3 days ago" }
]}
/>
The events are a list, as in Tailwind UI, and each event is one of its items: a screen reader announces the list with its number of events and moves through it event by event. A pressable event is a button inside its item. The label prop names the list (for example "Recent activity").
A virtualized feed with a bounded height scrolls its events in a list of its own. On the web, while those events overflow, that list is a keyboard tab stop (before the rows themselves when onItemPress makes them buttons), the keyboard can scroll it, and while it has keyboard focus the feed's card draws the theme's focus ring. Only the events near its viewport are mounted, and each says where it sits in the whole feed, so a screen reader still counts every event. Give a windowed feed a label: focused, a list with no name is named in Chromium from the text of every event it has rendered, so the kit warns in development when it has none.
activity provides the original Argus time gutter, sentence, and dividing rule. trace provides a colored marker, optional halo, optional numeric time gutter, and inline category label. These unframed rows inherit their owning panel. Pass rich content, marker color and halo, and optional kind on each item.

Tokens

Read from the playground render. Values follow the scheme and the ion hue.
--cyan
--fd
--fm
--ft
--ion
--ln2
--ok
--tx
--tx2
--tx3
--warn

Related components