UI 모듈 개요
Petnow Android UI 모듈의 구조와 핵심 컴포넌트 설명.
Petnow UI 모듈이란?
Petnow UI 모듈은 반려동물 생체 데이터 캡처를 위한 즉시 사용 가능한 카메라 엔진을 제공하는 모듈입니다. 복잡한 카메라 설정, 탐지 로직, 이미지 처리 등을 모두 처리하여 개발자는 몇 줄의 코드만으로 전문적인 생체 인식 기능을 앱에 통합할 수 있습니다.

핵심 가치
- 🚀 빠른 통합: 복잡한 Camera2 API를 알 필요 없음
- 🎯 실시간 가이드: 사용자에게 최적의 촬영 방법 안내
- 🎨 커스터마이즈 가능: 앱의 디자인에 맞게 조정 가능
- 🧩 유연한 호스팅: View, Jetpack Compose, React Native 등 어디에나 통합
핵심 컴포넌트
UI 모듈은 하나의 엔진(CameraController) 과, 이를 화면에 올리는 여러 호스팅 방식으로 구성됩니다.
CameraController (엔진)
카메라·탐지 세션의 전체 라이프사이클을 관리하는 핵심 컴포넌트입니다. UI 렌더링에는 관여하지 않으며, 상태/이벤트만 외부로 전달합니다.
import io.petnow.ui.CameraController
import io.petnow.ui.config.LicenseInfo
val controller = CameraController(
context,
LicenseInfo(apiKey = "YOUR_API_KEY"),
coroutineScope,
)역할:
- 카메라 열기/닫기, 탐지 세션 시작/일시정지/재개
- 탐지 상태를
PetnowCameraDetectionListenerV2콜백과state프로퍼티(StateFlow)로 제공 - 최종 결과(
CameraResult)를 콜백으로 전달
호스팅 방식 선택
| 방식 | 설명 | 문서 |
|---|---|---|
CameraView (권장) | 프리뷰 + 기본 트래킹 UI를 그리는 FrameLayout 위젯. cameraView.controller = controller로 연결 | 기본 사용법 |
| 완전 커스텀 | 직접 만든 SurfaceView를 attachPreviewSurface()로 연결. SDK는 UI를 그리지 않음(100% 커스텀) | 완전 커스텀 UI |
PetnowCameraFragment (레거시) | Fragment 상속 방식. 신규 통합에는 권장하지 않음 | Fragment 방식(레거시) |
아키텍처
Petnow UI 모듈은 복잡한 상태관리와 ML 프레임워크 연동 로직을 숨기고, 개발자에게 간단한 인터페이스만 제공합니다.
세션 개념
촬영 과정은 두 가지 세션으로 관리됩니다:
Capture Session (캡처 세션)
- 서버에서 Petnow Server API(
createCaptureSession)를 호출하여 생성 - 서버에서 받은
captureSessionId를 클라이언트로 전달하여initializeCamera()에 넘김 - 하나의 Capture Session은 여러 Detection Session을 포함할 수 있음
Detection Session (탐지 세션)
- 실제 탐지를 시작한 시점부터 탐지가 완료되거나 실패할 때까지의 세션
- 사용자가 재촬영하면(
startDetection()재호출) 새로운 Detection Session이 시작됨
captureSessionId 전달 방법
서버에서 받은 captureSessionId(UUID)를 initializeCamera()에 전달합니다.
import java.util.UUID
lifecycleScope.launch {
// 서버에서 captureSessionId를 받아옵니다
// (서버는 Petnow Server API의 createCaptureSession을 호출)
val captureSessionId: UUID = yourServerApi.createCaptureSession(
species = "DOG",
purpose = "PET_PROFILE_REGISTRATION",
)
controller.initializeCamera(configuration, captureSessionId)
controller.startDetection()
}Server API: captureSessionId는 서버에서 Petnow Server API를 통해 생성합니다. 클라이언트에서 직접 생성하지 않습니다.
상태 관리
DetectionStatus
PetnowCameraDetectionListenerV2.onDetectionStatus로 전달되는, 현재 프레임의 대표 탐지 상태입니다. sealed class이며 Failed는 구체적인 원인(reason)을 포함합니다.
import io.petnow.ui.status.DetectionStatus
import io.petnow.ui.status.DetectionFailureReason
sealed class DetectionStatus {
data object NoObject : DetectionStatus() // 대상 미탐지
data object Processing : DetectionStatus() // 탐지 처리 중
data object Detected : DetectionStatus() // 탐지 성공
data object Finished : DetectionStatus() // 촬영 완료
data class Failed(val reason: DetectionFailureReason) : DetectionStatus()
}전체 DetectionFailureReason 값은 기본 사용법을 참고하세요.
CameraResult
최종 촬영 결과입니다.
import io.petnow.ui.CameraResult
sealed class CameraResult {
data class Success(
val fingerprintImageFiles: List<File>, // 생체 인식용 (강아지=코, 고양이=얼굴)
val appearanceImageFiles: List<File> // 외형(얼굴) 이미지
) : CameraResult()
data object Fail : CameraResult()
}데이터 흐름
핵심 포인트:
CameraController를 생성하고PetnowCameraDetectionListenerV2를 등록하면, 컨트롤러가 모든 카메라 로직을 처리하고 필요한 이벤트만 콜백으로 전달합니다.
데이터 흐름 설명
1. 실시간 상태 업데이트
PetnowCameraDetectionListenerV2를 통해 다음 이벤트를 수신합니다:onDetectionStatus(status): 현재 프레임의 탐지 상태 (DetectionStatus)onDetectionProgress(progress): 탐지 진행률 (0 ~ 100)
- 코/얼굴 트래킹 박스가 필요하면
state.value.currentDetectionResult(DetectionResult)를 사용합니다.
2. 최종 결과 전달
- 탐지가 완료되면 컨트롤러가 이미지를 저장하고
CameraResult를 생성합니다. onDetectionFinished(result)콜백으로 결과가 전달됩니다.CameraResult.Success- 촬영 성공 (이미지 파일 리스트 포함)CameraResult.Fail- 촬영 실패
다음 단계
UI 모듈의 구조를 이해했다면 다음 문서를 참고하세요:
- 기본 사용법 -
CameraView+CameraController통합하기 - 완전 커스텀 UI - 직접 만든 SurfaceView로 100% 커스텀 UI
- 커스터마이즈 -
CameraView가이드 UI 커스터마이즈 - 사운드 가이드 - 사운드 재생 상세 가이드
- Fragment 방식 (레거시) - 기존
PetnowCameraFragment통합 방식
참고 자료
- 시작하기 - SDK 설치