본문 바로가기

Android/Tech

(52)
SharedPreferences 가 DataStore 에 대체될 수 밖에 없었던 이유 DataStore Android Jetpack Library 중 하나인 DataStore 는 안드로이드 생태계에 꽤 긴 시간 존재했던 SharedPreferences 의 대체재가 되었습니다. SharedPreferences 는 키-값 쌍으로 데이터를 저장할 수 있는 Light-Weight Database 입니다. 데이터는 디바이스에 직접적으로 저장되며, 별도의 비동기 처리 없이 데이터를 로드할 수 있어 간편하고 실용적인 API 입니다. 이러한 이유로, SharedPreferences 가 DataStore 에 의해 대체되었음에도 불구하고 여전히 사용되고 있는 앱이 많으리라 예상합니다. 사용해보면 상당히 편합니다. 대부분의 개발자들이 그러하듯, 기존에 사용되던 기술을 버리고 새로운 기술을 도입하는 것은 결코..
비트맵과 WebP 인간의 눈으로 디지털 디바이스에서 표시되는 이미지 (그림, 사진) 를 보는 것은 픽셀이라는 작은 점들이 빼곡히 모여있는 것을 보는 것과 같습니다. 학창 시절 미술 시간에 한 번 쯤은 해보았던 점묘화와 그 개념이 같습니다. 디바이스마다 사이즈가 다르고, 1개의 픽셀에 적용할 수 있는 비트 수가 다릅니다. 비트맵은 픽셀의 사각형 배열 내에서 각 픽셀의 색을 지정하는 비트 배열입니다. 개별 픽셀에 적용되는 비트 수에 따라 픽셀에 할당할 수 있는 색의 수가 결정됩니다. 즉, 비트 수가 높을 수록 더욱 다양한 색상을 할당할 수 있습니다. 픽셀당 비트 수 비트 당 색상 수 픽셀당 비트 수 1 2^1 = 2 픽셀당 비트 수 2 2^2 = 4 픽셀당 비트 수 4 2^4 = 16 픽셀당 비트 수 8 2^8 = 256 픽..
[Jetpack Compose] Image 의 ContentScale Jetpack Compose Image 안드로이드 앱 개발 시 이미지 표시를 위해 사용되는 Composable 입니다. 기존 XML 의 ImageView 와 같은 역할을 하며, Painter 를 기본적으로 지원하고 Bitmap 까지 지원합니다. 해당 Composable 의 파라미터 중 contentScale 은 이미지를 Composable 규격 내에서 어떻게 표시할 것인가를 결정합니다. XML 의 ImageView 속성 중 android:sacleType 속성과 역할이 같습니다. 다음은 각 속성값에 따른 이미지 표시를 정리했습니다. 보다 정확한 비교를 위해 5*5 의 체커보드 이미지를 사용했습니다. 1. Fit 최초로 Image Composable 을 구현하면 적용되어 있는 기본값이 Fit 입니다. 정사..
[Jetpack Compose] Clickable Ripple Effect 없애기 Android, iOS 등 모바일에서는 버튼이 눌렸다는 사실을 유저에게 알리기위해 Ripple Effect 가 존재합니다. 보통은 호숫가에 던져진 돌에 의해 파동이 일어나듯, 터치한 부분을 중심으로 원이 커져가는 형태입니다. 다만, 텍스트를 버튼 대신 사용하거나, 굳이 Ripple Effect 가 필요하지 않은 곳에는 Ripple Effect 가 없는 편이 UI적으로 더욱 좋은 경우가 있습니다. 안드로이드의 경우, XML 을 사용했을 때는 버튼 이외의 다른 View 에 지정하지 않은 Riffle 이 생성되는 경우가 적었습니다. 하지만 Compose 로 넘어오면서, Modifier.clickable { } 을 통해 클릭 이벤트를 추가해주면 자동으로 Ripple Effect 가 추가됩니다. 이를 없애는 방법..
[Jetpack Compose] 상태 호이스팅 기존 XML 방식에는 큰 문제점이 하나 있었는데, 그것은 바로 View 가 스스로의 상태를 정의하고 보존한다는 것입니다. 상태는 View 를 그 자체로 인식할 수 없도록 하며, 이는 곧 테스트 가능성과 재사용성을 저해하는 원인이 됩니다. State Hoisting Jetpack Compose 를 활용하여 UI 를 작성할 때에 사용할 수 있는 패턴입니다. Composable 은 XML 방식의 View 와 다르게, 그 자체로는 Stateless 상태입니다. 얼마든 재사용할 수 있고, 얼마든 테스트할 수 있습니다. 다만, Composable 이 특정한 상태가 부여되거나 특정 상황에 결속되는 경우가 있습니다. 전자는 TextField, Scrollable 한 Composable 이 해당하고, 후자의 경우 클릭 ..
[Glide] Glide 의 Cache Glide 사용하고 계신가요? 안드로이드 개발자들이 가장 사랑하는 이미지 처리 라이브러리입니다. 저 또한 애용 중이며, 많은 분들께서 사용 중이시리라 생각합니다. 수많은 메서드를 통해 이미지 수정 및 처리가 가능하고 Third-Party-Library도 많은 데다가 gif까지 훌륭히 지원하니, 놀랍도록 우수한 라이브러리가 등장하지 않는 이상은 Glide가 다른 라이브러리에게 자리를 내어줄 일은 없어 보입니다. Glide는 기본적인 캐시(Cache)를 지원하고 있습니다. 그럴 수 밖에 없는 것이, 앱 내 리소스에 이미지를 포함시키기에는 너무나 방대한 양의 이미지 파일을 저장해야 하는 경우가 많을 것이기 때문입니다. 아래는 제가 직접 제작한 1인 개발 앱 입니다. 저는 Glide에 기본 캐시가 있다는 것을 ..
[Dagger-Hilt] ActivityScope 와 ActivityRetainedScope 의 차이 Hilt Hilt 는 현재 가장 주목 받는 DI (Dependency Injection) 라이브러리입니다. 안드로이드 제트팩 라이브러리 이기도 하죠. Hilt 에는 수많은 스코프 가 있습니다. 스코프의 존재 이유는 외부에서 생성되어 주입되는 인스턴스가 안드로이드 컨테이너의 생명주기에 따라 자동적으로 생성 및 해제되도록 하기 위해서입니다. 제 때 생성되지 않아 문제가 생기는 경우나, 해제되지 않아 지속적으로 메모리가 낭비되는 상황을 방지하기 위해서지요. Scoping an object A to another object B means that throughout the lifecycle of B, it’ll always have the same instance of A. (오브젝트 A를 B에 스코핑하는 것..
Coroutine Dispatcher 란 무엇인가? 안드로이드 개발을 꽤 오래 하셨던 분들, 또는 지방에서 일하고 계신 분들은 자바로 안드로이드 개발을 해보셨을겁니다. 저 또한 그랬습니다. 처음 개발을 배울 때부터 자바로 배워서, 코틀린같은 고급 언어는 굉장히 낯설었습니다. 코틀린의 코루틴이 그랬습니다. AsyncTask 나 Thread 를 사용해서 외부와 통신해왔던 저로서는 받아들이기 여간 어려운 것이 아니었습니다. 코틀린으로의 전환 이후 가장 처음 마주한 것이 코루틴이었습니다. 코루틴은 다음과 같이 실행됩니다. CoroutineScope(Dispatchers.IO).launch { // do something } CoroutineScope 는 코루틴을 실행시키기 위해서 꼭 필요하다는 것은 쉽게 알 수 있습니다. 그렇다면 Dispatcher 는 뭘까요?..