在 Unity3D 中运行外部 shell 脚本的方法

有时候项目里需要执行一些shell脚本,来完成诸如文件移动,命令行打包,自己转换文件
格式什么的工作,省去一些手工劳动,然后这时候就需要用shell了。
网上也有一些关于调用方法的文章,这里就说一下我自己尝试时遇到的问题。。。

讲到c#里操作进程的方法,那肯定就是System.Diagnostics.Process这个类没跑了

代码如下:

using UnityEngine;
using UnityEditor;
using System.Diagnostics;
using System.Threading;
using System.IO;

public class TestRunShell : ScriptableObject
{
    [MenuItem("Menu/RunShell")]
    public static void RunShell()
    {
        // 这里不开线程的话,就会阻塞住unity的主线程,当然如果你需要阻塞的效果的话可以不开
        Thread newThread = new Thread(new ThreadStart(RunShellThreadStart));
        newThread.Start();
    }

    private static void RunShellThreadStart()
    {
        string cmdTxt = @"echo test
notepad C:\Users\pc\Desktop\1.txt
explorer.exe D:\
pause";

        RunCommand(cmdTxt);
        //RunProcessCommand("notepad", @"C:\Users\pc\Desktop\1.txt");
        //RunProcessCommand("explorer.exe", @"D:\");
    }

    private static void RunCommand(string command)
    {
        Process process = new Process();
        process.StartInfo.FileName = "powershell";
        process.StartInfo.Arguments = command;

        process.StartInfo.CreateNoWindow = false; // 获取或设置指示是否在新窗口中启动该进程的值(不想弹出powershell窗口看执行过程的话,就=true)
        process.StartInfo.ErrorDialog = true; // 该值指示不能启动进程时是否向用户显示错误对话框
        process.StartInfo.UseShellExecute = false;
        //process.StartInfo.RedirectStandardError = true;
        //process.StartInfo.RedirectStandardInput = true;
        //process.StartInfo.RedirectStandardOutput = true;

        process.Start();

        //process.StandardInput.WriteLine(@"explorer.exe D:\");
        //process.StandardInput.WriteLine("pause");

        process.WaitForExit();
        process.Close();
    }

    private static void RunProcessCommand(string command, string argument)
    {
        ProcessStartInfo start = new ProcessStartInfo();
        start.FileName = command;
        start.Arguments = argument;

        start.CreateNoWindow = false;
        start.ErrorDialog = true;
        start.UseShellExecute = false;

        Process p = Process.Start(start);
        p.WaitForExit();
        p.Close();
    }
}

cmd.exe 执行的问题

因为我是windows环境,且搜到的文章里都是

process.StartInfo.FileName = "cmd.exe";

这样的写法,但是经过测试发现,在cmd里能够执行的命令,传不进cmd.exe里面去,怀疑是不是mono的事,.net下可能就传进去了,这里懒得深究了。。。
但是换成powershell就可以很顺利的传进去执行。

我手上没有mac的环境,但是感觉把powershell换成bash,应该就可以在mac上顺利的执行shell脚本了


ProcessStartInfoRedirectStandardErrorRedirectStandardInputRedirectStandardOutput属性的设置问题

msdn上查的UseShellExecute的说明

若要在启动进程时使用外壳程序,则为 true;否则,直接从可执行文件创建进程。默认为 true。

将此属性设置为 false 使您能够重定向输入流、输出流和错误流。

测试结果:

①,UseShellExecute = false,3个重定向的设置为true时,打开的shell窗口中,我们就看不到echo 看我!这样命令的输出结果了。

②,UseShellExecute = true,他们3个也是true时,传入的shell脚本不能够运行。

③,3个重定向的属性为true时,我们并不能用截取输入流的方式往里面传入参数
例如:

process.Start();
process.StandardInput.WriteLine(@"explorer.exe D:\");
process.StandardInput.WriteLine("pause");
process.WaitForExit();
process.Close();

所以总结一下就是,那3个重定向属性还是保持默认值就好了,反正往输入流中写参数的方法也不管用,2333

使用的时候,我们就可以先把自己写的.bat文件读成字符串,然后用上面的RunCommand执行整个bat脚本了。
还可以用RunProcessCommand方法去调用指定的.exe,并为其传递参数了(前提是它能接收参数)

Shell脚本运行另一个Shell脚本可以通过两种方式实现。第一种方式是在当前进程运行另一个Shell脚本,可以使用source命令或点号(.)来执行。这样做会将另一个Shell脚本的内容直接插入到当前Shell脚本的执行环境,不会创建新的进程。例如,可以使用以下命令来运行另一个Shell脚本: ``` source 另一个脚本.sh . 另一个脚本.sh ``` 第二种方式是在新的进程运行另一个Shell脚本,可以使用以下命令来执行: ``` ./另一个脚本.sh ``` 在这种情况下,需要为另一个Shell脚本添加可执行权限,并指定正确的路径。注意,这种方式会创建一个新的Shell进程来执行另一个脚本。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *3* [Shell脚本【2】写和运行Shell脚本](https://blog.csdn.net/qq_43624033/article/details/106455124)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 50%"] - *2* [shell----shell脚本运行](https://blog.csdn.net/weixin_45606836/article/details/104377197)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 50%"] [ .reference_list ]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值