Add activities and connections

With lanes in place, the flow needs its steps. An activity is one step, placed in the lane of whoever performs it; connections put the steps in order; a connection crossing lanes is a hand-off.

Step 1 — Add activities

An activity's details form

Add activities into their lanes, left to right in the order things happen. Name them verb-first: "Validate claim", "Issue payment". When a new activity is created, its name field in the right pane is focused with the placeholder pre-selected — just type the real name.

Step 2 — Connect in sequence

Connections carrying the flow across lanes

Drag from an activity's connection handle to the next activity. Release on empty lane space instead, and a new connected activity is created in one motion — the fastest way to lay down a chain of steps.

Step 3 — Label the branches

A labeled branch on a connection

Where the path splits, label each outgoing connection with its outcome — "Approved", "Rejected". An unlabeled branch makes the reader guess.

Show dragging from an activity's connection handle and releasing on empty swimlane space to create a connected activity in one motion, then typing its name in the inline rename. Key moments: handle hover, the drag, the drop on empty space, the pre-selected placeholder text.

Synchronous calls

Not every connection is a hand-off. When a step calls another — the other side does its work, answers, and the caller carries on — drawing flow into that lane and back again tells the wrong story: control never moved. For these, switch the connection's Kind from Flow to Call in its form.

A call draws as one connection with two arrows: a solid request arrow to the callee and a lighter dashed arrow pointing back at the caller. Give the answer a name in the Return label field ("validation result", "audit id") and it appears on the return arrow with a ↩ mark. The caller's next step stays connected to the caller — exactly like the code.

A synchronous call: solid request arrow out, dashed return arrow back

Use Flow when responsibility moves to the target ("then the handler takes over"). Use Call when the source just needs an answer before continuing ("look this up, then proceed"). Boundary-event exit paths are always flows — an interruption can't wait for an answer.

Connection form extras

Open a connection's form to configure:

  • Kind — toggle between Flow (a hand-off to the next lane) and Call (a synchronous request-response to another lane). Calls draw as solid request + dashed return arrows.
  • Label — text shown on the edge (e.g. [payment-result], "Approved", "Rejected"). Branch outcomes especially benefit from labels.
  • Return label (calls only) — the label on the return arrow back to the caller (e.g. "validation result", "audit id" with a ↩ symbol).
  • Dashed line — check to draw the connection as a dashed line instead of solid. Useful for optional, conditional, or asynchronous flows. (Boundary event paths and call returns are always dashed; this option is disabled for them.)
  • Label position — drag the slider to move the label along the edge (left to right, or top to bottom depending on edge direction). Helps untangle overlapping labels.
  • From / To pickers — change the source or target activity without deleting and recreating the connection. The connection ID and metadata stay the same, so you preserve history and notes.

Some activities belong together conceptually — a series of validation steps, all the cleanup on error, a phased rollout. Wrap them in a Group: click the Group toolbar button to create one, then tick its member activities (and lanes) in the group's form on the right. A labeled overlay appears around the members, visually bundling the steps. Groups survive when you zoom and collapse the flow — the grouping persists even when the view changes altitude. Name a group for what it does ("Validation", "Error recovery", "Setup").

Configuring a group

Open a group's form to adjust:

  • Label — the text shown on the overlay border.
  • Display type — style it using a C4 element or display type (optional; inherits from C4 if bound).
  • Fill opacity — drag the slider (0–100%) to control how dark the background is. Lower opacity keeps activities visible; higher opacity emphasizes the boundary.
  • Member lanes and Member activities — checkboxes to add or remove elements from the group. A group can span multiple lanes or capture just a few steps in one lane.
  • Parent group — nest this group inside another group, creating visual hierarchy (e.g., a "Validation" group containing a "Format check" subgroup).

Groups are purely visual — they don't affect flow logic or connectivity, just how the diagram is read.

Order outgoing connections

When an activity sends to several next steps — the happy path, multiple error handlers, or parallel flows — you control the order they fan out. Select an activity and open its form. The Outgoing connections section lists all connections starting from that activity. Use the up/down controls to reorder them. When there are multiple connections of the same kind (all flows, or all calls), they fan out uniformly: flows spread vertically on the right edge of the activity (top to bottom in order), calls spread horizontally on the bottom edge (left to right in order). The first outgoing connection uses the default handle; additional ones get their own fanned positions so no two edges overlap.

Interruptions: boundary events

Something that can interrupt an activity while it runs — a timeout, an error, a cancellation — is a boundary event: a marker on the activity's edge with its own outgoing path. Use them for the "what if it doesn't go well" routes instead of weaving error paths through the happy path.

Event types

Five event types handle different interruption patterns:

TypeSymbolUse this whenSuggested tag
TimerTa timeout fires, a scheduled task triggers#timeout
ErrorEan exception is caught#error
CompensationCan earlier step needs undoing#compensation
SignalSan external alert arrives#unhappy
MessageManother lane sends a message in#unhappy

Events are created without tags — the suggested tag is a convention you apply yourself in the event's form when you want its path gated by visibility.

Adding a boundary event

Select an activity, open its form, and scroll down to Boundary events. Click the +T, +E, +C, +S, or +M button to attach an event of that type. Every boundary event gets a Title (optional; shows as a label on the marker), a Type (the five above), a Description, and Tags (to control visibility).

The event's tags determine when its exit path appears in the viewer. When you tag an event #timeout, that path only shows when the reader has the #timeout tag active in the Visibility panel.

Activating a marker in the viewer

In the viewer, hover over a boundary event marker (the small circle on the activity's edge) to see the event's title. Click the marker to toggle that event active, which shows its exit path. The Visibility panel in the toolbar carries the same event toggles — either control affects what you see on the canvas.

Activity data annotations

An activity can carry data annotations — short names of data elements (order ID, response code, session token) that flow in or out at that step. Open an activity's form and scroll to Data annotations to add them. Each annotation is a label (e.g. [order-id], [response]); display them to show what data moves between steps without cluttering the diagram.

Spotlight with tags

Give activities and lanes tags ("happy-path", "error-handling") in their forms. In the viewer, the Visibility panel lets readers spotlight chosen tags — ghosting the rest (dimmed) or hiding it. One flow, several readings.

The viewer's Visibility panel: tags with Ghost/Hide modes

Keep it disciplined

Swimlanes invite drawing every micro-step. Resist: model the steps that matter to the reader at this level, not every internal call. Detail that matters to fewer people belongs in a separate flow, linked from here (diagram links).

Where next