오늘은 MotionLayout
에 대해 알아보고 MotionLayout
을 활용해 Twitter 안드로이드 어플의 Splash 화면을 구현해보고자 합니다. Splash화면은 어플이 시작하면서 로딩이 필요할 때 잠깐 보이는 화면을 말합니다. 시작에 앞서 Twitter Splash화면 구현은 유튜브'Code with Joyce'님의 영상을 보며 만들었음을 알립니다. (해당 영상링크)
먼저 MotionLayout
에 대해 알아봅시다.
MotionLayout
MotionLayout
은 앱에서 모션과 위젯 애니메이션을 관리할 때 사용할 수 있는 레이아웃입니다. ConstraintLayout
의 서브클래스이기 때문에 ConstraintLayout
의 레이아웃 기능을 기초로 만들 수 있습니다.
Android Studio 4.0 버전부터 Motion Editor를 지원하게 되어 Device를 돌리지 않고도 Editor에서 Motion을 확인할 수 있게 되었습니다. 이게 굉장히 편해진 부분인데 Editor의 GUI로 쉽게 모션을 만들 수 있습니다.
특징
ConstraintLayout
의 Subclass이다. → Constraint Layout에서 Convert하여 사용한다.ConstraintLayout
과TransitionManager
를 합친 기능을 제공한다 .- 애니메이션이나 Transition을 xml파일 안에 모두 서술할 수 있다.
MotionLayout 예제 (Twitter Splah)
그럼 이제 예제를 통해 사용해보도록 하겠습니다.
먼저 우리가 만들게 될 화면을 보여드리도록 하겠습니다. 가능하시다면 화면만 먼저 보고 스스로 구글링을 하면서 똑같이 구현해보려고 노력해보시길 추천드립니다. 이렇게 해보고 막혔을 때 블로그를 쭉 보신다면 실력이 훨씬 오를 것입니다.
이제부터 코드를 설명하도록 하겠습니다.
1. 종속성 추가
MotionLayout
을 사용하기 위해서는 먼저 AndroidX
를 사용하거나 MotionLayout
지원 라이브러리를 Gradle에 추가해주어야 합니다. 보통 Empty Activity로 만든 코틀린 프로젝트에서는 기본적으로 AndroidX
가 추가되어 있으므로 넘어가도록 하겠습니다. (혹시 추가가 되어있지 않다면 공식문서를 참조하세요.)
2. MotionLayout
파일 만들기
먼저 대략적인 UI의 틀을 만들어봅시다. activity_main.xml
에 가셔서 가장 밖의 레이아웃의 배경색상을 Twitter 앱과 최대한 비슷한 색상으로 맞춰주겠습니다.저는 다음 색상을 사용했습니다.(#1DA1F2)
그리고 Twitter 사이트에 들어가서 화면에 새 그림을 가져와주겠습니다. 이 사이트에 들어가서 밑으로 스크롤하게 되면 'Get the goods' 메뉴에서 'Twitter logo'를 찾을 수 있습니다. 이것을 다운로드 해줍니다.

다운로드를 받았다면 폴더의 압축을 풀어줍니다. 그리고 Twitter logo > SVG 폴더에 들어갑니다. 우리는 하얀색 새 로고를 사용할 것이기 때문에 'Logo White'를 선택해줍니다.
이제 이 파일을 Android Studio에 가져오도록 하겠습니다. 해당 파일을 드래그해서 'res/drawable'폴더에 넣어줍니다. 알맞게 이름을 변경해주면 됩니다.
다시 activity_main.xml
로 와서 MotionLayout
안에 ImageView
를 넣어줍니다. 저는 다음과 같이 ImageView를 설정해주었습니다.
<ImageView
android:layout_width="140dp"
android:layout_height="140dp" app:srcCompat="@drawable/ic_logo_white" android:id="@+id/imageView"
app:layout_constraintTop_toTopOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintEnd_toEndOf="parent"
/>
이렇게 했을 때 안드로이드 스튜디오를 개발할 때 컨텐츠 접근성에 신경쓰도록 개발하라고 하는 메시지를 띄우는 것을 볼 수 있습니다.
Missing 'contentDescription' attribute on image
컨텐츠 접근성이란 컨텐츠가 사용자에게 제대로 보여지지 않을 경우(Ex> 엑스박스) 컨텐츠에 대한 설명을 적어놓아서 컨텐츠가 보이지 않더라고 설명을 보고 알 수 있게끔 해놓는 조치를 말합니다.
예제에서 사용한 ImvageView에서 컨텐츠 접근성을 주기 위해서는 두 가지 방법이 있습니다.
- xml을 이용하는 방법
android:contentDescription="String 추가" - Class를 이용하는 방법
imageView = view.findViewById(R.id.image_view) imageView.setContentDescription(getResources().getString(R.string.content_description))
ImageView에는 꼭 컨텐츠 접근성이 필요한 것은 아닙니다. 단, ListView 또는 TabLayout의 경우는 오히려 설명을 포함하면 탐색 속도가 늦춰지기 때문에 좋지 않습니다.
3. MotionScene 만들기
MotionLayout
은 app:layoutDescription
속성을 통해 MotionScene을 참조합니다. 이는 모션을 설명해주는 xml파일입니다.
이것을 만들기 위해서 activity_main.xml
파일에서 Design 파트에 들어가줍니다. 그리고 'Component Tree'에서 ConstraintLayout
를 우클릭 해줍니다. 우클릭을 해주면 'Conver to MotionLayout'이라는 선택지가 있을텐데 이것을 클릭해줍니다.
이렇게 해주면 Android Studio에서 자동으로 res폴더에 xml폴더를 새로 추가하고 activity_main_scene.xml
파일을 만들어준 것을 볼 수 있습니다. 또한 MotionLayout
에는 app:layoutDescription
속성을 추가해서 연결해준 것을 볼 수 있습니다.
4. Motion 설정하기
이제 Motion Editor에 대해 간략하게 설명해보도록 하겠습니다. activity_main.xml
파일에서 Design파트에 가보면 이런 그림이 생긴걸 볼 수 있을텐데요.

여기서 Motion을 설정해줄 수 있습니다. 먼저 'start'라고 써져있는 것을 'ConstraintSetStart'라고 부르고 'end'라고 써져있는 것을 'ConstraintSetEnd'라고 부릅니다. 이것은 activity_main_scene.xml
파일에서도 확인할 수 있습니다. 이것들은 처음과 마지막 순간에 View들에 대한 위치와 속성을 결정합니다.
새가 작아졌다가 커지는 모션을 설정하는 부분은 저 화살표를 클릭하여 설정해줄 수 있습니다. 화살표를 클릭하게 되면 'Transition'배너가 나타난 것을 보실 수 있습니다. 이제 여기에서 새 로고의 모션을 정해줄건데요. 새의 모션은 1~2초정도 작아졌다가 1초간 크기를 유지하고 화면을 꽉채우도록 하겠습니다.
'Transition'배너 이름 오른쪽에 플러스 그림이 있는 버튼을 클릭해줍니다. 그리고 'KeyAttribute'를 클릭해주고 Position는 20, Attribute는 scaleX
를 선택하고 "Add"를 눌러줍니다. 그러면 'Transition'배너에 점이 하나 생긴 것을 볼 수 있습니다. 0부터 100까지 모션이 어떻게 흐르는지를 타임라인으로 보여주는데 우리는 지금 20지점의 속성을 만들어준 것입니다.
점을 선택하면 scaleX
에 속성이 적혀있는 데 우리는 새를 줄일 것이기 때문에 scaleX
의 속성을 0.7로 설정하겠습니다. 그리고 +버튼을 누르고 scaleY
속성도 추가하여 동일하게 0.7로 맞춰주도록 하겠습니다.
이렇게 설정하면 0부터 20까지 타임라인이 흐를 때 새가 작아지는 것을 볼 수 있습니다.
다음으로 1초정도 크기가 유지되는 것을 구현하기 위해 아까처럼 'KeyAttribute'를 Position이 50, Attribute를 scaleX
로 설정해서 만들어줍니다. 이 부분도 동일하게 0.7로 만들어줍니다.
그 다음 화면을 꽉채우도록 설정하기 위해서 'KeyAttribute'를 Position이 100, Attribute를 scaleX
로 설정해서 만들어주고, 이번에는 scaleX
와 scaleY
의 속성을 50으로 설정하여 엄청 커지도록 하겠습니다.
이렇게 설정하고 Editor에서 재생을 눌러주면 위의 결과 화면과 같이 되는 것을 보실 수 있습니다.
혹시 동일하게 나오지 않는 분들을 위해 비교해보시라고 activity_main_scene.xml
파일의 코드를 첨부하겠습니다.
<?xml version="1.0" encoding="utf-8"?>
<MotionScene
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:motion="http://schemas.android.com/apk/res-auto">
<Transition
motion:constraintSetEnd="@+id/end"
motion:constraintSetStart="@id/start"
motion:duration="1000">
<KeyFrameSet>
<KeyAttribute motion:motionTarget="@+id/imageView" motion:framePosition="20" android:scaleX="0.7"
android:scaleY="0.7"/>
<KeyAttribute motion:motionTarget="@+id/imageView" motion:framePosition="50" android:scaleX="0.7"
android:scaleY="0.7"/>
<KeyAttribute motion:motionTarget="@+id/imageView" motion:framePosition="100" android:scaleX="50"
android:scaleY="50"/>
</KeyFrameSet>
<OnClick motion:targetId="@+id/imageView"/>
</Transition>
<ConstraintSet android:id="@+id/start">
</ConstraintSet>
<ConstraintSet android:id="@+id/end">
</ConstraintSet>
</MotionScene>
지금까지 MotionLayout
에 대해 알아보고 예제도 같이 만들어보았습니다. MotionLayout
을 통해 더 Active한 어플을 만들어보시길 추천드립니다! 지금까지 글을 읽어주셔서 감사합니다 (__)
'Android(Kotlin)' 카테고리의 다른 글
[Kotlin Android] View 객체 가져오기(1) - findViewById()와 Kotlin Android Extensions (0) | 2022.06.22 |
---|---|
[Kotlin Android] 반복문 (0) | 2022.06.05 |
[Kotlin Android] 정적 변수와 메소드 :: Companion Object (0) | 2022.05.30 |
[Kotlin Android] Array, ArrayList, List, MutableList (0) | 2022.05.28 |
[Kotlin Android] 람다식 (0) | 2022.05.27 |