アニメーションアイコンが作れるAndroid Icon Animatorを触ってみる

# AndroidIconAnimatorとは

GoogleのRoman Nurikにより神のようなツールが作られました。(まだPreview Releaseです)
https://romannurik.github.io/AndroidIconAnimator/


![image](https://qiita-image-store.s3.amazonaws.com/0/27388/07b5bcba-f4fe-89ce-e5aa-ac42afe1c836.png)

GUIでAndroidのAnimatedVectorDrawableを作れるツールです。

VectorDrawableのメリットなどはこちらをどうぞ。また最後の方にAnimated Vector Drawableについても紹介しています。
https://speakerdeck.com/takahirom/support-vector-drawable

これによりマテリアルデザインのicon animationが可能になります。
https://material.google.com/motion/creative-customization.html


これによりエンジニアいらずでデザイナがアニメーションするアイコンが作れてしまうかもしれません。

# アニメーションを再生してみる


かんたんに試すにはまず、画面上部のexamplesをクリックしてダウンロードします。
![image](https://qiita-image-store.s3.amazonaws.com/0/27388/bb31edb5-be9b-8ba0-add1-d06da5ecd067.png)

zipファイルがダウンロードできるので、その中のファイルをページにドラッグアンドロップします。
すると読み込まれ、そして再生ボタンを押すと以下のように再生されます。
![icon_animator.gif](https://qiita-image-store.s3.amazonaws.com/0/27388/a679ba50-24a1-2fd1-bf42-eeda03f582c0.gif)

また、この記事を公開した後に教えてもらったのですが、**SVGファイルを画面にドラッグ・アンド・ドロップで要素を追加できる**ようです。

# アニメーションを構成する要素
各要素を説明すると以下のようになります。

![image](https://qiita-image-store.s3.amazonaws.com/0/27388/acf9d0fd-6bae-5fd3-1f55-993dfde2f154.png)


## path

実際のSVGのパスのデータ(pathData)と色や大きさなどのデータがふくまれているものです。
この画像のデータはアニメーションしている矢印の上の部分です。
![image](https://qiita-image-store.s3.amazonaws.com/0/27388/4d87535e-d8f4-78e3-527f-3a096b9bb745.png)

### pathに対してのアニメーション要素
pathに対して、時計アイコンを押してアニメーションを追加できます。
![image](https://qiita-image-store.s3.amazonaws.com/0/27388/fca0968d-8322-9b2e-1fb1-24af19c44f0d.png)


以下の要素がアニメーション可能になります。
![image](https://qiita-image-store.s3.amazonaws.com/0/27388/d7f081bb-1ca8-67ea-5d81-2fea51869c85.png)

普通に大きさを変えたり、横にスライドさせるアニメーションの他にも特殊なアニメーションを利用できます。

あるパスからあるパスに滑らかに変更するアニメーション(path morphing)であるpathDataというものが利用できるのですが、これは現状ではAPI Level 21(Android 5.0以上でしか利用できないので注意してください。)

![path_morphing.gif](https://qiita-image-store.s3.amazonaws.com/0/27388/23cbf94b-1b53-c8bb-dd21-45ca1cc3d477.gif)


今回の矢印を先頭から消すアニメーションのtrimPathStartなどはSupport Libraryという公式ライブラリを利用することで、低いAPIレベルでもアニメーション可能となります。
つまり、この矢印のアニメーションはpathDataのアニメーションが入っていないので、Android 4.xでもちゃんと動作するはずです。
(直接関係ないのですが、Material DesignのNatural easing curvesとして紹介されているアニメーションの加速度などの調整ができるInterpolatorも設定できますね。)
![icon_animator.gif](https://qiita-image-store.s3.amazonaws.com/0/27388/a679ba50-24a1-2fd1-bf42-eeda03f582c0.gif)


## layer group

layer groupは複数のpathをまとめるもので、このlayer groupに対してアニメーションを追加することができます。
例えばpage_1に対して、右の時計マークを押して、scaleアニメーションを追加すると以下のように全体の大きさをアニメーションします。
![image](https://qiita-image-store.s3.amazonaws.com/0/27388/c2a139d8-0b86-5f07-37e3-45a8d2e7094f.png)
(右側のプロパティの設定でアニメーション秒数や最初の大きさと最後の大きさを指定してあげました。)
![grop_scale.gif](https://qiita-image-store.s3.amazonaws.com/0/27388/44dd49ad-1d9b-60c0-b7be-4491f85cc3a3.gif)

### layer groupに対してのアニメーション要素

ここにあるプロパティをアニメーションすることができます。
大きさを変えたり、横に移動したりできます。
![image](https://qiita-image-store.s3.amazonaws.com/0/27388/cba4906f-2a5f-8022-990b-5e12f31f6a70.png)

## clip path
アニメーション要素の追加から追加でき、これにより描画しない領域をアニメーションできたりするようなのですが、現状調べきれていません。

![clip.gif](https://qiita-image-store.s3.amazonaws.com/0/27388/3566dba3-ad1d-db43-20ce-bf3eebf710e5.gif)

# ExportしたAnimated Vector Drawable
以下のように吐き出されますのでdrawableフォルダに入れてください

```xml
<animated-vector
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:aapt="http://schemas.android.com/aapt">
    <aapt:attr name="android:drawable">

        <vector
            xmlns:android="http://schemas.android.com/apk/res/android"
            android:width="24dp"
            android:height="24dp"
            android:viewportWidth="24"
            android:viewportHeight="24">

            <!-- ****layer group**** -->
            <group android:name="page_1">
                <group android:name="artboard">

                    <!-- ****path**** -->
                    <path
                        android:name="top_arrow"
                        android:pathData="M4,12 L12,4"
                        android:strokeColor="#ff979797"
                        android:strokeWidth="2"
                        android:trimPathEnd="0"
                        android:strokeLineCap="square"
                        android:strokeLineJoin="miter"
                        android:strokeMiterLimit="10"/>
                    <path
                        android:name="bottom_arrow"
                        android:pathData="M 4 12 L 12 20"
                        android:strokeColor="#ff979797"
                        android:strokeWidth="2"
                        android:trimPathEnd="0"
                        android:strokeLineCap="square"
                        android:strokeLineJoin="miter"
                        android:strokeMiterLimit="10"/>
                    <path
                        android:name="middle"
                        android:pathData="M4.5,12 L20,12"
                        android:strokeColor="#ff979797"
                        android:strokeWidth="2"
                        android:strokeLineCap="butt"
                        android:strokeLineJoin="miter"
                        android:strokeMiterLimit="10"/>
                </group>
            </group>
        </vector>
    </aapt:attr>

    <!-- ****top_arrowに対するアニメーション**** -->
    <target android:name="top_arrow">
        <aapt:attr name="android:animation">
            <objectAnimator
                xmlns:android="http://schemas.android.com/apk/res/android"
                android:name="top_arrow"
                android:propertyName="trimPathEnd"
                android:startOffset="525"
                android:duration="731"
                android:valueFrom="0"
                android:valueTo="1"
                android:valueType="floatType"
                android:interpolator="@android:interpolator/fast_out_slow_in"/>
        </aapt:attr>
    </target>

    <!-- ****bottom_arrowに対するアニメーション**** -->
    <target android:name="bottom_arrow">
        <aapt:attr name="android:animation">
            <objectAnimator
                xmlns:android="http://schemas.android.com/apk/res/android"
                android:name="bottom_arrow"
                android:propertyName="trimPathEnd"
                android:startOffset="525"
                android:duration="731"
                android:valueFrom="0"
                android:valueTo="1"
                android:valueType="floatType"
                android:interpolator="@android:interpolator/fast_out_slow_in"/>
        </aapt:attr>
    </target>

    <!-- ****middleに対するアニメーション**** -->
    <target android:name="middle">
        <aapt:attr name="android:animation">
            <objectAnimator
                xmlns:android="http://schemas.android.com/apk/res/android"
                android:name="middle"
                android:propertyName="trimPathStart"
                android:duration="550"
                android:valueFrom="1"
                android:valueTo="0"
                android:valueType="floatType"
                android:interpolator="@android:interpolator/fast_out_slow_in"/>
        </aapt:attr>
    </target>
</animated-vector>

```

# まとめ

結構完成度が高く、Animated Vector Drawableでできそうなところは一通りサポートしているようです。
現状だと、デザイナーが使うにはtrimPathStartやInterpolatorなどを理解しないといけないので大変ですが、
イケイケなアプリを作っていきましょう！