@applicaster/zapp-react-native-utils 12.0.0-alpha.4337072244 → 12.0.0-alpha.4354608902

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.
Files changed (65) hide show
  1. package/analyticsUtils/AnalyticsEvents/index.ts +7 -0
  2. package/analyticsUtils/AnalyticsEvents/sendShareEvent.ts +21 -0
  3. package/analyticsUtils/analyticsPlugins.ts +25 -0
  4. package/analyticsUtils/events.ts +6 -0
  5. package/analyticsUtils/index.tsx +6 -0
  6. package/appUtils/HooksManager/{Hook.js → Hook.ts} +35 -23
  7. package/appUtils/HooksManager/{constants.js → constants.ts} +1 -1
  8. package/appUtils/HooksManager/{index.js → index.ts} +118 -111
  9. package/appUtils/HooksManager/types.ts +116 -0
  10. package/appUtils/RiverFocusManager/index.js +17 -12
  11. package/appUtils/accessibilityManager/const.ts +50 -0
  12. package/appUtils/accessibilityManager/hooks.ts +31 -0
  13. package/appUtils/accessibilityManager/index.ts +150 -0
  14. package/appUtils/accessibilityManager/logger.ts +5 -0
  15. package/appUtils/focusManager/__tests__/__snapshots__/focusManager.test.js.snap +1 -2
  16. package/appUtils/focusManager/__tests__/index.test.ts +1 -2
  17. package/appUtils/focusManager/index.ts +7 -73
  18. package/appUtils/focusManager/treeDataStructure/Tree/index.js +2 -3
  19. package/appUtils/focusManager/treeDataStructure/Utils/index.js +7 -8
  20. package/appUtils/focusManager/utils/index.ts +8 -2
  21. package/appUtils/focusManagerAux/index.ts +76 -0
  22. package/appUtils/focusManagerAux/utils/index.ts +100 -0
  23. package/appUtils/{index.js → index.ts} +2 -0
  24. package/appUtils/keyCodes/{index.js → index.ts} +2 -0
  25. package/appUtils/keyCodes/keys/index.ts +3 -0
  26. package/appUtils/keyCodes/{keys.android.js → keys/keyEventMapper.ts} +0 -19
  27. package/appUtils/keyCodes/keys/keys.android.ts +18 -0
  28. package/appUtils/keyCodes/keys/keys.ios.ts +25 -0
  29. package/appUtils/keyCodes/keys/keys.ts +15 -0
  30. package/appUtils/keyCodes/{keys.web.js → keys/keys.web.ts} +8 -0
  31. package/appUtils/keyCodes/{keysByPlatform.js → keys/keysByPlatform.ts} +11 -1
  32. package/appUtils/platform/const.ts +25 -0
  33. package/appUtils/platform/index.ts +3 -0
  34. package/appUtils/platform/platformUtils.ts +171 -0
  35. package/appUtils/playerManager/conts.ts +1 -0
  36. package/appUtils/playerManager/index.ts +11 -5
  37. package/appUtils/playerManager/nativePlayerManager.ts +12 -0
  38. package/appUtils/playerManager/player.ts +9 -3
  39. package/appUtils/playerManager/playerNative.ts +5 -14
  40. package/appUtils/playerManager/usePlayerControllerSetup.tsx +7 -1
  41. package/booleanUtils/index.ts +4 -4
  42. package/domUtils/{cookieManager.js → cookieManager.ts} +1 -2
  43. package/functionUtils/index.ts +15 -11
  44. package/keyboardState/index.ts +0 -0
  45. package/modalState/index.ts +1 -5
  46. package/navigationUtils/index.ts +62 -5
  47. package/package.json +2 -2
  48. package/pluginUtils/index.ts +9 -0
  49. package/reactHooks/cell-click/__tests__/index.test.js +2 -1
  50. package/reactHooks/cell-click/index.ts +1 -1
  51. package/reactHooks/feed/__tests__/useFeedRefresh.test.tsx +6 -2
  52. package/reactHooks/feed/useFeedRefresh.tsx +9 -7
  53. package/reactHooks/navigation/__tests__/index.test.tsx +11 -8
  54. package/reactHooks/navigation/index.ts +53 -72
  55. package/reactHooks/screen/useScreenContext.ts +1 -2
  56. package/reactUtils/index.ts +91 -0
  57. package/appUtils/focusManager/FocusableEvents.ts +0 -8
  58. package/appUtils/focusManager/treeDataStructure/Utils/__tests__/Utils_android.test.js +0 -1094
  59. package/appUtils/focusManager/treeDataStructure/Utils/index.android.js +0 -261
  60. package/appUtils/keyCodes/keys.ios.js +0 -46
  61. /package/appUtils/HooksManager/{logger.js → logger.ts} +0 -0
  62. /package/appUtils/{directionHelper.js → directionHelper.ts} +0 -0
  63. /package/appUtils/keyCodes/{androidTVKeys.js → androidTVKeys.ts} +0 -0
  64. /package/appUtils/{localizationsHelper.js → localizationsHelper.ts} +0 -0
  65. /package/domUtils/{logger.js → logger.ts} +0 -0
