Lottie で Xamarin.Forms のスプラッシュページを作ってみた.
Airbnb の Lottie が話題です.
Lottie の説明はこちらがわかりやすいです.
Lottie ですが、じつは Xamarin(Android/iOS/Forms)でも使えます!
今回は Lottie を使って Xamarin.Forms の スプラッシュページを実装してみます.
Android プロジェクト
Android では MainActivity の前に SplashActivity を一枚挟むことでスプラッシュページを実現します.
ただの画像を表示するだけならば Activity のスタイルに android:windowBackground を指定するだけでよいのですが、Lottie のアニメーションは LottieAnimationView というビューとして実装されているので、Activity のレイアウトにこちらのビューを設定することで実現します.
Resources.values.styles.xml
<?xml version="1.0" encoding="UTF-8"?>
<resources>
<style name="MyTheme" parent="MyTheme.Base">
</style>
<style name="MyTheme.Base" parent="Theme.AppCompat.Light.NoActionBar">
<item name="colorPrimary">@color/primary</item>
<item name="colorPrimaryDark">@color/primaryDark</item>
<item name="colorAccent">@color/accent</item>
<item name="android:windowBackground">@color/window_background</item>
<item name="colorButtonNormal">@color/primary</item>
<item name="android:textColorPrimary">@color/white</item>
<item name="android:colorActivatedHighlight">@android:color/transparent</item>
</style>
<style name="Theme.Splash" parent="Theme.AppCompat.Light.NoActionBar">
<item name="android:windowNoTitle">true</item>
<item name="android:windowActionBar">false</item>
<item name="android:windowFullscreen">true</item>
<item name="android:windowContentOverlay">@null</item>
<item name="android:windowBackground">@drawable/bg_color</item>
</style>
</resources>
まず、MainActivity とは別にスプラッシュページ用のテーマを用意します.今回はフルスクリーンの設定に加えて、背景を設定しています.
背景の android:windowBackground ですが、android:colorBackground でも同様のことは行えますが、こちらだと一瞬黒い画面が表示されてしまうので、あえて android:windowBackground を使用しています.
Resources.values.colors.xml
<resources>
<color name="primary">#2196F3</color>
<color name="primaryDark">#1976D2</color>
<color name="white">#FFF</color>
<color name="black">#000</color>
<color name="accent">#FFC107</color>
<color name="window_background">#F5F5F5</color>
<drawable name="bg_color">#02d1c4</drawable>
</resources>
背景色は colors.xml に定義しています.
SplashActivity.cs
using Android.Animation;
using Android.App;
using Android.Content;
using Android.OS;
using Com.Airbnb.Lottie;
namespace LottieSample.Droid
{
[Activity(Theme = "@style/Theme.Splash",
MainLauncher = true,
NoHistory = true)]
public class SplashActivity : Activity, Animator.IAnimatorListener
{
protected override void OnCreate(Bundle savedInstanceState)
{
base.OnCreate(savedInstanceState);
SetContentView(Resource.Layout.Activity_Splash);
var animationView = FindViewById(Resource.Id.animation_view);
animationView.AddAnimatorListener(this);
}
public void OnAnimationCancel(Animator animation)
{
}
public void OnAnimationEnd(Animator animation)
{
StartActivity(new Intent(Application.Context, typeof(MainActivity)));
}
public void OnAnimationRepeat(Animator animation)
{
}
public void OnAnimationStart(Animator animation)
{
}
}
}
SplashActivity.cs の実装です.
Animator.IAnimatorListener を継承して、アニメーション終了時に MainActivity に遷移するようにしています.
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.airbnb.lottie.LottieAnimationView
android:id="@+id/animation_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:lottie_fileName="LottieLogo1.json"
app:lottie_autoPlay="true"
android:layout_centerVertical="true"
android:layout_centerHorizontal="true" />
</RelativeLayout>
レイアウトは上記のようになっています.
レイアウトで指定している JSON ファイルは Assets に BuildAction = “AndroidAsset” で配置しています.
実装結果です.
Android pic.twitter.com/cZ9piREVFp
— Daiki Kawanuma (@Santea3173) 2017年3月8日
android:windowBackground が表示されてからアニメーションが始まるまで1秒少し遅延がありますが、おおよそいい感じかと思います.
以上が Android プロジェクトの実装です.
iOS プロジェクト
iOS も Android と同様に SplashViewController を一枚挟むことでスプラッシュページを実現します.
iOS では LaunchScreen があるので、そこに Lottie のビュー(iOS では LOTAnimationView になります)を追加すればよいかと思ったのですが、LaunchScreen にはカスタムビューを使えないという制限があったので、Android と同様に SplashViewController を用います.
AppDelegate.cs
using System;
using System.Collections.Generic;
using System.Linq;
using Foundation;
using Lottie.Forms.iOS.Renderers;
using UIKit;
namespace LottieSample.iOS
{
[Register("AppDelegate")]
public partial class AppDelegate : global::Xamarin.Forms.Platform.iOS.FormsApplicationDelegate
{
public override UIWindow Window { get; set; }
public override bool FinishedLaunching(UIApplication app, NSDictionary options)
{
if (Window == null)
{
Window = new UIWindow(frame: UIScreen.MainScreen.Bounds);
var initialViewController = new SplashViewController();
Window.RootViewController = initialViewController;
Window.MakeKeyAndVisible();
return true;
}
else
{
global::Xamarin.Forms.Forms.Init();
AnimationViewRenderer.Init();
LoadApplication(new App());
return base.FinishedLaunching(app, options);
}
}
}
}
まず、AppDelegate です.
Window = null ならば SplashViewController に遷移します.そうでないならば Forms の初期化を行います.
using Airbnb.Lottie;
using UIKit;
namespace LottieSample.iOS
{
public partial class SplashViewController : UIViewController
{
public SplashViewController() : base("SplashViewController", null)
{
}
public override void ViewDidLoad()
{
base.ViewDidLoad();
var animationView = LOTAnimationView.AnimationNamed("LottieLogo1");
this.View.AddSubview(animationView);
animationView.PlayWithCompletion((animationFinished) =>
{
UIApplication.SharedApplication.Delegate.FinishedLaunching(UIApplication.SharedApplication,
new Foundation.NSDictionary());
});
}
public override void DidReceiveMemoryWarning()
{
base.DidReceiveMemoryWarning();
}
}
}
SplashViewController では、LOTAnimationView を追加し、アニメーション終了時のイベントで再度 FinishedLaunching をコールし、Forms の初期化を行います.
FinishedLaunching の引数の LaunchOptions が null の場合、NRE でクラッシュしたのでインスタンスを設定していますが、どこかにグローバル変数が定義されていませんかね?
LOTAnimationView.AnimationNamed(“LottieLogo1”) で指定した JSON ファイルはプロジェクト直下に BuildAction = “BundleResource” で配置しています.
iOS pic.twitter.com/X852GdObiW
— Daiki Kawanuma (@Santea3173) 2017年3月8日
こちらが実装結果です.
Android と同様に、LaucheScreen が表示されてから少し遅延がありますが、おおよそいい感じかと思います.
以上が iOS プロジェクトの実装です.
まとめ
今回は Lottie を使って Xamarin.Forms のスプラッシュページを実装してみました.
Lottie は高度なアニメーションを簡単に実装できるのでとても便利ですね!Xamarin.Native、Xamarin.Forms 両方で使えるのもポイント高いです.
スプラッシュページの実装としては、Android はおおよそ問題ないかと思うのですが、iOS の Forms 初期化部分はだいぶ怪しいと思っています.Forms 初期化部分で正しい実装がありましたら、教えていただけると嬉しいです.
以上です.
参考
ディスカッション
コメント一覧
まだ、コメントがありません