react-native-gtkx 0.2.0-alpha.2 → 0.3.0-alpha.1
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 +5 -2
- package/dist/aliases/index.d.ts +84 -0
- package/dist/aliases/index.js +208 -0
- package/dist/aliases/index.js.map +1 -0
- package/dist/animated/index.d.ts +2 -0
- package/dist/animated/index.js +5 -0
- package/dist/animated/index.js.map +1 -1
- package/dist/animated/types.d.ts +1 -0
- package/dist/animated/types.js.map +1 -1
- package/dist/animated/value-animation.js +17 -4
- package/dist/animated/value-animation.js.map +1 -1
- package/dist/apis/host.gtkx.js +9 -12
- package/dist/apis/host.gtkx.js.map +1 -1
- package/dist/apis/index.d.ts +4 -2
- package/dist/apis/index.js +2 -0
- package/dist/apis/index.js.map +1 -1
- package/dist/apis/keyboard.d.ts +60 -0
- package/dist/apis/keyboard.js +63 -0
- package/dist/apis/keyboard.js.map +1 -0
- package/dist/apis/log-box.d.ts +15 -0
- package/dist/apis/log-box.js +46 -0
- package/dist/apis/log-box.js.map +1 -0
- package/dist/apis/platform.d.ts +18 -1
- package/dist/apis/platform.js.map +1 -1
- package/dist/common/index.d.ts +0 -1
- package/dist/common/index.js +24 -1
- package/dist/common/index.js.map +1 -1
- package/dist/components/animated.d.ts +70 -6
- package/dist/components/animated.js +559 -46
- package/dist/components/animated.js.map +1 -1
- package/dist/components/driven-size.d.ts +27 -0
- package/dist/components/driven-size.js +85 -0
- package/dist/components/driven-size.js.map +1 -0
- package/dist/components/find-node-handle.d.ts +11 -0
- package/dist/components/find-node-handle.js +53 -0
- package/dist/components/find-node-handle.js.map +1 -0
- package/dist/components/flat-list.d.ts +3 -2
- package/dist/components/flat-list.js.map +1 -1
- package/dist/components/frame-scheduler.d.ts +16 -0
- package/dist/components/frame-scheduler.js +37 -0
- package/dist/components/frame-scheduler.js.map +1 -0
- package/dist/components/image.d.ts +6 -1
- package/dist/components/image.js +15 -4
- package/dist/components/image.js.map +1 -1
- package/dist/components/index.d.ts +7 -5
- package/dist/components/index.js +5 -3
- package/dist/components/index.js.map +1 -1
- package/dist/components/measure.d.ts +51 -1
- package/dist/components/measure.js +101 -2
- package/dist/components/measure.js.map +1 -1
- package/dist/components/pressable.d.ts +61 -1
- package/dist/components/pressable.js +151 -4
- package/dist/components/pressable.js.map +1 -1
- package/dist/components/rect-store.d.ts +58 -0
- package/dist/components/rect-store.js +124 -3
- package/dist/components/rect-store.js.map +1 -1
- package/dist/components/root.js +6 -1
- package/dist/components/root.js.map +1 -1
- package/dist/components/scroll-phase.d.ts +35 -0
- package/dist/components/scroll-phase.js +26 -0
- package/dist/components/scroll-phase.js.map +1 -0
- package/dist/components/scroll-view.d.ts +39 -3
- package/dist/components/scroll-view.js +378 -43
- package/dist/components/scroll-view.js.map +1 -1
- package/dist/components/text-input.js +9 -25
- package/dist/components/text-input.js.map +1 -1
- package/dist/components/text.d.ts +6 -2
- package/dist/components/text.js +43 -8
- package/dist/components/text.js.map +1 -1
- package/dist/components/use-focus.d.ts +27 -0
- package/dist/components/use-focus.js +116 -0
- package/dist/components/use-focus.js.map +1 -0
- package/dist/components/use-layout-child.d.ts +13 -1
- package/dist/components/use-layout-child.js +188 -5
- package/dist/components/use-layout-child.js.map +1 -1
- package/dist/components/view.d.ts +5 -2
- package/dist/components/view.js +18 -13
- package/dist/components/view.js.map +1 -1
- package/dist/components/virtualized-list.d.ts +45 -5
- package/dist/components/virtualized-list.js +90 -24
- package/dist/components/virtualized-list.js.map +1 -1
- package/dist/components/wheel-scroll-session.d.ts +7 -0
- package/dist/components/wheel-scroll-session.js +53 -0
- package/dist/components/wheel-scroll-session.js.map +1 -0
- package/dist/components/widget-retention.d.ts +35 -0
- package/dist/components/widget-retention.js +169 -0
- package/dist/components/widget-retention.js.map +1 -0
- package/dist/contracts.d.ts +4 -0
- package/dist/contracts.js.map +1 -1
- package/dist/dnd/context.d.ts +69 -0
- package/dist/dnd/context.js +149 -0
- package/dist/dnd/context.js.map +1 -0
- package/dist/dnd/draggable.d.ts +59 -0
- package/dist/dnd/draggable.js +149 -0
- package/dist/dnd/draggable.js.map +1 -0
- package/dist/dnd/droppable.d.ts +24 -0
- package/dist/dnd/droppable.js +74 -0
- package/dist/dnd/droppable.js.map +1 -0
- package/dist/dnd/gtk-controllers.d.ts +39 -0
- package/dist/dnd/gtk-controllers.js +110 -0
- package/dist/dnd/gtk-controllers.js.map +1 -0
- package/dist/dnd/index.d.ts +6 -0
- package/dist/dnd/index.js +31 -0
- package/dist/dnd/index.js.map +1 -0
- package/dist/dnd/order.d.ts +7 -0
- package/dist/dnd/order.js +20 -0
- package/dist/dnd/order.js.map +1 -0
- package/dist/dnd/payload.d.ts +14 -0
- package/dist/dnd/payload.js +41 -0
- package/dist/dnd/payload.js.map +1 -0
- package/dist/dnd/sortable.d.ts +49 -0
- package/dist/dnd/sortable.js +307 -0
- package/dist/dnd/sortable.js.map +1 -0
- package/dist/dnd/types.d.ts +290 -0
- package/dist/dnd/types.js +25 -0
- package/dist/dnd/types.js.map +1 -0
- package/dist/gesture-handler-compat/builder.d.ts +251 -0
- package/dist/gesture-handler-compat/builder.js +513 -0
- package/dist/gesture-handler-compat/builder.js.map +1 -0
- package/dist/gesture-handler-compat/composition.d.ts +23 -0
- package/dist/gesture-handler-compat/composition.js +111 -0
- package/dist/gesture-handler-compat/composition.js.map +1 -0
- package/dist/gesture-handler-compat/deciders.d.ts +3 -0
- package/dist/gesture-handler-compat/deciders.js +47 -0
- package/dist/gesture-handler-compat/deciders.js.map +1 -0
- package/dist/gesture-handler-compat/detector-runtime.d.ts +44 -0
- package/dist/gesture-handler-compat/detector-runtime.js +374 -0
- package/dist/gesture-handler-compat/detector-runtime.js.map +1 -0
- package/dist/gesture-handler-compat/detector.d.ts +22 -0
- package/dist/gesture-handler-compat/detector.js +104 -0
- package/dist/gesture-handler-compat/detector.js.map +1 -0
- package/dist/gesture-handler-compat/fling.d.ts +24 -0
- package/dist/gesture-handler-compat/fling.js +123 -0
- package/dist/gesture-handler-compat/fling.js.map +1 -0
- package/dist/gesture-handler-compat/force-touch.d.ts +13 -0
- package/dist/gesture-handler-compat/force-touch.js +40 -0
- package/dist/gesture-handler-compat/force-touch.js.map +1 -0
- package/dist/gesture-handler-compat/hooks.d.ts +157 -0
- package/dist/gesture-handler-compat/hooks.js +268 -0
- package/dist/gesture-handler-compat/hooks.js.map +1 -0
- package/dist/gesture-handler-compat/hover.d.ts +2 -0
- package/dist/gesture-handler-compat/hover.js +22 -0
- package/dist/gesture-handler-compat/hover.js.map +1 -0
- package/dist/gesture-handler-compat/index.d.ts +98 -0
- package/dist/gesture-handler-compat/index.js +255 -0
- package/dist/gesture-handler-compat/index.js.map +1 -0
- package/dist/gesture-handler-compat/long-press.d.ts +6 -0
- package/dist/gesture-handler-compat/long-press.js +21 -0
- package/dist/gesture-handler-compat/long-press.js.map +1 -0
- package/dist/gesture-handler-compat/manual.d.ts +2 -0
- package/dist/gesture-handler-compat/manual.js +18 -0
- package/dist/gesture-handler-compat/manual.js.map +1 -0
- package/dist/gesture-handler-compat/native.d.ts +7 -0
- package/dist/gesture-handler-compat/native.js +34 -0
- package/dist/gesture-handler-compat/native.js.map +1 -0
- package/dist/gesture-handler-compat/orchestrator.d.ts +77 -0
- package/dist/gesture-handler-compat/orchestrator.js +284 -0
- package/dist/gesture-handler-compat/orchestrator.js.map +1 -0
- package/dist/gesture-handler-compat/pan.d.ts +23 -0
- package/dist/gesture-handler-compat/pan.js +116 -0
- package/dist/gesture-handler-compat/pan.js.map +1 -0
- package/dist/gesture-handler-compat/recognizer.d.ts +268 -0
- package/dist/gesture-handler-compat/recognizer.js +1056 -0
- package/dist/gesture-handler-compat/recognizer.js.map +1 -0
- package/dist/gesture-handler-compat/relations.d.ts +43 -0
- package/dist/gesture-handler-compat/relations.js +128 -0
- package/dist/gesture-handler-compat/relations.js.map +1 -0
- package/dist/gesture-handler-compat/tap.d.ts +6 -0
- package/dist/gesture-handler-compat/tap.js +29 -0
- package/dist/gesture-handler-compat/tap.js.map +1 -0
- package/dist/gesture-handler-compat/touchpad.d.ts +41 -0
- package/dist/gesture-handler-compat/touchpad.js +64 -0
- package/dist/gesture-handler-compat/touchpad.js.map +1 -0
- package/dist/gesture-handler-compat/types.d.ts +441 -0
- package/dist/gesture-handler-compat/types.js +167 -0
- package/dist/gesture-handler-compat/types.js.map +1 -0
- package/dist/gtk/controllers.d.ts +39 -0
- package/dist/gtk/controllers.js +92 -0
- package/dist/gtk/controllers.js.map +1 -0
- package/dist/gtk/index.d.ts +2 -1
- package/dist/gtk/index.js +7 -1
- package/dist/gtk/index.js.map +1 -1
- package/dist/gtkx/bridge/geometry.js +6 -4
- package/dist/gtkx/bridge/geometry.js.map +1 -1
- package/dist/gtkx/bridge/index.d.ts +5 -3
- package/dist/gtkx/bridge/index.js +6 -3
- package/dist/gtkx/bridge/index.js.map +1 -1
- package/dist/gtkx/bridge/slot-portal.js.map +1 -1
- package/dist/gtkx/bridge/use-signal.js +1 -1
- package/dist/gtkx/bridge/use-signal.js.map +1 -1
- package/dist/gtkx/bridge/view-box.d.ts +56 -0
- package/dist/gtkx/bridge/view-box.js +394 -9
- package/dist/gtkx/bridge/view-box.js.map +1 -1
- package/dist/gtkx/bridge/widget-css.d.ts +17 -0
- package/dist/gtkx/bridge/widget-css.js +72 -0
- package/dist/gtkx/bridge/widget-css.js.map +1 -0
- package/dist/index.d.ts +3 -3
- package/dist/index.js +2 -2
- package/dist/index.js.map +1 -1
- package/dist/layout/driven-size.d.ts +12 -0
- package/dist/layout/driven-size.js +70 -0
- package/dist/layout/driven-size.js.map +1 -0
- package/dist/layout/engine.d.ts +17 -1
- package/dist/layout/engine.js +3 -20
- package/dist/layout/engine.js.map +1 -1
- package/dist/layout/node.d.ts +13 -0
- package/dist/layout/node.js +14 -0
- package/dist/layout/node.js.map +1 -1
- package/dist/layout/yoga.d.ts +3 -2
- package/dist/layout/yoga.js +5 -2
- package/dist/layout/yoga.js.map +1 -1
- package/dist/mcp/data/generated.d.ts +257 -60
- package/dist/mcp/data/generated.js +306 -62
- package/dist/mcp/data/generated.js.map +1 -1
- package/dist/metro/index.d.ts +10 -0
- package/dist/metro/index.js +21 -12
- package/dist/metro/index.js.map +1 -1
- package/dist/navigation/sidebar.d.ts +16 -0
- package/dist/navigation/sidebar.js +65 -1
- package/dist/navigation/sidebar.js.map +1 -1
- package/dist/reanimated-compat/animated-ref.d.ts +32 -0
- package/dist/reanimated-compat/animated-ref.js +57 -0
- package/dist/reanimated-compat/animated-ref.js.map +1 -0
- package/dist/reanimated-compat/animation.d.ts +177 -0
- package/dist/reanimated-compat/animation.js +540 -0
- package/dist/reanimated-compat/animation.js.map +1 -0
- package/dist/reanimated-compat/color.d.ts +28 -0
- package/dist/reanimated-compat/color.js +249 -0
- package/dist/reanimated-compat/color.js.map +1 -0
- package/dist/reanimated-compat/decay.d.ts +39 -0
- package/dist/reanimated-compat/decay.js +96 -0
- package/dist/reanimated-compat/decay.js.map +1 -0
- package/dist/reanimated-compat/easing.d.ts +30 -0
- package/dist/reanimated-compat/easing.js +76 -0
- package/dist/reanimated-compat/easing.js.map +1 -0
- package/dist/reanimated-compat/hooks.d.ts +14 -0
- package/dist/reanimated-compat/hooks.js +217 -0
- package/dist/reanimated-compat/hooks.js.map +1 -0
- package/dist/reanimated-compat/index.d.ts +258 -0
- package/dist/reanimated-compat/index.js +464 -0
- package/dist/reanimated-compat/index.js.map +1 -0
- package/dist/reanimated-compat/interpolation.d.ts +18 -0
- package/dist/reanimated-compat/interpolation.js +122 -0
- package/dist/reanimated-compat/interpolation.js.map +1 -0
- package/dist/reanimated-compat/layout-animation-config.d.ts +43 -0
- package/dist/reanimated-compat/layout-animation-config.js +78 -0
- package/dist/reanimated-compat/layout-animation-config.js.map +1 -0
- package/dist/reanimated-compat/layout-animation-presets.d.ts +117 -0
- package/dist/reanimated-compat/layout-animation-presets.js +498 -0
- package/dist/reanimated-compat/layout-animation-presets.js.map +1 -0
- package/dist/reanimated-compat/layout-animation-runtime.d.ts +21 -0
- package/dist/reanimated-compat/layout-animation-runtime.js +311 -0
- package/dist/reanimated-compat/layout-animation-runtime.js.map +1 -0
- package/dist/reanimated-compat/layout-animation-view.d.ts +27 -0
- package/dist/reanimated-compat/layout-animation-view.js +266 -0
- package/dist/reanimated-compat/layout-animation-view.js.map +1 -0
- package/dist/reanimated-compat/layout-animation.d.ts +171 -0
- package/dist/reanimated-compat/layout-animation.js +469 -0
- package/dist/reanimated-compat/layout-animation.js.map +1 -0
- package/dist/reanimated-compat/layout-transitions.d.ts +83 -0
- package/dist/reanimated-compat/layout-transitions.js +350 -0
- package/dist/reanimated-compat/layout-transitions.js.map +1 -0
- package/dist/reanimated-compat/mutable.d.ts +29 -0
- package/dist/reanimated-compat/mutable.js +139 -0
- package/dist/reanimated-compat/mutable.js.map +1 -0
- package/dist/reanimated-compat/props.d.ts +18 -0
- package/dist/reanimated-compat/props.js +111 -0
- package/dist/reanimated-compat/props.js.map +1 -0
- package/dist/reanimated-compat/scroll-handler.d.ts +119 -0
- package/dist/reanimated-compat/scroll-handler.js +274 -0
- package/dist/reanimated-compat/scroll-handler.js.map +1 -0
- package/dist/reanimated-compat/scroll-offset.d.ts +12 -0
- package/dist/reanimated-compat/scroll-offset.js +104 -0
- package/dist/reanimated-compat/scroll-offset.js.map +1 -0
- package/dist/reanimated-compat/style.d.ts +90 -0
- package/dist/reanimated-compat/style.js +452 -0
- package/dist/reanimated-compat/style.js.map +1 -0
- package/dist/reanimated-compat/test-timers.d.ts +28 -0
- package/dist/reanimated-compat/test-timers.js +136 -0
- package/dist/reanimated-compat/test-timers.js.map +1 -0
- package/dist/reanimated-compat/threads.d.ts +13 -0
- package/dist/reanimated-compat/threads.js +41 -0
- package/dist/reanimated-compat/threads.js.map +1 -0
- package/dist/reanimated-compat/tracking.d.ts +41 -0
- package/dist/reanimated-compat/tracking.js +106 -0
- package/dist/reanimated-compat/tracking.js.map +1 -0
- package/dist/reanimated-compat/updater-animations.d.ts +36 -0
- package/dist/reanimated-compat/updater-animations.js +273 -0
- package/dist/reanimated-compat/updater-animations.js.map +1 -0
- package/dist/responder/system.d.ts +80 -7
- package/dist/responder/system.js +143 -23
- package/dist/responder/system.js.map +1 -1
- package/dist/responder/use-responder.d.ts +11 -0
- package/dist/responder/use-responder.js +225 -6
- package/dist/responder/use-responder.js.map +1 -1
- package/dist/runner/host-dev.js +1 -1
- package/dist/runner/host-dev.js.map +1 -1
- package/dist/runner/host.js +1 -1
- package/dist/runner/host.js.map +1 -1
- package/dist/runner/index.js +3 -3
- package/dist/runner/index.js.map +1 -1
- package/dist/sea/gtkx-config-module.js +1 -1
- package/dist/sea/gtkx-config-module.js.map +1 -1
- package/dist/style/absolute-insets.d.ts +26 -0
- package/dist/style/absolute-insets.js +113 -0
- package/dist/style/absolute-insets.js.map +1 -0
- package/dist/style/animated-size.d.ts +25 -0
- package/dist/style/animated-size.js +225 -0
- package/dist/style/animated-size.js.map +1 -0
- package/dist/style/colors.d.ts +17 -0
- package/dist/style/colors.js +25 -6
- package/dist/style/colors.js.map +1 -1
- package/dist/style/imperative-css.d.ts +21 -0
- package/dist/style/imperative-css.js +63 -0
- package/dist/style/imperative-css.js.map +1 -0
- package/dist/style/index.d.ts +2 -1
- package/dist/style/index.js +2 -1
- package/dist/style/index.js.map +1 -1
- package/dist/style/split-style.js +5 -0
- package/dist/style/split-style.js.map +1 -1
- package/dist/testing/index.js.map +1 -1
- package/dist/unsupported-export.d.ts +8 -0
- package/dist/unsupported-export.js +66 -0
- package/dist/unsupported-export.js.map +1 -0
- package/dist/vite/index.d.ts +21 -8
- package/dist/vite/index.js +127 -82
- package/dist/vite/index.js.map +1 -1
- package/dist/vitest/index.d.ts +2 -2
- package/dist/vitest/index.js.map +1 -1
- package/dist/worklets-compat/index.d.ts +4 -0
- package/dist/worklets-compat/index.js +28 -0
- package/dist/worklets-compat/index.js.map +1 -0
- package/dist/worklets-compat/surface.d.ts +110 -0
- package/dist/worklets-compat/surface.js +153 -0
- package/dist/worklets-compat/surface.js.map +1 -0
- package/package.json +25 -9
- package/types.d.ts +9 -0
- package/dist/common/list.d.ts +0 -82
- package/dist/common/list.js +0 -166
- package/dist/common/list.js.map +0 -1
package/dist/components/view.js
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
2
|
import { useImperativeHandle, useLayoutEffect, useRef, } from "react";
|
|
3
3
|
import { StyleSheet } from "../style/index";
|
|
4
|
-
import { getViewBoxComponent, setBoxPassthrough, } from "../gtkx/bridge/index";
|
|
4
|
+
import { getViewBoxComponent, setBoxOnly, setBoxPassthrough, setPointerTarget, } from "../gtkx/bridge/index";
|
|
5
5
|
import { useResponder } from "../responder/use-responder";
|
|
6
6
|
import { HostNodeContext } from "./host-node";
|
|
7
7
|
import { createMeasureHandle } from "./measure";
|
|
8
|
+
import { useFocusable, useFocusController } from "./use-focus";
|
|
8
9
|
import { useLayoutChild, useRnContainer, } from "./use-layout-child";
|
|
9
10
|
// Every View is a GtkBox subclass (RnGtkxViewBox) driven by RnGtkxLayout:
|
|
10
11
|
// Yoga computes the children's rects, the manager's allocate() applies
|
|
@@ -16,10 +17,12 @@ import { useLayoutChild, useRnContainer, } from "./use-layout-child";
|
|
|
16
17
|
// view-box.ts) — the box is never the pick target while children stay
|
|
17
18
|
// pickable, and toggling never remounts the subtree;
|
|
18
19
|
// - box-only: direct children (and thus their subtrees) get
|
|
19
|
-
// can-target=false
|
|
20
|
-
//
|
|
21
|
-
//
|
|
22
|
-
|
|
20
|
+
// can-target=false, restored to what their OWN pointerEvents wants when
|
|
21
|
+
// the mode changes. That is why the bridge owns can-target rather than
|
|
22
|
+
// this component writing it: two things want the same boolean, and a
|
|
23
|
+
// blanket restore to `true` was what made nesting a pointerEvents inside
|
|
24
|
+
// a box-only view unsupported.
|
|
25
|
+
export const View = ({ style, pointerEvents, onLayout, focusable = false, onFocus, onBlur, children, testID, ref, ...responderProps }) => {
|
|
23
26
|
const widgetRef = useRef(null);
|
|
24
27
|
const { host, node, cssClass } = useLayoutChild(widgetRef, {
|
|
25
28
|
style,
|
|
@@ -27,6 +30,8 @@ export const View = ({ style, pointerEvents, onLayout, children, testID, ref, ..
|
|
|
27
30
|
});
|
|
28
31
|
useRnContainer(widgetRef, node);
|
|
29
32
|
useImperativeHandle(ref, () => createMeasureHandle(widgetRef, node), [node]);
|
|
33
|
+
useFocusable(widgetRef, focusable);
|
|
34
|
+
useFocusController(widgetRef, onFocus, onBlur);
|
|
30
35
|
// Spreading PanResponder's panHandlers onto a View is the portable RN
|
|
31
36
|
// idiom, so every responder prop arrives here as a rest prop.
|
|
32
37
|
useResponder(widgetRef, responderProps);
|
|
@@ -36,11 +41,15 @@ export const View = ({ style, pointerEvents, onLayout, children, testID, ref, ..
|
|
|
36
41
|
if (!widget) {
|
|
37
42
|
return;
|
|
38
43
|
}
|
|
39
|
-
widget
|
|
44
|
+
setPointerTarget(widget, mode !== "none");
|
|
40
45
|
setBoxPassthrough(widget, mode === "box-none");
|
|
41
46
|
}, [mode]);
|
|
42
|
-
// box-only
|
|
43
|
-
// renders
|
|
47
|
+
// box-only re-runs every commit rather than on change, because the child
|
|
48
|
+
// set moves with the renders and a child that appears while the mode is on
|
|
49
|
+
// has to be masked too. Every View commits, and almost none of them are
|
|
50
|
+
// box-only, so the walk is skipped unless this view is masking now or was
|
|
51
|
+
// masking a moment ago — the one commit after the mode goes away is what
|
|
52
|
+
// gives the children their own modes back.
|
|
44
53
|
const wasBoxOnly = useRef(false);
|
|
45
54
|
useLayoutEffect(() => {
|
|
46
55
|
const widget = widgetRef.current;
|
|
@@ -49,11 +58,7 @@ export const View = ({ style, pointerEvents, onLayout, children, testID, ref, ..
|
|
|
49
58
|
}
|
|
50
59
|
const boxOnly = mode === "box-only";
|
|
51
60
|
if (boxOnly || wasBoxOnly.current) {
|
|
52
|
-
|
|
53
|
-
while (child) {
|
|
54
|
-
child.setCanTarget(!boxOnly);
|
|
55
|
-
child = child.getNextSibling();
|
|
56
|
-
}
|
|
61
|
+
setBoxOnly(widget, boxOnly);
|
|
57
62
|
}
|
|
58
63
|
wasBoxOnly.current = boxOnly;
|
|
59
64
|
});
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"view.js","sourceRoot":"","sources":["../../src/components/view.tsx"],"names":[],"mappings":";AAAA,OAAO,EACL,mBAAmB,EACnB,eAAe,EACf,MAAM,GAGP,MAAM,OAAO,CAAA;AACd,OAAO,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAA;AAE3C,OAAO,EACL,mBAAmB,EAEnB,iBAAiB,
|
|
1
|
+
{"version":3,"file":"view.js","sourceRoot":"","sources":["../../src/components/view.tsx"],"names":[],"mappings":"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","sourcesContent":["import {\n useImperativeHandle,\n useLayoutEffect,\n useRef,\n type ReactNode,\n type Ref,\n} from \"react\"\nimport { StyleSheet } from \"../style/index\"\nimport type { PointerEventsValue, StyleProp } from \"../contracts\"\nimport {\n getViewBoxComponent,\n GtkBox,\n setBoxOnly,\n setBoxPassthrough,\n setPointerTarget,\n type Gtk,\n} from \"../gtkx/bridge/index\"\nimport type { ResponderProps } from \"../responder/types\"\nimport { useResponder } from \"../responder/use-responder\"\nimport { HostNodeContext } from \"./host-node\"\nimport { createMeasureHandle, type MeasureHandle } from \"./measure\"\nimport { useFocusable, useFocusController } from \"./use-focus\"\nimport {\n useLayoutChild,\n useRnContainer,\n type LayoutEvent,\n} from \"./use-layout-child\"\n\n/** RN's imperative geometry methods, on a `View` ref. */\nexport type ViewHandle = MeasureHandle\n\nexport type ViewProps = ResponderProps & {\n style?: StyleProp\n // RN pointerEvents; the prop wins over style.pointerEvents (RN 0.71+).\n pointerEvents?: PointerEventsValue\n onLayout?: (event: LayoutEvent) => void\n // RN's own prop (Android, Windows): puts the view into the keyboard focus\n // chain. Off by default, as it is in RN — a desktop's Tab order is the\n // app's to decide, not something a layout box should join by existing.\n focusable?: boolean\n // react-native-web and react-native-windows both put these on View; RN\n // core has them on TextInput and the touchables. No argument, matching\n // this platform's own TextInput.\n onFocus?: () => void\n onBlur?: () => void\n children?: ReactNode\n testID?: string\n // React 19 takes `ref` as an ordinary prop, which is what we want here:\n // forwardRef is booby-trapped on this stack (useEffectEvent never\n // refreshes inside it — see gtkx/bridge/use-signal.ts).\n ref?: Ref<ViewHandle>\n}\n\n// Every View is a GtkBox subclass (RnGtkxViewBox) driven by RnGtkxLayout:\n// Yoga computes the children's rects, the manager's allocate() applies\n// them. Visual styles arrive as a GTK CSS class produced by the style\n// system. pointerEvents maps onto GTK picking:\n// - none: can-target=false — GTK skips the widget WITHOUT descending, the\n// whole subtree is transparent (exact RN semantics);\n// - box-none: the subclass' contains() fails for this widget (see\n// view-box.ts) — the box is never the pick target while children stay\n// pickable, and toggling never remounts the subtree;\n// - box-only: direct children (and thus their subtrees) get\n// can-target=false, restored to what their OWN pointerEvents wants when\n// the mode changes. That is why the bridge owns can-target rather than\n// this component writing it: two things want the same boolean, and a\n// blanket restore to `true` was what made nesting a pointerEvents inside\n// a box-only view unsupported.\nexport const View = ({\n style,\n pointerEvents,\n onLayout,\n focusable = false,\n onFocus,\n onBlur,\n children,\n testID,\n ref,\n ...responderProps\n}: ViewProps) => {\n const widgetRef = useRef<Gtk.Box | null>(null)\n const { host, node, cssClass } = useLayoutChild(widgetRef, {\n style,\n onLayout,\n })\n useRnContainer(widgetRef, node)\n\n useImperativeHandle(ref, () => createMeasureHandle(widgetRef, node), [node])\n\n useFocusable(widgetRef, focusable)\n useFocusController(widgetRef, onFocus, onBlur)\n\n // Spreading PanResponder's panHandlers onto a View is the portable RN\n // idiom, so every responder prop arrives here as a rest prop.\n useResponder(widgetRef, responderProps)\n\n const mode: PointerEventsValue =\n pointerEvents ?? StyleSheet.flatten(style)?.pointerEvents ?? \"auto\"\n\n useLayoutEffect(() => {\n const widget = widgetRef.current\n if (!widget) {\n return\n }\n setPointerTarget(widget, mode !== \"none\")\n setBoxPassthrough(widget, mode === \"box-none\")\n }, [mode])\n\n // box-only re-runs every commit rather than on change, because the child\n // set moves with the renders and a child that appears while the mode is on\n // has to be masked too. Every View commits, and almost none of them are\n // box-only, so the walk is skipped unless this view is masking now or was\n // masking a moment ago — the one commit after the mode goes away is what\n // gives the children their own modes back.\n const wasBoxOnly = useRef(false)\n useLayoutEffect(() => {\n const widget = widgetRef.current\n if (!widget) {\n return\n }\n const boxOnly = mode === \"box-only\"\n if (boxOnly || wasBoxOnly.current) {\n setBoxOnly(widget, boxOnly)\n }\n wasBoxOnly.current = boxOnly\n })\n\n const ViewBox = getViewBoxComponent() as typeof GtkBox\n return (\n <ViewBox\n ref={widgetRef}\n name={testID}\n cssClasses={cssClass ? [cssClass] : []}\n >\n <HostNodeContext.Provider\n value={{ engine: host.engine, node, widgetRef }}\n >\n {children}\n </HostNodeContext.Provider>\n </ViewBox>\n )\n}\n\n// RN parity aliases (no notches or status bars on the Linux desktop).\nexport const SafeAreaView = View\n\nexport const StatusBar = (): null => null\n"]}
|
|
@@ -1,6 +1,7 @@
|
|
|
1
|
-
import { type ComponentType, type ReactElement } from "react";
|
|
1
|
+
import { type ComponentType, type ReactElement, type ReactNode } from "react";
|
|
2
2
|
import type { StyleProp } from "../contracts";
|
|
3
|
-
import { type
|
|
3
|
+
import { type ScrollHandle, type ScrollViewProps } from "./scroll-view";
|
|
4
|
+
import type { LayoutEvent } from "./use-layout-child";
|
|
4
5
|
export type ListRenderItemInfo<T> = {
|
|
5
6
|
item: T;
|
|
6
7
|
index: number;
|
|
@@ -21,7 +22,7 @@ export type ViewabilityConfig = {
|
|
|
21
22
|
viewAreaCoveragePercentThreshold?: number;
|
|
22
23
|
minimumViewTime?: number;
|
|
23
24
|
};
|
|
24
|
-
export type VirtualizedListHandle =
|
|
25
|
+
export type VirtualizedListHandle = ScrollHandle & {
|
|
25
26
|
scrollToIndex(params: {
|
|
26
27
|
index: number;
|
|
27
28
|
viewPosition?: number;
|
|
@@ -38,11 +39,27 @@ export type VirtualizedListHandle = ScrollViewHandle & {
|
|
|
38
39
|
}): void;
|
|
39
40
|
};
|
|
40
41
|
export type VirtualizedListProps<T> = Omit<ScrollViewProps, "children"> & {
|
|
41
|
-
data: readonly T[];
|
|
42
|
+
data: readonly T[] | unknown;
|
|
43
|
+
/**
|
|
44
|
+
* RN's `VirtualizedList` accessor pair. Supplying them makes `data` opaque:
|
|
45
|
+
* the list asks `getItemCount(data)` for the length and `getItem(data, i)`
|
|
46
|
+
* for a row, and reads nothing else out of it. Left out (FlatList,
|
|
47
|
+
* SectionList) `data` is indexed directly.
|
|
48
|
+
*
|
|
49
|
+
* They are honoured LAZILY — `getItem` is called for the rows the window
|
|
50
|
+
* actually mounts, never for the whole range — because the point of the
|
|
51
|
+
* pair upstream is that the source need not be materialised.
|
|
52
|
+
*
|
|
53
|
+
* `never` for the `data` parameter is what makes an accessor written
|
|
54
|
+
* against a CONCRETE source (`(rows: Row[], i) => rows[i]`) assignable
|
|
55
|
+
* here: parameters are contravariant, and RN's own types say `any`.
|
|
56
|
+
*/
|
|
57
|
+
getItem?: (data: never, index: number) => T;
|
|
58
|
+
getItemCount?: (data: never) => number;
|
|
42
59
|
renderItem: (info: ListRenderItemInfo<T>) => ReactElement | null;
|
|
43
60
|
keyExtractor?: (item: T, index: number) => string;
|
|
44
61
|
estimatedItemSize?: number;
|
|
45
|
-
getItemLayout?: (data:
|
|
62
|
+
getItemLayout?: (data: never, index: number) => ItemLayout;
|
|
46
63
|
windowSize?: number;
|
|
47
64
|
initialNumToRender?: number;
|
|
48
65
|
maxToRenderPerBatch?: number;
|
|
@@ -51,6 +68,29 @@ export type VirtualizedListProps<T> = Omit<ScrollViewProps, "children"> & {
|
|
|
51
68
|
inverted?: boolean;
|
|
52
69
|
refreshing?: boolean;
|
|
53
70
|
onRefresh?: () => void;
|
|
71
|
+
/**
|
|
72
|
+
* RN's per-cell wrapper. The list still decides where a cell goes — the
|
|
73
|
+
* absolute `style` and the `onLayout` that measures it are handed in and
|
|
74
|
+
* must be applied — and this component owns everything else about the
|
|
75
|
+
* container, which is how a library adds a transform or a context to every
|
|
76
|
+
* row without touching `renderItem`.
|
|
77
|
+
*
|
|
78
|
+
* `react-native-draggable-flatlist` is the reason it exists here: its whole
|
|
79
|
+
* design is a cell renderer that translates the row being dragged and puts
|
|
80
|
+
* the "am I the active cell" context around it.
|
|
81
|
+
*
|
|
82
|
+
* NOT applied to a STICKY cell (`stickyHeaderIndices`): pinning works by
|
|
83
|
+
* reordering the cell's real GTK widget, so the sticky container has to be
|
|
84
|
+
* the cell. See docs/api.md.
|
|
85
|
+
*/
|
|
86
|
+
CellRendererComponent?: ComponentType<{
|
|
87
|
+
cellKey: string;
|
|
88
|
+
index: number;
|
|
89
|
+
item: T;
|
|
90
|
+
style?: StyleProp;
|
|
91
|
+
onLayout?: (event: LayoutEvent) => void;
|
|
92
|
+
children?: ReactNode;
|
|
93
|
+
}>;
|
|
54
94
|
ItemSeparatorComponent?: ComponentType | null;
|
|
55
95
|
ListHeaderComponent?: ComponentType | ReactElement | null;
|
|
56
96
|
ListFooterComponent?: ComponentType | ReactElement | null;
|
|
@@ -9,6 +9,8 @@ import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-run
|
|
|
9
9
|
import { forwardRef, useEffect, useImperativeHandle, useLayoutEffect, useMemo, useRef, useState, } from "react";
|
|
10
10
|
import { perfAddTime, perfBurst, perfCount, perfEnabled, perfNow, } from "../perf";
|
|
11
11
|
import { ActivityIndicator } from "./activity-indicator";
|
|
12
|
+
import { registerHandleAlias } from "./measure";
|
|
13
|
+
import { scrollPhaseSink, setScrollPhaseSink } from "./scroll-phase";
|
|
12
14
|
import { ScrollView, StickySlot, } from "./scroll-view";
|
|
13
15
|
import { View } from "./view";
|
|
14
16
|
const renderAux = (component) => {
|
|
@@ -23,7 +25,26 @@ const renderAux = (component) => {
|
|
|
23
25
|
};
|
|
24
26
|
// First index whose offset-end is past `target` (binary search over prefix
|
|
25
27
|
// sums; offsets has count+1 entries).
|
|
28
|
+
//
|
|
29
|
+
// The `target <= offsets[0]` guard is RN's, not an optimisation:
|
|
30
|
+
// `elementsThatOverlapOffsets` treats the FIRST cell's start as INCLUSIVE and
|
|
31
|
+
// every later cell's as exclusive (`mid === 0 && currentOffset <
|
|
32
|
+
// scaledOffsetStart`), and that asymmetry is the whole reason a list of
|
|
33
|
+
// ZERO-LENGTH cells resolves offset 0 to index 0 there. Without it the search
|
|
34
|
+
// walks past every cell whose end is `<= target` — and a zero-length cell at
|
|
35
|
+
// `target` always is — so it lands on the END of the run and the list mounts
|
|
36
|
+
// only its last row.
|
|
37
|
+
//
|
|
38
|
+
// That is not a hypothetical shape. A `FlatList` whose cells each contain one
|
|
39
|
+
// `position: absolute` child has zero flow height in EVERY cell, which is
|
|
40
|
+
// exactly how `react-native-reanimated-dnd`'s `Sortable` renders (rows are
|
|
41
|
+
// absolutely positioned and driven by a per-frame animated `top`), and how
|
|
42
|
+
// any list that positions its own rows does. RN renders all of them; we
|
|
43
|
+
// rendered one. See docs/research/dnd-differential.md.
|
|
26
44
|
const indexAt = (offsets, target) => {
|
|
45
|
+
if (target <= offsets[0]) {
|
|
46
|
+
return 0;
|
|
47
|
+
}
|
|
27
48
|
let low = 0;
|
|
28
49
|
let high = offsets.length - 2;
|
|
29
50
|
while (low < high) {
|
|
@@ -56,8 +77,28 @@ const CellMountProbe = () => {
|
|
|
56
77
|
}, []);
|
|
57
78
|
return null;
|
|
58
79
|
};
|
|
59
|
-
const VirtualizedListInner = forwardRef(({ data, renderItem, keyExtractor, estimatedItemSize = 44, getItemLayout, windowSize = DEFAULT_WINDOW_SIZE, initialNumToRender = 10, maxToRenderPerBatch = 10, updateCellsBatchingPeriod = 50, extraData, inverted = false, refreshing = false, onRefresh, ItemSeparatorComponent, ListHeaderComponent, ListFooterComponent, ListEmptyComponent, onEndReached, onEndReachedThreshold = 0.1, onViewableItemsChanged, viewabilityConfig, onScroll, onContentSizeChange, onLayout, horizontal = false, stickyHeaderIndices, ...scrollProps }, ref) => {
|
|
60
|
-
|
|
80
|
+
const VirtualizedListInner = forwardRef(({ data, getItem, getItemCount, renderItem, keyExtractor, estimatedItemSize = 44, getItemLayout, windowSize = DEFAULT_WINDOW_SIZE, initialNumToRender = 10, maxToRenderPerBatch = 10, updateCellsBatchingPeriod = 50, extraData, inverted = false, refreshing = false, onRefresh, CellRendererComponent, ItemSeparatorComponent, ListHeaderComponent, ListFooterComponent, ListEmptyComponent, onEndReached, onEndReachedThreshold = 0.1, onViewableItemsChanged, viewabilityConfig, onScroll, onContentSizeChange, onLayout, horizontal = false, stickyHeaderIndices, ...scrollProps }, ref) => {
|
|
81
|
+
// The three reads the list makes of its data source, in the one place
|
|
82
|
+
// that knows which shape it was given. Everything below goes through
|
|
83
|
+
// them, so the windowing, the prefix sums, the viewability pass and the
|
|
84
|
+
// scroll handle are identical whether the source is an array or RN's
|
|
85
|
+
// opaque value plus accessors.
|
|
86
|
+
const source = data;
|
|
87
|
+
const count = getItemCount ? getItemCount(data) : source.length;
|
|
88
|
+
const itemAt = (index) => getItem ? getItem(data, index) : source[index];
|
|
89
|
+
const indexOfItem = (item) => {
|
|
90
|
+
if (!getItem) {
|
|
91
|
+
return source.indexOf(item);
|
|
92
|
+
}
|
|
93
|
+
// RN's own VirtualizedList scans for `scrollToItem` too — an opaque
|
|
94
|
+
// source has no index to ask.
|
|
95
|
+
for (let index = 0; index < count; index += 1) {
|
|
96
|
+
if (itemAt(index) === item) {
|
|
97
|
+
return index;
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
return -1;
|
|
101
|
+
};
|
|
61
102
|
const scrollRef = useRef(null);
|
|
62
103
|
const measured = useRef([]);
|
|
63
104
|
const [version, setVersion] = useState(0);
|
|
@@ -267,7 +308,15 @@ const VirtualizedListInner = forwardRef(({ data, renderItem, keyExtractor, estim
|
|
|
267
308
|
: { index, viewPosition, animated: params.animated };
|
|
268
309
|
scrollToAxis(offsetForIndex(index, viewPosition), params.animated);
|
|
269
310
|
};
|
|
270
|
-
|
|
311
|
+
// The handle stands for the ScrollView this list renders: `findNodeHandle`
|
|
312
|
+
// on a list resolves to it (RN resolves a FlatList's the same way), and so
|
|
313
|
+
// does `measureLayout(listRef, …)` from another view. It gains no
|
|
314
|
+
// `measure()` of its own — see the note on VirtualizedListHandle.
|
|
315
|
+
const registerAlias = (handle) => {
|
|
316
|
+
registerHandleAlias(handle, () => scrollRef.current);
|
|
317
|
+
return handle;
|
|
318
|
+
};
|
|
319
|
+
useImperativeHandle(ref, () => registerAlias({
|
|
271
320
|
// Any direct scroll cancels a pending scrollToIndex correction. The
|
|
272
321
|
// caller always speaks RN-space offsets; inverted translates the main
|
|
273
322
|
// axis into raw adjustment space.
|
|
@@ -298,7 +347,7 @@ const VirtualizedListInner = forwardRef(({ data, renderItem, keyExtractor, estim
|
|
|
298
347
|
},
|
|
299
348
|
scrollToIndex,
|
|
300
349
|
scrollToItem: ({ item, viewPosition, animated }) => {
|
|
301
|
-
const index =
|
|
350
|
+
const index = indexOfItem(item);
|
|
302
351
|
if (index >= 0) {
|
|
303
352
|
scrollToIndex({ index, viewPosition, animated });
|
|
304
353
|
}
|
|
@@ -404,7 +453,7 @@ const VirtualizedListInner = forwardRef(({ data, renderItem, keyExtractor, estim
|
|
|
404
453
|
viewable = true;
|
|
405
454
|
}
|
|
406
455
|
if (viewable) {
|
|
407
|
-
const item =
|
|
456
|
+
const item = itemAt(index);
|
|
408
457
|
eligible.set(keyOf(item, index), { item, index });
|
|
409
458
|
}
|
|
410
459
|
}
|
|
@@ -494,6 +543,24 @@ const VirtualizedListInner = forwardRef(({ data, renderItem, keyExtractor, estim
|
|
|
494
543
|
}
|
|
495
544
|
}
|
|
496
545
|
};
|
|
546
|
+
const toExposedEvent = (event) => {
|
|
547
|
+
if (!inverted) {
|
|
548
|
+
return event;
|
|
549
|
+
}
|
|
550
|
+
const raw = horizontal
|
|
551
|
+
? event.nativeEvent.contentOffset.x
|
|
552
|
+
: event.nativeEvent.contentOffset.y;
|
|
553
|
+
const exposed = Math.max(0, maxRawScroll() - raw);
|
|
554
|
+
return {
|
|
555
|
+
nativeEvent: {
|
|
556
|
+
...event.nativeEvent,
|
|
557
|
+
contentOffset: {
|
|
558
|
+
x: horizontal ? exposed : event.nativeEvent.contentOffset.x,
|
|
559
|
+
y: horizontal ? event.nativeEvent.contentOffset.y : exposed,
|
|
560
|
+
},
|
|
561
|
+
},
|
|
562
|
+
};
|
|
563
|
+
};
|
|
497
564
|
const handleScroll = (event) => {
|
|
498
565
|
const raw = horizontal
|
|
499
566
|
? event.nativeEvent.contentOffset.x
|
|
@@ -501,29 +568,25 @@ const VirtualizedListInner = forwardRef(({ data, renderItem, keyExtractor, estim
|
|
|
501
568
|
scrollY.current = raw;
|
|
502
569
|
if (inverted) {
|
|
503
570
|
exposedOffset.current = Math.max(0, maxRawScroll() - raw);
|
|
504
|
-
// The caller sees RN-space offsets: contentOffset 0 is the far end
|
|
505
|
-
// where the data starts (a chat's latest message).
|
|
506
|
-
onScroll?.({
|
|
507
|
-
nativeEvent: {
|
|
508
|
-
...event.nativeEvent,
|
|
509
|
-
contentOffset: {
|
|
510
|
-
x: horizontal
|
|
511
|
-
? exposedOffset.current
|
|
512
|
-
: event.nativeEvent.contentOffset.x,
|
|
513
|
-
y: horizontal
|
|
514
|
-
? event.nativeEvent.contentOffset.y
|
|
515
|
-
: exposedOffset.current,
|
|
516
|
-
},
|
|
517
|
-
},
|
|
518
|
-
});
|
|
519
|
-
}
|
|
520
|
-
else {
|
|
521
|
-
onScroll?.(event);
|
|
522
571
|
}
|
|
572
|
+
onScroll?.(toExposedEvent(event));
|
|
523
573
|
updateRange();
|
|
524
574
|
recomputeViewability();
|
|
525
575
|
maybeFireEndReached();
|
|
526
576
|
};
|
|
577
|
+
// Reanimated attaches one phase sink to the handler it hands us. This
|
|
578
|
+
// wrapper used to forward only the function call and silently dropped the
|
|
579
|
+
// sink, so every FlatList/VirtualizedList received onScroll but NONE of
|
|
580
|
+
// onBeginDrag/onEndDrag/momentum — direct ScrollView tests could not catch
|
|
581
|
+
// it. Carry the seam through the composite, translating inverted offsets
|
|
582
|
+
// exactly as the ordinary event path does.
|
|
583
|
+
const upstreamPhaseSink = scrollPhaseSink(onScroll);
|
|
584
|
+
if (upstreamPhaseSink) {
|
|
585
|
+
setScrollPhaseSink(handleScroll, {
|
|
586
|
+
wants: (phase) => upstreamPhaseSink.wants(phase),
|
|
587
|
+
deliver: (phase, event) => upstreamPhaseSink.deliver(phase, toExposedEvent(event)),
|
|
588
|
+
});
|
|
589
|
+
}
|
|
527
590
|
const handleLayout = (event) => {
|
|
528
591
|
onLayout?.(event);
|
|
529
592
|
viewportH.current = horizontal
|
|
@@ -590,7 +653,7 @@ const VirtualizedListInner = forwardRef(({ data, renderItem, keyExtractor, estim
|
|
|
590
653
|
}
|
|
591
654
|
}
|
|
592
655
|
const renderCell = (index) => {
|
|
593
|
-
const item =
|
|
656
|
+
const item = itemAt(index);
|
|
594
657
|
const key = keyOf(item, index);
|
|
595
658
|
// Vertical cells stretch across the width and sit at their offset;
|
|
596
659
|
// horizontal cells stretch across the height and take their own
|
|
@@ -605,6 +668,9 @@ const VirtualizedListInner = forwardRef(({ data, renderItem, keyExtractor, estim
|
|
|
605
668
|
if (stickySorted.includes(index)) {
|
|
606
669
|
return (_jsx(StickySlot, { stickyKey: `cell-${key}`, top: cellStart(index), style: cellStyle, onLayout: measure, children: body }, key));
|
|
607
670
|
}
|
|
671
|
+
if (CellRendererComponent) {
|
|
672
|
+
return (_jsx(CellRendererComponent, { cellKey: key, index: index, item: item, style: cellStyle, onLayout: measure, children: body }, key));
|
|
673
|
+
}
|
|
608
674
|
return (_jsx(View, { style: cellStyle, onLayout: measure, children: body }, key));
|
|
609
675
|
};
|
|
610
676
|
const cells = [];
|