🔰

【Flutter × 初心者】Live2D サンプルキャラを Unity で表示!flutter_unity_widget 導入ガイド編

2024/09/21に公開

はじめに

本記事を読んでいただきありがとうございます!
フリーランスエンジニア Tielです。
普段はnextjsとhubspotをやっています。

タイトル通りにflutter_unity_widgetを使って
Live2Dのサンプルキャラを表示するまでやります!
自分が苦労した具体的な課題や解決方法も含めて解説します。

実装時に比べながら参考にさせていただいたサイトです!
https://qiita.com/trimscash/items/355c7b107bce8193a58d

[2024年09月24日 追記]
サンプルモーションを動かす記事です。
https://zenn.dev/tiel/articles/47f79c39b129c9

自作のLive2dを動かしたい方はUnityの箇所を下記の方を参考にした方が良いと思われます。
https://zenn.dev/miri/articles/473068d32830ee

経緯

とある理由でflutterを使ってLive2Dを表示できるか気になったので実装してみることにしました。
またflutter、unity、live2dはほぼ触ってきてなく、フォルダ構成等を理解している程度です。
ソースを書くときは公式サイトを見ないとわからない程度の初心者です。

flutter_unity_widgetについて資料が少なく苦労したので書き起こすことにしました。
最初にしっかりと公式サイトを読んでおけば回避できたとこは多そうです...

主なプログラム経験

  • 会社員時代
    • OracleDB 5年
    • Java 5年
  • フリーランス時代
    • supabse 2年
    • nextjs 2年
    • hubspot 2年

対象者

  • Android開発のみ
  • 同じぐらいのflutter初心者

書き方や対処法も独自で対応した部分もあるので別に良い方法があれば教えていただきたいです。

それではやっていきましょう。

開発環境

  • OS
    • Mac M3
  • IDE
    • Visual Studio Code
  • Flutter
    • version 3.22
       後から記述しますが3.19と3.24はunity連携のとこでバグを確認したので3.22に変更しました。
    • Flutterで使用するパッケージ
      • flutter_unity_widget: ^2022.2.1
  • Unity
    • 2022.3.46f1
    • unityで使用するパッケージファイル
      • CubismSdkForUnity-5-r.2.unitypackage
      • fuw-2022.2.0.unitypackage

Flutter 事前準備

プロジェクトの生成

今回動かすプロジェクトを生成します。

flutter create unity_live2d_sample

プロジェクトが無事作れたことを確認します。

flutter run 

pubspec.yamlに追記

dependenciesにflutter_unity_widgetを追記します。

dependencies:
  flutter:
    sdk: flutter
  # The following adds the Cupertino Icons font to your application.
  # Use with the CupertinoIcons class for iOS style icons.
  cupertino_icons: ^1.0.6
+ flutter_unity_widget: ^2022.2.1  #追記部分

パッケージを取得

pubspec.yaml に依存関係を追加したら、以下のコマンドでパッケージを取得します。

flutter pub get

次に、アプリを実行します。Unity側の準備がまだのため、以下のエラーが発生しますが、これは正常です。

flutter run

エラー抜粋:

* What went wrong:
A problem occurred evaluating project ':flutter_unity_widget'.
> Project with path ':unityLibrary' could not be found in project ':flutter_unity_widget'.

Unityで必要なものをflutterプロジェクトに配置

Unityを使用するのにあたってFlutterプロジェクト内に配置することになるので
unityファイルをandroidやiosの同階層に作成します。

(フォルダ階層:unity_live2d_sampleはルート)

/unity_live2d_sample
    - android
    - ios
    - unity // 新規作成
    ....

フォルダにUnityで使用するパッケージを格納

Unityの作業時に使います。Unityで一回読み取ったら不要ですが
作り直しだと面倒なのとプロジェクトで使ったものをまとめてます。

(フォルダ階層:他フォルダ略)

/unity //前セクションで作成したフォルダ
    - unitypackage // 新規作成
        - CubismSdkForUnity-5-r.2.unitypackage
        - fuw-2022.2.0.unitypackage

unitypackageには下記2点をダウンロードして格納してください。

