-
Notifications
You must be signed in to change notification settings - Fork 596
dynamic dark theme based on CSS class selector #1803
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
base: master
Are you sure you want to change the base?
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for this PR. Let me understand the context a bit more.
- Certain websites add a CSS class to all images when dark mode is turned on.
- This flag makes it so that this CSS class flows down into D2's CSS to control dark mode.
The downside is obviously that the image is no longer portable -- it's generated to be on a certain website.
It seems that apps/sites that do this type of dark mode configuration know that this is a limitation on most images and just have you specify two images, e.g.:
- https://docusaurus.io/docs/markdown-features/assets#github-style-themed-images
- https://github.blog/changelog/2021-11-24-specify-theme-context-for-images-in-markdown/
The benefit of using D2 is that you can have all your diagrams adapt with just 1 image.
I guess rendering an SVG for a particular website and thus having it not be portable for others is fine. I can't think of anything better and recognize this is a benefit for these use cases.
I think this flag should be either class or ID. If it starts with .something, it's a class. If it's #something, it's ID.
edit: nvm, IDs don't make sense here.
The "dark" class is technically applied to the
Writerside also supports this, enabling us to generate or provide two different static images, but I wouldn't say it is a downside. When rendering SVGs into bitmap format, the user loses the ability to copy text from the diagrams. To me, this is a valuable feature. Additionally, we should also consider scaling — Retina screens, for example, require 2x resolution images to provide crisp, detailed visuals. |
|
Cool and lastly, can you sign your PR please @develar ? We have it turned on as an organization-wide setting. |
52d4880 to
c2e881e
Compare
Sign Git commits? Done. |
alixander
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Forgive the delay here. This feature looks valuable, if you're still interested in pursuing it.
|
I'm not sure if it's too late to bring this up now: I suggest using Reasons:
Behavior ChangesCurrent behavior:
Using For both inline and embedded SVG:
A breaking change here is that inline SVG without a The proposed behavior actually aligns with how native web controls (e.g. If this proposal is adopted, issue #831 can be safely implemented, because authors will have direct page-level control without worrying about their SVGs unexpectedly switching to auto-applied dark mode. Just like native controls, every component supports dark mode—but only when Implementation:
Further explanation of point 2:Because:
So, if you remove an SVG's
By adding: svg:root {
color-scheme: light dark;
}
Example:<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
</head>
<body style="color-scheme: dark;">
<div style="display: flex; gap: 20px;">
<!-- inline SVG -->
<svg xmlns="http://www.w3.org/2000/svg"
viewBox="0 0 100 100"
width="100"
height="100">
<style>
svg:root {
color-scheme: light dark;
}
@scope {
--fill-color: light-dark(red, green);
circle {
fill: var(--fill-color);
}
}
</style>
<circle cx="50" cy="50" r="40" />
</svg>
<!-- embedded SVG -->
<img src="./light-dark-circle.svg" alt="SVG Image" />
</div>
</body>
</html>
<svg xmlns="http://www.w3.org/2000/svg"
viewBox="0 0 100 100"
width="100"
height="100">
<style>
svg:root {
color-scheme: light dark;
}
@scope {
--fill-color: light-dark(red, green);
circle {
fill: var(--fill-color);
}
}
</style>
<circle cx="50" cy="50" r="40" />
</svg>For brevity, this example uses |
|
I’ve started working on this PR again. I reviewed the comment above, and it does look like a better approach. It’s not exactly what I’d like to see in the long run, since ideally we should be able to use external CSS to reduce SVG size—but that’s a separate topic, as it involves different scenarios with their own trade-offs. |
c2e881e to
f7ce68f
Compare
--dark-theme-class: the CSS class to enable dark mode. When left unset prefers-color-scheme media query is used;When D2-produced SVG file is embedded into some documentation/site framework where dark mode is controlled by CSS class, using
prefers-color-schememedia query leads to inability to switch dark theme if needed. Writerside issue. Same for mkdocs and so on. IntelliJ D2 plugin also will use a new flag.Media Query Level 5, where it is possible to use some class as a condition, is not supported by any modern browser.
dark-dynamic.mov