rksoftware

Visual Studio とか C# とかが好きです

Xamarin.Android で ARCore Sceneform (2つ目以降のエラーを順に対応 その1)

先日、Android のサンプルコードを Xamarin.Android に書き換えてみた記事を書きました。

その際に長い戦いとなった Android バインド ライブラリ 作成について書いていきます。 今回は、4歩目 - MainActivity.cs の2つ目以降のエラーに順に対応して行きます。

目次はこちら ↓

■ 前回のおさらい

前回の記事です。

1つ目のクラスはエラーを解消できました。

■ com.google.ar.sceneform.rendering.ModelRenderable クラス

このクラスは、
https://dl.google.com/dl/android/maven2/com/google/ar/sceneform/rendering/1.9.0/rendering-1.9.0.aar
にいます。これまでと同様の手順で Android バインド ライブラリプロジェクトを作成します。

■ エラー

いくつかエラーが出るので、頑張っていきます。

エラー    CS0534  'ModelRenderable' は継承抽象メンバー 'Renderable.MakeCopy()' を実装しません。
エラー   CS0111  型 'ModelRenderable.Builder' は、'MakeRenderable' と呼ばれるメンバーを同じパラメーターの型で既に定義しています。
エラー   CS0111  型 'ModelRenderable.Builder' は、'Build' と呼ばれるメンバーを同じパラメーターの型で既に定義しています。
エラー   CS0513  'ModelRenderable.Builder.GetRenderableClass()' は抽象ですが、非抽象クラスの 'ModelRenderable.Builder' に含まれています。
エラー   CS0534  'ViewRenderable' は継承抽象メンバー 'Renderable.MakeCopy()' を実装しません。
エラー   CS0111  型 'ViewRenderable.Builder' は、'MakeRenderable' と呼ばれるメンバーを同じパラメーターの型で既に定義しています。
エラー   CS0111  型 'ViewRenderable.Builder' は、'Build' と呼ばれるメンバーを同じパラメーターの型で既に定義しています。
エラー   CS0513  'ViewRenderable.Builder.GetRenderableClass()' は抽象ですが、非抽象クラスの 'ViewRenderable.Builder' に含まれています。

'XXXXXXXX' は継承抽象メンバー 'Renderable.MakeCopy()' を実装しません

スーパークラス Renderable の MakeCopy() メソッドは次の様になっています。

public abstract global::Com.Google.AR.Sceneform.Rendering.Renderable MakeCopy ();

エラーの出ているクラス(例えば ModelRenderable クラス)では、

public virtual unsafe global::Com.Google.AR.Sceneform.Rendering.ModelRenderable MakeCopy ()

で戻りの型が違っています。サブクラス側の方をスーパークラスの型に変えてみました。

<attr path="/api/package[@name='com.google.ar.sceneform.rendering']/class[@name='ModelRenderable']/method[@name='makeCopy' and count(parameter)=0]"
      name="managedReturn">Com.Google.AR.Sceneform.Rendering.Renderable</attr>

型 'XXXXXXXX.Builder' は、'MakeRenderable' と呼ばれるメンバーを同じパラメーターの型で既に定義しています

エラーの出ているクラス(例えば ModelRenderable クラス)では、

protected unsafe global::Com.Google.AR.Sceneform.Rendering.ModelRenderable MakeRenderable () { /* 省略 */ }
protected unsafe global::Com.Google.AR.Sceneform.Rendering.Renderable MakeRenderable () { /* 省略 */ }

で戻り値違いの同名メソッドが作られています。今回、MakeRenderable メソッドは使わないので、削除してみました。

<remove-node path="/api/package[@name='com.google.ar.sceneform.rendering']/class[@name='ModelRenderable.Builder']/method[@name='makeRenderable' and count(parameter)=0]"/>

型 'XXXXXXXX' は、'Build' と呼ばれるメンバーを同じパラメーターの型で既に定義しています

'XXXXXXXX.Builder.GetRenderableClass()' は抽象ですが、非抽象クラスの 'XXXXXXXX.Builder' に含まれています

やはり消してみました。

<remove-node path="/api/package[@name='com.google.ar.sceneform.rendering']/class[@name='ModelRenderable.Builder']/method[@name='build' and count(parameter)=0]"/>
<remove-node path="/api/package[@name='com.google.ar.sceneform.rendering']/class[@name='ModelRenderable.Builder']/method[@name='getRenderableClass' and count(parameter)=0]"/>

■ 追加エラー

エラーには一通り対処しましたが追加のエラーがでるので、頑張っていきます。

エラー    CS0513  'ModelRenderable.Builder.RenderableClass.get' は抽象ですが、非抽象クラスの 'ModelRenderable.Builder' に含まれています。
エラー   CS0513  'ViewRenderable.Builder.RenderableClass.get' は抽象ですが、非抽象クラスの 'ViewRenderable.Builder' に含まれています。

'XXXXXXXX.Builder.RenderableClass.get' は抽象ですが、非抽象クラスの 'XXXXXXXX.Builder' に含まれています。

今回は、抽象メンバーが非抽象クラスいるのが悪いと言われているので、試しに該当クラスを抽象クラスにしてみました。

