1

在将 HandBrakeCLI 与 php 一起使用时,是否有另一种方法可以实时逐行显示?到目前为止,我在 proc_open() 函数中使用fgets()来获取字节。fgets() 手册提到了长度:“读取结束时读取长度 - 1 个字节,或换行符(包含在返回值中)或 EOF(以先到者为准)。”。到目前为止,它不识别新行。

// disable output buffering so we can send the encoding progress to the browser.
ob_implicit_flush(true);

$Command = 'HandBrakeCLI -i "/tmp/in-1.FLV" -t 1 -c 1 -o "/tmp/out.mp4" -f mp4 --strict-anamorphic  -e x264 -q 20 --cfr  -a 1 -E faac -B 160 -6 dpl2 -R Auto -D 0 --gain=0 --audio-copy-mask none --audio-fallback ffac3 -x ref=1:weightp=1:subq=2:rc-lookahead=10:trellis=0:8x8dct=0';

echo 'Starting...';

ob_flush();
flush();

$descriptorspec = array(
   0 => array("pipe", "r"),  // stdin is a pipe that the child will read from (we do not use it).
   1 => array("pipe", "w"),  // stdout is a pipe that the child will write to and we will read from.
   2 => array("pipe", "w") // stderr is a file to write to (we do not use it).
);

// We do not use exec() because we want to get the Stdout line by line.   
$process = proc_open($Command, $descriptorspec, $pipes);

if(is_resource($process))
{
    $line = 1;
    while(!feof($pipes[1]))
    {
        $InputLine = fgets($pipes[1], 1024);
        if(strlen($InputLine) == 0) break;
            echo '<pre><strong>Line: '.$line++.'<br /></strong>';
                print_r($InputLine);
            echo '</pre>';
        ob_flush();
        flush();
    }
    fclose($pipes[0]);
    fclose($pipes[1]);
    fclose($pipes[2]);
}
echo 'Done!';

目前输出:

开始...

线路:1
编码:任务 1 of 1, 3.10 % 编码:任务 1 of 1, 6.61 % 编码:任务 1 of 1, 8.81 % 编码:任务 1 of 1, 11.44 % 编码:任务 1 of 1, 14.52 % 编码:任务 1 of 1, 18.03 % 编码:任务 1 of 1, 21.10 % 编码:任务 1 of 1, 25.05 % 编码:任务 1 of 1, 27.25 % 编码:任务 1 of 1, 29.03 % 编码:任务 1 of 1, 29.91 % 编码:任务 1 of 1, 33.45 % 编码:任务 1 of 1, 36.52 % 编码:任务 1 of 1, 39.19 % (316.92 fps, avg 318.50 fps, ETA 00h00m06s) 编码:任务 1 of 1, 42.46 % (316.92 fps, avg 318.50 fps, ETA 00h00m06s) 编码:任务 1 of 1,46.44 %(316.92 fps,平均 318.50 fps,ETA 00h00m06s) 编码:任务 1 of 1, 47.32 % (316.92 fps, avg 318.50 fps, ETA 00h00m06s) 编码:任务 1 of 1,49.96 %(294.34 fps,平均 315.56 fps,ETA 00h00m05s) 编码:任务 1 of 1, 53.03 % (294.34 fps, avg 315.56 fps, ETA 00h00m05s) 编码:任务 1 of 1, 56.54 % (294.34 fps, avg 315.56 fps, ETA 00h00m05s) 编码:任务 1 of 1, 61.08 % (336.12 fps, avg 330.04 fps, ETA 00h00m04s) 编码:任务 1 of 1,
线路:2
61.95 %(336.12 fps,平均 330.04 fps,ETA 00h00m04s) 编码:任务 1 of 1, 65.03 % (336.12 fps, avg 330.04 fps, ETA 00h00m04s) 编码:任务 1 of 1, 67.13 % (336.12 fps, avg 330.04 fps, ETA 00h00m04s) 编码:任务 1 of 1, 68.89 % (320.33 fps, avg 319.28 fps, ETA 00h00m03s) 编码:任务 1 of 1, 71.12 % (320.33 fps, avg 319.28 fps, ETA 00h00m03s) 编码:任务 1 of 1, 74.42 % (320.33 fps, avg 319.28 fps, ETA 00h00m03s) 编码:任务 1 of 1, 76.65 % (307.54 fps, avg 312.58 fps, ETA 00h00m02s) 编码:任务 1 of 1, 79.72 % (307.54 fps, avg 312.58 fps, ETA 00h00m02s) 编码:任务 1 of 1,83.38 %(307.54 fps,平均 312.58 fps,ETA 00h00m02s) 编码:任务 1 of 1,86.01 %(285.58 fps,平均 315.19 fps,ETA 00h00m01s) 编码:任务 1 of 1, 87.33 % (285.58 fps, avg 315.19 fps, ETA 00h00m01s) 编码:任务 1 of 1, 89.08 % (285.58 fps, avg 315.19 fps, ETA 00h00m01s) 编码:任务 1 of 1, 91.72 % (285.58 fps, avg 315.19 fps, ETA 00h00m01s) 编码:任务 1 of 1, 94.79 % (278.94 fps, avg 307.07 fps, ETA 00h00m
线路:3
00s) 编码:任务 1 of 1, 96.99 % (278.94 fps, avg 307.07 fps, ETA 00h00m00s) 编码:任务 1 of 1, 100.00 % (278.94 fps, avg 307.07 fps, ETA 00h00m00s) 编码:任务 1 of 1, 100.00 % (278.94 fps, avg 307.07 fps, ETA 00h00m00s)
完毕!

结果不考虑换行并继续搜索,直到达到 1024 字节。有没有不同的方法可以用来逐行显示输出实时?

4

1 回答 1

3

我想通了:使用 fread() 而不是 fgets(); fread() 是二进制安全的。

于 2012-11-22T17:53:35.860 回答