1// Copyright (C) 2022 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3#ifndef QFFMPEGVIDEOFRAMEENCODER_P_H
4#define QFFMPEGVIDEOFRAMEENCODER_P_H
5
6//
7// W A R N I N G
8// -------------
9//
10// This file is not part of the Qt API. It exists purely as an
11// implementation detail. This header file may change from version to
12// version without notice, or even be removed.
13//
14// We mean it.
15//
16
17#include <QtFFmpegMediaPluginImpl/private/qffmpeghwaccel_p.h>
18#include <QtMultimedia/private/qplatformmediarecorder_p.h>
19#include <QtMultimedia/private/qmultimediautils_p.h>
20
21
22QT_BEGIN_NAMESPACE
23
24class QMediaEncoderSettings;
25
26namespace QFFmpeg {
27
28class VideoFrameEncoder;
29using VideoFrameEncoderUPtr = std::unique_ptr<VideoFrameEncoder>;
30
31class VideoFrameEncoder
32{
33public:
34 struct SourceParams
35 {
36 QSize size;
37 AVPixelFormat format = AV_PIX_FMT_NONE;
38 AVPixelFormat swFormat = AV_PIX_FMT_NONE;
39 VideoTransformation transform;
40 qreal frameRate = 0.;
41 AVColorTransferCharacteristic colorTransfer = AVCOL_TRC_UNSPECIFIED;
42 AVColorSpace colorSpace = AVCOL_SPC_UNSPECIFIED;
43 AVColorRange colorRange = AVCOL_RANGE_UNSPECIFIED;
44 };
45 static VideoFrameEncoderUPtr create(const QMediaEncoderSettings &encoderSettings,
46 const SourceParams &sourceParams,
47 AVFormatContext *formatContext);
48
49 ~VideoFrameEncoder();
50
51 AVPixelFormat sourceFormat() const { return m_sourceFormat; }
52 AVPixelFormat targetFormat() const { return m_targetFormat; }
53
54 qreal codecFrameRate() const;
55
56 qint64 getPts(qint64 ms) const;
57
58 const AVRational &getTimeBase() const;
59
60 int sendFrame(AVFrameUPtr inputFrame);
61 AVPacketUPtr retrievePacket();
62
63private:
64 VideoFrameEncoder(AVStream *stream, const Codec &codec, HWAccelUPtr hwAccel,
65 const SourceParams &sourceParams,
66 const QMediaEncoderSettings &encoderSettings);
67
68 static AVStream *createStream(const SourceParams &sourceParams, AVFormatContext *formatContext);
69
70 bool updateSourceFormatAndSize(const AVFrame *frame);
71
72 void updateConversions();
73
74 struct CreationResult
75 {
76 VideoFrameEncoderUPtr encoder;
77 AVPixelFormat targetFormat = AV_PIX_FMT_NONE;
78 };
79
80 static CreationResult create(AVStream *stream, const Codec &codec, HWAccelUPtr hwAccel,
81 const SourceParams &sourceParams,
82 const QMediaEncoderSettings &encoderSettings,
83 const AVPixelFormatSet &prohibitedTargetFormats = {});
84
85 void initTargetSize();
86
87 void initCodecFrameRate();
88
89 bool initTargetFormats(const AVPixelFormatSet &prohibitedTargetFormats);
90
91 void initStream();
92
93 bool initCodecContext();
94
95 bool open();
96
97 qint64 estimateDuration(const AVPacket &packet, bool isFirstPacket);
98
99private:
100 QMediaEncoderSettings m_settings;
101 AVStream *m_stream = nullptr;
102 Codec m_codec;
103 HWAccelUPtr m_accel;
104
105 QSize m_sourceSize;
106 QSize m_targetSize;
107
108 qint64 m_lastPacketTime = AV_NOPTS_VALUE;
109 AVCodecContextUPtr m_codecContext;
110 SwsContextUPtr m_scaleContext;
111 AVPixelFormat m_sourceFormat = AV_PIX_FMT_NONE;
112 AVPixelFormat m_sourceSWFormat = AV_PIX_FMT_NONE;
113 AVPixelFormat m_targetFormat = AV_PIX_FMT_NONE;
114 AVPixelFormat m_targetSWFormat = AV_PIX_FMT_NONE;
115 bool m_downloadFromHW = false;
116 bool m_uploadToHW = false;
117
118 AVRational m_codecFrameRate = { .num: 0, .den: 1 };
119
120 int64_t m_prevPacketDts = AV_NOPTS_VALUE;
121 int64_t m_packetDtsOffset = 0;
122};
123} // namespace QFFmpeg
124
125QT_END_NAMESPACE
126
127#endif
128

source code of qtmultimedia/src/plugins/multimedia/ffmpeg/recordingengine/qffmpegvideoframeencoder_p.h