kamod-hooks

June 17, 2026 · View on GitHub

License: MIT Preact Docs Demo

kamod-hooks docs preview

Production-ready hooks for Preact — fast to adopt, easy to tree-shake, and built with zero runtime dependencies beyond preact itself.

kamod-hooks is a Preact-first hook library inspired by ahooks. It brings together state, lifecycle, browser, async, and utility hooks in a single TypeScript-friendly package, backed by a live docs site with interactive demos and visible source code.

Start in 30 seconds

pnpm add @kamod-ch/hooks preact
import { useToggle, useCounter, useLocalStorageState } from '@kamod-ch/hooks'

Explore now: Live docs · Hooks index · Getting started

Table of contents

Why kamod-hooks?

Built for real Preact apps

Use hooks for the things you actually need in production:

  • state and lifecycle helpers
  • debounce / throttle / timing
  • storage and URL state sync
  • DOM and browser APIs
  • drag & drop, viewport, fullscreen, selection, media
  • async requests, caching, and pagination

Lean by default

  • Peer dependency only: preact
  • No runtime npm dependencies in @kamod-ch/hooks
  • ESM output for modern bundlers
  • TypeScript-first with generated declarations
  • Tree-shakeable root exports and subpath imports

Easy to evaluate

The project ships with a documentation site that doubles as a live demo environment:

  • interactive examples
  • source code shown directly with each example
  • searchable hook docs
  • guide pages for setup and usage

Feature matrix

CapabilityIncluded
Preact-first hooksYes
Zero runtime dependencies besides preactYes
TypeScript declarationsYes
ESM package outputYes
Tree-shakeable root exportsYes
Subpath importsYes
Interactive docs demosYes
Visible example sourceYes
GitHub Pages-ready docsYes
Hooks for state, effects, browser APIs, async, URL, storageYes

Install

pnpm add @kamod-ch/hooks preact

npm badge can be added as soon as the public package page is available.

Basic usage

import { useToggle, useUrlState } from '@kamod-ch/hooks'

Subpath imports are also supported:

import useToggle from '@kamod-ch/hooks/useToggle'
import useUrlState from '@kamod-ch/hooks/useUrlState'

The root export remains tree-shakeable in modern bundlers. Subpath imports can be useful when you prefer more explicit dependency boundaries or want to inspect bundle composition more directly.

Most used hooks

If you're new to the library, these are strong starting points:

Demo

The fastest way to understand the library is to try the live documentation:

Run the local demo/dev site:

pnpm install
pnpm demo

Example

import { useCounter, useToggle } from '@kamod-ch/hooks'

export function Example() {
  const [count, { inc, dec, reset }] = useCounter(0)
  const [enabled, { toggle }] = useToggle(false)

  return (
    <div>
      <p>Count: {count}</p>
      <p>Enabled: {String(enabled)}</p>

      <button onClick={() => inc()}>+</button>
      <button onClick={() => dec()}>-</button>
      <button onClick={reset}>Reset</button>
      <button onClick={toggle}>Toggle</button>
    </div>
  )
}

Documentation site

The documentation in packages/docs is built with PreactPress and acts as both reference and demo site.

It includes:

  • getting-started guides
  • hook reference pages
  • live interactive demos
  • visible example source code
  • search and outline navigation
  • static deployment support for GitHub Pages

Run locally:

pnpm docs:dev

Check docs integrity:

pnpm docs:check

Production build and preview:

pnpm docs:build
pnpm docs:preview

Notable behavior

  • useUrlState syncs query params via the History API (pushState / replaceState) and listens to popstate.
  • Browser-facing hooks use native platform APIs such as ResizeObserver, IntersectionObserver, Fullscreen API, matchMedia, and storage APIs.
  • The project is inspired by ahooks, but hooks are adapted for a Preact-first and browser-native setup.

Hooks and utilities

State and value helpers

Recommended: useToggle, useCounter, useSetState, useLocalStorageState

ExportDescription
useBooleanBoolean state with helpers (setTrue, setFalse, toggle).
useControllableValueControlled / uncontrolled value pattern with a single API.
useCounterNumeric counter with increment, decrement, and bounds.
useDynamicListList state with add, remove, replace, reorder, and bulk updates.
useGetStateuseState plus a getState() function that always reads the latest value.
useHistoryTravelUndo / redo over a value with past and future stacks.
useMapReactive Map with immutable-style update helpers.
usePreviousHolds the previous value of a state or prop across renders.
useReactiveMutable proxy object that triggers re-renders on deep changes.
useResetStateState with a reset back to the initial value.
useSafeStateuseState that ignores updates after unmount.
useSelectionsMulti-select items from a list with select-all / partial logic.
useSetReactive Set with add/remove/has helpers.
useSetStateObject state merged like class setState.
useToggleCycles or toggles among two or more values.

Effects, lifecycle, and render control

Recommended: useMemoizedFn, useLatest, useUpdateEffect, useIsomorphicLayoutEffect

