[Libav-user] AVFrame to PNG

Gustav González xtingray at gmail.com
Thu Apr 13 16:18:28 EEST 2023

On Wed, Apr 12, 2023 at 10:19 PM Strahinja Radman <dr.strashni at gmail.com>

> Hi Gustav,
> Thats because you are only saving luminance component. There are also two
> more components for color, in following arrays frame->data[1] and
> frame->data[2].

Thank you for the comment. Initially, I tried to fix the problem by
modifying the PNG creation procedure... trying to include the other color
components in the PNG data, with no luck.
After that, I tried a different approach: What if the AVFrame format is not
the one required by the PNG format? What if I need to make some kind of
data translation?
Understanding that the MP4 video container holds frames with the YUV420P
format, and PNG files contain image data with an RGB structure.

So, I decided to implement this piece of code before creating the PNG files:

            // To create the PNG files, the AVFrame data must be translated
from YUV420P format into RGB24
            struct SwsContext *sws_ctx = sws_getContext(
                pFrame->width, pFrame->height, pFrame->format,
                pFrame->width, pFrame->height, AV_PIX_FMT_RGB24,
                SWS_BILINEAR, NULL, NULL, NULL);

            // Allocate a new AVFrame for the output RGB24 image
            AVFrame* rgb_frame = av_frame_alloc();

            // Set the properties of the output AVFrame
            rgb_frame->format = AV_PIX_FMT_RGB24;
            rgb_frame->width = pFrame->width;
            rgb_frame->height = pFrame->height;

            int ret = av_frame_get_buffer(rgb_frame, 0);
            if (ret < 0) {
                logging("Error while preparing RGB frame: %s",
                return ret;

            logging("Transforming frame format from YUV420P into RGB24...");
            ret = sws_scale(sws_ctx, pFrame->data, pFrame->linesize, 0,
pFrame->height, rgb_frame->data, rgb_frame->linesize);
            if (ret < 0) {
                logging("Error while translating the frame format from
YUV420P into RGB24: %s", av_err2str(ret));
                return ret;

As result, the rgb_frame contains the accurate data input required to
create the PNG files in a successful way.
The final solution is available right here:

PS: The funny thing about this solution is that it was suggested by ChatGPT.

  Gustav Gonzalez
  xtingray at gmail.com
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://ffmpeg.org/pipermail/libav-user/attachments/20230413/1a878dd5/attachment.htm>

More information about the Libav-user mailing list