Resolved conflicts.

This commit is contained in:
Sofian Audry
2020-03-23 15:18:40 -04:00
30 changed files with 529 additions and 149 deletions
+1 -1
View File
@@ -6,7 +6,7 @@ TEMPLATE = app
VERSION = 0.6.3
TARGET = mapmap
DEFINES += UNICODE QT_THREAD_SUPPORT QT_CORE_LIB QT_GUI_LIB
DEFINES += UNICODE QT_THREAD_SUPPORT QT_CORE_LIB QT_GUI_LIB QT_MESSAGELOGCONTEXT
include(src/core/core.pri)
include(src/shape/shape.pri)
+4 -3
View File
@@ -27,10 +27,11 @@ MainApplication::MainApplication(int &argc, char *argv[])
: QApplication(argc, argv)
{
#ifdef Q_OS_WIN32
// Set GStreamer plugins path on Windows
QString pluginPath = QCoreApplication::applicationDirPath() + "/plugins";
// Set GStreamer plugins path on Windows
QString pluginPath = QCoreApplication::applicationDirPath() + "/plugin";
_putenv_s("GST_PLUGIN_PATH", pluginPath.toLocal8Bit());
if (QDir(pluginPath).exists())
_putenv_s("GST_PLUGIN_PATH", pluginPath.toLocal8Bit());
// Set settings default format
QSettings::setDefaultFormat(QSettings::IniFormat);
+1
View File
@@ -27,6 +27,7 @@
#include <QDebug>
#include "MM.h"
#include <QSettings>
#include <QDir>
namespace mmp {
+76
View File
@@ -0,0 +1,76 @@
/*
* CameraImpl.cpp
*
* (c) 2019 Dame Diongue -- baydamd(@)gmail(.)com
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "CameraImpl.h"
namespace mmp {
CameraImpl::CameraImpl() :
_camera(nullptr),
_cameraSurface(nullptr)
{
}
CameraImpl::~CameraImpl()
{
_camera->stop();
delete _camera;
delete _cameraSurface;
}
bool CameraImpl::loadMovie(const QString &deviceName)
{
VideoImpl::loadMovie(deviceName);
_camera = new QCamera(deviceName.toLocal8Bit());
_cameraSurface = new CameraSurface();
_camera->setViewfinder(_cameraSurface);
if (_camera->isAvailable())
_camera->start();
if (_camera->state() == QCamera::ActiveState)
return true;
if (_camera->error() != QCamera::NoError)
QMessageBox(QMessageBox::Critical, "Camera Error",
"Failed to start: " + _camera->errorString()).exec();
return false;
}
int CameraImpl::getWidth() const
{
return _cameraSurface->surfaceFormat().frameWidth();
}
int CameraImpl::getHeight() const
{
return _cameraSurface->surfaceFormat().frameHeight();
}
const uchar *CameraImpl::getBits()
{
return _cameraSurface->bits();
}
}
+57
View File
@@ -0,0 +1,57 @@
/*
* CameraImpl.h
*
* (c) 2019 Dame Diongue -- baydamd(@)gmail(.)com
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef CAMERAIMPL_H_
#define CAMERAIMPL_H_
#include "CameraSurface.h"
#include "VideoImpl.h"
#include <QCamera>
#include <QCameraInfo>
namespace mmp {
class CameraImpl : public VideoImpl
{
public:
CameraImpl();
~CameraImpl();
bool loadMovie(const QString& deviceName);
bool isLive() { return true; }
int getWidth() const;
int getHeight() const;
const uchar* getBits();
bool hasBits() const { return _cameraSurface->isActive(); }
bool bitsHaveChanged() const { return true; }
private:
QCamera *_camera;
CameraSurface *_cameraSurface;
};
}
#endif // CAMERAIMPL_H_
+115
View File
@@ -0,0 +1,115 @@
/****************************************************************************
**
** Copyright (C) 2015 The Qt Company Ltd.
** Contact: http://www.qt.io/licensing/
**
** This file is part of the examples of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
** You may use this file under the terms of the BSD license as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
** met:
** * Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** * Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in
** the documentation and/or other materials provided with the
** distribution.
** * Neither the name of The Qt Company Ltd nor the names of its
** contributors may be used to endorse or promote products derived
** from this software without specific prior written permission.
**
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "CameraSurface.h"
#include <QVideoSurfaceFormat>
#include <QGLWidget>
#include <QDebug>
namespace mmp {
CameraSurface::CameraSurface(QObject *parent)
: QAbstractVideoSurface(parent)
{
}
CameraSurface::~CameraSurface()
{
}
QList<QVideoFrame::PixelFormat> CameraSurface::supportedPixelFormats(
QAbstractVideoBuffer::HandleType handleType) const
{
if (handleType == QAbstractVideoBuffer::NoHandle) {
return QList<QVideoFrame::PixelFormat>()
<< QVideoFrame::Format_ARGB32
<< QVideoFrame::Format_ARGB32_Premultiplied
<< QVideoFrame::Format_RGB32
<< QVideoFrame::Format_RGB24
;
} else {
return QList<QVideoFrame::PixelFormat>();
}
}
bool CameraSurface::present(const QVideoFrame &frame)
{
if (frame.isValid()) {
// Copy current frame.
QVideoFrame currentFrame(frame);
if (currentFrame.map(QAbstractVideoBuffer::ReadOnly))
{
QImage::Format imageFormat = QVideoFrame::imageFormatFromPixelFormat(currentFrame.pixelFormat());
if (imageFormat != QImage::Format_Invalid) {
_temporaryImage = QImage(currentFrame.bits(),
currentFrame.width(),
currentFrame.height(),
imageFormat);
} else {
int nbytes = currentFrame.mappedBytes();
_temporaryImage = QImage::fromData(currentFrame.bits(), nbytes);
}
currentFrame.unmap();
}
#ifdef Q_OS_WIN
_temporaryImage = QGLWidget::convertToGLFormat(_temporaryImage);
#else
// Convert to OpenGLformat and apply transforms to straighten.
_temporaryImage = QGLWidget::convertToGLFormat(_temporaryImage)
.mirrored(true, false)
.transformed(QTransform().rotate(180));
#endif
return true;
}
return false;
}
const uchar* CameraSurface::bits()
{
return _temporaryImage.bits();
}
}
+70
View File
@@ -0,0 +1,70 @@
/****************************************************************************
**
** Copyright (C) 2015 The Qt Company Ltd.
** Contact: http://www.qt.io/licensing/
**
** This file is part of the examples of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:BSD$
** You may use this file under the terms of the BSD license as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
** met:
** * Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** * Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in
** the documentation and/or other materials provided with the
** distribution.
** * Neither the name of The Qt Company Ltd nor the names of its
** contributors may be used to endorse or promote products derived
** from this software without specific prior written permission.
**
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef CAMERA_SURFACE_H_
#define CAMERA_SURFACE_H_
#include <QAbstractVideoSurface>
#include <QVideoSurfaceFormat>
#include <QGraphicsItem>
#include <QAudio>
namespace mmp {
class CameraSurface : public QAbstractVideoSurface
{
Q_OBJECT
public:
CameraSurface(QObject *parent = nullptr);
~CameraSurface() override;
QList<QVideoFrame::PixelFormat> supportedPixelFormats(
QAbstractVideoBuffer::HandleType handleType) const override;
bool present(const QVideoFrame &frame) override;
const uchar* bits();
private:
QImage _temporaryImage;
};
}
#endif // CAMERA_SURFACE_H_
+3
View File
@@ -69,6 +69,9 @@ public:
static const int ZOOM_TOOLBAR_ICON_SIZE = 16;
static const int ZOOM_TOOLBAR_BUTTON_SIZE = 20;
static const int MAPPING_LIST_ICON_SIZE = 16;
static const int MAPPING_LIST_HIDE_COLUMN = 24;
static const int MAPPING_LIST_NAME_COLUMN = 135;
static const int MAPPING_LIST_BUTTONS_COLUMN = 128;
// OSC
static const int DEFAULT_OSC_PORT = 12345;
+5 -5
View File
@@ -109,7 +109,7 @@ public:
}
/// The type of the mapping (expressed as a string).
virtual QString getType() const = 0;
virtual MShape::ShapeType getType() const = 0;
// Return copy of this mapping.
virtual Mapping* clone() const = 0;
@@ -189,8 +189,8 @@ public:
/// Returns true iff paint is compatible with mapping.
virtual bool paintIsCompatible(Paint::ptr paint) const;
virtual QString getType() const {
return getShape()->getType() + "_color";
virtual MShape::ShapeType getType() const {
return getShape()->getType();
}
};
@@ -228,8 +228,8 @@ public:
/// Returns true iff paint is compatible with mapping.
virtual bool paintIsCompatible(Paint::ptr paint) const;
virtual QString getType() const {
return getShape()->getType() + "_texture";
virtual MShape::ShapeType getType() const {
return getShape()->getType();
}
};
+1
View File
@@ -105,6 +105,7 @@ bool MappingManager::removePaint(uid paintId)
Q_ASSERT(idx != -1);
paintVector.remove(idx);
paintMap.remove(paintId);
paint->~Paint(); // FIX ME: Explicit call of paint destructor in order add Camera more than once
return true;
}
else
+16 -14
View File
@@ -21,7 +21,7 @@
#include "Paint.h"
#include "VideoImpl.h"
#include "VideoUriDecodeBinImpl.h"
#include "VideoV4l2SrcImpl.h"
#include "CameraImpl.h"
#include "VideoShmSrcImpl.h"
#include <iostream>
@@ -188,7 +188,7 @@ void Image::_doPlay()
/* Implementation of the Video class */
Video::Video(int id) : Texture(id),
_uri(""),
_impl(NULL)
_impl(nullptr)
{
_impl = new VideoUriDecodeBinImpl();
setRate(1);
@@ -198,26 +198,24 @@ Video::Video(int id) : Texture(id),
Video::Video(const QString uri_, VideoType type, double rate, uid id):
Texture(id),
_uri(""),
_impl(NULL)
_videoType(type),
_impl(nullptr)
{
switch (type) {
case VIDEO_URI:
_impl = new VideoUriDecodeBinImpl();
break;
case VIDEO_WEBCAM:
_impl = new VideoV4l2SrcImpl();
_impl = new CameraImpl();
break;
case VIDEO_SHMSRC:
_impl = new VideoShmSrcImpl();
break;
default:
fprintf (stderr, "Could not determine type for video source\n ");
break;
}
//_impl = new VideoShmSrcImpl();//V4l2SrcImpl();//UriDecodeBinImpl();
setRate(rate);
setVolume(1);
setUri(uri_);
_videoType = type;
}
// vertigo
@@ -306,11 +304,11 @@ bool Video::hasVideoSupport()
bool Video::setUri(const QString &uri)
{
QSettings settings;
bool sameMediasource = settings.value("oscSameMediaSource").toBool();
bool sameMediaSourceOSC = settings.value("oscSameMediaSource").toBool();
// Check if we're actually changing the uri.
// In some case with OSC message the user may need to allow
// the same media source (uri)
if (sameMediasource || uri != _uri)
if (sameMediaSourceOSC || uri != _uri)
{
// Try to load movie.
if (!_impl->loadMovie(uri))
@@ -330,14 +328,18 @@ bool Video::setUri(const QString &uri)
return false;
}
if (!_generateThumbnail())
qDebug() << "Could not generate thumbnail for " << uri << ": using generic icon." << endl;
if (_videoType != VIDEO_WEBCAM) { // Generated thumbnail if source type is not camera
if (!_generateThumbnail())
qDebug() << "Could not generate thumbnail for " << uri << ": using generic icon." << endl;
}
_emitPropertyChanged("uri");
// Return success.
return true;
}
// Return success.
return true;
return false;
}
void Video::_doPlay()
+17 -4
View File
@@ -38,6 +38,8 @@
#include "Element.h"
#include "Maths.h"
#include <QCameraInfo>
namespace mmp {
typedef enum {
@@ -66,6 +68,11 @@ protected:
Paint(uid id=NULL_UID);
public:
enum SourceType {
Video, Image, Color
};
typedef QSharedPointer<Paint> ptr;
virtual ~Paint();
@@ -99,7 +106,7 @@ public:
/// Unlocks mutex (default = no effect).
virtual void unlockMutex() {}
virtual QString getType() const = 0;
virtual SourceType getSourceType() const = 0;
protected:
virtual void _doPlay() {}
@@ -125,7 +132,7 @@ public:
QColor getColor() const { return color; }
void setColor(const QColor& color_) { color = color_; }
virtual QString getType() const { return "color"; }
virtual SourceType getSourceType() const { return SourceType::Color; }
virtual QIcon getIcon() const {
QPixmap pixmap(MM::MAPPING_LIST_ICON_SIZE, MM::MAPPING_LIST_ICON_SIZE);
@@ -202,6 +209,11 @@ public:
virtual void read(const QDomElement& obj);
virtual void write(QDomElement& obj);
// Get Camera human-readable name from url
QString getCameraNameFromUri(const QString &uri) {
return QCameraInfo(uri.toLocal8Bit()).description();
}
protected:
// Lists QProperties that should NOT be parsed automatically.
virtual QList<QString> _propertiesSpecial() const { return Paint::_propertiesSpecial() << "x" << "y"; }
@@ -246,7 +258,7 @@ public:
const QString getUri() const { return _uri; }
bool setUri(const QString &uri);
virtual QString getType() const { return "image"; }
virtual SourceType getSourceType() const { return SourceType::Image; }
bool isAnimation() const { return (_images.size() > 1); }
@@ -312,7 +324,7 @@ public:
/// Unlocks mutex (default = no effect).
virtual void unlockMutex();
virtual QString getType() const { return "media"; }
virtual SourceType getSourceType() const { return SourceType::Video; }
virtual int getWidth() const;
virtual int getHeight() const;
@@ -353,6 +365,7 @@ protected:
QString _uri;
QIcon _icon;
VideoType _videoType;
/**
* Private implementation, so that GStreamer headers don't need
+2 -2
View File
@@ -101,14 +101,14 @@ void ProjectReader::parseProject(const QDomElement& project)
_window->addPaintItem(paint->getId(), paint->getIcon(), paint->getName());
// Locate media file if not found
if (paint->getType() == "media")
if (paint->getSourceType() == Paint::SourceType::Video)
{
QSharedPointer<Video> media = qSharedPointerCast<Video>(paint);
Q_CHECK_PTR(media);
if (!_window->fileExists(media->getUri()))
media->setUri(_window->locateMediaFile(media->getUri(), false));
}
if (paint->getType() == "image")
if (paint->getSourceType() == Paint::SourceType::Image)
{
QSharedPointer<Image> image = qSharedPointerCast<Image>(paint);
Q_CHECK_PTR(image);
+6 -6
View File
@@ -78,12 +78,12 @@ public:
/**
* Returns the width of the video image.
*/
int getWidth() const;
virtual int getWidth() const;
/**
* Returns the height of the video image.
*/
int getHeight() const;
virtual int getHeight() const;
/**
* Returns the path to the media file being played.
@@ -94,13 +94,13 @@ public:
* Returns the raw image of the last video frame.
* It is currently unused!
*/
const uchar* getBits();
virtual const uchar* getBits();
/// Returns true iff bits have started flowing (ie. if there is at least a first sample available).
bool hasBits() const { return (_currentFrameSample != NULL); }
virtual bool hasBits() const { return (_currentFrameSample != NULL); }
/// Returns true iff bits have changed since last call to getBits().
bool bitsHaveChanged() const { return _bitsChanged; }
virtual bool bitsHaveChanged() const { return _bitsChanged; }
/**
* Checks if the pipeline is ready.
@@ -195,7 +195,7 @@ public:
void unlockMutex();
/// Wait until first data samples are available (blocking).
bool waitForNextBits(int timeout, const uchar** bits=0);
bool waitForNextBits(int timeout, const uchar** bits = 0);
protected:
int _width;
+4
View File
@@ -2,6 +2,8 @@
include(../src.pri)
HEADERS += $$PWD/Commands.h \
$$PWD/CameraImpl.h \
$$PWD/CameraSurface.h \
$$PWD/Element.h \
$$PWD/Mapping.h \
$$PWD/MappingManager.h \
@@ -21,6 +23,8 @@ HEADERS += $$PWD/Commands.h \
$$PWD/Util.h
SOURCES += $$PWD/Commands.cpp \
$$PWD/CameraImpl.cpp \
$$PWD/CameraSurface.cpp \
$$PWD/Element.cpp \
$$PWD/Mapping.cpp \
$$PWD/MappingManager.cpp \
+1 -1
View File
@@ -36,7 +36,7 @@ class AboutDialog : public QDialog
{
Q_OBJECT
public:
AboutDialog(QWidget *parent = 0);
AboutDialog(QWidget *parent = nullptr);
~AboutDialog() {}
public slots:
+2 -2
View File
@@ -41,7 +41,7 @@ ConsoleWindow::ConsoleWindow(QWidget *parent) : QMainWindow(parent)
// Set color scheme
QPalette scheme = palette();
scheme.setColor(QPalette::Base, Qt::black);
scheme.setColor(QPalette::Base, QColor("#00020E"));
scheme.setColor(QPalette::Text, Qt::white);
_console->setPalette(scheme);
@@ -102,7 +102,7 @@ void ConsoleWindow::printMessage(QtMsgType type, const QMessageLogContext &conte
debug = "<strong style=\"color: #00FF00;\">Debug:</strong>",
info = "<strong style=\"color: #1E90FF;\">Info:</strong>",
warning = "<strong style=\"color: #FFFF00;\">Warning:</strong>",
critical = "<strong style=\"color: #FF0000;\">Critical:</strong>",
critical = "<strong style=\"color: #FF6600;\">Critical:</strong>",
fatal = "<strong style=\"background: #FF0000;\">Fatal!</strong>";
// Output
QString output;
+2 -2
View File
@@ -72,8 +72,8 @@ private:
QMenu *fileMenu;
// Constants
static const int CONSOLE_WINDOW_DEFAULT_WIDTH = 640;
static const int CONSOLE_WINDOW_DEFAULT_HEIGHT = 480;
static const int CONSOLE_WINDOW_DEFAULT_WIDTH = 1024;
static const int CONSOLE_WINDOW_DEFAULT_HEIGHT = 768;
};
}
+92 -65
View File
@@ -34,7 +34,7 @@ MainWindow::MainWindow()
{
// Create model.
#if QT_VERSION >= 0x050500
QMessageLogger(__FILE__, __LINE__, 0).info() << "Video support: " <<
QMessageLogger(__FILE__, __LINE__, nullptr).info() << "Video support: " <<
(Video::hasVideoSupport() ? "yes" : "no");
#else
QMessageLogger(__FILE__, __LINE__, 0).debug() << "Video support: " <<
@@ -182,6 +182,7 @@ void MainWindow::handleMappingItemSelectionChanged(const QModelIndex &index)
// Update canvases.
updateCanvases();
updateMappingListColumnWidth();
}
void MainWindow::handleMappingItemChanged(const QModelIndex &index)
@@ -239,7 +240,9 @@ void MainWindow::handlePaintChanged(Paint::ptr paint)
uid paintId = mappingManager->getPaintId(paint);
if (paint->getType() == "media")
// QSharedPointer<Texture> texture;
if (paint->getSourceType() == SourceType::Video)
{
QSharedPointer<Video> media = qSharedPointerCast<Video>(paint);
Q_CHECK_PTR(media);
@@ -250,7 +253,7 @@ void MainWindow::handlePaintChanged(Paint::ptr paint)
// if (!fileName.isEmpty())
// importMediaFile(fileName, paint, false);
}
if (paint->getType() == "image")
if (paint->getSourceType() == SourceType::Image)
{
QSharedPointer<Image> image = qSharedPointerCast<Image>(paint);
Q_CHECK_PTR(image);
@@ -261,7 +264,7 @@ void MainWindow::handlePaintChanged(Paint::ptr paint)
// if (!fileName.isEmpty())
// importMediaFile(fileName, paint, true);
}
else if (paint->getType() == "color")
else if (paint->getSourceType() == SourceType::Color)
{
// Pop-up color-choosing dialog to choose color paint.
QSharedPointer<Color> color = qSharedPointerCast<Color>(paint);
@@ -628,7 +631,10 @@ void MainWindow::importMedia()
void MainWindow::openCameraDevice()
{
#if QT_VERSION >= 0x050500
#if QT_VERSION >= 0x050300
// Stop video playback, if it is playing, to avoid lags. XXX Hack
pause(!pauseAction->isVisible());
QString device;
QList<QCameraInfo> cameras = QCameraInfo::availableCameras();
@@ -652,20 +658,27 @@ void MainWindow::openCameraDevice()
if (devices.contains(deviceName))
device = devices.value(deviceName);
}
}
else if (QCameraInfo::defaultCamera().isNull())
{
QMessageBox::warning(this, tr("No camera available"), tr("You can not use this feature!\nNo camera available in your system"));
}
else
{
device = QCameraInfo::defaultCamera().deviceName();
if (QCameraInfo::defaultCamera().isNull())
{
QMessageBox::warning(this, tr("No camera available"), tr("You can not use this feature!\nNo camera available in your system"));
}
else
{
device = QCameraInfo::defaultCamera().deviceName();
}
}
// Restart video playback if it was previously playing. XXX Hack
play(!pauseAction->isVisible());
if (!device.isEmpty())
importMediaFile(device, false);
importMediaFile(device, false, true);
#else
QMessageBox::warning(this, tr("No camera available"), tr("You can not use this feature!\nNo camera available in your system"));
#endif
@@ -712,7 +725,7 @@ void MainWindow::addMesh()
// Create input and output quads.
Mapping* mappingPtr;
if (paint->getType() == "color")
if (paint->getSourceType() == SourceType::Color)
{
MShape::ptr outputQuad = MShape::ptr(Util::createMeshForColor(sourceCanvas->width(), sourceCanvas->height()));
mappingPtr = new ColorMapping(paint, outputQuad);
@@ -747,7 +760,7 @@ void MainWindow::addTriangle()
// Create input and output quads.
Mapping* mappingPtr;
if (paint->getType() == "color")
if (paint->getSourceType() == SourceType::Color)
{
MShape::ptr outputTriangle = MShape::ptr(Util::createTriangleForColor(sourceCanvas->width(), sourceCanvas->height()));
mappingPtr = new ColorMapping(paint, outputTriangle);
@@ -782,7 +795,7 @@ void MainWindow::addEllipse()
// Create input and output ellipses.
Mapping* mappingPtr;
if (paint->getType() == "color")
if (paint->getSourceType() == SourceType::Color)
{
MShape::ptr outputEllipse = MShape::ptr(Util::createEllipseForColor(sourceCanvas->width(), sourceCanvas->height()));
mappingPtr = new ColorMapping(paint, outputEllipse);
@@ -1060,7 +1073,7 @@ void MainWindow::openRecentVideo()
{
QAction *action = qobject_cast<QAction *>(sender());
if (action)
importMediaFile(action->data().toString(),false);
importMediaFile(action->data().toString(), false);
}
bool MainWindow::clearProject()
@@ -1126,7 +1139,12 @@ uid MainWindow::createMediaPaint(uid paintId, QString uri, float x, float y,
// Add it to the manager.
Paint::ptr paint(tex);
paint->setName(strippedName(uri));
if (type == VIDEO_WEBCAM) {
paint->setName(tex->getCameraNameFromUri(uri));
} else {
paint->setName(strippedName(uri));
}
// Add paint to model and return its uid.
uid id = mappingManager->addPaint(paint);
@@ -1408,9 +1426,16 @@ void MainWindow::duplicateMapping(uid mappingId)
Mapping::ptr currentMapping = mappingManager->getMappingById(mappingId);
// Create new duplicated mapping item
Mapping::ptr clonedMappingPtr;
if (paintPtr->getSourceType() == SourceType::Color) // Color paint
//clonedMapping = new ColorMapping(paintPtr, shapePtr);
clonedMappingPtr = Mapping::ptr(new ColorMapping(paintPtr, shape));
else // Or Texture Paint
//clonedMapping = new TextureMapping(paintPtr, shapePtr, inputShape);
clonedMappingPtr = Mapping::ptr(new TextureMapping(paintPtr, shape, inputShape));
// Scale the duplicated shapes
if (shape->getType() == "mesh")
if (shape->getType() == ShapeType::Mesh)
shape->translate(QPointF(20, 20));
else
shape->translate(QPointF(0, 20));
@@ -1482,13 +1507,14 @@ void MainWindow::createLayout()
mappingList->setModel(mappingListModel);
mappingList->setItemDelegate(mappingItemDelegate);
// Pimp Mapping table widget
mappingList->horizontalHeader()->setResizeMode(QHeaderView::ResizeToContents);
mappingList->verticalHeader()->setResizeMode(QHeaderView::ResizeToContents);
mappingList->horizontalHeader()->setStretchLastSection(true);
//mappingList->setShowGrid(false);
mappingList->verticalHeader()->setSectionResizeMode(QHeaderView::ResizeToContents);
mappingList->setShowGrid(false);
mappingList->horizontalHeader()->hide();
mappingList->verticalHeader()->hide();
mappingList->setMouseTracking(true);// Important
mappingList->setColumnWidth(0, MM::MAPPING_LIST_HIDE_COLUMN);
mappingList->setColumnWidth(1, MM::MAPPING_LIST_NAME_COLUMN);
mappingList->setColumnWidth(2, MM::MAPPING_LIST_BUTTONS_COLUMN);
// Create property panel.
mappingPropertyPanel = new QStackedWidget;
@@ -1512,7 +1538,7 @@ void MainWindow::createLayout()
sourceLayout->addWidget(sourceCanvasToolbar, 0, Qt::AlignRight);
sourcePanel->setLayout(sourceLayout);
destinationCanvas = new MapperGLCanvas(this, true, 0, (QGLWidget*)sourceCanvas->viewport());
destinationCanvas = new MapperGLCanvas(this, true, nullptr, static_cast<QGLWidget*>(sourceCanvas->viewport()));
destinationCanvas->setFocusPolicy(Qt::ClickFocus);
destinationCanvas->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
destinationCanvas->setMinimumSize(CANVAS_MINIMUM_WIDTH, CANVAS_MINIMUM_HEIGHT);
@@ -1574,6 +1600,7 @@ void MainWindow::createLayout()
mainSplitter = new QSplitter(Qt::Horizontal);
mainSplitter->addWidget(canvasSplitter);
mainSplitter->addWidget(contentTab);
connect(mainSplitter, SIGNAL(splitterMoved(int, int)), this, SLOT(updateMappingListColumnWidth()));
// Initialize size to 9:1 proportions.
QSize sz = mainSplitter->size();
@@ -1677,16 +1704,14 @@ void MainWindow::createActions()
connect(importMediaAction, SIGNAL(triggered()), this, SLOT(importMedia()));
// Open camera.
#ifdef Q_OS_LINUX
openCameraAction = new QAction(tr("Open &Camera Device..."), this);
openCameraAction->setShortcut(Qt::CTRL + Qt::Key_C);
openCameraAction->setIcon(QIcon(":/add-camera"));
openCameraAction->setIconVisibleInMenu(false);
openCameraAction->setToolTip(tr("Choose your camera device..."));
openCameraAction->setShortcutContext(Qt::ApplicationShortcut);
addAction(openCameraAction);
connect(openCameraAction, SIGNAL(triggered()), this, SLOT(openCameraDevice()));
#endif
AddCameraAction = new QAction(tr("Open &Camera Device..."), this);
AddCameraAction->setShortcut(Qt::CTRL + Qt::Key_C);
AddCameraAction->setIcon(QIcon(":/add-camera"));
AddCameraAction->setIconVisibleInMenu(false);
AddCameraAction->setToolTip(tr("Choose your camera device..."));
AddCameraAction->setShortcutContext(Qt::ApplicationShortcut);
addAction(AddCameraAction);
connect(AddCameraAction, SIGNAL(triggered()), this, SLOT(openCameraDevice()));
// Add color.
addColorAction = new QAction(tr("Add &Color Source..."), this);
@@ -2128,9 +2153,7 @@ void MainWindow::createMenus()
fileMenu->addAction(saveAsAction);
fileMenu->addSeparator();
fileMenu->addAction(importMediaAction);
#ifdef Q_OS_LINUX
fileMenu->addAction(openCameraAction);
#endif
fileMenu->addAction(AddCameraAction);
fileMenu->addAction(addColorAction);
// Recent file separator
@@ -2292,9 +2315,7 @@ void MainWindow::createToolBars()
mainToolBar = addToolBar(tr("&Toolbar"));
mainToolBar->setMovable(false);
mainToolBar->addAction(importMediaAction);
#ifdef Q_OS_LINUX
mainToolBar->addAction(openCameraAction);
#endif
mainToolBar->addAction(AddCameraAction);
mainToolBar->addAction(addColorAction);
mainToolBar->addSeparator();
@@ -2302,7 +2323,6 @@ void MainWindow::createToolBars()
mainToolBar->addAction(addMeshAction);
mainToolBar->addAction(addTriangleAction);
mainToolBar->addAction(addEllipseAction);
mainToolBar->addSeparator();
mainToolBar->addAction(outputFullScreenAction);
@@ -2689,7 +2709,7 @@ void MainWindow::clearRecentFileList()
// {
// }
bool MainWindow::importMediaFile(const QString &fileName, bool isImage)
bool MainWindow::importMediaFile(const QString &fileName, bool isImage, bool isCamera)
{
QFile file(fileName);
QDir currentDir;
@@ -2698,11 +2718,11 @@ bool MainWindow::importMediaFile(const QString &fileName, bool isImage)
if (!fileSupported(fileName, isImage))
return false;
if (fileName.startsWith(QString("/dev/video"))) {
if (isCamera) {
type = VIDEO_WEBCAM;
}
if (!file.open(QIODevice::ReadOnly)) {
if (!isCamera && !file.open(QIODevice::ReadOnly)) {
if (file.isSequential()) {
type = VIDEO_SHMSRC;
}
@@ -2729,14 +2749,16 @@ bool MainWindow::importMediaFile(const QString &fileName, bool isImage)
QApplication::restoreOverrideCursor();
if (!isImage && type != VIDEO_WEBCAM)
{
settings.setValue("defaultVideoDir", currentDir.absoluteFilePath(fileName));
setCurrentVideo(fileName);
}
else
{
settings.setValue("defaultImageDir", currentDir.absoluteFilePath(fileName));
if (!isCamera) { // Do not add camera to recents files
if (!isImage)
{
settings.setValue("defaultVideoDir", currentDir.absoluteFilePath(fileName));
setCurrentVideo(fileName);
}
else
{
settings.setValue("defaultImageDir", currentDir.absoluteFilePath(fileName));
}
}
statusBar()->showMessage(tr("File imported"), 2000);
@@ -2772,12 +2794,12 @@ void MainWindow::addPaintItem(uid paintId, const QIcon& icon, const QString& nam
// Create paint gui.
PaintGui::ptr paintGui;
QString paintType = paint->getType();
if (paintType == "media")
SourceType paintType = paint->getSourceType();
if (paintType == SourceType::Video)
paintGui = PaintGui::ptr(new VideoGui(paint));
else if (paintType == "image")
else if (paintType == SourceType::Image)
paintGui = PaintGui::ptr(new ImageGui(paint));
else if (paintType == "color")
else if (paintType == SourceType::Color)
paintGui = PaintGui::ptr(new ColorGui(paint));
else
paintGui = PaintGui::ptr(new PaintGui(paint));
@@ -2856,13 +2878,13 @@ void MainWindow::addMappingItem(uid mappingId)
QString defaultName;
QIcon icon;
QString shapeType = mapping->getShape()->getType();
QString paintType = mapping->getPaint()->getType();
ShapeType shapeType = mapping->getShape()->getType();
SourceType paintType = mapping->getPaint()->getSourceType();
// Add mapper.
// XXX hardcoded for textures
QSharedPointer<TextureMapping> textureMapping;
if (paintType == "media" || paintType == "image")
if (paintType == SourceType::Video || paintType == SourceType::Image)
{
textureMapping = qSharedPointerCast<TextureMapping>(mapping);
Q_CHECK_PTR(textureMapping);
@@ -2873,31 +2895,31 @@ void MainWindow::addMappingItem(uid mappingId)
// XXX Branching on nVertices() is crap
// Triangle
if (shapeType == "triangle")
if (shapeType == ShapeType::Triangle)
{
defaultName = QString("Triangle %1").arg(mappingId);
icon = QIcon(":/shape-triangle");
if (paintType == "color")
if (paintType == SourceType::Color)
mapper = MappingGui::ptr(new PolygonColorMappingGui(mapping));
else
mapper = MappingGui::ptr(new TriangleTextureMappingGui(textureMapping));
}
// Mesh
else if (shapeType == "mesh")
else if (shapeType == ShapeType::Mesh)
{
defaultName = QString("Mesh %1").arg(mappingId);
icon = QIcon(":/shape-mesh");
if (paintType == "color")
if (paintType == SourceType::Color)
mapper = MappingGui::ptr(new MeshColorMappingGui(mapping));
else
mapper = MappingGui::ptr(new MeshTextureMappingGui(textureMapping));
}
else if (shapeType == "ellipse")
else if (shapeType == ShapeType::Ellipse)
{
defaultName = QString("Ellipse %1").arg(mappingId);
icon = QIcon(":/shape-ellipse");
if (paintType == "color")
if (paintType == SourceType::Color)
mapper = MappingGui::ptr(new EllipseColorMappingGui(mapping));
else
mapper = MappingGui::ptr(new EllipseTextureMappingGui(textureMapping));
@@ -3270,7 +3292,7 @@ void MainWindow::showMappingContextMenu(const QPoint &point)
mappingHideAction->setChecked(!mapping->isVisible());
mappingSoloAction->setChecked(mapping->isSolo());
if (objectSender != NULL) {
if (objectSender != nullptr) {
if (sender() == mappingItemDelegate) // XXX: The item delegate is not a widget
mappingContextMenu->exec(mappingList->mapToGlobal(point));
else
@@ -3282,7 +3304,7 @@ void MainWindow::showPaintContextMenu(const QPoint &point)
{
QWidget *objectSender = dynamic_cast<QWidget*>(sender());
if (objectSender != NULL && paintList->count() > 0)
if (objectSender != nullptr && paintList->count() > 0)
paintContextMenu->exec(objectSender->mapToGlobal(point));
}
@@ -3570,6 +3592,11 @@ void MainWindow::updateSettings()
stickyVerticesAction->setChecked(settings.value("stickyVertices").toBool());
}
void MainWindow::updateMappingListColumnWidth()
{
mappingList->setColumnWidth(1, mappingList->horizontalHeader()->width() - (MM::MAPPING_LIST_HIDE_COLUMN + MM::MAPPING_LIST_BUTTONS_COLUMN));
}
// void MainWindow::applyOscCommand(const QVariantList& command)
// {
// bool VERBOSE = true;
+7 -2
View File
@@ -166,6 +166,8 @@ private slots:
void updateSettings();
void updateMappingListColumnWidth();
public slots:
// CRUD.
@@ -304,7 +306,7 @@ public:
bool saveFile(const QString &fileName);
void setCurrentFile(const QString &fileName);
void setCurrentVideo(const QString &filename);
bool importMediaFile(const QString &fileName, bool isImage);
bool importMediaFile(const QString &fileName, bool isImage = false, bool isCamera = false);
bool addColorPaint(const QColor& color);
void addMappingItem(uid mappingId);
void removeMappingItem(uid mappingId);
@@ -378,7 +380,7 @@ private:
QAction *newAction;
QAction *openAction;
QAction *importMediaAction;
QAction *openCameraAction;
QAction *AddCameraAction;
QAction *addColorAction;
QAction *saveAction;
QAction *saveAsAction;
@@ -553,6 +555,9 @@ private:
QLabel *mousePosLabel;
QLabel *trueFramesPerSecondsLabel;
typedef Paint::SourceType SourceType;
typedef MShape::ShapeType ShapeType ;
public:
// Accessor/mutators for the view. ///////////////////////////////////////////////////////////////////
MappingManager& getMappingManager() const { return *mappingManager; }
+2 -2
View File
@@ -184,7 +184,7 @@ QWidget *MappingItemDelegate::createEditor(QWidget *parent,
}
else
{
return 0;
return nullptr;
}
}
@@ -205,7 +205,7 @@ void MappingItemDelegate::setModelData(QWidget *editor, QAbstractItemModel *mode
void MappingItemDelegate::updateEditorGeometry(QWidget *editor,
const QStyleOptionViewItem &option, const QModelIndex &index) const
{
Q_UNUSED(index);
Q_UNUSED(index)
editor->setGeometry(option.rect);
}
+7 -7
View File
@@ -39,17 +39,17 @@ class MappingItemDelegate : public QStyledItemDelegate
Q_OBJECT
public:
MappingItemDelegate(QObject *parent = 0);
MappingItemDelegate(QObject *parent = nullptr);
void paint(QPainter *painter, const QStyleOptionViewItem &option,
const QModelIndex &index) const Q_DECL_OVERRIDE;
const QModelIndex &index) const override;
QWidget *createEditor(QWidget *parent, const QStyleOptionViewItem &option,
const QModelIndex &index) const Q_DECL_OVERRIDE;
void setEditorData(QWidget *editor, const QModelIndex &index) const Q_DECL_OVERRIDE;
const QModelIndex &index) const override;
void setEditorData(QWidget *editor, const QModelIndex &index) const override;
void setModelData(QWidget *editor, QAbstractItemModel *model,
const QModelIndex &index) const Q_DECL_OVERRIDE;
const QModelIndex &index) const override;
void updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option,
const QModelIndex &index) const Q_DECL_OVERRIDE;
const QModelIndex &index) const override;
signals:
void itemContextMenuRequested(const QPoint &pos);
@@ -58,7 +58,7 @@ signals:
protected:
bool editorEvent(QEvent *event, QAbstractItemModel *model,
const QStyleOptionViewItem &option, const QModelIndex &index) Q_DECL_OVERRIDE;
const QStyleOptionViewItem &option, const QModelIndex &index) override;
};
}
+16 -17
View File
@@ -31,7 +31,7 @@ int MappingListModel::rowCount(const QModelIndex &parent) const
int MappingListModel::columnCount(const QModelIndex &parent) const
{
Q_UNUSED(parent);
Q_UNUSED(parent)
return 3;
}
@@ -43,39 +43,38 @@ QVariant MappingListModel::data(const QModelIndex &index, int role) const
switch (role) {
case Qt::CheckStateRole:
return mappingList.at(index.row()).isVisible ? Qt::Checked : Qt::Unchecked;
break;
case Qt::SizeHintRole:
if (index.column() == MM::HideColumn)
return QSize(24, 40);
// if (index.column() == MM::IconAndNameColum)
// return QSize(135, 40);
else if (index.column() == MM::GroupButtonColum)
return QSize(128, 40);
break;
return QSize(MM::MAPPING_LIST_HIDE_COLUMN, 40);
if (index.column() == MM::IconAndNameColum)
return QSize(MM::MAPPING_LIST_NAME_COLUMN, 40);
if (index.column() == MM::GroupButtonColum)
return QSize(MM::MAPPING_LIST_BUTTONS_COLUMN, 40);
break;
case Qt::CheckStateRole + 1:
return mappingList.at(index.row()).isSolo ? Qt::Checked : Qt::Unchecked;
break;
case Qt::CheckStateRole + 2:
return mappingList.at(index.row()).isLocked ? Qt::Checked : Qt::Unchecked;
break;
case Qt::UserRole:
return QVariant(mappingList.at(index.row()).id);
break;
case Qt::EditRole:
return QVariant(mappingList.at(index.row()).label);
break;
case Qt::DisplayRole:
return QVariant(mappingList.at(index.row()).label);
break;
case Qt::DecorationRole:
return mappingList.at(index.row()).icon;
break;
case Qt::ToolTipRole:
return QString("ID: %1").arg(mappingList.at(index.row()).id);
break;
default:
return QVariant();
break;
}
return QVariant();
@@ -84,7 +83,7 @@ QVariant MappingListModel::data(const QModelIndex &index, int role) const
Qt::ItemFlags MappingListModel::flags(const QModelIndex &index) const
{
if (!index.isValid())
return 0;
return Qt::NoItemFlags;
if (index.column() == MM::IconAndNameColum)
return Qt::ItemIsEnabled | Qt::ItemIsSelectable |
+11 -11
View File
@@ -38,22 +38,22 @@ class MappingListModel : public QAbstractTableModel
Q_OBJECT
public:
MappingListModel(QObject *parent = 0);
~MappingListModel() {}
MappingListModel(QObject *parent = nullptr);
~MappingListModel() override {}
int rowCount(const QModelIndex & parent = QModelIndex()) const Q_DECL_OVERRIDE;
int columnCount(const QModelIndex & parent = QModelIndex()) const Q_DECL_OVERRIDE;
QVariant data(const QModelIndex &index, int role) const Q_DECL_OVERRIDE;
int rowCount(const QModelIndex & parent = QModelIndex()) const override;
int columnCount(const QModelIndex & parent = QModelIndex()) const override;
QVariant data(const QModelIndex &index, int role) const override;
Qt::ItemFlags flags(const QModelIndex &index) const Q_DECL_OVERRIDE;
Qt::DropActions supportedDropActions() const Q_DECL_OVERRIDE;
Qt::ItemFlags flags(const QModelIndex &index) const override;
Qt::DropActions supportedDropActions() const override;
QStringList mimeTypes() const Q_DECL_OVERRIDE;
QMimeData *mimeData(const QModelIndexList &indexes) const Q_DECL_OVERRIDE;
QStringList mimeTypes() const override;
QMimeData *mimeData(const QModelIndexList &indexes) const override;
bool dropMimeData(const QMimeData *data, Qt::DropAction action,
int row, int column, const QModelIndex &parent) Q_DECL_OVERRIDE;
int row, int column, const QModelIndex &parent) override;
bool setData(const QModelIndex &index, const QVariant &value, int role) Q_DECL_OVERRIDE;
bool setData(const QModelIndex &index, const QVariant &value, int role) override;
void removeItem(int index);
void addItem(Mapping::ptr mapping, const QIcon &icon, const QString &label);
+1 -1
View File
@@ -61,7 +61,7 @@ public:
sanitize();
}
virtual QString getType() const { return "ellipse"; }
virtual ShapeType getType() const { return ShapeType::Ellipse; }
qreal getRotationRadians() const
{
+1 -1
View File
@@ -51,7 +51,7 @@ public:
virtual void build();
virtual QString getType() const { return "mesh"; }
virtual ShapeType getType() const { return ShapeType::Mesh; }
/// Returns a polygon that is formed by all the contour points of the mesh.
virtual QPolygonF toPolygon() const;
+1 -1
View File
@@ -45,7 +45,7 @@ public:
}
virtual ~Quad() {}
virtual QString getType() const { return "quad"; }
virtual ShapeType getType() const { return ShapeType::Quad; }
protected:
/// Returns a new MShape (using default constructor).
+5 -1
View File
@@ -66,6 +66,10 @@ public:
Vertical
};
enum ShapeType {
Mesh, Triangle, Ellipse, Quad
};
typedef QSharedPointer<MShape> ptr;
MShape() : _isLocked(false) {}
@@ -97,7 +101,7 @@ public:
virtual void applyTransform(const QTransform& transform);
virtual QString getType() const = 0;
virtual ShapeType getType() const = 0;
/** Return true if Shape includes point (x,y), false otherwise
* Algorithm should work for all polygons, including non-convex
+1 -1
View File
@@ -41,7 +41,7 @@ public:
build();
}
virtual ~Triangle() {}
virtual QString getType() const { return "triangle"; }
virtual ShapeType getType() const { return ShapeType::Triangle; }
protected:
/// Returns a new MShape (using default constructor).
+2
View File
@@ -76,6 +76,8 @@ win32 {
$${GST_HOME}/lib/gstreamer-1.0.lib \
$${GST_HOME}/lib/gobject-2.0.lib \
$${GST_HOME}/lib/glib-2.0.lib \
$${GST_HOME}/lib/gstaudio-1.0.lib \
$${GST_HOME}/lib/gstvideo-1.0.lib \
-lopengl32
CONFIG -= debug