ExportDescription
useAsyncEffectuseEffect that allows an async function and optional async cleanup.
useCreationMemoizes a value with a stable reference (similar intent to useMemo for instances).
useDeepCompareEffectuseEffect with deep-equality dependency comparison.
useDeepCompareLayoutEffectuseLayoutEffect variant with deep-equality deps.
useIsomorphicLayoutEffectuseLayoutEffect in the browser, useEffect on the server.
useLatestRef that always holds the latest value of a variable.
useMemoizedFnStable function reference that always calls the latest implementation.
useMountRuns a callback once when the component mounts.
useTrackedEffectuseEffect that reports which dependencies changed.
useUnmountRuns a callback when the component unmounts.
useUnmountedRefRef that becomes true after the component has unmounted.
useUpdateReturns a function that forces a re-render.
useUpdateEffectLike useEffect but skips the first run (updates only).
useUpdateLayoutEffectLike useLayoutEffect but skips the first run.
createUpdateEffectBuilds an effect hook that runs only on updates, not on mount.

Timing, debounce, and throttle

Recommended: useDebounce, useDebounceFn, useThrottle, useTimeout

ExportDescription
useDebounceDebounced value that updates after a delay.
useDebounceEffectuseEffect that debounces when dependencies change.
useDebounceFnReturns a debounced version of a function.
useIntervalDeclarative setInterval tied to the component lifecycle.
useLockFnWraps an async function so concurrent calls are serialized / deduped.
useRafIntervalInterval callbacks scheduled with requestAnimationFrame.
useRafStateState updates coalesced on requestAnimationFrame.
useRafTimeoutDelayed callback scheduled with requestAnimationFrame.
useThrottleThrottled value that updates at most every N ms.
useThrottleEffectuseEffect that throttles when dependencies change.
useThrottleFnReturns a throttled version of a function.
useTimeoutDeclarative setTimeout with cancel / reset.

Browser, DOM, and interaction hooks

Recommended: useClickAway, useSize, useInViewport, useFullscreen

ExportDescription
useClickAwayFires a callback when the user clicks outside given target(s).
useDocumentVisibilitySubscribes to document.visibilityState (tab visible / hidden).
useDragHTML5 drag source: sets draggable, serializes payload into dataTransfer (pairs with useDrop).
useDropHTML5 drop target: accepts custom DOM data, files, URIs, text, and paste events.
useEventListenerAttaches a DOM event listener with sensible defaults and cleanup.
useExternalLoads external scripts or stylesheets and tracks loading status.
useFaviconSets the document favicon URL.
useFocusWithinWhether focus is inside a subtree (focus-within semantics).
useFullscreenFullscreen API for an element (enter / exit / toggle).
useHoverWhether the pointer is hovering over a target element.
useInViewportWhether an element is visible via IntersectionObserver.
useInfiniteScrollInfinite scroll: load more when a sentinel enters the viewport.
useKeyPressListens for specific keys or key combinations.
useLongPressDetects a long-press gesture with configurable delay.
useMouseTracks mouse position (page / screen / element-relative).
useMutationObserverSubscribes to DOM mutations on an element.
useScrollScroll position and scrolling for window or an element.
useSizeObserved width and height of a DOM element (ResizeObserver).
useTextSelectionCurrent text selection within a target or document.
useTitleSets document.title and restores on unmount if configured.

Storage, URL, and environment

Recommended: useUrlState, useLocalStorageState, useTheme, useResponsive

ExportDescription
useCookieStateState persisted in a browser cookie.
useEventTargetNormalized state for form-like targets (value, onChange).
useLocalStorageStateState synced with localStorage.
useNetworkOnline / offline and connection-aware network state.
useResponsiveBreakpoint flags from matchMedia (uses configResponsive).
useSessionStorageStateState synced with sessionStorage.
useThemeLight / dark / system theme with media-query and storage sync.
useUrlStateState mirrored in the URL query string via the History API.
configResponsiveRegisters breakpoint names and widths for useResponsive.

Async data and advanced utilities

Recommended: useRequest, usePagination, useWebSocket, clearCache

ExportDescription
useAntdTableTable data flow for Ant Design–style tables: async service, pagination, filters, and sorters.
useCountDownCountdown to a target time with formatted remaining time.
useEventEmitterSimple pub/sub event bus shared across components.
useFusionTableLike useAntdTable but oriented toward Fusion Design table usage.
usePaginationPagination state and helpers for list or table data.
useRequestAsync request lifecycle: loading, data, error, refresh, and cache.
useVirtualListVirtual list: only renders visible slice of a long list.
useWebSocketWebSocket connection with reconnect and message helpers.
useWhyDidYouUpdateLogs which props or state changed between renders (dev aid).
clearCacheClears cached results used by useRequest.

Scripts

CommandDescription
pnpm buildBuild all packages
pnpm testRun @kamod-ch/hooks tests
pnpm typecheckTypecheck workspace
pnpm demoStart the docs/demo site locally
pnpm docs:devRun PreactPress docs locally
pnpm docs:checkValidate docs pages, demos, links, and routes
pnpm docs:buildBuild static docs to packages/docs/dist
pnpm docs:previewPreview the built docs locally
pnpm qa:packageBuild package and run package-quality checks

Contributing

Issues and improvements are welcome. If you change docs behavior or hook APIs, please validate both package and docs flows:

pnpm build
pnpm test
pnpm docs:check

License

Released under the MIT License. See LICENSE and NOTICE.