浏览代码

add apm game plugin

/yanmeng
meng.yan 4 年前
当前提交
7f43cfca
共有 29 个文件被更改,包括 3347 次插入212 次删除
  1. 41
      .DS_Store
  2. 1
      .gitignore
  3. 24
      Assets/HuaweiService/apm/APMS.cs
  4. 148
      Assets/HuaweiService/apm/AddCustomTrace.cs
  5. 154
      Assets/HuaweiService/apm/Editor/TraceInjectPostProecess.cs
  6. 44
      Assets/HuaweiService/apm/NetworkMeasure.cs
  7. 2
      Assets/Plugins/Android/baseProjectTemplate.gradle
  8. 7
      Assets/Plugins/Android/launcherTemplate.gradle
  9. 7
      Assets/Plugins/Android/mainTemplate.gradle
  10. 880
      Assets/HuaweiService/apm/Editor/Unity.Cecil.Mdb.dll
  11. 1001
      Assets/HuaweiService/apm/Editor/Unity.Cecil.Pdb.dll
  12. 1001
      Assets/HuaweiService/apm/Editor/Unity.Cecil.dll
  13. 1
      Assets/HuaweiService/.DS_Store
  14. 1
      Assets/HuaweiService/apm/.DS_Store
  15. 1
      Assets/HuaweiService/apm/Editor/.DS_Store
  16. 39
      Assets/HuaweiService/apm/GameAPM.cs
  17. 43
      Assets/HuaweiService/apm/GameAttribute.cs
  18. 1
      Assets/HuaweiService/app_linking/.DS_Store
  19. 2
      Assets/HuaweiServiceDemo/Scripts/test/.DS_Store
  20. 27
      Assets/HuaweiServiceDemo/Scripts/test/apm/EnableGamePluginButton.cs
  21. 70
      Assets/HuaweiServiceDemo/Scripts/test/apm/GameApmTest.cs
  22. 24
      Assets/HuaweiServiceDemo/Scripts/test/apm/GameApmTestButton.cs
  23. 24
      Assets/HuaweiServiceDemo/Scripts/test/apm/StopLoadingSceneButton.cs
  24. 8
      Assets/HuaweiService/apm.meta
  25. 8
      Assets/HuaweiServiceDemo/Scripts/test/apm.meta
  26. 0
      /Assets/HuaweiService/apm/Editor/Unity.Cecil.Mdb.dll
  27. 0
      /Assets/HuaweiService/apm/Editor/Unity.Cecil.Pdb.dll
  28. 0
      /Assets/HuaweiService/apm/Editor/Unity.Cecil.dll

41
.DS_Store
文件差异内容过多而无法显示
查看文件

1
.gitignore


