@applicaster/zapp-react-native-utils 15.0.0-rc.1 → 15.0.0-rc.100
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/actionsExecutor/ActionExecutorContext.tsx +3 -6
- package/actionsExecutor/feedDecorator.ts +6 -6
- package/adsUtils/__tests__/createVMAP.test.ts +419 -0
- package/adsUtils/index.ts +2 -2
- package/analyticsUtils/AnalyticPlayerListener.ts +5 -2
- package/analyticsUtils/README.md +1 -1
- package/analyticsUtils/analyticsMapper.ts +10 -2
- package/appDataUtils/__tests__/urlScheme.test.ts +678 -0
- package/appUtils/HooksManager/__tests__/__snapshots__/hooksManager.test.js.snap +0 -188
- package/appUtils/HooksManager/__tests__/hooksManager.test.js +16 -2
- package/appUtils/HooksManager/index.ts +10 -10
- package/appUtils/RiverFocusManager/{index.js → index.ts} +25 -18
- package/appUtils/accessibilityManager/__tests__/utils.test.ts +360 -0
- package/appUtils/accessibilityManager/const.ts +4 -0
- package/appUtils/accessibilityManager/hooks.ts +20 -13
- package/appUtils/accessibilityManager/index.ts +28 -1
- package/appUtils/accessibilityManager/utils.ts +59 -8
- package/appUtils/contextKeysManager/__tests__/getKeys/failure.test.ts +7 -2
- package/appUtils/contextKeysManager/__tests__/getKeys/success.test.ts +48 -0
- package/appUtils/contextKeysManager/contextResolver.ts +51 -22
- package/appUtils/contextKeysManager/index.ts +65 -10
- package/appUtils/focusManager/__tests__/__snapshots__/focusManager.test.js.snap +4 -0
- package/appUtils/focusManager/index.ios.ts +59 -3
- package/appUtils/focusManagerAux/utils/index.ios.ts +122 -0
- package/appUtils/focusManagerAux/utils/index.ts +19 -1
- package/appUtils/focusManagerAux/utils/utils.ios.ts +231 -0
- package/appUtils/keyCodes/keys/keys.web.ts +1 -4
- package/appUtils/orientationHelper.ts +2 -4
- package/appUtils/platform/platformUtils.ts +117 -18
- package/appUtils/playerManager/OverlayObserver/OverlaysObserver.ts +94 -4
- package/appUtils/playerManager/OverlayObserver/utils.ts +32 -20
- package/appUtils/playerManager/conts.ts +21 -0
- package/appUtils/playerManager/player.ts +4 -0
- package/appUtils/playerManager/playerNative.ts +29 -16
- package/appUtils/playerManager/usePlayerState.tsx +14 -2
- package/arrayUtils/__tests__/allTruthy.test.ts +24 -0
- package/arrayUtils/__tests__/anyThruthy.test.ts +24 -0
- package/arrayUtils/index.ts +5 -0
- package/cellUtils/index.ts +32 -0
- package/cloudEventsUtils/__tests__/index.test.ts +529 -0
- package/cloudEventsUtils/index.ts +65 -1
- package/configurationUtils/__tests__/imageSrcFromMediaItem.test.ts +38 -0
- package/configurationUtils/__tests__/manifestKeyParser.test.ts +26 -26
- package/configurationUtils/index.ts +17 -11
- package/dateUtils/__tests__/dayjs.test.ts +330 -0
- package/enumUtils/__tests__/getEnumKeyByEnumValue.test.ts +207 -0
- package/errorUtils/__tests__/GeneralError.test.ts +97 -0
- package/errorUtils/__tests__/HttpStatusCode.test.ts +344 -0
- package/errorUtils/__tests__/MissingPluginError.test.ts +113 -0
- package/errorUtils/__tests__/NetworkError.test.ts +202 -0
- package/errorUtils/__tests__/getParsedResponse.test.ts +188 -0
- package/errorUtils/__tests__/invariant.test.ts +112 -0
- package/focusManager/aux/index.ts +1 -1
- package/headersUtils/__tests__/headersUtils.test.js +11 -1
- package/headersUtils/index.ts +2 -1
- package/manifestUtils/defaultManifestConfigurations/player.js +125 -11
- package/manifestUtils/keys.js +21 -0
- package/manifestUtils/platformIsTV.js +13 -0
- package/manifestUtils/sharedConfiguration/screenPicker/utils.js +1 -0
- package/manifestUtils/tvAction/container/index.js +1 -1
- package/navigationUtils/index.ts +34 -21
- package/numberUtils/__tests__/toNumber.test.ts +12 -0
- package/numberUtils/__tests__/toPositiveNumber.test.ts +165 -0
- package/numberUtils/index.ts +19 -1
- package/package.json +4 -4
- package/playerUtils/usePlayerTTS.ts +8 -3
- package/pluginUtils/index.ts +4 -0
- package/reactHooks/advertising/index.ts +2 -2
- package/reactHooks/analytics/__tests__/useSendAnalyticsOnPress.test.ts +537 -0
- package/reactHooks/app/__tests__/useAppState.test.ts +1 -1
- package/reactHooks/autoscrolling/__tests__/useTrackCurrentAutoScrollingElement.test.ts +1 -1
- package/reactHooks/autoscrolling/__tests__/useTrackedView.test.tsx +1 -2
- package/reactHooks/cell-click/__tests__/index.test.js +1 -3
- package/reactHooks/configuration/__tests__/index.test.tsx +1 -1
- package/reactHooks/connection/__tests__/index.test.js +1 -1
- package/reactHooks/debugging/__tests__/index.test.js +4 -4
- package/reactHooks/dev/__tests__/useReRenderLog.test.ts +188 -0
- package/reactHooks/device/useIsTablet.tsx +14 -19
- package/reactHooks/device/useMemoizedIsTablet.ts +3 -3
- package/reactHooks/events/index.ts +20 -0
- package/reactHooks/feed/__tests__/useBatchLoading.test.tsx +32 -23
- package/reactHooks/feed/__tests__/useBuildPipesUrl.test.tsx +19 -19
- package/reactHooks/feed/__tests__/useEntryScreenId.test.tsx +4 -1
- package/reactHooks/feed/__tests__/useFeedLoader.test.tsx +42 -30
- package/reactHooks/feed/__tests__/useFeedRefresh.test.tsx +1 -1
- package/reactHooks/feed/__tests__/{useInflatedUrl.test.ts → useInflatedUrl.test.tsx} +62 -7
- package/reactHooks/feed/useBatchLoading.ts +7 -1
- package/reactHooks/feed/useEntryScreenId.ts +2 -2
- package/reactHooks/feed/useFeedLoader.tsx +0 -9
- package/reactHooks/feed/useInflatedUrl.ts +57 -37
- package/reactHooks/feed/usePipesCacheReset.ts +3 -1
- package/reactHooks/flatList/useLoadNextPageIfNeeded.ts +13 -16
- package/reactHooks/hookModal/hooks/useHookModalScreenData.ts +12 -8
- package/reactHooks/index.ts +2 -0
- package/reactHooks/layout/__tests__/index.test.tsx +1 -1
- package/reactHooks/layout/__tests__/useLayoutVersion.test.tsx +1 -1
- package/reactHooks/layout/index.ts +1 -1
- package/reactHooks/layout/useDimensions/__tests__/{useDimensions.test.ts → useDimensions.test.tsx} +105 -25
- package/reactHooks/layout/useDimensions/useDimensions.ts +2 -2
- package/reactHooks/navigation/__tests__/index.test.tsx +40 -9
- package/reactHooks/navigation/index.ts +27 -11
- package/reactHooks/navigation/useRoute.ts +11 -7
- package/reactHooks/player/TVSeekControlller/TVSeekController.ts +27 -10
- package/reactHooks/player/__tests__/useAutoSeek._test.tsx +1 -1
- package/reactHooks/player/__tests__/useTapSeek._test.ts +1 -1
- package/reactHooks/resolvers/__tests__/useCellResolver.test.tsx +1 -1
- package/reactHooks/resolvers/__tests__/useComponentResolver.test.tsx +1 -1
- package/reactHooks/resolvers/useCellResolver.ts +6 -2
- package/reactHooks/resolvers/useComponentResolver.ts +8 -2
- package/reactHooks/screen/__tests__/useCurrentScreenData.test.tsx +2 -2
- package/reactHooks/screen/__tests__/useScreenBackgroundColor.test.tsx +1 -1
- package/reactHooks/screen/__tests__/useScreenData.test.tsx +1 -1
- package/reactHooks/screen/__tests__/useTargetScreenData.test.tsx +12 -4
- package/reactHooks/screen/useTargetScreenData.ts +4 -2
- package/reactHooks/state/useRefWithInitialValue.ts +10 -0
- package/reactHooks/state/useRivers.ts +1 -1
- package/reactHooks/ui/__tests__/useFadeOutWhenBlurred.test.ts +580 -0
- package/reactHooks/usePluginConfiguration.ts +2 -2
- package/reactHooks/utils/__tests__/index.test.js +1 -1
- package/rectUtils/__tests__/index.test.ts +549 -0
- package/rectUtils/index.ts +2 -2
- package/screenPickerUtils/__tests__/index.test.ts +333 -0
- package/screenState/__tests__/index.test.ts +1 -1
- package/searchUtils/const.ts +7 -0
- package/searchUtils/index.ts +3 -0
- package/services/storageServiceSync.web.ts +1 -1
- package/stringUtils/index.ts +1 -1
- package/testUtils/index.tsx +30 -21
- package/time/__tests__/BackgroundTimer.test.ts +156 -0
- package/time/__tests__/Timer.test.ts +236 -0
- package/typeGuards/__tests__/isString.test.ts +21 -0
- package/typeGuards/index.ts +4 -0
- package/utils/__tests__/mapAccum.test.ts +73 -0
- package/utils/__tests__/mergeRight.test.ts +48 -0
- package/utils/__tests__/selectors.test.ts +124 -0
- package/utils/index.ts +20 -0
- package/utils/mapAccum.ts +23 -0
- package/utils/mergeRight.ts +5 -0
- package/utils/path.ts +6 -3
- package/utils/pathOr.ts +5 -1
- package/utils/selectors.ts +46 -0
- package/zappFrameworkUtils/HookCallback/callbackNavigationAction.ts +128 -38
- package/zappFrameworkUtils/HookCallback/hookCallbackManifestExtensions.config.js +26 -10
- package/zappFrameworkUtils/HookCallback/useCallbackActions.ts +6 -9
- package/reactHooks/componentsMap/index.ts +0 -55
|
@@ -1,3 +1,34 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
|
|
3
|
+
import { WrappedWithProviders } from "@applicaster/zapp-react-native-utils/testUtils";
|
|
4
|
+
|
|
5
|
+
import {
|
|
6
|
+
getInflatedDataSourceUrl,
|
|
7
|
+
getSearchContext,
|
|
8
|
+
useGetUrlInflater,
|
|
9
|
+
} from "../useInflatedUrl";
|
|
10
|
+
|
|
11
|
+
import { reactHooksLogger } from "../../logger";
|
|
12
|
+
|
|
13
|
+
jest.mock("../../navigation", () => ({
|
|
14
|
+
useRoute: () => ({ pathname: "/mock/path" }),
|
|
15
|
+
}));
|
|
16
|
+
|
|
17
|
+
// mock contexts hooks
|
|
18
|
+
jest.mock("@applicaster/zapp-react-native-ui-components/Contexts", () => ({
|
|
19
|
+
ZappPipesEntryContext: {
|
|
20
|
+
useZappPipesContext: () => [
|
|
21
|
+
{ id: "entry-1", extensions: { showId: "A123" } },
|
|
22
|
+
],
|
|
23
|
+
},
|
|
24
|
+
ZappPipesSearchContext: {
|
|
25
|
+
useZappPipesContext: () => ["user%20query"],
|
|
26
|
+
},
|
|
27
|
+
ZappPipesScreenContext: {
|
|
28
|
+
useZappPipesContext: () => [{ id: "screen-1" }],
|
|
29
|
+
},
|
|
30
|
+
}));
|
|
31
|
+
|
|
1
32
|
jest.mock("../../logger", () => ({
|
|
2
33
|
reactHooksLogger: {
|
|
3
34
|
warning: jest.fn(),
|
|
@@ -5,13 +36,6 @@ jest.mock("../../logger", () => ({
|
|
|
5
36
|
},
|
|
6
37
|
}));
|
|
7
38
|
|
|
8
|
-
const {
|
|
9
|
-
getInflatedDataSourceUrl,
|
|
10
|
-
getSearchContext,
|
|
11
|
-
} = require("../useInflatedUrl");
|
|
12
|
-
|
|
13
|
-
const { reactHooksLogger } = require("../../logger");
|
|
14
|
-
|
|
15
39
|
let mockStore;
|
|
16
40
|
|
|
17
41
|
describe("getInflatedDataSourceUrl", () => {
|
|
@@ -188,3 +212,34 @@ describe("getSearchContext", () => {
|
|
|
188
212
|
expect(result).toHaveProperty(mapping.queryParam.property, searchContext);
|
|
189
213
|
});
|
|
190
214
|
});
|
|
215
|
+
|
|
216
|
+
describe("useGetUrlInflater", () => {
|
|
217
|
+
const { renderHook } = require("@testing-library/react-native");
|
|
218
|
+
|
|
219
|
+
it("returns original url when mapping is not provided", () => {
|
|
220
|
+
const { result } = renderHook(() => useGetUrlInflater(), {
|
|
221
|
+
wrapper: WrappedWithProviders,
|
|
222
|
+
});
|
|
223
|
+
|
|
224
|
+
const src = "https://foo.com/feed";
|
|
225
|
+
expect(result.current(src)).toBe(src);
|
|
226
|
+
});
|
|
227
|
+
|
|
228
|
+
it("inflates url using entry/search/screen contexts when mapping provided", () => {
|
|
229
|
+
const { result } = renderHook(() => useGetUrlInflater(), {
|
|
230
|
+
wrapper: ({ children }) => (
|
|
231
|
+
<WrappedWithProviders>{children}</WrappedWithProviders>
|
|
232
|
+
),
|
|
233
|
+
});
|
|
234
|
+
|
|
235
|
+
const source = "https://foo.com/shows/{{showId}}?q={{q}}";
|
|
236
|
+
|
|
237
|
+
const mapping = {
|
|
238
|
+
showId: { source: "entry", property: "extensions.showId" },
|
|
239
|
+
q: { source: "search", property: "q" },
|
|
240
|
+
};
|
|
241
|
+
|
|
242
|
+
const url = result.current(source, mapping);
|
|
243
|
+
expect(url).toBe("https://foo.com/shows/A123?q=user%20query");
|
|
244
|
+
});
|
|
245
|
+
});
|
|
@@ -151,7 +151,13 @@ export const useBatchLoading = (
|
|
|
151
151
|
}
|
|
152
152
|
}
|
|
153
153
|
});
|
|
154
|
-
}, [
|
|
154
|
+
}, [
|
|
155
|
+
batchComponents,
|
|
156
|
+
feeds,
|
|
157
|
+
getUrl,
|
|
158
|
+
loadPipesDataDispatcher,
|
|
159
|
+
options.riverId,
|
|
160
|
+
]);
|
|
155
161
|
|
|
156
162
|
React.useEffect(() => {
|
|
157
163
|
runBatchLoading();
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { useContentTypes } from "@applicaster/zapp-react-native-redux";
|
|
2
2
|
|
|
3
3
|
export const useEntryScreenId = (entry?: ZappEntry): string | undefined => {
|
|
4
|
-
const
|
|
4
|
+
const contentTypes = useContentTypes();
|
|
5
5
|
|
|
6
6
|
if (!entry) {
|
|
7
7
|
return;
|
|
@@ -37,15 +37,6 @@ export const useFeedLoader = ({
|
|
|
37
37
|
mapping,
|
|
38
38
|
pipesOptions = {},
|
|
39
39
|
}: Props): FeedLoaderResponse => {
|
|
40
|
-
useEffect(() => {
|
|
41
|
-
if (!feedUrl) {
|
|
42
|
-
logger.warning({
|
|
43
|
-
message: "Required parameter feedUrl is missing",
|
|
44
|
-
data: { feedUrl },
|
|
45
|
-
});
|
|
46
|
-
}
|
|
47
|
-
}, []);
|
|
48
|
-
|
|
49
40
|
const isInitialRender = useIsInitialRender();
|
|
50
41
|
|
|
51
42
|
const callableFeedUrl = useInflatedUrl({ feedUrl, mapping });
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { useMemo } from "react";
|
|
1
|
+
import { useCallback, useMemo, useRef } from "react";
|
|
2
2
|
import * as R from "ramda";
|
|
3
3
|
|
|
4
4
|
import {
|
|
@@ -18,6 +18,7 @@ import {
|
|
|
18
18
|
} from "@applicaster/zapp-pipes-v2-client";
|
|
19
19
|
import { appStore } from "@applicaster/zapp-react-native-redux/AppStore";
|
|
20
20
|
import { ENDPOINT_TAGS } from "../../types";
|
|
21
|
+
import { isNilOrEmpty } from "../../reactUtils/helpers";
|
|
21
22
|
|
|
22
23
|
/**
|
|
23
24
|
* will match any occurrence in a string of one or more word characters
|
|
@@ -75,15 +76,19 @@ export const getInflatedDataSourceUrl: GetInflatedDataSourceUrl = ({
|
|
|
75
76
|
* https://foo.com/shows/A1234
|
|
76
77
|
*/
|
|
77
78
|
|
|
78
|
-
if (!
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
79
|
+
if (!isNilOrEmpty(mapping)) {
|
|
80
|
+
if (!source) {
|
|
81
|
+
if (__DEV__) {
|
|
82
|
+
// eslint-disable-next-line no-console
|
|
83
|
+
throw new Error(
|
|
84
|
+
"getInflatedDataSourceUrl: source is empty while mapping is provided"
|
|
85
|
+
);
|
|
86
|
+
}
|
|
85
87
|
|
|
86
|
-
|
|
88
|
+
return null;
|
|
89
|
+
}
|
|
90
|
+
} else {
|
|
91
|
+
return source || null;
|
|
87
92
|
}
|
|
88
93
|
|
|
89
94
|
// Hack because in tv we expect to get key names instead of values from the fake entry
|
|
@@ -164,7 +169,7 @@ const encodeIfNeeded: (string) => string = R.tryCatch(
|
|
|
164
169
|
|
|
165
170
|
export function getSearchContext(
|
|
166
171
|
searchContext: string,
|
|
167
|
-
mapping: ZappTypeMapping
|
|
172
|
+
mapping: Nullable<ZappTypeMapping>
|
|
168
173
|
) {
|
|
169
174
|
if (!mapping) {
|
|
170
175
|
return {};
|
|
@@ -178,6 +183,45 @@ export function getSearchContext(
|
|
|
178
183
|
return { [property]: encodeIfNeeded(searchContext) };
|
|
179
184
|
}
|
|
180
185
|
|
|
186
|
+
/**
|
|
187
|
+
* Hook returns a function that replace placeholders with context values
|
|
188
|
+
* @returns function that inflates urls based on contexts
|
|
189
|
+
*/
|
|
190
|
+
export const useGetUrlInflater = () => {
|
|
191
|
+
const { pathname } = useRoute();
|
|
192
|
+
|
|
193
|
+
const [entryContext] = ZappPipesEntryContext.useZappPipesContext(pathname);
|
|
194
|
+
const [searchContext] = ZappPipesSearchContext.useZappPipesContext();
|
|
195
|
+
const [screenContext] = ZappPipesScreenContext.useZappPipesContext();
|
|
196
|
+
|
|
197
|
+
const entryContextRef = useRef(entryContext);
|
|
198
|
+
entryContextRef.current = entryContext;
|
|
199
|
+
|
|
200
|
+
const screenContextRef = useRef(screenContext);
|
|
201
|
+
screenContextRef.current = screenContext;
|
|
202
|
+
|
|
203
|
+
const searchContextRef = useRef(searchContext);
|
|
204
|
+
searchContextRef.current = searchContext;
|
|
205
|
+
|
|
206
|
+
return useCallback(
|
|
207
|
+
(
|
|
208
|
+
feedUrl: Nullable<string>,
|
|
209
|
+
mapping?: Nullable<ZappTypeMapping>
|
|
210
|
+
): Nullable<string> => {
|
|
211
|
+
return getInflatedDataSourceUrl({
|
|
212
|
+
source: feedUrl,
|
|
213
|
+
contexts: {
|
|
214
|
+
entry: entryContextRef.current,
|
|
215
|
+
screen: screenContextRef.current,
|
|
216
|
+
search: getSearchContext(searchContextRef.current, mapping),
|
|
217
|
+
},
|
|
218
|
+
mapping,
|
|
219
|
+
});
|
|
220
|
+
},
|
|
221
|
+
[]
|
|
222
|
+
);
|
|
223
|
+
};
|
|
224
|
+
|
|
181
225
|
export function useInflatedUrl({
|
|
182
226
|
feedUrl,
|
|
183
227
|
mapping,
|
|
@@ -185,36 +229,12 @@ export function useInflatedUrl({
|
|
|
185
229
|
feedUrl?: string;
|
|
186
230
|
mapping?: ZappTypeMapping;
|
|
187
231
|
}) {
|
|
188
|
-
const
|
|
189
|
-
|
|
190
|
-
const [entryContext] = ZappPipesEntryContext.useZappPipesContext(pathname);
|
|
191
|
-
const [searchContext] = ZappPipesSearchContext.useZappPipesContext();
|
|
192
|
-
const [screenContext] = ZappPipesScreenContext.useZappPipesContext();
|
|
232
|
+
const urlInflater = useGetUrlInflater();
|
|
193
233
|
|
|
194
234
|
const url = useMemo(
|
|
195
|
-
() =>
|
|
196
|
-
|
|
197
|
-
? getInflatedDataSourceUrl({
|
|
198
|
-
source: feedUrl,
|
|
199
|
-
contexts: {
|
|
200
|
-
entry: entryContext,
|
|
201
|
-
screen: screenContext,
|
|
202
|
-
search: getSearchContext(searchContext, mapping),
|
|
203
|
-
},
|
|
204
|
-
mapping,
|
|
205
|
-
})
|
|
206
|
-
: feedUrl,
|
|
207
|
-
[feedUrl, mapping]
|
|
235
|
+
() => urlInflater(feedUrl, mapping),
|
|
236
|
+
[urlInflater, feedUrl, mapping]
|
|
208
237
|
);
|
|
209
238
|
|
|
210
|
-
if (!feedUrl) {
|
|
211
|
-
logger.warning({
|
|
212
|
-
message: "Required parameter feedUrl is missing",
|
|
213
|
-
data: { feedUrl },
|
|
214
|
-
});
|
|
215
|
-
|
|
216
|
-
return null;
|
|
217
|
-
}
|
|
218
|
-
|
|
219
239
|
return url;
|
|
220
240
|
}
|
|
@@ -1,10 +1,8 @@
|
|
|
1
1
|
import { noop } from "@applicaster/zapp-react-native-utils/functionUtils";
|
|
2
2
|
import React from "react";
|
|
3
3
|
|
|
4
|
-
type Return = (index: number) => void;
|
|
5
|
-
|
|
6
4
|
type Predicate = (
|
|
7
|
-
|
|
5
|
+
entryLength: number,
|
|
8
6
|
index: number,
|
|
9
7
|
numberOfColumns: number
|
|
10
8
|
) => boolean;
|
|
@@ -12,19 +10,15 @@ type Predicate = (
|
|
|
12
10
|
type Props = {
|
|
13
11
|
ifNeeded: Predicate;
|
|
14
12
|
loadNextData: () => void;
|
|
15
|
-
|
|
13
|
+
entryLength: number;
|
|
16
14
|
numberOfColumns?: number;
|
|
17
15
|
};
|
|
18
16
|
|
|
19
17
|
const handleLoadNextPage =
|
|
20
18
|
(
|
|
21
|
-
ifNeeded:
|
|
22
|
-
entry: ZappEntry[],
|
|
23
|
-
index: number,
|
|
24
|
-
numberOfColumns?: number
|
|
25
|
-
) => boolean,
|
|
19
|
+
ifNeeded: Predicate,
|
|
26
20
|
loadNextData: () => void,
|
|
27
|
-
|
|
21
|
+
entryLength: number,
|
|
28
22
|
numberOfColumns
|
|
29
23
|
) =>
|
|
30
24
|
(index: number) => {
|
|
@@ -32,7 +26,7 @@ const handleLoadNextPage =
|
|
|
32
26
|
* Lazy-Loading, invoke nextLoadData if we reach the end of the List
|
|
33
27
|
*/
|
|
34
28
|
|
|
35
|
-
if (ifNeeded(
|
|
29
|
+
if (ifNeeded(entryLength, index, numberOfColumns)) {
|
|
36
30
|
loadNextData();
|
|
37
31
|
}
|
|
38
32
|
};
|
|
@@ -40,11 +34,14 @@ const handleLoadNextPage =
|
|
|
40
34
|
export const useLoadNextPageIfNeeded = ({
|
|
41
35
|
ifNeeded,
|
|
42
36
|
loadNextData = noop,
|
|
43
|
-
|
|
37
|
+
entryLength,
|
|
44
38
|
numberOfColumns = 0,
|
|
45
|
-
}: Props)
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
39
|
+
}: Props) => {
|
|
40
|
+
const memoFn = React.useMemo(
|
|
41
|
+
() =>
|
|
42
|
+
handleLoadNextPage(ifNeeded, loadNextData, entryLength, numberOfColumns),
|
|
43
|
+
[ifNeeded, loadNextData, entryLength, numberOfColumns]
|
|
49
44
|
);
|
|
45
|
+
|
|
46
|
+
return memoFn;
|
|
50
47
|
};
|
|
@@ -1,20 +1,24 @@
|
|
|
1
1
|
import { reactHooksLogger } from "../../logger";
|
|
2
|
-
import {
|
|
2
|
+
import { useZappHookModalStore } from "@applicaster/zapp-react-native-ui-components/Contexts/ZappHookModalContext";
|
|
3
3
|
|
|
4
4
|
const logger = reactHooksLogger.addSubsystem("useHookModalScreenData");
|
|
5
5
|
|
|
6
6
|
type VariousScreenData = LegacyNavigationScreenData | ZappRiver | ZappEntry;
|
|
7
7
|
|
|
8
|
-
export const useHookModalScreenData = (
|
|
9
|
-
|
|
8
|
+
export const useHookModalScreenData = (
|
|
9
|
+
skipSubscription: boolean
|
|
10
|
+
): VariousScreenData | undefined => {
|
|
11
|
+
const hookModalState = useZappHookModalStore((state) =>
|
|
12
|
+
skipSubscription ? undefined : state.state
|
|
13
|
+
);
|
|
10
14
|
|
|
11
|
-
if (!hookModalState
|
|
15
|
+
if (!hookModalState?.screenData) {
|
|
12
16
|
return;
|
|
13
17
|
}
|
|
14
18
|
|
|
15
19
|
try {
|
|
16
|
-
const screenData = hookModalState.
|
|
17
|
-
const hookPlugin = hookModalState.
|
|
20
|
+
const screenData = hookModalState.screenData?.payload;
|
|
21
|
+
const hookPlugin = hookModalState.screenData.hookPlugin;
|
|
18
22
|
|
|
19
23
|
if (hookPlugin?.screen_id) {
|
|
20
24
|
return {
|
|
@@ -23,7 +27,7 @@ export const useHookModalScreenData = (): VariousScreenData | undefined => {
|
|
|
23
27
|
};
|
|
24
28
|
}
|
|
25
29
|
|
|
26
|
-
return hookModalState.
|
|
30
|
+
return hookModalState.screenData?.payload;
|
|
27
31
|
} catch (error) {
|
|
28
32
|
logger.error({
|
|
29
33
|
message: "Hook modal screen data creation failed",
|
|
@@ -34,6 +38,6 @@ export const useHookModalScreenData = (): VariousScreenData | undefined => {
|
|
|
34
38
|
jsOnly: true,
|
|
35
39
|
});
|
|
36
40
|
|
|
37
|
-
return hookModalState.
|
|
41
|
+
return hookModalState.screenData?.payload;
|
|
38
42
|
}
|
|
39
43
|
};
|
package/reactHooks/index.ts
CHANGED
package/reactHooks/layout/useDimensions/__tests__/{useDimensions.test.ts → useDimensions.test.tsx}
RENAMED
|
@@ -1,16 +1,10 @@
|
|
|
1
|
-
import
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { renderHook } from "@testing-library/react-native";
|
|
2
3
|
import { Dimensions, StatusBar } from "react-native";
|
|
3
4
|
import { useDimensions } from "../useDimensions";
|
|
4
|
-
import { usePickFromState } from "@applicaster/zapp-react-native-redux";
|
|
5
5
|
|
|
6
6
|
import { useIsScreenActive } from "@applicaster/zapp-react-native-utils/reactHooks/navigation/useIsScreenActive";
|
|
7
|
-
|
|
8
|
-
jest.mock("@applicaster/zapp-react-native-redux/hooks", () => {
|
|
9
|
-
return {
|
|
10
|
-
...jest.requireActual("@applicaster/zapp-react-native-redux/hooks"),
|
|
11
|
-
usePickFromState: jest.fn(),
|
|
12
|
-
};
|
|
13
|
-
});
|
|
7
|
+
import { WrappedWithProviders } from "@applicaster/zapp-react-native-utils/testUtils";
|
|
14
8
|
|
|
15
9
|
jest.mock(
|
|
16
10
|
"@applicaster/zapp-react-native-utils/reactHooks/navigation/useIsScreenActive",
|
|
@@ -42,12 +36,22 @@ describe("useDimensions", () => {
|
|
|
42
36
|
|
|
43
37
|
beforeEach(() => {
|
|
44
38
|
StatusBar.currentHeight = 20;
|
|
45
|
-
(usePickFromState as jest.Mock).mockReturnValue({ appData: mockAppData });
|
|
46
39
|
});
|
|
47
40
|
|
|
48
41
|
it("returns correct initial dimensions", () => {
|
|
49
|
-
const { result } = renderHook(
|
|
50
|
-
useDimensions("window", { fullDimensions: false })
|
|
42
|
+
const { result } = renderHook(
|
|
43
|
+
() => useDimensions("window", { fullDimensions: false }),
|
|
44
|
+
{
|
|
45
|
+
wrapper: ({ children }) => (
|
|
46
|
+
<WrappedWithProviders
|
|
47
|
+
store={{
|
|
48
|
+
appData: mockAppData,
|
|
49
|
+
}}
|
|
50
|
+
>
|
|
51
|
+
{children}
|
|
52
|
+
</WrappedWithProviders>
|
|
53
|
+
),
|
|
54
|
+
}
|
|
51
55
|
);
|
|
52
56
|
|
|
53
57
|
expect(result.current).toMatchObject({
|
|
@@ -56,7 +60,17 @@ describe("useDimensions", () => {
|
|
|
56
60
|
});
|
|
57
61
|
|
|
58
62
|
it("calls handler on mount", () => {
|
|
59
|
-
renderHook(() => useDimensions("window", { fullDimensions: false })
|
|
63
|
+
renderHook(() => useDimensions("window", { fullDimensions: false }), {
|
|
64
|
+
wrapper: ({ children }) => (
|
|
65
|
+
<WrappedWithProviders
|
|
66
|
+
store={{
|
|
67
|
+
appData: mockAppData,
|
|
68
|
+
}}
|
|
69
|
+
>
|
|
70
|
+
{children}
|
|
71
|
+
</WrappedWithProviders>
|
|
72
|
+
),
|
|
73
|
+
});
|
|
60
74
|
|
|
61
75
|
expect(Dimensions.addEventListener).toHaveBeenCalledWith(
|
|
62
76
|
"change",
|
|
@@ -65,12 +79,23 @@ describe("useDimensions", () => {
|
|
|
65
79
|
});
|
|
66
80
|
|
|
67
81
|
it("calls handler on isActive change", () => {
|
|
68
|
-
const { rerender } = renderHook(
|
|
69
|
-
useDimensions("window", { fullDimensions: false })
|
|
82
|
+
const { rerender } = renderHook(
|
|
83
|
+
() => useDimensions("window", { fullDimensions: false }),
|
|
84
|
+
{
|
|
85
|
+
wrapper: ({ children }) => (
|
|
86
|
+
<WrappedWithProviders
|
|
87
|
+
store={{
|
|
88
|
+
appData: mockAppData,
|
|
89
|
+
}}
|
|
90
|
+
>
|
|
91
|
+
{children}
|
|
92
|
+
</WrappedWithProviders>
|
|
93
|
+
),
|
|
94
|
+
}
|
|
70
95
|
);
|
|
71
96
|
|
|
72
97
|
(useIsScreenActive as jest.Mock).mockReturnValue(false);
|
|
73
|
-
rerender();
|
|
98
|
+
rerender({});
|
|
74
99
|
|
|
75
100
|
expect(Dimensions.addEventListener).toHaveBeenCalledWith(
|
|
76
101
|
"change",
|
|
@@ -79,8 +104,19 @@ describe("useDimensions", () => {
|
|
|
79
104
|
});
|
|
80
105
|
|
|
81
106
|
it("handles fullDimensions option", () => {
|
|
82
|
-
const { result } = renderHook(
|
|
83
|
-
useDimensions("window", { fullDimensions: true })
|
|
107
|
+
const { result } = renderHook(
|
|
108
|
+
() => useDimensions("window", { fullDimensions: true }),
|
|
109
|
+
{
|
|
110
|
+
wrapper: ({ children }) => (
|
|
111
|
+
<WrappedWithProviders
|
|
112
|
+
store={{
|
|
113
|
+
appData: mockAppData,
|
|
114
|
+
}}
|
|
115
|
+
>
|
|
116
|
+
{children}
|
|
117
|
+
</WrappedWithProviders>
|
|
118
|
+
),
|
|
119
|
+
}
|
|
84
120
|
);
|
|
85
121
|
|
|
86
122
|
expect(result.current).toMatchObject({
|
|
@@ -91,8 +127,19 @@ describe("useDimensions", () => {
|
|
|
91
127
|
});
|
|
92
128
|
|
|
93
129
|
it("handles excludeStatusBar option", () => {
|
|
94
|
-
const { result } = renderHook(
|
|
95
|
-
useDimensions("window", { excludeStatusBar: true })
|
|
130
|
+
const { result } = renderHook(
|
|
131
|
+
() => useDimensions("window", { excludeStatusBar: true }),
|
|
132
|
+
{
|
|
133
|
+
wrapper: ({ children }) => (
|
|
134
|
+
<WrappedWithProviders
|
|
135
|
+
store={{
|
|
136
|
+
appData: mockAppData,
|
|
137
|
+
}}
|
|
138
|
+
>
|
|
139
|
+
{children}
|
|
140
|
+
</WrappedWithProviders>
|
|
141
|
+
),
|
|
142
|
+
}
|
|
96
143
|
);
|
|
97
144
|
|
|
98
145
|
expect(result.current.height).toBe(
|
|
@@ -101,8 +148,19 @@ describe("useDimensions", () => {
|
|
|
101
148
|
});
|
|
102
149
|
|
|
103
150
|
it("handles rounded option", () => {
|
|
104
|
-
const { result } = renderHook(
|
|
105
|
-
useDimensions("window", { rounded: true })
|
|
151
|
+
const { result } = renderHook(
|
|
152
|
+
() => useDimensions("window", { rounded: true }),
|
|
153
|
+
{
|
|
154
|
+
wrapper: ({ children }) => (
|
|
155
|
+
<WrappedWithProviders
|
|
156
|
+
store={{
|
|
157
|
+
appData: mockAppData,
|
|
158
|
+
}}
|
|
159
|
+
>
|
|
160
|
+
{children}
|
|
161
|
+
</WrappedWithProviders>
|
|
162
|
+
),
|
|
163
|
+
}
|
|
106
164
|
);
|
|
107
165
|
|
|
108
166
|
expect(result.current.width).toBe(Math.ceil(mockDimensions.width));
|
|
@@ -110,8 +168,19 @@ describe("useDimensions", () => {
|
|
|
110
168
|
});
|
|
111
169
|
|
|
112
170
|
it("handles deviceInfo option", () => {
|
|
113
|
-
const { result } = renderHook(
|
|
114
|
-
useDimensions("window", { deviceInfo: true })
|
|
171
|
+
const { result } = renderHook(
|
|
172
|
+
() => useDimensions("window", { deviceInfo: true }),
|
|
173
|
+
{
|
|
174
|
+
wrapper: ({ children }) => (
|
|
175
|
+
<WrappedWithProviders
|
|
176
|
+
store={{
|
|
177
|
+
appData: mockAppData,
|
|
178
|
+
}}
|
|
179
|
+
>
|
|
180
|
+
{children}
|
|
181
|
+
</WrappedWithProviders>
|
|
182
|
+
),
|
|
183
|
+
}
|
|
115
184
|
);
|
|
116
185
|
|
|
117
186
|
expect(result.current.deviceInfo).toMatchObject({
|
|
@@ -121,7 +190,18 @@ describe("useDimensions", () => {
|
|
|
121
190
|
|
|
122
191
|
it("logs deprecation warning when fullDimensions is boolean", () => {
|
|
123
192
|
const consoleWarnSpy = jest.spyOn(console, "warn").mockImplementation();
|
|
124
|
-
|
|
193
|
+
|
|
194
|
+
renderHook(() => useDimensions("window", true), {
|
|
195
|
+
wrapper: ({ children }) => (
|
|
196
|
+
<WrappedWithProviders
|
|
197
|
+
store={{
|
|
198
|
+
appData: mockAppData,
|
|
199
|
+
}}
|
|
200
|
+
>
|
|
201
|
+
{children}
|
|
202
|
+
</WrappedWithProviders>
|
|
203
|
+
),
|
|
204
|
+
});
|
|
125
205
|
|
|
126
206
|
expect(consoleWarnSpy).toHaveBeenCalledWith(
|
|
127
207
|
"Deprecation Warning\nSecond argument is now the options object. {fullDimensions: boolean, ...}"
|
|
@@ -3,7 +3,7 @@ import { useLayoutEffect, useMemo, useRef, useState } from "react";
|
|
|
3
3
|
import * as R from "ramda";
|
|
4
4
|
|
|
5
5
|
import { Dimensions, Platform, StatusBar } from "react-native";
|
|
6
|
-
import {
|
|
6
|
+
import { useAppData } from "@applicaster/zapp-react-native-redux/hooks";
|
|
7
7
|
|
|
8
8
|
import { isTV } from "../../../reactUtils";
|
|
9
9
|
|
|
@@ -37,7 +37,7 @@ export const useDimensions: UseDimensions = (
|
|
|
37
37
|
) => {
|
|
38
38
|
const statusBarHeight = StatusBar?.currentHeight;
|
|
39
39
|
const isActive = useIsScreenActive();
|
|
40
|
-
const
|
|
40
|
+
const appData = useAppData();
|
|
41
41
|
|
|
42
42
|
if (typeof fullDimensions === "boolean") {
|
|
43
43
|
// eslint-disable-next-line no-console
|