Added Highlights (#86)

Added Highlights
This commit is contained in:
Cranken 2017-07-31 00:37:22 +02:00 committed by pajlada
parent 467ca90fd8
commit 8fb0671834
17 changed files with 245 additions and 12 deletions

View file

@ -4,7 +4,7 @@
# #
#------------------------------------------------- #-------------------------------------------------
QT += core gui network QT += core gui network multimedia
CONFIG += communi CONFIG += communi
COMMUNI += core model util COMMUNI += core model util
CONFIG += c++14 CONFIG += c++14

@ -1 +1 @@
Subproject commit d3faa9b3996e0871473b0e2b1821c93a50821f40 Subproject commit 1282c351db528f9e2f166b2bb1c217c9d67a8bc8

View file

@ -31,5 +31,6 @@
<file>images/StatusAnnotations_Blocked_16xLG_color.png</file> <file>images/StatusAnnotations_Blocked_16xLG_color.png</file>
<file>images/UserProfile_22x.png</file> <file>images/UserProfile_22x.png</file>
<file>images/VSO_Link_blue_16x.png</file> <file>images/VSO_Link_blue_16x.png</file>
<file>sounds/ping2.wav</file>
</qresource> </qresource>
</RCC> </RCC>

BIN
resources/sounds/ping2.wav Normal file

Binary file not shown.

View file

@ -29,9 +29,10 @@ Message::Message(const QString &text)
} }
*/ */
Message::Message(const QString &text, const std::vector<Word> &words) Message::Message(const QString &text, const std::vector<Word> &words, const bool &highlight)
: text(text) : text(text)
, words(words) , words(words)
, highlightTab(highlight)
{ {
} }

View file

@ -24,7 +24,7 @@ class Message
{ {
public: public:
// explicit Message(const QString &text); // explicit Message(const QString &text);
explicit Message(const QString &text, const std::vector<messages::Word> &words); explicit Message(const QString &text, const std::vector<messages::Word> &words, const bool &highlight);
bool getCanHighlightTab() const; bool getCanHighlightTab() const;
const QString &getTimeoutUser() const; const QString &getTimeoutUser() const;

View file

@ -16,7 +16,7 @@ MessageBuilder::MessageBuilder()
SharedMessage MessageBuilder::build() SharedMessage MessageBuilder::build()
{ {
return SharedMessage(new Message(this->originalMessage, _words)); return SharedMessage(new Message(this->originalMessage, _words,highlight));
} }
void MessageBuilder::appendWord(const Word &word) void MessageBuilder::appendWord(const Word &word)
@ -31,6 +31,10 @@ void MessageBuilder::appendTimestamp()
appendTimestamp(t); appendTimestamp(t);
} }
void MessageBuilder::setHighlight(const bool &value){
highlight = value;
}
void MessageBuilder::appendTimestamp(time_t time) void MessageBuilder::appendTimestamp(time_t time)
{ {
char timeStampBuffer[69]; char timeStampBuffer[69];

View file

@ -18,6 +18,7 @@ public:
void appendWord(const Word &word); void appendWord(const Word &word);
void appendTimestamp(); void appendTimestamp();
void appendTimestamp(std::time_t time); void appendTimestamp(std::time_t time);
void setHighlight(const bool &value);
QString matchLink(const QString &string); QString matchLink(const QString &string);
QRegularExpression regex; QRegularExpression regex;
@ -26,6 +27,7 @@ public:
private: private:
std::vector<Word> _words; std::vector<Word> _words;
bool highlight = false;
std::chrono::time_point<std::chrono::system_clock> _parseTime; std::chrono::time_point<std::chrono::system_clock> _parseTime;
}; };

View file

@ -43,6 +43,10 @@ public:
return _value; return _value;
} }
T &getnonConst() {
return _value;
}
void set(const T &newValue) void set(const T &newValue)
{ {
if (_value != newValue) { if (_value != newValue) {
@ -65,6 +69,12 @@ public:
} }
} }
void insertMap(QString id, bool sound, bool task){
QPair<bool,bool> pair(sound,task);
_value.insert(id,pair);
}
boost::signals2::signal<void(const T &newValue)> valueChanged; boost::signals2::signal<void(const T &newValue)> valueChanged;
private: private:

View file

