From c98e6ba5a7688689d24c5f5d90fa4b4a9bad297c Mon Sep 17 00:00:00 2001 From: Ian Morland <16573496+imorland@users.noreply.github.com> Date: Mon, 7 Nov 2022 15:49:47 +0000 Subject: [PATCH] fix: groupmentions have poor contrast on some backgrounds (#3672) * fix: poor text contrast on some backgrounds * use hexdec() * fix render test * appears to be working now --- .../js/src/forum/utils/textFormatter.js | 2 ++ extensions/mentions/less/forum.less | 36 +++++++++++++++---- extensions/mentions/src/ConfigureMentions.php | 34 +++++++++++++++++- .../integration/api/GroupMentionsTest.php | 2 +- 4 files changed, 66 insertions(+), 8 deletions(-) diff --git a/extensions/mentions/js/src/forum/utils/textFormatter.js b/extensions/mentions/js/src/forum/utils/textFormatter.js index 415d99907..54055069e 100644 --- a/extensions/mentions/js/src/forum/utils/textFormatter.js +++ b/extensions/mentions/js/src/forum/utils/textFormatter.js @@ -1,6 +1,7 @@ import app from 'flarum/forum/app'; import username from 'flarum/common/helpers/username'; import extractText from 'flarum/common/utils/extractText'; +import isDark from 'flarum/common/utils/isDark'; export function filterUserMentions(tag) { let user; @@ -40,6 +41,7 @@ export function filterGroupMentions(tag) { tag.setAttribute('groupname', extractText(group.namePlural())); tag.setAttribute('icon', group.icon()); tag.setAttribute('color', group.color()); + tag.setAttribute('class', isDark(group.color()) ? 'GroupMention--light' : 'GroupMention--dark'); return true; } diff --git a/extensions/mentions/less/forum.less b/extensions/mentions/less/forum.less index 0932c60df..4843645a6 100644 --- a/extensions/mentions/less/forum.less +++ b/extensions/mentions/less/forum.less @@ -98,16 +98,40 @@ .Button--color(@tooltip-color, @tooltip-bg); } .GroupMention { - color: @body-bg; + & when (@config-dark-mode = false) { + &, + &:hover, + &:active { + color: @text-on-light; + } + } + & when (@config-dark-mode = true) { + &, + &:hover, + &:active { + color: @text-on-dark; + } + } + + &--light { + &, + &:hover, + &:active { + color: @text-on-light; + } + } + + &--dark { + &, + &:hover, + &:active { + color: @text-on-dark; + } + } .icon { margin-left: 5px; } - - &:hover, - &:active { - color: @body-bg; - } } .MentionsDropdown .Badge { box-shadow: none; diff --git a/extensions/mentions/src/ConfigureMentions.php b/extensions/mentions/src/ConfigureMentions.php index d57904f5e..ef7780755 100644 --- a/extensions/mentions/src/ConfigureMentions.php +++ b/extensions/mentions/src/ConfigureMentions.php @@ -14,6 +14,7 @@ use Flarum\Http\UrlGenerator; use Flarum\Post\CommentPost; use Flarum\Settings\SettingsRepositoryInterface; use Flarum\User\User; +use Illuminate\Support\Str; use s9e\TextFormatter\Configurator; class ConfigureMentions @@ -147,12 +148,13 @@ class ConfigureMentions $tag->attributes->add('groupname'); $tag->attributes->add('icon'); $tag->attributes->add('color'); + $tag->attributes->add('class'); $tag->attributes->add('id')->filterChain->append('#uint'); $tag->template = ' - @ + @ @ @@ -177,10 +179,40 @@ class ConfigureMentions $tag->setAttribute('groupname', $group->name_plural); $tag->setAttribute('icon', $group->icon ?? 'fas fa-at'); $tag->setAttribute('color', $group->color); + if (! empty($group->color)) { + $tag->setAttribute('class', self::isDark($group->color) ? 'GroupMention--light' : 'GroupMention--dark'); + } else { + $tag->setAttribute('class', ''); + } return true; } $tag->invalidate(); } + + /** + * The `isDark` utility converts a hex color to rgb, and then calcul a YIQ + * value in order to get the appropriate brightness value (is it dark or is it + * light?) See https://www.w3.org/TR/AERT/#color-contrast for references. A YIQ + * value >= 128 is a light color. + */ + public static function isDark(?string $hexColor): bool + { + if (! $hexColor) { + return false; + } + + $hexNumbers = Str::replace('#', '', $hexColor); + if (Str::length($hexNumbers) === 3) { + $hexNumbers += $hexNumbers; + } + + $r = hexdec(Str::substr($hexNumbers, 0, 2)); + $g = hexdec(Str::subStr($hexNumbers, 2, 2)); + $b = hexdec(Str::subStr($hexNumbers, 4, 2)); + $yiq = ($r * 299 + $g * 587 + $b * 114) / 1000; + + return $yiq >= 128 ? false : true; + } } diff --git a/extensions/mentions/tests/integration/api/GroupMentionsTest.php b/extensions/mentions/tests/integration/api/GroupMentionsTest.php index 78ea3d50c..9df5e9de6 100644 --- a/extensions/mentions/tests/integration/api/GroupMentionsTest.php +++ b/extensions/mentions/tests/integration/api/GroupMentionsTest.php @@ -84,7 +84,7 @@ class GroupMentionsTest extends TestCase $response = json_decode($response->getBody(), true); - $this->assertStringContainsString('

One of the @Mods will look at this

', $response['data']['attributes']['contentHtml']); + $this->assertStringContainsString('

One of the @Mods will look at this

', $response['data']['attributes']['contentHtml']); $this->assertNotNull(CommentPost::find($response['data']['id'])->mentionsGroups->find(4)); }