ffmpeg 可以显示进度条吗? [英] Can ffmpeg show a progress bar?

查看:255
本文介绍了ffmpeg 可以显示进度条吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用 ffmpeg 将 .avi 文件转换为 .flv 文件.由于转换文件需要很长时间,我想显示一个进度条.有人可以指导我如何做同样的事情.

I am converting a .avi file to .flv file using ffmpeg. As it takes a long time to convert a file I would like to display a progress bar. Can someone please guide me on how to go about the same.

我知道 ffmpeg 必须以某种方式在文本文件中输出进度,我必须使用 ajax 调用读取它.但是如何让ffmpeg将进度输出到文本文件?

I know that ffmpeg somehow has to output the progress in a text file and I have to read it using ajax calls. But how do I get ffmpeg to output the progress to the text file?

推荐答案

我已经玩了几天了.ffmpegprogress"这个东西有帮助,但很难开始使用我的设置,也很难阅读代码.

I've been playing around with this for a few days. That "ffmpegprogress" thing helped, but it was very hard to get to work with my set up, and hard to read the code.

为了显示ffmpeg的进度,您需要执行以下操作:

In order to show the progress of ffmpeg you need to do the following:

  1. 从 php 运行 ffmpeg 命令,无需等待响应(对我来说,这是最难的部分)
  2. 告诉 ffmpeg 将其输出发送到文件
  3. 从前端(AJAX、Flash 等)直接点击该文件或可以从 ffmpeg 的输出中提取进度的 php 文件.

这是我解决每个部分的方法:

Here's how I solved each part:

1.我从ffmpegprogress"中得到了以下想法.这就是他所做的:一个 PHP 文件通过 http 套接字调用另一个.第二个实际上运行exec",第一个文件只是挂在它上面.对我来说,他的实现太复杂了.他正在使用fsockopen".我喜欢卷毛.所以这就是我所做的:

1. I got the following idea from "ffmpegprogress". This is what he did: one PHP file calls another through an http socket. The 2nd one actually runs the "exec" and the first file just hangs up on it. For me his implementation was too complex. He was using "fsockopen". I like CURL. So here's what I did:

$url = "http://".$_SERVER["HTTP_HOST"]."/path/to/exec/exec.php";
curl_setopt($curlH, CURLOPT_URL, $url);
$postData = "&cmd=".urlencode($cmd);
$postData .= "&outFile=".urlencode("path/to/output.txt");
curl_setopt($curlH, CURLOPT_POST, TRUE);
curl_setopt($curlH, CURLOPT_POSTFIELDS, $postData);

curl_setopt($curlH, CURLOPT_RETURNTRANSFER, TRUE);

// # this is the key!
curl_setopt($curlH, CURLOPT_TIMEOUT, 1);
$result = curl_exec($curlH);

将 CURLOPT_TIMEOUT 设置为 1 意味着它将等待 1 秒以获得响应.最好是更低.还有需要毫秒的 CURLOPT_TIMEOUT_MS,但它对我不起作用.

Setting CURLOPT_TIMEOUT to 1 means it will wait 1 second for a response. Preferably that would be lower. There is also the CURLOPT_TIMEOUT_MS which takes milliseconds, but it didn't work for me.

1 秒后,CURL 挂断,但 exec 命令仍在运行.第 1 部分已解决.

After 1 second, CURL hangs up, but the exec command still runs. Part 1 solved.

顺便说一句 - 有些人建议为此使用nohup"命令.但这似乎对我不起作用.

BTW - A few people were suggesting using the "nohup" command for this. But that didn't seem to work for me.

*还有!在您的服务器上拥有一个可以直接在命令行上执行代码的 php 文件是一个明显的安全风险.您应该有密码,或者以某种方式对帖子数据进行编码.

*ALSO! Having a php file on your server that can execute code directly on the command line is an obvious security risk. You should have a password, or encode the post data in some way.

2.上面的exec.php"脚本还必须告诉 ffmpeg 输出到文件.这是代码:

2. The "exec.php" script above must also tell ffmpeg to output to a file. Here's code for that:

exec("ffmpeg -i path/to/input.mov path/to/output.flv 1> path/to/output.txt 2>&1");

注意1> path/to/output.txt 2>&1".我不是命令行专家,但据我所知,这一行说将正常输出发送到这个文件,并将错误发送到同一个地方".查看此网址了解更多信息:http://tldp.org/LDP/abs/html/io-redirection.html

Note the "1> path/to/output.txt 2>&1". I'm no command line expert, but from what I can tell this line says "send normal output to this file, AND send errors to the same place". Check out this url for more info: http://tldp.org/LDP/abs/html/io-redirection.html

3.从前端调用一个 php 脚本,给出 output.txt 文件的位置.然后该 php 文件将从文本文件中提取进度.我是这样做的:

3. From the front end call a php script giving it the location of the output.txt file. That php file will then pull out the progress from the text file. Here's how I did that:

// # get duration of source
preg_match("/Duration: (.*?), start:/", $content, $matches);

$rawDuration = $matches[1];

// # rawDuration is in 00:00:00.00 format. This converts it to seconds.
$ar = array_reverse(explode(":", $rawDuration));
$duration = floatval($ar[0]);
if (!empty($ar[1])) $duration += intval($ar[1]) * 60;
if (!empty($ar[2])) $duration += intval($ar[2]) * 60 * 60;


// # get the current time
preg_match_all("/time=(.*?) bitrate/", $content, $matches); 

$last = array_pop($matches);
// # this is needed if there is more than one match
if (is_array($last)) {
    $last = array_pop($last);
}

$curTime = floatval($last);


// # finally, progress is easy
$progress = $curTime/$duration;

希望这对某人有所帮助.

Hope this helps someone.

这篇关于ffmpeg 可以显示进度条吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