theme.ts 2.0 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071
  1. import { EditorView } from '@codemirror/view'
  2. import { Compartment } from '@codemirror/state'
  3. export type FontFamily = 'monaco' | 'lucida'
  4. export type LineHeight = 'compact' | 'normal' | 'wide'
  5. export type OverallTheme = '' | 'light-'
  6. export type Options = {
  7. fontSize: number
  8. fontFamily: FontFamily
  9. lineHeight: LineHeight
  10. overallTheme: OverallTheme
  11. }
  12. const optionsThemeConf = new Compartment()
  13. export const theme = (options: Options) => [
  14. optionsThemeConf.of(createThemeFromOptions(options)),
  15. ]
  16. export const lineHeights: Record<LineHeight, number> = {
  17. compact: 1.33,
  18. normal: 1.6,
  19. wide: 2,
  20. }
  21. const fontFamilies: Record<FontFamily, string[]> = {
  22. monaco: ['Monaco', 'Menlo', 'Ubuntu Mono', 'Consolas', 'monospace'],
  23. lucida: ['Lucida Console', 'Source Code Pro', 'monospace'],
  24. }
  25. const createThemeFromOptions = ({
  26. fontSize = 12,
  27. fontFamily = 'monaco',
  28. lineHeight = 'normal',
  29. overallTheme = '',
  30. }: Options) => {
  31. // Theme styles that depend on settings
  32. return [
  33. EditorView.editorAttributes.of({
  34. class: overallTheme === '' ? 'overall-theme-dark' : 'overall-theme-light',
  35. }),
  36. EditorView.theme({
  37. '&.cm-editor': {
  38. '--font-size': `${fontSize}px`,
  39. '--source-font-family': fontFamilies[fontFamily]?.join(', '),
  40. '--line-height': lineHeights[lineHeight],
  41. },
  42. '.cm-content': {
  43. fontSize: 'var(--font-size)',
  44. fontFamily: 'var(--source-font-family)',
  45. lineHeight: 'var(--line-height)',
  46. color: '#000',
  47. },
  48. '.cm-gutters': {
  49. fontSize: 'var(--font-size)',
  50. lineHeight: 'var(--line-height)',
  51. },
  52. '.cm-tooltip': {
  53. // Set variables for tooltips, which are outside the editor
  54. '--font-size': `${fontSize}px`,
  55. '--source-font-family': fontFamilies[fontFamily]?.join(', '),
  56. // NOTE: fontFamily is not set here, as most tooltips use the UI font
  57. fontSize: 'var(--font-size)',
  58. },
  59. '.cm-lineNumbers': {
  60. fontFamily: 'var(--source-font-family)',
  61. },
  62. }),
  63. ]
  64. }