diff --git a/src/private/directrenderer.cpp b/src/private/directrenderer.cpp index fea4ed26d0c3044fb5f8dafe995b99463ec41590..a5a2d78d296e2c8bdb8aa7added8d873c91297f9 100644 --- a/src/private/directrenderer.cpp +++ b/src/private/directrenderer.cpp @@ -21,7 +21,9 @@ #include <QtCore/QMutex> #include <QtCore/QThread> #include <QtCore/QTime> +#include <QtCore/QTimer> +#include <cstring> #ifndef CLOCK_REALTIME #define CLOCK_REALTIME 0 @@ -48,8 +50,6 @@ private: } - - Video::DirectRendererPrivate::DirectRendererPrivate(Video::DirectRenderer* parent) : QObject(parent), q_ptr(parent) { } @@ -58,12 +58,6 @@ Video::DirectRendererPrivate::DirectRendererPrivate(Video::DirectRenderer* paren Video::DirectRenderer::DirectRenderer(const QByteArray& id, const QSize& res): Renderer(id, res), d_ptr(new DirectRendererPrivate(this)) { setObjectName("Video::DirectRenderer:"+id); - - - //DBusVideoManager::instance().registerFrameListener("local", [this] { -// qDebug() << "RECEIVED FRAME"; - // }); - } ///Destructor @@ -74,10 +68,28 @@ Video::DirectRenderer::~DirectRenderer() void Video::DirectRenderer::startRendering() { + qWarning() << "STARTING RENDERING"; + setRendering(true); + emit started(); } void Video::DirectRenderer::stopRendering () { + qWarning() << "STOPPING RENDERING"; + setRendering(false); + emit stopped(); +} +void Video::DirectRenderer::onNewFrame(const QByteArray& frame) +{ +// qDebug("Frame received by DirectRenderer, size: w %d, h %d", size().width(), size().height()); + if (!isRendering()) { + return; + } + if (static_cast<Video::Renderer*>(this)->d_ptr->otherFrame().size() != (size().height() * size().width())) + static_cast<Video::Renderer*>(this)->d_ptr->otherFrame().resize(size().height() * size().width()*4); + ::memcpy(static_cast<Video::Renderer*>(this)->d_ptr->otherFrame().data(),frame,static_cast<Video::Renderer*>(this)->d_ptr->otherFrame().size()); + static_cast<Video::Renderer*>(this)->d_ptr->updateFrameIndex(); + emit frameUpdated(); } #include <directrenderer.moc> diff --git a/src/private/directrenderer.h b/src/private/directrenderer.h index c59d5d21f33799a36637fc61782d70cf1aecf802..a71fb06b25a66e5c472ab9bd76da6a5a8bb49f39 100644 --- a/src/private/directrenderer.h +++ b/src/private/directrenderer.h @@ -25,6 +25,8 @@ //Qt class QMutex; +class QTimer; +class QThread; //Ring #include "video/device.h" @@ -41,10 +43,14 @@ class LIB_EXPORT DirectRenderer : public Renderer { #pragma GCC diagnostic pop public: + //Constructor DirectRenderer (const QByteArray& id, const QSize& res); virtual ~DirectRenderer(); + void onNewFrame(const QByteArray& frame); + + public Q_SLOTS: virtual void startRendering() override; virtual void stopRendering () override; diff --git a/src/private/videorenderer_p.h b/src/private/videorenderer_p.h index 16c2402b9baae887a424e400d9e05ce97df3c940..6770d5e57ec07b296a3e90936fb309d6d364446c 100644 --- a/src/private/videorenderer_p.h +++ b/src/private/videorenderer_p.h @@ -45,7 +45,7 @@ public: QSize m_pSize ; //Helpers - QByteArray& otherFrame () const; + QByteArray& otherFrame () ; void updateFrameIndex () ; private: diff --git a/src/private/videorenderermanager.cpp b/src/private/videorenderermanager.cpp index 32d71cfc014bd0d906fa83ba91872f9df418c87b..2e7c51c85b046cde5cf031f6158b8a273dec5442 100644 --- a/src/private/videorenderermanager.cpp +++ b/src/private/videorenderermanager.cpp @@ -18,6 +18,9 @@ ***************************************************************************/ #include "videorenderermanager.h" + +#include <vector> + //Qt #include <QtCore/QMutex> @@ -58,7 +61,7 @@ public: private: VideoRendererManager* q_ptr; -private Q_SLOTS: +public Q_SLOTS: void startedDecoding(const QString& id, const QString& shmPath, int width, int height); void stoppedDecoding(const QString& id, const QString& shmPath); void deviceEvent(); @@ -124,6 +127,7 @@ Video::Renderer* VideoRendererManager::previewRenderer() ///Stop video preview void VideoRendererManager::stopPreview() { + //d_ptr->stoppedDecoding("local",""); VideoManagerInterface& interface = DBus::VideoManager::instance(); interface.stopCamera(); d_ptr->m_PreviewState = false; @@ -132,6 +136,9 @@ void VideoRendererManager::stopPreview() ///Start video preview void VideoRendererManager::startPreview() { + qWarning() << "STARTING PREVIEW"; + // d_ptr->startedDecoding("local","",500,500); + if (d_ptr->m_PreviewState) return; VideoManagerInterface& interface = DBus::VideoManager::instance(); interface.startCamera(); @@ -159,13 +166,18 @@ void VideoRendererManagerPrivate::deviceEvent() ///A video is not being rendered void VideoRendererManagerPrivate::startedDecoding(const QString& id, const QString& shmPath, int width, int height) { - const QSize res = QSize(width,height); const QByteArray rid = id.toLatin1(); + qWarning() << "startedDecoding for sink id: " << id; if (m_lRenderers[rid] == nullptr ) { #if defined(Q_OS_DARWIN) m_lRenderers[rid] = new Video::DirectRenderer(rid, res); + qWarning() << "Calling registerFrameListener"; + DBus::VideoManager::instance().registerSinkTarget(id, [this, id, width, height] (const unsigned char* frame) { + static_cast<Video::DirectRenderer*>(m_lRenderers[id.toLatin1()])->onNewFrame( + QByteArray::fromRawData(reinterpret_cast<const char *>(frame), width*height)); + }); #else m_lRenderers[rid] = new Video::ShmRenderer(rid,shmPath,res); #endif @@ -174,9 +186,12 @@ void VideoRendererManagerPrivate::startedDecoding(const QString& id, const QStri q_ptr->start(); } else { - // Video::Renderer* Renderer = m_lRenderers[rid]; - //TODO: do direct renderer stuff here m_lRenderers[rid]->setSize(res); + DBus::VideoManager::instance().registerSinkTarget(id, [this, id, width, height] (const unsigned char* frame) { + static_cast<Video::DirectRenderer*>(m_lRenderers[id.toLatin1()])->onNewFrame( + QByteArray::fromRawData(reinterpret_cast<const char *>(frame), width*height)); + }); + #if !defined(Q_OS_DARWIN) static_cast<Video::ShmRenderer*>(m_lRenderers[rid])->setShmPath(shmPath); #endif diff --git a/src/qtwrapper/CMakeLists.txt b/src/qtwrapper/CMakeLists.txt index ab9c2e8389a4f4e675fc069b67621b8c66aa1d99..562f1772236798ce564b666b8f40efcfa3fcc937 100644 --- a/src/qtwrapper/CMakeLists.txt +++ b/src/qtwrapper/CMakeLists.txt @@ -10,6 +10,10 @@ SET(ENABLE_LIBWRAP true) ADD_DEFINITIONS(-DENABLE_LIBWRAP=true) ADD_DEFINITIONS("-std=c++0x") +MESSAGE("VIDEO enabled") +ADD_DEFINITIONS(-DENABLE_VIDEO=true) +SET(ENABLE_VIDEO 1 CACHE BOOLEAN "Enable video") + SET(LOCAL_CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/../../cmake/) SET(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${LOCAL_CMAKE_MODULE_PATH}) diff --git a/src/qtwrapper/instancemanager.cpp b/src/qtwrapper/instancemanager.cpp index 61232c4c185ef5e9bd24a48e84e69d38366ba9ad..486a472522c4f9a2c996bb1d70e87fa061f576d1 100644 --- a/src/qtwrapper/instancemanager.cpp +++ b/src/qtwrapper/instancemanager.cpp @@ -39,9 +39,9 @@ InstanceInterface::InstanceInterface() : m_pTimer(nullptr) using DRing::ConfigurationSignal; using DRing::PresenceSignal; - #ifdef ENABLE_VIDEO +#ifdef ENABLE_VIDEO using DRing::VideoSignal; - #endif +#endif m_pTimer = new QTimer(this); m_pTimer->setInterval(50); @@ -55,7 +55,7 @@ InstanceInterface::InstanceInterface() : m_pTimer(nullptr) registerCallHandlers(DBus::CallManager::instance().callHandlers); registerConfHandlers(DBus::ConfigurationManager::instance().confHandlers); registerPresHandlers(DBus::PresenceManager::instance().presHandlers); -#ifdef RING_VIDEO +#ifdef ENABLE_VIDEO registerVideoHandlers(DBus::VideoManager::instance().videoHandlers); #endif diff --git a/src/qtwrapper/videomanager_wrap.h b/src/qtwrapper/videomanager_wrap.h index 0b195986bacb352fd9957d9e4adaa300edacfe47..e1056c0922f1c84210e07892add8c9498868b859 100644 --- a/src/qtwrapper/videomanager_wrap.h +++ b/src/qtwrapper/videomanager_wrap.h @@ -19,6 +19,10 @@ #ifndef VIDEO_DBUS_INTERFACE_H #define VIDEO_DBUS_INTERFACE_H +// libstdc++ +#include <functional> + +// Qt #include <QtCore/QObject> #include <QtCore/QCoreApplication> #include <QtCore/QByteArray> @@ -88,10 +92,6 @@ private: VideoManagerSignalProxy* proxy; VideoManagerProxySender* sender; -#ifdef ENABLE_VIDEO - std::map<std::string, std::shared_ptr<DRing::CallbackWrapperBase>> videoHandlers; -#endif - public Q_SLOTS: // METHODS void applySettings(const QString &name, MapStringString settings) { @@ -192,17 +192,27 @@ public Q_SLOTS: // METHODS #endif } + void registerSinkTarget(const QString &sinkID, std::function<void(uint8_t*)>&& cb) + { +#ifdef ENABLE_VIDEO + DRing::registerSinkTarget(sinkID.toStdString(), std::move(cb)); +#endif + } + + void registerSinkTarget(const QString &sinkID, std::function<void(uint8_t*)>& cb) + { +#ifdef ENABLE_VIDEO + DRing::registerSinkTarget(sinkID.toStdString(), std::move(cb)); +#endif + } + Q_SIGNALS: // SIGNALS void deviceEvent(); void startedDecoding(const QString &id, const QString &shmPath, int width, int height, bool isMixer); void stoppedDecoding(const QString &id, const QString &shmPath, bool isMixer); }; -namespace org { - namespace ring { - namespace Ring { +namespace org { namespace ring { namespace Ring { typedef ::VideoManagerInterface VideoManager; - } - } -} +}}} // namesapce org::ring::Ring #endif diff --git a/src/video/renderer.cpp b/src/video/renderer.cpp index 4f136e9ccf648aed88e9b9738df89b02e56e9725..d6ae913a60010fc6d8b6a4e108789ee2cfec4615 100644 --- a/src/video/renderer.cpp +++ b/src/video/renderer.cpp @@ -49,10 +49,10 @@ bool Video::Renderer::isRendering() const return d_ptr->m_isRendering; } -QByteArray& Video::RendererPrivate::otherFrame() const +QByteArray& Video::RendererPrivate::otherFrame() { static QByteArray empty; - return q_ptr->isRendering()?const_cast<Video::RendererPrivate*>(this)->m_Frame[!m_FrameIdx]:empty; + return q_ptr->isRendering()?m_Frame[!m_FrameIdx]:empty; } ///Return the current framerate diff --git a/src/video/renderer.h b/src/video/renderer.h index 6b6e05ec813ba7e1b0a8a29f9d7d6a4a186e30aa..aa5f6548551fa8cd2ba90ee45abbf85ac9b76854 100644 --- a/src/video/renderer.h +++ b/src/video/renderer.h @@ -34,12 +34,13 @@ namespace Video { class RendererPrivate; class ShmRendererPrivate; class DirectRendererPrivate; +class DirectRenderer; /** * This class provide a rendering object to be used by clients * to get the video content. This object is not intended to be * extended outside of the LibRingClient. - * + * * Each platform transparently provide its own implementation. */ class LIB_EXPORT Renderer : public QObject { @@ -50,6 +51,7 @@ Q_OBJECT friend class Video::ShmRendererPrivate; friend class Video::DirectRendererPrivate; +friend class Video::DirectRenderer; public: //Constructor