You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
213 lines
7.2 KiB
213 lines
7.2 KiB
import 'dart:async';
|
|
|
|
import 'package:flutter/material.dart';
|
|
import 'package:flutter/services.dart';
|
|
|
|
import '../facade_controller.dart';
|
|
import '../helpers/events.dart';
|
|
import 'device_method.dart';
|
|
import 'cocos_widget.dart';
|
|
import 'cocos_widget_platform.dart';
|
|
|
|
class MobileCocosWidgetController extends CocosWidgetController {
|
|
final MobileCocosWidgetState _cocosWidgetState;
|
|
|
|
/// The cocosId for this controller
|
|
final int cocosId;
|
|
|
|
/// used for cancel the subscription
|
|
StreamSubscription? _onCocosMessageSub,
|
|
_onCocosSceneLoadedSub,
|
|
_onCocosUnloadedSub;
|
|
|
|
MobileCocosWidgetController._(this._cocosWidgetState,
|
|
{required this.cocosId}) {
|
|
_connectStreams(cocosId);
|
|
}
|
|
|
|
/// Initialize [CocosWidgetController] with [id]
|
|
/// Mainly for internal use when instantiating a [CocosWidgetController] passed
|
|
/// in [CocosWidget.onCocosCreated] callback.
|
|
static Future<MobileCocosWidgetController> init(
|
|
int id, MobileCocosWidgetState cocosWidgetState) async {
|
|
await CocosWidgetPlatform.instance.init(id);
|
|
return MobileCocosWidgetController._(
|
|
cocosWidgetState,
|
|
cocosId: id,
|
|
);
|
|
}
|
|
|
|
@visibleForTesting
|
|
MethodChannel? get channel {
|
|
if (CocosWidgetPlatform.instance is MethodChannelCocosWidget) {
|
|
return (CocosWidgetPlatform.instance as MethodChannelCocosWidget)
|
|
.channel(cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
void _connectStreams(int cocosId) {
|
|
if (_cocosWidgetState.widget.onCocosMessage != null) {
|
|
_onCocosMessageSub = CocosWidgetPlatform.instance
|
|
.onCocosMessage(cocosId: cocosId)
|
|
.listen((CocosMessageEvent e) =>
|
|
_cocosWidgetState.widget.onCocosMessage!(e.value));
|
|
}
|
|
|
|
if (_cocosWidgetState.widget.onCocosSceneLoaded != null) {
|
|
_onCocosSceneLoadedSub = CocosWidgetPlatform.instance
|
|
.onCocosSceneLoaded(cocosId: cocosId)
|
|
.listen((CocosSceneLoadedEvent e) =>
|
|
_cocosWidgetState.widget.onCocosSceneLoaded!(e.value));
|
|
}
|
|
|
|
if (_cocosWidgetState.widget.onCocosUnloaded != null) {
|
|
_onCocosUnloadedSub = CocosWidgetPlatform.instance
|
|
.onCocosUnloaded(cocosId: cocosId)
|
|
.listen((_) => _cocosWidgetState.widget.onCocosUnloaded!());
|
|
}
|
|
}
|
|
|
|
/// Checks to see if cocos player is ready to be used
|
|
/// Returns `true` if cocos player is ready.
|
|
Future<bool?>? isReady() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.isReady(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Get the current pause state of the cocos player
|
|
/// Returns `true` if cocos player is paused.
|
|
Future<bool?>? isPaused() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.isPaused(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Get the current load state of the cocos player
|
|
/// Returns `true` if cocos player is loaded.
|
|
Future<bool?>? isLoaded() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.isLoaded(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Helper method to know if Cocos has been put in background mode (WIP) unstable
|
|
/// Returns `true` if cocos player is in background.
|
|
Future<bool?>? inBackground() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.inBackground(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Creates a cocos player if it's not already created. Please only call this if cocos is not ready,
|
|
/// or is in unloaded state. Use [isLoaded] to check.
|
|
/// Returns `true` if cocos player was created succesfully.
|
|
Future<bool?>? create() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.createCocosPlayer(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Post message to cocos from flutter. This method takes in a string [message].
|
|
/// The [gameObject] must match the name of an actual cocos game object in a scene at runtime, and the [methodName],
|
|
/// must exist in a `MonoDevelop` `class` and also exposed as a method. [message] is an parameter taken by the method
|
|
///
|
|
/// ```dart
|
|
/// postMessage("GameManager", "openScene", "ThirdScene")
|
|
/// ```
|
|
Future<void>? postMessage(String gameObject, methodName, message) {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.postMessage(
|
|
cocosId: cocosId,
|
|
gameObject: gameObject,
|
|
methodName: methodName,
|
|
message: message,
|
|
);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Post message to cocos from flutter. This method takes in a Json or map structure as the [message].
|
|
/// The [gameObject] must match the name of an actual cocos game object in a scene at runtime, and the [methodName],
|
|
/// must exist in a `MonoDevelop` `class` and also exposed as a method. [message] is an parameter taken by the method
|
|
///
|
|
/// ```dart
|
|
/// postJsonMessage("GameManager", "openScene", {"buildIndex": 3, "name": "ThirdScene"})
|
|
/// ```
|
|
Future<void>? postJsonMessage(
|
|
String gameObject, String methodName, Map<String, dynamic> message) {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.postJsonMessage(
|
|
cocosId: cocosId,
|
|
gameObject: gameObject,
|
|
methodName: methodName,
|
|
message: message,
|
|
);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Pause the cocos in-game player with this method
|
|
Future<void>? pause() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.pausePlayer(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Resume the cocos in-game player with this method idf it is in a paused state
|
|
Future<void>? resume() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.resumePlayer(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Sometimes you want to open cocos in it's own process and openInNativeProcess does just that.
|
|
/// It works for Android and iOS is WIP
|
|
Future<void>? openInNativeProcess() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.openInNativeProcess(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Unloads cocos player from th current process (Works on Android only for now)
|
|
/// iOS is WIP. For more information please read [Cocos Docs](https://docs.cocos3d.com/2020.2/Documentation/Manual/CocosasaLibrary.html)
|
|
Future<void>? unload() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.unloadPlayer(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// Quits cocos player. Note that this kills the current flutter process, thus quiting the app
|
|
Future<void>? quit() {
|
|
if (!_cocosWidgetState.widget.enablePlaceholder) {
|
|
return CocosWidgetPlatform.instance.quitPlayer(cocosId: cocosId);
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/// cancel the subscriptions when dispose called
|
|
void _cancelSubscriptions() {
|
|
_onCocosMessageSub?.cancel();
|
|
_onCocosSceneLoadedSub?.cancel();
|
|
_onCocosUnloadedSub?.cancel();
|
|
|
|
_onCocosMessageSub = null;
|
|
_onCocosSceneLoadedSub = null;
|
|
_onCocosUnloadedSub = null;
|
|
}
|
|
|
|
void dispose() {
|
|
_cancelSubscriptions();
|
|
CocosWidgetPlatform.instance.dispose(cocosId: cocosId);
|
|
}
|
|
}
|
|
|