通過aar包實現Unity與安卓間的通訊
前言:
(最近做了一個虛擬現實和物聯網專案,名字聽起來高大上,其實就是用Unity做個安卓端的虛擬現實場景,然後通過藍芽接收單片機發來的溫度資料,在場景裡顯示。由於Unity引擎本身沒法呼叫藍芽,所以需要通過呼叫安卓aar包來呼叫藍芽,所以涉及到了安卓和unity之間的通訊。)
本例不再展示藍芽的呼叫,只是通過Unity呼叫顯示日期和Toast來示範兩者間的通訊。
網上的教程很多是Eclipse,而講Android studio的很少用aar包,或者教程對應的軟體版本較早。本文旨在總結網上的各種教程,望能給大家一些幫助。
本專案使用的是Unity 5.5.4 和 Android Studio 3.0.1,其它版本方法可能略有不同,但大致相似。
一.Android Studio
1.新建工程
開啟Android Studio,新建工程,如圖所示。
工程設定:命名為UnityAndroid。包名為com.learn.unityandroid(注意都是小寫)
再往後一直點Next,最後點Finish,預設建立了MainActivity。
2.修改檔案
點選左上角的選單,選擇Project檢視,可以顯示更加詳細的層級結構。
首先修改app資料夾下的build.gradle檔案。
開啟後修改第一行,將application改為library。(這樣就可以釋出aar包)
刪除掉第6行,否則會報錯。
點選上方的錘子按鈕來Make Project,以測試是否可以釋出aar包。
第一次Make Project的時間會比較長。完成之後,可以看到在app-build-outputs-arr資料夾下已經發布了app-debug.aar,說明打包成功。
3.匯入Unity提供給安卓的classes.jar
在Unity的安裝目錄中找到classes.jar,Windows系統中的安卓包路徑如下(其他系統或Unity版本的路徑請自行搜尋):
E:\Unity 3d\Editor\Data\PlaybackEngines\AndroidPlayer\Variations\mono\Release\Classes
(當然,我的Unity是裝在了E盤,大家要換成自己安裝的路徑。找不到的可以右鍵桌面Unity圖示,點選屬性就能看到路徑。)
切記一定要將這個檔案備份,多多益善,不然弄丟了很麻煩的(切身經歷= = 如果匯入的classes.jar和你的Unity版本不對應很有可能出錯,所以網上也不好找,可能要重新下Unity才有。雲盤裡存一份也是個好辦法。)
將這個jar包拖到libs資料夾下,如圖(看見沒,我備份了很多):
右鍵匯入的classes.jar,點選倒數第二項的“Add As Library”以建立依賴關係。
最終的build.gradle如下:
apply plugin: 'com.android.library'
android {
compileSdkVersion 26
defaultConfig {
minSdkVersion 14
targetSdkVersion 26
versionCode 1
versionName "1.0"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
}
dependencies {
implementation fileTree(include: ['*.jar'], dir: 'libs')
implementation files('libs/classes.jar')
}
4.修改工程以便unity呼叫
修改MainActivity.java檔案。
讓MainActivity繼承UnityPlayerActivity,因為我們將要釋出的Unity安卓端應用本身就是一個Activity。
將圖示一行刪除,因為我們不需要介面。
然後我們寫一個ShowDate方法,呼叫Unity中Main Camera物體上掛的指令碼中的GetDate方法,以更新顯示日期;再寫一個ShowToast方法,來被Unity呼叫,以顯示Toast。
完整程式碼如下:
package com.learn.unityandroid;
import android.os.Bundle;
import android.widget.Toast;
import com.unity3d.player.UnityPlayer;
import com.unity3d.player.UnityPlayerActivity;
import java.text.SimpleDateFormat;
public class MainActivity extends UnityPlayerActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
public void ShowDate(){
SimpleDateFormat sDateFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
String date = sDateFormat.format(new java.util.Date());
UnityPlayer.UnitySendMessage("Main Camera","GetDate",date);
}
public void ShowToast(String str){
Toast.makeText(this, str, Toast.LENGTH_SHORT).show();
}
}
將res資料夾下的layout資料夾刪除,因為我們不需要介面。
同理,再將values資料夾下的styles.xml檔案刪除。
開啟下邊的AndroidManifest檔案。
可以看見此時已經顯示紅色,表明有錯誤。
把theme修改成安卓自帶的主題就可以了:
將activity的name改為如圖所示,以防止報錯。
再新增一行meta-data資訊,否則釋出的apk是無法執行的(別問我怎麼知道的……)
最終的AndroidManifest如下:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.learn.unityandroid">
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@android:style/Theme.NoTitleBar">
<activity android:name="com.learn.unityandroid.MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
<meta-data android:name="unityplayer.UnityActivity" android:value="true"/>
</activity>
</application>
</manifest>
點選小錘子按鈕來Make Project
右鍵剛剛釋出的aar包。
點選下方的Show In Explorer,顯示具體檔案。雙擊開啟。
在壓縮包裡將libs資料夾下的classes.jar刪除,因為後期Unity呼叫的時候會自動加入。
好了,我們的安卓包已經制作完成,接下來就是Unity方面的事了。
二、Unity
1.新建工程
新建工程,命名為UnityAndroid(可以隨便起名)。在場景中建立Canvas畫布,然後新增Text和Button。按ctrl+s儲存場景,命名為main。
scene中檢視如下:
在File - Build Setting裡匯入main場景,並且將平臺切換成安卓。
2.建立指令碼並繫結
在Main Camera上掛載新建的名為Main Camera的指令碼。開啟MainCamera指令碼進行編輯,最終程式碼如下:
using UnityEngine;
using UnityEngine.UI;
public class MainCamera : MonoBehaviour
{
//獲取日期顯示檔案的text元件
public Text dateText;
private AndroidJavaObject mainActivity;
//每幀呼叫安卓的ShowDate函式,再通過安卓呼叫下方的GetDate函式。
void Update()
{
AndroidJavaClass jc = new AndroidJavaClass("com.unity3d.player.UnityPlayer");
mainActivity = jc.GetStatic<AndroidJavaObject>("currentActivity");
mainActivity.Call("ShowDate");
}
//安卓呼叫,更新日期文字的顯示
public void GetDate(string str)
{
dateText.text = str;
}
//按鈕呼叫安卓顯示Toast
public void ShowToastButton()
{
AndroidJavaClass jc = new AndroidJavaClass("com.unity3d.player.UnityPlayer");
mainActivity = jc.GetStatic<AndroidJavaObject>("currentActivity");
mainActivity.Call("ShowToast", "Unity呼叫安卓Toast了");
}
}
將DateText拖拽到Main Camera指令碼來繫結,再將按鈕繫結ShowToastButton事件。
3.匯入aar包和Manifest檔案
在Project面板中,在Assets根目錄下新建Plugins資料夾,再在其下新建Android資料夾。
將我們之前製作好的aar包和AndroidManifest檔案拖拽到剛剛建好的Android資料夾下。
4.修改player settings併發布apk
將預設旋轉設為Landscape Right,即為鎖定右向橫屏。
將bundle identifier修改為安卓的ID名,將Minimum API Level設為manifest裡的最低版本。
注意這時是無法直接執行進行模擬的,我們需要在真機上執行。可以接上手機開啟除錯模式,然後點選Build & Run;也可以釋出apk,然後傳到手機上安裝執行。
三、執行效果
最終執行效果如下圖所示,上方文字實時顯示日期,點選“顯示Toast”按鈕顯示了Toast:
本文到此結束, 有問題請在下方留言,我會盡量及時回覆。謝謝觀看。