chore: migrate from framer-motion to motion library

Signed-off-by: Innei <tukon479@gmail.com>
This commit is contained in:
Innei 2025-04-18 00:12:20 +08:00
parent 7801aef62b
commit 735fe90a10
No known key found for this signature in database
GPG Key ID: 0F62D33977F021F7
76 changed files with 140 additions and 118 deletions

View File

@ -56,7 +56,6 @@
"es-toolkit": "1.34.1",
"firebase": "11.6.0",
"foxact": "0.2.45",
"framer-motion": "12.6.5",
"franc-min": "6.2.0",
"fuse.js": "7.1.0",
"hast-util-to-jsx-runtime": "2.3.6",
@ -70,6 +69,7 @@
"masonic": "4.0.1",
"mdast-util-gfm-table": "2.0.0",
"mdast-util-to-markdown": "2.1.2",
"motion": "12.7.4",
"nanoid": "5.1.5",
"ofetch": "1.4.1",
"plain-shiki": "0.2.0",

View File

@ -1,5 +1,5 @@
import type { MotionProps, TargetAndTransition } from "framer-motion"
import { m as M } from "framer-motion"
import type { MotionProps, TargetAndTransition } from "motion/react"
import { m as M } from "motion/react"
import { createElement, forwardRef } from "react"
import { useReduceMotion } from "~/hooks/biz/useReduceMotion"

View File

