在小菜的《吹弹牛皮之Unity 100行代码找出性能消耗源头》公众号文章中,小菜提及了一版lua版的性能采样分析工具。由于不够全面,且存在多处设计上需要改良的地方。基于此,在最近的项目上又做了一版c#版本的。
不管是bat(windows批处理调用),还是python调用Unity的方式,都只有一种。总结如下
set unityPath="C:\program files\Unity\Editor\Unity.exe" set projectPath="D:\WorkSpace\Project_Main\Client" %unityPath% -quit -batchmode -projectPath %projectPath% -nographics -executeMethod JenkinsBuild.DistributedBuildSetup
当然了在调用前,我们也需要切掉当前正在打开的Unity.exe
taskkill /f /im Unity.exe
在批处理模式下运行Unity。应始终与其他命令行参数一起使用,因为它确保不会弹出窗口,无需任何人为的干预。当脚本代码在执行过程中发生异常,资源服务器更新失败或其他操作失败时Unity将立即退出,并返回代码为1。请注意,在批处理模式下, Unity将向控制台发送输出版本最小的日志。当然,日志文件将包含完整的日志信息。
其他命令执行完毕后将退出Unity编辑器。请注意,这可能会导致错误消息被隐藏(但他们将显示在Editor.log文件)
打开指定路径的项目
当运行在批处理模式,不会初始化显卡设备。这使得它可以在你的机器上自动按工作流程运行,甚至它没有GPU。
在Unity启动的同时会执行静态方法,该项目是开放的并且是在可选资源服务器更新完成之后。这可以用来不断的整合,进行单元测试,制作模型,准备一些数据等。如果你想通过命令行返回一个错误,你可以抛出一个异常,会引发代码为1的Unity关闭或其他引发EditorApplication.Exit非零代码。
指定将要被写入编辑的log文件
导入提供的package,不会显示导入对话框
根据提供的路径建立一个空项目
bat是windows下的批处理命令。经过上面的介绍大体有了一个认识。调用Unity如下:
set unityPath="C:\program files\Unity\Editor\Unity.exe" set projectPath="D:\WorkSpace\Project_Main\Client" taskkill /f /im agent.exe taskkill /f /im conductor.exe taskkill /f /im Unity.exe %unityPath% -quit -batchmode -projectPath %projectPath% -nographics -executeMethod JenkinsBuild.DistributedBuildSetup
Bat调用Python是非常简单的
python F:\WorkSpace\ToolTest\ToolPython.py
当然了也可以传入参数
python F:\WorkSpace\ToolTest\ToolPython.py -targetModel "1" -unity "C:\Program Files\Unity\Editor\Unity.exe" -project "D:\WorkSpace\Project_Main\Client"
python中解析Bat中传入的参数如下
def WriteFileLog(logContext): fileName = "pythonLog.txt" logFile = open(fileName,"a+") logFile.write(logContext + '\n') if __name__ == '__main__': import argparse parser = argparse.ArgumentParser(description=u'Unity realtime log printing build!') parser.add_argument('-targetModel', required=True, help=u'Target Model') parser.add_argument('-unity', required=True, help=u'Unity executable file path') parser.add_argument('-project', required=True, help=u'Unity project path') args = parser.parse_args() WriteFileLog(args.unity) WriteFileLog(args.project) if args.targetModel == "1": WriteFileLog("1111111") else: WriteFileLog("222222")
根据设计模式中的开闭原则。尽可能在外部的改动时,不会动到原有的实现了,而是扩展。我们的工作操作者很可能是非技术,更多的情形他们认识配置文件,却无从改动编码。因此我们希望常改动配置的项放在ini文件中。
#unity路径 unityPath=C:/Program Files/Unity/Editor/Unity.exe #工程路径 projectPath=F:/Branches/Int_RG/Client targetModel=1
现在我们的Bat只要将ini作为参数传入python就好。
python ToolPython_ini.py ToolIni.ini
如何在python中解析这些参数呢? 跟着小菜往下看
def WriteFileLog(logContext): fileName = "pythonLog.txt" logFile = open(fileName,"a+") logFile.write(logContext + '\n') if __name__ == '__main__': config = sys.argv[1] unityPath = readconfig(config, "unityPath").replace("\n","") projectPath = readconfig(config, "projectPath").replace("\n", "") targetModel = readconfig(config, "targetModel").replace("\n", "") WriteFileLog(unityPath) WriteFileLog(projectPath) if targetModel == "1": WriteFileLog("1111111") else: WriteFileLog("222222")
“我可以悄悄学个Python然后惊艳所有人!” 哈哈终于派到python出场了。 这里尤其要说明python的头定义报错问题。 在python的脚本前定义上这两行编码
#!/usr/bin/python # -*- coding: UTF-8 -*-
下面是一段完整的Pyhton调用Unity编码,具体细节在UnityBuild函数中
#!/usr/bin/python # -*- coding: UTF-8 -*- import platform import os import thread import tail import subprocess #执行命令,如果错误,打印错误代码 _isWinPlatform = ("Windows" in platform.system()) def DoCmd(cmd): if _isWinPlatform: print("cmd: " + cmd) status = os.system(cmd) print ("\ncmd [" + cmd + "]: " + str(status)) return status == 0 return False def WriteFileLog(logContext): fileName = "pythonLog.txt" logFile = open(fileName,"a+") logFile.write(logContext + '\n') def fullpath(path): return os.path.abspath(os.path.expanduser(path)) def tail_thread(tail_file): print "wait for tail file ... %s" % tail_file while True: if os.path.exists(tail_file): print "Start tail file..... %s" % tail_file break t = tail.Tail(tail_file) t.register_callback(unity_log_tail) t.follow(s=1) def unity_log_tail(txt): print(txt) def UnityBuild(projectPath,unityPath,args1,args2,args3): DoCmd('''taskkill /f /im Unity.exe''') build_cmd = [unityPath, '-batchmode', '-quit', '-projectPath', projectPath, '-nographics', '-executeMethod', 'JenkinsBuild.DistributedBuildSetup' 'Args1='+args1, 'Args2='+args2, 'Args3='+args3] print 'Unity running ....' logOutPath = fullpath(os.path.join(projectPath, 'UnityBuildLog.txt') # new thread to tail log file thread.start_new_thread(tail_thread, (logOutPath, )) process = subprocess.Popen( build_cmd, stdout=subprocess.PIPE, stderr=subprocess.STDOUT, cwd=projectPath ) while True: out = process.stdout.read(1) if out == '' and process.poll() != None: break if out != '': sys.stdout.write("[Unity process console output]: " + out) sys.stdout.flush() print 'sys.stdout.flush. out: ' + out print 'done!' time.sleep(5) def WriteFileLog(logContext): fileName = "pythonLog.txt" logFile = open(fileName,"a+") logFile.write(logContext + '\n') if __name__ == '__main__': import argparse parser = argparse.ArgumentParser(description=u'Unity realtime log printing build!') parser.add_argument('-targetModel', required=True, help=u'Target Model') parser.add_argument('-unity', required=True, help=u'Unity executable file path') parser.add_argument('-project', required=True, help=u'Unity project path') args = parser.parse_args() WriteFileLog(args.unity) WriteFileLog(args.project) if args.targetModel == "1": WriteFileLog("1111111") else: WriteFileLog("222222") Args1 = "agcdefg" Args2 = "66666" Args3 = "true" UnityBuild(fullpath(args.project),fullpath(args.unity),Args1,Args2,Args3)
百度网盘地址: 链接:https://pan.baidu.com/s/1gRnEWKqf2uqVBRxLjNEi7Q 提取码:w4so
微信公众号:吹弹牛皮之unity程序设计 作者:赵晋伟 《吹弹牛皮之Unity 工具制作常用交互bat ini python》版权归原作者小菜(赵晋伟)所有,请勿随意转载和抄袭一经作者发现将需要追究其法律责任和经济损失!谢谢!
本文分享自微信公众号 - 吹弹牛皮之unity程序设计(gh_4f97f8f53f59)
原文出处及转载信息见文内详细说明,如有侵权,请联系 [email protected] 删除。
原始发表时间: 2021-10-24
本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。