refactor: upgrade FlashList to v2 (#4298)
* refactor: upgrade FlashList to v2 * chore: upgrade @shopify/flash-list to v2.0.0 * chore: update packageManager version to pnpm@10.14.0 * fix: revert packageManager version to pnpm@10.12.1 * chore: update ref type for TimelineSelectorMasonryList component
This commit is contained in:
parent
7a4f5078e7
commit
3e04dc7291
|
|
@ -45,7 +45,7 @@
|
|||
"@react-native-masked-view/masked-view": "0.3.2",
|
||||
"@react-native-menu/menu": "1.2.3",
|
||||
"@react-native-picker/picker": "2.11.1",
|
||||
"@shopify/flash-list": "1.8.3",
|
||||
"@shopify/flash-list": "2.0.0",
|
||||
"@tanstack/query-sync-storage-persister": "5.81.5",
|
||||
"@tanstack/react-query": "5.81.5",
|
||||
"@tanstack/react-query-persist-client": "5.81.5",
|
||||
|
|
|
|||
|
|
@ -1,12 +1,12 @@
|
|||
import { RSSHubCategories } from "@follow/constants"
|
||||
import type { RSSHubRouteDeclaration } from "@follow/models/rsshub"
|
||||
import { isASCII } from "@follow/utils"
|
||||
import type { ContentStyle } from "@shopify/flash-list"
|
||||
import type { FlashListRef } from "@shopify/flash-list"
|
||||
import { FlashList } from "@shopify/flash-list"
|
||||
import { useQuery } from "@tanstack/react-query"
|
||||
import { useEffect, useMemo, useRef, useState } from "react"
|
||||
import { useTranslation } from "react-i18next"
|
||||
import type { ScrollView } from "react-native"
|
||||
import type { ScrollView, StyleProp, ViewStyle } from "react-native"
|
||||
import { Animated, useAnimatedValue, useWindowDimensions, View } from "react-native"
|
||||
import type { SharedValue } from "react-native-reanimated"
|
||||
import { useSharedValue } from "react-native-reanimated"
|
||||
|
|
@ -137,7 +137,7 @@ const LanguageMap = {
|
|||
cmn: "zh-CN",
|
||||
} as const
|
||||
export const RecommendationTab: TabComponent<{
|
||||
contentContainerStyle?: ContentStyle
|
||||
contentContainerStyle?: StyleProp<ViewStyle>
|
||||
insets?: {
|
||||
top?: number
|
||||
bottom?: number
|
||||
|
|
@ -231,7 +231,7 @@ export const RecommendationTab: TabComponent<{
|
|||
|
||||
// Add ref for FlashList
|
||||
const listRef = useRegisterNavigationScrollView<
|
||||
FlashList<{
|
||||
FlashListRef<{
|
||||
key: string
|
||||
data: RSSHubRouteDeclaration
|
||||
}>
|
||||
|
|
@ -287,7 +287,6 @@ export const RecommendationTab: TabComponent<{
|
|||
}
|
||||
}}
|
||||
scrollEventThrottle={16}
|
||||
estimatedItemSize={150}
|
||||
ref={listRef}
|
||||
data={alphabetGroups}
|
||||
keyExtractor={keyExtractor}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
import type { FeedViewType } from "@follow/constants"
|
||||
import { usePrefetchEntryTranslation } from "@follow/store/translation/hooks"
|
||||
import type { FlashList, ListRenderItemInfo } from "@shopify/flash-list"
|
||||
import type { FlashListRef, ListRenderItemInfo } from "@shopify/flash-list"
|
||||
import type { ElementRef } from "react"
|
||||
import { useCallback, useImperativeHandle, useMemo, useRef } from "react"
|
||||
import { View } from "react-native"
|
||||
|
|
@ -43,7 +43,7 @@ export const EntryListContentArticle = ({
|
|||
[hasNextPage, fetchedTime],
|
||||
)
|
||||
|
||||
const ref = useRef<FlashList<any>>(null)
|
||||
const ref = useRef<FlashListRef<any>>(null)
|
||||
|
||||
const { onViewableItemsChanged, onScroll, viewableItems } = useOnViewableItemsChanged({
|
||||
disabled: active === false || isFetching,
|
||||
|
|
@ -82,7 +82,6 @@ export const EntryListContentArticle = ({
|
|||
data={entryIds}
|
||||
extraData={extraData}
|
||||
keyExtractor={defaultKeyExtractor}
|
||||
estimatedItemSize={100}
|
||||
renderItem={renderItem}
|
||||
onEndReached={fetchNextPage}
|
||||
onScroll={onScroll}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
import { useTypeScriptHappyCallback } from "@follow/hooks"
|
||||
import { usePrefetchEntryTranslation } from "@follow/store/translation/hooks"
|
||||
import type { FlashList, MasonryFlashListProps } from "@shopify/flash-list"
|
||||
import type { FlashListProps, FlashListRef } from "@shopify/flash-list"
|
||||
import type { ElementRef } from "react"
|
||||
import { useImperativeHandle, useRef } from "react"
|
||||
import { StyleSheet, View } from "react-native"
|
||||
|
|
@ -24,10 +24,10 @@ export const EntryListContentPicture = ({
|
|||
active,
|
||||
...rest
|
||||
}: { entryIds: string[] | null; active?: boolean } & Omit<
|
||||
MasonryFlashListProps<string>,
|
||||
FlashListProps<string>,
|
||||
"data" | "renderItem"
|
||||
> & { ref?: React.Ref<ElementRef<typeof TimelineSelectorMasonryList> | null> }) => {
|
||||
const ref = useRef<FlashList<any>>(null)
|
||||
const ref = useRef<FlashListRef<any>>(null)
|
||||
|
||||
useImperativeHandle(forwardRef, () => ref.current!)
|
||||
const { fetchNextPage, refetch, isRefetching, hasNextPage, isFetching, isReady } = useEntries()
|
||||
|
|
@ -84,7 +84,6 @@ export const EntryListContentPicture = ({
|
|||
onScroll={onScroll}
|
||||
onEndReached={fetchNextPage}
|
||||
numColumns={2}
|
||||
estimatedItemSize={100}
|
||||
contentContainerStyle={styles.contentContainer}
|
||||
ListFooterComponent={
|
||||
hasNextPage ? (
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
import { usePrefetchEntryTranslation } from "@follow/store/translation/hooks"
|
||||
import type { FlashList, ListRenderItemInfo } from "@shopify/flash-list"
|
||||
import type { FlashListRef, ListRenderItemInfo } from "@shopify/flash-list"
|
||||
import type { ElementRef } from "react"
|
||||
import { useCallback, useImperativeHandle, useMemo, useRef } from "react"
|
||||
import { View } from "react-native"
|
||||
|
|
@ -25,7 +25,7 @@ export const EntryListContentSocial = ({
|
|||
const { fetchNextPage, isFetching, refetch, isRefetching, hasNextPage, isReady } = useEntries()
|
||||
const extraData: EntryExtraData = useMemo(() => ({ entryIds }), [entryIds])
|
||||
|
||||
const ref = useRef<FlashList<any>>(null)
|
||||
const ref = useRef<FlashListRef<any>>(null)
|
||||
useImperativeHandle(forwardRef, () => ref.current!)
|
||||
// eslint-disable-next-line @eslint-react/hooks-extra/no-unnecessary-use-callback
|
||||
const renderItem = useCallback(
|
||||
|
|
@ -61,7 +61,6 @@ export const EntryListContentSocial = ({
|
|||
isRefetching={false}
|
||||
data={Array.from({ length: 5 }).map((_, index) => `skeleton-${index}`)}
|
||||
keyExtractor={(id) => id}
|
||||
estimatedItemSize={5}
|
||||
renderItem={EntryItemSkeleton}
|
||||
ItemSeparatorComponent={ItemSeparatorFullWidth}
|
||||
/>
|
||||
|
|
@ -78,7 +77,6 @@ export const EntryListContentSocial = ({
|
|||
data={entryIds}
|
||||
extraData={extraData}
|
||||
keyExtractor={(id) => id}
|
||||
estimatedItemSize={100}
|
||||
renderItem={renderItem}
|
||||
onEndReached={fetchNextPage}
|
||||
onViewableItemsChanged={onViewableItemsChanged}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
import { useTypeScriptHappyCallback } from "@follow/hooks"
|
||||
import { usePrefetchEntryTranslation } from "@follow/store/translation/hooks"
|
||||
import type { FlashList, MasonryFlashListProps } from "@shopify/flash-list"
|
||||
import type { FlashListProps, FlashListRef } from "@shopify/flash-list"
|
||||
import type { ElementRef } from "react"
|
||||
import { useImperativeHandle, useMemo, useRef } from "react"
|
||||
import { StyleSheet, View } from "react-native"
|
||||
|
|
@ -22,10 +22,10 @@ export const EntryListContentVideo = ({
|
|||
active,
|
||||
...rest
|
||||
}: { entryIds: string[] | null; active?: boolean } & Omit<
|
||||
MasonryFlashListProps<string>,
|
||||
FlashListProps<string>,
|
||||
"data" | "renderItem"
|
||||
> & { ref?: React.Ref<ElementRef<typeof TimelineSelectorMasonryList> | null> }) => {
|
||||
const ref = useRef<FlashList<any>>(null)
|
||||
const ref = useRef<FlashListRef<any>>(null)
|
||||
useImperativeHandle(forwardRef, () => ref.current!)
|
||||
const { fetchNextPage, refetch, isRefetching, isFetching, hasNextPage, isReady } = useEntries()
|
||||
const { onViewableItemsChanged, onScroll, viewableItems } = useOnViewableItemsChanged({
|
||||
|
|
@ -95,7 +95,6 @@ export const EntryListContentVideo = ({
|
|||
onScroll={onScroll}
|
||||
onEndReached={fetchNextPage}
|
||||
numColumns={2}
|
||||
estimatedItemSize={100}
|
||||
ListFooterComponent={ListFooterComponent}
|
||||
{...rest}
|
||||
onRefresh={refetch}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
import { FeedViewType } from "@follow/constants"
|
||||
import { useWhoami } from "@follow/store/user/hooks"
|
||||
import type { FlashList } from "@shopify/flash-list"
|
||||
import type { FlashListRef } from "@shopify/flash-list"
|
||||
import type { RefObject } from "react"
|
||||
import { useEffect } from "react"
|
||||
|
||||
|
|
@ -30,7 +30,7 @@ type EntryListSelectorProps = {
|
|||
}
|
||||
|
||||
function EntryListSelectorImpl({ entryIds, viewId, active = true }: EntryListSelectorProps) {
|
||||
const ref = useRegisterNavigationScrollView<FlashList<any>>(active)
|
||||
const ref = useRegisterNavigationScrollView<FlashListRef<any>>(active)
|
||||
|
||||
let ContentComponent:
|
||||
| typeof EntryListContentSocial
|
||||
|
|
@ -89,7 +89,7 @@ export const EntryListSelector = withErrorBoundary(
|
|||
)
|
||||
|
||||
const useAutoScrollToEntryAfterPullUpToNext = (
|
||||
ref: RefObject<FlashList<any> | null>,
|
||||
ref: RefObject<FlashListRef<any> | null>,
|
||||
entryIds: string[],
|
||||
) => {
|
||||
const navigation = useNavigation()
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
import { debouncedFetchEntryContentByStream } from "@follow/store/entry/store"
|
||||
import { unreadSyncService } from "@follow/store/unread/store"
|
||||
import type ViewToken from "@shopify/flash-list/dist/viewability/ViewToken"
|
||||
import type { ViewToken } from "@shopify/flash-list"
|
||||
import { fetch as expoFetch } from "expo/fetch"
|
||||
import { useCallback, useEffect, useInsertionEffect, useMemo, useRef, useState } from "react"
|
||||
import type { NativeScrollEvent, NativeSyntheticEvent } from "react-native"
|
||||
|
|
@ -8,14 +8,14 @@ import type { NativeScrollEvent, NativeSyntheticEvent } from "react-native"
|
|||
import { useGeneralSettingKey } from "@/src/atoms/settings/general"
|
||||
import { getCookie } from "@/src/lib/auth"
|
||||
|
||||
const defaultIdExtractor = (item: ViewToken) => item.key
|
||||
const defaultIdExtractor = (item: ViewToken<string>) => item.key
|
||||
export function useOnViewableItemsChanged({
|
||||
disabled,
|
||||
idExtractor = defaultIdExtractor,
|
||||
onScroll: onScrollProp,
|
||||
}: {
|
||||
disabled?: boolean
|
||||
idExtractor?: (item: ViewToken) => string
|
||||
idExtractor?: (item: ViewToken<string>) => string
|
||||
onScroll?: (e: NativeSyntheticEvent<NativeScrollEvent>) => void
|
||||
} = {}) {
|
||||
const orientation = useRef<"down" | "up">("down")
|
||||
|
|
@ -23,15 +23,15 @@ export function useOnViewableItemsChanged({
|
|||
|
||||
const markAsReadWhenScrolling = useGeneralSettingKey("scrollMarkUnread")
|
||||
const markAsReadWhenRendering = useGeneralSettingKey("renderMarkUnread")
|
||||
const [viewableItems, setViewableItems] = useState<ViewToken[]>([])
|
||||
const [lastViewableItems, setLastViewableItems] = useState<ViewToken[] | null>()
|
||||
const [lastRemovedItems, setLastRemovedItems] = useState<ViewToken[] | null>(null)
|
||||
const [viewableItems, setViewableItems] = useState<ViewToken<string>[]>([])
|
||||
const [lastViewableItems, setLastViewableItems] = useState<ViewToken<string>[] | null>()
|
||||
const [lastRemovedItems, setLastRemovedItems] = useState<ViewToken<string>[] | null>(null)
|
||||
|
||||
const [stableIdExtractor] = useState(() => idExtractor)
|
||||
|
||||
const onViewableItemsChanged: (info: {
|
||||
viewableItems: ViewToken[]
|
||||
changed: ViewToken[]
|
||||
viewableItems: ViewToken<string>[]
|
||||
changed: ViewToken<string>[]
|
||||
}) => void = useNonReactiveCallback(({ viewableItems, changed }) => {
|
||||
setViewableItems(viewableItems)
|
||||
|
||||
|
|
|
|||
|
|
@ -2,14 +2,9 @@ import { useTypeScriptHappyCallback } from "@follow/hooks"
|
|||
import { usePrefetchSubscription } from "@follow/store/subscription/hooks"
|
||||
import { usePrefetchUnread } from "@follow/store/unread/hooks"
|
||||
import { nextFrame } from "@follow/utils"
|
||||
import type {
|
||||
FlashListProps,
|
||||
MasonryFlashListProps,
|
||||
MasonryFlashListRef,
|
||||
} from "@shopify/flash-list"
|
||||
import { FlashList, MasonryFlashList } from "@shopify/flash-list"
|
||||
import type { FlashListProps, FlashListRef } from "@shopify/flash-list"
|
||||
import { FlashList } from "@shopify/flash-list"
|
||||
import * as Haptics from "expo-haptics"
|
||||
import type { ElementRef, RefObject } from "react"
|
||||
import { use, useCallback, useImperativeHandle, useRef } from "react"
|
||||
import type { NativeScrollEvent, NativeSyntheticEvent } from "react-native"
|
||||
import { RefreshControl, View } from "react-native"
|
||||
|
|
@ -32,8 +27,9 @@ export const TimelineSelectorList = ({
|
|||
onRefresh,
|
||||
isRefetching,
|
||||
...props
|
||||
}: Props & Omit<FlashListProps<any>, "onRefresh"> & { ref?: React.Ref<FlashList<any> | null> }) => {
|
||||
const ref = useRef<FlashList<any>>(null)
|
||||
}: Props &
|
||||
Omit<FlashListProps<any>, "onRefresh"> & { ref?: React.Ref<FlashListRef<any> | null> }) => {
|
||||
const ref = useRef<FlashListRef<any>>(null)
|
||||
useImperativeHandle(forwardedRef, () => ref.current!)
|
||||
const { refetch: unreadRefetch } = usePrefetchUnread()
|
||||
const { refetch: subscriptionRefetch } = usePrefetchSubscription()
|
||||
|
|
@ -118,8 +114,8 @@ export const TimelineSelectorMasonryList = ({
|
|||
isRefetching,
|
||||
...props
|
||||
}: Props &
|
||||
Omit<MasonryFlashListProps<any>, "onRefresh"> & {
|
||||
ref?: React.Ref<ElementRef<typeof MasonryFlashList> | null>
|
||||
Omit<FlashListProps<any>, "onRefresh"> & {
|
||||
ref?: React.Ref<FlashListRef<any> | null>
|
||||
}) => {
|
||||
const { refetch: unreadRefetch } = usePrefetchUnread()
|
||||
const { refetch: subscriptionRefetch } = usePrefetchSubscription()
|
||||
|
|
@ -147,8 +143,9 @@ export const TimelineSelectorMasonryList = ({
|
|||
}
|
||||
|
||||
return (
|
||||
<MasonryFlashList
|
||||
ref={ref as RefObject<MasonryFlashListRef<any>>}
|
||||
<FlashList
|
||||
ref={ref}
|
||||
masonry
|
||||
refreshControl={
|
||||
<RefreshControl
|
||||
progressViewOffset={headerHeight}
|
||||
|
|
@ -163,11 +160,13 @@ export const TimelineSelectorMasonryList = ({
|
|||
/>
|
||||
}
|
||||
{...props}
|
||||
contentContainerStyle={{
|
||||
paddingTop: headerHeight,
|
||||
paddingBottom: tabBarHeight,
|
||||
...props.contentContainerStyle,
|
||||
}}
|
||||
contentContainerStyle={[
|
||||
{
|
||||
paddingTop: headerHeight,
|
||||
paddingBottom: tabBarHeight,
|
||||
},
|
||||
props.contentContainerStyle,
|
||||
]}
|
||||
scrollIndicatorInsets={{
|
||||
top: headerHeight - insets.top,
|
||||
bottom: tabBarHeight ? tabBarHeight - insets.bottom : undefined,
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ import {
|
|||
useSortedUngroupedSubscription,
|
||||
} from "@follow/store/subscription/hooks"
|
||||
import { subscriptionSyncService } from "@follow/store/subscription/store"
|
||||
import type { FlashList } from "@shopify/flash-list"
|
||||
import type { FlashListRef } from "@shopify/flash-list"
|
||||
import type { ParseKeys } from "i18next"
|
||||
import { memo, useCallback, useMemo, useState } from "react"
|
||||
import { useTranslation } from "react-i18next"
|
||||
|
|
@ -127,7 +127,7 @@ const SubscriptionListImpl = ({
|
|||
const onRefresh = useEventCallback(() => {
|
||||
return subscriptionSyncService.fetch(view)
|
||||
})
|
||||
const scrollViewRef = useRegisterNavigationScrollView<FlashList<any> | null>(active)
|
||||
const scrollViewRef = useRegisterNavigationScrollView<FlashListRef<any> | null>(active)
|
||||
|
||||
return (
|
||||
<TimelineSelectorList
|
||||
|
|
@ -141,7 +141,6 @@ const SubscriptionListImpl = ({
|
|||
}}
|
||||
isRefetching={refreshing}
|
||||
data={data}
|
||||
estimatedItemSize={50}
|
||||
renderItem={ItemRender}
|
||||
keyExtractor={keyExtractor}
|
||||
extraData={extraData}
|
||||
|
|
|
|||
|
|
@ -863,8 +863,8 @@ importers:
|
|||
specifier: 2.11.1
|
||||
version: 2.11.1(react-native@0.79.1(@babel/core@7.28.0)(@types/react@19.1.8)(bufferutil@4.0.9)(react@19.0.0))(react@19.0.0)
|
||||
'@shopify/flash-list':
|
||||
specifier: 1.8.3
|
||||
version: 1.8.3(@babel/runtime@7.27.6)(react-native@0.79.1(@babel/core@7.28.0)(@types/react@19.1.8)(bufferutil@4.0.9)(react@19.0.0))(react@19.0.0)
|
||||
specifier: 2.0.0
|
||||
version: 2.0.0(@babel/runtime@7.27.6)(react-native@0.79.1(@babel/core@7.28.0)(@types/react@19.1.8)(bufferutil@4.0.9)(react@19.0.0))(react@19.0.0)
|
||||
'@tanstack/query-sync-storage-persister':
|
||||
specifier: 5.81.5
|
||||
version: 5.81.5
|
||||
|
|
@ -6229,8 +6229,8 @@ packages:
|
|||
'@shikijs/vscode-textmate@10.0.2':
|
||||
resolution: {integrity: sha512-83yeghZ2xxin3Nj8z1NMd/NCuca+gsYXswywDy5bHvwlWL8tpTQmzGeUuHd9FC3E/SBEMvzJRwWEOz5gGes9Qg==}
|
||||
|
||||
'@shopify/flash-list@1.8.3':
|
||||
resolution: {integrity: sha512-vXuj6JyuMjONVOXjEhWFeaONPuWN/53Cl2LeyeM8TZ0JzUcNU+BE6iyga1/yyJeDf0K7YPgAE/PcUX2+DM1LiA==}
|
||||
'@shopify/flash-list@2.0.0':
|
||||
resolution: {integrity: sha512-N04dXZq4wgrXx3nGytchR4FUN/hBO9PmvpcqMXvy4841zTL8GKLPbdwsFe8UdLsaM5n++mBPWft0wqEddW5Q/w==}
|
||||
peerDependencies:
|
||||
'@babel/runtime': '*'
|
||||
react: 19.0.0
|
||||
|
|
@ -13961,12 +13961,6 @@ packages:
|
|||
resolution: {integrity: sha512-/vxpCXddiX8NGfGO/mTafwjq4aFa/71pvamip0++IQk3zG8cbCj0fifNPrjjF1XMXUne91jL9OoxmdykoEtifQ==}
|
||||
engines: {node: '>= 10.13.0'}
|
||||
|
||||
recyclerlistview@4.2.3:
|
||||
resolution: {integrity: sha512-STR/wj/FyT8EMsBzzhZ1l2goYirMkIgfV3gYEPxI3Kf3lOnu6f7Dryhyw7/IkQrgX5xtTcDrZMqytvteH9rL3g==}
|
||||
peerDependencies:
|
||||
react: 19.0.0
|
||||
react-native: '>= 0.30.0'
|
||||
|
||||
redeyed@2.1.1:
|
||||
resolution: {integrity: sha512-FNpGGo1DycYAdnrKFxCMmKYgo/mILAqtRYbkdQD8Ep/Hk2PQ5+aEAEx+IU713RTDmuBaH0c8P5ZozurNu5ObRQ==}
|
||||
|
||||
|
|
@ -15151,9 +15145,6 @@ packages:
|
|||
'@swc/wasm':
|
||||
optional: true
|
||||
|
||||
ts-object-utils@0.0.5:
|
||||
resolution: {integrity: sha512-iV0GvHqOmilbIKJsfyfJY9/dNHCs969z3so90dQWsO1eMMozvTpnB1MEaUbb3FYtZTGjv5sIy/xmslEz0Rg2TA==}
|
||||
|
||||
ts-pattern@5.7.1:
|
||||
resolution: {integrity: sha512-EGs8PguQqAAUIcQfK4E9xdXxB6s2GK4sJfT/vcc9V1ELIvC4LH/zXu2t/5fajtv6oiRCxdv7BgtVK3vWgROxag==}
|
||||
|
||||
|
|
@ -22090,13 +22081,11 @@ snapshots:
|
|||
|
||||
'@shikijs/vscode-textmate@10.0.2': {}
|
||||
|
||||
'@shopify/flash-list@1.8.3(@babel/runtime@7.27.6)(react-native@0.79.1(@babel/core@7.28.0)(@types/react@19.1.8)(bufferutil@4.0.9)(react@19.0.0))(react@19.0.0)':
|
||||
'@shopify/flash-list@2.0.0(@babel/runtime@7.27.6)(react-native@0.79.1(@babel/core@7.28.0)(@types/react@19.1.8)(bufferutil@4.0.9)(react@19.0.0))(react@19.0.0)':
|
||||
dependencies:
|
||||
'@babel/runtime': 7.27.6
|
||||
react: 19.0.0
|
||||
react-native: 0.79.1(@babel/core@7.28.0)(@types/react@19.1.8)(bufferutil@4.0.9)(react@19.0.0)
|
||||
recyclerlistview: 4.2.3(react-native@0.79.1(@babel/core@7.28.0)(@types/react@19.1.8)(bufferutil@4.0.9)(react@19.0.0))(react@19.0.0)
|
||||
tslib: 2.8.1
|
||||
|
||||
'@shuding/opentype.js@1.4.0-beta.0':
|
||||
dependencies:
|
||||
|
|
@ -31236,14 +31225,6 @@ snapshots:
|
|||
dependencies:
|
||||
resolve: 1.22.10
|
||||
|
||||
recyclerlistview@4.2.3(react-native@0.79.1(@babel/core@7.28.0)(@types/react@19.1.8)(bufferutil@4.0.9)(react@19.0.0))(react@19.0.0):
|
||||
dependencies:
|
||||
lodash.debounce: 4.0.8
|
||||
prop-types: 15.8.1
|
||||
react: 19.0.0
|
||||
react-native: 0.79.1(@babel/core@7.28.0)(@types/react@19.1.8)(bufferutil@4.0.9)(react@19.0.0)
|
||||
ts-object-utils: 0.0.5
|
||||
|
||||
redeyed@2.1.1:
|
||||
dependencies:
|
||||
esprima: 4.0.1
|
||||
|
|
@ -32645,8 +32626,6 @@ snapshots:
|
|||
v8-compile-cache-lib: 3.0.1
|
||||
yn: 3.1.1
|
||||
|
||||
ts-object-utils@0.0.5: {}
|
||||
|
||||
ts-pattern@5.7.1: {}
|
||||
|
||||
ts-tiny-invariant@2.0.5: {}
|
||||
|
|
|
|||
Loading…
Reference in New Issue