관리 메뉴

나만을 위한 블로그

[Android] 프레임 이미지들을 이어서 애니메이션 만들기 본문

Android

[Android] 프레임 이미지들을 이어서 애니메이션 만들기

참깨빵위에참깨빵_ 2021. 11. 11. 19:59
728x90
반응형

애니메이션이란 움직이지 않는 물체를 움직이는 것처럼 보이게 만드는 촬영기법이나 그렇게 만들어진 영화를 말한다.

그럼 어떻게 움직이지 않는 물체를 움직이는 것처럼 보이게 만들까?

 

동작이나 모양이 조금씩 다른 많은 그림이나 인형을 한 장면씩 촬영하여 영사하였을 때에 화상이 연속하여 움직이는 것처럼 보이게 하는 것

 

그냥 피사체 자세를 일일이 조금씩 바꿔가면서 사진을 많이 찍은 다음 이어붙여서 영상 형태로 만드는 것이다.

그럼 안드로이드에서도 비슷한 게 가능하지 않을까 싶어서 찾아보니 있었다. AnimationDrawable이란 걸 쓰는 것인데, 이번 포스팅에선 이걸 사용한 예제를 포스팅하려 한다. 먼저 아래의 압축파일을 다운받는다.

새 폴더.zip
1.57MB

두 선수가 권투를 하는 GIF 영상을 다운받아 직접 프레임 추출 프로그램을 써서 프레임 별 이미지로 나눈 것이다.

다운받고 폴더 내부를 확인하면 이런 이미지들이 들어있다.

 

 

이제 이것들을 안드로이드 스튜디오의 res/drawable 폴더 안에 집어넣는다. 그리고 drawable 폴더 안에 animation_test라는 xml 파일을 만든다. 만들 때 Root element는 animation-list로 설정해줘야 한다! 그 외에 건드릴 건 없다.

 

 

파일을 만들었다면 아래의 소스코드를 animation_test.xml 안에 복붙한다.

<?xml version="1.0" encoding="utf-8"?>
<animation-list xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:drawable="@drawable/frame0" android:duration="50" />
    <item android:drawable="@drawable/frame1" android:duration="50" />
    <item android:drawable="@drawable/frame2" android:duration="50" />
    <item android:drawable="@drawable/frame3" android:duration="50" />
    <item android:drawable="@drawable/frame4" android:duration="50" />
    <item android:drawable="@drawable/frame5" android:duration="50" />
    <item android:drawable="@drawable/frame6" android:duration="50" />
    <item android:drawable="@drawable/frame7" android:duration="50" />
    <item android:drawable="@drawable/frame8" android:duration="50" />
    <item android:drawable="@drawable/frame9" android:duration="50" />
    <item android:drawable="@drawable/frame10" android:duration="50" />
    <item android:drawable="@drawable/frame11" android:duration="50" />
    <item android:drawable="@drawable/frame12" android:duration="50" />
    <item android:drawable="@drawable/frame13" android:duration="50" />
    <item android:drawable="@drawable/frame14" android:duration="50" />
    <item android:drawable="@drawable/frame15" android:duration="50" />
    <item android:drawable="@drawable/frame16" android:duration="50" />
    <item android:drawable="@drawable/frame17" android:duration="50" />
    <item android:drawable="@drawable/frame18" android:duration="50" />
    <item android:drawable="@drawable/frame19" android:duration="50" />
    <item android:drawable="@drawable/frame20" android:duration="50" />
    <item android:drawable="@drawable/frame21" android:duration="50" />
    <item android:drawable="@drawable/frame22" android:duration="50" />
    <item android:drawable="@drawable/frame23" android:duration="50" />
    <item android:drawable="@drawable/frame24" android:duration="50" />
    <item android:drawable="@drawable/frame25" android:duration="50" />
    <item android:drawable="@drawable/frame26" android:duration="50" />
    <item android:drawable="@drawable/frame27" android:duration="50" />
    <item android:drawable="@drawable/frame28" android:duration="50" />
    <item android:drawable="@drawable/frame29" android:duration="50" />
    <item android:drawable="@drawable/frame30" android:duration="50" />
    <item android:drawable="@drawable/frame31" android:duration="50" />
    <item android:drawable="@drawable/frame32" android:duration="50" />
    <item android:drawable="@drawable/frame33" android:duration="50" />
    <item android:drawable="@drawable/frame34" android:duration="50" />
    <item android:drawable="@drawable/frame35" android:duration="50" />
    <item android:drawable="@drawable/frame36" android:duration="50" />
    <item android:drawable="@drawable/frame37" android:duration="50" />
    <item android:drawable="@drawable/frame38" android:duration="50" />
    <item android:drawable="@drawable/frame39" android:duration="50" />
    <item android:drawable="@drawable/frame40" android:duration="50" />
    <item android:drawable="@drawable/frame41" android:duration="50" />
    <item android:drawable="@drawable/frame42" android:duration="50" />
    <item android:drawable="@drawable/frame43" android:duration="50" />
    <item android:drawable="@drawable/frame44" android:duration="50" />
    <item android:drawable="@drawable/frame45" android:duration="50" />
    <item android:drawable="@drawable/frame46" android:duration="50" />
    <item android:drawable="@drawable/frame47" android:duration="50" />
    <item android:drawable="@drawable/frame48" android:duration="50" />
    <item android:drawable="@drawable/frame49" android:duration="50" />
    <item android:drawable="@drawable/frame50" android:duration="50" />
    <item android:drawable="@drawable/frame51" android:duration="50" />
    <item android:drawable="@drawable/frame52" android:duration="50" />
    <item android:drawable="@drawable/frame53" android:duration="50" />
    <item android:drawable="@drawable/frame54" android:duration="50" />
    <item android:drawable="@drawable/frame55" android:duration="50" />
    <item android:drawable="@drawable/frame56" android:duration="50" />
    <item android:drawable="@drawable/frame57" android:duration="50" />
    <item android:drawable="@drawable/frame58" android:duration="50" />
