PDA

View Full Version : Calculating Time of a flv file when the flv file is created from wmv file


farooqsam_786
07-11-2006, 09:24 AM
Hi All, :)

Language : PHP


I am working in video organiser project. In my project we have a functionality like to convert wmv file to flv and to capture the first frame of the video file to image file. its working fine. But i need to capture the total time will be taken by the flv file when it is played in Flash palyer in browser. Bcz to display the time in the image which is generated when the image file is created for the wmv file.

If anybody has a idea or experience in getting the total time will be taken by the flv file when its palyed.


regards

Umar Farooq

:)

cb2531
07-13-2006, 04:48 AM
Search the methods of the WF_VideoInputProperties interface.



GetDuration

Retrieves the duration of the input file in seconds. SetInputFile() must be called first.

C++:

HRESULT GetDuration(

long* pDuration

);


Visual Basic:

object.GetDuration as Long

rectalogic
09-07-2006, 06:05 PM
The problem with GetDuration() is it is the duration of the input file and I seem to remember this differed from the FLV duration. GetDurationMilli() might return better results.

I compute the FLV duration from the encoded FLV itself. The FLV file format is documented at Macromedias site. Basically validate the FLV header and determine if there is a video stream or only audio. Then seek to the end of the file and read the UI32 there which is the size of the last tag, then keep seeking backwards skipping over tags until you find a video (or audio if no video) tag, skip forward a UI24 (tag size) then read a UI24 and UI8 - this is the last timestamp (a big endian UI24 followed by UI8 which is the upper byte) and this is the duration in milliseconds.

It would be nice if FlixEngine had an API to get this directly since it obviously knows.

kerrizor
09-16-2006, 07:27 PM
It would be nice if FlixEngine had an API to get this directly since it obviously knows.

It /does/ seem to be an obvious value to return. :rolleyes:

rbichon
10-26-2006, 02:12 PM
We have an admin system on our site built in PHP for uploading FLV's and storing their info in a database. Here is our function for calculating the duration of the movie.

function GetFLVDuration($file){
// get contents of a file into a string
if (file_exists($file)){
$handle = fopen($file, "r");
$contents = fread($handle, filesize($file));
fclose($handle);

if (strlen($contents) > 3){
if (substr($contents,0,3) == "FLV"){
$taglen = hexdec(bin2hex(substr($contents,strlen($contents)-3)));
if (strlen($contents) > $taglen){
$duration = hexdec(bin2hex(substr($contents,strlen($contents)-$taglen,3)));
return $duration;
}
}
}
}
return false;
}

notevenclose
10-30-2006, 06:11 PM
function GetFLVDuration($file){
// get contents of a file into a string
if (file_exists($file)){
$handle = fopen($file, "r");
$contents = fread($handle, filesize($file));
fclose($handle);

if (strlen($contents) > 3){
if (substr($contents,0,3) == "FLV"){
$taglen = hexdec(bin2hex(substr($contents,strlen($contents)-3)));
if (strlen($contents) > $taglen){
$duration = hexdec(bin2hex(substr($contents,strlen($contents)-$taglen,3)));
return $duration;
}
}
}
}
return false;
}

Interesting technique, but not even close. This, in most cases returns zero byte info. And when you have server configuration correct, it will return a hex value of the general file size of the flv your trying to get. This in no way takes into consideration bitrate, and codec.

Note: Do NOT use this method above, it will do nothing for you.

There is no way to calculate an accurate flv duration without having the codec.

If you want to do a general calculation with file size, this method is ok, but I would recommend curl instead.

rectalogic
11-06-2006, 07:45 PM
This in no way takes into consideration bitrate, and codec.

There is no way to calculate an accurate flv duration without having the codec.



This isn't correct at all, you don't need to take into account codec or bitrate to get the file duration in milliseconds. Re-read the FLV format spec - the timestamp of each video packet is independent of the codec used - all you need to do is seek to the end of the file, read the size of the last tag, back up and read the duration. The code posted looks basically correct although I didn't test it and aside from a couple of issues (should read the last 4 bytes - UI32 - although 3 bytes will suffice for most durations, should check the tag is video and not audio, and sucking the whole FLV into memory could present issues).

rbichon
02-16-2007, 03:35 PM
Thank you rectalogic for agreeing with me. I am a little insulted by the “Not Even Close” comment from the other guy. This method was derived directly from the FLV specs furnished by Adobe. The duration is encoded in the FLV itself and most definitely works. I have used it on more that 100 FLV’s since I wrote it and it has never failed.

You are correct about memory consumption. We have a dedicated server so it isn’t an issue. If you don't have one then you will probably run into memory limits with PHP on larger FLV files. I only calculate the duration when I upload the FLV with PHP and then store it into a MySQL table. That way, it never has to be done twice.

zas
11-27-2008, 11:46 AM
function GetFLVDuration($file){
$duration = false;

if (file_exists($file)){
$fp = fopen($file, 'r');
if ($fp) {
$header = fread($fp, 5);
if ($header !== false) {
$is_flv = ($header[0]=='F' && $header[1]=='L' && $header[2]=='V');
$is_flv_video = (hexdec(bin2hex($header[4])) & 0x01);
if ($is_flv && $is_flv_video) {
if (fseek($fp, 0, SEEK_END) == 0) {
$length = ftell($fp);
if ($length !== false) {
if (fseek($fp, -4, SEEK_END) == 0) {
$value = fread($fp,4);
if ($value !== false) {
$taglen = hexdec(bin2hex($value));
if ($length > $taglen) {
if (fseek($fp, $length - $taglen, SEEK_SET) == 0) {
$value = fread($fp, 3);
if ($value !== false) {
$duration = hexdec(bin2hex($value));
}
}
}
}
}
}
}
}
}
fclose($fp);
}
}
return $duration;
}


This version don't load all the data in the memory and is much faster.
It checks the file header for flv video.
It will return the duration in milliseconds or false on error.