MayaFlux 0.4.0
Digital-First Multimedia Processing Framework
Loading...
Searching...
No Matches

◆ encode_frame()

bool MayaFlux::IO::VideoEncodeContext::encode_frame ( const uint8_t *  src_data,
size_t  src_size,
uint32_t  src_width,
uint32_t  src_height,
FFmpegMuxContext mux 
)

Encode one raw pixel frame into the mux context.

Converts src_data from the source pixel format to the encoder's required format via SwsContext, stamps the monotonic PTS, and submits the frame to the encoder. Drains any available packets to the mux immediately.

src_data must be a packed, row-major image of exactly width * height * bytes_per_pixel(src_pixel_format) bytes as delivered by the swapchain readback. No stride padding is expected; the source linesize is computed as width * bytes_per_pixel.

Non-blocking with respect to the observer thread: this runs exclusively on the VideoFileWriter worker thread.

Parameters
src_dataPointer to the first byte of the packed source image.
src_sizeByte count of src_data; must equal width * height * bpp.
muxMux context to receive encoded packets.
Returns
True on success.

Definition at line 255 of file VideoEncodeContext.cpp.

260{
261 if (!is_valid())
262 return false;
263
264 if (src_width == 0 || src_height == 0) {
265 m_last_error = "encode_frame: zero source dimensions";
266 return false;
267 }
268
269 const size_t expected = static_cast<size_t>(src_width)
270 * static_cast<size_t>(src_height)
271 * static_cast<size_t>(m_src_src_bpp);
272
273 if (src_size < expected) {
274 m_last_error = "encode_frame: src_size too small for declared dimensions";
275 return false;
276 }
277
278 if (av_frame_make_writable(m_scratch_frame) < 0) {
279 m_last_error = "av_frame_make_writable failed";
280 return false;
281 }
282
283 if (static_cast<int>(src_width) != m_cached_src_width
284 || static_cast<int>(src_height) != m_cached_src_height) {
285
286 sws_freeContext(sws_context);
287 sws_context = sws_getContext(
288 static_cast<int>(src_width),
289 static_cast<int>(src_height),
291 codec_context->width,
292 codec_context->height,
293 codec_context->pix_fmt,
294 SWS_BILINEAR,
295 nullptr, nullptr, nullptr);
296
297 if (!sws_context) {
298 m_last_error = "sws_getContext failed on dimension change";
299 return false;
300 }
301
302 m_cached_src_width = static_cast<int>(src_width);
303 m_cached_src_height = static_cast<int>(src_height);
304 }
305
306 const int src_stride = static_cast<int>(src_width) * m_src_src_bpp;
307 sws_scale(sws_context,
308 &src_data, &src_stride,
309 0, static_cast<int>(src_height),
310 m_scratch_frame->data, m_scratch_frame->linesize);
311
312 m_scratch_frame->pts = m_pts++;
313
314 if (avcodec_send_frame(codec_context, m_scratch_frame) < 0) {
315 m_last_error = "avcodec_send_frame failed";
316 return false;
317 }
318
319 return drain_packets(mux);
320}
AVFrame * m_scratch_frame
Owned scratch buffer for encoder input.
bool is_valid() const
True if codec, scaler, and scratch frame are all ready.
bool drain_packets(FFmpegMuxContext &mux)
SwsContext * sws_context
Owned; freed in destructor.
AVCodecContext * codec_context
Owned; freed in destructor.

References codec_context, drain_packets(), is_valid(), m_cached_src_height, m_cached_src_width, m_last_error, m_pts, m_scratch_frame, m_src_pixel_fmt, m_src_src_bpp, and sws_context.

Referenced by MayaFlux::IO::VideoFileWriter::worker_loop().

+ Here is the call graph for this function:
+ Here is the caller graph for this function: