Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: change favicon per theme #1348

Closed
wants to merge 6 commits into from
Closed

Conversation

DiogoSoaress
Copy link
Member

What it solves

Resolves #1123

How this PR fixes it

Implements a hook to detect the system's preferred color scheme and subscribes to that media query changes

How to test it

Go to your OS preferences and change the dark/light theme.
Observe the favicon in the browsers tab changing accordingly.

Screenshots

Screenshot 2022-12-12 at 15 41 49

@github-actions
Copy link

github-actions bot commented Dec 12, 2022

Branch preview

✅ Deploy successful!

https://fixchangefaviconpertheme--webcore.review-web-core.5afe.dev

@github-actions
Copy link

github-actions bot commented Dec 12, 2022

ESLint Summary View Full Report

Annotations are provided inline on the Files Changed tab. You can also see all annotations that were generated on the annotations page.

Type Occurrences Fixable
Errors 0 0
Warnings 0 0
Ignored 0 N/A
  • Result: ✅ success
  • Annotations: 0 total

Report generated by eslint-plus-action

import { renderHook } from '@/tests/test-utils'

describe('usePrefersColorScheme', () => {
it('should return the initial color scheme', () => {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could we add more tests for the listeners of the media query which would set the result to dark / light?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added. I found it a bit difficult to mock the media query event without adding the dependency. Maybe we can look at it quickly together

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@DiogoSoaress DiogoSoaress changed the title Fix change favicon per theme fix: change favicon per theme Dec 12, 2022
Comment on lines 42 to 44
<link rel="shortcut icon" href="/favicons/favicon.ico" />
<link rel="apple-touch-icon" sizes="180x180" href="/favicons/apple-touch-icon.png" />
<link rel="icon" type="image/png" sizes="32x32" href="/favicons/favicon-32x32.png" />
<link rel="icon" type="image/png" sizes="16x16" href="/favicons/favicon-16x16.png" />
<link rel="mask-icon" href="/favicons/safari-pinned-tab.svg" color="#000" />
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we not need to update these other favicons?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've added dark versions to the ones that were subject to poor contrast in browser's tabs.
If I get it correctly the ones I left in <MetaTags> are for other uses.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm still seeing the old icon in Firefox:
image

I would suggest we test adding an icon to the home screen of an iPhone, as well as pinning a tab in Safari.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm still seeing the old icon in Firefox

Must be the cache

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I opened it in a Private Window though.

src/hooks/usePrefersColorScheme.ts Show resolved Hide resolved
src/hooks/usePrefersColorScheme.ts Outdated Show resolved Hide resolved
Comment on lines 89 to 90
<link rel="icon" type="image/png" sizes="32x32" href={`/favicons/favicon${darkPath}-32x32.png`} />
<link rel="icon" type="image/png" sizes="16x16" href={`/favicons/favicon${darkPath}-16x16.png`} />
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we not keep these and associated logic inside MetaTag?

Copy link
Member Author

@DiogoSoaress DiogoSoaress Dec 13, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tried to include the logic inside <MetaTag /> component but it was not taking effect. I tried to log from inside that component but unsuccessfully. Happy to look at it together if we want to move these <link> back there

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it would be best to keep them together. I am happy to look at it with you.

Copy link
Member

@katspaugh katspaugh left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You propose adding 128 lines of JS and an external library to change a favicon.
From the maintainability standpoint, I would much prefer a low-tech solution like an icon with a background.

Comment on lines 11 to 12
const isDark = window.matchMedia('(prefers-color-scheme: dark)')
const isLight = window.matchMedia('(prefers-color-scheme: light)')
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Aren't they mutually exclusive?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From my understanding of https://w3c.github.io/csswg-drafts/mediaqueries-5/#prefers-color-scheme they are not mutually exclusive but correct me if I'm wrong. The user can prefer dark or light or have no preference.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, but you don't have a third icon for !isDark && !isLight, do you?
Also from the docs you linked (emphasis mine):

light
Indicates that user has expressed the preference for a page that has a light theme (dark text on light background), or has not expressed an active preference (and thus should receive the "web default" of a light theme).

@@ -77,11 +78,16 @@ interface WebCoreAppProps extends AppProps {
}

const WebCoreApp = ({ Component, pageProps, emotionCache = clientSideEmotionCache }: WebCoreAppProps): ReactElement => {
const prefersColorScheme = usePrefersColorScheme()
const darkPath = prefersColorScheme === 'dark' ? '-dark' : ''
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

darkPath is not the best name if it can be either dark or light.

@katspaugh
Copy link
Member

There's a CSS-only solution too, have you tried it?
https://stackoverflow.com/a/60158619/352796

@DiogoSoaress
Copy link
Member Author

You propose adding 128 lines of JS and an external library to change a favicon.

I know. Well, the changes are more numerous given the added hook and the test coverage. The dev dependency is also only used for tests and it was added following the code review.

I will talk with @liliiaorlenko to get a svg favicon to explore the CSS-only solution and to get her feedback on changing the favicon to a round background that would have good contrast regardless of the OS preferred theme.

@DiogoSoaress
Copy link
Member Author

DiogoSoaress commented Dec 14, 2022

There's a CSS-only solution too, have you tried it?

I was trying this implementation but I don't think it suits our use case give it builds over the assumption that nowadays you can use an SVG as a favicon for your website, which is hardly true.
https://caniuse.com/link-icon-svg

I also got the favicon with the green background from the designer. I will create a different PR for it so we can compare the 2 solutions

@DiogoSoaress
Copy link
Member Author

I've addressed the comments and opened an alternative implementation to this PR using the favicon with the green background #1376

@katspaugh
Copy link
Member

It wasn't necessary to spend time addressing the comments. Closing in favor of the other PR.

@katspaugh katspaugh closed this Dec 15, 2022
@katspaugh katspaugh deleted the fix-change-favicon-per-theme branch December 15, 2022 11:52
@github-actions github-actions bot locked and limited conversation to collaborators Dec 15, 2022
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Safe icon is not visible in dark mode
4 participants