</animation-list>

 

대충 0.05초마다 이미지를 바꿔 보여주기 위해 만든 것이다. duration은 이미지가 보여지는 시간이기 때문에 이 부분의 숫자를 바꿔 사진들이 보여지는 시간을 바꿀 수 있다.

이제 메인 액티비티만 바꾸면 된다. 메인 액티비티의 XML을 아래와 같이 수정한다.

 

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">

    <ImageView
        android:id="@+id/imageview"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:background="@drawable/animation_test"/>

    <Button
        android:id="@+id/button"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_marginTop="130dp"
        android:text="버튼"/>

</LinearLayout>
import androidx.appcompat.app.AppCompatActivity;

import android.graphics.drawable.AnimationDrawable;
import android.os.Bundle;
import android.widget.Button;
import android.widget.ImageView;

public class MainActivity extends AppCompatActivity {

    private ImageView imageView;
    private Button button;
    private AnimationDrawable animationDrawable;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        imageView = findViewById(R.id.imageview);
        button = findViewById(R.id.button);
        animationDrawable = (AnimationDrawable) imageView.getBackground();

        animationDrawable.start();

        button.setOnClickListener(view -> {
            if (animationDrawable.isRunning())
                animationDrawable.stop();
        });
    }
}

 

(AnimationDrawable)은 꼭 써줘야 한다. 그 외에는 앱이 실행되면 프레임 이미지들이 연속으로 보여지면서 하나의 영상이 되고, 버튼을 눌렀을 때 실행중이면 실행을 멈춘다는 단순한 내용의 코드들이다.

실행해 보면 아래와 같이 작동한다.

 

그런데 이걸 어디에 응용할 수 있을까? 아래의 경우에 활용해서 앱을 풍부하게 만들 수 있을 것 같다.

 

  • 안드로이드 OS 수준에서 알림이 왔을 때(배터리 충전, 인터넷 연결 등) 애니메이션을 보여주고 싶을 때
  • 특정 이벤트가 실행되고 끝나기까지 애니메이션을 보여주고 싶을 때
반응형
Comments