我想从我的应用程序启动ffmpeg并检索ffmpeg产生的所有控制台输出。事情似乎很明显,我跟随了许多论坛的帖子/文章,但我有问题,尽管我遵循了所有的信息,但我似乎最终陷入了死胡同。
应该包含ffmpeg输出的字符串总是空的。我试着看看问题出在哪里,所以我做了一个简单的c#控制台应用程序,只列出所有传递给ffmpeg的执行参数,只是为了检查问题是否由ffmpeg本身引起。在这种情况下,一切都按预期进行。
我也预览了我的应用程序的控制台窗口。当我启动ffmpeg时,我看到控制台中的所有输出,但是应该接收输出以进一步处理报告的函数该字符串为空。当我的参数列表应用程序启动时,我看到的唯一一件事就是得到输出的函数的预期报告。
所以我的问题是怎么做才能得到ffmpeg输出,因为我打算在第一。
提前感谢m
这是一个很长的镜头,但是你试过重定向标准错误吗?
这是我的ffmpeg包装器类的一部分,特别展示了如何从ffmpeg收集输出和错误。
我把进程放在GetVideoDuration()
函数中,这样你就可以在一个地方看到所有的东西。
设置:
我的ffmpeg在桌面上,ffPath是用来指向它的
namespace ChildTools.Tools
{
public class FFMpegWrapper
{
//path to ffmpeg (I HATE!!! MS special folders)
string ffPath = System.Environment.GetFolderPath(Environment.SpecialFolder.Desktop) + "\ffmpeg.exe";
//outputLines receives each line of output, only if they are not zero length
List<string> outputLines = new List<string>();
//In GetVideoDuration I only want the one line of output and in text form.
//To get the whole output just remove the filter I use (my search for 'Duration') and either return the List<>
//Or joint the strings from List<> (you could have used StringBuilder, but I find a List<> handier.
public string GetVideoDuration(FileInfo fi)
{
outputLines.Clear();
//I only use the information flag in this function
string strCommand = string.Concat(" -i "", fi.FullName, """);
//Point ffPath to my ffmpeg
string ffPath = System.Environment.GetFolderPath(Environment.SpecialFolder.Desktop) + "\ffmpeg.exe";
Process processFfmpeg = new Process();
processFfmpeg.StartInfo.Arguments = strCommand;
processFfmpeg.StartInfo.FileName = ffPath;
//I have to say that I struggled for a while with the order that I setup the process.
//But this order below I know to work
processFfmpeg.StartInfo.UseShellExecute = false;
processFfmpeg.StartInfo.RedirectStandardOutput = true;
processFfmpeg.StartInfo.RedirectStandardError = true;
processFfmpeg.StartInfo.CreateNoWindow = true;
processFfmpeg.ErrorDataReceived += processFfmpeg_OutData;
processFfmpeg.OutputDataReceived += processFfmpeg_OutData;
processFfmpeg.EnableRaisingEvents = true;
processFfmpeg.Start();
processFfmpeg.BeginOutputReadLine();
processFfmpeg.BeginErrorReadLine();
processFfmpeg.WaitForExit();
//I filter the lines because I only want 'Duration' this time
string oStr = "";
foreach (string str in outputLines)
{
if (str.Contains("Duration"))
{
oStr = str;
}
}
//return a single string with the duration line
return oStr;
}
private void processFfmpeg_OutData(object sender, DataReceivedEventArgs e)
{
//The data we want is in e.Data, you must be careful of null strings
string strMessage = e.Data;
if outputLines != null && strMessage != null && strMessage.Length > 0)
{
outputLines.Add(string.Concat( strMessage,"n"));
//Try a Console output here to see all of the output. Particularly
//useful when you are examining the packets and working out timeframes
//Console.WriteLine(strMessage);
}
}
}
}