Commit 32e1913c authored by Andreas Traczyk's avatar Andreas Traczyk

call view: refactor animation code out of video overlay

- Creates some helper classes that extend QPropertyAnimation to harness
  QGraphicsOpacityEffect for fading in/out drawable objects.

- Moves fading animation logic from video overlay to an extended
  QWidget helper class.

- Adds a vignette to video view, and reorders the drawn layers.

Change-Id: I1b29113805deb8a565059a5369be0d7918350df7
parent d5e3a903
/***************************************************************************
* Copyright (C) 2019-2019 by Savoir-faire Linux *
* Copyright (C) 2019 by Savoir-faire Linux *
* Author: Andreas Traczyk <andreas.traczyk@savoirfairelinux.com> *
* *
* This program is free software; you can redistribute it and/or modify *
......@@ -18,113 +18,42 @@
#include "animationhelpers.h"
#include "ui_animatedoverlay.h"
#include <QGraphicsOpacityEffect>
#include <QTimer>
#include <QtMath>
OpacityAnimation::OpacityAnimation(QWidget* target, QObject* parent)
: QObject(parent),
target_(target),
timer_(nullptr),
frameTime_((1.0 / 24.0) * 1000),
startValue_(0.0),
endValue_(1.0),
t_(0),
value_(0),
duration_(1000)
{
timer_ = new QTimer(this);
connect(timer_, SIGNAL(timeout()), this, SLOT(updateAnimation()));
effect_ = new QGraphicsOpacityEffect(this);
effect_->setOpacity(startValue_);
target_->setGraphicsEffect(effect_);
target_->setAutoFillBackground(true);
}
OpacityAnimation::~OpacityAnimation()
{
}
void
OpacityAnimation::setFPS(const int& fps)
OpacityAnimation::OpacityAnimation(QWidget* target)
: QPropertyAnimation(target)
{
frameTime_ = (1.0 / static_cast<double>(fps)) * 1000;
auto effect = new QGraphicsOpacityEffect(target);
target->setGraphicsEffect(effect);
setTargetObject(effect);
setPropertyName("opacity");
}
void
OpacityAnimation::setFrameTime(const int& milliseconds)
OpacityAnimation::reset()
{
frameTime_ = milliseconds;
stop();
targetObject()->setProperty(propertyName(), startValue());
}
void
OpacityAnimation::setDuration(const int& milliseconds)
{
duration_ = milliseconds;
}
void
OpacityAnimation::setStartValue(const double& value)
{
startValue_ = value;
effect_->setOpacity(startValue_);
}
void
OpacityAnimation::setEndValue(const double& value)
{
endValue_ = value;
}
void
OpacityAnimation::start()
{
timer_->start(frameTime_);
}
void
OpacityAnimation::stop()
{
timer_->stop();
}
void
OpacityAnimation::updateAnimation()
{
double d = (startValue_ + endValue_) * 0.5;
double a = abs(startValue_ - endValue_) * 0.5;
t_ += frameTime_;
value_ = a * sin(2 * M_PI * t_ * duration_ * .000001) + d;
effect_->setOpacity(value_);
target_->update();
}
AnimatedOverlay::AnimatedOverlay(QColor color, QWidget* parent) :
QWidget(parent),
ui(new Ui::AnimatedOverlay)
{
ui->setupUi(this);
ui->backgroundLabel->setAutoFillBackground(true);
auto values = QString("%1,%2,%3,255")
.arg(color.red())
.arg(color.green())
.arg(color.blue());
ui->backgroundLabel->setStyleSheet("background-color: rgba(" + values + ");");
oa_ = new OpacityAnimation(this, this);
oa_->setFPS(16);
oa_->setDuration(1000);
oa_->setStartValue(0.0);
oa_->setEndValue(0.25);
oa_->start();
}
AnimatedOverlay::~AnimatedOverlay()
{
disconnect(this);
delete ui;
}
OpacityAnimation::~OpacityAnimation()
{}
FadeAnimation::FadeAnimation(QWidget* target,
const quint64 duration,
const qreal minOpacity,
const qreal maxOpacity,
const QEasingCurve curve)
: OpacityAnimation(target)
{
if (auto effect = qobject_cast<QGraphicsOpacityEffect*>(targetObject())) {
effect->setOpacity(maxOpacity);
}
setDuration(duration);
setStartValue(maxOpacity);
setEndValue(minOpacity);
setEasingCurve(curve);
}
FadeAnimation::~FadeAnimation()
{}
/***************************************************************************
* Copyright (C) 2019-2019 by Savoir-faire Linux *
* Copyright (C) 2019 by Savoir-faire Linux *
* Author: Andreas Traczyk <andreas.traczyk@savoirfairelinux.com> *
* *
* This program is free software; you can redistribute it and/or modify *
......@@ -20,55 +20,33 @@
#include <QWidget>
#include <QPropertyAnimation>
#include <QGraphicsOpacityEffect>
#include <QMovie>
class OpacityAnimation : public QObject
// TODO: fix when changing Qt version
// Full(1.0) opacity bug affecting many Qt versions (macOS + win10)
// causing the render to take a buggy code path which can be avoided
// by using opacity values other than precisely 1.0.
// https://bugreports.qt.io/browse/QTBUG-65981
// https://bugreports.qt.io/browse/QTBUG-66803
constexpr static qreal MAX_OPACITY { 0.9999999999980000442 };
class OpacityAnimation : public QPropertyAnimation
{
Q_OBJECT
public:
explicit OpacityAnimation(QWidget* target, QObject* parent = nullptr);
~OpacityAnimation();
void setFPS(const int& fps);
void setFrameTime(const int& milliseconds);
void setDuration(const int& milliseconds);
void setStartValue(const double& value);
void setEndValue(const double& value);
void start();
void stop();
private slots:
void updateAnimation();
private:
QGraphicsOpacityEffect* effect_;
double value_;
explicit OpacityAnimation(QWidget* target);
virtual ~OpacityAnimation();
QWidget* target_;
QTimer* timer_;
int frameTime_;
double t_;
int duration_;
double startValue_;
double endValue_;
void reset();
};
namespace Ui {
class AnimatedOverlay;
}
class AnimatedOverlay : public QWidget
class FadeAnimation : public OpacityAnimation
{
Q_OBJECT
public:
explicit AnimatedOverlay(QColor color, QWidget* parent = 0);
~AnimatedOverlay();
private:
Ui::AnimatedOverlay* ui;
OpacityAnimation* oa_;
explicit FadeAnimation(QWidget* target,
const quint64 duration = 1000,
const qreal minOpacity = 0.0,
const qreal maxOpacity = MAX_OPACITY,
const QEasingCurve curve = QEasingCurve::OutQuad);
~FadeAnimation();
};
\ No newline at end of file
......@@ -81,7 +81,8 @@ HEADERS += ./aboutdialog.h \
./videowidgetbase.h \
./section.h \
./collapsiblepasswordwidget.h \
./notifypushbutton.h
./notifypushbutton.h \
./widgethelpers.h \
SOURCES += ./aboutdialog.cpp \
./banneditemwidget.cpp \
./conversationsfilterwidget.cpp \
......@@ -98,6 +99,7 @@ SOURCES += ./aboutdialog.cpp \
./ringcontactlineedit.cpp \
./splashscreen.cpp \
./videowidget.cpp \
./animationhelpers.cpp \
./accountlistmodel.cpp \
./bezierconnectorwidget.cpp \
./deleteaccountdialog.cpp \
......@@ -144,7 +146,8 @@ SOURCES += ./aboutdialog.cpp \
./videowidgetbase.cpp \
./section.cpp \
./collapsiblepasswordwidget.cpp \
./notifypushbutton.cpp
./notifypushbutton.cpp \
./widgethelpers.cpp \
FORMS += ./aboutdialog.ui \
./advancedsipsettingwidget.ui \
./callwidget.ui \
......
......@@ -448,8 +448,24 @@ del /s /q $(OutDir)\Jami.exp</Command>
<ClCompile Include="updateconfirmdialog.cpp" />
<ClCompile Include="videowidgetbase.cpp" />
<ClCompile Include="webchathelpers.cpp" />
<ClCompile Include="widgethelpers.cpp">
<OutputFile Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.\GeneratedFiles\$(ConfigurationName)\%(Filename).moc</OutputFile>
<DynamicSource Condition="'$(Configuration)|$(Platform)'=='Release|x64'">input</DynamicSource>
<IncludePath Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;$(ProjectDir)..\ring-daemon\contrib\msvc\include;$(ProjectDir)..\daemon\contrib\msvc\include;$(ProjectDir)..\ring-lrc\src;$(ProjectDir)..\lrc\src;$(ProjectDir)qrencode-win32\qrencode-win32;$(QTDIR)\include;$(QTDIR)\include\QtSvg;$(QTDIR)\include\QtWidgets;$(QTDIR)\include\QtWinExtras;$(QTDIR)\include\QtGui;$(QTDIR)\include\QtANGLE;$(QTDIR)\include\QtXml;$(QTDIR)\include\QtNetwork;$(QTDIR)\include\QtWebEngineWidgets;$(QTDIR)\include\QtWebChannel;$(QTDIR)\include\QtCore;$(QTDIR)\mkspecs\win32-msvc;.\release</IncludePath>
<OutputFile Condition="'$(Configuration)|$(Platform)'=='ReleaseCompile|x64'">.\GeneratedFiles\$(ConfigurationName)\%(Filename).moc</OutputFile>
<DynamicSource Condition="'$(Configuration)|$(Platform)'=='ReleaseCompile|x64'">input</DynamicSource>
<IncludePath Condition="'$(Configuration)|$(Platform)'=='ReleaseCompile|x64'">.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;$(ProjectDir)..\ring-daemon\contrib\msvc\include;$(ProjectDir)..\daemon\contrib\msvc\include;$(ProjectDir)..\ring-lrc\src;$(ProjectDir)..\lrc\src;$(ProjectDir)winsparkle\include;$(ProjectDir)qrencode-win32\qrencode-win32;$(QTDIR)\include;$(QTDIR)\include\QtSvg;$(QTDIR)\include\QtWidgets;$(QTDIR)\include\QtWinExtras;$(QTDIR)\include\QtGui;$(QTDIR)\include\QtANGLE;$(QTDIR)\include\QtXml;$(QTDIR)\include\QtNetwork;$(QTDIR)\include\QtWebEngineWidgets;$(QTDIR)\include\QtWebChannel;$(QTDIR)\include\QtCore;$(QTDIR)\mkspecs\win32-msvc;.\release</IncludePath>
<OutputFile Condition="'$(Configuration)|$(Platform)'=='Beta|x64'">.\GeneratedFiles\$(ConfigurationName)\%(Filename).moc</OutputFile>
<DynamicSource Condition="'$(Configuration)|$(Platform)'=='Beta|x64'">input</DynamicSource>
<IncludePath Condition="'$(Configuration)|$(Platform)'=='Beta|x64'">.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;$(ProjectDir)..\ring-daemon\contrib\msvc\include;$(ProjectDir)..\daemon\contrib\msvc\include;$(ProjectDir)..\ring-lrc\src;$(ProjectDir)..\lrc\src;$(ProjectDir)qrencode-win32\qrencode-win32;$(QTDIR)\include;$(QTDIR)\include\QtSvg;$(QTDIR)\include\QtWidgets;$(QTDIR)\include\QtWinExtras;$(QTDIR)\include\QtGui;$(QTDIR)\include\QtANGLE;$(QTDIR)\include\QtXml;$(QTDIR)\include\QtNetwork;$(QTDIR)\include\QtWebEngineWidgets;$(QTDIR)\include\QtWebChannel;$(QTDIR)\include\QtCore;$(QTDIR)\mkspecs\win32-msvc;.\release</IncludePath>
</ClCompile>
</ItemGroup>
<ItemGroup>
<QtMoc Include="widgethelpers.h">
<IncludePath Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;$(ProjectDir)..\ring-daemon\contrib\msvc\include;$(ProjectDir)..\daemon\contrib\msvc\include;$(ProjectDir)..\ring-lrc\src;$(ProjectDir)..\lrc\src;$(ProjectDir)qrencode-win32\qrencode-win32;$(QTDIR)\include;$(QTDIR)\include\QtSvg;$(QTDIR)\include\QtWidgets;$(QTDIR)\include\QtWinExtras;$(QTDIR)\include\QtGui;$(QTDIR)\include\QtANGLE;$(QTDIR)\include\QtXml;$(QTDIR)\include\QtNetwork;$(QTDIR)\include\QtWebEngineWidgets;$(QTDIR)\include\QtWebChannel;$(QTDIR)\include\QtCore;$(QTDIR)\mkspecs\win32-msvc;.\release</IncludePath>
<IncludePath Condition="'$(Configuration)|$(Platform)'=='ReleaseCompile|x64'">.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;$(ProjectDir)..\ring-daemon\contrib\msvc\include;$(ProjectDir)..\daemon\contrib\msvc\include;$(ProjectDir)..\ring-lrc\src;$(ProjectDir)..\lrc\src;$(ProjectDir)winsparkle\include;$(ProjectDir)qrencode-win32\qrencode-win32;$(QTDIR)\include;$(QTDIR)\include\QtSvg;$(QTDIR)\include\QtWidgets;$(QTDIR)\include\QtWinExtras;$(QTDIR)\include\QtGui;$(QTDIR)\include\QtANGLE;$(QTDIR)\include\QtXml;$(QTDIR)\include\QtNetwork;$(QTDIR)\include\QtWebEngineWidgets;$(QTDIR)\include\QtWebChannel;$(QTDIR)\include\QtCore;$(QTDIR)\mkspecs\win32-msvc;.\release</IncludePath>
<IncludePath Condition="'$(Configuration)|$(Platform)'=='Beta|x64'">.\GeneratedFiles\$(ConfigurationName);.\GeneratedFiles;.;$(ProjectDir)..\ring-daemon\contrib\msvc\include;$(ProjectDir)..\daemon\contrib\msvc\include;$(ProjectDir)..\ring-lrc\src;$(ProjectDir)..\lrc\src;$(ProjectDir)qrencode-win32\qrencode-win32;$(QTDIR)\include;$(QTDIR)\include\QtSvg;$(QTDIR)\include\QtWidgets;$(QTDIR)\include\QtWinExtras;$(QTDIR)\include\QtGui;$(QTDIR)\include\QtANGLE;$(QTDIR)\include\QtXml;$(QTDIR)\include\QtNetwork;$(QTDIR)\include\QtWebEngineWidgets;$(QTDIR)\include\QtWebChannel;$(QTDIR)\include\QtCore;$(QTDIR)\mkspecs\win32-msvc;.\release</IncludePath>
</QtMoc>
<QtMoc Include="aboutdialog.h">
</QtMoc>
<QtMoc Include="callwidget.h">
......@@ -981,4 +997,4 @@ del /s /q $(OutDir)\Jami.exp</Command>
<UserProperties UicDir=".\GeneratedFiles" RccDir=".\GeneratedFiles" Qt5Version_x0020_x64="$(DefaultQtVersion)" />
</VisualStudio>
</ProjectExtensions>
</Project>
</Project>
\ No newline at end of file
......@@ -252,6 +252,9 @@
<ClCompile Include="notifypushbutton.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="widgethelpers.cpp">
<Filter>Source Files</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<QtMoc Include="aboutdialog.h">
......@@ -446,6 +449,9 @@
<QtMoc Include="notifypushbutton.h">
<Filter>Header Files</Filter>
</QtMoc>
<QtMoc Include="widgethelpers.h">
<Filter>Header Files</Filter>
</QtMoc>
</ItemGroup>
<ItemGroup>
<CustomBuild Include="debug\moc_predefs.h.cbt">
......@@ -903,4 +909,4 @@
<Filter>Resource Files</Filter>
</Image>
</ItemGroup>
</Project>
</Project>
\ No newline at end of file
......@@ -27,20 +27,16 @@
#include "utils.h"
#include <QTime>
#include <QMouseEvent>
#include <QGraphicsOpacityEffect>
VideoOverlay::VideoOverlay(QWidget* parent) :
QWidget(parent),
ui(new Ui::VideoOverlay),
oneSecondTimer_(new QTimer(this)),
contactPicker_(new ContactPicker(this)),
sipInputPanel_(new SipInputPanel(this))
VideoOverlay::VideoOverlay(QWidget* parent)
: FadeOutable(parent)
, ui(new Ui::VideoOverlay)
, oneSecondTimer_(new QTimer(this))
, contactPicker_(new ContactPicker(this))
, sipInputPanel_(new SipInputPanel(this))
{
ui->setupUi(this);
setAttribute(Qt::WA_NoSystemBackground);
ui->bottomButtons->setMouseTracking(true);
ui->chatButton->setCheckable(true);
......@@ -65,70 +61,11 @@ VideoOverlay::VideoOverlay(QWidget* parent) :
this, &VideoOverlay::slotWillDoTransfer);
connect(sipInputPanel_, &SipInputPanel::sipInputPanelClicked,
this, &VideoOverlay::slotSIPInputPanelClicked);
// fading mechanism
auto effect = new QGraphicsOpacityEffect(this);
effect->setOpacity(maxOverlayOpacity_);
this->setGraphicsEffect(effect);
fadeAnim_ = new QPropertyAnimation(this);
fadeAnim_->setTargetObject(effect);
fadeAnim_->setPropertyName("opacity");
fadeAnim_->setDuration(fadeOverlayTime_);
fadeAnim_->setStartValue(effect->opacity());
fadeAnim_->setEndValue(0);
fadeAnim_->setEasingCurve(QEasingCurve::OutQuad);
// Setup the timer to start the fade when the mouse stops moving
fadeTimer_.setSingleShot(true);
connect(&fadeTimer_, SIGNAL(timeout()), this, SLOT(fadeOverlayOut()));
}
VideoOverlay::~VideoOverlay()
{
delete ui;
delete fadeAnim_;
}
void
VideoOverlay::enterEvent(QEvent* event)
{
Q_UNUSED(event);
showOverlay();
}
void
VideoOverlay::leaveEvent(QEvent* event)
{
Q_UNUSED(event);
fadeTimer_.start(startfadeOverlayTime_);
}
void
VideoOverlay::mouseMoveEvent(QMouseEvent* event)
{
Q_UNUSED(event);
// start/restart the timer after which the overlay will fade
if (fadeTimer_.isActive()) {
showOverlay();
} else {
fadeTimer_.start(startfadeOverlayTime_);
}
event->ignore();
}
void
VideoOverlay::showOverlay()
{
fadeAnim_->stop();
fadeAnim_->targetObject()->setProperty(fadeAnim_->propertyName(),
fadeAnim_->startValue());
}
void
VideoOverlay::fadeOverlayOut()
{
if (!shouldShowOverlay()) {
fadeAnim_->start(QAbstractAnimation::KeepWhenStopped);
}
}
void
......@@ -142,8 +79,7 @@ VideoOverlay::updateCall(const conversation::Info& convInfo)
QObject::connect(oneSecondTimer_, &QTimer::timeout,
this, &VideoOverlay::setTime);
oneSecondTimer_->start(1000);
showOverlay();
fadeTimer_.start(startfadeOverlayTime_);
resetOpacity();
// close chat panel
emit setChatVisibility(false);
......@@ -200,7 +136,7 @@ VideoOverlay::setTime()
}
bool
VideoOverlay::shouldShowOverlay()
VideoOverlay::shouldFadeOut()
{
auto callId = LRCInstance::getCallIdForConversationUid(convUid_, accountId_);
if (callId.empty() || !LRCInstance::getCurrentCallModel()->hasCall(callId)) {
......@@ -208,10 +144,10 @@ VideoOverlay::shouldShowOverlay()
}
auto callInfo = LRCInstance::getCurrentCallModel()->getCall(callId);
bool hoveringOnButtons = ui->bottomButtons->underMouse() || ui->topInfoBar->underMouse();
return hoveringOnButtons ||
(callInfo.status == lrc::api::call::Status::PAUSED) ||
contactPicker_->isActiveWindow() ||
sipInputPanel_->isActiveWindow();
return not (hoveringOnButtons ||
(callInfo.status == lrc::api::call::Status::PAUSED) ||
contactPicker_->isActiveWindow() ||
sipInputPanel_->isActiveWindow());
}
void
......
......@@ -18,6 +18,8 @@
#pragma once
#include "widgethelpers.h"
#include "api/conversationmodel.h"
#include <QWidget>
......@@ -35,7 +37,7 @@ class VideoOverlay;
using namespace lrc::api;
class VideoOverlay : public QWidget
class VideoOverlay : public FadeOutable
{
Q_OBJECT
......@@ -46,13 +48,14 @@ public:
void updateCall(const conversation::Info& convInfo);
void simulateShowChatview(bool checked);
bool shouldFadeOut() override;
signals:
void setChatVisibility(bool visible);
void holdStateChanged(bool state);
void videoMuteStateChanged(bool state);
private slots:
void fadeOverlayOut();
void setTime();
void on_hangupButton_clicked();
void on_chatButton_toggled(bool checked);
......@@ -68,11 +71,6 @@ private slots:
void slotCallWillJoinConference(const std::string& callId);
void slotSIPInputPanelClicked(const int& id);
protected:
void enterEvent(QEvent* event);
void leaveEvent(QEvent* event);
void mouseMoveEvent(QMouseEvent* event);
private:
Ui::VideoOverlay* ui;
......@@ -83,22 +81,4 @@ private:
ContactPicker* contactPicker_;
SipInputPanel* sipInputPanel_;
QTimer* oneSecondTimer_;
QTimer fadeTimer_;
QPropertyAnimation* fadeAnim_;
constexpr static int fadeOverlayTime_ = 1000; //msec
// Time before the overlay starts fading out after the mouse stops
// moving within the videoview.
constexpr static int startfadeOverlayTime_ = 2000; //msec
// TODO: fix when changing Qt version
// Full(1.0) opacity bug affecting many Qt versions (macOS + win10)
// causing the render to take a buggy code path which can be avoided
// by using opacity values other than precisely 1.0.
// https://bugreports.qt.io/browse/QTBUG-65981
// https://bugreports.qt.io/browse/QTBUG-66803
constexpr static qreal maxOverlayOpacity_ = 0.9999999999980000442;
bool shouldShowOverlay();
void showOverlay();
};
......@@ -22,6 +22,8 @@
#include "lrcinstance.h"
#include "utils.h"
#include "selectareadialog.h"
#include "videooverlay.h"
#include <QDesktopWidget>
#include <QFileDialog>
......@@ -35,19 +37,34 @@
#include <memory>
#include "selectareadialog.h"
#include "videooverlay.h"
VideoView::VideoView(QWidget* parent)
: QWidget(parent)
, ui(new Ui::VideoView)
{
ui->setupUi(this);
// video overlay
vignette_ = new VignetteWidget(this);
overlay_ = new VideoOverlay(this);
audioOnlyAvatar_ = new CallAudioOnlyAvatarOverlay(this);
previewWidget_ = new VideoCallPreviewWidget(this);
// setup layer order
vignette_->stackUnder(previewWidget_);
overlay_->raise();
overlay_->setMouseTracking(true);
// preview widget animation
moveAnim_ = new QPropertyAnimation(previewWidget_, "geometry");
moveAnim_->setDuration(250);
moveAnim_->setEasingCurve(QEasingCurve::OutExpo);
// this connects the vignette's opacity to the overlay
connect(overlay_, &FadeOutable::willFadeOut,
vignette_, &VignetteWidget::slotWillFadeOut);
connect(overlay_, &FadeOutable::willReset,
vignette_, &VignetteWidget::slotWillResetOpacity);
// context menu
this->setContextMenuPolicy(Qt::CustomContextMenu);
connect(this, SIGNAL(customContextMenuRequested(const QPoint&)),
......@@ -78,23 +95,11 @@ VideoView::VideoView(QWidget* parent)
this,
&VideoView::slotVideoMuteStateChanged,
Qt::UniqueConnection);
// audio only overlay
audioOnlyAvatar_ = new CallAudioOnlyAvatarOverlay(this);
// preview widget
previewWidget_ = new VideoCallPreviewWidget(this);
// preview widget animation
moveAnim_ = new QPropertyAnimation(previewWidget_, "geometry");
moveAnim_->setDuration(250);
moveAnim_->setEasingCurve(QEasingCurve::OutExpo);
}
VideoView::~VideoView()
{
delete ui;
delete overlay_;
}
void
......@@ -106,11 +111,9 @@ VideoView::resizeEvent(QResizeEvent* event)
resetPreview();
vignette_->resize(this->size());
audioOnlyAvatar_->resize(this->size());
overlay_->resize(this->size());
overlay_->show();
overlay_->raise();
}
void
......
......@@ -73,6 +73,9 @@ private:
std::string accountId_;
std::string convUid_;
// vignette
VignetteWidget* vignette_;
// overlay
VideoOverlay* overlay_;
// audio only overlay
......
/***************************************************************************
* Copyright (C) 2019 by Savoir-faire Linux *
* Author: Andreas Traczyk <andreas.traczyk@savoirfairelinux.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 "widgethelpers.h"
FadeOutable::FadeOutable(QWidget* parent)
: QWidget(parent)
{
setAttribute(Qt::WA_NoSystemBackground);
fadeAnimation_ = new FadeAnimation(this, fadeTime_);
fadeTimer_.setSingleShot(true);
connect(&fadeTimer_, SIGNAL(timeout()), this, SLOT(slotTimeout()));
}
FadeOutable::~FadeOutable()
{}
void
FadeOutable::resetOpacity()
{
fadeAnimation_->reset();
Q_EMIT willReset();
fadeTimer_.start(fadeDelay_);
}
void
FadeOutable::enterEvent(QEvent* event)
{
Q_UNUSED(event);
fadeAnimation_->reset();
Q_EMIT willReset();
event->ignore();
}
void
FadeOutable::leaveEvent(QEvent* event)
{
Q_UNUSED(event);
fadeTimer_.start(fadeDelay_);
event->ignore();
}
void
FadeOutable::mouseMoveEvent(QMouseEvent* event)
{
// start/restart the timer after which the widget will fade
fadeAnimation_->reset();
fadeTimer_.start(fadeDelay_);
Q_EMIT willReset();
event->ignore();
}
void
FadeOutable::slotTimeout()
{
if (!shouldFadeOut()) {
return;
}
fadeAnimation_->start();
Q_EMIT willFadeOut();
}
VignetteWidget::VignetteWidget(QWidget* parent)
: QWidget(parent)
{
setAttribute(Qt::WA_NoSystemBackground);
fadeOutAnimation_ = new FadeAnimation(this, fadeTime_);
}
VignetteWidget::~VignetteWidget()
{}
void
VignetteWidget::slotWillFadeOut()
{
fadeOutAnimation_->setDirection(QAbstractAnimation::Direction::Forward);
fadeOutAnimation_->start();
}
void
VignetteWidget::slotWillResetOpacity()
{
if (fadeOutAnimation_->direction() != QAbstractAnimation::Direction::Forward) {
return;
}
fadeOutAnimation_->setDirection(QAbstractAnimation::Direction::Backward);
fadeOutAnimation_->start();
}
void
VignetteWidget::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event);
QPainter painter(this);
painter.setRenderHints(QPainter::Antialiasing, true);
QLinearGradient gradient;
// top
gradient.setStart(0, rect().top());
gradient.setFinalStop(0, rect().top() + height_);
gradient.setColorAt(0, QColor(0, 0, 0, 96));
gradient.setColorAt(0.5, QColor(0, 0, 0, 32));
gradient.setColorAt(1, Qt::transparent);
painter.fillRect(rect(), gradient);
// bottom
gradient.setStart(0, rect().bottom() - height_);
gradient.setFinalStop(0, rect().bottom());
gradient.setColorAt(0, Qt::transparent);
gradient.setColorAt(0.5, QColor(0, 0, 0, 32));
gradient.setColorAt(1, QColor(0, 0, 0, 96));
painter.fillRect(rect(), gradient);
}
\ No newline at end of file
/***************************************************************************
* Copyright (C) 2019 by Savoir-faire Linux *
* Author: Andreas Traczyk <andreas.traczyk@savoirfairelinux.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. *
* *