ios -Unity3D的EasyAR集成到已经有项目中。
近期 在做AR这一块,用EasyAR集成到iOS端,由于现在到项目已经上线,下一版本要做一个AR功能,于是迫于需求需要,自己研究和翻阅读好多集成到资料。
通过整理分出几个重要到模块,其中在这里指出Xcode9版本确实好坑,建议弃坑,该用稍微好点到版本Xcode9.1.
一模块.Unity3D导出iOS项目(UD,表示)。
二模块.从UD取出重要到三个文件。
三模块.新建一个iOS项目(ID,表示)
四模块.在ID配置Unity3D的环境
五模块.在ID创建Unity3D的控制器文件及代码
开始演示:
一模块.Unity3D导出iOS项目(UD,表示)。
1.在搞好Unity的代码开发后就可以倒出iOS版本了(如果没有AR项目,可以到EasyAR去找dome来做)。
2.导出到相关配置如标,按里面的配置好就好,注意【’允许使用相机?‘,要写,不然导出iOS后运行会崩溃】:(图是取来别人的图)
二模块.从UD取出重要到三个文件。
1.三个目录,Classes,Libraries,Data。
三模块.新建一个iOS项目(ID,表示)
1.引用UD项目里的三个文件,并集成到ID项目里。
2.这里需要注意的是,Classes和Libraries目录作为Group引用,切记不要勾选copy。
3.而Data目录不需要参与编译,作为folder引用进来即可。
文件结构如下:(可以不要创建文件夹放置,按照UD项目的结构来做)
四模块.在ID配置Unity3D的环境
1.关闭bitcode。新版的Unity已经支持Bitcode但EasyAR并不支持,不关闭无法正常编译。如图:
2.修改Linking -> Other Linker Flags选项,添加参数 -weak_framework CoreMotion -weak-lSystem
。
3.修改头文件搜索目录,如图:
结构如:
"$(SRCROOT)/项目名称/Classes"
"$(SRCROOT)/项目名称/Libraries"
"$(SRCROOT)/项目名称/Libraries/libil2cpp/include"
"$(SRCROOT)/项目名称/Classes/Native"
"$(SRCROOT)/项目名称"
"$(SRCROOT)"
4.修改库搜索目录,如图:
结构如:
"$(SRCROOT)/项目名称/Libraries"
"$(SRCROOT)/项目名称/Libraries/Plugins/iOS"
"$(SRCROOT)/项目名称"
5. 修改LLVM - Custom Complier Flags -> Other C Flags选项,添加两个参数: -DINIT_SCRIPTING_BACKEND=1
和 -DRUNTIME_IL2CPP=1
。
6.修改LLVM - Language -> C Language Dialect选项,选择C99
。
7.修改LLVM - Language - C++ -> C++ Language Dialect选项,选择 C++11
。
8.添加三项自定义设置
- MTL_ENABLE_DEBUG_INFO -> NO
- UNITY_RUNTIME_VERSION -> 2017.1.1f1(当前你的Unity3d版本号,请自行替换)
- UNITY_SCRIPTING_BACKEND -> il2cpp
9.新建一个PCH文件,并修改Precompile Prefix Header为YES,关联pch文件路径。此处新建文件名为 PrefixHeader.pch。
10.添加工程依赖(注意三个Optional)
五模块.在ID创建Unity3D的控制器文件及代码
1.ID项目中,将Classes/
下的main.mm
文件里面的内容,复制全部到集成项目的Supporting Files/
下的main.m
文件中,然后删除Classes/main.mm
,并且把文件后缀改成.mm
。并且按照下图对内容进行修改
2.修改 UnityAppController文件
改之前:
改之后:(‘delegate.unityController’的unityController,是之后要建的自定义文件,用来处理AR界面处理的,不明白可以不管)
3.新建一个UnityController文件继承于UnityAppController用来处理AR界面处理(注意变成C++混编文件【把.m文件变成.mm文件】)
UnityController.mm文件如下:
// Created by XY IOS on 2017/11/18.
// Copyright © 2017年 陈诗友. All rights reserved.
//
#import "UnityController.h"
#import "UnityAppController.h"
#import "UnityAppController+ViewHandling.h"
#import "UnityAppController+Rendering.h"
#import "DisplayManager.h"
#import "UnityView.h"
#include "RegisterMonoModules.h"
#include "RegisterFeatures.h"
#include <csignal>
@interface UnityController()
@property (nonatomic, assign) BOOL isInitUnity;
@end
@implementation UnityController
+ (instancetype)instance
{
return (UnityController *)[[UIApplication sharedApplication]valueForKeyPath:@"delegate.unityController"];
}
- (instancetype)init
{
self = [super init];
if (self) {
self.isInitUnity = NO;
// 注册Unity的事件
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(appDidBecomeActive:) name:UIApplicationDidBecomeActiveNotification object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(appWillEnterForeground:) name:UIApplicationWillEnterForegroundNotification object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(appWillResignActive:) name:UIApplicationWillResignActiveNotification object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(appWillTerminate:) name:UIApplicationWillTerminateNotification object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(appDidReceiveMemoryWarning:) name:UIApplicationDidReceiveMemoryWarningNotification object:nil];
}
return self;
}
- (void)appWillEnterForeground:(NSNotification *)notification {
[self applicationWillEnterForeground:[UIApplication sharedApplication]];
}
- (void)appDidBecomeActive:(NSNotification *)notification {
if (nil == self.unityView) {
return;
}
[self applicationDidBecomeActive:[UIApplication sharedApplication]];
}
- (void)appWillResignActive:(NSNotification *)notification {
[self applicationWillResignActive:[UIApplication sharedApplication]];
}
- (void)appWillTerminate:(NSNotification *)notification {
[self applicationWillTerminate:[UIApplication sharedApplication]];
}
- (void)appDidReceiveMemoryWarning:(NSNotification *)notification {
[self applicationDidReceiveMemoryWarning:[UIApplication sharedApplication]];
}
- (UIView *)playView
{
return self.unityView;
}
static const int constsection = 0;
void UnityInitTrampoline();
void initMain() {
@autoreleasepool
{
// UnityInitTrampoline();
// UnityInitStartupTime();
UnityInitTrampoline();
UnityInitRuntime(0, NULL);
RegisterMonoModules();
NSLog(@"-> registered mono modules %p\n", &constsection);
RegisterFeatures();
// iOS terminates open sockets when an application enters background mode.
// The next write to any of such socket causes SIGPIPE signal being raised,
// even if the request has been done from scripting side. This disables the
// signal and allows Mono to throw a proper C# exception.
std::signal(SIGPIPE, SIG_IGN);
}
}
- (void)initUnity {
if (!self.isInitUnity) {
initMain();
if ([UIDevice currentDevice].generatesDeviceOrientationNotifications == NO)
[[UIDevice currentDevice] beginGeneratingDeviceOrientationNotifications];
UnityInitApplicationNoGraphics([[[NSBundle mainBundle] bundlePath] UTF8String]);
[self selectRenderingAPI];
[UnityRenderingView InitializeForAPI: self.renderingAPI];
_window = nil;
_unityView = [self createUnityView];
[DisplayManager Initialize];
_mainDisplay = [DisplayManager Instance].mainDisplay;
[_mainDisplay createWithWindow: _window andView: _unityView];
[super applicationDidBecomeActive:[UIApplication sharedApplication]];
self.isInitUnity = YES;
}
}
- (void)pauseUnity {
//[self applicationWillResignActive:[UIApplication sharedApplication]];
UnityPause(1);
}
- (void)startUnity {
//[self applicationDidBecomeActive:[UIApplication sharedApplication]];
UnityPause(0);
}
- (BOOL)isPaused {
if (UnityIsPaused() == 1) {
return YES;
}
else {
return NO;
}
}
@end
4.在ViewController 文件创建一个(sbtn)按钮[驱动AR], 一个view[AR容器],要注意一点要在AppDelegate.m文件初始化UnityController
#import "ViewController.h"
#import "UnityController.h"
@interface ViewController ()
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
[self initUI];
// Do any additional setup after loading the view, typically from a nib.
}
- (void)initUI
{
// self.view.backgroundColor = [UIColor whiteColor];
UIButton *sbtn = [UIButton buttonWithType:UIButtonTypeCustom];
sbtn.frame = CGRectMake((CGRectGetMaxX(self.view.frame) - 60 ) / 2, 150, 60, 40);
sbtn.backgroundColor = [UIColor purpleColor];
[sbtn setTitle:@"AR开始" forState:UIControlStateNormal];
[sbtn addTarget:self action:@selector(Actions) forControlEvents:UIControlEventTouchDown];
[self.view addSubview:sbtn];
// UIButton *button1 = [UIButton buttonWithType:UIButtonTypeRoundedRect];
// button1.frame = CGRectMake((CGRectGetMaxX(self.view.frame) - 60 ) / 2, 150 + 40, 60, 40);
// [button1 setTitle:@"AR暂停" forState:UIControlStateNormal];
// [self.view addSubview:button1];
// button1.backgroundColor = [UIColor redColor];
// [button1 addTarget:self action:@selector(clickHandler1:) forControlEvents:UIControlEventTouchUpInside];
// 供Unity显示的View
// UIView *view = [[UIView alloc] initWithFrame:CGRectMake(0, CGRectGetMaxY(sbtn.frame) + 50, CGRectGetWidth(self.view.frame), 400)];
UIView *view = [[UIView alloc] initWithFrame:self.view.bounds];
[view setBackgroundColor:[UIColor grayColor]];
[view setTag:22];
view.hidden = YES;
[self.view addSubview:view];
}
- (void) clickHandler1:(id)sender
{
if ([[UnityController instance] isPaused]) {
[[UnityController instance] startUnity];
}
else {
[[UnityController instance] pauseUnity];
}
}
- (void)Actions
{
NSLog(@"ar");
// self.unityController = [[UnityController alloc]init];
[self.view viewWithTag:22].hidden = NO;
[[UnityController instance]initUnity];
[UnityController instance].playView.frame = [self.view viewWithTag:22].bounds;
[[self.view viewWithTag:22] addSubview:[UnityController instance].playView];
// AppDelegate *delegate = (AppDelegate *)[UIApplication sharedApplication].delegate;
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
@end
5.在AppDelegate.m文件初始化UnityController
7.问题收集
(1)在使用统一摄像头的时候黑屏
问题表现为,在使用Unity打包出来的项目运行是正常的,但是集合到现有项目的时候,摄像头显示区域是黑屏。错误码是:EasyAR is running on an unsupported graphics device of type -4
。
解决的方法:
运行结果:
ios -Unity3D的EasyAR集成到已经有项目中。的更多相关文章
- 将React Native 集成进现有OC项目中(过程记录) 、jsCodeLocation 生成方式总结
将RN集成到现有OC项目应该是最常见的,特别是已经有OC项目的,不太可能会去专门搞个纯RN的项目.又因为RN不同版本,引用的依赖可能不尽相同,所以特别说明下,本文参考的文档是React Native ...
- React-Native集成到已有项目中的总结
安装Python 从官网下载并安装python 2.7.x(3.x版本不行) 安装node.js 从官网下载node.js的官方V6.X.X版本或更高版本.安装完成后检测是否安装成功:node -v ...
- 【开发工具】-- IDEA集成Git在实际项目中的运用
1.企业实际项目中Git的使用 在实际的企业项目开发中,我们一般Java的项目在公司都有自己的局域网代码仓库,仓库上存放着很多的项目.以我工作过的公司如华为的项目,一般是存放在企业内部的CodeHub ...
- ZXingObjC 64位 集成到自己的项目中(xcode 6.4)
参考 http://www.cocoachina.com/bbs/read.php?tid-280058-page-1.html 楼主发的DEMO中 ZXingObjC 支持64位 但是是以项目形 ...
- 集成activiti到现有项目中
1.在lib中添加相关的jar包 2.找到一个activiti.cfg.xml,若是想用现有的数据库需要配置 <?xml version="1.0" encoding=&qu ...
- 四、spring集成ibatis进行项目中dao层基类封装
Apache iBatis(现已迁至Google Code下发展,更名为MyBatis)是当前IT项目中使用很广泛的一个半自动ORM框架,区别于Hibernate之类的全自动框架,iBatis对数据库 ...
- iOS图表库Charts集成与使用
Charts是一个很优秀的图表库,它支持Android.iOS.tvOS和macOS,这样使用起来,可以节省学习成本,可以从GitHub上了解更多信息.本文记录在iOS项目上的集成与使用. Chart ...
- iOS原生项目中集成React Native
1.本文的前提条件是,电脑上已经安装了CocoaPods,React Native相关环境. 2.使用Xcode新建一个工程.EmbedRNMeituan [图1] 3.使用CocoaPods安装Re ...
- iOS实用技能扩展-集成支付宝
前奏 现在随着移动开发的快速发展,移动支付变得越来越流行与必不可少.最近做了一个关于支付宝支付功能的应用,在使用支付宝的过程中,遇到一些不必要的弯路,因此,写了这篇文章总结一下关于iOS中如何开发使用 ...
随机推荐
- FPGA在其他领域的应用(四)
工业领域: 从工厂和过程自动化到能源基础设施和机器视觉系统,工业产品有助于改善我们的世界.产品必须安全.可靠.适应性强,而且耐用.同时,商业成功要求你在激烈竞争的市场中行动迅速,同时降低总成本. 英特 ...
- JAVA提高五:注解Annotation
今天我们学习JDK5.0中一个非常重要的特性,叫做注解.是现在非常流行的一种方式,可以说因为配置XML 比较麻烦或者比容易查找出错误,现在越来越多的框架开始支持注解方式,比如注明的Spring 框架, ...
- (转)java内存泄漏的定位与分析
转自:http://blog.csdn.net/x_i_y_u_e/article/details/51137492 1.为什么会发生内存泄漏 java 如何检测内在泄漏呢?我们需要一些工具进行检测, ...
- 【ASP.NET MVC 学习笔记】- 07 使用 Entity Framework
本文参考:http://www.cnblogs.com/willick/p/3304534.html 1.ORM(Object Relation Mapping)工具,是为了解决“关系数据库”和“面向 ...
- python + selenium 自动化测试框架
分享一个网站自动化测试框架 结构如下: test_project|--logs|---pages |---register_page.py| |---base_page.py|---test ...
- SpringBoot的几个使用技巧
SpringBoot的几个使用技巧 首先提供几个SpringBoot开发过程中常用的网站: Spring Boot官方文档:http://docs.spring.io/spring-boot/docs ...
- 加载web项目时报的错误:Tomcat version 6.0 only supports J2EE 1.2, 1.3, 1.4, and Java EE 5 Web modul
用eclipse开发的java项目不能加载到tomcat6.0服务器,原因是:jst.web的版本高了 <installed facet="jst.web" version= ...
- SQL2008清空删除日志:
SQL2008清空删除日志: '在SQL2008中清除日志就必须在简单模式下进行,等清除动作完毕再调回到完全模式. USE [master] GO ALTER DATABASE DNName SET ...
- VPS搭建离线下载服务器——后网盘时代
动机 由于学习的需要,在国外某服务器厂商购买了vps服务(至于是哪个厂商就不说啦).但是呢,就算用作梯子,一个月1T的流量总是用不完.最经觉得自己营养充足,想找点电影看看. 无奈现在百度网盘的速度真的 ...
- Swift 之Protocol在cocoa中的使用范例搜集(一)
protocol Reusable: class { static var reuseIndentifier: String {get} static var nib: UINib? {get} } ...