・CubismSdkForUnity-5-r.2.unitypackage
https://www.live2d.com/sdk/download/unity/

・fuw-2022.2.0.unitypackage
https://github.com/juicycleff/flutter-unity-view-widget/tree/master/unitypackages

筆者はどれも変わらないだろうと思い一番上のパッケージを選んだ為、バグが発生しました。

これで一旦はFlutter側はOKです。

Unityでの作業

いよいよUnityの操作です。

Unityバージョン:2022.3.46f1

UnityHubの設定

UnityHubを開きます。

デフォルトの保存場所の変更

ここで先に私が引っかかったとこを処理します。
設定(歯車マーク) -> プロジェクト -> デフォルトの保存場所
※プロジェクト生成時でも選べますが今後、変えるのめんどくさいので設定します。

ここを生成した「Flutterプロジェクト/unity」にしてください。

 /unity_live2d_sample
    - unity //ここを指定
    - unitypackage

ここが今までにない経験だったのでflutterプロジェクト in Unityプロジェクトになるので
手間取りました。

Unityプロジェクトの生成

いよいよプロジェクトの生成です。

  • プロジェクト名: Flutter_Live2d
  • テンプレート: 2D(Build-In Render Pipeline)
    ※3Dでもできるらしいですが試してないです。

初期状態

Unityパッケージをimportする

Projectタブ -> Assets を右クリック -> import -> Custom Package

Flutterプロジェクトのunity/unitypackageに保存したパッケージを両方インポートしてください。
それぞれ上部のバーに下記が表示されます。

  • fuw-2022.2.0.unitypackag -> Flutter
  • CubismSdkForUnity-5-r.2.unitypackage -> Live2D

UnityにLive2Dサンプルキャラを表示させる。

ここでサンプルキャラを表示させます。
Unityの操作ですね。今回はKoharuモデルにします。

Assets -> Live2D -> Cubism -> Samples -> Models -> Koharu
Koharuの青色がプレハブなのでSampleSceneのMainCameraにドラッグ&ドロップで入れます。

真ん中の再生ボタンを押したら小さいですが表示されます。

右のインスペクタのScaleを7,7,7にしたらちょうど良いぐらいになります。

Unity Build設定

UnityのナビゲーションバーのFlutterからAndroidビルドする必要があるのですが
その前にビルド設定が必要です。

File -> Build Settings...

  • Platform : Androidを選択

左下のPlayer Settingsを押します。

[Player Settingsの変更内容]

  • Mono -> IL2CPPに変更

  • ARM64 にチェック

Unity でFlutterをBuild

ここまでできたらもう少しです。

  • Export Android(Debug)を選択してください。

コンソールにSUCCESSFULがでたらOKです。
これでFlutterプロジェクトに「unityLibrary」が生成されました。

-- Android Debug Build: SUCCESSFUL --

Flutterで作業

ここでまたrunを実行してください。

flutter run

minSdkVersionのエラーになります。これはエラーの指示通りに修正します。

minSdkVersion 22  

[unity_live2d_sample/android/app/build.gradle]

defaultConfig {
    applicationId = "com.example.unity_live2d_sample"
-   minSdk = flutter.minSdkVersion
+   minSdk = 22
    targetSdk = flutter.targetSdkVersion
    versionCode = flutterVersionCode.toInteger()
    versionName = flutterVersionName
}

再度runを実行します。
ようやくまた画面が表示されるようになりました!

Flutter Live2Dを表示させるコード

これは公式にサンプルソースがあるのでコピーしてきます。
https://pub.dev/packages/flutter_unity_widget

import 'package:flutter/material.dart';
import 'package:flutter_unity_widget/flutter_unity_widget.dart';

void main() {
  runApp(
    const MaterialApp(
      home: UnityDemoScreen(),
    ),
  );
}

class UnityDemoScreen extends StatefulWidget {
  const UnityDemoScreen({Key? key}) : super(key: key);

  @override
  State<UnityDemoScreen> createState() => _UnityDemoScreenState();
}

