React Native Reanimated Bottom Sheet 핵심 원리 분석: 제스처와 애니메이션의 결합

React Native Reanimated Bottom Sheet는 react-native-reanimatedreact-native-gesture-handler를 활용하여 유연한 제스처 상호작용과 부드러운 애니메이션을 제공하는 고도로 설정 가능한 바텀 시트 컴포넌트입니다. 이 글에서는 제스처 처리와 애니메이션 시스템의 통합 방식을 중심으로 핵심 원리를 분석합니다.

컴포넌트 핵심 아키텍처 및 작동 원리

React Native Reanimated Bottom Sheet의 핵심은 제스처 인식과 애니메이션 시스템을 원활하게 통합하는 데 있습니다. BottomSheetBehavior 클래스(src/index.tsx)가 주요 기능을 담당하며, 제스처 처리 로직과 애니메이션 제어 메커니즘을 포함합니다.

컴포넌트의 주요 작동 흐름은 다음과 같습니다.

  1. 제스처 인식 - PanGestureHandlerTapGestureHandler를 통해 사용자 상호작용을 감지합니다.
  2. 상태 관리 - 바텀 시트의 위치 상태와 애니메이션 상태를 유지합니다.
  3. 애니메이션 계산 - Reanimated 라이브러리를 사용하여 부드러운 전환 효과를 구현합니다.
  4. 경계 처리 - 바텀 시트의 최소/최대 위치와 제약 조건을 관리합니다.

제스처 처리 시스템 상세 분석

컴포넌트는 다중 레이어 제스처 처리 메커니즘을 사용합니다. PanGestureHandler로 드래그 기능을 구현하며, 주요 코드는 src/index.tsx의 handleMasterPanhandlePan 메서드에 있습니다.

제스처 인식 흐름

1. 마스터 제스처 핸들러 - 전체 드래그 작업을 처리합니다.

private handleMasterPan = event([
  {
    nativeEvent: {
      translationY: this.dragMasterY,
      state: this.panMasterState,
      velocityY: this.masterVelocity,
    },
  },
])

2. 콘텐츠 제스처 핸들러 - 콘텐츠 영역의 스크롤과 상호작용을 처리합니다.

private handlePan = event([
  {
    nativeEvent: {
      translationY: this.props.enabledInnerScrolling
        ? this.dragY
        : this.dragMasterY,
      state: this.props.enabledInnerScrolling
        ? this.panState
        : this.panMasterState,
      velocityY: this.props.enabledInnerScrolling
        ? this.velocity
        : this.masterVelocity,
    },
  },
])

3. 탭 제스처 핸들러 - 탭 이벤트를 처리하여 애니메이션을 중단합니다.

private handleTap = event([{ nativeEvent: { state: this.tapState } }])

제스처 상태 관리

컴포넌트는 GestureState 열거형을 사용하여 제스처 상태를 관리합니다. 주요 상태는 다음과 같습니다.

  • BEGAN - 제스처 시작
  • ACTIVE - 제스처 진행 중
  • END - 제스처 종료
  • CANCELLED - 제스처 취소
  • FAILED - 제스처 실패

이 상태들은 src/index.tsx 7번째 줄에서 정의됩니다.

import {
  PanGestureHandler,
  TapGestureHandler,
  State as GestureState,
} from 'react-native-gesture-handler'

애니메이션 시스템 구현 원리

React Native Reanimated Bottom Sheet는 Reanimated 라이브러리를 통해 고성능 애니메이션을 구현하며, 주요 메커니즘은 다음과 같습니다.

스프링 애니메이션 설정

컴포넌트는 자연스러운 애니메이션 전환을 위해 스프링 물리 효과를 사용합니다. 설정은 src/index.tsx의 magic 객체에 정의되어 있습니다.

const magic = {
  damping: 50,
  mass: 0.3,
  stiffness: 121.6,
  overshootClamping: true,
  restSpeedThreshold: 0.3,
  restDisplacementThreshold: 0.3,
  deceleration: 0.999,
  bouncyFactor: 1,
  velocityFactor: P(1, 0.8),
  toss: 0.4,
  coefForTranslatingVelocities: 5,
}

