2021/05/20

[SwiftUI]Lottieファイルを使ってSplash画面をつくる

swiftuiswift

SwiftUIベースのiOSアプリにLottieファイルを使って動きのある起動画面を作りました。

以下の手順で実施しました。

  1. SVGファイルの作成
  2. SVGファイルを元にLottieファイルを作成
  3. SwiftUIにLotieファイルを使ったViewを定義して実装

Lottieファイルとは

Lottieファイルは、Airbnb社が開発したアニメーションライブラリで、json形式で定義されたファイルを元にアニメーションを行うライブラリです。

  • 動画に比べて圧倒的に容量が軽い
  • どんなプラットフォームでも(ライブラリがあれば)動作する

みたいな利点があるようです。

Lottieファイルの作成

Lottieファイルを作るには本来なら、Adobe社が提供するAfter Effectsなどのツールを駆使しないと作れないようなのですが、そこまで時間がないので、Web上のツールを利用させていただきました。

※ SVGファイルの作成は割愛しますが、画像ファイルをSVGファイルにうまく変換してくれるようなサービスを使って土台を作っておくと楽でした。

LottieFilesというサービスに登録して、Convert SVG to Lottieのサービスを利用しました。

SVGファイルから簡単なアニメーションをつけてくれるので、ノンデザイナーでも簡単にLottieファイルを作成できました。

SwiftUIにLotieファイルを使ったViewを定義して実装

事前準備

作成したjson形式のLottieファイルをsplash.jsonという名前でアプリのルートディレクトリ(Info.plistとかがあるフォルダに格納しておきます。)

ライブラリのインストール

airbnb/lottie-iosを利用しました。

Swift Package Manager経由でもインストールできるようなので、Swift Package Managerを使ってインストールしました。

  1. https://github.com/airbnb/lottie-iosのURLを使ってパッケージを追加します。
  2. XCode上のアプリの設定で、Build SettingsからDead Code Strippingを探して、Noに設定します。

Viewの実装

以下のような感じになりました。

  • LottieパッケージのAnimationViewを使って、Lottieファイルを呼び出し、アニメーションの終了時に表示フラグをOffにするようにできます。
import SwiftUI
import Lottie

struct SplashScreen: View {
    
    @State var show = true
    
    var body: some View {
        ZStack(alignment: .center) {
            if (show) {
                SplashAnimationView(show: $show)
                    .frame(width: 120, height: 120)
            } else {
                // TODO show view after splash lottie animation
            }
        }
    }
}

struct SplashAnimationView: UIViewRepresentable {
    
    @Binding var show: Bool
    
    func makeUIView(context: Context) -> some AnimationView {
        let view = AnimationView(name: "splash", bundle: Bundle.main)
        // lottie animationを表示開始
        view.play { (status) in
            if status {
                withAnimation(.spring()) {
                    // 表示が終了したタイミングで表示フラグをOFFに
                    show = false
                }
            }
        }
        return view
    }
    
    func updateUIView(_ uiView: UIViewType, context: Context) {
    }
}

以上になります。