*.gen.*
obj$
obj.meta$
*.meta
build/**
PackageSources

24
Assets/HuaweiService/apm/APMS.cs


public NetworkMeasure createNetworkMeasure(string arg0, string arg1) {
return Call<NetworkMeasure>("createNetworkMeasure", arg0, arg1);
}
public void startGamePlugin() {
GameAPM.getInstance().start();
}
public void stopGamePlugin() {
GameAPM.getInstance().stop();
}
public string startLoadingScene(GameAttribute arg0)
{
return GameAPM.getInstance().startLoadingScene(arg0);
}
public void stopLoadingScene(string arg0)
{
GameAPM.getInstance().stopLoadingScene(arg0);
}
public void setCurrentGameAttribute(GameAttribute arg0) {
GameAPM.getInstance().setCurrentGameAttribute(arg0);
}
public void setReportRate(int arg0) {
GameAPM.getInstance().setReportRate(arg0);
}
public void enableGamePlugin(bool arg0) {
GameAPM.getInstance().enableGamePlugin(arg0);
}
}
}

148
Assets/HuaweiService/apm/AddCustomTrace.cs


using UnityEngine;
using System.Reflection;
using System.Linq;
using Mono.Cecil;
using Mono.Cecil.Cil;
using HuaweiService.apm;
namespace HuaweiService
{

set{
m_enable = value;
}
}
}
public class TraceInjector
{
public static void Inject(string assemblyPath)
{
//Debug.Log("inject custom trace Start");
// 按路径读取程序集, 如果文件不存在则返回错误信息
if(!System.IO.File.Exists(assemblyPath)){
Debug.LogError(string.Format("{0} is not Exists",
assemblyPath));
}
var readerParameters = new ReaderParameters { ReadSymbols = true };
var assembly = AssemblyDefinition.ReadAssembly(assemblyPath, readerParameters);
if (assembly == null)
{
Debug.LogError(string.Format("InjectTool Inject Load assembly failed: {0}",
assemblyPath));
return;
}
try
{
var module = assembly.MainModule;
foreach (var type in module.Types)
{
foreach (var method in type.Methods)
{
// 找到method中需要注入的类型
var needInjectAttr = typeof(AddCustomTrace).FullName;
bool needInject = method.CustomAttributes.Any(typeAttribute => typeAttribute.AttributeType.FullName == needInjectAttr);
if (!needInject)
{
continue;
}
// 只对公有方法进行注入
if (method.IsConstructor || method.IsGetter || method.IsSetter || !method.IsPublic)
continue;
Inject(module, method, type);
}
}
assembly.Write(assemblyPath, new WriterParameters { WriteSymbols = true });
}
catch (System.Exception ex)
{
Debug.LogError(string.Format("InjectTool Inject failed: {0}", ex));
throw;
}
finally
{
if (assembly.MainModule.SymbolReader != null)
{
assembly.MainModule.SymbolReader.Dispose();
}
}
}
private static void Inject(ModuleDefinition module, MethodDefinition method, TypeDefinition type)
{
if(module == null){
throw new ArgumentNullException("input argument invalid, module is null");
}
if(method == null){
throw new ArgumentNullException("input argument invalid, method is null");
}
if(type == null){
throw new ArgumentNullException("input argument invalid, type is null");
}
//获取方法AddCustomTrace
AddCustomTrace attr = getTraceAttribute(type, method);
//判断功能是否开启
if(attr.enable != true){
//Debug.Log(method.Name + " close add custom trace attribute.");
return;
}
//获取特性名称
String name = attr.name;
//更改待注入函数局部变量表
method.Body.InitLocals = true;
var customTraceType = module.ImportReference(typeof(CustomTrace));
var customTraceTypeDef = new VariableDefinition(customTraceType);
method.Body.Variables.Add(customTraceTypeDef);
//准备注入的函数
MethodReference getInstance = module.ImportReference(typeof(APMS).GetMethod("getInstance"));
MethodReference createInstance = module.ImportReference(typeof(APMS).GetMethod("createCustomTrace", new Type[] {typeof(string)}));
MethodReference customTraceStart = module.ImportReference(typeof(CustomTrace).GetMethod("start"));
MethodReference customTraceEnd = module.ImportReference(typeof(CustomTrace).GetMethod("stop"));
//设置一些标签用于语句跳转
Instruction first = method.Body.Instructions[0];
// 开始注入IL代码
var ilProcessor = method.Body.GetILProcessor();
ilProcessor.InsertBefore(first, ilProcessor.Create(OpCodes.Nop));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Call, getInstance));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Ldstr, name));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Callvirt, createInstance));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Stloc, customTraceTypeDef));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Ldloc, customTraceTypeDef));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Callvirt, customTraceStart));
ilProcessor.InsertBefore(first, ilProcessor.Create(OpCodes.Nop));
//在每一个返回的地方插入stop函数,注意插入指令之后,method.Body.Instructions.Count会增加,需要调整i值
for(int i=0;i<method.Body.Instructions.Count;i++){
Instruction ins = method.Body.Instructions[i];
OpCode code = ins.OpCode;
if(ins.OpCode.Equals(OpCodes.Ret) || ins.OpCode.Equals(OpCodes.Throw)){
//Debug.Log("method: " + method.Name + "i: " + i + " code: " + code);
ilProcessor.InsertBefore(ins, ilProcessor.Create(OpCodes.Nop));
ilProcessor.InsertBefore(ins, Instruction.Create(OpCodes.Ldloc, customTraceTypeDef));
ilProcessor.InsertBefore(ins, Instruction.Create(OpCodes.Callvirt, customTraceEnd));
ilProcessor.InsertBefore(ins, ilProcessor.Create(OpCodes.Nop));
i+=4;
}
}
}
//获取函数的特性
private static AddCustomTrace getTraceAttribute(TypeDefinition type, MethodDefinition method){
Type inejectClassType = Type.GetType(type.FullName);
if(inejectClassType == null){
throw new NullReferenceException("Class Type is null, Attribute: " + type.FullName);
}
MethodInfo methodinfo = inejectClassType.GetMethod(method.Name);
if(methodinfo == null){
throw new NullReferenceException("methodinfo in class " + type.FullName + " is null, method name: " + method.Name);
}
AddCustomTrace attr = (AddCustomTrace)methodinfo.GetCustomAttributes(typeof(AddCustomTrace), true)[0] ;
if(attr == null){
throw new NullReferenceException("attr AddCustomTrace on method "+ method.Name + " is null");
}
return attr;
}
}
}

154
Assets/HuaweiService/apm/Editor/TraceInjectPostProecess.cs


using UnityEditor;
using UnityEditor.Compilation;
using UnityEngine;
using System.Reflection;
using System;
using System.Linq;
using Mono.Cecil;
using Mono.Cecil.Cil;
using HuaweiService.apm;
namespace HuaweiService{
[InitializeOnLoad]
public class TraceInjectPostProecess{

TraceInjector.Inject(arg1);
}
}
}
public class TraceInjector
{
public static void Inject(string assemblyPath)
{
//Debug.Log("inject custom trace Start");
//Read the assembly according to the path, if the file does not exist, return an error message
if(!System.IO.File.Exists(assemblyPath)){
Debug.LogError(string.Format("{0} is not Exists",
assemblyPath));
}
var readerParameters = new ReaderParameters { ReadSymbols = true };
var assembly = AssemblyDefinition.ReadAssembly(assemblyPath, readerParameters);
if (assembly == null)
{
Debug.LogError(string.Format("InjectTool Inject Load assembly failed: {0}",
assemblyPath));
return;
}
try
{
var module = assembly.MainModule;
foreach (var type in module.Types)
{
foreach (var method in type.Methods)
{
//Find the type that needs to be injected in the method
var needInjectAttr = typeof(AddCustomTrace).FullName;
bool needInject = method.CustomAttributes.Any(typeAttribute => typeAttribute.AttributeType.FullName == needInjectAttr);
if (!needInject)
{
continue;
}
//Only public methods need to be injected
if (method.IsConstructor || method.IsGetter || method.IsSetter || !method.IsPublic)
continue;
Inject(module, method, type, assembly);
}
}
assembly.Write(assemblyPath, new WriterParameters { WriteSymbols = true });
}
catch (System.Exception ex)
{
Debug.LogError(string.Format("InjectTool Inject failed: {0}", ex));
throw;
}
finally
{
if (assembly.MainModule.SymbolReader != null)
{
assembly.MainModule.SymbolReader.Dispose();
}
}
}
private static void Inject(ModuleDefinition module, MethodDefinition method, TypeDefinition type, AssemblyDefinition assembly)
{
if(module == null){
throw new ArgumentNullException("input argument invalid, module is null");
}
if(method == null){
throw new ArgumentNullException("input argument invalid, method is null");
}
if(type == null){
throw new ArgumentNullException("input argument invalid, type is null");
}
//get AddCustomTrace attribute in method
AddCustomTrace attr = getTraceAttribute(type, method, assembly);
//whether the function is turned on
if(attr.enable != true){
return;
}
//get name of attribute
String name = attr.name;
//Change the local variable table of the function to be injected
method.Body.InitLocals = true;
var customTraceType = module.ImportReference(typeof(CustomTrace));
var customTraceTypeDef = new VariableDefinition(customTraceType);
method.Body.Variables.Add(customTraceTypeDef);
//Prepare functions to be injected
MethodReference getInstance = module.ImportReference(typeof(APMS).GetMethod("getInstance"));
MethodReference createInstance = module.ImportReference(typeof(APMS).GetMethod("createCustomTrace", new Type[] {typeof(string)}));
MethodReference customTraceStart = module.ImportReference(typeof(CustomTrace).GetMethod("start"));
MethodReference customTraceEnd = module.ImportReference(typeof(CustomTrace).GetMethod("stop"));
//Set some labels for statement jump
Instruction first = method.Body.Instructions[0];
// start injecting IL code
var ilProcessor = method.Body.GetILProcessor();
ilProcessor.InsertBefore(first, ilProcessor.Create(OpCodes.Nop));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Call, getInstance));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Ldstr, name));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Callvirt, createInstance));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Stloc, customTraceTypeDef));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Ldloc, customTraceTypeDef));
ilProcessor.InsertBefore(first, Instruction.Create(OpCodes.Callvirt, customTraceStart));
ilProcessor.InsertBefore(first, ilProcessor.Create(OpCodes.Nop));
//Insert stop functions at every return. Note that after inserting the instruction,
//method.Body.Instructions.Count increment,and need to adjust the value of i
for(int i=0;i<method.Body.Instructions.Count;i++){
Instruction ins = method.Body.Instructions[i];
OpCode code = ins.OpCode;
if(ins.OpCode.Equals(OpCodes.Ret) || ins.OpCode.Equals(OpCodes.Throw)){
//Debug.Log("method: " + method.Name + "i: " + i + " code: " + code);
ilProcessor.InsertBefore(ins, ilProcessor.Create(OpCodes.Nop));
ilProcessor.InsertBefore(ins, Instruction.Create(OpCodes.Ldloc, customTraceTypeDef));
ilProcessor.InsertBefore(ins, Instruction.Create(OpCodes.Callvirt, customTraceEnd));
ilProcessor.InsertBefore(ins, ilProcessor.Create(OpCodes.Nop));
i+=4;
}
}
}
//get attribute of given method
private static AddCustomTrace getTraceAttribute(TypeDefinition type, MethodDefinition method, AssemblyDefinition assembly){
Type inejectClassType = Type.GetType(type.FullName + ", " + assembly.Name);
if(inejectClassType == null){
throw new NullReferenceException("Class Type is null, Attribute: " + type.FullName);
}
MethodInfo methodinfo = inejectClassType.GetMethod(method.Name);
if(methodinfo == null){
throw new NullReferenceException("methodinfo in class " + type.FullName + " is null, method name: " + method.Name);
}
AddCustomTrace attr = (AddCustomTrace)methodinfo.GetCustomAttributes(typeof(AddCustomTrace), true)[0] ;
if(attr == null){
throw new NullReferenceException("attr AddCustomTrace on method "+ method.Name + " is null");
}
return attr;
}
}
}

44
Assets/HuaweiService/apm/NetworkMeasure.cs


using UnityEngine;
using System.Collections.Generic;
namespace HuaweiService.apm
{
public class NetworkMeasure_Data : IHmsBaseClass{
public string name => "com.huawei.agconnect.apms.custom.NetworkMeasure";
}
public class NetworkMeasure :HmsClass<NetworkMeasure_Data>
{
public NetworkMeasure (string arg0, string arg1): base(arg0, arg1) { }
public NetworkMeasure (): base() { }
public void start() {
Call("start");
}
public void stop() {
Call("stop");
}
public void setStatusCode(int arg0) {
Call("setStatusCode", arg0);
}
public void setBytesSent(long arg0) {
Call("setBytesSent", arg0);
}
public void setBytesReceived(long arg0) {
Call("setBytesReceived", arg0);
}
public void setContentType(string arg0) {
Call("setContentType", arg0);
}
public void putProperty(string arg0, string arg1) {
Call("putProperty", arg0, arg1);
}
public void removeProperty(string arg0) {
Call("removeProperty", arg0);
}
public Map getProperties() {
return Call<Map>("getProperties");
}
public string getProperty(string arg0) {
return Call<string>("getProperty", arg0);
}
}
}

2
Assets/Plugins/Android/baseProjectTemplate.gradle


// To specify a custom Gradle version in Unity, go do "Preferences > External Tools", uncheck "Gradle Installed with Unity (recommended)" and specify a path to a custom Gradle version
classpath 'com.android.tools.build:gradle:3.4.0'
classpath 'com.huawei.agconnect:agcp:1.4.2.300'
classpath 'com.huawei.agconnect:agconnect-apms-plugin:1.4.1.303'
classpath 'com.huawei.agconnect:agconnect-apms-plugin:1.5.2.300'
**BUILD_SCRIPT_DEPS**
}
}

7
Assets/Plugins/Android/launcherTemplate.gradle


dependencies {
implementation project(':unityLibrary')
implementation 'com.huawei.agconnect:agconnect-apms:1.4.1.303'
implementation 'com.huawei.agconnect:agconnect-apms:1.5.2.300'
implementation 'com.huawei.agconnect:agconnect-apms-game:1.5.2.300'
implementation "com.huawei.agconnect:agconnect-storage:1.3.1.100"
implementation "com.huawei.agconnect:agconnect-appmessaging:1.4.1.300"
implementation 'com.huawei.agconnect:agconnect-applinking:1.4.1.300'

implementation 'androidx.appcompat:appcompat:1.2.0'
implementation 'com.huawei.hms:hianalytics:5.1.0.300'
implementation 'com.huawei.agconnect:agconnect-crash:1.4.1.300'
implementation 'com.huawei.agconnect:agconnect-core:1.4.1.300'
implementation 'com.huawei.agconnect:agconnect-core:1.4.1.300'
implementation 'com.huawei.agconnect:agconnect-function:1.4.2.300'
implementation 'com.huawei.hms:base:5.0.5.300'
implementation 'com.huawei.hms:game:5.0.4.302'

sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
packagingOptions {
exclude 'META-INF/INDEX.LIST'
exclude 'META-INF/io.netty.versions.properties'

7
Assets/Plugins/Android/mainTemplate.gradle


implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation "com.huawei.agconnect:agconnect-appmessaging:1.4.1.300"
implementation 'com.huawei.hms:hianalytics:5.1.0.300'
//Google
//Google
implementation 'com.google.android.gms:play-services-auth:18.1.0'
//Google Play Game
implementation 'com.google.android.gms:play-services-games:17.0.0'

api 'com.tencent.mm.opensdk:wechat-sdk-android-without-mta:+'
//facebook
implementation 'com.facebook.android:facebook-android-sdk:4.20.0'
implementation 'com.huawei.agconnect:agconnect-apms:1.3.1.300'
implementation 'com.huawei.agconnect:agconnect-apms:1.5.2.300'
implementation 'com.huawei.agconnect:agconnect-apms-game:1.5.2.300'
//hms
implementation 'com.huawei.hms:base:5.0.5.300'

880
Assets/HuaweiService/apm/Editor/Unity.Cecil.Mdb.dll
文件差异内容过多而无法显示
查看文件

1001
Assets/HuaweiService/apm/Editor/Unity.Cecil.Pdb.dll
文件差异内容过多而无法显示
查看文件

1001
Assets/HuaweiService/apm/Editor/Unity.Cecil.dll
文件差异内容过多而无法显示
查看文件

1
Assets/HuaweiService/.DS_Store
文件差异内容过多而无法显示
查看文件

1
Assets/HuaweiService/apm/.DS_Store
文件差异内容过多而无法显示
查看文件

1
Assets/HuaweiService/apm/Editor/.DS_Store
文件差异内容过多而无法显示
查看文件

39
Assets/HuaweiService/apm/GameAPM.cs


using UnityEngine;
using System.Collections.Generic;
namespace HuaweiService.apm
{
public class GameAPM_Data : IHmsBaseClass{
public string name => "com.huawei.agconnect.apms.game.GameAPM";
}
public class GameAPM :HmsClass<GameAPM_Data>
{
public GameAPM (): base() { }
public static GameAPM getInstance() {
return CallStatic<GameAPM>("getInstance");
}
public void start() {
Call("start");
}
public void stop() {
Call("stop");
}
public string startLoadingScene(GameAttribute arg0) {
return Call<string>("startLoadingScene", arg0);
}
public void stopLoadingScene(string arg0) {
Call("stopLoadingScene", arg0);
}
public void setCurrentGameAttribute(GameAttribute arg0) {
Call("setCurrentGameAttribute", arg0);
}
public void setReportRate(int arg0) {
Call("setReportRate", arg0);
}
public void enableGamePlugin(bool arg0) {
Call("enableGamePlugin", arg0);
}
}
}

43
Assets/HuaweiService/apm/GameAttribute.cs


using UnityEngine;
using System.Collections.Generic;
namespace HuaweiService.apm
{
public class GameAttribute_Data : IHmsBaseClass{
public string name => "com.huawei.agconnect.apms.game.GameAttribute";
}
public class GameAttribute :HmsClass<GameAttribute_Data>
{
public GameAttribute(string arg0, LoadingState arg1) : base(arg0, arg1)
{
this.obj = this.obj;
}
public GameAttribute() : base()
{
this.obj = this.obj;
}
public LoadingState getLoadingState() {
return Call<LoadingState>("getLoadingState");
}
public void setLoadingState(LoadingState arg0) {
Call("setLoadingState", arg0);
}
public string getScene() {
return Call<string>("getScene");
}
public class LoadingState_Data : IHmsBaseClass{
public string name => "com.huawei.agconnect.apms.game.GameAttribute$LoadingState";
}
public class LoadingState :HmsClass<LoadingState_Data>
{
public static LoadingState NOT_LOADING => HmsUtil.GetStaticValue<LoadingState>("NOT_LOADING");
public static LoadingState LOADING => HmsUtil.GetStaticValue<LoadingState>("LOADING");
public LoadingState (string arg0, int arg1, int arg2): base(arg0, arg1, arg2) { }
public LoadingState (): base() { }
}
}
}

1
Assets/HuaweiService/app_linking/.DS_Store
文件差异内容过多而无法显示
查看文件

2
Assets/HuaweiServiceDemo/Scripts/test/.DS_Store
文件差异内容过多而无法显示
查看文件

27
Assets/HuaweiServiceDemo/Scripts/test/apm/EnableGamePluginButton.cs


using UnityEngine;
using UnityEngine.UI;
namespace ApmTest
{
public class EnableGamePluginButton : MonoBehaviour
{
// Start is called before the first frame update
public Button m_button;
private GameApmTest m_test;
private bool m_gamePluginStatus;
void Start()
{
m_gamePluginStatus = false;
m_test = new GameApmTest();
Button btn = m_button.GetComponent<Button>();
btn.onClick.AddListener(this.switchStatus);
}
void switchStatus()
{
m_test.switchGamePluginStatus(m_gamePluginStatus);
m_gamePluginStatus = !m_gamePluginStatus;
}
}
}

70
Assets/HuaweiServiceDemo/Scripts/test/apm/GameApmTest.cs


using System.IO;
using System.Threading;
using UnityEngine;
using HuaweiService.apm;
using HuaweiService;
using UnityEngine.UI;
namespace ApmTest
{
public class GameApmTest
{
private static string sceneHandler = "";
static int gameApmTest_count = 0;
private static int stopLoadingSceneTest_count = 0;
public void gameApmTest(Text text)
{
gameApmTest_count++;
text.text = "gameApmTest start, count: " + gameApmTest_count + "\n";
GameAttribute attribute = new GameAttribute("new scene", GameAttribute.LoadingState.NOT_LOADING);
text.text += "create new attribute success\n";
APMS.getInstance().startGamePlugin();
text.text +="GameAPM start\n";
APMS.getInstance().enableGamePlugin(true);
text.text +="enableGamePlugin: true\n";
sceneHandler = APMS.getInstance().startLoadingScene(attribute);
text.text +="startLoadingScene, sceneHandler= " + sceneHandler + "\n";
APMS.getInstance().setCurrentGameAttribute(attribute);
text.text +="setCurrentGameAttribute\n";
APMS.getInstance().setReportRate(1);
text.text += "setReportRate\n";
text.text += "gameApmTest success\n\n";
}
public void stopLoadingScene(Text text)
{
stopLoadingSceneTest_count++;
text.text = "stopLoadingSceneTest start, count: " + stopLoadingSceneTest_count + "\n";
APMS.getInstance().stopLoadingScene(sceneHandler);
text.text +="stopLoadingScene\n";
APMS.getInstance().stopGamePlugin();
text.text +="GameAPM stop\n";
text.text += "stopLoadingSceneTest success\n";
}
public void switchGamePluginStatus(bool status)
{
if (status == false)
{
Debug.Log("switch enableCollection status from false -> true");
APMS.getInstance().enableGamePlugin(true);
}
else if (status == true)
{
Debug.Log("switch enableCollection status from true -> false");
APMS.getInstance().enableGamePlugin(false);
}
}
}
}

24
Assets/HuaweiServiceDemo/Scripts/test/apm/GameApmTestButton.cs


using UnityEngine;
using UnityEngine.UI;
namespace ApmTest
{
public class GameApmTestButton : MonoBehaviour
{
// Start is called before the first frame update
public Button m_button;
void Start()
{
Button btn = m_button.GetComponent<Button>();
btn.onClick.AddListener(this.gameApmTest);
}
void gameApmTest()
{
GameApmTest test = new GameApmTest();
Text text = this.GetComponentInChildren<Text>();
test.gameApmTest(text);
}
}
}

24
Assets/HuaweiServiceDemo/Scripts/test/apm/StopLoadingSceneButton.cs


using UnityEngine;
using UnityEngine.UI;
namespace ApmTest
{
public class StopLoadingSceneButton : MonoBehaviour
{
// Start is called before the first frame update
public Button m_button;
void Start()
{
Button btn = m_button.GetComponent<Button>();
btn.onClick.AddListener(this.stopLoadingScene);
}
void stopLoadingScene()
{
GameApmTest test = new GameApmTest();
Text text = this.GetComponentInChildren<Text>();
test.stopLoadingScene(text);
}
}
}

8
Assets/HuaweiService/apm.meta


fileFormatVersion: 2
guid: ed0048e9ddfc0420e99d42298a7beba2
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

8
Assets/HuaweiServiceDemo/Scripts/test/apm.meta


fileFormatVersion: 2
guid: 7a58a1d7ae6354573b066eb9f7d85940
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

/Assets/HuaweiService/apm/Plugin/Unity.Cecil.Mdb.dll → /Assets/HuaweiService/apm/Editor/Unity.Cecil.Mdb.dll

/Assets/HuaweiService/apm/Plugin/Unity.Cecil.Pdb.dll → /Assets/HuaweiService/apm/Editor/Unity.Cecil.Pdb.dll

/Assets/HuaweiService/apm/Plugin/Unity.Cecil.dll → /Assets/HuaweiService/apm/Editor/Unity.Cecil.dll

正在加载...
取消
保存