<attr path="/api/package[@name='com.google.ar.sceneform.rendering']/class[@name='ModelRenderable.Builder']"
      name="abstract">true</attr>
<attr path="/api/package[@name='com.google.ar.sceneform.rendering']/class[@name='ModelRenderable.Builder']"
      name="final">false</attr>

■ 追加エラー

ここまでのエラーには一通り対処しましたが追加のエラーがでるので、頑張っていきます。

エラー    CS0102  型 'ModelRenderable.Builder' は既に 'cb_getSelf' の定義を含んでいます。
エラー   CS0111  型 'ModelRenderable.Builder' は、'GetGetSelfHandler' と呼ばれるメンバーを同じパラメーターの型で既に定義しています。
エラー   CS0111  型 'ModelRenderable.Builder' は、'n_GetSelf' と呼ばれるメンバーを同じパラメーターの型で既に定義しています。
エラー   CS0102  型 'ViewRenderable.Builder' は既に 'cb_getSelf' の定義を含んでいます。
エラー   CS0111  型 'ViewRenderable.Builder' は、'GetGetSelfHandler' と呼ばれるメンバーを同じパラメーターの型で既に定義しています。
エラー   CS0111  型 'ViewRenderable.Builder' は、'n_GetSelf' と呼ばれるメンバーを同じパラメーターの型で既に定義しています。
エラー   CS0229  ModelRenderable.Builder.cb_getSelf' と 'ModelRenderable.Builder.cb_getSelf' 間があいまいです
エラー   CS0229  ModelRenderable.Builder.cb_getSelf' と 'ModelRenderable.Builder.cb_getSelf' 間があいまいです
エラー   CS0121  次のメソッドまたはプロパティ間で呼び出しが不適切です: 'ModelRenderable.Builder.n_GetSelf(IntPtr, IntPtr)' と 'ModelRenderable.Builder.n_GetSelf(IntPtr, IntPtr)'
エラー   CS0229  ModelRenderable.Builder.cb_getSelf' と 'ModelRenderable.Builder.cb_getSelf' 間があいまいです
エラー   CS0229  ModelRenderable.Builder.cb_getSelf' と 'ModelRenderable.Builder.cb_getSelf' 間があいまいです
エラー   CS0229  ModelRenderable.Builder.cb_getSelf' と 'ModelRenderable.Builder.cb_getSelf' 間があいまいです
エラー   CS0121  次のメソッドまたはプロパティ間で呼び出しが不適切です: 'ModelRenderable.Builder.n_GetSelf(IntPtr, IntPtr)' と 'ModelRenderable.Builder.n_GetSelf(IntPtr, IntPtr)'
エラー   CS0229  ModelRenderable.Builder.cb_getSelf' と 'ModelRenderable.Builder.cb_getSelf' 間があいまいです

各エラー

どれも getSelf メソッドのようなので消してみます。

<remove-node path="/api/package[@name='com.google.ar.sceneform.rendering']/class[@name='ModelRenderable.Builder']/method[@name='getSelf' and count(parameter)=0]"/>

ここまでで、いったん Android バインド ライブラリがビルドできたので、MainActivity.cs のエラー対処を進めて行きます。

■ com.google.ar.core.HitResult クラス

このクラスは、NuGet パッケージ Xamarin.Google.ARCore を追加します。

■ エラー CS0117 'Resource.Id' に 'ux_fragment' の定義がありません

\Resources\layout\activity_main.axml の中身を Android サンプルのレイアウトの xml 中身で上書きします。

■ エラー CS0117 'ModelRenderable' に 'CreateBuilder' の定義がありません

ModelRenderable のインナークラス Builder と builder() メソッドがかぶってしまっているのでメソッド名前を変えてみました。

<attr path="/api/package[@name='com.google.ar.sceneform.rendering']/class[@name='ModelRenderable']/method[@name='builder' and count(parameter)=0]"
      name="managedName">CreateBuilder</attr>

■ エラー CS1061 'ModelRenderable.Builder' に 'SetSource' の定義が含まれておらず、型 'ModelRenderable.Builder' の最初の引数を受け付けるアクセス可能な拡張メソッド 'SetSource' が見つかりませんでした。using ディレクティブまたはアセンブリ参照が不足していないことを確認してください

SetSource メソッドは本来 ModelRenderable.Builder クラスのスーパークラスである Renderable.Builder クラスのメソッドですが、生成された C# コードでは継承関係がなくなっていました。
ModelRenderable.Builder クラスに SetSource メソッドを追加してみました。

<attr path="/api/package[@name='com.google.ar.sceneform.rendering']/class[@name='Renderable.Builder']/method[@name='setSource' and count(parameter)=2 and parameter[1][@type='android.content.Context'] and parameter[2][@type='int']]"
      name="return">com.google.ar.sceneform.rendering.Renderable.Builder</attr>

■ エラー CS0117 'Resource.Raw' に 'andy' の定義がありません

\Resources\ ディレクトリに raw ディレクトリを作ってその中に、 Android サンプルをビルドするとできる andy.sfb をコピーします。
プロパティでビルド アクションは AndroidResource にします。

まだまだエラーは消えないので、続きも書いて行こうと思います。

(つづく)