11#if QT_VERSION >= QT_VERSION_CHECK(6,5,0)
12#include <QtEnvironmentVariables>
15#include "libmythbase/mythconfig.h"
28#include "libavutil/imgutils.h"
38#define LOC QString("VideoOutputD3D: ")
45 if (Options.
decoders->contains(
"ffmpeg"))
50 if (Options.
decoders->contains(
"dxva2"))
70 QMutexLocker locker(&
m_lock);
86 QMutexLocker locker(&
m_lock);
104 QSize video_dim_disp,
108 int [[maybe_unused]] reference_frames,
111 QMutexLocker locker(&
m_lock);
115 LOG(VB_PLAYBACK, LOG_INFO,
LOC +
116 QString(
"InputChanged from %1: %2x%3 aspect %4 to %5: %6x%7 aspect %9")
119 .arg(
toString(av_codec_id)).arg(video_dim_disp.width())
120 .arg(video_dim_disp.height()).arg(video_aspect));
124 bool res_changed = video_dim_disp != cursize;
127 if (!res_changed && !cid_changed && !force_change)
140 if (
Init(video_dim_buf, video_dim_disp,
141 video_aspect, disp, av_codec_id))
146 LOG(VB_GENERAL, LOG_ERR,
LOC +
"Failed to re-initialise video output.");
154 QMutexLocker locker(&
m_lock);
166 LOG(VB_PLAYBACK, LOG_INFO,
LOC +
167 "Direct3D device successfully initialized.");
173 QSize video_dim_disp,
181 QMutexLocker locker(&
m_lock);
185 video_aspect, win_rect, codec_id);
187 LOG(VB_PLAYBACK, LOG_INFO,
LOC + QString(
"Init with codec: %1")
222 LOG(VB_PLAYBACK, LOG_INFO,
LOC + QString(
"Created %1 empty DXVA2 buffers.")
238 QMutexLocker locker(&
m_lock);
241 for (
int i = 0; i < NUM_DXVA2_BUFS; i++)
243 ok &= vbuffers.CreateBuffer(video_dim.width(),
244 video_dim.height(), i,
248 LOG(VB_PLAYBACK, LOG_INFO,
LOC +
"Initialised DXVA2 buffers.");
262 LOG(VB_GENERAL, LOG_ERR,
LOC +
263 "RenderFrame() called while IsErrored is true.");
313 LOG(VB_GENERAL, LOG_ERR,
LOC +
314 "Show() called while IsErrored is true.");
328 QMutexLocker locker(&
m_lock);
346 LOG(VB_PLAYBACK, LOG_WARNING,
LOC +
"Failed to update pause frame");
356 bool hardware_conv =
false;
358 uint8_t *buf = img->
GetBuffer(hardware_conv, pitch);
359 if (buf && hardware_conv)
361 copybuffer(buf, frame, pitch);
363 else if (buf && !hardware_conv)
366 av_image_fill_arrays(image_out.data, image_out.linesize,
369 image_out.linesize[0] = pitch;
380 QMutexLocker locker(&
m_lock);
383 LOG(VB_GENERAL, LOG_ERR,
LOC +
384 "ProcessFrame() called while IsErrored is true.");
392 LOG(VB_GENERAL, LOG_ERR,
LOC +
"Wrong frame format");
397 bool pauseframe =
false;
443 !qEnvironmentVariableIsSet(
"NO_DXVA2")))
451 AVCodecContext **Context,
const AVCodec ** Codec,
452 const QString &decoder,
uint stream_type)
457 if ((decoder ==
"dxva2") && !qEnvironmentVariableIsSet(
"NO_DXVA2") && !use_cpu)
466 QMutexLocker locker(&
m_lock);
471 video_dim.width(), video_dim.height());
472 return (m_decoder && m_decoder->Init(
m_render));
481 QMutexLocker locker(&
m_lock);
uint8_t * GetBuffer(bool &hardware_conv, uint &pitch)
bool UpdateVertices(const QRect &dvr, const QRect &vr, int alpha=255, bool video=false)
int Copy(AVFrame *To, const MythVideoFrame *From, unsigned char *Buffer, AVPixelFormat Fmt=AV_PIX_FMT_YUV420P)
Initialise AVFrame and copy contents of VideoFrame frame into it, performing any required conversion.
virtual void FreeResources(void)
void CopyFrame(void *surface, D3D9Image *img)
bool Create(QSize size, HWND window)
QRect GetDisplayVideoRect(void) const
bool IsEmbedding(void) const
QSize GetVideoDim(void) const
void MoveResize(void)
performs all the calculations for video framing and any resizing.
QRect GetVideoRect(void) const
QRect GetDisplayVisibleRect(void) const
float GetVideoAspect(void) const
void VideoAspectRatioChanged(float Aspect)
Calls SetVideoAspectRatio(float aspect), then calls MoveResize() to apply changes.
std::chrono::milliseconds m_displayTimecode
Common code shared between GPU accelerated sub-classes (e.g. OpenGL)
MythCodecID m_videoCodecID
VideoErrorState m_errorState
virtual bool Init(QSize VideoDim, QSize VideoDispDim, float VideoAspect, QRect WindowRect, MythCodecID CodecID)
MythVideoProfilePtr m_videoProfile
VideoBuffers m_videoBuffers
virtual int DecrRef(void)
Decrements reference count and deletes on 0.
static uint GetNumBuffers(int PixelFormat, int MaxReferenceFrames=16, bool Decoder=false)
bool CreateBuffers(VideoFrameType Type, const VideoFrameTypes *RenderFormats, QSize Size, uint NeedFree, uint NeedprebufferNormal, uint NeedPrebufferSmall, int MaxReferenceFrames=16)
void Reset(void)
Resets the class so that Init may be called again.
void DiscardFrames(bool NextFrameIsKeyFrame)
Mark all used frames as ready to be reused, this is for seek.
void Init(uint NumDecode, uint NeedFree, uint NeedprebufferNormal, uint NeedPrebufferSmall)
Creates buffers and sets various buffer management parameters.
MythVideoFrame * Head(BufferType Type)
void UpdateFrame(MythVideoFrame *frame, D3D9Image *img)
bool Init(QSize video_dim_buf, QSize video_dim_disp, float video_aspect, QRect win_rect, MythCodecID codec_id) override
static void GetRenderOptions(RenderOptions &Options)
MythRenderD3D9 * m_render
MythVideoFrame m_pauseFrame
static MythCodecID GetSupportedCodec(AVCodecContext **Context, const AVCodec **Codec, const QString &decoder, uint stream_type)
void PrepareFrame(MythVideoFrame *frame, FrameScanType scan) override
static QStringList GetAllowedRenderers(MythCodecID myth_codec_id, const QSize &video_dim)
void DestroyContext(void)
void UpdatePauseFrame(std::chrono::milliseconds &disp_timecode, FrameScanType Scan=kScan_Progressive) override
void RenderEnd() override
VideoOutputD3D(MythMainWindow *MainWindow, MythRenderD3D9 *Render, MythD3D9Painter *Painter, MythDisplay *Display, const MythVideoProfilePtr &VideoProfile, QString &Profile)
bool InputChanged(QSize video_dim_buf, QSize video_dim_disp, float video_aspect, MythCodecID av_codec_id, bool &aspect_only, int reference_frames, bool force_change) override
Tells video output to discard decoded frames and wait for new ones.
void RenderFrame(MythVideoFrame *buffer, FrameScanType) override
static bool codec_is_std(MythCodecID id)
static bool codec_is_dxva2_hw(MythCodecID id)
static bool codec_is_dxva2(MythCodecID id)
#define LOG(_MASK_, _LEVEL_, _QSTRING_)
MythPainter * GetMythPainter(void)
std::shared_ptr< MythVideoProfile > MythVideoProfilePtr
QString toString(const QDateTime &raw_dt, uint format)
Returns formatted string representing the time.
def scan(profile, smoonURL, gate)
QMap< QString, QStringList > * safe_renderers
QMap< QString, uint > * priorities
const int kPrebufferFramesSmall
const int kPrebufferFramesNormal
const int kNeedFreeFrames