Added basic iOS support (no messaging yet)
This commit is contained in:
parent
5277f942a8
commit
18c013a374
|
@ -1,25 +0,0 @@
|
||||||
//
|
|
||||||
// Created by rex on 19/03/2019.
|
|
||||||
//
|
|
||||||
|
|
||||||
#ifndef FLUTTER_UNITY_WIDGET_FLUTTERUNITY_H
|
|
||||||
#define FLUTTER_UNITY_WIDGET_FLUTTERUNITY_H
|
|
||||||
|
|
||||||
|
|
||||||
#import <Flutter/Flutter.h>
|
|
||||||
|
|
||||||
@interface FlutterUnityController : NSObject <FlutterPlatformView>
|
|
||||||
|
|
||||||
- (instancetype)initWithWithFrame:(CGRect)frame
|
|
||||||
viewIdentifier:(int64_t)viewId
|
|
||||||
arguments:(id _Nullable)args
|
|
||||||
binaryMessenger:(NSObject<FlutterBinaryMessenger>*)messenger;
|
|
||||||
|
|
||||||
- (UIView*)view;
|
|
||||||
@end
|
|
||||||
|
|
||||||
@interface FlutterUnityFactory : NSObject <FlutterPlatformViewFactory>
|
|
||||||
- (instancetype)initWithMessenger:(NSObject<FlutterBinaryMessenger>*)messenger;
|
|
||||||
@end
|
|
||||||
|
|
||||||
#endif //FLUTTER_UNITY_WIDGET_FLUTTERUNITY_H
|
|
|
@ -1,87 +0,0 @@
|
||||||
//
|
|
||||||
// Created by rex on 19/03/2019.
|
|
||||||
//
|
|
||||||
|
|
||||||
#include "FlutterUnity.h"
|
|
||||||
|
|
||||||
@implementation FlutterUnityFactory {
|
|
||||||
NSObject<FlutterBinaryMessenger>* _messenger;
|
|
||||||
}
|
|
||||||
|
|
||||||
- (instancetype)initWithMessenger:(NSObject<FlutterBinaryMessenger>*)messenger {
|
|
||||||
self = [super init];
|
|
||||||
if (self) {
|
|
||||||
_messenger = messenger;
|
|
||||||
}
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
@implementation FlutterUnityController {
|
|
||||||
WKWebView* _webView;
|
|
||||||
int64_t _viewId;
|
|
||||||
FlutterMethodChannel* _channel;
|
|
||||||
}
|
|
||||||
|
|
||||||
- (instancetype)initWithWithFrame:(CGRect)frame
|
|
||||||
viewIdentifier:(int64_t)viewId
|
|
||||||
arguments:(id _Nullable)args
|
|
||||||
binaryMessenger:(NSObject<FlutterBinaryMessenger>*)messenger {
|
|
||||||
if ([super init]) {
|
|
||||||
_viewId = viewId;
|
|
||||||
_webView = [[WKWebView alloc] initWithFrame:frame];
|
|
||||||
NSString* channelName = [NSString stringWithFormat:@"nativeweb_%lld", viewId];
|
|
||||||
_channel = [FlutterMethodChannel methodChannelWithName:channelName binaryMessenger:messenger];
|
|
||||||
__weak __typeof__(self) weakSelf = self;
|
|
||||||
[_channel setMethodCallHandler:^(FlutterMethodCall* call, FlutterResult result) {
|
|
||||||
[weakSelf onMethodCall:call result:result];
|
|
||||||
}];
|
|
||||||
|
|
||||||
}
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
- (UIView*)view {
|
|
||||||
return _webView;
|
|
||||||
}
|
|
||||||
|
|
||||||
- (void)onMethodCall:(FlutterMethodCall*)call result:(FlutterResult)result {
|
|
||||||
if ([[call method] isEqualToString:@"postMessage"]) {
|
|
||||||
[self postMessage:call result:result];
|
|
||||||
} else if ([[call method] isEqualToString:@"isReady"]) {
|
|
||||||
[self postMessage:call result:result];
|
|
||||||
} else if ([[call method] isEqualToString:@"createUnity"]) {
|
|
||||||
[self postMessage:call result:result];
|
|
||||||
} else if ([[call method] isEqualToString:@"pause"]) {
|
|
||||||
[self postMessage:call result:result];
|
|
||||||
} else if ([[call method] isEqualToString:@"resume"]) {
|
|
||||||
[self postMessage:call result:result];
|
|
||||||
} else {
|
|
||||||
result(FlutterMethodNotImplemented);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
- (void)postMessage:(FlutterMethodCall*)call result:(FlutterResult)result {
|
|
||||||
NSString* url = [call arguments];
|
|
||||||
if (![self postMessage:url]) {
|
|
||||||
result([FlutterError errorWithCode:@"loadUrl_failed"
|
|
||||||
message:@"Failed parsing the URL"
|
|
||||||
details:[NSString stringWithFormat:@"URL was: '%@'", url]]);
|
|
||||||
} else {
|
|
||||||
result(nil);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
- (bool)onPostMessage:(NSString*)url {
|
|
||||||
NSURL* nsUrl = [NSURL URLWithString:url];
|
|
||||||
if (!nsUrl) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
NSURLRequest* req = [NSURLRequest requestWithURL:nsUrl];
|
|
||||||
[_webView loadRequest:req];
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,18 @@
|
||||||
|
//
|
||||||
|
// FlutterUnityView.h
|
||||||
|
// FlutterUnityView
|
||||||
|
//
|
||||||
|
// Created by krispypen on 8/1/2019
|
||||||
|
//
|
||||||
|
|
||||||
|
#import <UIKit/UIKit.h>
|
||||||
|
|
||||||
|
#import "UnityUtils.h"
|
||||||
|
|
||||||
|
@interface FlutterUnityView : UIView
|
||||||
|
|
||||||
|
@property (nonatomic, strong) UIView* uView;
|
||||||
|
|
||||||
|
- (void)setUnityView:(UIView *)view;
|
||||||
|
|
||||||
|
@end
|
|
@ -0,0 +1,37 @@
|
||||||
|
//
|
||||||
|
// FlutterUnityView.m
|
||||||
|
// FlutterUnityView
|
||||||
|
//
|
||||||
|
// Created by krispypen on 8/1/2019
|
||||||
|
//
|
||||||
|
|
||||||
|
#import "FlutterUnityView.h"
|
||||||
|
|
||||||
|
@implementation FlutterUnityView
|
||||||
|
|
||||||
|
- (id)initWithFrame:(CGRect)frame
|
||||||
|
{
|
||||||
|
self = [super initWithFrame:frame];
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)dealloc
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)setUnityView:(UIView *)view
|
||||||
|
{
|
||||||
|
self.uView = view;
|
||||||
|
[self setNeedsLayout];
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)layoutSubviews
|
||||||
|
{
|
||||||
|
[super layoutSubviews];
|
||||||
|
[(UIView *)self.uView removeFromSuperview];
|
||||||
|
[self insertSubview:(UIView *)self.uView atIndex:0];
|
||||||
|
((UIView *)self.uView).frame = self.bounds;
|
||||||
|
[(UIView *)self.uView setNeedsLayout];
|
||||||
|
}
|
||||||
|
|
||||||
|
@end
|
|
@ -1,4 +1,25 @@
|
||||||
|
//
|
||||||
|
// FlutterUnityWidgetPlugin.h
|
||||||
|
// FlutterUnityWidgetPlugin
|
||||||
|
//
|
||||||
|
// Created by Kris Pypen on 8/1/19.
|
||||||
|
//
|
||||||
|
|
||||||
#import <Flutter/Flutter.h>
|
#import <Flutter/Flutter.h>
|
||||||
|
|
||||||
@interface FlutterUnityWidgetPlugin : NSObject<FlutterPlugin>
|
@interface FlutterUnityWidgetPlugin : NSObject<FlutterPlugin>
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
@interface FUController : NSObject <FlutterPlatformView>
|
||||||
|
|
||||||
|
- (instancetype)initWithFrame:(CGRect)frame
|
||||||
|
viewIdentifier:(int64_t)viewId
|
||||||
|
arguments:(id _Nullable)args
|
||||||
|
binaryMessenger:(NSObject<FlutterBinaryMessenger>*)messenger;
|
||||||
|
|
||||||
|
- (UIView*)view;
|
||||||
|
@end
|
||||||
|
|
||||||
|
@interface FUViewFactory : NSObject <FlutterPlatformViewFactory>
|
||||||
|
- (instancetype)initWithRegistrar:(NSObject<FlutterPluginRegistrar> *)registrar;
|
||||||
|
@end
|
||||||
|
|
|
@ -1,20 +1,84 @@
|
||||||
|
//
|
||||||
|
// FlutterUnityWidgetPlugin.m
|
||||||
|
// FlutterUnityWidgetPlugin
|
||||||
|
//
|
||||||
|
// Created by Kris Pypen on 8/1/19.
|
||||||
|
//
|
||||||
|
|
||||||
#import "FlutterUnityWidgetPlugin.h"
|
#import "FlutterUnityWidgetPlugin.h"
|
||||||
#import <flutter_unity_widget/flutter_unity_widget-Swift.h>
|
#import "UnityUtils.h"
|
||||||
|
#import "FlutterUnityView.h"
|
||||||
|
|
||||||
+ (void)registerWithRegistrar:(NSObject<FlutterPluginRegistrar>*)registrar {
|
#include <UnityFramework/UnityFramework.h>
|
||||||
FlutterNativeWebFactory* webviewFactory =
|
|
||||||
[[FlutterNativeWebFactory alloc] initWithMessenger:registrar.messenger];
|
|
||||||
[registrar registerViewFactory:webviewFactory withId:@"unity_view"];
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
#import "FlutterUnityWidgetPlugin.h"
|
|
||||||
#import <flutter_unity_widget/flutter_unity_widget-Swift.h>
|
|
||||||
|
|
||||||
@implementation FlutterUnityWidgetPlugin
|
@implementation FlutterUnityWidgetPlugin
|
||||||
+ (void)registerWithRegistrar:(NSObject<FlutterPluginRegistrar>*)registrar {
|
+ (void)registerWithRegistrar:(NSObject<FlutterPluginRegistrar>*)registrar {
|
||||||
[SwiftFlutterUnityWidgetPlugin registerWithRegistrar:registrar];
|
FUViewFactory* fuviewFactory = [[FUViewFactory alloc] initWithRegistrar:registrar];
|
||||||
|
[registrar registerViewFactory:fuviewFactory withId:@"unity_view"];
|
||||||
}
|
}
|
||||||
@end
|
@end
|
||||||
*/
|
|
||||||
|
@implementation FUViewFactory {
|
||||||
|
NSObject<FlutterPluginRegistrar>* _registrar;
|
||||||
|
}
|
||||||
|
- (instancetype)initWithRegistrar:(NSObject<FlutterPluginRegistrar>*)registrar {
|
||||||
|
self = [super init];
|
||||||
|
if (self) {
|
||||||
|
_registrar = registrar;
|
||||||
|
}
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
- (NSObject<FlutterMessageCodec>*)createArgsCodec {
|
||||||
|
return [FlutterStandardMessageCodec sharedInstance];
|
||||||
|
}
|
||||||
|
|
||||||
|
- (NSObject<FlutterPlatformView>*)createWithFrame:(CGRect)frame
|
||||||
|
viewIdentifier:(int64_t)viewId
|
||||||
|
arguments:(id _Nullable)args {
|
||||||
|
FUController* controller = [[FUController alloc] initWithFrame:frame
|
||||||
|
viewIdentifier:viewId
|
||||||
|
arguments:args
|
||||||
|
binaryMessenger:_registrar];
|
||||||
|
return controller;
|
||||||
|
}
|
||||||
|
|
||||||
|
@end
|
||||||
|
|
||||||
|
@implementation FUController {
|
||||||
|
FlutterUnityView* _uView;
|
||||||
|
int64_t _viewId;
|
||||||
|
FlutterMethodChannel* _channel;
|
||||||
|
}
|
||||||
|
|
||||||
|
- (instancetype)initWithFrame:(CGRect)frame
|
||||||
|
viewIdentifier:(int64_t)viewId
|
||||||
|
arguments:(id _Nullable)args
|
||||||
|
binaryMessenger:(NSObject<FlutterBinaryMessenger>*)messenger {
|
||||||
|
if ([super init]) {
|
||||||
|
_viewId = viewId;
|
||||||
|
|
||||||
|
NSString* channelName = [NSString stringWithFormat:@"unity_view_%lld", viewId];
|
||||||
|
_channel = [FlutterMethodChannel methodChannelWithName:channelName binaryMessenger:messenger];
|
||||||
|
|
||||||
|
}
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
|
- (UIView*)view {
|
||||||
|
_uView = [[FlutterUnityView alloc] init];
|
||||||
|
if ([UnityUtils isUnityReady]) {
|
||||||
|
[_uView setUnityView: (UIView*)[GetAppController() unityView]];
|
||||||
|
} else {
|
||||||
|
[UnityUtils createPlayer:^{
|
||||||
|
[_uView setUnityView: (UIView*)[GetAppController() unityView]];
|
||||||
|
}];
|
||||||
|
}
|
||||||
|
return _uView;
|
||||||
|
}
|
||||||
|
|
||||||
|
@end
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,27 +1,23 @@
|
||||||
//
|
|
||||||
// Created by rex on 15/03/2019.
|
|
||||||
//
|
|
||||||
|
|
||||||
#ifndef FLUTTER_UNITY_WIDGET_UNITYUTILS_H
|
|
||||||
#define FLUTTER_UNITY_WIDGET_UNITYUTILS_H
|
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
#import <Foundation/Foundation.h>
|
||||||
|
|
||||||
|
#ifndef UnityUtils_h
|
||||||
|
#define UnityUtils_h
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
extern "C" {
|
extern "C" {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
void InitArgs(int argc, char* argv[]);
|
void InitArgs(int argc, char* argv[]);
|
||||||
|
|
||||||
bool UnityIsInited(void);
|
bool UnityIsInited(void);
|
||||||
|
|
||||||
void InitUnity();
|
void InitUnity();
|
||||||
|
|
||||||
void UnityPostMessage(NSString* gameObject, NSString* methodName, NSString* message);
|
void UnityPostMessage(NSString* gameObject, NSString* methodName, NSString* message);
|
||||||
|
|
||||||
void UnityPauseCommand();
|
void UnityPauseCommand();
|
||||||
|
|
||||||
void UnityResumeCommand();
|
void UnityResumeCommand();
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
} // extern "C"
|
} // extern "C"
|
||||||
|
@ -40,5 +36,4 @@ void UnityResumeCommand();
|
||||||
|
|
||||||
@end
|
@end
|
||||||
|
|
||||||
#endif //FLUTTER_UNITY_WIDGET_UNITYUTILS_H
|
#endif /* UnityUtils_h */
|
||||||
|
|
||||||
|
|
|
@ -1,10 +1,8 @@
|
||||||
#include "RegisterMonoModules.h"
|
|
||||||
#include "RegisterFeatures.h"
|
|
||||||
#include <csignal>
|
#include <csignal>
|
||||||
#import <UIKit/UIKit.h>
|
#import <UIKit/UIKit.h>
|
||||||
#import "UnityInterface.h"
|
|
||||||
#import "UnityUtils.h"
|
#import "UnityUtils.h"
|
||||||
#import "UnityAppController.h"
|
|
||||||
|
#include <UnityFramework/UnityFramework.h>
|
||||||
|
|
||||||
// Hack to work around iOS SDK 4.3 linker problem
|
// Hack to work around iOS SDK 4.3 linker problem
|
||||||
// we need at least one __TEXT, __const section entry in main application .o files
|
// we need at least one __TEXT, __const section entry in main application .o files
|
||||||
|
@ -18,6 +16,8 @@ char** g_argv;
|
||||||
|
|
||||||
void UnityInitTrampoline();
|
void UnityInitTrampoline();
|
||||||
|
|
||||||
|
UnityFramework* ufw;
|
||||||
|
|
||||||
extern "C" void InitArgs(int argc, char* argv[])
|
extern "C" void InitArgs(int argc, char* argv[])
|
||||||
{
|
{
|
||||||
g_argc = argc;
|
g_argc = argc;
|
||||||
|
@ -29,6 +29,19 @@ extern "C" bool UnityIsInited()
|
||||||
return unity_inited;
|
return unity_inited;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
UnityFramework* UnityFrameworkLoad()
|
||||||
|
{
|
||||||
|
NSString* bundlePath = nil;
|
||||||
|
bundlePath = [[NSBundle mainBundle] bundlePath];
|
||||||
|
bundlePath = [bundlePath stringByAppendingString: @"/Frameworks/UnityFramework.framework"];
|
||||||
|
|
||||||
|
NSBundle* bundle = [NSBundle bundleWithPath: bundlePath];
|
||||||
|
if ([bundle isLoaded] == false) [bundle load];
|
||||||
|
|
||||||
|
UnityFramework* ufw = [bundle.principalClass getInstance];
|
||||||
|
return ufw;
|
||||||
|
}
|
||||||
|
|
||||||
extern "C" void InitUnity()
|
extern "C" void InitUnity()
|
||||||
{
|
{
|
||||||
if (unity_inited) {
|
if (unity_inited) {
|
||||||
|
@ -36,41 +49,28 @@ extern "C" void InitUnity()
|
||||||
}
|
}
|
||||||
unity_inited = true;
|
unity_inited = true;
|
||||||
|
|
||||||
UnityInitStartupTime();
|
ufw = UnityFrameworkLoad();
|
||||||
|
|
||||||
@autoreleasepool
|
[ufw setDataBundleId: "com.unity3d.framework"];
|
||||||
{
|
[ufw frameworkWarmup: g_argc argv: g_argv];
|
||||||
UnityInitTrampoline();
|
|
||||||
UnityInitRuntime(g_argc, g_argv);
|
|
||||||
|
|
||||||
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);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
extern "C" void UnityPostMessage(NSString* gameObject, NSString* methodName, NSString* message)
|
extern "C" void UnityPostMessage(NSString* gameObject, NSString* methodName, NSString* message)
|
||||||
{
|
{
|
||||||
UnitySendMessage([gameObject UTF8String], [methodName UTF8String], [message UTF8String]);
|
////UnitySendMessage([gameObject UTF8String], [methodName UTF8String], [message UTF8String]);
|
||||||
}
|
}
|
||||||
|
|
||||||
extern "C" void UnityPauseCommand()
|
extern "C" void UnityPauseCommand()
|
||||||
{
|
{
|
||||||
dispatch_async(dispatch_get_main_queue(), ^{
|
dispatch_async(dispatch_get_main_queue(), ^{
|
||||||
UnityPause(1);
|
[ufw pause:true];
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
extern "C" void UnityResumeCommand()
|
extern "C" void UnityResumeCommand()
|
||||||
{
|
{
|
||||||
dispatch_async(dispatch_get_main_queue(), ^{
|
dispatch_async(dispatch_get_main_queue(), ^{
|
||||||
UnityPause(0);
|
[ufw pause:false];
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -17,5 +17,8 @@ Flutter unity 3D widget for embedding unity in flutter
|
||||||
s.dependency 'Flutter'
|
s.dependency 'Flutter'
|
||||||
|
|
||||||
s.ios.deployment_target = '8.0'
|
s.ios.deployment_target = '8.0'
|
||||||
|
s.xcconfig = {
|
||||||
|
'FRAMEWORK_SEARCH_PATHS' => '$(inherited) "${PODS_ROOT}/../.symlinks/flutter/ios-release" "${PODS_ROOT}/../Unity3Export" "${PODS_CONFIGURATION_BUILD_DIR}"',
|
||||||
|
'OTHER_LDFLAGS' => '$(inherited) -framework UnityFramework ${PODS_LIBRARIES}'
|
||||||
|
}
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
Reference in New Issue