Components

One design system, drawn natively everywhere

Every OpenVibe component is described by what it is: its parts, the tokens they wear, its states, and how it reads to a screen reader. The web draws it with the kit; an Android or iOS app draws the same component with its own views, so an app is never a web page in a frame.

Notice

A line in the page that tells the person what happened: ok, info, warn, or an error (announced at once).

Notices

Saved. Every OpenVibe site follows.

Parts and their tokens

  • iconsizesize.icon
  • textcolorcolor.text.primary

How it behaves

Role
status, or alert for errors
Props
kind text* * required
States
default
Name
its text
Keys
none; errors are announced
Phone
full width
Computer
in its column
kind
ok color.status.ok.text
info color.status.info.text
warn color.status.warn.text
error color.status.bad.text, role alert

Code

Jetpack Compose, on the theme file from Tokens (Android): Material 3 roles for colour, OvScale for sizes.

// OpenVibe kit for Jetpack Compose: add the theme file from openvibe.design/tokens (Android) and wrap the app in
// MaterialTheme(colorScheme = if (isSystemInDarkTheme()) VibeDarkColorScheme else VibeLightColorScheme) { … }
enum class OvKind { Primary, Quiet, Danger }
enum class OvNoticeKind { Ok, Info, Warn, Error }

@Composable
fun OvNotice(text: String, kind: OvNoticeKind = OvNoticeKind.Info) {
    val c = MaterialTheme.colorScheme
    val tint = when (kind) { OvNoticeKind.Error -> c.error; OvNoticeKind.Ok -> c.primary; else -> c.tertiary }
    Row(Modifier.fillMaxWidth().semantics { liveRegion = if (kind == OvNoticeKind.Error) LiveRegionMode.Assertive else LiveRegionMode.Polite }
        .background(tint.copy(alpha = .12f), RoundedCornerShape(OvScale.RadiusSm)).padding(OvScale.SpaceMd), horizontalArrangement = Arrangement.spacedBy(OvScale.SpaceSm)) {
        Icon(if (kind == OvNoticeKind.Error) Icons.Default.Error else Icons.Default.Info, null, tint = tint)
        Text(text, color = c.onSurface)
    }
}

Shared interfaces

Web, Android and iOS definitions for the navigation, composer, sheets, settings and motion used across OpenVibe. See the whole registry, or read it as JSON at /api/v1/components.

Kit documents: screens as data

A screen can be sent as a tree of these components, for example { "type": "rail", "children": [{ "type": "card", … }] }. Every OpenVibe client renders the same document with its own views, so a screen can change without an app release (the server-driven UI pattern of Airbnb and DivKit). Documents are checked strictly: known components and props only, typed values, which children each takes, a size limit, and https or same-site links.

The specs as JSON The tokens they wear