在移动开发中,将 Unity 作为游戏引擎嵌入 Android 原生 App,或者从 Unity 项目导出 Android 工程后需要调用原生功能(如获取设备信息、支付、推送等),两者之间的双向通信是核心需求。下面详细介绍通信原理、实现方式及注意事项。
一、通信基础原理
- **Unity 侧**:运行在 C# 虚拟机(Mono 或 IL2CPP)中,通过 `AndroidJavaClass` 和 `AndroidJavaObject` 通过 JNI 调用 Android Java 代码。
- **Android 侧**:原生 Java/Kotlin 代码通过 `UnityPlayer.UnitySendMessage` 方法向 Unity 中指定游戏对象上的 C# 方法发送消息。
本质上都是通过 JNI(Java Native Interface)桥接,Unity 封装了底层细节,使调用较为简洁。
二、Unity → Android 通信
1. 基础方式:使用 `AndroidJavaClass` 和 `AndroidJavaObject`
Unity C# 代码可以动态调用任意 Android Java 类。
```csharp
using UnityEngine;
public class UnityToAndroid : MonoBehaviour
{
void Start()
{
// 调用静态方法:UnityPlayer 类中的静态方法
AndroidJavaClass unityPlayer = new AndroidJavaClass("com.unity3d.player.UnityPlayer");
AndroidJavaObject currentActivity = unityPlayer.GetStatic<AndroidJavaObject>("currentActivity");
// 调用实例方法:Toast 显示消息
AndroidJavaClass toastClass = new AndroidJavaClass("android.widget.Toast");
toastClass.CallStatic<AndroidJavaObject>("makeText", currentActivity, "Hello from Unity", 0)
.Call("show");
}
}
```
2. 调用自定义 Android 方法
在 Android 工程中编写一个原生插件类:
```java
// 文件:MyNativePlugin.java
package com.example.myapp;
import android.app.Activity;
import android.widget.Toast;
import com.unity3d.player.UnityPlayer;
public class MyNativePlugin {
private static Activity activity = UnityPlayer.currentActivity;
public static void showToast(final String message) {
activity.runOnUiThread(new Runnable() {
@Override
public void run() {