4#include <common/qgst_p.h>
5#include <common/qgst_debug_p.h>
6#include <common/qgstpipeline_p.h>
7#include <common/qgstreamermessage_p.h>
9#include <QtCore/qdebug.h>
10#include <QtMultimedia/qcameradevice.h>
26 { QVideoFrameFormat::Format_YUV420P, GST_VIDEO_FORMAT_I420 },
27 { QVideoFrameFormat::Format_YUV422P, GST_VIDEO_FORMAT_Y42B },
28 { QVideoFrameFormat::Format_YV12, GST_VIDEO_FORMAT_YV12 },
29 { QVideoFrameFormat::Format_UYVY, GST_VIDEO_FORMAT_UYVY },
30 { QVideoFrameFormat::Format_YUYV, GST_VIDEO_FORMAT_YUY2 },
31 { QVideoFrameFormat::Format_NV12, GST_VIDEO_FORMAT_NV12 },
32 { QVideoFrameFormat::Format_NV21, GST_VIDEO_FORMAT_NV21 },
33 { QVideoFrameFormat::Format_AYUV, GST_VIDEO_FORMAT_AYUV },
34 { QVideoFrameFormat::Format_Y8, GST_VIDEO_FORMAT_GRAY8 },
35 { QVideoFrameFormat::Format_XRGB8888, GST_VIDEO_FORMAT_xRGB },
36 { QVideoFrameFormat::Format_XBGR8888, GST_VIDEO_FORMAT_xBGR },
37 { QVideoFrameFormat::Format_RGBX8888, GST_VIDEO_FORMAT_RGBx },
38 { QVideoFrameFormat::Format_BGRX8888, GST_VIDEO_FORMAT_BGRx },
39 { QVideoFrameFormat::Format_ARGB8888, GST_VIDEO_FORMAT_ARGB },
40 { QVideoFrameFormat::Format_ABGR8888, GST_VIDEO_FORMAT_ABGR },
41 { QVideoFrameFormat::Format_RGBA8888, GST_VIDEO_FORMAT_RGBA },
42 { QVideoFrameFormat::Format_BGRA8888, GST_VIDEO_FORMAT_BGRA },
43#if Q_BYTE_ORDER == Q_LITTLE_ENDIAN
44 { QVideoFrameFormat::Format_Y16, GST_VIDEO_FORMAT_GRAY16_LE },
45 { QVideoFrameFormat::Format_P010, GST_VIDEO_FORMAT_P010_10LE },
47 { QVideoFrameFormat::Format_Y16, GST_VIDEO_FORMAT_GRAY16_BE },
48 { QVideoFrameFormat::Format_P010, GST_VIDEO_FORMAT_P010_10BE },
54 for (size_t i = 0; i < qt_videoFormatLookup.size(); ++i)
63 for (size_t i = 0; i < qt_videoFormatLookup.size(); ++i)
83 if (!G_VALUE_HOLDS_BOOLEAN(value))
85 return g_value_get_boolean(value);
90 if (!G_VALUE_HOLDS_INT(value))
92 return g_value_get_int(value);
97 if (!G_VALUE_HOLDS_INT64(value))
99 return g_value_get_int64(value);
104 return value ? g_value_get_string(value) :
nullptr;
109 if (!GST_VALUE_HOLDS_FRACTION(value))
111 return (
float)gst_value_get_fraction_numerator(value)
112 / (
float)gst_value_get_fraction_denominator(value);
117 if (!GST_VALUE_HOLDS_FRACTION_RANGE(value))
119 QGValue min = QGValue{ gst_value_get_fraction_range_min(value) };
120 QGValue max = QGValue{ gst_value_get_fraction_range_max(value) };
121 return QGRange<
float>{ *min.getFraction(), *max.getFraction() };
126 if (!GST_VALUE_HOLDS_INT_RANGE(value))
128 return QGRange<
int>{ gst_value_get_int_range_min(value), gst_value_get_int_range_max(value) };
133 if (!value || !GST_VALUE_HOLDS_STRUCTURE(value))
134 return QGstStructureView(
nullptr);
135 return QGstStructureView(gst_value_get_structure(value));
140 if (!value || !GST_VALUE_HOLDS_CAPS(value))
142 return QGstCaps(gst_caps_copy(gst_value_get_caps(value)), QGstCaps::HasRef);
147 return value && GST_VALUE_HOLDS_LIST(value);
152 return gst_value_list_get_size(value);
157 return QGValue{ gst_value_list_get_value(value, index) };
171 return QUniqueGstStructureHandle{ gst_structure_copy(structure) };
181 return gst_structure_get_name(structure);
186 return QGValue{ gst_structure_get_value(structure, fieldname) };
200 QGstTagListHandle tagList;
201 gst_structure_get(structure,
"tags", GST_TYPE_TAG_LIST, &tagList,
nullptr);
210 if (structure && gst_structure_get_int(structure,
"width", &w)
211 && gst_structure_get_int(structure,
"height", &h)) {
221 QVideoFrameFormat::PixelFormat pixelFormat = QVideoFrameFormat::Format_Invalid;
226 if (gst_structure_has_name(structure,
"video/x-raw")) {
227 const gchar *s = gst_structure_get_string(structure,
"format");
229 GstVideoFormat format = gst_video_format_from_string(s);
230 int index = indexOfVideoFormat(format);
233 pixelFormat = qt_videoFormatLookup[index].pixelFormat;
235 }
else if (gst_structure_has_name(structure,
"image/jpeg")) {
236 pixelFormat = QVideoFrameFormat::Format_Jpeg;
247 std::optional<
float> minRate;
248 std::optional<
float> maxRate;
250 auto extractFraction = [](
const GValue *v) ->
float {
251 return (
float)gst_value_get_fraction_numerator(v)
252 / (
float)gst_value_get_fraction_denominator(v);
254 auto extractFrameRate = [&](
const GValue *v) {
255 auto insert = [&](
float min,
float max) {
256 if (!maxRate || max > maxRate)
258 if (!minRate || min < minRate)
262 if (GST_VALUE_HOLDS_FRACTION(v)) {
263 float rate = extractFraction(v);
265 }
else if (GST_VALUE_HOLDS_FRACTION_RANGE(v)) {
266 const GValue *min = gst_value_get_fraction_range_min(v);
267 const GValue *max = gst_value_get_fraction_range_max(v);
268 insert(extractFraction(min), extractFraction(max));
272 const GValue *gstFrameRates = gst_structure_get_value(structure,
"framerate");
274 if (GST_VALUE_HOLDS_LIST(gstFrameRates)) {
275 guint nFrameRates = gst_value_list_get_size(gstFrameRates);
276 for (guint f = 0; f < nFrameRates; ++f) {
277 extractFrameRate(gst_value_list_get_value(gstFrameRates, f));
280 extractFrameRate(gstFrameRates);
283 const GValue *min = gst_structure_get_value(structure,
"min-framerate");
284 const GValue *max = gst_structure_get_value(structure,
"max-framerate");
286 minRate = extractFraction(min);
287 maxRate = extractFraction(max);
291 if (!minRate || !maxRate)
295 minRate.value_or(*maxRate),
296 maxRate.value_or(*minRate),
305 const GValue *width = gst_structure_get_value(structure,
"width");
306 const GValue *height = gst_structure_get_value(structure,
"height");
308 if (!width || !height)
311 for (
const GValue *v : { width, height })
312 if (!GST_VALUE_HOLDS_INT_RANGE(v))
315 int minWidth = gst_value_get_int_range_min(width);
316 int maxWidth = gst_value_get_int_range_max(width);
317 int minHeight = gst_value_get_int_range_min(height);
318 int maxHeight = gst_value_get_int_range_max(height);
320 return QGRange<QSize>{
321 QSize(minWidth, minHeight),
322 QSize(maxWidth, maxHeight),
328 GstMessage *message =
nullptr;
329 gst_structure_get(structure,
"message", GST_TYPE_MESSAGE, &message,
nullptr);
330 return QGstreamerMessage(message, QGstreamerMessage::HasRef);
337 if (gst_structure_get_fraction(structure,
"pixel-aspect-ratio", &numerator, &denominator)) {
351 if (par.numerator == par.denominator || par.numerator < 1 || par.denominator < 1)
355 resolution.width() * par.numerator / par.denominator,
362 QSize size = resolution();
363 if (!size.isValid()) {
364 qWarning() << Q_FUNC_INFO <<
"invalid resolution when querying nativeSize";
368 std::optional<Fraction> par = pixelAspectRatio();
370 size = qCalculateFrameSizeGStreamer(size, *par);
376std::optional<std::pair<QVideoFrameFormat, GstVideoInfo>>
QGstCaps::formatAndVideoInfo()
const
378 GstVideoInfo vidInfo;
380 bool success = gst_video_info_from_caps(&vidInfo, get());
384 int index = indexOfVideoFormat(vidInfo.finfo->format);
388 QVideoFrameFormat format(QSize(vidInfo.width, vidInfo.height),
389 qt_videoFormatLookup[index].pixelFormat);
391 if (vidInfo.fps_d > 0)
392 format.setStreamFrameRate(qreal(vidInfo.fps_n) / vidInfo.fps_d);
394 QVideoFrameFormat::ColorRange range = QVideoFrameFormat::ColorRange_Unknown;
395 switch (vidInfo.colorimetry.range) {
396 case GST_VIDEO_COLOR_RANGE_UNKNOWN:
398 case GST_VIDEO_COLOR_RANGE_0_255:
399 range = QVideoFrameFormat::ColorRange_Full;
401 case GST_VIDEO_COLOR_RANGE_16_235:
402 range = QVideoFrameFormat::ColorRange_Video;
405 format.setColorRange(range);
407 QVideoFrameFormat::ColorSpace colorSpace = QVideoFrameFormat::ColorSpace_Undefined;
408 switch (vidInfo.colorimetry.matrix) {
409 case GST_VIDEO_COLOR_MATRIX_UNKNOWN:
410 case GST_VIDEO_COLOR_MATRIX_RGB:
411 case GST_VIDEO_COLOR_MATRIX_FCC:
413 case GST_VIDEO_COLOR_MATRIX_BT709:
414 colorSpace = QVideoFrameFormat::ColorSpace_BT709;
416 case GST_VIDEO_COLOR_MATRIX_BT601:
417 colorSpace = QVideoFrameFormat::ColorSpace_BT601;
419 case GST_VIDEO_COLOR_MATRIX_SMPTE240M:
420 colorSpace = QVideoFrameFormat::ColorSpace_AdobeRgb;
422 case GST_VIDEO_COLOR_MATRIX_BT2020:
423 colorSpace = QVideoFrameFormat::ColorSpace_BT2020;
426 format.setColorSpace(colorSpace);
428 QVideoFrameFormat::ColorTransfer transfer = QVideoFrameFormat::ColorTransfer_Unknown;
429 switch (vidInfo.colorimetry.transfer) {
430 case GST_VIDEO_TRANSFER_UNKNOWN:
432 case GST_VIDEO_TRANSFER_GAMMA10:
433 transfer = QVideoFrameFormat::ColorTransfer_Linear;
435 case GST_VIDEO_TRANSFER_GAMMA22:
436 case GST_VIDEO_TRANSFER_SMPTE240M:
437 case GST_VIDEO_TRANSFER_SRGB:
438 case GST_VIDEO_TRANSFER_ADOBERGB:
439 transfer = QVideoFrameFormat::ColorTransfer_Gamma22;
441 case GST_VIDEO_TRANSFER_GAMMA18:
442 case GST_VIDEO_TRANSFER_GAMMA20:
444 case GST_VIDEO_TRANSFER_BT709:
445 case GST_VIDEO_TRANSFER_BT2020_12:
446 transfer = QVideoFrameFormat::ColorTransfer_BT709;
448 case GST_VIDEO_TRANSFER_GAMMA28:
449 transfer = QVideoFrameFormat::ColorTransfer_Gamma28;
451 case GST_VIDEO_TRANSFER_LOG100:
452 case GST_VIDEO_TRANSFER_LOG316:
454 case GST_VIDEO_TRANSFER_SMPTE2084:
455 transfer = QVideoFrameFormat::ColorTransfer_ST2084;
457 case GST_VIDEO_TRANSFER_ARIB_STD_B67:
458 transfer = QVideoFrameFormat::ColorTransfer_STD_B67;
460 case GST_VIDEO_TRANSFER_BT2020_10:
461 transfer = QVideoFrameFormat::ColorTransfer_BT709;
463 case GST_VIDEO_TRANSFER_BT601:
464 transfer = QVideoFrameFormat::ColorTransfer_BT601;
467 format.setColorTransfer(transfer);
476 const char *modifier)
478 if (!gst_caps_is_writable(get()))
479 *
this = QGstCaps(gst_caps_make_writable(release()), QGstCaps::RefMode::HasRef);
482 g_value_init(&list, GST_TYPE_LIST);
484 for (QVideoFrameFormat::PixelFormat format : formats) {
485 int index = indexOfVideoFormat(format);
490 g_value_init(&item, G_TYPE_STRING);
491 g_value_set_string(&item,
492 gst_video_format_to_string(qt_videoFormatLookup[index].gstFormat));
493 gst_value_list_append_value(&list, &item);
494 g_value_unset(&item);
497 auto *structure = gst_structure_new(
"video/x-raw",
"framerate", GST_TYPE_FRACTION_RANGE, 0, 1,
498 INT_MAX, 1,
"width", GST_TYPE_INT_RANGE, 1, INT_MAX,
499 "height", GST_TYPE_INT_RANGE, 1, INT_MAX,
nullptr);
500 gst_structure_set_value(structure,
"format", &list);
501 gst_caps_append_structure(get(), structure);
502 g_value_unset(&list);
505 gst_caps_set_features(get(),
size() - 1, gst_caps_features_from_string(modifier));
510 Q_ASSERT(resolution.isValid());
512 g_value_init(&width, G_TYPE_INT);
513 g_value_set_int(&width, resolution.width());
515 g_value_init(&height, G_TYPE_INT);
516 g_value_set_int(&height, resolution.height());
518 gst_caps_set_value(caps(),
"width", &width);
519 gst_caps_set_value(caps(),
"height", &height);
524 QSize size = format.resolution();
525 GstStructure *structure =
nullptr;
526 if (format.pixelFormat() == QVideoFrameFormat::Format_Jpeg) {
527 structure = gst_structure_new(
"image/jpeg",
"width", G_TYPE_INT, size.width(),
"height",
528 G_TYPE_INT, size.height(),
nullptr);
530 int index = indexOfVideoFormat(format.pixelFormat());
533 auto gstFormat = qt_videoFormatLookup[index].gstFormat;
534 structure = gst_structure_new(
"video/x-raw",
"format", G_TYPE_STRING,
535 gst_video_format_to_string(gstFormat),
"width", G_TYPE_INT,
536 size.width(),
"height", G_TYPE_INT, size.height(),
nullptr);
539 gst_caps_append_structure(caps.get(), structure);
546 gst_caps_copy(caps()),
553 auto *features = gst_caps_get_features(get(), 0);
554 if (gst_caps_features_contains(features,
"memory:GLMemory"))
556 if (gst_caps_features_contains(features,
"memory:DMABuf"))
563 return int(gst_caps_get_size(get()));
569 gst_caps_get_structure(get(), index),
580 return QGstCaps(gst_caps_new_empty(), HasRef);
587 g_object_set(get(), property, str,
nullptr);
592 g_object_set(get(), property, gboolean(b),
nullptr);
597 g_object_set(get(), property, guint(i),
nullptr);
602 g_object_set(get(), property, gint(i),
nullptr);
607 g_object_set(get(), property, gint64(i),
nullptr);
612 g_object_set(get(), property, guint64(i),
nullptr);
617 g_object_set(get(), property, gdouble(d),
nullptr);
622 g_object_set(get(), property, o.object(),
nullptr);
627 g_object_set(get(), property, c.caps(),
nullptr);
630void QGstObject::
set(
const char *property,
void *object, GDestroyNotify destroyFunction)
632 g_object_set_data_full(qGstCheckedCast<GObject>(get()), property, object, destroyFunction);
638 g_object_get(get(), property, &s,
nullptr);
644 GstStructure *s =
nullptr;
645 g_object_get(get(), property, &s,
nullptr);
652 g_object_get(get(), property, &b,
nullptr);
659 g_object_get(get(), property, &i,
nullptr);
666 g_object_get(get(), property, &i,
nullptr);
673 g_object_get(get(), property, &i,
nullptr);
680 g_object_get(get(), property, &i,
nullptr);
687 g_object_get(get(), property, &d,
nullptr);
694 g_object_get(get(), property, &d,
nullptr);
700 GstObject *o =
nullptr;
701 g_object_get(get(), property, &o,
nullptr);
702 return QGstObject(o, HasRef);
707 return g_object_get_data(qGstCheckedCast<GObject>(get()), property);
715 g_signal_connect(get(), name, callback, userData),
721 g_signal_handler_disconnect(get(), handlerId);
726 return G_OBJECT_TYPE(get());
731 return QLatin1StringView{
743 using namespace Qt::StringLiterals;
745 return get() ? QLatin1StringView{ GST_OBJECT_NAME(get()) } :
"(null)"_L1;
760 object.disconnect(handlerId);
762 handlerId = invalidHandlerId;
777 connection.disconnect();
782 connection.disconnect();
805 return QGstCaps(gst_pad_get_current_caps(pad()), QGstCaps::HasRef);
810 return QGstCaps(gst_pad_query_caps(pad(),
nullptr), QGstCaps::HasRef);
815 QGstTagListHandle tagList;
816 g_object_get(object(),
"tags", &tagList,
nullptr);
823 gst_pad_get_stream_id(pad()),
829 using namespace Qt::Literals;
830 QLatin1StringView padName = name();
832 if (padName.startsWith(
"video_"_L1))
833 return QPlatformMediaPlayer::TrackType::VideoStream;
834 if (padName.startsWith(
"audio_"_L1))
835 return QPlatformMediaPlayer::TrackType::AudioStream;
836 if (padName.startsWith(
"text_"_L1))
837 return QPlatformMediaPlayer::TrackType::SubtitleStream;
844 return gst_pad_is_linked(pad());
849 return gst_pad_link(pad(), sink.pad()) == GST_PAD_LINK_OK;
854 return gst_pad_unlink(pad(), sink.pad());
861 return GST_PAD_IS_SRC(pad()) ? unlink(peerPad) : peerPad.unlink(*
this);
868 return QGstPad(gst_pad_get_peer(pad()), HasRef);
873 return QGstElement(gst_pad_get_parent_element(pad()), HasRef);
878 return qGstCheckedCast<GstPad>(object());
883 return gst_pad_get_sticky_event(pad(), type, 0);
888 return gst_pad_send_event(pad(), event);
893 GstEvent *flushStart = gst_event_new_flush_start();
894 gboolean ret = sendEvent(flushStart);
896 qWarning(
"failed to send flush-start event");
900 GstEvent *flushStop = gst_event_new_flush_stop(resetTime);
901 ret = sendEvent(flushStop);
903 qWarning(
"failed to send flush-stop event");
908 using namespace std::chrono_literals;
910 GstState state = parent().state(1s);
912 if (state != GST_STATE_PAUSED)
938 return qGstCheckedCast<GstClock>(object());
943 return gst_clock_get_time(clock());
958 GstElement *element = gst_element_factory_make(factory, name);
962 qWarning() <<
"Failed to make element" << name <<
"from factory" << factory;
963 return QGstElement{};
976 gst_element_factory_create(factory, name),
989 return createFromDevice(device.get(), name);
995 gst_device_create_element(device, name),
996 QGstElement::NeedsRef,
1002 QUniqueGErrorHandle error;
1004 gst_parse_launch(str, &error),
1005 QGstElement::NeedsRef,
1009 qWarning() <<
"gst_parse_launch error:" << error;
1021 return QGstElementFactoryHandle{
1022 gst_element_factory_find(name),
1023 QGstElementFactoryHandle::HasRef,
1027QGstElementFactoryHandle
QGstElement::findFactory(
const QByteArray &name)
1029 return findFactory(name.constData());
1034 return QGstPad(gst_element_get_static_pad(element(), name), HasRef);
1049 return QGstPad(gst_element_request_pad_simple(element(), name), HasRef);
1054 return gst_element_release_request_pad(element(), pad.pad());
1059 using namespace std::chrono_literals;
1062 GstStateChangeReturn change =
1063 gst_element_get_state(element(), &state,
nullptr, timeout.count());
1065 if (Q_UNLIKELY(change == GST_STATE_CHANGE_ASYNC))
1066 qWarning() <<
"QGstElement::state detected an asynchronous state change. Return value not "
1074 return gst_element_set_state(element(), state);
1079 GstStateChangeReturn change = gst_element_set_state(element(), state);
1080 if (change == GST_STATE_CHANGE_ASYNC)
1081 change = gst_element_get_state(element(),
nullptr, &state, timeout.count());
1083 if (change != GST_STATE_CHANGE_SUCCESS && change != GST_STATE_CHANGE_NO_PREROLL) {
1084 qWarning() <<
"Could not change state of" << name() <<
"to" << state << change;
1087 return change == GST_STATE_CHANGE_SUCCESS || change == GST_STATE_CHANGE_NO_PREROLL;
1092 Q_ASSERT(element());
1093 return gst_element_sync_state_with_parent(element()) == TRUE;
1098 GstState state, pending;
1099 GstStateChangeReturn change =
1100 gst_element_get_state(element(), &state, &pending, timeout.count());
1102 if (change != GST_STATE_CHANGE_SUCCESS && change != GST_STATE_CHANGE_NO_PREROLL) {
1103 qWarning() <<
"Could not finish change state of" << name() << change << state << pending;
1106 return change == GST_STATE_CHANGE_SUCCESS;
1112 GstStateChangeReturn change =
1113 gst_element_get_state(element(), &state,
nullptr, timeout.count());
1114 return change == GST_STATE_CHANGE_ASYNC;
1117bool QGstElement::waitForAsyncStateChangeComplete(
std::chrono::nanoseconds timeout)
const
1119 using namespace std::chrono_literals;
1121 if (!hasAsyncStateChange())
1126 std::this_thread::sleep_for(10ms);
1132 gst_element_set_locked_state(element(), locked);
1137 return gst_element_is_locked_state(element());
1142 gst_element_send_event(element(), event);
1147 sendEvent(gst_event_new_eos());
1153 if (!gst_element_query_duration(element(), GST_FORMAT_TIME, &d)) {
1154 qDebug() <<
"QGstElement: failed to query duration";
1155 return std::nullopt;
1157 return std::chrono::nanoseconds{ d };
1162 using namespace std::chrono;
1163 auto dur = duration();
1165 return round<milliseconds>(*dur);
1166 return std::nullopt;
1171 QGstQueryHandle &query = positionQuery();
1174 if (gst_element_query(element(), query.get())) {
1175 gst_query_parse_position(query.get(),
nullptr, &pos);
1176 return std::chrono::nanoseconds{ pos };
1179 qDebug() <<
"QGstElement: failed to query position";
1180 return std::nullopt;
1185 using namespace std::chrono;
1186 auto pos = position();
1188 return round<milliseconds>(*pos);
1189 return std::nullopt;
1194 QGstQueryHandle query{
1195 gst_query_new_seeking(GST_FORMAT_TIME),
1196 QGstQueryHandle::HasRef,
1198 gboolean canSeek =
false;
1199 gst_query_parse_seeking(query.get(),
nullptr, &canSeek,
nullptr,
nullptr);
1201 if (gst_element_query(element(), query.get())) {
1202 gst_query_parse_seeking(query.get(),
nullptr, &canSeek,
nullptr,
nullptr);
1205 return std::nullopt;
1210 return gst_element_get_base_time(element());
1215 gst_element_set_base_time(element(), time);
1220 return GST_ELEMENT_CAST(get());
1226 qGstCheckedCast<GstElement>(gst_element_get_parent(object())),
1227 QGstElement::HasRef,
1236 if (greatAncestor) {
1237 ancestor =
std::move(greatAncestor);
1241 return QGstPipeline{
1242 qGstSafeCast<GstPipeline>(ancestor.element()),
1243 QGstPipeline::NeedsRef,
1250 static const bool dumpEnabled = qEnvironmentVariableIsSet(
"GST_DEBUG_DUMP_DOT_DIR");
1258QGstQueryHandle &
QGstElement::positionQuery()
const
1260 if (Q_UNLIKELY(!m_positionQuery))
1261 m_positionQuery = QGstQueryHandle{
1262 gst_query_new_position(GST_FORMAT_TIME),
1263 QGstQueryHandle::HasRef,
1266 return m_positionQuery;
1273 return QGstBin(gst_bin_new(name), NeedsRef);
1279 Q_ASSERT(GST_IS_BIN(element.element()));
1281 GST_BIN(element.release()),
1287 const char *name,
bool ghostUnlinkedPads)
1293 bool ghostUnlinkedPads)
1295 QUniqueGErrorHandle error;
1297 GstElement *element =
1298 gst_parse_bin_from_description_full(pipelineDescription, ghostUnlinkedPads,
1299 nullptr, GST_PARSE_FLAG_NONE, &error);
1302 qWarning() <<
"Failed to make element from pipeline description" << pipelineDescription
1308 gst_element_set_name(element, name);
1326 return qGstCheckedCast<GstBin>(object());
1336 gst_element_add_pad(element(), gst_ghost_pad_new(name, pad.pad()));
1341 return gst_bin_sync_children_states(bin());
1349 GST_DEBUG_BIN_TO_DOT_FILE(bin(), GST_DEBUG_GRAPH_SHOW_VERBOSE, fileNamePrefix);
1355 gst_bin_get_by_name(bin(), name),
1356 QGstElement::NeedsRef,
1362 gst_bin_recalculate_latency(bin());
1377 gst_base_sink_set_sync(baseSink(), arg ? TRUE : FALSE);
1382 return qGstCheckedCast<GstBaseSink>(element());
1397 return qGstCheckedCast<GstBaseSrc>(element());
1414 qGstCheckedCast<GstAppSink>(created.element()),
1415 QGstAppSink::NeedsRef,
1421 return qGstCheckedCast<GstAppSink>(element());
1424# if GST_CHECK_VERSION(1
, 24
, 0
)
1425void QGstAppSink::setMaxBufferTime(std::chrono::nanoseconds ns)
1427 gst_app_sink_set_max_time(appSink(), qGstClockTimeFromChrono(ns));
1433 gst_app_sink_set_max_buffers(appSink(), n);
1438 gst_app_sink_set_caps(appSink(), caps.caps());
1442 GDestroyNotify notify)
1444 gst_app_sink_set_callbacks(appSink(), &callbacks, user_data, notify);
1449 return QGstSampleHandle{
1450 gst_app_sink_pull_sample(appSink()),
1451 QGstSampleHandle::HasRef,
1469 qGstCheckedCast<GstAppSrc>(created.element()),
1470 QGstAppSrc::NeedsRef,
1476 return qGstCheckedCast<GstAppSrc>(element());
1480 GDestroyNotify notify)
1482 gst_app_src_set_callbacks(appSrc(), &callbacks, user_data, notify);
1487 return gst_app_src_push_buffer(appSrc(), buffer);
1492 return QStringLiteral(
"Could not find the %1 GStreamer element")
1493 .arg(QLatin1StringView(element));
QGObjectHandlerConnection(QGstObject object, gulong handler)
~QGObjectHandlerScopedConnection()
QGObjectHandlerScopedConnection(QGObjectHandlerConnection connection)
std::optional< int > toInt64() const
std::optional< QGRange< int > > toIntRange() const
std::optional< int > toInt() const
QGstStructureView toStructure() const
std::optional< QGRange< float > > getFractionRange() const
const char * toString() const
std::optional< float > getFraction() const
QGValue at(int index) const
std::optional< bool > toBool() const
QGstSampleHandle pullSample()
void setCallbacks(GstAppSinkCallbacks &callbacks, gpointer user_data, GDestroyNotify notify)
GstAppSink * appSink() const
void setCaps(const QGstCaps &caps)
static QGstAppSink create(const char *name)
QGstAppSink(GstAppSink *, RefMode)
static QGstAppSrc create(const char *name)
GstFlowReturn pushBuffer(GstBuffer *)
void setCallbacks(GstAppSrcCallbacks &callbacks, gpointer user_data, GDestroyNotify notify)
QGstAppSrc(GstAppSrc *, RefMode)
GstAppSrc * appSrc() const
QGstBaseSink(GstBaseSink *, RefMode)
GstBaseSink * baseSink() const
QGstBaseSrc(GstBaseSrc *, RefMode)
GstBaseSrc * baseSrc() const
QGstElement findByName(const char *)
void dumpGraph(const char *fileNamePrefix) const
void recalculateLatency()
static QGstBin create(const char *name)
void addGhostPad(const QGstElement &child, const char *name)
static QGstBin createFromPipelineDescription(const char *pipelineDescription, const char *name=nullptr, bool ghostUnlinkedPads=false)
static QGstBin createFromFactory(const char *factory, const char *name)
void addGhostPad(const char *name, const QGstPad &pad)
QGstBin(GstBin *bin, RefMode mode=NeedsRef)
void addPixelFormats(const QList< QVideoFrameFormat::PixelFormat > &formats, const char *modifier=nullptr)
MemoryFormat memoryFormat() const
static QGstCaps fromCameraFormat(const QCameraFormat &format)
void setResolution(QSize)
QGstStructureView at(int index) const
QGstClock(GstClock *clock, RefMode mode)
GstClockTime time() const
QGstClock(const QGstObject &o)
void setBaseTime(GstClockTime time) const
GstStateChangeReturn setState(GstState state)
std::optional< std::chrono::nanoseconds > position() const
GstElement * element() const
QGstElement(GstElement *element, RefMode mode)
void lockState(bool locked)
QGstPad getRequestPad(const char *name) const
std::optional< bool > canSeek() const
std::optional< std::chrono::nanoseconds > duration() const
bool isStateLocked() const
void sendEvent(GstEvent *event) const
void dumpPipelineGraph(const char *filename) const
GstClockTime baseTime() const
void releaseRequestPad(const QGstPad &pad) const
bool syncStateWithParent()
QGstPad staticPad(const char *name) const
std::optional< std::chrono::milliseconds > positionInMs() const
static QGstElement createFromFactory(const char *factory, const char *name=nullptr)
QGstElement getParent() const
QGstPipeline getPipeline() const
static QGstElement createFromPipelineDescription(const char *)
std::optional< std::chrono::milliseconds > durationInMs() const
void set(const char *property, double d)
QGObjectHandlerConnection connect(const char *name, GCallback callback, gpointer userData)
void * getObject(const char *property) const
double getDouble(const char *property) const
int getInt(const char *property) const
void set(const char *property, int32_t i)
QLatin1StringView name() const
void set(const char *property, const QGstObject &o)
QGString getString(const char *property) const
void disconnect(gulong handlerId)
QGstObject getGstObject(const char *property) const
QLatin1StringView typeName() const
void set(const char *property, const char *str)
bool getBool(const char *property) const
QGstObject & operator=(QGstObject &&) noexcept=default
void set(const char *property, void *object, GDestroyNotify destroyFunction)
void set(const char *property, bool b)
quint64 getUInt64(const char *property) const
QGstStructureView getStructure(const char *property) const
qint64 getInt64(const char *property) const
void set(const char *property, const QGstCaps &c)
float getFloat(const char *property) const
uint getUInt(const char *property) const
GstObject * object() const
bool link(const QGstPad &sink) const
GstEvent * stickyEvent(GstEventType type)
QGstTagListHandle tags() const
QGstPad(const QGstObject &o)
QGstCaps queryCaps() const
QGstPad(GstPad *pad, RefMode mode)
void sendFlushStartStop(bool resetTime)
QGString streamId() const
std::optional< QPlatformMediaPlayer::TrackType > inferTrackTypeFromName() const
bool sendEvent(GstEvent *event)
QGstCaps currentCaps() const
QGstElement parent() const
bool unlink(const QGstPad &sink) const
QGstStructureView(const QUniqueGstStructureHandle &)
QGRange< float > frameRateRange() const
QGValue operator[](const char *fieldname) const
QVideoFrameFormat::PixelFormat pixelFormat() const
QUniqueGstStructureHandle clone() const
std::optional< QGRange< QSize > > resolutionRange() const
QGstreamerMessage getMessage()
std::optional< Fraction > pixelAspectRatio() const
QGstTagListHandle tags() const
QByteArrayView name() const
QGstStructureView(const GstStructure *)
constexpr std::array< VideoFormat, 19 > qt_videoFormatLookup
int indexOfVideoFormat(QVideoFrameFormat::PixelFormat format)
static QSize qCalculateFrameSizeGStreamer(QSize resolution, Fraction par)
QString qGstErrorMessageCannotFindElement(std::string_view element)