class _UnityDemoScreenState extends State<UnityDemoScreen> {
  static final GlobalKey<ScaffoldState> _scaffoldKey =
      GlobalKey<ScaffoldState>();
  UnityWidgetController? _unityWidgetController;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      key: _scaffoldKey,
      body: SafeArea(
        bottom: false,
        child: WillPopScope(
          onWillPop: () async {
            // Pop the category page if Android back button is pressed.
            return true;
          },
          child: Container(
            color: Colors.yellow,
            child: UnityWidget(
              onUnityCreated: onUnityCreated,
            ),
          ),
        ),
      ),
    );
  }

  // Callback that connects the created controller to the unity controller
  void onUnityCreated(controller) {
    _unityWidgetController = controller;
  }
}

再度、run

flutter run 

おめでとうございます!
表示されるようになりました!

実機でも確認取れました。
エミュレータは推奨されないそうです。

表示させた感想

これを解決するのに2~3日間ぐらいかかっているのですが、改めて書き起こすと
flutterのソースはサンプルソースで動くのでソース等で引っかかる部分は無さそうですね。。。
そもそも私はflutterが3.19でその後3.24に上げたのが悪手でした。
3.19が原因のバグに気がつくのに時間かかった気がします。

見辛く拙い文章でしたがここまで読んでいただきありがとうございました。
今後、ボタンを押して手を動かすなども面白そうだったら記事を書いてみようと思います。

以降は引っかかって対応した内容を書いときます。

引っかかったもの

ndk.dirについて

local.propertiesにndk.dirを書くようにあったのですが
すでにflutterのndk宣言があるので重複でエラーになりました。
flutterのndkを消すかlocal.propertiesnのndk.dirを消せば
解消されるのですが、今回はndk.dir記載をしないようにしました。

UnityのMainCamera

そもそもflutterもunityもlive2dもわからない状態でやるのが悪いのですが
MainCameraにプレハブを入れ子にしないといけないのがわからず。表示されませんでした。
MainCameraど同階層でunity画面では出てるけど、エミュで出ないとなってました。。。

Flutter 3.19の罠

初回表示時は表示されないが
HotRestart(command + R)したときに表示される事象でした。

描画タイミングかと思い強制描画させたり、画面自体をuniquekeyを再発行したりとしたものの
治らず、githubのissuesをみることにしたところ下記がありました。

https://github.com/juicycleff/flutter-unity-view-widget/issues/985

現象は全く同じでした。
まさかFlutterのバージョンとは思わず唖然としました。
私はとりあえず3.24にアプデしました。

Flutter 3.24の罠

3.19から3.24に上げました。
長く原因不明から希望が見えたので舞い上がってしまい、よく読んでなかったとこがありました。
flutter run をするとビルドすらされなくなりました。

先ほどのissuesをよくみると3.24について記載がありました。
https://github.com/juicycleff/flutter-unity-view-widget/issues/985

If you upgrade to Flutter 3.24, you have to use the workaround in this issue as that version requires a small fix in the plugin that isn't on pub.dev yet.

3.24にする場合はこの問題に対応する必要があると!
https://github.com/juicycleff/flutter-unity-view-widget/issues/973

要するとwidgetで用意したAndroidのクラスがFlutterのバージョンアップで使えなくなってしまった
しかしprivateで宣言されているのと確認したところ使われてないから該当のクラスをコメントアウトか削除で
対応できるとのこと。

流石に自分で手を入れるのも気が引けたので泣く泣く3.24から3.22へ...

fuw-2022.x の 罠

これでバージョン関係を全て終わったと思いflutter runを実行
なんと表示後にクラッシュ

3.19だとHotRestateすれば表示されたので悪化?してると思われ
エラーログを見る限り原因は不明、buildSettingsを確認して細かく調整してみる治らず。

そこで最初の手順から確認してみることにそこで気づく。
unityにimportしてたパッケージが
「fuw-2022.1.1-v2.unitypackage」だということ。

思い返すと参考にしてたサイトさんとナビゲーションの表示が違ったなー
と思いながら「fuw-2022.2.0.unitypackage」にしてビルドしたら
無事表示されました。

Discussion