From 05a5a9e9a0e659e762f3d463522362a86cd1c57f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=B5=AE=E7=94=9F=E8=8B=A5=E6=A2=A6?= <1070753498@qq.com> Date: Mon, 30 Oct 2023 18:41:02 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BC=98=E5=8C=96truehd=E9=9F=B3=E9=A2=91?= =?UTF-8?q?=E6=92=AD=E6=94=BE=EF=BC=9B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ffmpeg/avcontextinfo.cpp | 48 +++++++++++++++-------------- ffmpeg/avcontextinfo.h | 4 +-- ffmpeg/averrormanager.hpp | 2 +- ffmpeg/codeccontext.h | 6 ++-- ffmpeg/decoder.h | 20 ++++++++++-- ffmpeg/formatcontext.h | 12 ++++---- ffmpeg/gpu/hardwareencode.hpp | 7 ++--- ffmpeg/player.cpp | 16 +++++----- ffmpeg/player.h | 12 ++++---- ffmpeg/subtitle.cpp | 6 +++- ffmpeg/subtitle.h | 2 +- ffmpeg/videorender/openglrender.cc | 2 +- ffmpeg/videorender/openglrender.hpp | 2 +- ffmpeg/videorender/videorender.hpp | 2 +- utils/boundedblockingqueue.hpp | 4 +-- utils/utils.h | 4 +-- 16 files changed, 84 insertions(+), 65 deletions(-) diff --git a/ffmpeg/avcontextinfo.cpp b/ffmpeg/avcontextinfo.cpp index 33bd5bd..e22236a 100644 --- a/ffmpeg/avcontextinfo.cpp +++ b/ffmpeg/avcontextinfo.cpp @@ -80,9 +80,9 @@ AVContextInfo::AVContextInfo(QObject *parent) , d_ptr(new AVContextInfoPrivate(this)) {} -AVContextInfo::~AVContextInfo() {} +AVContextInfo::~AVContextInfo() = default; -CodecContext *AVContextInfo::codecCtx() +auto AVContextInfo::codecCtx() -> CodecContext * { return d_ptr->codecCtx.data(); } @@ -97,12 +97,12 @@ void AVContextInfo::setIndex(int index) d_ptr->streamIndex = index; } -int AVContextInfo::index() +auto AVContextInfo::index() -> int { return d_ptr->streamIndex; } -bool AVContextInfo::isIndexVaild() +auto AVContextInfo::isIndexVaild() -> bool { return d_ptr->streamIndex != Error_Index; } @@ -114,12 +114,12 @@ void AVContextInfo::setStream(AVStream *stream) // d_ptr->printMetaData(); } -AVStream *AVContextInfo::stream() +auto AVContextInfo::stream() -> AVStream * { return d_ptr->stream; } -bool AVContextInfo::initDecoder(const AVRational &frameRate) +auto AVContextInfo::initDecoder(const AVRational &frameRate) -> bool { Q_ASSERT(d_ptr->stream != nullptr); const char *typeStr = av_get_media_type_string(d_ptr->stream->codecpar->codec_type); @@ -144,7 +144,7 @@ bool AVContextInfo::initDecoder(const AVRational &frameRate) return true; } -bool AVContextInfo::initEncoder(AVCodecID codecId) +auto AVContextInfo::initEncoder(AVCodecID codecId) -> bool { auto encodec = avcodec_find_encoder(codecId); if (!encodec) { @@ -155,7 +155,7 @@ bool AVContextInfo::initEncoder(AVCodecID codecId) return true; } -bool AVContextInfo::initEncoder(const QString &name) +auto AVContextInfo::initEncoder(const QString &name) -> bool { auto encodec = avcodec_find_encoder_by_name(name.toLocal8Bit().constData()); if (!encodec) { @@ -166,7 +166,7 @@ bool AVContextInfo::initEncoder(const QString &name) return true; } -bool AVContextInfo::openCodec(GpuType type) +auto AVContextInfo::openCodec(GpuType type) -> bool { d_ptr->gpuType = type; if (mediaType() == AVMEDIA_TYPE_VIDEO) { @@ -192,13 +192,14 @@ bool AVContextInfo::openCodec(GpuType type) return true; } -bool AVContextInfo::decodeSubtitle2(const QSharedPointer &subtitlePtr, - const QSharedPointer &packetPtr) +auto AVContextInfo::decodeSubtitle2(const QSharedPointer &subtitlePtr, + const QSharedPointer &packetPtr) -> bool { return d_ptr->codecCtx->decodeSubtitle2(subtitlePtr.data(), packetPtr.data()); } -std::vector> AVContextInfo::decodeFrame(const QSharedPointer &packetPtr) +auto AVContextInfo::decodeFrame(const QSharedPointer &packetPtr) + -> std::vector> { std::vector framePtrs; if (!d_ptr->codecCtx->sendPacket(packetPtr.data())) { @@ -219,7 +220,8 @@ std::vector> AVContextInfo::decodeFrame(const QSharedPoint return framePtrs; } -std::vector> AVContextInfo::encodeFrame(const QSharedPointer &framePtr) +auto AVContextInfo::encodeFrame(const QSharedPointer &framePtr) + -> std::vector> { std::vector packetPtrs{}; auto frame_tmp_ptr = framePtr; @@ -242,52 +244,52 @@ std::vector> AVContextInfo::encodeFrame(const QSharedPoin return packetPtrs; } -double AVContextInfo::calTimebase() const +auto AVContextInfo::calTimebase() const -> double { return av_q2d(d_ptr->stream->time_base); } -AVRational AVContextInfo::timebase() const +auto AVContextInfo::timebase() const -> AVRational { return d_ptr->stream->time_base; } -double AVContextInfo::fps() const +auto AVContextInfo::fps() const -> double { return av_q2d(d_ptr->stream->avg_frame_rate); } -qint64 AVContextInfo::fames() const +auto AVContextInfo::fames() const -> qint64 { return d_ptr->stream->nb_frames; } -QSize AVContextInfo::resolutionRatio() const +auto AVContextInfo::resolutionRatio() const -> QSize { return {d_ptr->stream->codecpar->width, d_ptr->stream->codecpar->height}; } -AVMediaType AVContextInfo::mediaType() const +auto AVContextInfo::mediaType() const -> AVMediaType { return d_ptr->stream->codecpar->codec_type; } -QString AVContextInfo::mediaTypeString() const +auto AVContextInfo::mediaTypeString() const -> QString { return av_get_media_type_string(mediaType()); } -bool AVContextInfo::isDecoder() const +auto AVContextInfo::isDecoder() const -> bool { return d_ptr->codecCtx->isDecoder(); } -AVContextInfo::GpuType AVContextInfo::gpuType() const +auto AVContextInfo::gpuType() const -> AVContextInfo::GpuType { return d_ptr->gpuType; } -AVPixelFormat AVContextInfo::pixfmt() const +auto AVContextInfo::pixfmt() const -> AVPixelFormat { if (d_ptr->gpuType == GpuEncode && mediaType() == AVMEDIA_TYPE_VIDEO && d_ptr->hardWareEncodePtr->isVaild()) { diff --git a/ffmpeg/avcontextinfo.h b/ffmpeg/avcontextinfo.h index ad17e98..262d313 100644 --- a/ffmpeg/avcontextinfo.h +++ b/ffmpeg/avcontextinfo.h @@ -43,8 +43,8 @@ class FFMPEG_EXPORT AVContextInfo : public QObject auto openCodec(GpuType type = NotUseGpu) -> bool; // sendPacket and receiveFrame - std::vector> decodeFrame(const QSharedPointer &packetPtr); - std::vector> encodeFrame(const QSharedPointer &framePtr); + auto decodeFrame(const QSharedPointer &packetPtr) -> std::vector>; + auto encodeFrame(const QSharedPointer &framePtr) -> std::vector>; auto decodeSubtitle2(const QSharedPointer &subtitlePtr, const QSharedPointer &packetPtr) -> bool; diff --git a/ffmpeg/averrormanager.hpp b/ffmpeg/averrormanager.hpp index 5bf1378..78ac714 100644 --- a/ffmpeg/averrormanager.hpp +++ b/ffmpeg/averrormanager.hpp @@ -27,7 +27,7 @@ class FFMPEG_EXPORT AVErrorManager : public QObject void setErrorCode(int errorCode); [[nodiscard]] auto lastErrorString() const -> QString; - [[nodiscard]] QVector errorCodes() const; + [[nodiscard]] auto errorCodes() const -> QVector; signals: void error(const Ffmpeg::AVError &avError); diff --git a/ffmpeg/codeccontext.h b/ffmpeg/codeccontext.h index 7f8c91c..a8e16c4 100644 --- a/ffmpeg/codeccontext.h +++ b/ffmpeg/codeccontext.h @@ -45,10 +45,10 @@ class CodecContext : public QObject [[nodiscard]] auto size() const -> QSize; void setQuailty(int quailty); - [[nodiscard]] QPair quantizer() const; + [[nodiscard]] auto quantizer() const -> QPair; - [[nodiscard]] QVector supportPixFmts() const; - [[nodiscard]] QVector supportSampleFmts() const; + [[nodiscard]] auto supportPixFmts() const -> QVector; + [[nodiscard]] auto supportSampleFmts() const -> QVector; // Set before open, Soft solution is effective void setThreadCount(int threadCount); diff --git a/ffmpeg/decoder.h b/ffmpeg/decoder.h index e1f5a3e..6feb587 100644 --- a/ffmpeg/decoder.h +++ b/ffmpeg/decoder.h @@ -11,10 +11,16 @@ #include "avcontextinfo.h" #include "formatcontext.h" +extern "C" { +#include +} + namespace Ffmpeg { -static const auto s_waitQueueEmptyMilliseconds = 50; -static const auto s_frameQueueSize = 25; // for truehd codec, maybe need more, maybe 500 +static constexpr auto s_waitQueueEmptyMilliseconds = 50; +static constexpr auto s_videoQueueSize = 10; +// For truehd audio, the queue size should be large enough +static constexpr auto s_audioQueueSize = 200; template class Decoder : public QThread @@ -22,7 +28,7 @@ class Decoder : public QThread public: explicit Decoder(QObject *parent = nullptr) : QThread(parent) - , m_queue(s_frameQueueSize) + , m_queue(s_videoQueueSize) {} ~Decoder() override = default; @@ -32,6 +38,14 @@ class Decoder : public QThread m_formatContext = formatContext; m_contextInfo = contextInfo; m_runing = true; + if (!m_contextInfo->isIndexVaild()) { + return; + } + if (m_contextInfo->stream()->codecpar->codec_type == AVMEDIA_TYPE_AUDIO) { + m_queue.setMaxSize(s_audioQueueSize); + } else { + m_queue.setMaxSize(s_videoQueueSize); + } start(); } diff --git a/ffmpeg/formatcontext.h b/ffmpeg/formatcontext.h index e5225e1..5e5e506 100644 --- a/ffmpeg/formatcontext.h +++ b/ffmpeg/formatcontext.h @@ -42,10 +42,10 @@ class FFMPEG_EXPORT FormatContext : public QObject auto stream(int index) -> AVStream *; //音频流 auto createStream() -> AVStream *; - [[nodiscard]] QVector audioTracks() const; - [[nodiscard]] QVector vidioTracks() const; - [[nodiscard]] QVector subtitleTracks() const; - [[nodiscard]] QVector attachmentTracks() const; + [[nodiscard]] auto audioTracks() const -> QVector; + [[nodiscard]] auto vidioTracks() const -> QVector; + [[nodiscard]] auto subtitleTracks() const -> QVector; + [[nodiscard]] auto attachmentTracks() const -> QVector; [[nodiscard]] auto findBestStreamIndex(AVMediaType type) const -> int; // 丢弃除indexs中包含的音视频流,优化av_read_frame性能 @@ -53,8 +53,8 @@ class FFMPEG_EXPORT FormatContext : public QObject auto seekFirstFrame() -> bool; auto seek(qint64 timestamp) -> bool; - auto seek(qint64 timestamp, bool forward) -> bool; // microsecond - auto seekFrame(int index, qint64 timestamp) -> bool; // microsecond + auto seek(qint64 timestamp, bool forward) -> bool; // microsecond + auto seekFrame(int index, qint64 timestamp) -> bool; // microsecond auto readFrame(Packet *packet) -> bool; diff --git a/ffmpeg/gpu/hardwareencode.hpp b/ffmpeg/gpu/hardwareencode.hpp index 55d7ab6..4778d57 100644 --- a/ffmpeg/gpu/hardwareencode.hpp +++ b/ffmpeg/gpu/hardwareencode.hpp @@ -21,11 +21,10 @@ class HardWareEncode : public QObject auto initEncoder(const AVCodec *encoder) -> bool; auto initHardWareDevice(CodecContext *codecContext) -> bool; - QSharedPointer transToGpu(CodecContext *codecContext, - QSharedPointer inPtr, - bool &ok); + auto transToGpu(CodecContext *codecContext, QSharedPointer inPtr, bool &ok) + -> QSharedPointer; - [[nodiscard]] AVPixelFormat swFormat() const; + [[nodiscard]] auto swFormat() const -> AVPixelFormat; auto isVaild() -> bool; diff --git a/ffmpeg/player.cpp b/ffmpeg/player.cpp index 3e464b3..eba6eaf 100644 --- a/ffmpeg/player.cpp +++ b/ffmpeg/player.cpp @@ -234,7 +234,7 @@ class Player::PlayerPrivate addPropertyChangeEventEvent(new MediaStateEvent(mediaState)); } - [[nodiscard]] QSize resolutionRatio() const + [[nodiscard]] auto resolutionRatio() const -> QSize { return videoInfo->isIndexVaild() ? videoInfo->resolutionRatio() : QSize(); } @@ -601,7 +601,7 @@ auto Player::fames() const -> qint64 return d_ptr->videoInfo->isIndexVaild() ? d_ptr->videoInfo->fames() : 0; } -QSize Player::resolutionRatio() const +auto Player::resolutionRatio() const -> QSize { return d_ptr->resolutionRatio(); } @@ -633,7 +633,7 @@ void Player::setVideoRenders(QVector videoRenders) d_ptr->subtitleDecoder->setVideoRenders(videoRenders); } -QVector Player::videoRenders() +auto Player::videoRenders() -> QVector { return d_ptr->videoRenders; } @@ -643,17 +643,17 @@ void Player::setPropertyEventQueueMaxSize(size_t size) d_ptr->maxPropertyEventQueueSize.store(size); } -size_t Player::propertEventyQueueMaxSize() const +auto Player::propertEventyQueueMaxSize() const -> size_t { return d_ptr->maxPropertyEventQueueSize.load(); } -size_t Player::propertyChangeEventSize() const +auto Player::propertyChangeEventSize() const -> size_t { return d_ptr->propertyChangeEventQueue.size(); } -PropertyChangeEventPtr Player::takePropertyChangeEvent() +auto Player::takePropertyChangeEvent() -> PropertyChangeEventPtr { return d_ptr->propertyChangeEventQueue.take(); } @@ -663,12 +663,12 @@ void Player::setEventQueueMaxSize(size_t size) d_ptr->maxEventQueueSize.store(size); } -size_t Player::eventQueueMaxSize() const +auto Player::eventQueueMaxSize() const -> size_t { return d_ptr->maxEventQueueSize.load(); } -[[nodiscard]] size_t Player::eventSize() const +[[nodiscard]] auto Player::eventSize() const -> size_t { return d_ptr->eventQueue.size(); } diff --git a/ffmpeg/player.h b/ffmpeg/player.h index 1e81a96..1ce8119 100644 --- a/ffmpeg/player.h +++ b/ffmpeg/player.h @@ -36,16 +36,16 @@ class FFMPEG_EXPORT Player : public QThread [[nodiscard]] auto subtitleIndex() const -> int; void setVideoRenders(QVector videoRenders); - QVector videoRenders(); + auto videoRenders() -> QVector; void setPropertyEventQueueMaxSize(size_t size); - [[nodiscard]] size_t propertEventyQueueMaxSize() const; - [[nodiscard]] size_t propertyChangeEventSize() const; - PropertyChangeEventPtr takePropertyChangeEvent(); + [[nodiscard]] auto propertEventyQueueMaxSize() const -> size_t; + [[nodiscard]] auto propertyChangeEventSize() const -> size_t; + auto takePropertyChangeEvent() -> PropertyChangeEventPtr; void setEventQueueMaxSize(size_t size); - [[nodiscard]] size_t eventQueueMaxSize() const; - [[nodiscard]] size_t eventSize() const; + [[nodiscard]] auto eventQueueMaxSize() const -> size_t; + [[nodiscard]] auto eventSize() const -> size_t; auto addEvent(const EventPtr &eventPtr) -> bool; public slots: diff --git a/ffmpeg/subtitle.cpp b/ffmpeg/subtitle.cpp index 92d753c..2f7bee1 100644 --- a/ffmpeg/subtitle.cpp +++ b/ffmpeg/subtitle.cpp @@ -27,6 +27,8 @@ class Subtitle::SubtitlePrivate image = QImage(videoResolutionRatio, QImage::Format_RGBA8888); image.fill(Qt::transparent); QPainter painter(&image); + painter.setRenderHints(painter.renderHints() | QPainter::Antialiasing + | QPainter::TextAntialiasing | QPainter::SmoothPixmapTransform); for (size_t i = 0; i < subtitle.num_rects; i++) { auto sub_rect = subtitle.rects[i]; @@ -180,7 +182,7 @@ void Subtitle::setAssDataInfoList(const AssDataInfoList &list) d_ptr->assList = list; } -AssDataInfoList Subtitle::list() const +auto Subtitle::list() const -> AssDataInfoList { return d_ptr->assList; } @@ -193,6 +195,8 @@ auto Subtitle::generateImage() const -> QImage d_ptr->image = QImage(d_ptr->videoResolutionRatio, QImage::Format_RGBA8888); d_ptr->image.fill(Qt::transparent); QPainter painter(&d_ptr->image); + painter.setRenderHints(painter.renderHints() | QPainter::Antialiasing + | QPainter::TextAntialiasing | QPainter::SmoothPixmapTransform); for (const auto &data : qAsConst(d_ptr->assList)) { auto rect = data.rect(); QImage image((uchar *) data.rgba().constData(), diff --git a/ffmpeg/subtitle.h b/ffmpeg/subtitle.h index e71e81b..37d16bb 100644 --- a/ffmpeg/subtitle.h +++ b/ffmpeg/subtitle.h @@ -35,7 +35,7 @@ class FFMPEG_EXPORT Subtitle : public QObject auto resolveAss(Ass *ass) -> bool; void setAssDataInfoList(const AssDataInfoList &list); - [[nodiscard]] AssDataInfoList list() const; + [[nodiscard]] auto list() const -> AssDataInfoList; [[nodiscard]] auto generateImage() const -> QImage; [[nodiscard]] auto image() const -> QImage; diff --git a/ffmpeg/videorender/openglrender.cc b/ffmpeg/videorender/openglrender.cc index 8aefa7d..09c0ba2 100644 --- a/ffmpeg/videorender/openglrender.cc +++ b/ffmpeg/videorender/openglrender.cc @@ -112,7 +112,7 @@ auto OpenglRender::convertSupported_pix_fmt(QSharedPointer frame) -> QSha return frameRgbPtr; } -QVector OpenglRender::supportedOutput_pix_fmt() +auto OpenglRender::supportedOutput_pix_fmt() -> QVector { return d_ptr->supportFormats; } diff --git a/ffmpeg/videorender/openglrender.hpp b/ffmpeg/videorender/openglrender.hpp index b1927ea..59676cf 100644 --- a/ffmpeg/videorender/openglrender.hpp +++ b/ffmpeg/videorender/openglrender.hpp @@ -20,7 +20,7 @@ class FFMPEG_EXPORT OpenglRender : public VideoRender, auto isSupportedOutput_pix_fmt(AVPixelFormat pix_fmt) -> bool override; auto convertSupported_pix_fmt(QSharedPointer frame) -> QSharedPointer override; - QVector supportedOutput_pix_fmt() override; + auto supportedOutput_pix_fmt() -> QVector override; void resetAllFrame() override; diff --git a/ffmpeg/videorender/videorender.hpp b/ffmpeg/videorender/videorender.hpp index ef81396..23ffdf8 100644 --- a/ffmpeg/videorender/videorender.hpp +++ b/ffmpeg/videorender/videorender.hpp @@ -24,7 +24,7 @@ class FFMPEG_EXPORT VideoRender virtual ~VideoRender(); virtual auto isSupportedOutput_pix_fmt(AVPixelFormat pix_fmt) -> bool = 0; - virtual QVector supportedOutput_pix_fmt() = 0; + virtual auto supportedOutput_pix_fmt() -> QVector = 0; virtual auto convertSupported_pix_fmt(QSharedPointer framePtr) -> QSharedPointer = 0; void setFrame(QSharedPointer framePtr); diff --git a/utils/boundedblockingqueue.hpp b/utils/boundedblockingqueue.hpp index 0d55610..b1e7de7 100644 --- a/utils/boundedblockingqueue.hpp +++ b/utils/boundedblockingqueue.hpp @@ -99,7 +99,7 @@ class BoundedBlockingQueue return m_queue.size() >= m_maxSize; } - [[nodiscard]] size_t size() const + [[nodiscard]] auto size() const -> size_t { QMutexLocker locker(&m_mutex); return m_queue.size(); @@ -111,7 +111,7 @@ class BoundedBlockingQueue m_maxSize = maxSize; } - [[nodiscard]] size_t maxSize() const + [[nodiscard]] auto maxSize() const -> size_t { QMutexLocker locker(&m_mutex); return m_maxSize; diff --git a/utils/utils.h b/utils/utils.h index 6dd423b..7784ff2 100644 --- a/utils/utils.h +++ b/utils/utils.h @@ -23,8 +23,8 @@ UTILS_EXPORT auto fileSize(const QString &localPath) -> qint64; UTILS_EXPORT auto generateDirectorys(const QString &directory) -> bool; UTILS_EXPORT void removeDirectory(const QString &path); UTILS_EXPORT auto convertBytesToString(qint64 bytes) -> QString; -UTILS_EXPORT QJsonObject jsonFromFile(const QString &filePath); -UTILS_EXPORT QJsonObject jsonFromBytes(const QByteArray &bytes); +UTILS_EXPORT auto jsonFromFile(const QString &filePath) -> QJsonObject; +UTILS_EXPORT auto jsonFromBytes(const QByteArray &bytes) -> QJsonObject; UTILS_EXPORT auto getConfigPath() -> QString; } // namespace Utils