@ -27,9 +27,12 @@ SettingsManager::SettingsManager()
, mentionUsersWithAt(_settingsItems, "mentionUsersWithAt", false) , mentionUsersWithAt(_settingsItems, "mentionUsersWithAt", false)
, allowCommandsAtEnd(_settingsItems, "allowCommandsAtEnd", false) , allowCommandsAtEnd(_settingsItems, "allowCommandsAtEnd", false)
, enableHighlights(_settingsItems, "enableHighlights", true) , enableHighlights(_settingsItems, "enableHighlights", true)
, enableHighlightsSelf(_settingsItems,"enableHighlightsSelf", true)
, enableHighlightSound(_settingsItems, "enableHighlightSound", true) , enableHighlightSound(_settingsItems, "enableHighlightSound", true)
, enableHighlightTaskbar(_settingsItems, "enableHighlightTaskbar", true) , enableHighlightTaskbar(_settingsItems, "enableHighlightTaskbar", true)
, customHighlightSound(_settingsItems, "customHighlightSound", false) , customHighlightSound(_settingsItems, "customHighlightSound", false)
, pathHighlightSound(_settingsItems, "pathHighlightSound", "qrc:/sounds/ping2.wav")
, highlightProperties(_settingsItems,"highlightProperties",QMap<QString,QPair<bool,bool>>())
, enableTwitchEmotes(_settingsItems, "enableTwitchEmotes", true) , enableTwitchEmotes(_settingsItems, "enableTwitchEmotes", true)
, enableBttvEmotes(_settingsItems, "enableBttvEmotes", true) , enableBttvEmotes(_settingsItems, "enableBttvEmotes", true)
, enableFfzEmotes(_settingsItems, "enableFfzEmotes", true) , enableFfzEmotes(_settingsItems, "enableFfzEmotes", true)
@ -61,17 +64,44 @@ SettingsManager::SettingsManager()
void SettingsManager::save() void SettingsManager::save()
{ {
for (auto &item : _settingsItems) { for (auto &item : _settingsItems) {
_settings.setValue(item.get().getName(), item.get().getVariant()); if(item.get().getName() != "highlightProperties"){
_settings.setValue(item.get().getName(), item.get().getVariant());
} else {
_settings.beginGroup("Highlights");
QStringList list = highlightProperties.get().keys();
list.removeAll("");
_settings.remove("");
for (auto string : list){
_settings.beginGroup(string);
_settings.setValue("highlightSound",highlightProperties.get().value(string).first);
_settings.setValue("highlightTask",highlightProperties.get().value(string).second);
_settings.endGroup();
}
_settings.endGroup();
}
} }
} }
void SettingsManager::load() void SettingsManager::load()
{ {
for (auto &item : _settingsItems) { for (auto &item : _settingsItems) {
item.get().setVariant(_settings.value(item.get().getName())); if(item.get().getName() != "highlightProperties"){
item.get().setVariant(_settings.value(item.get().getName()));
} else {
_settings.beginGroup("Highlights");
QStringList list = _settings.childGroups();
qDebug() << list.join(",");
for (auto string : list){
_settings.beginGroup(string);
highlightProperties.insertMap(string,_settings.value("highlightSound").toBool(),_settings.value("highlightTask").toBool());
_settings.endGroup();
}
_settings.endGroup();
}
} }
} }
Word::Type SettingsManager::getWordTypeMask() Word::Type SettingsManager::getWordTypeMask()
{ {
return _wordTypeMask; return _wordTypeMask;
@ -129,7 +159,11 @@ SettingsSnapshot SettingsManager::createSnapshot()
SettingsSnapshot snapshot; SettingsSnapshot snapshot;
for (auto &item : this->_settingsItems) { for (auto &item : this->_settingsItems) {
if(item.get().getName() != "highlightProperties"){
snapshot.addItem(item, item.get().getVariant()); snapshot.addItem(item, item.get().getVariant());
} else {
snapshot._mapItems = highlightProperties.get();
}
} }
return snapshot; return snapshot;

View file

@ -57,9 +57,12 @@ public:
Setting<bool> mentionUsersWithAt; Setting<bool> mentionUsersWithAt;
Setting<bool> allowCommandsAtEnd; Setting<bool> allowCommandsAtEnd;
Setting<bool> enableHighlights; Setting<bool> enableHighlights;
Setting<bool> enableHighlightsSelf;
Setting<bool> enableHighlightSound; Setting<bool> enableHighlightSound;
Setting<bool> enableHighlightTaskbar; Setting<bool> enableHighlightTaskbar;
Setting<bool> customHighlightSound; Setting<bool> customHighlightSound;
Setting<QString> pathHighlightSound;
Setting<QMap<QString,QPair<bool,bool>>> highlightProperties;
Setting<bool> enableTwitchEmotes; Setting<bool> enableTwitchEmotes;
Setting<bool> enableBttvEmotes; Setting<bool> enableBttvEmotes;
Setting<bool> enableFfzEmotes; Setting<bool> enableFfzEmotes;

View file

@ -8,6 +8,7 @@ struct SettingsSnapshot {
public: public:
SettingsSnapshot() SettingsSnapshot()
: _items() : _items()
, _mapItems()
{ {
} }
@ -17,6 +18,12 @@ public:
std::pair<std::reference_wrapper<BaseSetting>, QVariant>(setting.get(), value)); std::pair<std::reference_wrapper<BaseSetting>, QVariant>(setting.get(), value));
} }
void addMapItem(QString string,QPair<bool,bool> pair){
QMap<QString,QPair<bool,bool>> map;
_mapItems.insert(string,pair);
}
void apply() void apply()
{ {
for (auto &item : _items) { for (auto &item : _items) {
@ -24,6 +31,8 @@ public:
} }
} }
QMap<QString,QPair<bool,bool>> _mapItems;
private: private:
std::vector<std::pair<std::reference_wrapper<BaseSetting>, QVariant>> _items; std::vector<std::pair<std::reference_wrapper<BaseSetting>, QVariant>> _items;
}; };

