Newest 'ffmpeg' Questions - Stack Overflow
Les articles publiés sur le site
-
Using swscale for image composing
15 août 2018, par armigeroI have an input image A and a resulting image B with the size 800x600 stored in YUV420 format and I need to scale image A into 100x100 size and place it into resulting image B at some point (x=100, y=100). To decrease memory and CPU usage I put swscale result right into final B image.
Here is a code snippets (pretty straightforward):
//here we a creating sws context for scaling into 100x100 sws_ctx = sws_getCachedContext(sws_ctx, frame.hdr.width, frame.hdr.height, AV_PIX_FMT_YUV420P, 100, 100, AV_PIX_FMT_YUV420P, SWS_BILINEAR, nullptr, nullptr, nullptr);
Next we create corresponding slice and strides describing image A
int src_y_plane_sz = frame.hdr.width * frame.hdr.height; int src_uv_plane_sz = src_y_plane_sz / 2; std::int32_t src_stride[] = { frame.hdr.width, frame.hdr.width / 2, frame.hdr.width / 2, 0}; const uint8_t* const src_slice[] = { &frame.raw_frame[0], &frame.raw_frame[0] + src_y_plane_sz, &frame.raw_frame[0] + src_y_plane_sz + src_uv_plane_sz, nullptr};
Now doing the same for a destination B image
std::int32_t dst_stride[] = { current_frame.hdr.width, current_frame.hdr.width /2, current_frame.hdr.width /2, 0 }; std::int32_t y_plane_sz = current_frame.hdr.width * current_frame.hdr.height; std::int32_t uv_plane_sz = y_plane_sz / 2; //calculate offset in slices for x=100, y=100 position std::int32_t y_offset = current_frame.hdr.width * 100 + 100; uint8_t* const dst_slice[] = { ¤t_frame.raw_frame[0] + y_offset, ¤t_frame.raw_frame[0] + y_plane_sz + y_offset / 2, ¤t_frame.raw_frame[0] + y_plane_sz + uv_plane_sz + y_offset / 2, nullptr};
After all - calling swscale
int ret = sws_scale(sws_ctx, src_slice, src_stride, 0, frame.hdr.height, dst_slice, dst_stride);
After using a testing sequence I having some invalid result with the following problems:
- Y component got some padding line
- UV components got misplaced - they are a bit lower then original Y components.
Does anyone have had the same problems with swscale function? I am pretty new to this FFmpeg library collection so I am open to any opinions how to perform this task correctly.
FFmpeg version used 3.3
-
Overlay video with other video in ffmpeg
15 août 2018, par user2212461I have a short and a long mp4 video. In the long video, I would like to replace the visual with a part of the visual of the short video. Additionally, I would like to keep the audio of the long video throughout.
The following set of commands work. However the concat and audio replacing seems to add a slight delay to the video, which makes the audio slightly out of sync from the video.
ffmpeg -ss 0 -i short.mp4 -t 2.0 -vcodec copy -an v1_short.mp4 ffmpeg -ss 0 -i long.mp4 -t 6.0 -vcodec copy -an v1_before.mp4 ffmpeg -ss 8.0 -i v_before.mp4 -vcodec copy -an v1_after.mp4.mp4 ffmpeg -i v1_before.mp4 -i v1_short.mp4 -i v1_after.mp4 -filter_complex "[0:v] [1:v] [2:v] concat=n=3:v=1 [v]" -map "[v]" out_temp.mp4 ffmpeg -i long.mp4 -i out_temp.mp4 -c copy -map 0:v -map 1:a out_final.mp4
How can I do this without the audio getting out of sync?
I am using ffmpeg version 4.0.2.
-
C# execute external program and capture (stream) the output
15 août 2018, par Roberto CorreiaI'm making a program to work with some video files.
I'm using the ffmpeg executable to merge several files in a single file. This command takes several minutes to finish, so, I need a way to "monitor" the output, and show a progress bar on GUI.
Looking at the following stackoverflow topics:
- How to parse command line output from c#?
- Process.start: how to get the output?
- How To: Execute command line in C#, get STD OUT results
I made this code:
Process ffmpeg = new Process { StartInfo = { FileName = @"d:\tmp\ffmpeg.exe", Arguments = "-f concat -safe 0 -i __sync.txt -c copy output.mp4", UseShellExecute = false, RedirectStandardOutput = true, CreateNoWindow = true, WorkingDirectory = @"d:\tmp" } } ffmpeg.EnableRaisingEvents = true; ffmpeg.OutputDataReceived += (s, e) => Debug.WriteLine(e.Data); ffmpeg.ErrorDataReceived += (s, e) => Debug.WriteLine($@"Error: {e.Data}"); ffmpeg.Start(); ffmpeg.BeginOutputReadLine(); ffmpeg.WaitForExit();
When I run this code, the ffmpeg start to merge files, I can see the ffmpeg process on Windows Task Manager, and if I wait long enough, the ffmpeg finish the job without any error. But, the
Debug.WriteLine(e.Data)
is never called (no output on Debug window). Tried to change toConsole.WriteLine
too (again, no output).So, after this, I tried this another version:
Process ffmpeg = new Process { StartInfo = { FileName = @"d:\tmp\ffmpeg.exe", Arguments = "-f concat -safe 0 -i __sync.txt -c copy output.mp4", UseShellExecute = false, RedirectStandardOutput = true, CreateNoWindow = true, WorkingDirectory = @"d:\tmp" } } ffmpeg.Start(); while (!ffmpeg.StandardOutput.EndOfStream) { var line = ffmpeg.StandardOutput.ReadLine(); System.Diagnostics.Debug.WriteLine(line); Console.WriteLine(line); } ffmpeg.WaitForExit();
Again, the ffmpeg is started without any error, but the C# "hangs" on
While (!ffmpeg.StandardOutput.EndOfStream)
until ffmpeg is finished.If I execute the exact command on Windows prompt, a lot of output text is showed with progress of ffmpeg.
-
FFMPEG DirectShow AJA Audio capture
15 août 2018, par NiCOI have an AJA board with an SDI input cable connected to it. The input signal has video and audio embeded.
The video is accesible through the "Vid" Pin and the audio is accesible through the "Aud 1-2" pin.
Well running DirectShow filter graphs:
"No Direct Show Audio Devices":
I cannot get FFMPEG to correctly map the audio part.
This is what I tried without success to record the audio:
ffmpeg -y -rtbufsize 2048M -f dshow -i audio="AJA S-Capture KonaLHi- 0" -acodec pcm_s24le -ar 48000 output.wav ffmpeg -y -rtbufsize 2048M -f dshow -audio_pin_name "Aud 1-2" -i audio="AJA S-Capture KonaLHi- 0" -acodec pcm_s24le -ar 48000 output.wav
this is the return error I get return error:
The filter is NOT being used by any other software. I have no problems recording the video.
-
Java/OpenCV - How to do a lossless h264 video writing in openCV ?
15 août 2018, par JohnDoeAnonin the last time I had some struggle with the VideoWriter in openCV under java. I want to write a video file in a *.mp4 container with h.264 codec - but I see no option to toggle bitrate or quality in openCV VideoWriter. I did build openCV with ffmpeg as backend. I just want to write the video file in exact quality values as the original input video. I also have some code to do the job
import org.opencv.core.Mat; import org.opencv.core.Size; import org.opencv.videoio.VideoWriter; import org.opencv.videoio.Videoio; public class VideoOutput { private final int H264_CODEC = 33; private VideoWriter writer; private String filename; public VideoOutput (String filename) { writer = null; this.filename = filename; } public void initialize(double framesPerSecond, int height, int width) throws Exception { this.writer = new VideoWriter(); this.writer.open(filename, H264_CODEC, framesPerSecond, new Size(width, height)); if(!writer.isOpened()) { Logging.LOGGER.severe("Could not create video output file " + filename + "\n"); throw new Exception("Could not create video output file " + filename + "\n"); } } public void setFrame(VideoFrame videoFrame) throws Exception { if (writer.isOpened()) { Mat frame = ImageUtil.imageToMat(videoFrame.getFrame()); writer.write(frame); frame.release(); } }
I hoped the VideoWriter gives some options to do the job but it seems not the way.
So is there an option or flag that I am missing for lossless h264 video writing under openCV and java OR maybe there is another way to do this? Please help me - if you have done this already I really would appreciate some example code to get things done.
UPDATE
I do have now a solution that fits for my application, so here it is:
String fps = Double.toString(this.config.getInputConfig().getFramesPerSecond()); Runtime.getRuntime().exec( new String[] { "C:\\ffmpeg-3.4.2-win64-static\\bin\\ffmpeg.exe", "-framerate", fps, "-i", imageOutputPath + File.separator + "%01d.jpg", "-c:v", "libx265", "-crf", "1", imageOutputPath + File.separator + "ffmpeg.mp4" } );
Credits to @Gyan who gave me the correct ffmpeg call in this post:
Win/ffmpeg - How to generate a video from images under ffmpeg?
Greets