From 8bdfbf7b87dfc3f6ba0ff66cf5bd1c8ef8dc53d1 Mon Sep 17 00:00:00 2001 From: pajlada Date: Sun, 26 Jun 2022 12:43:34 +0200 Subject: [PATCH] Allow non-message phrases to be highlighted by self (#3835) * All non-phrase highlights can now trigger on messages from self New state: Allows self highlights: Subscription, Whisper, User, Badge Does not allow self highlights: Message * Add changelog entry * fix PR number in changelog --- CHANGELOG.md | 2 +- .../highlights/HighlightController.cpp | 48 ++++++++++++------- .../highlights/HighlightController.hpp | 2 +- src/messages/SharedMessageBuilder.cpp | 7 --- tests/src/HighlightController.cpp | 35 +++++++++++++- 5 files changed, 68 insertions(+), 26 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index cbc624a3a..f841ac855 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -39,7 +39,7 @@ - Bugfix: Add icon in the CMake macOS bundle. (#3832) - Bugfix: Adopt popup windows in order to force floating behavior on some window managers. (#3836) - Dev: Rewrite LimitedQueue (#3798) -- Dev: Overhaul highlight system by moving all checks into a Controller allowing for easier tests. (#3399, #3801) +- Dev: Overhaul highlight system by moving all checks into a Controller allowing for easier tests. (#3399, #3801, #3835) - Dev: Use Game Name returned by Get Streams instead of querying it from the Get Games API. (#3662) - Dev: Batch checking live status for all channels after startup. (#3757, #3762, #3767) - Dev: Move most command context into the command controller. (#3824) diff --git a/src/controllers/highlights/HighlightController.cpp b/src/controllers/highlights/HighlightController.cpp index aa122d9a9..632f76cc4 100644 --- a/src/controllers/highlights/HighlightController.cpp +++ b/src/controllers/highlights/HighlightController.cpp @@ -6,15 +6,21 @@ namespace { using namespace chatterino; -auto highlightPhraseCheck(HighlightPhrase highlight) -> HighlightCheck +auto highlightPhraseCheck(const HighlightPhrase &highlight) -> HighlightCheck { return HighlightCheck{ - [highlight]( - const auto &args, const auto &badges, const auto &senderName, - const auto &originalMessage) -> boost::optional { - (void)args; // unused - (void)badges; // unused - (void)originalMessage; // unused + [highlight](const auto &args, const auto &badges, + const auto &senderName, const auto &originalMessage, + const auto self) -> boost::optional { + (void)args; // unused + (void)badges; // unused + (void)senderName; // unused + + if (self) + { + // Phrase checks should ignore highlights from the user + return boost::none; + } if (!highlight.isMatch(originalMessage)) { @@ -54,11 +60,13 @@ void rebuildSubscriptionHighlights(Settings &settings, checks.emplace_back(HighlightCheck{ [=](const auto &args, const auto &badges, const auto &senderName, - const auto &originalMessage) - -> boost::optional { + const auto &originalMessage, + const auto self) -> boost::optional { (void)badges; // unused (void)senderName; // unused (void)originalMessage; // unused + (void)self; // unused + if (!args.isSubscriptionMessage) { return boost::none; @@ -97,11 +105,13 @@ void rebuildWhisperHighlights(Settings &settings, checks.emplace_back(HighlightCheck{ [=](const auto &args, const auto &badges, const auto &senderName, - const auto &originalMessage) - -> boost::optional { + const auto &originalMessage, + const auto self) -> boost::optional { (void)badges; // unused (void)senderName; // unused (void)originalMessage; // unused + (void)self; // unused + if (!args.isReceivedWhisper) { return boost::none; @@ -152,11 +162,12 @@ void rebuildUserHighlights(Settings &settings, { checks.emplace_back(HighlightCheck{ [highlight](const auto &args, const auto &badges, - const auto &senderName, const auto &originalMessage) - -> boost::optional { + const auto &senderName, const auto &originalMessage, + const auto self) -> boost::optional { (void)args; // unused (void)badges; // unused (void)originalMessage; // unused + (void)self; // unused if (!highlight.isMatch(senderName)) { @@ -187,11 +198,13 @@ void rebuildBadgeHighlights(Settings &settings, { checks.emplace_back(HighlightCheck{ [highlight](const auto &args, const auto &badges, - const auto &senderName, const auto &originalMessage) - -> boost::optional { + const auto &senderName, const auto &originalMessage, + const auto self) -> boost::optional { (void)args; // unused (void)senderName; // unused (void)originalMessage; // unused + (void)self; // unused + for (const Badge &badge : badges) { if (highlight.isMatch(badge)) @@ -302,10 +315,13 @@ std::pair HighlightController::check( // Access for checking const auto checks = this->checks_.accessConst(); + auto currentUser = getIApp()->getAccounts()->twitch.getCurrent(); + auto self = (senderName == currentUser->getUserName()); + for (const auto &check : *checks) { if (auto checkResult = - check.cb(args, badges, senderName, originalMessage); + check.cb(args, badges, senderName, originalMessage, self); checkResult) { highlighted = true; diff --git a/src/controllers/highlights/HighlightController.hpp b/src/controllers/highlights/HighlightController.hpp index eb20716f0..0a1ecb2a9 100644 --- a/src/controllers/highlights/HighlightController.hpp +++ b/src/controllers/highlights/HighlightController.hpp @@ -142,7 +142,7 @@ struct HighlightResult { struct HighlightCheck { using Checker = std::function( const MessageParseArgs &args, const std::vector &badges, - const QString &senderName, const QString &originalMessage)>; + const QString &senderName, const QString &originalMessage, bool self)>; Checker cb; }; diff --git a/src/messages/SharedMessageBuilder.cpp b/src/messages/SharedMessageBuilder.cpp index 2dae93669..f059a6708 100644 --- a/src/messages/SharedMessageBuilder.cpp +++ b/src/messages/SharedMessageBuilder.cpp @@ -147,13 +147,6 @@ void SharedMessageBuilder::parseHighlights() return; } - auto currentUser = getIApp()->getAccounts()->twitch.getCurrent(); - if (this->ircMessage->nick() == currentUser->getUserName()) - { - // Do nothing. We ignore any potential highlights from the logged in user - return; - } - auto badges = SharedMessageBuilder::parseBadgeTag(this->tags); auto [highlighted, highlightResult] = getIApp()->getHighlights()->check( this->args, badges, this->ircMessage->nick(), this->originalMessage_); diff --git a/tests/src/HighlightController.cpp b/tests/src/HighlightController.cpp index 8e4a05ebb..81d9029dc 100644 --- a/tests/src/HighlightController.cpp +++ b/tests/src/HighlightController.cpp @@ -245,6 +245,16 @@ static QString DEFAULT_SETTINGS = R"!( "soundUrl": "", "color": "#7fffffff" }, + { + "pattern": "testaccount_420", + "showInMentions": false, + "alert": false, + "sound": false, + "regex": false, + "case": false, + "soundUrl": "", + "color": "#6fffffff" + }, { "pattern": "gempir", "showInMentions": true, @@ -497,6 +507,27 @@ TEST_F(HighlightControllerTest, A) }, }, }, + { + // TEST CASE: Message phrase from sender should be ignored (so showInMentions false), but since it's a user highlight, it should set a color + { + // input + MessageParseArgs{}, // no special args + {}, // no badges + "testaccount_420", // sender name + "!testmanxd", // original message + }, + { + // expected + true, // state + { + false, // alert + false, // playsound + boost::none, // custom sound url + std::make_shared("#6fffffff"), // color + false, + }, + }, + }, }; for (const auto &[input, expected] : tests) @@ -504,7 +535,9 @@ TEST_F(HighlightControllerTest, A) auto [isMatch, matchResult] = this->controller->check( input.args, input.badges, input.senderName, input.originalMessage); - EXPECT_EQ(isMatch, expected.state); + EXPECT_EQ(isMatch, expected.state) + << qUtf8Printable(input.senderName) << ": " + << qUtf8Printable(input.originalMessage); EXPECT_EQ(matchResult, expected.result); } }