@@ -4,6 +4,7 @@ import { useEffect } from "react";
4
4
  import { playerManager } from "./index";
5
5
  import { useValidatePlayerConfig } from "../../playerUtils/useValidatePlayerConfig";
6
6
  import { PlayerRole } from "./conts";
7
+ import { isAppleTV } from "@applicaster/zapp-react-native-ui-components/Helpers/Platform";
7
8
 
8
9
  // TODO: Rename to ControllerType
9
10
  export const usePlayerControllerSetup = ({
@@ -34,10 +35,14 @@ export const usePlayerControllerSetup = ({
34
35
  useValidatePlayerConfig(config);
35
36
 
36
37
  useEffect(() => {
38
+ const newConfig = isAppleTV()
39
+ ? { supports_native_controls: true, ...config }
40
+ : config;
41
+
37
42
  const newPlayerController = new ControllerType({
38
43
  player: ref,
39
44
  listener: props as any,
40
- config,
45
+ config: newConfig,
41
46
  playerId,
42
47
  entry,
43
48
  playerPluginId: pluginId,
@@ -67,6 +72,7 @@ export const usePlayerControllerSetup = ({
67
72
 
68
73
  return () => {
69
74
  playerManager.unregisterPlayer(playerId);
75
+ playerController.destroy?.();
70
76
  };
71
77
  }, [playerId, playerController]);
72
78
 
@@ -1,7 +1,7 @@
1
- import * as R from "ramda";
1
+ import { is, toLower } from "ramda";
2
2
 
3
3
  export const toBoolean = (value: any): boolean | undefined => {
4
- if (R.is(Boolean, value)) {
4
+ if (is(Boolean, value)) {
5
5
  return value;
6
6
  }
7
7
 
@@ -17,12 +17,12 @@ export const toBooleanWithDefaultTrue = toBooleanWithDefault(true);
17
17
 
18
18
  export const toBooleanWithDefaultFalse = toBooleanWithDefault(false);
19
19
 
20
- export const isTrue = (value: any): boolean => {
20
+ export const isTrue = (value: unknown): boolean => {
21
21
  if (value === true) {
22
22
  return true;
23
23
  }
24
24
 
25
- if (R.is(String, value) && value.toLowerCase() === "true") {
25
+ if (is(String, value) && toLower(value) === "true") {
26
26
  return true;
27
27
  }
28
28
 
@@ -2,7 +2,6 @@ import { domUtilsLogger } from "./logger";
2
2
 
3
3
  /**
4
4
  * Gets an object of cookies and sets them on the DOM.
5
- * @param {Object} cookies selected data key for label.
6
5
  */
7
6
  export function setCookies(cookies): void {
8
7
  const cookieKeys = Object.keys(cookies);
@@ -25,7 +24,7 @@ export function setCookies(cookies): void {
25
24
  /**
26
25
  * Gets cookies set on DOM
27
26
  */
28
- export function getCookies(): Object {
27
+ export function getCookies(): typeof document.cookie {
29
28
  try {
30
29
  if (document) {
31
30
  return document.cookie;
@@ -73,12 +73,12 @@ type SubscriberFn<T> = (
73
73
 
74
74
  export type EventHandlerFn<T> = (event: string, ...args: unknown[]) => T;
75
75
 
76
- type SubscriberObj = Partial<{
77
- on?: SubscriberFn<SubscriberObj>;
78
- invokeHandler: EventHandlerFn<SubscriberObj>;
79
- removeHandler: EventHandlerFn<SubscriberObj>;
80
- handlers: Record<string, SubscriberFn<SubscriberObj>[] | []>;
81
- }>;
76
+ export type SubscriberObj<T extends {} = {}> = {
77
+ on: SubscriberFn<SubscriberObj<T>>;
78
+ invokeHandler: EventHandlerFn<SubscriberObj<T>>;
79
+ removeHandler: EventHandlerFn<SubscriberObj<T>>;
80
+ handlers: Record<string, SubscriberFn<SubscriberObj<T>>[] | []>;
81
+ } & T;
82
82
 
83
83
  export const clearObject = (object: { [key: string]: unknown }) =>
84
84
  Object.keys(object).forEach((key) => delete object[key]);
@@ -88,7 +88,11 @@ export const clearObject = (object: { [key: string]: unknown }) =>
88
88
  * @param {Object} obj to add the subscription feature on
89
89
  * @returns {Object} subscriber object
90
90
  */
91
- export function subscriber(obj: SubscriberObj = {}): SubscriberObj {
91
+ export function subscriber<T extends Partial<SubscriberObj> = {}>(
92
+ _obj: T = {} as T
93
+ ): SubscriberObj {
94
+ const obj: T = _obj;
95
+
92
96
  if (!obj.handlers) {
93
97
  obj.handlers = {};
94
98
  }
@@ -134,7 +138,7 @@ export function subscriber(obj: SubscriberObj = {}): SubscriberObj {
134
138
  | SubscriberFn<SubscriberObj>[]
135
139
  | [];
136
140
 
137
- return obj;
141
+ return obj as SubscriberObj;
138
142
  };
139
143
 
140
144
  /**
@@ -150,16 +154,16 @@ export function subscriber(obj: SubscriberObj = {}): SubscriberObj {
150
154
 
151
155
  R.compose(R.forEach(callHandlerWithDispose), R.propOr([], event))(handlers);
152
156
 
153
- return obj;
157
+ return obj as SubscriberObj;
154
158
  };
155
159
 
156
160
  obj.removeHandler = function (event, handler) {
157
161
  handlers[event] = R.reject(R.equals(handler), handlers[event]);
158
162
 
159
- return obj;
163
+ return obj as SubscriberObj;
160
164
  };
161
165
 
162
- return obj;
166
+ return obj as SubscriberObj;
163
167
  }
164
168
 
165
169
  /**
File without changes
@@ -31,11 +31,7 @@ export const useModalStore = create<ModalStore>((set) => ({
31
31
  set((state) => ({
32
32
  modalState: { ...state.modalState, ...newState },
33
33
  })),
34
- openModal: ({
35
- item,
36
- options = {},
37
- props = { screenData: {} },
38
- }: OpenModalArg) =>
34
+ openModal: ({ item, options = {}, props }: OpenModalArg) =>
39
35
  set({
40
36
  modalState: {
41
37
  visible: true,
@@ -324,7 +324,13 @@ export function getPathAttributes({
324
324
  * @param {object} rivers
325
325
  * @returns {object}
326
326
  */
327
- export function getRiverFromRoute({ route, rivers }) {
327
+ export function getRiverFromRoute({
328
+ route,
329
+ rivers,
330
+ }: {
331
+ route: string;
332
+ rivers: Record<string, ZappRiver>;
333
+ }) {
328
334
  if (!route) {
329
335
  return null;
330
336
  }
@@ -437,7 +443,7 @@ export const runZappHooksForEntry = async (
437
443
 
438
444
  let success;
439
445
  let payload;
440
- const rivers = appStore.get("rivers");
446
+ const rivers: Record<string, ZappRiver> = appStore.get("rivers");
441
447
  const plugins = appStore.get("plugins");
442
448
  const appData = appStore.get("appData");
443
449
 
@@ -492,13 +498,16 @@ export const runZappHooksForEntry = async (
492
498
  payload = _payload;
493
499
  };
494
500
 
495
- HooksManager(hooksOptions)
501
+ const hooksManager = HooksManager(hooksOptions);
502
+
503
+ hooksManager.subscriber
496
504
  .on(HOOKS_EVENTS.PRESENT_SCREEN_HOOK, handleHookPresent)
497
505
  .on(HOOKS_EVENTS.START_BACKGROUND_HOOK, handleBackgroundHook)
498
506
  .on(HOOKS_EVENTS.ERROR, onFinished(false))
499
507
  .on(HOOKS_EVENTS.CANCEL, onFinished(false))
500
- .on(HOOKS_EVENTS.COMPLETE, onFinished(true))
501
- .handleHooks(entry);
508
+ .on(HOOKS_EVENTS.COMPLETE, onFinished(true));
509
+
510
+ hooksManager.handleHooks(entry);
502
511
 
503
512
  // eslint-disable-next-line no-unmodified-loop-condition
504
513
  while (success === undefined) {
@@ -592,3 +601,51 @@ export function isMenuDisabled(
592
601
  export function routeIsPlayerScreen(currentRoute) {
593
602
  return currentRoute?.includes("/playable");
594
603
  }
604
+
605
+ export const getNavBarProps =
606
+ (currentRiver: ZappRiver, pathname: string, title: string) => () => {
607
+ const props = getNavigationPropsV2({
608
+ currentRiver,
609
+ title,
610
+ category: "nav_bar",
611
+ });
612
+
613
+ if (props) {
614
+ return {
615
+ ...props,
616
+ id: pathname,
617
+ pathname: pathname,
618
+ };
619
+ }
620
+
621
+ return null;
622
+ };
623
+
624
+ export const findMenuPlugin = (
625
+ navigations: ZappNavigation[],
626
+ plugins
627
+ ): QuickBrickPlugin => {
628
+ return resolveNavigationPlugin({
629
+ category: "menu",
630
+ navigations,
631
+ plugins,
632
+ }) as QuickBrickPlugin;
633
+ };
634
+
635
+ export const shouldNavBarDisplayMenu = (currentRiver: ZappRiver, plugins) =>
636
+ findMenuPlugin(currentRiver.navigations, plugins)?.identifier ===
637
+ "quick_brick_side_menu" ||
638
+ currentRiver?.navigations.findIndex(
639
+ (nav) => nav.category === "nav_bar" && nav.general?.override_menu_target
640
+ ) > -1;
641
+
642
+ export const getScreenId = (
643
+ screenData: LegacyNavigationScreenData,
644
+ fallbackRiver: ZappRiver
645
+ ) => {
646
+ return screenData?.targetScreen
647
+ ? screenData?.targetScreen?.id ?? fallbackRiver.id
648
+ : "screen_id" in screenData
649
+ ? screenData.screen_id
650
+ : fallbackRiver.id;
651
+ };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@applicaster/zapp-react-native-utils",
3
- "version": "12.0.0-alpha.4337072244",
3
+ "version": "12.0.0-alpha.4354608902",
4
4
  "description": "Applicaster Zapp React Native utilities package",
5
5
  "main": "index.js",
6
6
  "types": "index.d.ts",
@@ -28,7 +28,7 @@
28
28
  },
29
29
  "homepage": "https://github.com/applicaster/quickbrick#readme",
30
30
  "dependencies": {
31
- "@applicaster/applicaster-types": "12.0.0-alpha.4337072244",
31
+ "@applicaster/applicaster-types": "12.0.0-alpha.4354608902",
32
32
  "buffer": "^5.2.1",
33
33
  "camelize": "^1.0.0",
34
34
  "create-react-context": "^0.2.3",
@@ -245,3 +245,12 @@ export function generateManifest({ manifestConfig, version }) {
245
245
 
246
246
  return manifestConfig({ platform, version });
247
247
  }
248
+
249
+ const getPluginType = R.pathOr("unknown_plugin_type", [
250
+ "state",
251
+ "screen",
252
+ "plugin_type",
253
+ ]);
254
+
255
+ export const isPlayerPlugin = (routeState): boolean =>
256
+ getPluginType(routeState) === "player";
@@ -8,6 +8,7 @@ import { waitFor } from "@testing-library/react-native";
8
8
  const navigator = {
9
9
  getPathname: () => "pathnameMock",
10
10
  push: jest.fn(),
11
+ data: {},
11
12
  };
12
13
 
13
14
  jest.mock("@applicaster/zapp-react-native-utils/reactHooks/navigation", () => ({
@@ -30,7 +31,7 @@ jest.mock("@applicaster/zapp-react-native-ui-components/Contexts", () => ({
30
31
  },
31
32
  }));
32
33
 
33
- const { useCellClick } = require("..");
34
+ const { useCellClick } = require("../");
34
35
 
35
36
  const mockProps = {
36
37
  item: {},
@@ -83,7 +83,7 @@ export const useCellClick = ({ component, zappPipesData, item }: Props) => {
83
83
  if (isFunction(onCellTap)) {
84
84
  onCellTap?.(selectedItem, _index);
85
85
  } else {
86
- if (currentRoute === pathname || pathname === "videoModal") {
86
+ if (currentRoute === pathname || pathname.includes("video-modal")) {
87
87
  const targetScreen = component?.data?.target;
88
88
 
89
89
  push(
@@ -1,9 +1,13 @@
1
1
  import { renderHook } from "@testing-library/react-hooks";
2
2
 
3
- import { useFeedRefresh, feedRefreshLogger } from "../";
4
-
5
3
  jest.useFakeTimers();
6
4
 
5
+ jest.mock("@applicaster/zapp-react-native-utils/reactHooks/navigation", () => ({
6
+ useIsScreenActive: () => true,
7
+ }));
8
+
9
+ const { useFeedRefresh, feedRefreshLogger } = require("..");
10
+
7
11
  describe("useFeedRefresh", () => {
8
12
  const reloadData = jest.fn();
9
13
 
@@ -1,7 +1,8 @@
1
1
  import * as React from "react";
2
- import * as R from "ramda";
2
+ import { path, max } from "ramda";
3
3
  import { isTrue } from "@applicaster/zapp-react-native-utils/booleanUtils";
4
4
  import { toNumberWithDefault } from "@applicaster/zapp-react-native-utils/numberUtils";
5
+ import { useIsScreenActive } from "@applicaster/zapp-react-native-utils/reactHooks/navigation";
5
6
 
6
7
  import { reactHooksLogger } from "../logger";
7
8
  import { ReloadDataFunction } from "./useFeedLoader";
@@ -18,9 +19,8 @@ const minimumRefreshingInterval = 5;
18
19
  const defaultRefreshInterval = 60;
19
20
 
20
21
  export const useFeedRefresh = ({ reloadData, component }: Props): void => {
21
- const enable_data_refreshing = R.path(
22
- ["rules", "enable_data_refreshing"],
23
- component
22
+ const isDataRefreshingEnabled = isTrue(
23
+ path(["rules", "enable_data_refreshing"], component)
24
24
  );
25
25
 
26
26
  const refreshing_interval = toNumberWithDefault(
@@ -29,10 +29,12 @@ export const useFeedRefresh = ({ reloadData, component }: Props): void => {
29
29
  );
30
30
 
31
31
  const refreshingIntervalInMilliseconds =
32
- R.max(refreshing_interval, minimumRefreshingInterval) * 1000;
32
+ max(refreshing_interval, minimumRefreshingInterval) * 1000;
33
+
34
+ const isScreenActive = useIsScreenActive();
33
35
 
34
36
  React.useEffect(() => {
35
- if (isTrue(enable_data_refreshing) && refreshing_interval) {
37
+ if (isDataRefreshingEnabled && refreshing_interval && isScreenActive) {
36
38
  if (refreshing_interval < minimumRefreshingInterval) {
37
39
  feedRefreshLogger.warning({
38
40
  message: `You set your feed refresh interval to ${refreshing_interval} when minimum value is ${minimumRefreshingInterval}seconds.Your feed will refresh after ${minimumRefreshingInterval}seconds.`,
@@ -59,5 +61,5 @@ export const useFeedRefresh = ({ reloadData, component }: Props): void => {
59
61
  clearInterval(refreshInterval);
60
62
  };
61
63
  }
62
- }, [reloadData]);
64
+ }, [reloadData, isScreenActive]);
63
65
  };
@@ -1,12 +1,13 @@
1
1
  import React from "react";
2
2
  import { PathnameContext } from "@applicaster/zapp-react-native-ui-components/Contexts/PathnameContext";
3
3
  import { renderHook } from "@testing-library/react-hooks";
4
- import { useRoute, isNavBarVisible } from "../";
4
+ import { isNavBarVisible, useRoute } from "../";
5
5
  import { Provider } from "react-redux";
6
6
  import configureMockStore from "redux-mock-store";
7
7
  import { NavigationContext } from "@applicaster/zapp-react-native-ui-components/Contexts/NavigationContext";
8
8
  import { ZappHookModalContext } from "@applicaster/zapp-react-native-ui-components/Contexts";
9
9
  import { ROUTE_TYPES } from "@applicaster/zapp-react-native-utils/navigationUtils/routeTypes";
10
+ import { ScreenDataContext } from "@applicaster/zapp-react-native-ui-components/Contexts/ScreenDataContext";
10
11
 
11
12
  const plugins = [];
12
13
 
@@ -100,13 +101,15 @@ const mainStackWrapper = ({
100
101
  pathname = homeStack.route,
101
102
  }) => (
102
103
  <Provider store={store}>
103
- <NavigationContext.Provider
104
- value={{ ...mainStackNavigator, ...navigator, currentRoute: pathname }}
105
- >
106
- <PathnameContext.Provider value={pathname}>
107
- {children}
108
- </PathnameContext.Provider>
109
- </NavigationContext.Provider>
104
+ <ScreenDataContext.Provider value={homeStack.state}>
105
+ <NavigationContext.Provider
106
+ value={{ ...mainStackNavigator, ...navigator, currentRoute: pathname }}
107
+ >
108
+ <PathnameContext.Provider value={pathname}>
109
+ {children}
110
+ </PathnameContext.Provider>
111
+ </NavigationContext.Provider>
112
+ </ScreenDataContext.Provider>
110
113
  </Provider>
111
114
  );
112
115
 
@@ -1,7 +1,7 @@
1
1
  /* eslint-disable @typescript-eslint/no-use-before-define */
2
2
  /* eslint max-len: off */
3
3
 
4
- import React, { useEffect, useMemo } from "react";
4
+ import React, { useContext, useEffect, useMemo } from "react";
5
5
  import { BackHandler, InteractionManager, NativeModules } from "react-native";
6
6
  import { useSafeAreaInsets } from "react-native-safe-area-context";
7
7
 
@@ -12,7 +12,11 @@ import {
12
12
  import { HooksManager } from "@applicaster/zapp-react-native-utils/appUtils/HooksManager";
13
13
 
14
14
  import { legacyScreenData } from "@applicaster/quick-brick-core/App/NavigationProvider/utils";
15
- import { LONG_KEY_PRESS_TIMEOUT } from "@applicaster/quick-brick-core/const";
15
+ import {
16
+ LONG_KEY_PRESS_TIMEOUT,
17
+ QUICK_BRICK_NAVBAR,
18
+ QUICK_BRICK_CONTENT,
19
+ } from "@applicaster/quick-brick-core/const";
16
20
  import { useZappHooksModalState } from "@applicaster/zapp-react-dom-ui-components/Components/ZappHooksModal/ZappHooksModal";
17
21
  import { ZappHookModalContext } from "@applicaster/zapp-react-native-ui-components/Contexts";
18
22
  import { PathnameContext } from "@applicaster/zapp-react-native-ui-components/Contexts/PathnameContext";
@@ -27,10 +31,11 @@ import { platformSelect } from "../../reactUtils";
27
31
  import { useConnectionInfo } from "../connection";
28
32
  import { getTargetScreenData } from "../screen/useTargetScreenData";
29
33
 
30
- import { isTV } from "@applicaster/zapp-react-native-utils/reactUtils";
34
+ import { isTV, isWeb } from "@applicaster/zapp-react-native-utils/reactUtils";
31
35
  import { useNavbarState } from "../screen";
32
36
  import { useNavigation } from "./useNavigation";
33
37
  import { useModalStore } from "../../modalState";
38
+ import { ScreenDataContext } from "@applicaster/zapp-react-native-ui-components/Contexts/ScreenDataContext";
34
39
 
35
40
  export { useNavigation } from "./useNavigation";
36
41
 
@@ -73,6 +78,10 @@ export function isNavBarVisible(
73
78
  return false;
74
79
  }
75
80
 
81
+ if (screenData?.plugin_type === "login" && isTV()) {
82
+ return false;
83
+ }
84
+
76
85
  /* Match if screen is Hook */
77
86
  if (route.startsWith("/hooks/")) {
78
87
  const module = screenData?.module;
@@ -146,16 +155,8 @@ export const useRoute = (): {
146
155
  pathname: string;
147
156
  } => {
148
157
  const pathname = usePathname() || "";
149
-
150
- /**
151
- * compose `useRoute()` output data
152
- */
153
- const composeRouteData = (screenData: VariousScreenData) => ({
154
- screenData,
155
- pathname,
156
- });
157
-
158
158
  const navigator = useNavigation();
159
+ const screenDataContext = legacyScreenData(useContext(ScreenDataContext));
159
160
 
160
161
  const { plugins, contentTypes, rivers } = usePickFromState([
161
162
  "plugins",
@@ -163,10 +164,11 @@ export const useRoute = (): {
163
164
  "contentTypes",
164
165
  ]);
165
166
 
166
- const currentStack = navigator.getStackForPathname(pathname);
167
167
  const { modalState } = useModalStore();
168
168
  const hookModalState = useZappHooksModalState();
169
+
169
170
  const modalScreenData = modalState.screen;
171
+
170
172
  const hookModalScreenData = hookModalState.state.screenData?.payload;
171
173
 
172
174
  const videoModalScreenData =
@@ -183,15 +185,6 @@ export const useRoute = (): {
183
185
  plugins
184
186
  );
185
187
 
186
- const currentRouteScreenData = legacyScreenData(
187
- {
188
- screen: currentStack?.state?.screen ?? navigator.data?.screen ?? {},
189
- entry: currentStack?.state?.entry ?? {},
190
- } as NavigationScreenData,
191
-
192
- plugins
193
- );
194
-
195
188
  // There are 4 route scenarios
196
189
  // For regular screens take date from navigator stack.
197
190
  // is path is model grab screenData from modal state
@@ -200,63 +193,30 @@ export const useRoute = (): {
200
193
  // if path is hook grab screenData from screenData
201
194
 
202
195
  if (isModalPathname(pathname)) {
203
- return composeRouteData(modalScreenData ?? ({} as ZappEntry));
196
+ const screenData = modalScreenData ?? ({} as ZappEntry);
197
+
198
+ return { screenData, pathname };
204
199
  }
205
200
 
206
201
  if (isVideoModalPathname(pathname)) {
207
- return composeRouteData(videoModalScreenData as LegacyNavigationScreenData);
202
+ const screenData = videoModalScreenData as LegacyNavigationScreenData;
203
+
204
+ return { screenData, pathname };
208
205
  }
209
206
 
210
207
  if (isHookModalPathname(pathname)) {
211
- return composeRouteData(hookModalScreenData);
208
+ const screenData = hookModalScreenData;
209
+
210
+ return { screenData, pathname };
212
211
  }
213
212
 
214
213
  if (isHookPathname(pathname)) {
215
- /**
216
- * HACK
217
- *
218
- * This condition relies on hacky approach to get the current hook screen data
219
- * using navigator.screenData for some cases.
220
- * This is used when hook is in sequence.
221
- */
222
-
223
- // case 1: stack not yet updated in navigator context, but navigator.screenData is updated already.
224
- if (!currentStack) {
225
- return composeRouteData(navigator.screenData);
226
- }
227
-
228
- const isValidHookInCurrentRouteScreenData =
229
- "hookPlugin" in currentRouteScreenData &&
230
- !!currentRouteScreenData.hookPlugin?.module;
231
-
232
- let screenData;
233
-
234
- // case 2: stack has valid hook data
235
- if (isValidHookInCurrentRouteScreenData) {
236
- screenData = currentRouteScreenData;
237
- }
238
-
239
- const navigatorScreenData = navigator.screenData as NavigatorEntry;
240
-
241
- // case 3: current hookPlugin is missing weight, but navigator.screenData has weight, use navigator.screenData
242
- if (
243
- screenData.hookPlugin.identifier ===
244
- navigatorScreenData?.hookPlugin?.identifier &&
245
- !screenData.hookPlugin?.weight &&
246
- navigatorScreenData?.hookPlugin?.weight
247
- ) {
248
- screenData = navigator.screenData;
249
- }
250
-
251
- return composeRouteData(screenData);
214
+ return { screenData: screenDataContext, pathname };
252
215
  }
253
216
 
254
- // case 1: stack not yet updated in navigator context, but navigator.screenData is updated already.
255
- if (!currentStack) {
256
- return composeRouteData(navigator.screenData);
257
- }
217
+ const screenData = screenDataContext;
258
218
 
259
- return composeRouteData(currentRouteScreenData);
219
+ return { screenData, pathname };
260
220
  };
261
221
 
262
222
  type Callbacks = Partial<{
@@ -360,16 +320,19 @@ export const useZappHooksForEntry = (
360
320
  callbacks?.handleHookComplete?.(props);
361
321
  };
362
322
 
363
- const hookManager = HooksManager(hooksOptions)
323
+ const hookManager = HooksManager(hooksOptions);
324
+
325
+ hookManager.subscriber
364
326
  .on(HOOKS_EVENTS.PRESENT_SCREEN_HOOK, handleHookPresent)
365
327
  .on(HOOKS_EVENTS.ERROR, handleHookError)
366
328
  .on(HOOKS_EVENTS.CANCEL, handleHookCancel)
367
329
  .on(HOOKS_EVENTS.START_BACKGROUND_HOOK, handleBackgroundHook)
368
- .on(HOOKS_EVENTS.COMPLETE, handleHookComplete)
369
- .handleHooks(entry);
330
+ .on(HOOKS_EVENTS.COMPLETE, handleHookComplete);
331
+
332
+ hookManager.handleHooks(entry);
370
333
 
371
334
  return () => {
372
- hookManager
335
+ hookManager.subscriber
373
336
  .removeHandler(HOOKS_EVENTS.PRESENT_SCREEN_HOOK, handleHookPresent)
374
337
  .removeHandler(HOOKS_EVENTS.ERROR, handleHookError)
375
338
  .removeHandler(HOOKS_EVENTS.CANCEL, handleHookCancel)
@@ -506,8 +469,26 @@ export const useUniqueRouteSuffix = (): Return => {
506
469
  const suffix = `currentRoute:${currentRoute}_pathname:${pathname}`;
507
470
 
508
471
  const withUniqueRouteSuffix = React.useCallback((prefix: string) => {
509
- return `${prefix}___${suffix}`;
472
+ if (isWeb()) {
473
+ // we should use extended route prefix only on Web, where we have stack-navigator
474
+ return `${prefix}___${suffix}`;
475
+ }
476
+
477
+ // for other platforms use previous version
478
+ return prefix;
510
479
  }, []);
511
480
 
512
481
  return withUniqueRouteSuffix;
513
482
  };
483
+
484
+ export const useNavbarId = () => {
485
+ const withUniqueRouteSuffix = useUniqueRouteSuffix();
486
+
487
+ return withUniqueRouteSuffix(QUICK_BRICK_NAVBAR);
488
+ };
489
+
490
+ export const useContentId = () => {
491
+ const withUniqueRouteSuffix = useUniqueRouteSuffix();
492
+
493
+ return withUniqueRouteSuffix(QUICK_BRICK_CONTENT);
494
+ };
@@ -5,7 +5,7 @@ import { useNestedNavigationContext } from "@applicaster/zapp-react-native-ui-co
5
5
  import { useNavigation } from "../navigation/useNavigation";
6
6
 
7
7
  import { ScreenContext } from "@applicaster/zapp-react-native-ui-components/Contexts/ScreenContext";
8
- import { ScreenDataContext } from "@applicaster/zapp-react-native-ui-components/Components/Layout/TV";
8
+ import { ScreenDataContext } from "@applicaster/zapp-react-native-ui-components/Contexts/ScreenDataContext";
9
9
 
10
10
  export function useScreenContextV2() {
11
11
  return useContext(ScreenContext);
@@ -45,7 +45,6 @@ export function useSetNavbarState() {
45
45
 
46
46
  export function useScreenContext(): NavigationScreenData {
47
47
  const navigator = useNavigation();
48
-
49
48
  const screenData = useContext(ScreenDataContext);
50
49
 
51
50
  const modalScreenData = navigator?.modalData;