Skip to main content
161

Search Lumen

Find components, APIs, guides, and recipes.

GitHub
React Native docs
React Native

Hooks built for native React

Keep application state reusable across React targets, then connect it to controllers adapted for native components, events, and accessibility semantics.

Public hooks
8
DOM runtime
None
State mode
Controlled or local

What React and React Native share

React Native supports React’s built-in hooks and application-defined hooks. Share data, validation, domain state, and mutations in a platform-neutral workspace package. Render that state with @santi020k/lumen-react on the web and@santi020k/lumen-react-native in the native app.

Do not import the web hook implementation into React Native. Web controllers can depend on DOM focus, ARIA attributes, browser storage, CSS, and keyboard events. Hooks with portable state semantics have native adaptations from the React Native package instead.

tsx
// packages/product-state/src/use-projects.ts
import { useCallback, useState } from 'react'

export function useProjects() {
  const [selectedId, setSelectedId] = useState<string | null>(null)
  const selectProject = useCallback((id: string) => setSelectedId(id), [])

  return { selectProject, selectedId }
}

// Web imports @santi020k/lumen-react for rendering.
// Native imports @santi020k/lumen-react-native for rendering.
// Both apps import useProjects from the shared workspace package.
// packages/product-state/src/use-projects.ts
import { useCallback, useState } from 'react'

export function useProjects() {
  const [selectedId, setSelectedId] = useState<string | null>(null)
  const selectProject = useCallback((id: string) => setSelectedId(id), [])

  return { selectProject, selectedId }
}

// Web imports @santi020k/lumen-react for rendering.
// Native imports @santi020k/lumen-react-native for rendering.
// Both apps import useProjects from the shared workspace package.

Native hook reference

The adapted controllers preserve controlled and uncontrolled state ownership while returning props shaped for native Lumen components.

React Native hooks and their component connections
HookOwnsConnects to
useDisclosure / useDialogControlled or uncontrolled visibilityLumenAlertDialog, LumenSheet
useTabsControlled or uncontrolled selected valueLumenTabs
useSelectNormalized options and selected valueLumenPicker or an app-owned picker
useLanguageToggleLocale cycling without browser side effectsApplication localization provider
useThemeToggleExplicit light and dark selectionLumenProvider
useToastBounded notification queue and dismissal timersLumenToast
useLumenThemeCurrent semantic native themeCustom native composition
useLumenNavigationBarVisibilityScroll-responsive navigation visibilityLumenCollapsibleNavigationBar

Disclosure and dialog state

Spread dialogProps onto an alert dialog or sheet. The controller exposesshow, close, toggle, and setOpen for application events.

tsx
import {
  LumenAlertDialog,
  LumenButton,
  useDialog
} from '@santi020k/lumen-react-native'

export function DeleteProject() {
  const dialog = useDialog()

  return (
    <>
      <LumenButton intent="danger" onPress={dialog.show}>
        Delete project
      </LumenButton>
      <LumenAlertDialog
        {...dialog.dialogProps}
        confirmLabel="Delete"
        destructive
        onConfirm={() => {
          deleteProject()
          dialog.close()
        }}
        title="Delete this project?"
      />
    </>
  )
}
import {
  LumenAlertDialog,
  LumenButton,
  useDialog
} from '@santi020k/lumen-react-native'

export function DeleteProject() {
  const dialog = useDialog()

  return (
    <>
      <LumenButton intent="danger" onPress={dialog.show}>
        Delete project
      </LumenButton>
      <LumenAlertDialog
        {...dialog.dialogProps}
        confirmLabel="Delete"
        destructive
        onConfirm={() => {
          deleteProject()
          dialog.close()
        }}
        title="Delete this project?"
      />
    </>
  )
}

Selection state

useTabs and useSelect keep the value app-controllable. Native components continue to own touch, accessibility, and rendering behavior.

tsx
import {
  LumenTabs,
  useTabs
} from '@santi020k/lumen-react-native'

const options = [
  { label: 'Overview', value: 'overview' },
  { label: 'Activity', value: 'activity' }
]

export function ProjectTabs() {
  const tabs = useTabs({ defaultValue: 'overview' })

  return (
    <LumenTabs
      {...tabs.tabsProps}
      label="Project sections"
      options={options}
    >
      <ProjectPanel value={tabs.value} />
    </LumenTabs>
  )
}
import {
  LumenTabs,
  useTabs
} from '@santi020k/lumen-react-native'

const options = [
  { label: 'Overview', value: 'overview' },
  { label: 'Activity', value: 'activity' }
]

export function ProjectTabs() {
  const tabs = useTabs({ defaultValue: 'overview' })

  return (
    <LumenTabs
      {...tabs.tabsProps}
      label="Project sections"
      options={options}
    >
      <ProjectPanel value={tabs.value} />
    </LumenTabs>
  )
}

Toast queue

The queue is local to the component that calls useToast. Lift the hook to an application provider when notifications must be created from multiple screens.

tsx
import {
  LumenButton,
  LumenToast,
  useToast
} from '@santi020k/lumen-react-native'

export function SaveProject() {
  const notifications = useToast()

  return (
    <>
      <LumenButton
        onPress={() => notifications.create({
          title: 'Project saved',
          variant: 'success'
        })}
      >
        Save
      </LumenButton>
      {notifications.toasts.map(toast => (
        <LumenToast
          key={toast.id}
          {...notifications.getToastProps(toast)}
        />
      ))}
    </>
  )
}
import {
  LumenButton,
  LumenToast,
  useToast
} from '@santi020k/lumen-react-native'

export function SaveProject() {
  const notifications = useToast()

  return (
    <>
      <LumenButton
        onPress={() => notifications.create({
          title: 'Project saved',
          variant: 'success'
        })}
      >
        Save
      </LumenButton>
      {notifications.toasts.map(toast => (
        <LumenToast
          key={toast.id}
          {...notifications.getToastProps(toast)}
        />
      ))}
    </>
  )
}
React Native docsNative primitives