View file

@ -3,8 +3,13 @@
#include "emotemanager.hpp" #include "emotemanager.hpp"
#include "ircmanager.hpp" #include "ircmanager.hpp"
#include "resources.hpp" #include "resources.hpp"
#include "settingsmanager.hpp"
#include "windowmanager.hpp" #include "windowmanager.hpp"
#include <QApplication>
#include <QDebug>
#include <QMediaPlayer>
using namespace chatterino::messages; using namespace chatterino::messages;
namespace chatterino { namespace chatterino {
@ -48,7 +53,41 @@ SharedMessage TwitchMessageBuilder::parse()
this->parseUsername(); this->parseUsername();
// highlights // highlights
// TODO: implement this xD const QString &originalMessage = ircMessage->content();
this->originalMessage = originalMessage;
SettingsManager &settings = SettingsManager::getInstance();
static auto player = new QMediaPlayer;
if(settings.customHighlightSound.get()){
player->setMedia(QUrl(settings.pathHighlightSound.get()));
} else {
player->setMedia(QUrl("qrc:/sounds/ping2.wav"));
}
if(settings.enableHighlights.get() && ircMessage->nick().compare(settings.selectedUser.get(), Qt::CaseInsensitive)){
if(settings.enableHighlightsSelf.get() && originalMessage.contains(settings.selectedUser.get(), Qt::CaseInsensitive)){
this->setHighlight(true);
if(settings.enableHighlightSound.get()){
player->play();
}
if(settings.enableHighlightTaskbar.get()){
QApplication::alert(windowManager.getMainWindow().window(),2500);
}
} else {
QStringList lines = settings.highlightProperties.get().keys();
for(QString string : lines){
if(originalMessage.contains(string,Qt::CaseInsensitive)){
this->setHighlight(true);
// Sound
if(settings.highlightProperties.get().value(string).first){
player->play();
}
// Taskbar
if(settings.highlightProperties.get().value(string).second){
QApplication::alert(windowManager.getMainWindow().window(),2500);
}
}
}
}
}
// bits // bits
QString bits = ""; QString bits = "";
@ -85,8 +124,6 @@ SharedMessage TwitchMessageBuilder::parse()
// words // words
QColor textColor = ircMessage->isAction() ? this->usernameColor : this->colorScheme.Text; QColor textColor = ircMessage->isAction() ? this->usernameColor : this->colorScheme.Text;
const QString &originalMessage = ircMessage->content();
this->originalMessage = originalMessage;
QStringList splits = originalMessage.split(' '); QStringList splits = originalMessage.split(' ');
long int i = 0; long int i = 0;

View file

@ -53,6 +53,7 @@ private:
std::string roomID; std::string roomID;
QColor usernameColor; QColor usernameColor;
bool highlight;
void parseMessageID(); void parseMessageID();
void parseRoomID(); void parseRoomID();

View file

@ -227,8 +227,7 @@ void ChatWidgetView::paintEvent(QPaintEvent * /*event*/)
// update messages that have been changed // update messages that have been changed
if (updateBuffer) { if (updateBuffer) {
QPainter painter(buffer); QPainter painter(buffer);
painter.fillRect(buffer->rect(), this->colorScheme.ChatBackground); painter.fillRect(buffer->rect(), (messageRef->getMessage()->getCanHighlightTab()) ? this->colorScheme.ChatBackgroundHighlighted : this->colorScheme.ChatBackground);
for (messages::WordPart const &wordPart : messageRef->getWordParts()) { for (messages::WordPart const &wordPart : messageRef->getWordParts()) {
// image // image
if (wordPart.getWord().isImage()) { if (wordPart.getWord().isImage()) {

View file

@ -11,10 +11,12 @@
#include <QFile> #include <QFile>
#include <QFontDialog> #include <QFontDialog>
#include <QFormLayout> #include <QFormLayout>
#include <QFileDialog>
#include <QGroupBox> #include <QGroupBox>
#include <QLabel> #include <QLabel>
#include <QListWidget> #include <QListWidget>
#include <QPalette> #include <QPalette>
#include <QTextEdit>
#include <QResource> #include <QResource>
namespace chatterino { namespace chatterino {
@ -106,6 +108,23 @@ void SettingsDialog::addTabs()
listWidget->addItem(user.getUserName()); listWidget->addItem(user.getUserName());
} }
if(listWidget->count()){
int itemIndex = 0;
for(; itemIndex < listWidget->count(); ++itemIndex){
if(listWidget->item(itemIndex)->text().compare(settings.selectedUser.get(),Qt::CaseInsensitive)){
++itemIndex;
break;
}
}
listWidget->setCurrentRow(itemIndex);
}
QObject::connect(listWidget,&QListWidget::clicked,this,[&,listWidget]{
if(!listWidget->selectedItems().isEmpty()){
settings.selectedUser.set(listWidget->currentItem()->text());
}
});
vbox->addWidget(listWidget); vbox->addWidget(listWidget);
} }
@ -347,6 +366,105 @@ void SettingsDialog::addTabs()
// Highlighting // Highlighting
vbox = new QVBoxLayout(); vbox = new QVBoxLayout();
auto highlights = new QListWidget();
globalHighlights = highlights;
QStringList items = settings.highlightProperties.get().keys();
highlights->addItems(items);
auto customSound = new QHBoxLayout();
auto soundForm = new QFormLayout();
{
vbox->addWidget(createCheckbox("Enable Highlighting", settings.enableHighlights));
vbox->addWidget(createCheckbox("Highlight messages containing your name", settings.enableHighlightsSelf));
vbox->addWidget(createCheckbox("Play sound when your name is mentioned", settings.enableHighlightSound));
vbox->addWidget(createCheckbox("Flash taskbar when your name is mentioned", settings.enableHighlightTaskbar));
customSound->addWidget(createCheckbox("Custom sound", settings.customHighlightSound));
auto selectBtn = new QPushButton("Select");
QObject::connect(selectBtn,&QPushButton::clicked,this,[&settings,this]{
auto fileName = QFileDialog::getOpenFileName(this,
tr("Open Sound"), "", tr("Image Files (*.mp3 *.wav)"));
settings.pathHighlightSound.set(fileName);
});
customSound->addWidget(selectBtn);
}
soundForm->addRow(customSound);
{
auto hbox = new QHBoxLayout();
auto addBtn = new QPushButton("Add");
auto editBtn = new QPushButton("Edit");
auto delBtn = new QPushButton("Remove");
QObject::connect(addBtn,&QPushButton::clicked,this,[highlights,this,&settings]{
auto show = new QWidget();
auto box = new QBoxLayout(QBoxLayout::TopToBottom);
auto edit = new QLineEdit();
auto add = new QPushButton("Add");
auto sound = new QCheckBox("Play sound");
auto task = new QCheckBox("Flash taskbar");
QObject::connect(add,&QPushButton::clicked,this,[=,&settings]{
if(edit->text().length()){
highlights->addItem(edit->text());
settings.highlightProperties.insertMap(edit->text(),sound->isChecked(),task->isChecked());
show->close();
}
});
box->addWidget(edit);
box->addWidget(add);
box->addWidget(sound);
box->addWidget(task);
show->setLayout(box);
show->show();
});
QObject::connect(editBtn,&QPushButton::clicked,this,[highlights,this,&settings]{
if(!highlights->selectedItems().isEmpty()){
auto show = new QWidget();
auto box = new QBoxLayout(QBoxLayout::TopToBottom);
auto edit = new QLineEdit();
edit->setText(highlights->selectedItems().first()->text());
auto add = new QPushButton("Apply");
auto sound = new QCheckBox("Play sound");
auto task = new QCheckBox("Flash taskbar");
QObject::connect(add,&QPushButton::clicked,this,[=,&settings]{
if(edit->text().length()){
settings.highlightProperties.getnonConst().remove(highlights->selectedItems().first()->text());
delete highlights->selectedItems().first();
highlights->addItem(edit->text());
settings.highlightProperties.insertMap(edit->text(),sound->isChecked(),task->isChecked());
show->close();
}
});
box->addWidget(edit);
box->addWidget(add);
box->addWidget(sound);
sound->setChecked(settings.highlightProperties.get().value(highlights->selectedItems().first()->text()).first);
box->addWidget(task);
task->setChecked(settings.highlightProperties.get().value(highlights->selectedItems().first()->text()).second);
show->setLayout(box);
show->show();
}
});
QObject::connect(delBtn,&QPushButton::clicked,this,[highlights,&settings]{
if(!highlights->selectedItems().isEmpty()){
settings.highlightProperties.getnonConst().remove(highlights->selectedItems().first()->text());
delete highlights->selectedItems().first();
}
});
vbox->addLayout(soundForm);
vbox->addWidget(highlights);
hbox->addWidget(addBtn);
hbox->addWidget(editBtn);
hbox->addWidget(delBtn);
vbox->addLayout(hbox);
}
vbox->addStretch(1); vbox->addStretch(1);
addTab(vbox, "Highlighting", ":/images/format_Bold_16xLG.png"); addTab(vbox, "Highlighting", ":/images/format_Bold_16xLG.png");
@ -461,7 +579,18 @@ void SettingsDialog::okButtonClicked()
void SettingsDialog::cancelButtonClicked() void SettingsDialog::cancelButtonClicked()
{ {
// TODO: Re-implement the snapshot feature properly // TODO: Re-implement the snapshot feature properly
auto &instance = SettingsManager::getInstance();
this->snapshot.apply(); this->snapshot.apply();
instance.highlightProperties.set(this->snapshot._mapItems);
QStringList list = instance.highlightProperties.get().keys();
list.removeDuplicates();
while(globalHighlights->count()>0)
{
delete globalHighlights->takeItem(0);
}
globalHighlights->addItems(list);
this->close(); this->close();
} }

View file

@ -10,6 +10,7 @@
#include <QDialogButtonBox> #include <QDialogButtonBox>
#include <QHBoxLayout> #include <QHBoxLayout>
#include <QListView> #include <QListView>
#include <QListWidget>
#include <QMainWindow> #include <QMainWindow>
#include <QPushButton> #include <QPushButton>
#include <QStackedLayout> #include <QStackedLayout>
@ -51,6 +52,8 @@ private:
SettingsDialogTab *selectedTab = nullptr; SettingsDialogTab *selectedTab = nullptr;
QListWidget* globalHighlights;
/// Widget creation helpers /// Widget creation helpers
QCheckBox *createCheckbox(const QString &title, Setting<bool> &setting); QCheckBox *createCheckbox(const QString &title, Setting<bool> &setting);
QCheckBox *createCheckbox(const QString &title, pajlada::Settings::Setting<bool> &setting); QCheckBox *createCheckbox(const QString &title, pajlada::Settings::Setting<bool> &setting);