@ -3,8 +3,8 @@ import { useCorrectZIndex } from "@follow/components/ui/z-index/ctx.js"
import { stopPropagation } from "@follow/utils/dom"
import { cn } from "@follow/utils/utils"
import { Combobox, ComboboxInput, ComboboxOption, ComboboxOptions } from "@headlessui/react"
import { AnimatePresence, m } from "framer-motion"
import Fuse from "fuse.js"
import { AnimatePresence, m } from "motion/react"
import { forwardRef, Fragment, useCallback, useEffect, useState } from "react"
export type Suggestion = {

View File

@ -1,8 +1,8 @@
import { MotionButtonBase } from "@follow/components/ui/button/index.js"
import { useTypeScriptHappyCallback } from "@follow/hooks"
import { cn } from "@follow/utils/utils"
import type { HTMLMotionProps, Variants } from "framer-motion"
import { AnimatePresence, m } from "framer-motion"
import type { HTMLMotionProps, Variants } from "motion/react"
import { AnimatePresence, m } from "motion/react"
import type { FC } from "react"
import * as React from "react"
import { cloneElement, useRef, useState } from "react"

View File

@ -1,8 +1,8 @@
import { jotaiStore } from "@follow/utils/jotai"
import { cn } from "@follow/utils/utils"
import type { Variants } from "framer-motion"
import { AnimatePresence, m } from "framer-motion"
import { atom, useAtom, useStore } from "jotai"
import type { Variants } from "motion/react"
import { AnimatePresence, m } from "motion/react"
import * as React from "react"
import { useEffect } from "react"

View File

@ -1,4 +1,4 @@
import type { Spring } from "framer-motion"
import type { Spring } from "motion/react"
export const reboundPreset: Spring = {
type: "spring",

View File

@ -2,9 +2,9 @@ import { RootPortal } from "@follow/components/ui/portal/index.jsx"
import { useTypeScriptHappyCallback } from "@follow/hooks"
import { clsx, cn } from "@follow/utils/utils"
import { typescriptHappyForwardRef } from "foxact/typescript-happy-forward-ref"
import type { HTMLMotionProps } from "framer-motion"
import { AnimatePresence } from "framer-motion"
import { atom, useAtomValue } from "jotai"
import type { HTMLMotionProps } from "motion/react"
import { AnimatePresence } from "motion/react"
import type * as React from "react"
import type { JSX, PropsWithChildren, ReactNode } from "react"
import { useId } from "react"

View File

@ -1,7 +1,7 @@
import { useViewport } from "@follow/components/hooks/useViewport.js"
import { cn } from "@follow/utils/utils"
import * as HoverCard from "@radix-ui/react-hover-card"
import { AnimatePresence, m } from "framer-motion"
import { AnimatePresence, m } from "motion/react"
import { memo, useContext, useEffect, useRef, useState } from "react"
import { useRealInWideMode } from "~/atoms/settings/ui"

View File

@ -2,7 +2,7 @@ import { nextFrame } from "@follow/utils/dom"
import { getImageProxyUrl } from "@follow/utils/img-proxy"
import { cn } from "@follow/utils/utils"
import { omit } from "es-toolkit/compat"
import { useForceUpdate } from "framer-motion"
import { useForceUpdate } from "motion/react"
import type { FC, ImgHTMLAttributes, VideoHTMLAttributes } from "react"
import { createContext, memo, useContext, useMemo, useState } from "react"
import { Blurhash, BlurhashCanvas } from "react-blurhash"

View File

@ -5,7 +5,7 @@ import { useRefValue, useVideo } from "@follow/hooks"
import { nextFrame, stopPropagation } from "@follow/utils/dom"
import { clsx, cn } from "@follow/utils/utils"
import * as Slider from "@radix-ui/react-slider"
import { m, useDragControls, useSpring } from "framer-motion"
import { m, useDragControls, useSpring } from "motion/react"
import type { PropsWithChildren } from "react"
import {
forwardRef,

View File

@ -2,7 +2,7 @@ import { Button } from "@follow/components/ui/button/index.js"
import { LoadingCircle } from "@follow/components/ui/loading/index.jsx"
import { Tooltip, TooltipContent, TooltipTrigger } from "@follow/components/ui/tooltip/index.jsx"
import { stopPropagation } from "@follow/utils/dom"
import { m } from "framer-motion"
import { m } from "motion/react"
import * as React from "react"
import { useTranslation } from "react-i18next"

View File

@ -1,4 +1,4 @@
import type { MotionProps, Target } from "framer-motion"
import type { MotionProps, Target } from "motion/react"
import { microReboundPreset } from "../../constants/spring"

View File

@ -1,6 +1,6 @@
import { nextFrame, stopPropagation } from "@follow/utils/dom"
import { cn } from "@follow/utils/utils"
import { m, useAnimationControls } from "framer-motion"
import { m, useAnimationControls } from "motion/react"
import type { FC, PropsWithChildren } from "react"
import { useEffect, useState } from "react"

View File

@ -1,5 +1,5 @@
import { cn } from "@follow/utils/utils"
import { AnimatePresence } from "framer-motion"
import { AnimatePresence } from "motion/react"
import type { FC, ReactNode } from "react"
import { useId, useMemo } from "react"

View File

@ -1,7 +1,7 @@
import { Button } from "@follow/components/ui/button/index.js"
import { nextFrame } from "@follow/utils/dom"
import type { DragControls } from "framer-motion"
import { atom, useAtomValue } from "jotai"
import type { DragControls } from "motion/react"
import type { ResizeCallback, ResizeStartCallback } from "re-resizable"
import { useContext, useId, useRef, useState } from "react"
import { flushSync } from "react-dom"

View File

@ -1,5 +1,5 @@
import { nextFrame } from "@follow/utils/dom"
import { useAnimationControls } from "framer-motion"
import { useAnimationControls } from "motion/react"
import { useCallback, useEffect, useLayoutEffect } from "react"
import { useEventCallback } from "usehooks-ts"

View File

@ -1,4 +1,4 @@
import { useDragControls } from "framer-motion"
import { useDragControls } from "motion/react"
import type { PointerEventHandler, RefObject } from "react"
import { useCallback } from "react"

View File

@ -1,5 +1,5 @@
import { AnimatePresence } from "framer-motion"
import { useAtomValue } from "jotai"
import { AnimatePresence } from "motion/react"
import { modalStackAtom } from "./atom"
import { useModalStack } from "./hooks"

View File

@ -2,9 +2,9 @@ import { sheetStackAtom } from "@follow/components/ui/sheet/context.js"
import type { SheetRef } from "@follow/components/ui/sheet/Sheet.js"
import { PresentSheet } from "@follow/components/ui/sheet/Sheet.js"
import { jotaiStore } from "@follow/utils/jotai"
import { AnimatePresence } from "framer-motion"
import { produce } from "immer"
import { useAtomValue, useSetAtom } from "jotai"
import { AnimatePresence } from "motion/react"
import { createElement, useMemo, useRef } from "react"
import { useEventCallback } from "usehooks-ts"

View File

@ -7,10 +7,10 @@ import { ELECTRON_BUILD } from "@follow/shared/constants"
import { nextFrame, preventDefault, stopPropagation } from "@follow/utils/dom"
import { cn, getOS } from "@follow/utils/utils"
import * as Dialog from "@radix-ui/react-dialog"
import type { BoundingBox } from "framer-motion"
import { produce } from "immer"
import { useAtomValue, useSetAtom } from "jotai"
import { selectAtom } from "jotai/utils"
import type { BoundingBox } from "motion/react"
import { Resizable } from "re-resizable"
import type { FC, PropsWithChildren, SyntheticEvent } from "react"
import {

View File

@ -1,6 +1,6 @@
import { cn } from "@follow/utils/utils"
import * as Dialog from "@radix-ui/react-dialog"
import { AnimatePresence } from "framer-motion"
import { AnimatePresence } from "motion/react"
import type { ForwardedRef } from "react"
import { forwardRef } from "react"

View File

@ -1,6 +1,6 @@
import { cn } from "@follow/utils/utils"
import type { Spring, Target } from "framer-motion"
import { AnimatePresence, m } from "framer-motion"
import type { Spring, Target } from "motion/react"
import { AnimatePresence, m } from "motion/react"
import * as React from "react"
import { cloneElement, useEffect, useState } from "react"

View File

@ -1,4 +1,4 @@
import { useReducedMotion } from "framer-motion"
import { useReducedMotion } from "motion/react"
import { useUISettingKey } from "~/atoms/settings/ui"

View File

@ -10,7 +10,7 @@ import {
import { Input } from "@follow/components/ui/input/index.js"
import { cn } from "@follow/utils/utils"
import { zodResolver } from "@hookform/resolvers/zod"
import { m } from "framer-motion"
import { m } from "motion/react"
import { useEffect, useState } from "react"
import { useForm } from "react-hook-form"
import { useTranslation } from "react-i18next"

View File

@ -12,9 +12,9 @@ import {
} from "@follow/components/ui/tooltip/index.jsx"
import { nextFrame, stopPropagation } from "@follow/utils/dom"
import { cn, isBizId } from "@follow/utils/utils"
import type { Variant } from "framer-motion"
import { m, useAnimationControls } from "framer-motion"
import type { Components } from "hast-util-to-jsx-runtime"
import type { Variant } from "motion/react"
import { m, useAnimationControls } from "motion/react"
import type { FC } from "react"
import { useEffect, useMemo, useState } from "react"
import { Trans, useTranslation } from "react-i18next"

View File

@ -1,7 +1,7 @@
import { FeedViewType } from "@follow/constants"
import { cn } from "@follow/utils/utils"
import { AnimatePresence, LayoutGroup, m } from "framer-motion"
import { atom, useAtomValue, useSetAtom } from "jotai"
import { AnimatePresence, LayoutGroup, m } from "motion/react"
import * as React from "react"
import { CollapseGroup } from "~/components/ui/collapse"

View File

@ -1,7 +1,7 @@
import { views } from "@follow/constants"
import { cn } from "@follow/utils/utils"
import { useWheel } from "@use-gesture/react"
import { easeOut } from "framer-motion"
import { easeOut } from "motion/react"
import type { FC, PropsWithChildren } from "react"
import { useState } from "react"
import { useHotkeys } from "react-hotkeys-hook"

View File

@ -4,7 +4,7 @@ import { DividerVertical } from "@follow/components/ui/divider/Divider.js"
import { views } from "@follow/constants"
import { stopPropagation } from "@follow/utils/dom"
import { clsx } from "@follow/utils/utils"
import { m, useAnimationControls } from "framer-motion"
import { m, useAnimationControls } from "motion/react"
import { useCallback, useEffect, useRef, useState } from "react"
import { useAudioPlayerAtomSelector } from "~/atoms/player"

View File

@ -1,5 +1,5 @@
import { cn } from "@follow/utils/utils"
import { easeOut, m, useScroll, useTransform } from "framer-motion"
import { easeOut, m, useScroll, useTransform } from "motion/react"
import { Outlet } from "react-router"
import { HeaderTopReturnBackButton } from "~/components/mobile/button"

View File

@ -10,7 +10,7 @@ import {
} from "@follow/components/ui/tooltip/index.js"
import type { LoginRuntime } from "@follow/shared/auth"
import { clsx } from "@follow/utils/utils"
import { m } from "framer-motion"
import { m } from "motion/react"
import { useTranslation } from "react-i18next"
import { useCurrentModal } from "~/components/ui/modal/stacked/hooks"

View File

@ -1,7 +1,7 @@
import { Button } from "@follow/components/ui/button/index.js"
import { LoadingWithIcon } from "@follow/components/ui/loading/index.jsx"
import { from } from "dnum"
import { AnimatePresence, m } from "framer-motion"
import { AnimatePresence, m } from "motion/react"
import { useCallback, useState } from "react"
import { softSpringPreset } from "~/components/ui/constants/spring"

View File

@ -1,7 +1,7 @@
import { RadioCard } from "@follow/components/ui/radio-group/RadioCard.js"
import { RadioGroup } from "@follow/components/ui/radio-group/RadioGroup.js"
import dayjs from "dayjs"
import { m } from "framer-motion"
import { m } from "motion/react"
import { softSpringPreset } from "~/components/ui/constants/spring"

View File

@ -16,9 +16,9 @@ import { getBackgroundGradient } from "@follow/utils/color"
import { zodResolver } from "@hookform/resolvers/zod"
import { repository } from "@pkg"
import { useMutation } from "@tanstack/react-query"
import { m } from "framer-motion"
import { produce } from "immer"
import { atom, useAtomValue, useStore } from "jotai"
import { m } from "motion/react"
import type { ChangeEvent, FC } from "react"
import { memo, useCallback, useState } from "react"
import { useForm } from "react-hook-form"

View File

@ -2,7 +2,7 @@ import { ActionButton } from "@follow/components/ui/button/index.js"
import { FeedViewType } from "@follow/constants"
import { stopPropagation } from "@follow/utils/dom"
import { cn } from "@follow/utils/utils"
import { m } from "framer-motion"
import { m } from "motion/react"
import type { FC, PropsWithChildren } from "react"
import { cloneElement, memo, useCallback, useId, useMemo, useRef, useState } from "react"
import { Trans } from "react-i18next"

View File

@ -6,7 +6,7 @@ import { LRUCache } from "@follow/utils/lru-cache"
import { clsx } from "@follow/utils/utils"
import type { Range, VirtualItem, Virtualizer } from "@tanstack/react-virtual"
import { defaultRangeExtractor, useVirtualizer } from "@tanstack/react-virtual"
import type { HTMLMotionProps } from "framer-motion"
import type { HTMLMotionProps } from "motion/react"
import type { FC, MutableRefObject, ReactNode } from "react"
import {
forwardRef,

View File

@ -8,7 +8,7 @@ import {
import { EllipsisHorizontalTextWithTooltip } from "@follow/components/ui/typography/index.js"
import { FeedViewType } from "@follow/constants"
import { getNameInitials } from "@follow/utils/cjk"
import { m } from "framer-motion"
import { m } from "motion/react"
import { memo } from "react"
import { useTranslation } from "react-i18next"

View File

@ -1,7 +1,7 @@
import { EllipsisHorizontalTextWithTooltip } from "@follow/components/ui/typography/EllipsisWithTooltip.js"
import { cn } from "@follow/utils/utils"
import type { Target, TargetAndTransition } from "framer-motion"
import { m } from "framer-motion"
import type { Target, TargetAndTransition } from "motion/react"
import { m } from "motion/react"
import { useIsZenMode } from "~/atoms/settings/ui"
import { useAsRead } from "~/hooks/biz/useAsRead"

View File

@ -1,5 +1,5 @@
import { IN_ELECTRON } from "@follow/shared/constants"
import { AnimatePresence } from "framer-motion"
import { AnimatePresence } from "motion/react"
import { useEffect, useRef, useState } from "react"
import { useShowSourceContent } from "~/atoms/source-content"

View File

@ -1,6 +1,6 @@
import { views } from "@follow/constants"
import { cn } from "@follow/utils/utils"
import { AnimatePresence, m } from "framer-motion"
import { AnimatePresence, m } from "motion/react"
import { memo } from "react"
import { useUISettingKey } from "~/atoms/settings/ui"

View File

@ -3,7 +3,7 @@ import { RootPortal } from "@follow/components/ui/portal/index.js"
import { findElementInShadowDOM } from "@follow/utils/dom"
import { clsx, cn } from "@follow/utils/utils"
import { DismissableLayer } from "@radix-ui/react-dismissable-layer"
import { AnimatePresence, m } from "framer-motion"
import { AnimatePresence, m } from "motion/react"
import { memo, useEffect, useState } from "react"
import { RemoveScroll } from "react-remove-scroll"
import { useEventCallback } from "usehooks-ts"

View File

@ -4,7 +4,7 @@ import { getBackgroundGradient } from "@follow/utils/color"
import { getImageProxyUrl } from "@follow/utils/img-proxy"
import { cn, getUrlIcon } from "@follow/utils/utils"
import { Avatar, AvatarFallback, AvatarImage } from "@radix-ui/react-avatar"
import { m } from "framer-motion"
import { m } from "motion/react"
import type { ReactNode } from "react"
import { forwardRef, useMemo } from "react"

View File

@ -2,7 +2,7 @@ import { MotionButtonBase } from "@follow/components/ui/button/index.js"
import { KbdCombined } from "@follow/components/ui/kbd/Kbd.js"
import { ScrollArea } from "@follow/components/ui/scroll-area/index.js"
import { clsx, cn } from "@follow/utils/utils"
import { m, useDragControls } from "framer-motion"
import { m, useDragControls } from "motion/react"
import { useCallback, useEffect } from "react"
import { useTranslation } from "react-i18next"

View File

@ -3,7 +3,7 @@ import { Button } from "@follow/components/ui/button/index.js"
import { Kbd } from "@follow/components/ui/kbd/Kbd.js"
import { tracker } from "@follow/tracker"
import { cn } from "@follow/utils/utils"
import { AnimatePresence, m } from "framer-motion"
import { AnimatePresence, m } from "motion/react"
import type { ComponentProps, FunctionComponentElement } from "react"
import { createElement, useCallback, useEffect, useMemo, useState } from "react"
import { Trans, useTranslation } from "react-i18next"

View File

@ -6,7 +6,7 @@ import { RootPortal } from "@follow/components/ui/portal/index.jsx"
import { useInputComposition, useRefValue } from "@follow/hooks"
import { useSubscribeElectronEvent } from "@follow/shared/event"
import { nextFrame } from "@follow/utils/dom"
import { AnimatePresence, m } from "framer-motion"
import { AnimatePresence, m } from "motion/react"
import type { FC } from "react"
import { useCallback, useEffect, useLayoutEffect, useRef, useState } from "react"
import { useDebounceCallback, useEventCallback } from "usehooks-ts"

View File

@ -6,7 +6,7 @@ import { tracker } from "@follow/tracker"
import { cn } from "@follow/utils/utils"
import * as Slider from "@radix-ui/react-slider"
import dayjs from "dayjs"
import { AnimatePresence, m } from "framer-motion"
import { AnimatePresence, m } from "motion/react"
import { useEffect, useMemo, useState } from "react"
import Marquee from "react-fast-marquee"
import { useHotkeys } from "react-hotkeys-hook"

View File

@ -12,7 +12,7 @@ import { Label } from "@follow/components/ui/label/index.js"
import { cn } from "@follow/utils/utils"
import { zodResolver } from "@hookform/resolvers/zod"
import { useMutation } from "@tanstack/react-query"
import { m } from "framer-motion"
import { m } from "motion/react"
import { useForm } from "react-hook-form"
import { useTranslation } from "react-i18next"
import { toast } from "sonner"

View File

@ -11,7 +11,7 @@ import { Input, InputOTP, InputOTPGroup, InputOTPSlot } from "@follow/components
import { Label } from "@follow/components/ui/label/index.js"
import { zodResolver } from "@hookform/resolvers/zod"
import { useMutation } from "@tanstack/react-query"
import { m, useAnimation } from "framer-motion"
import { m, useAnimation } from "motion/react"
import { useState } from "react"
import { useForm } from "react-hook-form"
import { useTranslation } from "react-i18next"

View File

@ -7,9 +7,9 @@ import { nextFrame, stopPropagation } from "@follow/utils/dom"
import { getStorageNS } from "@follow/utils/ns"
import { clsx, cn } from "@follow/utils/utils"
import { throttle } from "es-toolkit/compat"
import { useAnimationControls } from "framer-motion"
import { useAtom } from "jotai"
import { atomWithStorage } from "jotai/utils"
import { useAnimationControls } from "motion/react"
import type { FC } from "react"
import { Fragment, useEffect, useMemo, useRef, useState } from "react"
import { useTranslation } from "react-i18next"

View File

@ -7,7 +7,7 @@ import { LoadingWithIcon } from "@follow/components/ui/loading/index.jsx"
import { EllipsisHorizontalTextWithTooltip } from "@follow/components/ui/typography/index.js"
import type { SubscriptionModel } from "@follow/models/types"
import { cn } from "@follow/utils/utils"
import { AnimatePresence } from "framer-motion"
import { AnimatePresence } from "motion/react"
import type { FC } from "react"
import { Fragment, memo, useState } from "react"
import { useEventCallback } from "usehooks-ts"

View File

@ -3,7 +3,7 @@ import { LetsIconsResizeDownRightLight } from "@follow/components/icons/resize.j
import { IN_ELECTRON } from "@follow/shared/constants"
import { preventDefault } from "@follow/utils/dom"
import { cn, getOS } from "@follow/utils/utils"
import type { BoundingBox } from "framer-motion"
import type { BoundingBox } from "motion/react"
import { Resizable } from "re-resizable"
import type { PropsWithChildren } from "react"
import { memo, Suspense, useCallback, useEffect, useRef } from "react"

View File

@ -13,7 +13,7 @@ import { useIsDark, useThemeAtomValue } from "@follow/hooks"
import { ELECTRON_BUILD, IN_ELECTRON } from "@follow/shared/constants"
import { capitalizeFirstLetter, getOS } from "@follow/utils/utils"
import dayjs from "dayjs"
import { useForceUpdate } from "framer-motion"
import { useForceUpdate } from "motion/react"
import { lazy, Suspense, useEffect, useRef, useState } from "react"
import { useTranslation } from "react-i18next"
import { bundledThemesInfo } from "shiki/themes"

View File

@ -9,7 +9,7 @@ import { useInputComposition, useRefValue } from "@follow/hooks"
import { stopPropagation } from "@follow/utils/dom"
import { cn, sortByAlphabet } from "@follow/utils/utils"
import { useMutation } from "@tanstack/react-query"
import { AnimatePresence, m } from "framer-motion"
import { AnimatePresence, m } from "motion/react"
import type { FC } from "react"
import { Fragment, memo, useCallback, useEffect, useMemo, useRef, useState } from "react"
import { useTranslation } from "react-i18next"

View File

@ -5,7 +5,7 @@ import { stopPropagation } from "@follow/utils/dom"
import { cn } from "@follow/utils/utils"
import * as HoverCard from "@radix-ui/react-hover-card"
import { useQuery } from "@tanstack/react-query"
import { AnimatePresence, m } from "framer-motion"
import { AnimatePresence, m } from "motion/react"
import { memo, useRef, useState } from "react"
import { useTranslation } from "react-i18next"
import { Link } from "react-router"

View File

@ -4,7 +4,7 @@ import { ActionButton } from "@follow/components/ui/button/index.js"
import { Popover, PopoverContent, PopoverTrigger } from "@follow/components/ui/popover/index.jsx"
import { stopPropagation } from "@follow/utils/dom"
import { cn } from "@follow/utils/utils"
import { m } from "framer-motion"
import { m } from "motion/react"
import type { FC, PropsWithChildren } from "react"
import { memo, useCallback, useEffect, useRef, useState } from "react"
import { useHotkeys } from "react-hotkeys-hook"

View File

@ -6,8 +6,8 @@ import { useRegisterGlobalContext } from "@follow/shared/bridge"
import { ELECTRON_BUILD } from "@follow/shared/constants"
import { clamp, cn } from "@follow/utils/utils"
import { useWheel } from "@use-gesture/react"
import { AnimatePresence, m } from "framer-motion"
import { Lethargy } from "lethargy"
import { AnimatePresence, m } from "motion/react"
import type { FC, PropsWithChildren } from "react"
import { memo, useCallback, useEffect, useLayoutEffect, useRef, useState } from "react"
import { isHotkeyPressed, useHotkeys } from "react-hotkeys-hook"

View File

@ -1,4 +1,4 @@
import { m } from "framer-motion"
import { m } from "motion/react"
import { useCallback } from "react"
import { useTranslation } from "react-i18next"

View File

@ -1,6 +1,6 @@
import { tracker } from "@follow/tracker"
import { cn } from "@follow/utils/utils"
import { m, useMotionTemplate, useMotionValue } from "framer-motion"
import { m, useMotionTemplate, useMotionValue } from "motion/react"
import { useCallback, useEffect } from "react"
import { useTranslation } from "react-i18next"

View File

@ -241,7 +241,7 @@ export default ({ mode }) => {
],
["vfile", "unified"],
["es-toolkit/compat"],
["framer-motion"],
["motion/react"],
["clsx", "tailwind-merge", "class-variance-authority"],
[

View File

@ -133,7 +133,7 @@ export const EntryNormalItem = memo(
)}
</View>
{view !== FeedViewType.Notifications && (
<View className="relative ml-2">
<View className="relative ml-4">
{image &&
(thumbnailRatio === "square" ? (
<SquareImage image={image} blurhash={blurhash} />

View File

@ -19,8 +19,8 @@ import { nextFrame } from "@follow/utils/dom"
import { cn } from "@follow/utils/utils"
import dayjs from "dayjs"
import { throttle } from "es-toolkit/compat"
import { AnimatePresence, m } from "framer-motion"
import type { RenderComponentProps } from "masonic"
import { AnimatePresence, m } from "motion/react"
import type { FC, PropsWithChildren } from "react"
import { memo, useEffect, useLayoutEffect, useMemo, useRef, useState } from "react"
import { PhotoProvider, PhotoView } from "react-photo-view"

View File

@ -4,8 +4,8 @@ import { Logo } from "@follow/components/icons/logo.jsx"
import { Button } from "@follow/components/ui/button/index.jsx"
import { Kbd } from "@follow/components/ui/kbd/Kbd.jsx"
import { cn } from "@follow/utils/utils"
import type { MotionValue } from "framer-motion"
import { useMotionValueEvent, useScroll } from "framer-motion"
import type { MotionValue } from "motion/react"
import { useMotionValueEvent, useScroll } from "motion/react"
import * as React from "react"
import { useState } from "react"
import { useHotkeys } from "react-hotkeys-hook"

View File

@ -21,13 +21,13 @@
"click-to-react-component": "1.1.2",
"dayjs": "1.11.13",
"fastify": "5.3.0",
"framer-motion": "12.6.5",
"i18next": "24.2.3",
"jotai": "2.12.2",
"kose-font": "1.0.0",
"linkedom": "0.18.9",
"motion": "12.7.4",
"ofetch": "1.4.1",
"rc-modal-sheet": "0.3.2",
"rc-modal-sheet": "1.0.0",
"react-blurhash": "0.3.0",
"react-google-recaptcha": "3.1.0",
"react-hook-form": "7.55.0",

View File

@ -52,13 +52,13 @@
"class-variance-authority": "0.7.1",
"dayjs": "1.11.13",
"foxact": "0.2.45",
"framer-motion": "12.6.5",
"hast-util-to-jsx-runtime": "2.3.6",
"hast-util-to-text": "4.0.2",
"input-otp": "1.4.2",
"jotai": "2.12.2",
"katex": "0.16.22",
"masonic": "4.0.1",
"motion": "12.7.4",
"react-blurhash": "0.3.0",
"react-fast-marquee": "1.6.5",
"react-hook-form": "7.55.0",

View File

@ -1,4 +1,4 @@
import { LazyMotion, MotionConfig } from "framer-motion"
import { LazyMotion, MotionConfig } from "motion/react"
const loadFeatures = () => import("../framer-lazy-feature").then((res) => res.default)
export const MotionProvider = ({ children }: { children: React.ReactNode }) => {

View File

@ -1 +1 @@
export { domMax as default } from "framer-motion"
export { domMax as default } from "motion/react"

View File

@ -1,6 +1,6 @@
import { cn } from "@follow/utils/utils"
import type { Spring } from "framer-motion"
import { m } from "framer-motion"
import type { Spring } from "motion/react"
import { m } from "motion/react"
import { useEffect, useRef, useState } from "react"
const softSpringPreset: Spring = {

View File

@ -2,8 +2,8 @@ import { useMobile } from "@follow/components/hooks/useMobile.js"
import { LoadingCircle } from "@follow/components/ui/loading/index.jsx"
import { cn } from "@follow/utils/utils"
import type { VariantProps } from "class-variance-authority"
import type { HTMLMotionProps } from "framer-motion"
import { m } from "framer-motion"
import type { HTMLMotionProps } from "motion/react"
import { m } from "motion/react"
import * as React from "react"
import { styledButtonVariant } from "./variants"

View File

@ -3,7 +3,7 @@ import { getColorScheme, stringToHue } from "@follow/utils/color"
import { getImageProxyUrl } from "@follow/utils/img-proxy"
import { cn } from "@follow/utils/utils"
import { Avatar, AvatarFallback, AvatarImage } from "@radix-ui/react-avatar"
import { m } from "framer-motion"
import { m } from "motion/react"
import type { ReactNode } from "react"
import { forwardRef, useMemo } from "react"

View File

@ -2,7 +2,7 @@ import { useInputComposition } from "@follow/hooks"
import { stopPropagation } from "@follow/utils/dom"
import { cn } from "@follow/utils/utils"
import clsx from "clsx"
import { useMotionValue } from "framer-motion"
import { useMotionValue } from "motion/react"
import type { DetailedHTMLProps, PropsWithChildren, TextareaHTMLAttributes } from "react"
import { forwardRef, useCallback, useState } from "react"

View File

@ -1,5 +1,5 @@
import { cn } from "@follow/utils/utils"
import { m, useAnimation } from "framer-motion"
import { m, useAnimation } from "motion/react"
import * as React from "react"
import { cloneElement, useEffect } from "react"

View File

@ -2,9 +2,9 @@
import { clearRequestTimeout, requestTimeout } from "@essentials/request-timeout"
import { useWindowSize } from "@react-hook/window-size"
import { isEqual, throttle } from "es-toolkit/compat"
import { useForceUpdate } from "framer-motion"
import type { ContainerPosition, MasonryProps, MasonryScrollerProps, Positioner } from "masonic"
import { createResizeObserver, useMasonry, usePositioner, useScrollToIndex } from "masonic"
import { useForceUpdate } from "motion/react"
import * as React from "react"
import { useScrollViewElement } from "../scroll-area/hooks.js"

View File

@ -1,5 +1,5 @@
import { cn } from "@follow/utils/utils"
import { m } from "framer-motion"
import { m } from "motion/react"
import type { ReactNode } from "react"
import { useId, useMemo, useState } from "react"
import { useContextSelector } from "use-context-selector"

View File

@ -1,6 +1,6 @@
import { cn } from "@follow/utils/utils"
import * as TooltipPrimitive from "@radix-ui/react-tooltip"
import { m } from "framer-motion"
import { m } from "motion/react"
import * as React from "react"
import { tooltipStyle } from "./styles"

View File

@ -37,8 +37,8 @@
"chardet": "2.1.0",
"clsx": "2.1.1",
"dompurify": "3.2.5",
"framer-motion": "12.6.5",
"linkedom": "0.18.9",
"motion": "12.7.4",
"nanoid": "5.1.5",
"path-to-regexp": "8.2.0",
"tailwind-merge": "3.2.0",

View File

@ -1,7 +1,7 @@
// @see https://github.com/Innei/sprightly/blob/2444dcdb789ca585337a4d241095640a524231db/src/lib/scroller.ts
import type { Spring } from "framer-motion"
import { animateValue } from "framer-motion"
import type { Spring } from "motion/react"
import { animateValue } from "motion/react"
const spring: Spring = {
type: "spring",

View File

@ -597,9 +597,6 @@ importers:
foxact:
specifier: 0.2.45
version: 0.2.45(react@18.3.1)
framer-motion:
specifier: 12.6.5
version: 12.6.5(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
franc-min:
specifier: 6.2.0
version: 6.2.0
@ -639,6 +636,9 @@ importers:
mdast-util-to-markdown:
specifier: 2.1.2
version: 2.1.2
motion:
specifier: 12.7.4
version: 12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
nanoid:
specifier: 5.1.5
version: 5.1.5
@ -1156,9 +1156,6 @@ importers:
fastify:
specifier: 5.3.0
version: 5.3.0
framer-motion:
specifier: 12.6.5
version: 12.6.5(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
i18next:
specifier: 24.2.3
version: 24.2.3(typescript@5.8.3)
@ -1171,12 +1168,15 @@ importers:
linkedom:
specifier: 0.18.9
version: 0.18.9
motion:
specifier: 12.7.4
version: 12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
ofetch:
specifier: 1.4.1
version: 1.4.1
rc-modal-sheet:
specifier: 0.3.2
version: 0.3.2(@radix-ui/react-dialog@1.1.7(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(clsx@2.1.1)(framer-motion@12.6.5(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(tailwind-merge@3.2.0)(vaul@1.1.2(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1))
specifier: 1.0.0
version: 1.0.0(@radix-ui/react-dialog@1.1.7(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(clsx@2.1.1)(motion@12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(tailwind-merge@3.2.0)(vaul@1.1.2(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1))
react-blurhash:
specifier: 0.3.0
version: 0.3.0(blurhash@2.0.5)(react@18.3.1)
@ -1400,9 +1400,6 @@ importers:
foxact:
specifier: 0.2.45
version: 0.2.45(react@18.3.1)
framer-motion:
specifier: 12.6.5
version: 12.6.5(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
hast-util-to-jsx-runtime:
specifier: 2.3.6
version: 2.3.6
@ -1421,6 +1418,9 @@ importers:
masonic:
specifier: 4.0.1
version: 4.0.1(react@18.3.1)
motion:
specifier: 12.7.4
version: 12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
react-blurhash:
specifier: 0.3.0
version: 0.3.0(blurhash@2.0.5)(react@18.3.1)
@ -1595,12 +1595,12 @@ importers:
dompurify:
specifier: 3.2.5
version: 3.2.5
framer-motion:
specifier: 12.6.5
version: 12.6.5(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
linkedom:
specifier: 0.18.9
version: 0.18.9
motion:
specifier: 12.7.4
version: 12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
nanoid:
specifier: 5.1.5
version: 5.1.5
@ -9816,8 +9816,8 @@ packages:
fraction.js@4.3.7:
resolution: {integrity: sha512-ZsDfxO51wGAXREY55a7la9LScWpwv9RxIrYABrlvOFBlH/ShPnrtsXeuUIfXKKOVicNxQ+o8JTbJvjS4M89yew==}
framer-motion@12.6.5:
resolution: {integrity: sha512-MKvnWov0paNjvRJuIy6x418w23tFqRfS6CXHhZrCiSEpXVlo/F+usr8v4/3G6O0u7CpsaO1qop+v4Ip7PRCBqQ==}
framer-motion@12.7.4:
resolution: {integrity: sha512-jX0bPsTmU0oPZTYz/dVyD0dmOyEOEJvdn0TaZBE5I8g2GvVnnQnW9f65cJnoVfUkY3WZWNXGXnPbVA9YnaIfVA==}
peerDependencies:
'@emotion/is-prop-valid': '*'
react: 18.3.1
@ -11882,11 +11882,25 @@ packages:
moment@2.30.1:
resolution: {integrity: sha512-uEmtNhbDOrWPFS+hdjFCBfy9f2YoyzRpwcl+DqpC6taX21FzsTLQVbMV/W7PzNSX6x/bhC1zA3c2UQ5NzH6how==}
motion-dom@12.6.5:
resolution: {integrity: sha512-jpM9TQLXzYMWMJ7Ec7sAj0iis8oIuu6WvjI3yNKJLdrZyrsI/b2cRInDVL8dCl683zQQq19DpL9cSMP+k8T1NA==}
motion-dom@12.7.4:
resolution: {integrity: sha512-1ZUHAoSUMMxP6jPqyxlk9XUfb6NxMsnWPnH2YGhrOhTURLcXWbETi6eemoKb60Pe32NVJYduL4B62VQSO5Jq8Q==}
motion-utils@12.6.5:
resolution: {integrity: sha512-IsOeKsOF+FWBhxQEDFBO6ZYC8/jlidmVbbLpe9/lXSA9j9kzGIMUuIBx2SZY+0reAS0DjZZ1i7dJp4NHrjocPw==}
motion-utils@12.7.2:
resolution: {integrity: sha512-XhZwqctxyJs89oX00zn3OGCuIIpVevbTa+u82usWBC6pSHUd2AoNWiYa7Du8tJxJy9TFbZ82pcn5t7NOm1PHAw==}
motion@12.7.4:
resolution: {integrity: sha512-MBGrMbYageHw4iZJn+pGTr7abq5n53jCxYkhFC1It3vYukQPRWg5zij46MnwYGpLR8KG465MLHSASXot9edYOw==}
peerDependencies:
'@emotion/is-prop-valid': '*'
react: 18.3.1
react-dom: 18.3.1
peerDependenciesMeta:
'@emotion/is-prop-valid':
optional: true
react:
optional: true
react-dom:
optional: true
mri@1.2.0:
resolution: {integrity: sha512-tzzskb3bG8LvYGFF/mDTpq3jpI6Q9wc3LEmBaghu+DdCssd1FakN7Bc0hVNmEyGq1bq3RgfkCb3cmQLpNPOroA==}
@ -13103,12 +13117,12 @@ packages:
resolution: {integrity: sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==}
engines: {node: '>= 0.8'}
rc-modal-sheet@0.3.2:
resolution: {integrity: sha512-V6q4+xpeIj9VRL/44zCaXCkRLjVZ1iSYUuyiqveD24gQFy41s9GwjTrMoZ0T6Xg54I2wzuXRUITRH1hrHIjF+A==}
rc-modal-sheet@1.0.0:
resolution: {integrity: sha512-bhKDxa67CyQUvjoJQ+IBms6eyTR1XV0COE/Vbuy33RznO66EkeFGh0dtwM2pbMcVhvJscAR7G9+n2msU4EWI1A==}
peerDependencies:
'@radix-ui/react-dialog': ^1
clsx: '*'
framer-motion: ^11
motion: ^12
tailwind-merge: ^2
vaul: ^0.9.0
@ -26077,10 +26091,10 @@ snapshots:
fraction.js@4.3.7: {}
framer-motion@12.6.5(react-dom@18.3.1(react@18.3.1))(react@18.3.1):
framer-motion@12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1):
dependencies:
motion-dom: 12.6.5
motion-utils: 12.6.5
motion-dom: 12.7.4
motion-utils: 12.7.2
tslib: 2.8.1
optionalDependencies:
react: 18.3.1
@ -28709,11 +28723,19 @@ snapshots:
moment@2.30.1:
optional: true
motion-dom@12.6.5:
motion-dom@12.7.4:
dependencies:
motion-utils: 12.6.5
motion-utils: 12.7.2
motion-utils@12.6.5: {}
motion-utils@12.7.2: {}
motion@12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1):
dependencies:
framer-motion: 12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
tslib: 2.8.1
optionalDependencies:
react: 18.3.1
react-dom: 18.3.1(react@18.3.1)
mri@1.2.0: {}
@ -29839,11 +29861,11 @@ snapshots:
iconv-lite: 0.6.3
unpipe: 1.0.0
rc-modal-sheet@0.3.2(@radix-ui/react-dialog@1.1.7(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(clsx@2.1.1)(framer-motion@12.6.5(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(tailwind-merge@3.2.0)(vaul@1.1.2(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1)):
rc-modal-sheet@1.0.0(@radix-ui/react-dialog@1.1.7(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(clsx@2.1.1)(motion@12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1))(tailwind-merge@3.2.0)(vaul@1.1.2(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1)):
dependencies:
'@radix-ui/react-dialog': 1.1.7(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
clsx: 2.1.1
framer-motion: 12.6.5(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
motion: 12.7.4(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
tailwind-merge: 3.2.0
vaul: 1.1.2(@types/react-dom@18.3.1)(@types/react@18.3.12)(react-dom@18.3.1(react@18.3.1))(react@18.3.1)