애니메이션 구동 메커니즘

컴포넌트는 runSpring 메서드로 스프링 애니메이션을, runDecay 메서드로 감쇠 애니메이션을 구현합니다. 이 메서드들은 src/index.tsx의 195번째 줄과 249번째 줄에서 정의됩니다.

Animated.Value를 통해 관리되는 주요 애니메이션 값은 다음과 같습니다.

  • translateMaster - 바텀 시트 전체 위치를 제어하는 메인 애니메이션 값
  • Y - 콘텐츠 영역의 애니메이션 값
  • snapPoint - 목표 위치를 계산하는 애니메이션 노드

다중 스냅 포인트 시스템

컴포넌트는 여러 "스냅 포인트"를 지원하여 바텀 시트가 다양한 높이에 머물 수 있게 합니다. 이 기능은 src/index.tsx의 15번째 줄에 정의된 snapPoints 속성을 통해 제공됩니다.

snapPoints: (number | string)[]

고급 기능 및 최적화 팁

성능 최적화 전략

  1. 네이티브 구동 애니메이션 - Reanimated의 네이티브 구동 모드를 활용하여 자바스크립트 브릿지 병목 현상을 방지합니다.
  2. 제스처 충돌 처리 - simultaneousHandlerswaitFor 속성을 사용하여 복잡한 제스처 시나리오를 처리합니다.
  3. 지연 로딩 및 조건부 렌더링 - 필요할 때만 콘텐츠를 렌더링하여 초기 로딩 성능을 개선합니다.

설정 가능성 설계

컴포넌트는 다음과 같은 다양한 설정 옵션을 제공합니다.

  • enabledGestureInteraction - 제스처 상호작용 활성화/비활성화
  • enabledBottomClamp - 하단 최소 위치 제한
  • springConfig - 스프링 애니메이션 파라미터 커스터마이즈
  • overdragResistanceFactor - 오버드래그 저항 계수 제어

이러한 설정은 src/index.tsx의 Props 타입 정의(10번째 줄부터)에 상세히 설명되어 있습니다.

실제 적용 및 모범 사례

설치 및 기본 사용법

React Native Reanimated Bottom Sheet를 사용하려면 먼저 저장소를 클론합니다.

git clone https://gitcode.com/gh_mirrors/re/react-native-reanimated-bottom-sheet

이후 의존성을 설치하고 네이티브 모듈을 링크합니다.

일반적인 사용 시나리오

  1. 지도 앱 - 장소 세부 정보 표시(예: Example/Map.js)
  2. 미디어 플레이어 - 음악 재생 제어(예: Example/AppleMusic.tsx)
  3. 폼 입력 - 추가 입력 인터페이스 제공
  4. 메뉴 네비게이션 - 앱 기능 메뉴 표시

커스터마이징 및 확장

renderHeaderrenderContent 메서드를 재정의하여 바텀 시트의 모양과 콘텐츠를 완전히 커스터마이즈할 수 있습니다.

<BottomSheet
  snapPoints={['80%', '40%', '20%']}
  renderHeader={() => <CustomHeader />}
  renderContent={() => <CustomContent />}
/>

React Native Reanimated Bottom Sheet는 정교한 제스처 처리와 애니메이션 설계를 통해 모바일 앱에 부드럽고 자연스러운 바텀 시트 경험을 제공합니다. 핵심 강점은 고성능 애니메이션(Reanimated 기반 60fps), 유연한 제스처 제어(드래그, 탭 등), 풍부한 설정 옵션(다양한 앱 시나리오 적응), 그리고 우수한 사용자 경험(모바일 상호작용 디자인 준수)에 있습니다.

구현 세부 사항을 깊이 이해하려면 src/index.tsx의 전체 소스 코드, 특히 제스처 처리 및 애니메이션 계산 부분을 분석하는 것을 권장합니다.

태그: React Native Reanimated Gesture Handler Bottom Sheet 모바일 UI

7월 8일 03:23에 게시됨