2017-11-12 17:21:50 +01:00
|
|
|
#include "widgets/helper/splitheader.hpp"
|
2018-01-17 16:52:51 +01:00
|
|
|
#include "singletons/resourcemanager.hpp"
|
2017-12-31 00:50:07 +01:00
|
|
|
#include "singletons/thememanager.hpp"
|
2017-09-16 00:05:06 +02:00
|
|
|
#include "twitch/twitchchannel.hpp"
|
2018-01-13 04:05:38 +01:00
|
|
|
#include "util/layoutcreator.hpp"
|
2017-09-15 17:23:49 +02:00
|
|
|
#include "util/urlfetch.hpp"
|
2017-11-12 17:21:50 +01:00
|
|
|
#include "widgets/split.hpp"
|
|
|
|
#include "widgets/splitcontainer.hpp"
|
2017-12-23 22:17:38 +01:00
|
|
|
#include "widgets/tooltipwidget.hpp"
|
2017-01-01 02:30:42 +01:00
|
|
|
|
2017-01-15 16:38:30 +01:00
|
|
|
#include <QByteArray>
|
|
|
|
#include <QDrag>
|
|
|
|
#include <QMimeData>
|
|
|
|
#include <QPainter>
|
|
|
|
|
2018-01-19 14:48:17 +01:00
|
|
|
#ifdef USEWEBENGINE
|
|
|
|
#include "widgets/streamview.hpp"
|
|
|
|
#endif
|
|
|
|
|
2017-04-14 17:52:22 +02:00
|
|
|
namespace chatterino {
|
|
|
|
namespace widgets {
|
2017-01-18 21:30:23 +01:00
|
|
|
|
2018-01-13 04:05:38 +01:00
|
|
|
SplitHeader::SplitHeader(Split *_split)
|
|
|
|
: BaseWidget(_split)
|
|
|
|
, split(_split)
|
2017-01-01 02:30:42 +01:00
|
|
|
{
|
2017-12-23 22:17:38 +01:00
|
|
|
this->setMouseTracking(true);
|
|
|
|
|
2018-01-17 16:52:51 +01:00
|
|
|
singletons::ResourceManager &resourceManager = singletons::ResourceManager::getInstance();
|
|
|
|
|
2018-01-13 04:05:38 +01:00
|
|
|
util::LayoutCreator<SplitHeader> layoutCreator(this);
|
|
|
|
auto layout = layoutCreator.emplace<QHBoxLayout>().withoutMargin();
|
|
|
|
{
|
|
|
|
// dropdown label
|
2018-01-17 16:52:51 +01:00
|
|
|
auto dropdown = layout.emplace<RippleEffectButton>(this).assign(&this->dropdownButton);
|
2018-01-13 04:05:38 +01:00
|
|
|
dropdown->setMouseTracking(true);
|
2018-01-17 16:52:51 +01:00
|
|
|
dropdown->setPixmap(resourceManager.splitHeaderContext->getPixmap());
|
2018-01-13 04:05:38 +01:00
|
|
|
this->addDropdownItems(dropdown.getElement());
|
2018-01-17 16:52:51 +01:00
|
|
|
QObject::connect(dropdown.getElement(), &RippleEffectButton::clicked, this, [this] {
|
2018-01-13 04:05:38 +01:00
|
|
|
QTimer::singleShot(80, [&] {
|
|
|
|
this->dropdownMenu.move(
|
2018-01-17 16:52:51 +01:00
|
|
|
this->dropdownButton->mapToGlobal(QPoint(0, this->dropdownButton->height())));
|
2018-01-13 04:05:38 +01:00
|
|
|
this->dropdownMenu.show();
|
|
|
|
});
|
|
|
|
});
|
|
|
|
|
2018-01-14 22:24:21 +01:00
|
|
|
layout->addStretch(1);
|
|
|
|
|
2018-01-13 04:05:38 +01:00
|
|
|
// channel name label
|
|
|
|
auto title = layout.emplace<SignalLabel>().assign(&this->titleLabel);
|
|
|
|
title->setMouseTracking(true);
|
|
|
|
QObject::connect(this->titleLabel, &SignalLabel::mouseDoubleClick, this,
|
|
|
|
&SplitHeader::mouseDoubleClickEvent);
|
|
|
|
|
2018-01-14 22:24:21 +01:00
|
|
|
layout->addStretch(1);
|
|
|
|
|
2018-01-13 04:05:38 +01:00
|
|
|
// moderation mode
|
2018-01-17 16:52:51 +01:00
|
|
|
auto moderator = layout.emplace<RippleEffectButton>(this).assign(&this->moderationButton);
|
|
|
|
|
|
|
|
QObject::connect(moderator.getElement(), &RippleEffectButton::clicked, this, [this] {
|
|
|
|
this->split->setModerationMode(!this->split->getModerationMode());
|
|
|
|
});
|
|
|
|
|
|
|
|
this->updateModerationModeIcon();
|
2018-01-13 04:05:38 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
// ---- misc
|
|
|
|
this->layout()->setMargin(0);
|
2017-07-02 14:28:37 +02:00
|
|
|
this->refreshTheme();
|
|
|
|
|
2017-06-11 09:11:55 +02:00
|
|
|
this->updateChannelText();
|
2017-01-15 16:38:30 +01:00
|
|
|
|
2017-11-04 14:57:29 +01:00
|
|
|
this->initializeChannelSignals();
|
|
|
|
|
2018-01-13 04:05:38 +01:00
|
|
|
this->split->channelChanged.connect([this]() {
|
2017-11-04 14:57:29 +01:00
|
|
|
this->initializeChannelSignals(); //
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
2018-01-13 04:05:38 +01:00
|
|
|
SplitHeader::~SplitHeader()
|
|
|
|
{
|
|
|
|
this->onlineStatusChangedConnection.disconnect();
|
|
|
|
}
|
|
|
|
|
2018-01-17 16:52:51 +01:00
|
|
|
void SplitHeader::addDropdownItems(RippleEffectButton *label)
|
2018-01-13 04:05:38 +01:00
|
|
|
{
|
|
|
|
// clang-format off
|
|
|
|
this->dropdownMenu.addAction("Add new split", this->split, &Split::doAddSplit, QKeySequence(tr("Ctrl+T")));
|
|
|
|
this->dropdownMenu.addAction("Close split", this->split, &Split::doCloseSplit, QKeySequence(tr("Ctrl+W")));
|
2018-01-17 02:04:10 +01:00
|
|
|
// this->dropdownMenu.addAction("Move split", this, SLOT(menuMoveSplit()));
|
2018-01-13 04:05:38 +01:00
|
|
|
this->dropdownMenu.addAction("Popup", this->split, &Split::doPopup);
|
|
|
|
this->dropdownMenu.addAction("Open viewer list", this->split, &Split::doOpenViewerList);
|
|
|
|
this->dropdownMenu.addSeparator();
|
2018-01-19 14:48:17 +01:00
|
|
|
#ifdef USEWEBENGINE
|
|
|
|
this->dropdownMenu.addAction("Start watching", this, [this]{
|
|
|
|
SharedChannel _channel = this->split->getChannel();
|
|
|
|
twitch::TwitchChannel *tc = dynamic_cast<twitch::TwitchChannel *>(_channel.get());
|
|
|
|
|
|
|
|
if (tc != nullptr) {
|
|
|
|
StreamView *view = new StreamView(_channel, "https://player.twitch.tv/?channel=" + tc->name);
|
|
|
|
view->setAttribute(Qt::WA_DeleteOnClose, true);
|
|
|
|
view->show();
|
|
|
|
}
|
|
|
|
});
|
|
|
|
#endif
|
2018-01-13 04:05:38 +01:00
|
|
|
this->dropdownMenu.addAction("Change channel", this->split, &Split::doChangeChannel, QKeySequence(tr("Ctrl+R")));
|
|
|
|
this->dropdownMenu.addAction("Clear chat", this->split, &Split::doClearChat);
|
2018-01-17 02:04:10 +01:00
|
|
|
this->dropdownMenu.addAction("Open in web browser", this->split, &Split::doOpenChannel);
|
2018-01-19 14:48:17 +01:00
|
|
|
#ifndef USEWEBENGINE
|
2018-01-17 03:18:47 +01:00
|
|
|
this->dropdownMenu.addAction("Open web player", this->split, &Split::doOpenPopupPlayer);
|
2018-01-19 14:48:17 +01:00
|
|
|
#endif
|
2018-01-13 04:05:38 +01:00
|
|
|
this->dropdownMenu.addAction("Open in Streamlink", this->split, &Split::doOpenStreamlink);
|
|
|
|
this->dropdownMenu.addSeparator();
|
|
|
|
this->dropdownMenu.addAction("Reload channel emotes", this, SLOT(menuReloadChannelEmotes()));
|
|
|
|
this->dropdownMenu.addAction("Manual reconnect", this, SLOT(menuManualReconnect()));
|
|
|
|
this->dropdownMenu.addSeparator();
|
|
|
|
this->dropdownMenu.addAction("Show changelog", this, SLOT(menuShowChangelog()));
|
|
|
|
// clang-format on
|
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::initializeChannelSignals()
|
2017-11-04 14:57:29 +01:00
|
|
|
{
|
|
|
|
// Disconnect any previous signal first
|
|
|
|
this->onlineStatusChangedConnection.disconnect();
|
|
|
|
|
2018-01-13 04:05:38 +01:00
|
|
|
auto channel = this->split->getChannel();
|
2017-11-04 14:57:29 +01:00
|
|
|
twitch::TwitchChannel *twitchChannel = dynamic_cast<twitch::TwitchChannel *>(channel.get());
|
|
|
|
|
|
|
|
if (twitchChannel) {
|
|
|
|
twitchChannel->onlineStatusChanged.connect([this]() {
|
|
|
|
this->updateChannelText(); //
|
|
|
|
});
|
|
|
|
}
|
2017-01-15 16:38:30 +01:00
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::resizeEvent(QResizeEvent *event)
|
2017-09-22 00:50:43 +02:00
|
|
|
{
|
2018-01-13 04:05:38 +01:00
|
|
|
int w = 28 * getDpiMultiplier();
|
|
|
|
|
|
|
|
this->setFixedHeight(w);
|
2018-01-17 16:52:51 +01:00
|
|
|
this->dropdownButton->setFixedWidth(w);
|
|
|
|
this->moderationButton->setFixedWidth(w);
|
2017-09-22 00:50:43 +02:00
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::updateChannelText()
|
2017-01-17 00:15:44 +01:00
|
|
|
{
|
2018-01-13 04:05:38 +01:00
|
|
|
const std::string channelName = this->split->channelName;
|
2017-07-09 17:49:02 +02:00
|
|
|
if (channelName.empty()) {
|
2018-01-13 04:05:38 +01:00
|
|
|
this->titleLabel->setText("<no channel>");
|
2017-07-09 17:49:02 +02:00
|
|
|
} else {
|
2018-01-13 04:05:38 +01:00
|
|
|
auto channel = this->split->getChannel();
|
2017-09-16 00:05:06 +02:00
|
|
|
|
|
|
|
twitch::TwitchChannel *twitchChannel = dynamic_cast<twitch::TwitchChannel *>(channel.get());
|
2017-09-22 00:50:43 +02:00
|
|
|
|
2017-09-20 18:12:29 +02:00
|
|
|
if (twitchChannel != nullptr && twitchChannel->isLive) {
|
2017-12-23 22:17:38 +01:00
|
|
|
this->isLive = true;
|
|
|
|
this->tooltip = "<style>.center { text-align: center; }</style>"
|
|
|
|
"<p class = \"center\">" +
|
|
|
|
twitchChannel->streamStatus + "<br><br>" + twitchChannel->streamGame +
|
|
|
|
"<br>"
|
|
|
|
"Live for " +
|
|
|
|
twitchChannel->streamUptime + " with " +
|
2018-01-13 04:05:38 +01:00
|
|
|
twitchChannel->streamViewerCount +
|
|
|
|
" viewers"
|
|
|
|
"</p>";
|
|
|
|
this->titleLabel->setText(QString::fromStdString(channelName) + " (live)");
|
2017-09-15 17:23:49 +02:00
|
|
|
} else {
|
2017-12-23 22:17:38 +01:00
|
|
|
this->isLive = false;
|
2018-01-13 04:05:38 +01:00
|
|
|
this->titleLabel->setText(QString::fromStdString(channelName));
|
2017-12-23 22:17:38 +01:00
|
|
|
this->tooltip = "";
|
2017-09-11 22:37:39 +02:00
|
|
|
}
|
2017-07-09 17:49:02 +02:00
|
|
|
}
|
2017-01-17 00:15:44 +01:00
|
|
|
}
|
|
|
|
|
2018-01-17 16:52:51 +01:00
|
|
|
void SplitHeader::updateModerationModeIcon()
|
|
|
|
{
|
|
|
|
singletons::ResourceManager &resourceManager = singletons::ResourceManager::getInstance();
|
|
|
|
this->moderationButton->setPixmap(this->split->getModerationMode()
|
|
|
|
? resourceManager.moderationmode_enabled->getPixmap()
|
|
|
|
: resourceManager.moderationmode_disabled->getPixmap());
|
2018-01-17 17:17:26 +01:00
|
|
|
|
2018-01-17 18:36:12 +01:00
|
|
|
bool modButtonVisible = false;
|
|
|
|
SharedChannel channel = this->split->getChannel();
|
|
|
|
|
|
|
|
twitch::TwitchChannel *tc = dynamic_cast<twitch::TwitchChannel *>(channel.get());
|
|
|
|
|
|
|
|
if (tc != nullptr && tc->hasModRights()) {
|
|
|
|
modButtonVisible = true;
|
|
|
|
}
|
|
|
|
|
|
|
|
this->moderationButton->setVisible(modButtonVisible);
|
2018-01-17 16:52:51 +01:00
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::paintEvent(QPaintEvent *)
|
2017-01-01 02:30:42 +01:00
|
|
|
{
|
|
|
|
QPainter painter(this);
|
|
|
|
|
2018-01-02 02:15:11 +01:00
|
|
|
painter.fillRect(rect(), this->themeManager.splits.header.background);
|
|
|
|
painter.setPen(this->themeManager.splits.header.border);
|
2017-01-01 02:30:42 +01:00
|
|
|
painter.drawRect(0, 0, width() - 1, height() - 1);
|
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::mousePressEvent(QMouseEvent *event)
|
2017-01-01 02:30:42 +01:00
|
|
|
{
|
2017-06-11 09:11:55 +02:00
|
|
|
this->dragging = true;
|
2017-01-01 02:30:42 +01:00
|
|
|
|
2017-06-11 09:11:55 +02:00
|
|
|
this->dragStart = event->pos();
|
2017-01-01 02:30:42 +01:00
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::mouseMoveEvent(QMouseEvent *event)
|
2017-01-01 02:30:42 +01:00
|
|
|
{
|
2017-12-23 22:17:38 +01:00
|
|
|
if (!this->dragging && this->isLive) {
|
|
|
|
auto tooltipWidget = TooltipWidget::getInstance();
|
2018-01-22 15:06:36 +01:00
|
|
|
tooltipWidget->moveTo(this, event->globalPos());
|
2017-12-23 22:17:38 +01:00
|
|
|
tooltipWidget->setText(tooltip);
|
|
|
|
tooltipWidget->show();
|
|
|
|
}
|
|
|
|
|
2017-06-11 09:11:55 +02:00
|
|
|
if (this->dragging) {
|
|
|
|
if (std::abs(this->dragStart.x() - event->pos().x()) > 12 ||
|
|
|
|
std::abs(this->dragStart.y() - event->pos().y()) > 12) {
|
2018-01-17 01:19:42 +01:00
|
|
|
this->split->drag();
|
|
|
|
this->dragging = false;
|
2017-01-01 02:30:42 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-12-23 22:17:38 +01:00
|
|
|
void SplitHeader::leaveEvent(QEvent *event)
|
|
|
|
{
|
|
|
|
TooltipWidget::getInstance()->hide();
|
|
|
|
BaseWidget::leaveEvent(event);
|
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::mouseDoubleClickEvent(QMouseEvent *event)
|
2017-01-17 00:15:44 +01:00
|
|
|
{
|
|
|
|
if (event->button() == Qt::LeftButton) {
|
2018-01-13 04:05:38 +01:00
|
|
|
this->split->doChangeChannel();
|
2017-01-17 00:15:44 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::rightButtonClicked()
|
2017-01-15 16:38:30 +01:00
|
|
|
{
|
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::refreshTheme()
|
2017-07-02 14:28:37 +02:00
|
|
|
{
|
|
|
|
QPalette palette;
|
2018-01-02 02:15:11 +01:00
|
|
|
palette.setColor(QPalette::Foreground, this->themeManager.splits.header.text);
|
2017-07-02 14:28:37 +02:00
|
|
|
|
2018-01-17 16:52:51 +01:00
|
|
|
// this->dropdownButton->setPalette(palette);
|
2018-01-13 04:05:38 +01:00
|
|
|
this->titleLabel->setPalette(palette);
|
2018-01-17 16:52:51 +01:00
|
|
|
// this->moderationLabel->setPalette(palette);
|
2017-07-02 14:28:37 +02:00
|
|
|
}
|
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::menuMoveSplit()
|
2017-01-15 16:38:30 +01:00
|
|
|
{
|
|
|
|
}
|
2017-06-10 23:53:39 +02:00
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::menuReloadChannelEmotes()
|
2017-01-15 16:38:30 +01:00
|
|
|
{
|
|
|
|
}
|
2017-06-10 23:53:39 +02:00
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::menuManualReconnect()
|
2017-01-15 16:38:30 +01:00
|
|
|
{
|
2018-01-17 15:07:55 +01:00
|
|
|
singletons::IrcManager::getInstance().connect();
|
2017-01-15 16:38:30 +01:00
|
|
|
}
|
2017-06-10 23:53:39 +02:00
|
|
|
|
2017-11-12 17:21:50 +01:00
|
|
|
void SplitHeader::menuShowChangelog()
|
2017-01-15 16:38:30 +01:00
|
|
|
{
|
|
|
|
}
|
2017-06-07 10:09:24 +02:00
|
|
|
|
|
|
|
} // namespace widgets
|
|
|
|
} // namespace chatterino
|