Tag Archives: Objective-C

Integrating Unity into a native iOS App

This Post describes the integration for Unity 4. If you are working with Unity 5 (which you should ūüėČ look at this post

For a full working sample with Unity 5 including source code look at this post

With Unity, its really easy to create and deploy stunning 3D-Apps. But what if you have a native iOS app, that is implemented in Objective-C, and only want to add unity-content only as a view?

Lucky us: With the new version of Unity, this is easier than ever.

The easiest way is to start your native app from the unity-generated XCode Project. Dont worry, its really easy to update the unity stuff within the app if it changes after the first export (which usually happens alot). This way round you dont have to set all the necessary build settings needed for unity on your own.

First thing you wanna do is change the Debug Format in the build settings from “DWARF with dSym” to “DWARF”. Otherwise you waste 30 seconds+ each build. Just keep in mind that you changed it if you need to change it back while debugging later.

Since everyone should use ARC nowadays, activate that in the buildsettings too. Make sure you add -fno-objc-arc to all .m and .mm files generated by unity (which are all of them at this state in the project).

Now create your own AppDelegate class by subclassing the Unity Version which is called UnityAppController. Your AppDelegate must be a .mm file. Generally the UnityAppController  takes care of everything related to the app-lifecycle so you wont need to implement that stuff. The only important stuff is to add

IMPL_APP_CONTROLLER_SUBCLASS(AppDelegate)

at the beginning of AppDelegate.mm. (FYI this macro is defined in  UnityAppController.h)

When launching the application (e.g. in applicationDidFinishLaunchingWithOptions) Unity creates an UIWindow and presents a splashscreen. Then it starts the initialization of the real unity-engine asynchronosly (with delay 0 on the mainthread). This means that if you want to do anything AFTER the unityview is loaded (f.e. put it as a subview into your own application) you dont want to put code into applicationDidFinishLaunchingWithOptions. You better override startUnity:

-(void) startUnity:(UIApplication*) application {
[super startUnity:application];
//anything that should be done AFTER the unity viewhierachy is loaded. like replacing the rootviewcontroller with your own.
}

Because thats the method called asynchronously. So in [super startUnity:] the UnityAppController  creates the Unityview and ViewController. Then the Unity-ViewController is set as rootviewcontroller in the window and the unityview added as subview to the window. Therefore it doesnt help if you change these things before startUnity is done.

If you add the Unity-Viewcontroller as subviewcontroller within your own Hierachy you only have to set the transform of its view back to the identity. Unity adds the view directly as subview of the window and therefore sets the transform to reflect the rotation of the app.

If you want to change the size of the unityview (Unity always asumes to be shown fullscreen) you need UnityRequestRenderingResolution. This function (yes, a c-style function) is defined in UnityInterface.h Just call it with the new dimensions, resize the view and call setNeedsLayout on it.

Once you added the Unityviewcontroller (received by either taking the rootviewController from UnityAppController) as a child to your own UIViewController, you can easily add any native interface on top of unity. And with UnityRequestRenderingResolution you can furthermore use the unityview as a non-fullscreen subview within your layout.

If you have any further questions or problems, just leave a comment.