@uxf/core-react 11.97.0 → 11.104.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -105,6 +105,9 @@ useKey<HTMLDivElement>("Enter", () => console.log("callback"), {
105
105
  ```
106
106
  ---
107
107
  ### useMinWindowWidth
108
+
109
+ > **Deprecated** — Use `useMediaQuery` instead.
110
+
108
111
  Returns boolean if window width is equal or greater than given value.
109
112
  ```tsx
110
113
  import { useMinWindowWidth } from "@uxf/core-react/hooks/use-min-window-width";
@@ -387,14 +390,35 @@ import { nl2br } from "@uxf/core-react/string/nl2br";
387
390
  ```
388
391
  ---
389
392
  ### useMediaQuery
390
- Returns if the media query is matched.
393
+ Returns whether the given media query is currently matched. Optionally accepts a callback that is called on every change.
394
+
395
+ Uses `window.matchMedia` with a `change` event listener (via `AbortController`) for efficient updates.
396
+
391
397
  ```tsx
392
398
  import { useMediaQuery } from "@uxf/core-react/hooks/use-media-query";
399
+ import type { UseMediaQueryCallback } from "@uxf/core-react/hooks/use-media-query";
393
400
  import { twScreens } from "@generated/tw-tokens/tw-screens";
394
401
 
402
+ // Basic usage – reactive boolean (SSR-safe, initializes as false)
395
403
  const isDesktop = useMediaQuery(`(min-width: ${twScreens.sm})`);
404
+
405
+ // With optional callback – fired on every match change
406
+ const callback: UseMediaQueryCallback = (isMatching, mediaQueryString) => {
407
+ console.log(isMatching, mediaQueryString);
408
+ };
409
+
410
+ const isDesktopWithCallback = useMediaQuery(`(min-width: ${twScreens.sm})`, callback);
411
+
412
+ // Client-only usage – initializes immediately from window.matchMedia (no SSR hydration)
413
+ // Pass isSSR=false only when the component is guaranteed to render client-side only
414
+ const isDesktopClientOnly = useMediaQuery(`(min-width: ${twScreens.sm})`, undefined, false);
396
415
  ```
397
416
 
417
+ **Parameters:**
418
+ - `mediaQueryString` – CSS media query string
419
+ - `callback` *(optional)* – called with `(isMatching, mediaQueryString)` on every match change
420
+ - `isSSR` *(optional, default: `true`)* – when `true`, initial state is `false` to avoid SSR/hydration mismatch; when `false`, initial state is read directly from `window.matchMedia` (use only in client-only components)
421
+
398
422
  ## Drag and Drop (DND) Hooks
399
423
 
400
424
  Provides a set of hooks built on top of [@dnd-kit](https://dndkit.com/) for implementing drag-and-drop functionality with different patterns.
@@ -1 +1,2 @@
1
- export declare function useMediaQuery(mediaQueryString: string): boolean;
1
+ export type UseMediaQueryCallback = (isMatching: boolean, mediaQueryString: string) => void;
2
+ export declare function useMediaQuery(mediaQueryString: string, callback?: UseMediaQueryCallback, isSSR?: boolean): boolean;
@@ -2,17 +2,26 @@
2
2
  "use client";
3
3
  Object.defineProperty(exports, "__esModule", { value: true });
4
4
  exports.useMediaQuery = useMediaQuery;
5
+ const use_latest_1 = require("@uxf/core-react/hooks/use-latest");
5
6
  const react_1 = require("react");
6
- function useMediaQuery(mediaQueryString) {
7
- const [isMatched, setIsMatched] = (0, react_1.useState)(false);
7
+ function useMediaQuery(mediaQueryString, callback, isSSR = true) {
8
+ const [isMatching, setIsMatching] = (0, react_1.useState)(isSSR ? false : window.matchMedia(mediaQueryString).matches);
9
+ const latestCallback = (0, use_latest_1.useLatest)(callback);
8
10
  (0, react_1.useEffect)(() => {
9
- const observer = new ResizeObserver(() => {
10
- setIsMatched(window.matchMedia(mediaQueryString).matches);
11
+ const controller = new AbortController();
12
+ const mqList = window.matchMedia(mediaQueryString);
13
+ function handler(matches, media) {
14
+ var _a;
15
+ setIsMatching(matches);
16
+ (_a = latestCallback.current) === null || _a === void 0 ? void 0 : _a.call(latestCallback, matches, media);
17
+ }
18
+ handler(mqList.matches, mqList.media);
19
+ mqList.addEventListener("change", (e) => handler(e.matches, e.media), {
20
+ signal: controller.signal,
11
21
  });
12
- observer.observe(document.body);
13
22
  return () => {
14
- observer.unobserve(document.body);
23
+ controller.abort();
15
24
  };
16
- }, [mediaQueryString]);
17
- return isMatched;
25
+ }, [latestCallback, mediaQueryString]);
26
+ return isMatching;
18
27
  }
@@ -1 +1,4 @@
1
+ /**
2
+ * @deprecated Use useMediaQuery instead
3
+ */
1
4
  export declare function useMinWindowWidth(minWidth: number, debounce?: number): boolean | undefined;
@@ -3,6 +3,9 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.useMinWindowWidth = useMinWindowWidth;
4
4
  const react_1 = require("react");
5
5
  const use_raf_state_1 = require("./use-raf-state");
6
+ /**
7
+ * @deprecated Use useMediaQuery instead
8
+ */
6
9
  function useMinWindowWidth(minWidth, debounce = 0) {
7
10
  const [state, setState] = (0, use_raf_state_1.useRafState)();
8
11
  (0, react_1.useEffect)(() => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@uxf/core-react",
3
- "version": "11.97.0",
3
+ "version": "11.104.0",
4
4
  "description": "UXF Core",
5
5
  "author": "UX Fans s.r.o",
6
6
  "license": "MIT",
@@ -12,7 +12,7 @@
12
12
  "typecheck": "tsc --noEmit --skipLibCheck"
13
13
  },
14
14
  "dependencies": {
15
- "@uxf/core": "11.97.0",
15
+ "@uxf/core": "11.100.0",
16
16
  "@dnd-kit/core": "6.3.1",
17
17
  "@dnd-kit/sortable": "10.0.0"
18
18
  },