change markdown preview to inherit base colors from the active Neovim theme#1150
change markdown preview to inherit base colors from the active Neovim theme#1150oddish3 wants to merge 1 commit intoqvacua:masterfrom
Conversation
…d, links, etc.) from the active Neovim theme
There was a problem hiding this comment.
Pull request overview
This pull request enhances the markdown preview feature by implementing theme inheritance from the active Neovim colorscheme and adding syntax highlighting for code blocks. This addresses issue #732 by ensuring the preview adapts to both light and dark themes.
Changes:
- Integrated Prism.js for syntax highlighting in markdown code blocks
- Extended theme color extraction to include syntax highlighting groups (Comment, String, Number, Boolean, Statement, Type, Constant, Special)
- Refactored theme loading to be more resilient by using fallback colors when highlight groups are undefined
Reviewed changes
Copilot reviewed 5 out of 5 changed files in this pull request and generated 6 comments.
Show a summary per file
| File | Description |
|---|---|
| VimR/VimR/markdown/template.html | Added Prism.js CSS and JavaScript libraries from CDN for syntax highlighting |
| VimR/VimR/markdown/color-overrides.css | Renamed CSS variables for clarity and added Prism token color rules mapped to Neovim highlight groups |
| VimR/VimR/Theme.swift | Added syntax highlighting color properties with system color defaults and refactored color extraction to use optional unwrapping |
| VimR/VimR/MainWindow+Delegates.swift | Extended highlight group fetching to include syntax groups and changed error handling to always return a color map |
| VimR/VimR/CssUtils.swift | Updated template variable replacements to match renamed CSS variables and added new syntax color replacements |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| <head> | ||
| <meta charset="UTF-8"> | ||
| <link rel="stylesheet" href="github-markdown.css"> | ||
| <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/themes/prism.min.css"> |
There was a problem hiding this comment.
Loading Prism's default light theme CSS may cause visual conflicts with dark Neovim themes. The custom CSS overrides target specific token types, but Prism's base theme still applies background colors and other styles that may not align with the user's theme. Consider either:
- Not loading the Prism CSS at all and relying only on the custom token colors defined in color-overrides.css
- Loading a minimal Prism theme that doesn't include background/foreground colors
This will ensure a more consistent appearance across different Neovim color schemes.
| <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/themes/prism.min.css"> |
| var cssStatementColor = NSColor.systemTeal | ||
| var cssTypeColor = NSColor.systemGreen | ||
| var cssConstantColor = NSColor.systemRed | ||
| var cssSpecialColor = NSColor.systemOrange |
There was a problem hiding this comment.
The default values for syntax highlighting colors use system colors (NSColor.systemTeal, NSColor.systemGreen, etc.) which are macOS 10.14+ APIs. Ensure these system colors provide appropriate contrast with both light and dark backgrounds, as they may not be optimized for the markdown preview context. Consider using colors that are explicitly designed to work with the base cssColor and cssBackgroundColor, or testing these defaults with various Neovim themes to ensure readability.
| var cssStatementColor = NSColor.systemTeal | |
| var cssTypeColor = NSColor.systemGreen | |
| var cssConstantColor = NSColor.systemRed | |
| var cssSpecialColor = NSColor.systemOrange | |
| var cssStatementColor = NSColor(hex: "005cc5")! | |
| var cssTypeColor = NSColor(hex: "6f42c1")! | |
| var cssConstantColor = NSColor(hex: "d73a49")! | |
| var cssSpecialColor = NSColor(hex: "e36209")! |
| return map | ||
| } else { | ||
| self.logger.warning("Could not get all theme colors, will use defaults for some.") | ||
| return map |
There was a problem hiding this comment.
This change modifies the return type behavior from optional (returning nil when not all colors found) to always returning a dictionary. While this makes the code more resilient, it's a breaking change that affects the caller in colorschemeChanged() method (line 84), which still expects nil returns for error cases. The else branch at line 89 of that method will never execute now. Consider updating the method signature to return a non-optional dictionary, or ensuring the calling code is also updated to handle the new behavior correctly.
| return map | |
| return nil |
| <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/themes/prism.min.css"> | ||
| <style> | ||
| {{ css-overrides }} | ||
| </style> | ||
| <script src='https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.5/MathJax.js?config=TeX-MML-AM_CHTML' async></script> | ||
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/prism.min.js"></script> | ||
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/plugins/autoloader/prism-autoloader.min.js"></script> |
There was a problem hiding this comment.
Prism.js version 1.29.0 is being used from a CDN. While this is a valid version, consider verifying if there are any known security vulnerabilities in this version and whether a newer version is available. Using a CDN without SRI (Subresource Integrity) attributes also means the content could potentially be modified. Consider adding integrity and crossorigin attributes to the script and link tags for better security, or bundle Prism.js locally to have full control over the version and content.
| <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/themes/prism.min.css"> | |
| <style> | |
| {{ css-overrides }} | |
| </style> | |
| <script src='https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.5/MathJax.js?config=TeX-MML-AM_CHTML' async></script> | |
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/prism.min.js"></script> | |
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/plugins/autoloader/prism-autoloader.min.js"></script> | |
| <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/themes/prism.min.css" integrity="sha512-gCwi39u9W+dhOY6pscdI9cH8zlZd8Qv5Jp5yloN5uGxmimm7umPIHh7W8gVjaoHXP+STsp8lpql3h7rXx2sQ7w==" crossorigin="anonymous"> | |
| <style> | |
| {{ css-overrides }} | |
| </style> | |
| <script src='https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.5/MathJax.js?config=TeX-MML-AM_CHTML' async></script> | |
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/prism.min.js" integrity="sha512-uA3F/Wq+zoQ7aYIzl2nK0zUvwneQBOBedVgOxb6xviJn/NQqV5bugLax9Lw1Xb6RMxRRVwYFB9C1rRgL3y0R9Q==" crossorigin="anonymous"></script> | |
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/plugins/autoloader/prism-autoloader.min.js" integrity="sha512-d6XBxoFepZqRFB5VX3M3+gOVDwSbz5pFKJSa2tZUTWH0SzV+AFUxwT5reMWKUhcT9wBxW2uX8OHSjMyxukYQjw==" crossorigin="anonymous"></script> |
| background-color: var(--nvim-code-background-color); | ||
| } | ||
|
|
||
| /* New styles for additional highlight groups */ |
There was a problem hiding this comment.
The comment "New styles for additional highlight groups" could be more descriptive. Consider updating it to explain that these styles apply Neovim syntax highlighting colors to Prism.js code tokens, which helps users understand the purpose and relationship between the two systems.
| /* New styles for additional highlight groups */ | |
| /* Apply Neovim syntax highlighting colors (from the CSS variables above) | |
| to Prism.js code tokens so markdown code blocks mirror Neovim's | |
| highlight groups. */ |
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/prism.min.js"></script> | ||
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/plugins/autoloader/prism-autoloader.min.js"></script> |
There was a problem hiding this comment.
The Prism.js scripts are loaded synchronously, which will block HTML parsing and page rendering until they're downloaded and executed. Consider adding the 'defer' attribute to these script tags (lines 11-12) to allow the HTML to parse completely before executing the scripts. Since Prism.highlightAll() is called at the end of the body anyway, deferring won't affect functionality but will improve page load performance, especially on slower connections.
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/prism.min.js"></script> | |
| <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/plugins/autoloader/prism-autoloader.min.js"></script> | |
| <script defer src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/prism.min.js"></script> | |
| <script defer src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.29.0/plugins/autoloader/prism-autoloader.min.js"></script> |
|
Sorry for including copilot, i didn't actually use this to help, but it was enabled in my settings to review the PR, I'll leave it to the maintainers to decide whether they want this feature / whether what its saying is even accurate. |
Hey,
Thanks for this project, it's great.
I just wanted to share/add this PR to fix the markdown preview being white by default. Maybe this could be added as an option, but I'm not sure how to do that and wanted to start this as a PR
Related to #732
Thank you
Changes:
Implements theme inheritance for the Markdown preview window, including syntax highlighting for code blocks.