Unity3D Plugins
Development Guide
ChenKaiJung
Plugins Are?
● Libraries of native code written in C, C++,
Objective-C….etc
● Allow your game code to call functions from
these libraries
Why do you need to develop a Plugin?
●
●
●
●
●
●

Unity3D can’t Do That
Reuse C/C++/Objective-C components
Difficult customize in Unity3D Assets Store
Cross-Device
Cross-Platform
Security Issues
Interface?
● Just like call Unmanaged DLL in .NET
● Sync
○ Call the functions and get return values

● Async
○ Use UnitySendMessage

● Name mangling Issue
○ Use extern "C" { }
○ or _ZN·9funtown·7ios·6init·E
Plugins for Different Device
● Compile time - iOS
#if UNITY_IOS
#else
#endif

● Compile time - Android
#if UNITY_ANDROID
#else
#endif
Plugins for Different Device
● Runtime - iOS
if (Application.platform == RuntimePlatform.OSXPlayer)

● Runtime - Android
if (Application.platform == RuntimePlatform.Android)
iOS Plugins
● C# Dll Import
[DllImport ("__Internal")] private static extern void iosInit(bool cookie, bool
logging, bool status, bool frictionlessRequests);

● C/C++ Native Functions in xxx.mm
extern "C" {
void iosInit(bool _cookie, bool _logging, bool _status, bool
_frictionlessRequests) { [[FbUnityInterface alloc] initWithCookie:_cookie
logging:_logging status:_status frictionlessRequests:_frictionlessRequests]; } }
iOS Plugins
#ifdef __cplusplus
extern "C" {
#endif
void UnitySendMessage(const char* obj, const char* method, const char*
msg);
#ifdef __cplusplus
}
#endif
iOS 3rd Powerful tools
● XCode Editor for
Unity3D

{
"group": "Facebook",
"patches": [],
"libs": [
"Facebook/Editor/iOS/FacebookSDK/libfacebook_ios_sdk.a:<group>"
],
"librarysearchpaths": [
"Facebook/Editor/iOS/FacebookSDK/"
],
"frameworks": [
"Accounts.framework:weak"
],
"headerpaths": [
"Facebook/Editor/iOS"
],
"files": [
"Facebook/Editor/iOS/FbUnityInterface.mm",
"Facebook/Editor/iOS/FbUnityInterface.h"
],
"folders": [],
"excludes": [
"^.*.meta$",
"^.*.mdown^",
"^.*.pdf$"
]

○ Post Process Build
○ Json Configure
(fixup.projmods)

}
iOS Tips
● DO NOT call plugins Pre-Frame
● String passing should be encoded by UTF-8
● Wrappers your Message and let it easily
encodes and decodes cross language. Ex:
JSON,Query String
● Uses XCode Editor for building automation
Android Plugins
● C# Dll Import
[DllImport ("unityinapppurchase")] private static extern void androidFTInit
(bool cookie, bool logging, bool status, bool frictionlessRequests);

● C++ Native Functions in unityinapppurchase.
so
extern "C" {
void androidFTInit(bool _cookie, bool _logging, bool _status, bool
_frictionlessRequests) { LOGD("androidFTInit called"); } }
Android Plugins
● C# Load Java Class
ftJava = new AndroidJavaClass("tw.com.funtown.unity.FT");
ftjava.CallStatic("Init", "");

● Java Class
public class FT
{
public static void init(String params) {
Log.d("FTUnitySDK", "init called with params: " + params);
}
}
Android Plugins
● Overwrite onActivityResult
public class FTUnityPlayerActivity extends UnityPlayerActivity
{
public void onActivityResult(int requestCode, int resultCode, Intent data)
{
Log.d("FTUnityPlayerActivity", "onActivityResult: requestCode: " +
requestCode + ", resultCode:" + resultCode);
}
}
Android Plugins
● Modify your Manifest.xml Automatically
<activity android:name="tw.com.funtown.unity.FTUnityPlayerActivity" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity android:name="tw.com.funtown.LoginActivity" >
</activity>
Android Plugins
● Call UnitySendMessage using JNI
bool retval=JniHelper::getStaticMethodInfo(t, "com/unity3d/player/UnityPlayer" ,"UnitySendMessage"
,"(Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)V");
if(retval==false) return;
jstring objectStr = t.env->NewStringUTF(obj);
jstring methodStr = t.env->NewStringUTF(method);
jstring msgStr = t.env->NewStringUTF(msg);
t.env->CallStaticVoidMethod(t.classID,t.methodID,objectStr,methodStr,msgStr);
jthrowable exception = t.env->ExceptionOccurred();
if (exception) {
t.env->ExceptionDescribe();
t.env->DeleteLocalRef(exception);
t.env->ExceptionClear();
} else {
}
…..Please delete your allocated resource here
Android Tips
● DO NOT call plugins Pre-Frame
● Mono garbage collector by using(){..} or xx.
Dispose() in C#
● Put your *.jar *.so in
YOUR_PROJECT/Assets/Plugins
● Be careful of Android resource conflict
problem
Go through OAuth SDK
Q&A
References
● Unity3D Official Plugins document http://docs.unity3d.
com/Documentation/Manual/Plugins.html
● Facebook Unity3D Plugin https://developers.facebook.
com/docs/unity
● A company sells Unity3D Mobile Plugins http://prime31.
com/

