FFmpeg duration

Collapse
X
 
  • Time
  • Show
Clear All
new posts
  • mikeworks
    Confirmed User
    • Apr 2010
    • 272

    #1

    Tech FFmpeg duration

    I can see video duration with following command

    Code:
    ffmpeg -i 'video.mp4'
    
    Duration: 00:01:17.92, start: 0.023220, bitrate: 1593 kb/s
    Is there a way to use that duration value in the ffmpeg command?
  • Colmike9
    (>^_^)b
    • Dec 2011
    • 7230

    #2
    PHP


    $file=file.avi;
    $time = exec("$ffmpeg -i /path/".$file." 2>&1 |
    grep Duration | cut -d ' ' -f 4 | sed s/,//");
    echo $time;
    Join the BEST cam affiliate program on the internet!
    I've referred over $1.7mil in spending this past year, you should join in.
    I make a lot more money in the medical field in a lab now, fuck you guys. Don't ask me to come back, but do join Chaturbate in my sig, it still makes bank without me touching shit for years..

    Comment

    • Barry-xlovecam
      It's 42
      • Jun 2010
      • 18083

      #3
      https://stackoverflow.com/questions/...-ffmpeg-output
      here are some interesting ideas to try -- you don't need php
      Code:
      The program 'avconv' is currently not installed. You can install it by typing:
      sudo apt install libav-tools
      
      
      ...pvid/porno$ avconv -i \
      Wife_sharing_her_husband_with_horny_lesbian_friend_Video.flv\
        2>&1 | grep Duration | sed 's/Duration: \(.*\), start.*/\1/g'
      
        00:39:16.04

      Comment

      • mikeworks
        Confirmed User
        • Apr 2010
        • 272

        #4
        Thanks guys, with current encoded script I have found another solution that almost works.

        If I paste this into command line it works:
        Code:
        eval $(ffprobe -v error -of flat=s=_ -select_streams v:0 -show_entries stream=duration /path/to/file/1.mp4) duration=${streams_stream_0_duration}
        
        /usr/local/bin/ffmpeg -i '/path/to/file/1.mp4' -vf 'scale=448:trunc(ow/a/vsub)*vsub' -vf drawtext="fontsize=16:[email protected]:fontfile=/usr/local/share/fonts/freefont-ttf/FreeSans.ttf:text='Blah blah blah':y=25:x=w-(t-($duration/2))*w/20" -threads 0 -acodec libfaac -ar 44100 -ab 128k -vcodec libx264 -preset slower -keyint_min 25 -g 250 -r 25 -y /path/to/output/file/temp_vid.mp4
        Note the line break between the ffprobe and ffmpeg commands.

        Now, when I save this in the database of encoded script (only way to use command), it removes that line ending up like this:

        Code:
        eval $(ffprobe -v error -of flat=s=_ -select_streams v:0 -show_entries stream=duration /path/to/file/1.mp4) duration=${streams_stream_0_duration} /usr/local/bin/ffmpeg -i '/path/to/file/1.mp4' -vf 'scale=448:trunc(ow/a/vsub)*vsub' -vf drawtext="fontsize=16:[email protected]:fontfile=/usr/local/share/fonts/freefont-ttf/FreeSans.ttf:text='Blah blah blah':y=25:x=w-(t-($duration/2))*w/20" -threads 0 -acodec libfaac -ar 44100 -ab 128k -vcodec libx264 -preset slower -keyint_min 25 -g 250 -r 25 -y /path/to/output/file/temp_vid.mp4
        Without the line break, command line reports this error:

        Syntax error: "(" unexpected

        Is there any way to save into the database and maintain the important line break between the ffprobe and ffmpeg command?

        Comment

        • Colmike9
          (>^_^)b
          • Dec 2011
          • 7230

          #5
          Originally posted by Barry-xlovecam
          https://stackoverflow.com/questions/...-ffmpeg-output
          here are some interesting ideas to try -- you don't need php
          Code:
          The program 'avconv' is currently not installed. You can install it by typing:
          sudo apt install libav-tools
          
          
          ...pvid/porno$ avconv -i \
          Wife_sharing_her_husband_with_horny_lesbian_friend_Video.flv\
            2>&1 | grep Duration | sed 's/Duration: \(.*\), start.*/\1/g'
          
            00:39:16.04
          Yeah, I think I read it wrong before..
          Join the BEST cam affiliate program on the internet!
          I've referred over $1.7mil in spending this past year, you should join in.
          I make a lot more money in the medical field in a lab now, fuck you guys. Don't ask me to come back, but do join Chaturbate in my sig, it still makes bank without me touching shit for years..

          Comment

          • Barry-xlovecam
            It's 42
            • Jun 2010
            • 18083

            #6
            try

            ${streams_stream_0_duration} /usr/local/b
            replaced with
            ${streams_stream_0_duration}; /usr/local/b
            or
            ${streams_stream_0_duration} && /usr/local/b

            if that won't work you will need to run it as 2 commands in a bash *.sh script

            loop and read `cat`a file list

            Comment

            • mikeworks
              Confirmed User
              • Apr 2010
              • 272

              #7
              Thanks for help. I have tried everything so far and still no joy.

              I went from using ffprobe to ffmpeg itself to output duration in seconds:

              duration=$(/usr/local/bin/ffmpeg -i /path/to/file/1.mp4 2>&1 | grep "Duration"| cut -d ' ' -f 4 | sed s/,// | sed 's@\..*@@g' | awk '{ split($1, A, ":"); split(A[3], B, "."); print 3600*A[1] + 60*A[2] + B[1] }') /usr/local/bin/ffmpeg -i /path/to/file/1.mp4 -vf 'scale=448:trunc(ow/a/vsub)*vsub' -vf drawtext="fontsize=16:[email protected]:fontfile =/usr/local/share/fonts/freefont-ttf/FreeSans.ttf:text='Blah blah blah':y=25:x=w-(t-($duration/2))*w/20" -threads 0 -acodec libfaac -ar 44100 -ab 128k -vcodec libx264 -preset slower -keyint_min 25 -g 250 -r 24 -y /path/to/output/temp_vid.mp4

              It works in command line perfect, even without a line break it works.

              But when I save it in database for script to use, damn thing won't encode and shows in admin area the error code, if I copy the 'error code' into command line it works perfect.

              Comment

              • Barry-xlovecam
                It's 42
                • Jun 2010
                • 18083

                #8
                what is it?
                "But when I save it in database"
                what gets stored in the 'database'( mysql? )
                paste me/us the stored field value and the table column type you are storing it in?

                a ':' is not the same in all column types
                https://dev.mysql.com/doc/refman/5.7/en/time.html

                you are not dealing with time you are dealing with text
                you are not performing time arithmetic (end time - start time)=elapsed time
                you are just trying to store and retrive a text value of 'video run time length'

                Is this the problem?

                Comment

                • mikeworks
                  Confirmed User
                  • Apr 2010
                  • 272

                  #9
                  The field value is:

                  duration=$(%ffmpeg_path% -i %video_file% 2>&1 | grep "Duration"| cut -d ' ' -f 4 | sed s/,// | sed 's@..*@@g' | awk '{ split($1, A, ":"); split(A[3], B, "."); print 3600*A[1] + 60*A[2] + B[1] }') %ffmpeg_path% -i %video_file% %video_filters% -vf 'scale=448:trunc(ow/a/vsub)*vsub' -vf drawtext="fontsize=16:[email protected]:fontfile =/usr/local/share/fonts/freefont-ttf/FreeSans.ttf:text='Blah blah blah':y=25:x=w-(t-($duration/2))*w/20" -threads 0 %audio_encoder% -ar 44100 -ab %audio_bitrate%k -vcodec libx264 -preset slower -keyint_min 25 -g 250 -r %video_fps% %video_rotate% -y %video_target%

                  The field type is 'text'.

                  You can see the script replaces %ffmpeg_path% and others with true values.

                  I need to determine the duration of the video in seconds. Then divide that duration by 2, so I can add a watermark half way through the video.

                  Comment

                  • Barry-xlovecam
                    It's 42
                    • Jun 2010
                    • 18083

                    #10
                    The field value in your database server should be the result like 45:09:32 or similar. The returned result of your command.

                    I would use a bash .sh script for this. You can use PHP, Python, or other interrupter language you would prefer also (the devil you know best).
                    1. You need to loop a list of the files to process in a script. Then foreach($file){
                    2. perform the commands (ffmpeg +)
                    3. then get the duration 00:00:00
                    4. do your database UPDATE }
                    5. then in your cms get that duration value and display the HTML


                    MyVideo elapsed time 45:09:32

                    That is what you want to do? NO i read it again LOL

                    you need to do this in a few processes.

                    convert the video.
                    determine the seconds like 2400
                    the do the math 1200 = the middle
                    convert that to time 00:20:00 and use that in the command (a separate command to watermark)

                    nope edited -- that didn't work right

                    you are going to have to do a script for the math ... but that is the logic to use

                    Comment

                    • mikeworks
                      Confirmed User
                      • Apr 2010
                      • 272

                      #11
                      The database field runtime contains the count in seconds for example 256, but only after the video has been processed. Would then have to process video a second time to add watermark.

                      This is not ideal solution due to content amount and that cdn will sync video as soon as it has been encoded, and won't unless manual flush via contacting host, sync video after second encoding.

                      It's frustrating. I have no idea why the exact same code pasted into command line works, but script fails when using it.

                      The ffmpeg log is showing this:

                      [Parsed_drawtext_0 @ 0x808c3e320] [Eval @ 0x7fffffff9250] Undefined constant or missing '(' in '/2))*w/20'
                      [Parsed_drawtext_0 @ 0x808c3e320] Failed to configure input pad on Parsed_drawtext_0
                      Error opening filters!

                      So it looks like when run via script $duration is empty.
                      Last edited by mikeworks; 10-26-2017, 11:28 AM. Reason: ffmpeg log

                      Comment

                      • Kafka
                        Confirmed User
                        • Oct 2002
                        • 466

                        #12
                        You can add a linebreak : \n
                        Or just type a linebreak in the mysql insert like: this is
                        a linebreak

                        Or make one line by adding a && between the commands.

                        Comment

                        • Barry-xlovecam
                          It's 42
                          • Jun 2010
                          • 18083

                          #13
                          Use a bash script loop the files and ladder though it echoing out the variables. That is how you want to run terminal commands.
                          $ ./watermark.sh

                          Is that what you are doing?

                          Comment

                          • symtab
                            Confirmed User
                            • Nov 2009
                            • 415

                            #14
                            You can use ffprobe to actually get a json string. You can then convert this json string to an object in php with json_decode. This is more elegant and simplier.

                            Code:
                            exec('ffprobe -v quiet -loglevel quiet -show_format -show_streams -print_format json file.mp4', $output);
                            $json = json_decode(implode('', $output));
                            $duration = $json->format->duration;
                            Now in your watermark cmd you replace the duration with the above $duration variable.
                            Adult Scripts: Adult Script Pro 3.4.0 - Adult Search Script 3.8.0
                            Adult Traffic: Plug Rush - ExoClick

                            Comment

                            • Barry-xlovecam
                              It's 42
                              • Jun 2010
                              • 18083

                              #15
                              I found this It maybe could be adapted
                              the purpose was to extract a thumbnail from the middle
                              but it does find the middle an do something

                              your problem is that you want to do this in a single pass

                              the thread> https://superuser.com/questions/4773...eo-with-ffmpeg

                              up vote
                              -1
                              down vote


                              This bash command works like a charm:

                              Code:
                              avconv -i 'in.mpg' -vcodec mjpeg -vframes 1 -an -f rawvideo \
                              -s 420x300 -ss `avconv -i in.mpg 2>&1 | grep Duration \
                              | awk '{print $2}' | tr -d , \ 
                              | awk -F ':' '{print ($3+$2*60+$1*3600)/2}'` out.jpg
                              shareimprove this answer

                              edited May 15 '15 at 7:40
                              Matt Joiner
                              463725

                              answered Nov 9 '14 at 17:14
                              Георги Стефанов
                              1



                              My god that's complicated ? Sridhar-Sarnobat Mar 18 '15 at 18:22
                              Last post -- well life ain't simple dude
                              awk -F ':' '{print ($3+$2*60+$1*3600)/2 gets your midpoint

                              Comment

                              • mikeworks
                                Confirmed User
                                • Apr 2010
                                • 272

                                #16
                                Thanks everyone for help.

                                Problem is made much more difficult due to script being encoded.

                                I tried this as suggested:
                                exec('ffprobe -v quiet -loglevel quiet -show_format -show_streams -print_format json %video_file%', $output);
                                $json = json_decode(implode('', $output));
                                $duration = $json->format->duration;
                                $duration = $duration/2;

                                But whenever I have tried ffprobe it breaks the scripts encoding process for whatever reason. In command line it works perfect.

                                This works:
                                duration=$(%ffmpeg_path% -i %video_file% 2>&1 | grep "Duration"| cut -d ' ' -f 4 | sed s/,// | sed 's@..*@@g' | awk '{ split($1, A, ":"); split(A[3], B, "."); print 3600*A[1] + 60*A[2] + B[1] }') ;
                                %ffmpeg_path% -i %video_file% %video_filters% -vf 'scale=448:trunc(ow/a/vsub)*vsub' -vf drawtext="fontsize=16:[email protected]:fontfile =/usr/local/share/fonts/freefont-ttf/FreeSans.ttf:text='Blah blah blah':y=25:x=w-(t-($duration/2))*w/20" -threads 0 %audio_encoder% -ar 44100 -ab %audio_bitrate%k -vcodec libx264 -preset slower -keyint_min 25 -g 250 -r %video_fps% %video_rotate% -y %video_target%

                                as does this:
                                duration=$(%ffmpeg_path% -i %video_file% 2>&1 | grep "Duration"| cut -d ' ' -f 4 | sed s/,// | sed 's@..*@@g' | awk '{ split($1, A, ":"); split(A[3], B, "."); print 3600*A[1] + 60*A[2] + B[1] }') &&
                                %ffmpeg_path% -i %video_file% %video_filters% -vf 'scale=448:trunc(ow/a/vsub)*vsub' -vf drawtext="fontsize=16:[email protected]:fontfile =/usr/local/share/fonts/freefont-ttf/FreeSans.ttf:text='Blah blah blah':y=25:x=w-(t-($duration/2))*w/20" -threads 0 %audio_encoder% -ar 44100 -ab %audio_bitrate%k -vcodec libx264 -preset slower -keyint_min 25 -g 250 -r %video_fps% %video_rotate% -y %video_target%

                                and this:
                                duration=$(%ffmpeg_path% -i %video_file% 2>&1 | grep "Duration"| cut -d ' ' -f 4 | sed s/,// | sed 's@..*@@g' | awk '{ split($1, A, ":"); split(A[3], B, "."); print (3600*A[1] + 60*A[2] + B[1])/2 }') &&
                                %ffmpeg_path% -i %video_file% %video_filters% -vf 'scale=448:trunc(ow/a/vsub)*vsub' -vf drawtext="fontsize=16:[email protected]:fontfile =/usr/local/share/fonts/freefont-ttf/FreeSans.ttf:text='Blah blah blah':y=25:x=w-(t-($duration))*w/20" -threads 0 %audio_encoder% -ar 44100 -ab %audio_bitrate%k -vcodec libx264 -preset slower -keyint_min 25 -g 250 -r %video_fps% %video_rotate% -y %video_target%

                                As in it actually create thumbs, encodes video, watermarks video. But, the watermark appears from the start of the video. So I guess the $duration is not being populated with a value.

                                I have a log being generated now by ffmpeg by adding 2> 'path/to/log.txt' at the end of the command. It would helpful if it showed the ffmpeg command executed, but it only shows the encoding process. I believe I can adjust log to debug level, so will try that next, in case it gives a clue why $duration empty.

                                Comment

                                • symtab
                                  Confirmed User
                                  • Nov 2009
                                  • 415

                                  #17
                                  What i wrote is ment to be used from php. Is your script a shell script or you execute the cmd from php?
                                  Adult Scripts: Adult Script Pro 3.4.0 - Adult Search Script 3.8.0
                                  Adult Traffic: Plug Rush - ExoClick

                                  Comment

                                  • Barry-xlovecam
                                    It's 42
                                    • Jun 2010
                                    • 18083

                                    #18
                                    duration=$(%ffmpeg_path% -i %video_file% 2>&1 | grep "Duration"| cut -d ' ' -f 4 | sed s/,// | sed 's@..*@@g' | awk '{ split($1, A, ":")}'
                                    #; split(A[3], B, ".")

                                    echo $duration

                                    ; is an end next; next ...

                                    This really needs to be in a bash script --then you don't need all the ;'s and it is a lot less confusing to work with IMO

                                    Code:
                                    #!/bin/bash
                                    duration=$(%ffmpeg_path% -i %video_file% 2>&1 | grep "Duration"| cut -d ' ' -f 4 | sed s/,// | sed 's@..*@@g' | awk '{ split($1, A, ":")}'
                                    #; split(A[3], B, ".")
                                    
                                    echo $duration



                                    see if it works now
                                    Ladder up with the rest of the code
                                    spaghetti is good for dinner -- that is one fuck of a one liner (I like ) but can get confusing.

                                    gedit has a plugin that matches brackets {}

                                    Comment

                                    • mikeworks
                                      Confirmed User
                                      • Apr 2010
                                      • 272

                                      #19
                                      Script is php with database. The ffmpeg code is saved to field in database. Then script executes that code.

                                      With debug ffmpeg I can see problem is with variable duration:

                                      Reading option '-vf' ... matched as option 'vf' (set video filters) with argument 'drawtext=fontsize=16:[email protected]:fontfile =/usr/local/share/fonts/freefont-ttf/FreeSans.ttf:text='Blah blah blah':y=25:x=w-(t-0)*w/20'.

                                      You can see t-0, where 0 should be the duration.

                                      duration=10 works
                                      duration=$(10) does not assign value to variable, 0 output as above
                                      duration="$(10)" does not assign value to variable, 0 output as above
                                      duration=`10` does not work, breaks encoding

                                      I will try and work out how to integrate bash solution, thanks. But difficult with encoded script knowing how to send value of %video_file% to a bash script.

                                      More head scratching to do.

                                      Comment

                                      • symtab
                                        Confirmed User
                                        • Nov 2009
                                        • 415

                                        #20
                                        So what you could do is first get the duration and save it to a $duration variable. The ffmpeg command you use #DURATION# where you want to have the duration. Then you run str_replace like str_replace('#DURATION#', $duration, $ffmpeg_cmd); then you run the cmd. Also the ffmpeg drawtext requires to escape some characters, if you use single quote for the drawtext options then use double quote for the text itself (or remove the single quotes, this will also work), also other characters that need to be excaped are :,} and some other characters...
                                        Adult Scripts: Adult Script Pro 3.4.0 - Adult Search Script 3.8.0
                                        Adult Traffic: Plug Rush - ExoClick

                                        Comment

                                        • Barry-xlovecam
                                          It's 42
                                          • Jun 2010
                                          • 18083

                                          #21
                                          If you are working with a PHP Iron Cube or similar script encoding you are working with one hand tied behind your back.

                                          I think you will need to do this in bash outside of your encoded script. Just work one level above your video directory(s)

                                          Code:
                                          find . "*.mpg*"
                                          Make a .csv of that output
                                          then loop the files in a bash variable
                                          do the commands.

                                          it is trivial to loop twice
                                          only the time to read and do the conversion.
                                          if you have to; make a second .csv with the filepath, time just cut -d',' -f? < assign the field variables
                                          then loop that file and watermark I guess.

                                          You don't need PHP to do this that is like pounding a nail with a pile driver. It will take 2 days to set up the pile driver then you will bend the nail. PHP is a interpreter language. As soon as you start doing system commands in PHP other than for something trivial you will make a mess.
                                          Code:
                                          php  script.php
                                          ^^ works well in .sh (bash) scripts (cli) we are doing system work with ffmpeg. Use the right tool for the job rather than spend lots of time making what you know best work.

                                          Oh, and PHP json_encode; _decode; is good for many things. I am using it a lot these days but for its intended purpose ... JSON Use the right tool ...

                                          Comment

                                          Working...