Unity3D Plugins Development Guide

  • 1.
  • 2.
    Plugins Are? ● Librariesof native code written in C, C++, Objective-C….etc ● Allow your game code to call functions from these libraries
  • 3.
    Why do youneed to develop a Plugin? ● ● ● ● ● ● Unity3D can’t Do That Reuse C/C++/Objective-C components Difficult customize in Unity3D Assets Store Cross-Device Cross-Platform Security Issues
  • 4.
    Interface? ● Just likecall Unmanaged DLL in .NET ● Sync ○ Call the functions and get return values ● Async ○ Use UnitySendMessage ● Name mangling Issue ○ Use extern "C" { } ○ or _ZN·9funtown·7ios·6init·E
  • 5.
    Plugins for DifferentDevice ● Compile time - iOS #if UNITY_IOS #else #endif ● Compile time - Android #if UNITY_ANDROID #else #endif
  • 6.
    Plugins for DifferentDevice ● Runtime - iOS if (Application.platform == RuntimePlatform.OSXPlayer) ● Runtime - Android if (Application.platform == RuntimePlatform.Android)
  • 7.
    iOS Plugins ● C#Dll Import [DllImport ("__Internal")] private static extern void iosInit(bool cookie, bool logging, bool status, bool frictionlessRequests); ● C/C++ Native Functions in xxx.mm extern "C" { void iosInit(bool _cookie, bool _logging, bool _status, bool _frictionlessRequests) { [[FbUnityInterface alloc] initWithCookie:_cookie logging:_logging status:_status frictionlessRequests:_frictionlessRequests]; } }
  • 8.
    iOS Plugins #ifdef __cplusplus extern"C" { #endif void UnitySendMessage(const char* obj, const char* method, const char* msg); #ifdef __cplusplus } #endif
  • 9.
    iOS 3rd Powerfultools ● XCode Editor for Unity3D { "group": "Facebook", "patches": [], "libs": [ "Facebook/Editor/iOS/FacebookSDK/libfacebook_ios_sdk.a:<group>" ], "librarysearchpaths": [ "Facebook/Editor/iOS/FacebookSDK/" ], "frameworks": [ "Accounts.framework:weak" ], "headerpaths": [ "Facebook/Editor/iOS" ], "files": [ "Facebook/Editor/iOS/FbUnityInterface.mm", "Facebook/Editor/iOS/FbUnityInterface.h" ], "folders": [], "excludes": [ "^.*.meta$", "^.*.mdown^", "^.*.pdf$" ] ○ Post Process Build ○ Json Configure (fixup.projmods) }
  • 10.
    iOS Tips ● DONOT call plugins Pre-Frame ● String passing should be encoded by UTF-8 ● Wrappers your Message and let it easily encodes and decodes cross language. Ex: JSON,Query String ● Uses XCode Editor for building automation
  • 11.
    Android Plugins ● C#Dll Import [DllImport ("unityinapppurchase")] private static extern void androidFTInit (bool cookie, bool logging, bool status, bool frictionlessRequests); ● C++ Native Functions in unityinapppurchase. so extern "C" { void androidFTInit(bool _cookie, bool _logging, bool _status, bool _frictionlessRequests) { LOGD("androidFTInit called"); } }
  • 12.
    Android Plugins ● C#Load Java Class ftJava = new AndroidJavaClass("tw.com.funtown.unity.FT"); ftjava.CallStatic("Init", ""); ● Java Class public class FT { public static void init(String params) { Log.d("FTUnitySDK", "init called with params: " + params); } }
  • 13.
    Android Plugins ● OverwriteonActivityResult public class FTUnityPlayerActivity extends UnityPlayerActivity { public void onActivityResult(int requestCode, int resultCode, Intent data) { Log.d("FTUnityPlayerActivity", "onActivityResult: requestCode: " + requestCode + ", resultCode:" + resultCode); } }
  • 14.
    Android Plugins ● Modifyyour Manifest.xml Automatically <activity android:name="tw.com.funtown.unity.FTUnityPlayerActivity" > <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> </activity> <activity android:name="tw.com.funtown.LoginActivity" > </activity>
  • 15.
    Android Plugins ● CallUnitySendMessage using JNI bool retval=JniHelper::getStaticMethodInfo(t, "com/unity3d/player/UnityPlayer" ,"UnitySendMessage" ,"(Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)V"); if(retval==false) return; jstring objectStr = t.env->NewStringUTF(obj); jstring methodStr = t.env->NewStringUTF(method); jstring msgStr = t.env->NewStringUTF(msg); t.env->CallStaticVoidMethod(t.classID,t.methodID,objectStr,methodStr,msgStr); jthrowable exception = t.env->ExceptionOccurred(); if (exception) { t.env->ExceptionDescribe(); t.env->DeleteLocalRef(exception); t.env->ExceptionClear(); } else { } …..Please delete your allocated resource here
  • 16.
    Android Tips ● DONOT call plugins Pre-Frame ● Mono garbage collector by using(){..} or xx. Dispose() in C# ● Put your *.jar *.so in YOUR_PROJECT/Assets/Plugins ● Be careful of Android resource conflict problem
  • 17.
  • 18.
  • 19.
    References ● Unity3D OfficialPlugins document http://docs.unity3d. com/Documentation/Manual/Plugins.html ● Facebook Unity3D Plugin https://developers.facebook. com/docs/unity ● A company sells Unity3D Mobile Plugins http://prime31. com/