mirror of
https://github.com/overleaf/overleaf.git
synced 2024-11-21 20:47:08 -05:00
Ensure that each editor theme is only created once (#17095)
GitOrigin-RevId: 3551e02fab44fae7fcab5cb12886d45969e3990f
This commit is contained in:
parent
aa17e1e7e1
commit
3f29aa2195
15 changed files with 679 additions and 647 deletions
|
@ -13,6 +13,7 @@ export type Options = {
|
|||
const optionsThemeConf = new Compartment()
|
||||
|
||||
export const theme = (options: Options) => [
|
||||
baseTheme,
|
||||
optionsThemeConf.of(createThemeFromOptions(options)),
|
||||
]
|
||||
|
||||
|
@ -35,36 +36,46 @@ const createThemeFromOptions = ({
|
|||
// Theme styles that depend on settings
|
||||
const fontFamilyValue = fontFamilies[fontFamily]?.join(', ')
|
||||
return [
|
||||
EditorView.theme({
|
||||
'&.cm-editor': {
|
||||
EditorView.editorAttributes.of({
|
||||
style: Object.entries({
|
||||
'--font-size': `${fontSize}px`,
|
||||
'--source-font-family': fontFamilyValue,
|
||||
'--line-height': lineHeights[lineHeight],
|
||||
},
|
||||
'.cm-content': {
|
||||
fontSize: 'var(--font-size)',
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
color: '#000',
|
||||
},
|
||||
'.cm-gutters': {
|
||||
fontSize: 'var(--font-size)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
},
|
||||
})
|
||||
.map(([key, value]) => `${key}: ${value}`)
|
||||
.join(';'),
|
||||
}),
|
||||
// Set variables for tooltips, which are outside the editor
|
||||
// TODO: set these on document.body, or a new container element for the tooltips, without using a style mod
|
||||
EditorView.baseTheme({
|
||||
'.cm-tooltip': {
|
||||
// Set variables for tooltips, which are outside the editor
|
||||
'--font-size': `${fontSize}px`,
|
||||
'--source-font-family': fontFamilyValue,
|
||||
// NOTE: fontFamily is not set here, as most tooltips use the UI font
|
||||
fontSize: 'var(--font-size)',
|
||||
},
|
||||
'.cm-lineNumbers': {
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
},
|
||||
}),
|
||||
]
|
||||
}
|
||||
|
||||
const baseTheme = EditorView.baseTheme({
|
||||
'.cm-content': {
|
||||
fontSize: 'var(--font-size)',
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
color: '#000',
|
||||
},
|
||||
'.cm-gutters': {
|
||||
fontSize: 'var(--font-size)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
},
|
||||
'.cm-lineNumbers': {
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
},
|
||||
'.cm-tooltip': {
|
||||
// NOTE: fontFamily is not set here, as most tooltips use the UI font
|
||||
fontSize: 'var(--font-size)',
|
||||
},
|
||||
})
|
||||
|
||||
export const setOptionsTheme = (options: Options): TransactionSpec => {
|
||||
return {
|
||||
effects: optionsThemeConf.reconfigure(createThemeFromOptions(options)),
|
||||
|
|
|
@ -24,16 +24,18 @@ export const annotations = () => [
|
|||
lintGutter({
|
||||
hoverTime: 0,
|
||||
}),
|
||||
/**
|
||||
* A theme which moves the lint gutter outside the line numbers.
|
||||
*/
|
||||
EditorView.baseTheme({
|
||||
'.cm-gutter-lint': {
|
||||
order: -1,
|
||||
},
|
||||
}),
|
||||
annotationsTheme,
|
||||
]
|
||||
|
||||
/**
|
||||
* A theme which moves the lint gutter outside the line numbers.
|
||||
*/
|
||||
const annotationsTheme = EditorView.baseTheme({
|
||||
'.cm-gutter-lint': {
|
||||
order: -1,
|
||||
},
|
||||
})
|
||||
|
||||
export const lintSourceConfig = {
|
||||
delay: 100,
|
||||
// Show highlights only for errors
|
||||
|
|
|
@ -134,9 +134,11 @@ export const bracketSelection = (): Extension[] => [
|
|||
return false
|
||||
},
|
||||
}),
|
||||
EditorView.baseTheme({
|
||||
'.cm-matchingBracket': {
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
}),
|
||||
matchingBracketTheme,
|
||||
]
|
||||
|
||||
const matchingBracketTheme = EditorView.baseTheme({
|
||||
'.cm-matchingBracket': {
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
})
|
||||
|
|
|
@ -26,49 +26,51 @@ export const cursorHighlights = () => {
|
|||
return [
|
||||
cursorHighlightsState,
|
||||
cursorHighlightsLayer,
|
||||
cursorHighlightsTheme,
|
||||
hoverTooltip(cursorTooltip, {
|
||||
hoverTime: 1,
|
||||
}),
|
||||
EditorView.theme({
|
||||
'.ol-cm-cursorHighlightsLayer': {
|
||||
zIndex: 100,
|
||||
contain: 'size style',
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
'.ol-cm-cursorHighlight': {
|
||||
color: 'hsl(var(--hue), 70%, 50%)',
|
||||
borderLeft: '2px solid hsl(var(--hue), 70%, 50%)',
|
||||
display: 'inline-block',
|
||||
height: '1.6em',
|
||||
position: 'absolute',
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
'.ol-cm-cursorHighlight:before': {
|
||||
content: "''",
|
||||
position: 'absolute',
|
||||
left: '-2px',
|
||||
top: '-5px',
|
||||
height: '5px',
|
||||
width: '5px',
|
||||
borderWidth: '3px 3px 2px 2px',
|
||||
borderStyle: 'solid',
|
||||
borderColor: 'inherit',
|
||||
},
|
||||
'.ol-cm-cursorHighlightLabel': {
|
||||
lineHeight: 1,
|
||||
backgroundColor: 'hsl(var(--hue), 70%, 50%)',
|
||||
padding: '1em 1em',
|
||||
fontSize: '0.8rem',
|
||||
fontFamily: 'Lato, sans-serif',
|
||||
color: 'white',
|
||||
fontWeight: 700,
|
||||
whiteSpace: 'nowrap',
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
}),
|
||||
]
|
||||
}
|
||||
|
||||
const cursorHighlightsTheme = EditorView.theme({
|
||||
'.ol-cm-cursorHighlightsLayer': {
|
||||
zIndex: 100,
|
||||
contain: 'size style',
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
'.ol-cm-cursorHighlight': {
|
||||
color: 'hsl(var(--hue), 70%, 50%)',
|
||||
borderLeft: '2px solid hsl(var(--hue), 70%, 50%)',
|
||||
display: 'inline-block',
|
||||
height: '1.6em',
|
||||
position: 'absolute',
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
'.ol-cm-cursorHighlight:before': {
|
||||
content: "''",
|
||||
position: 'absolute',
|
||||
left: '-2px',
|
||||
top: '-5px',
|
||||
height: '5px',
|
||||
width: '5px',
|
||||
borderWidth: '3px 3px 2px 2px',
|
||||
borderStyle: 'solid',
|
||||
borderColor: 'inherit',
|
||||
},
|
||||
'.ol-cm-cursorHighlightLabel': {
|
||||
lineHeight: 1,
|
||||
backgroundColor: 'hsl(var(--hue), 70%, 50%)',
|
||||
padding: '1em 1em',
|
||||
fontSize: '0.8rem',
|
||||
fontFamily: 'Lato, sans-serif',
|
||||
color: 'white',
|
||||
fontWeight: 700,
|
||||
whiteSpace: 'nowrap',
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
})
|
||||
|
||||
class HighlightRangeValue extends RangeValue {
|
||||
mapMode = MapMode.Simple
|
||||
|
||||
|
|
|
@ -12,24 +12,22 @@ import { updateHasReviewPanelToggledEffect } from './changes/change-manager'
|
|||
* of the coords to cover the full line height.
|
||||
*/
|
||||
export const drawSelection = () => {
|
||||
return [cursorLayer, selectionLayer, hideNativeSelection]
|
||||
return [cursorLayer, selectionLayer, Prec.highest(hideNativeSelection)]
|
||||
}
|
||||
|
||||
const canHidePrimary = !browser.ios
|
||||
|
||||
const hideNativeSelection = Prec.highest(
|
||||
EditorView.theme({
|
||||
'.cm-line': {
|
||||
'caret-color': canHidePrimary ? 'transparent !important' : null,
|
||||
'& ::selection': {
|
||||
backgroundColor: 'transparent !important',
|
||||
},
|
||||
'&::selection': {
|
||||
backgroundColor: 'transparent !important',
|
||||
},
|
||||
const hideNativeSelection = EditorView.theme({
|
||||
'.cm-line': {
|
||||
'caret-color': canHidePrimary ? 'transparent !important' : null,
|
||||
'& ::selection': {
|
||||
backgroundColor: 'transparent !important',
|
||||
},
|
||||
})
|
||||
)
|
||||
'&::selection': {
|
||||
backgroundColor: 'transparent !important',
|
||||
},
|
||||
},
|
||||
})
|
||||
|
||||
const cursorLayer = layer({
|
||||
above: true,
|
||||
|
|
|
@ -70,10 +70,12 @@ export const emptyLineFiller = () => {
|
|||
},
|
||||
}
|
||||
),
|
||||
EditorView.baseTheme({
|
||||
'.ol-cm-filler': {
|
||||
padding: '0 2px',
|
||||
},
|
||||
}),
|
||||
emptyLineFillerTheme,
|
||||
]
|
||||
}
|
||||
|
||||
const emptyLineFillerTheme = EditorView.baseTheme({
|
||||
'.ol-cm-filler': {
|
||||
padding: '0 2px',
|
||||
},
|
||||
})
|
||||
|
|
|
@ -17,49 +17,51 @@ export const goToLinePanel = () => {
|
|||
},
|
||||
])
|
||||
),
|
||||
EditorView.baseTheme({
|
||||
'.cm-panel.cm-gotoLine': {
|
||||
padding: '10px',
|
||||
fontSize: '14px',
|
||||
'& label': {
|
||||
margin: 0,
|
||||
fontSize: '14px',
|
||||
'& .cm-textfield': {
|
||||
margin: '0 10px',
|
||||
maxWidth: '100px',
|
||||
height: '34px',
|
||||
padding: '5px 16px',
|
||||
fontSize: '14px',
|
||||
fontWeight: 'normal',
|
||||
lineHeight: 'var(--line-height-base)',
|
||||
color: 'var(--input-color)',
|
||||
backgroundColor: '#fff',
|
||||
backgroundImage: 'none',
|
||||
borderRadius: 'var(--input-border-radius)',
|
||||
boxShadow: 'inset 0 1px 1px rgb(0 0 0 / 8%)',
|
||||
transition:
|
||||
'border-color ease-in-out .15s, box-shadow ease-in-out .15s',
|
||||
'&:focus-visible': {
|
||||
outline: 'none',
|
||||
},
|
||||
'&:focus': {
|
||||
borderColor: 'var(--input-border-focus)',
|
||||
},
|
||||
},
|
||||
},
|
||||
'& .cm-button': {
|
||||
padding: '4px 16px 5px',
|
||||
textTransform: 'capitalize',
|
||||
fontSize: '14px',
|
||||
lineHeight: 'var(--line-height-base)',
|
||||
userSelect: 'none',
|
||||
backgroundImage: 'none',
|
||||
backgroundColor: 'var(--btn-default-bg)',
|
||||
borderRadius: 'var(--btn-border-radius-base)',
|
||||
border: '0 solid transparent',
|
||||
color: '#fff',
|
||||
},
|
||||
},
|
||||
}),
|
||||
gotoLineTheme,
|
||||
]
|
||||
}
|
||||
|
||||
const gotoLineTheme = EditorView.baseTheme({
|
||||
'.cm-panel.cm-gotoLine': {
|
||||
padding: '10px',
|
||||
fontSize: '14px',
|
||||
'& label': {
|
||||
margin: 0,
|
||||
fontSize: '14px',
|
||||
'& .cm-textfield': {
|
||||
margin: '0 10px',
|
||||
maxWidth: '100px',
|
||||
height: '34px',
|
||||
padding: '5px 16px',
|
||||
fontSize: '14px',
|
||||
fontWeight: 'normal',
|
||||
lineHeight: 'var(--line-height-base)',
|
||||
color: 'var(--input-color)',
|
||||
backgroundColor: '#fff',
|
||||
backgroundImage: 'none',
|
||||
borderRadius: 'var(--input-border-radius)',
|
||||
boxShadow: 'inset 0 1px 1px rgb(0 0 0 / 8%)',
|
||||
transition:
|
||||
'border-color ease-in-out .15s, box-shadow ease-in-out .15s',
|
||||
'&:focus-visible': {
|
||||
outline: 'none',
|
||||
},
|
||||
'&:focus': {
|
||||
borderColor: 'var(--input-border-focus)',
|
||||
},
|
||||
},
|
||||
},
|
||||
'& .cm-button': {
|
||||
padding: '4px 16px 5px',
|
||||
textTransform: 'capitalize',
|
||||
fontSize: '14px',
|
||||
lineHeight: 'var(--line-height-base)',
|
||||
userSelect: 'none',
|
||||
backgroundImage: 'none',
|
||||
backgroundColor: 'var(--btn-default-bg)',
|
||||
borderRadius: 'var(--btn-border-radius-base)',
|
||||
border: '0 solid transparent',
|
||||
color: '#fff',
|
||||
},
|
||||
},
|
||||
})
|
||||
|
|
|
@ -20,14 +20,16 @@ export const highlightActiveLine = (visual: boolean) => {
|
|||
return sourceOnly(visual, [
|
||||
activeLineLayer,
|
||||
singleLineHighlighter,
|
||||
EditorView.baseTheme({
|
||||
'.ol-cm-activeLineLayer': {
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
}),
|
||||
highlightActiveLineTheme,
|
||||
])
|
||||
}
|
||||
|
||||
const highlightActiveLineTheme = EditorView.baseTheme({
|
||||
'.ol-cm-activeLineLayer': {
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
})
|
||||
|
||||
/**
|
||||
* Line decoration approach used for non-wrapped lines, adapted from built-in
|
||||
* CodeMirror 6 highlightActiveLine, licensed under the MIT license:
|
||||
|
|
|
@ -36,10 +36,8 @@ function measureHalfLeading(view: EditorView) {
|
|||
}
|
||||
|
||||
function createTheme(halfLeading: number) {
|
||||
return EditorView.theme({
|
||||
'.cm-content': {
|
||||
'--half-leading': halfLeading + 'px',
|
||||
},
|
||||
return EditorView.contentAttributes.of({
|
||||
style: `--half-leading: ${halfLeading}px`,
|
||||
})
|
||||
}
|
||||
|
||||
|
|
|
@ -251,126 +251,126 @@ export const search = () => {
|
|||
}
|
||||
}
|
||||
}),
|
||||
|
||||
// search form theme
|
||||
EditorView.theme({
|
||||
'.ol-cm-search-form': {
|
||||
padding: '10px',
|
||||
display: 'flex',
|
||||
gap: '10px',
|
||||
background: 'var(--ol-blue-gray-1)',
|
||||
'--ol-cm-search-form-focus-shadow':
|
||||
'inset 0 1px 1px rgb(0 0 0 / 8%), 0 0 8px rgb(102 175 233 / 60%)',
|
||||
'--ol-cm-search-form-error-shadow':
|
||||
'inset 0 1px 1px rgb(0 0 0 / 8%), 0 0 8px var(--input-shadow-danger-color)',
|
||||
},
|
||||
'.ol-cm-search-controls': {
|
||||
display: 'grid',
|
||||
gridTemplateColumns: 'auto auto',
|
||||
gridTemplateRows: 'auto auto',
|
||||
gap: '10px',
|
||||
},
|
||||
'.ol-cm-search-form-row': {
|
||||
display: 'flex',
|
||||
gap: '10px',
|
||||
justifyContent: 'space-between',
|
||||
},
|
||||
'.ol-cm-search-form-group': {
|
||||
display: 'flex',
|
||||
gap: '10px',
|
||||
alignItems: 'center',
|
||||
},
|
||||
'.ol-cm-search-input-group': {
|
||||
border: '1px solid var(--input-border)',
|
||||
borderRadius: '20px',
|
||||
background: 'white',
|
||||
width: '100%',
|
||||
maxWidth: '25em',
|
||||
'& input[type="text"]': {
|
||||
background: 'none',
|
||||
boxShadow: 'none',
|
||||
},
|
||||
'& input[type="text"]:focus': {
|
||||
outline: 'none',
|
||||
boxShadow: 'none',
|
||||
},
|
||||
'& .btn.btn': {
|
||||
background: 'var(--ol-blue-gray-0)',
|
||||
color: 'var(--ol-blue-gray-3)',
|
||||
borderRadius: '50%',
|
||||
height: '2em',
|
||||
display: 'inline-flex',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
width: '2em',
|
||||
marginRight: '3px',
|
||||
'&.checked': {
|
||||
color: '#fff',
|
||||
backgroundColor: 'var(--ol-blue)',
|
||||
},
|
||||
'&:active': {
|
||||
boxShadow: 'none',
|
||||
},
|
||||
},
|
||||
'&:focus-within': {
|
||||
borderColor: 'var(--input-border-focus)',
|
||||
boxShadow: 'var(--ol-cm-search-form-focus-shadow)',
|
||||
},
|
||||
},
|
||||
'.ol-cm-search-input-group.ol-cm-search-input-error': {
|
||||
'&:focus-within': {
|
||||
borderColor: 'var(--input-border-danger)',
|
||||
boxShadow: 'var(--ol-cm-search-form-error-shadow)',
|
||||
},
|
||||
},
|
||||
'.input-group .ol-cm-search-form-input': {
|
||||
border: 'none',
|
||||
},
|
||||
'.ol-cm-search-input-button': {
|
||||
background: '#fff',
|
||||
color: 'inherit',
|
||||
border: 'none',
|
||||
},
|
||||
'.ol-cm-search-input-button.focused': {
|
||||
borderColor: 'var(--input-border-focus)',
|
||||
boxShadow: 'var(--ol-cm-search-form-focus-shadow)',
|
||||
},
|
||||
'.ol-cm-search-form-button-group': {
|
||||
flexShrink: 0,
|
||||
},
|
||||
'.ol-cm-search-form-position': {
|
||||
flexShrink: 0,
|
||||
color: 'var(--ol-blue-gray-4)',
|
||||
},
|
||||
'.ol-cm-search-hidden-inputs': {
|
||||
position: 'absolute',
|
||||
left: '-10000px',
|
||||
},
|
||||
'.ol-cm-search-form-close': {
|
||||
flex: 1,
|
||||
},
|
||||
'.ol-cm-search-replace-input': {
|
||||
order: 3,
|
||||
},
|
||||
'.ol-cm-search-replace-buttons': {
|
||||
order: 4,
|
||||
},
|
||||
'.ol-cm-stored-selection': {
|
||||
background: 'rgba(125, 125, 125, 0.1)',
|
||||
paddingTop: 'var(--half-leading)',
|
||||
paddingBottom: 'var(--half-leading)',
|
||||
},
|
||||
// set the default "match" style
|
||||
'.cm-selectionMatch, .cm-searchMatch': {
|
||||
backgroundColor: 'transparent',
|
||||
outlineOffset: '-1px',
|
||||
paddingTop: 'var(--half-leading)',
|
||||
paddingBottom: 'var(--half-leading)',
|
||||
},
|
||||
// make sure selectionMatch inside searchMatch doesn't have a background colour
|
||||
'.cm-searchMatch .cm-selectionMatch': {
|
||||
backgroundColor: 'transparent !important',
|
||||
},
|
||||
}),
|
||||
searchFormTheme,
|
||||
]
|
||||
}
|
||||
|
||||
const searchFormTheme = EditorView.theme({
|
||||
'.ol-cm-search-form': {
|
||||
padding: '10px',
|
||||
display: 'flex',
|
||||
gap: '10px',
|
||||
background: 'var(--ol-blue-gray-1)',
|
||||
'--ol-cm-search-form-focus-shadow':
|
||||
'inset 0 1px 1px rgb(0 0 0 / 8%), 0 0 8px rgb(102 175 233 / 60%)',
|
||||
'--ol-cm-search-form-error-shadow':
|
||||
'inset 0 1px 1px rgb(0 0 0 / 8%), 0 0 8px var(--input-shadow-danger-color)',
|
||||
},
|
||||
'.ol-cm-search-controls': {
|
||||
display: 'grid',
|
||||
gridTemplateColumns: 'auto auto',
|
||||
gridTemplateRows: 'auto auto',
|
||||
gap: '10px',
|
||||
},
|
||||
'.ol-cm-search-form-row': {
|
||||
display: 'flex',
|
||||
gap: '10px',
|
||||
justifyContent: 'space-between',
|
||||
},
|
||||
'.ol-cm-search-form-group': {
|
||||
display: 'flex',
|
||||
gap: '10px',
|
||||
alignItems: 'center',
|
||||
},
|
||||
'.ol-cm-search-input-group': {
|
||||
border: '1px solid var(--input-border)',
|
||||
borderRadius: '20px',
|
||||
background: 'white',
|
||||
width: '100%',
|
||||
maxWidth: '25em',
|
||||
'& input[type="text"]': {
|
||||
background: 'none',
|
||||
boxShadow: 'none',
|
||||
},
|
||||
'& input[type="text"]:focus': {
|
||||
outline: 'none',
|
||||
boxShadow: 'none',
|
||||
},
|
||||
'& .btn.btn': {
|
||||
background: 'var(--ol-blue-gray-0)',
|
||||
color: 'var(--ol-blue-gray-3)',
|
||||
borderRadius: '50%',
|
||||
height: '2em',
|
||||
display: 'inline-flex',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
width: '2em',
|
||||
marginRight: '3px',
|
||||
'&.checked': {
|
||||
color: '#fff',
|
||||
backgroundColor: 'var(--ol-blue)',
|
||||
},
|
||||
'&:active': {
|
||||
boxShadow: 'none',
|
||||
},
|
||||
},
|
||||
'&:focus-within': {
|
||||
borderColor: 'var(--input-border-focus)',
|
||||
boxShadow: 'var(--ol-cm-search-form-focus-shadow)',
|
||||
},
|
||||
},
|
||||
'.ol-cm-search-input-group.ol-cm-search-input-error': {
|
||||
'&:focus-within': {
|
||||
borderColor: 'var(--input-border-danger)',
|
||||
boxShadow: 'var(--ol-cm-search-form-error-shadow)',
|
||||
},
|
||||
},
|
||||
'.input-group .ol-cm-search-form-input': {
|
||||
border: 'none',
|
||||
},
|
||||
'.ol-cm-search-input-button': {
|
||||
background: '#fff',
|
||||
color: 'inherit',
|
||||
border: 'none',
|
||||
},
|
||||
'.ol-cm-search-input-button.focused': {
|
||||
borderColor: 'var(--input-border-focus)',
|
||||
boxShadow: 'var(--ol-cm-search-form-focus-shadow)',
|
||||
},
|
||||
'.ol-cm-search-form-button-group': {
|
||||
flexShrink: 0,
|
||||
},
|
||||
'.ol-cm-search-form-position': {
|
||||
flexShrink: 0,
|
||||
color: 'var(--ol-blue-gray-4)',
|
||||
},
|
||||
'.ol-cm-search-hidden-inputs': {
|
||||
position: 'absolute',
|
||||
left: '-10000px',
|
||||
},
|
||||
'.ol-cm-search-form-close': {
|
||||
flex: 1,
|
||||
},
|
||||
'.ol-cm-search-replace-input': {
|
||||
order: 3,
|
||||
},
|
||||
'.ol-cm-search-replace-buttons': {
|
||||
order: 4,
|
||||
},
|
||||
'.ol-cm-stored-selection': {
|
||||
background: 'rgba(125, 125, 125, 0.1)',
|
||||
paddingTop: 'var(--half-leading)',
|
||||
paddingBottom: 'var(--half-leading)',
|
||||
},
|
||||
// set the default "match" style
|
||||
'.cm-selectionMatch, .cm-searchMatch': {
|
||||
backgroundColor: 'transparent',
|
||||
outlineOffset: '-1px',
|
||||
paddingTop: 'var(--half-leading)',
|
||||
paddingBottom: 'var(--half-leading)',
|
||||
},
|
||||
// make sure selectionMatch inside searchMatch doesn't have a background colour
|
||||
'.cm-searchMatch .cm-selectionMatch': {
|
||||
backgroundColor: 'transparent !important',
|
||||
},
|
||||
})
|
||||
|
|
|
@ -31,19 +31,7 @@ type Options = { spellCheckLanguage?: string }
|
|||
*/
|
||||
export const spelling = ({ spellCheckLanguage }: Options) => {
|
||||
return [
|
||||
EditorView.baseTheme({
|
||||
'.ol-cm-spelling-error': {
|
||||
textDecorationColor: 'red',
|
||||
textDecorationLine: 'underline',
|
||||
textDecorationStyle: 'dotted',
|
||||
textDecorationThickness: '2px',
|
||||
textDecorationSkipInk: 'none',
|
||||
textUnderlineOffset: '0.2em',
|
||||
},
|
||||
'.cm-tooltip.ol-cm-spelling-context-menu-tooltip': {
|
||||
borderWidth: '0',
|
||||
},
|
||||
}),
|
||||
spellingTheme,
|
||||
parserWatcher,
|
||||
spellCheckLanguageConf.of(spellCheckLanguageFacet.of(spellCheckLanguage)),
|
||||
spellCheckField,
|
||||
|
@ -54,6 +42,20 @@ export const spelling = ({ spellCheckLanguage }: Options) => {
|
|||
]
|
||||
}
|
||||
|
||||
const spellingTheme = EditorView.baseTheme({
|
||||
'.ol-cm-spelling-error': {
|
||||
textDecorationColor: 'red',
|
||||
textDecorationLine: 'underline',
|
||||
textDecorationStyle: 'dotted',
|
||||
textDecorationThickness: '2px',
|
||||
textDecorationSkipInk: 'none',
|
||||
textUnderlineOffset: '0.2em',
|
||||
},
|
||||
'.cm-tooltip.ol-cm-spelling-context-menu-tooltip': {
|
||||
borderWidth: '0',
|
||||
},
|
||||
})
|
||||
|
||||
const spellCheckField = StateField.define<SpellChecker | null>({
|
||||
create(state) {
|
||||
const [spellCheckLanguage] = state.facet(spellCheckLanguageFacet)
|
||||
|
|
|
@ -74,44 +74,21 @@ const createThemeFromOptions = ({
|
|||
return [
|
||||
EditorView.editorAttributes.of({
|
||||
class: overallTheme === '' ? 'overall-theme-dark' : 'overall-theme-light',
|
||||
style: Object.entries({
|
||||
'--font-size': `${fontSize}px`,
|
||||
'--source-font-family': fontFamilies[fontFamily]?.join(', '),
|
||||
'--line-height': lineHeights[lineHeight],
|
||||
})
|
||||
.map(([key, value]) => `${key}: ${value}`)
|
||||
.join(';'),
|
||||
}),
|
||||
// set variables for tooltips, which are outside the editor
|
||||
// TODO: set these on document.body, or a new container element for the tooltips, without using a style mod
|
||||
EditorView.theme({
|
||||
'&.cm-editor': {
|
||||
// set variables
|
||||
'--font-size': `${fontSize}px`,
|
||||
'--source-font-family': fontFamilies[fontFamily]?.join(', '),
|
||||
'--line-height': lineHeights[lineHeight],
|
||||
},
|
||||
'.cm-content': {
|
||||
fontSize: 'var(--font-size)',
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
},
|
||||
'.cm-cursor-primary': {
|
||||
fontSize: 'var(--font-size)',
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
},
|
||||
'.cm-gutters': {
|
||||
fontSize: 'var(--font-size)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
},
|
||||
'.cm-tooltip': {
|
||||
// set variables for tooltips, which are outside the editor
|
||||
'--font-size': `${fontSize}px`,
|
||||
'--source-font-family': fontFamilies[fontFamily]?.join(', '),
|
||||
'--line-height': lineHeights[lineHeight],
|
||||
// NOTE: fontFamily is not set here, as most tooltips use the UI font
|
||||
fontSize: 'var(--font-size)',
|
||||
},
|
||||
'.cm-panel': {
|
||||
fontSize: 'var(--font-size)',
|
||||
},
|
||||
'.cm-foldGutter .cm-gutterElement > span': {
|
||||
height: 'calc(var(--font-size) * var(--line-height))',
|
||||
},
|
||||
'.cm-lineNumbers': {
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
},
|
||||
}),
|
||||
]
|
||||
|
@ -121,6 +98,33 @@ const createThemeFromOptions = ({
|
|||
* Base styles that can have &dark and &light variants
|
||||
*/
|
||||
const baseTheme = EditorView.baseTheme({
|
||||
'.cm-content': {
|
||||
fontSize: 'var(--font-size)',
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
},
|
||||
'.cm-cursor-primary': {
|
||||
fontSize: 'var(--font-size)',
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
},
|
||||
'.cm-gutters': {
|
||||
fontSize: 'var(--font-size)',
|
||||
lineHeight: 'var(--line-height)',
|
||||
},
|
||||
'.cm-tooltip': {
|
||||
// NOTE: fontFamily is not set here, as most tooltips use the UI font
|
||||
fontSize: 'var(--font-size)',
|
||||
},
|
||||
'.cm-panel': {
|
||||
fontSize: 'var(--font-size)',
|
||||
},
|
||||
'.cm-foldGutter .cm-gutterElement > span': {
|
||||
height: 'calc(var(--font-size) * var(--line-height))',
|
||||
},
|
||||
'.cm-lineNumbers': {
|
||||
fontFamily: 'var(--source-font-family)',
|
||||
},
|
||||
// use a background color for lint error ranges
|
||||
'.cm-lintRange-error': {
|
||||
padding: 'var(--half-leading, 0) 0',
|
||||
|
@ -255,17 +259,25 @@ const staticTheme = EditorView.theme({
|
|||
},
|
||||
})
|
||||
|
||||
const themeCache = new Map<string, any>()
|
||||
|
||||
const loadSelectedTheme = async (editorTheme: string) => {
|
||||
if (!editorTheme) {
|
||||
editorTheme = 'textmate' // use the default theme if unset
|
||||
}
|
||||
|
||||
const { theme, highlightStyle, dark } = await import(
|
||||
/* webpackChunkName: "cm6-theme" */ `../themes/cm6/${editorTheme}.json`
|
||||
)
|
||||
if (!themeCache.has(editorTheme)) {
|
||||
const { theme, highlightStyle, dark } = await import(
|
||||
/* webpackChunkName: "cm6-theme" */ `../themes/cm6/${editorTheme}.json`
|
||||
)
|
||||
|
||||
return [
|
||||
EditorView.theme(theme, { dark }),
|
||||
EditorView.theme(highlightStyle, { dark }),
|
||||
]
|
||||
const extension = [
|
||||
EditorView.theme(theme, { dark }),
|
||||
EditorView.theme(highlightStyle, { dark }),
|
||||
]
|
||||
|
||||
themeCache.set(editorTheme, extension)
|
||||
}
|
||||
|
||||
return themeCache.get(editorTheme)
|
||||
}
|
||||
|
|
|
@ -21,285 +21,284 @@ export function createToolbarPanel() {
|
|||
return { dom, top: true }
|
||||
}
|
||||
|
||||
const toolbarTheme = EditorView.theme({
|
||||
'.ol-cm-toolbar': {
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
color: 'var(--toolbar-btn-color)',
|
||||
flex: 1,
|
||||
display: 'flex',
|
||||
overflowX: 'hidden',
|
||||
},
|
||||
'&.overall-theme-dark .ol-cm-toolbar': {
|
||||
'& img': {
|
||||
filter: 'invert(1)',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-overflow': {
|
||||
display: 'flex',
|
||||
flexWrap: 'wrap',
|
||||
},
|
||||
'#popover-toolbar-overflow': {
|
||||
padding: 0,
|
||||
borderColor: 'rgba(125, 125, 125, 0.2)',
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
color: 'var(--toolbar-btn-color)',
|
||||
'& .popover-content': {
|
||||
padding: 0,
|
||||
},
|
||||
'& .arrow': {
|
||||
borderBottomColor: 'rgba(125, 125, 125, 0.2)',
|
||||
'&:after': {
|
||||
borderBottomColor: 'var(--editor-toolbar-bg)',
|
||||
},
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-button-menu-popover': {
|
||||
'& > .popover-content': {
|
||||
padding: 0,
|
||||
},
|
||||
'& .arrow': {
|
||||
display: 'none',
|
||||
},
|
||||
'& .list-group': {
|
||||
marginBottom: 0,
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
borderRadius: '4px',
|
||||
},
|
||||
'& .list-group-item': {
|
||||
width: '100%',
|
||||
textAlign: 'start',
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
gap: '5px',
|
||||
color: 'var(--toolbar-btn-color)',
|
||||
borderColor: 'var(--editor-toolbar-bg)',
|
||||
background: 'none',
|
||||
'&:hover, &:focus': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
},
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-button-group': {
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
whiteSpace: 'nowrap',
|
||||
flexWrap: 'nowrap',
|
||||
padding: '0 4px',
|
||||
margin: '4px 0',
|
||||
lineHeight: '1',
|
||||
'&:not(:first-of-type)': {
|
||||
borderLeft: '1px solid rgba(125, 125, 125, 0.3)',
|
||||
'&.ol-cm-toolbar-end': {
|
||||
borderLeft: 'none',
|
||||
},
|
||||
'&.ol-cm-toolbar-stretch': {
|
||||
flex: 1,
|
||||
},
|
||||
'&.overflow-hidden': {
|
||||
borderLeft: 'none',
|
||||
},
|
||||
},
|
||||
'&.overflow-hidden': {
|
||||
width: 0,
|
||||
padding: 0,
|
||||
},
|
||||
},
|
||||
'.formatting-buttons-wrapper': {
|
||||
flex: 1,
|
||||
},
|
||||
'.ol-cm-toolbar-button': {
|
||||
display: 'inline-flex',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
padding: '0',
|
||||
margin: '0 1px',
|
||||
backgroundColor: 'transparent',
|
||||
border: 'none',
|
||||
borderRadius: '1px',
|
||||
lineHeight: '1',
|
||||
width: '24px',
|
||||
height: '24px',
|
||||
overflow: 'hidden',
|
||||
'&:hover, &:focus, &:active, &.active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.1)',
|
||||
color: 'inherit',
|
||||
boxShadow: 'none',
|
||||
'&[aria-disabled="true"]': {
|
||||
opacity: '0.2',
|
||||
},
|
||||
},
|
||||
'&.active, &:active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
},
|
||||
'&[aria-disabled="true"]': {
|
||||
opacity: '0.2',
|
||||
cursor: 'not-allowed',
|
||||
},
|
||||
'.overflow-hidden &': {
|
||||
display: 'none',
|
||||
},
|
||||
'&.ol-cm-toolbar-button-math': {
|
||||
fontFamily: '"Noto Serif", serif',
|
||||
fontSize: '16px',
|
||||
fontWeight: 700,
|
||||
},
|
||||
},
|
||||
'&.overall-theme-dark .ol-cm-toolbar-button': {
|
||||
opacity: 0.8,
|
||||
'&:hover, &:focus, &:active, &.active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
},
|
||||
'&.active, &:active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.4)',
|
||||
},
|
||||
'&[aria-disabled="true"]': {
|
||||
opacity: 0.2,
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-end': {
|
||||
justifyContent: 'flex-end',
|
||||
'& .badge': {
|
||||
marginRight: '5px',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-overflow-toggle': {
|
||||
display: 'none',
|
||||
'&.ol-cm-toolbar-overflow-toggle-visible': {
|
||||
display: 'flex',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-menu-toggle': {
|
||||
background: 'transparent',
|
||||
boxShadow: 'none !important',
|
||||
border: 'none',
|
||||
whiteSpace: 'nowrap',
|
||||
color: 'inherit',
|
||||
borderRadius: '0',
|
||||
opacity: 0.8,
|
||||
width: '120px',
|
||||
fontSize: '13px',
|
||||
fontFamily: 'Lato',
|
||||
fontWeight: '700',
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'space-between',
|
||||
padding: '5px 6px',
|
||||
'&:hover, &:focus, &.active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.1)',
|
||||
opacity: '1',
|
||||
color: 'inherit',
|
||||
},
|
||||
'& .caret': {
|
||||
marginTop: '0',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-menu-popover': {
|
||||
border: 'none',
|
||||
borderRadius: '0',
|
||||
borderBottomLeftRadius: '4px',
|
||||
borderBottomRightRadius: '4px',
|
||||
boxShadow: '0 2px 5px rgb(0 0 0 / 20%)',
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
color: 'var(--toolbar-btn-color)',
|
||||
padding: '0',
|
||||
'&.bottom': {
|
||||
marginTop: '1px',
|
||||
},
|
||||
'&.top': {
|
||||
marginBottom: '1px',
|
||||
},
|
||||
'& .arrow': {
|
||||
display: 'none',
|
||||
},
|
||||
'& .popover-content': {
|
||||
padding: '0',
|
||||
},
|
||||
'& .ol-cm-toolbar-menu': {
|
||||
width: '120px',
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
boxSizing: 'border-box',
|
||||
fontSize: '14px',
|
||||
},
|
||||
'& .ol-cm-toolbar-menu-item': {
|
||||
border: 'none',
|
||||
background: 'none',
|
||||
padding: '4px 12px',
|
||||
height: '40px',
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
fontWeight: 'bold',
|
||||
'&.ol-cm-toolbar-menu-item-active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.1)',
|
||||
},
|
||||
'&:hover': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
color: 'inherit',
|
||||
},
|
||||
'&.section-level-section': {
|
||||
fontSize: '1.44em',
|
||||
},
|
||||
'&.section-level-subsection': {
|
||||
fontSize: '1.2em',
|
||||
},
|
||||
'&.section-level-body': {
|
||||
fontWeight: 'normal',
|
||||
},
|
||||
},
|
||||
},
|
||||
'&.overall-theme-dark .ol-cm-toolbar-table-grid-popover': {
|
||||
color: '#fff',
|
||||
},
|
||||
'&.overall-theme-dark .ol-cm-toolbar-table-grid': {
|
||||
'& td.active': {
|
||||
outlineColor: 'white',
|
||||
background: 'rgb(125, 125, 125)',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-table-grid': {
|
||||
borderCollapse: 'separate',
|
||||
tableLayout: 'fixed',
|
||||
fontSize: '6px',
|
||||
cursor: 'pointer',
|
||||
width: '160px',
|
||||
'& td': {
|
||||
outline: '1px solid #E7E9EE',
|
||||
outlineOffset: '-2px',
|
||||
width: '16px',
|
||||
height: '16px',
|
||||
|
||||
'&.active': {
|
||||
outlineColor: '#3265B2',
|
||||
background: '#F1F4F9',
|
||||
},
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-table-size-label': {
|
||||
maxWidth: '160px',
|
||||
fontFamily: 'Lato, sans-serif',
|
||||
fontSize: '12px',
|
||||
},
|
||||
'.ol-cm-toolbar-table-grid-popover': {
|
||||
maxWidth: 'unset',
|
||||
padding: '8px',
|
||||
boxShadow: '0 5px 10px rgba(0, 0, 0, 0.2)',
|
||||
borderRadius: '4px',
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
pointerEvents: 'all',
|
||||
},
|
||||
'.ol-cm-toolbar-button-menu-popover-unstyled': {
|
||||
maxWidth: 'unset',
|
||||
background: 'transparent',
|
||||
border: 0,
|
||||
padding: '0 8px 8px 160px',
|
||||
boxShadow: 'none',
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
})
|
||||
|
||||
/**
|
||||
* A panel which contains the editor toolbar, provided by a state field which allows the toolbar to be toggled,
|
||||
* and styles for the toolbar.
|
||||
*/
|
||||
export const toolbarPanel = () => [
|
||||
toolbarState,
|
||||
EditorView.theme({
|
||||
'.ol-cm-toolbar': {
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
color: 'var(--toolbar-btn-color)',
|
||||
flex: 1,
|
||||
display: 'flex',
|
||||
overflowX: 'hidden',
|
||||
},
|
||||
'&.overall-theme-dark .ol-cm-toolbar': {
|
||||
'& img': {
|
||||
filter: 'invert(1)',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-overflow': {
|
||||
display: 'flex',
|
||||
flexWrap: 'wrap',
|
||||
},
|
||||
'#popover-toolbar-overflow': {
|
||||
padding: 0,
|
||||
borderColor: 'rgba(125, 125, 125, 0.2)',
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
color: 'var(--toolbar-btn-color)',
|
||||
'& .popover-content': {
|
||||
padding: 0,
|
||||
},
|
||||
'& .arrow': {
|
||||
borderBottomColor: 'rgba(125, 125, 125, 0.2)',
|
||||
'&:after': {
|
||||
borderBottomColor: 'var(--editor-toolbar-bg)',
|
||||
},
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-button-menu-popover': {
|
||||
'& > .popover-content': {
|
||||
padding: 0,
|
||||
},
|
||||
'& .arrow': {
|
||||
display: 'none',
|
||||
},
|
||||
'& .list-group': {
|
||||
marginBottom: 0,
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
borderRadius: '4px',
|
||||
},
|
||||
'& .list-group-item': {
|
||||
width: '100%',
|
||||
textAlign: 'start',
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
gap: '5px',
|
||||
color: 'var(--toolbar-btn-color)',
|
||||
borderColor: 'var(--editor-toolbar-bg)',
|
||||
background: 'none',
|
||||
'&:hover, &:focus': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
},
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-button-group': {
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
whiteSpace: 'nowrap',
|
||||
flexWrap: 'nowrap',
|
||||
padding: '0 4px',
|
||||
margin: '4px 0',
|
||||
lineHeight: '1',
|
||||
'&:not(:first-of-type)': {
|
||||
borderLeft: '1px solid rgba(125, 125, 125, 0.3)',
|
||||
'&.ol-cm-toolbar-end': {
|
||||
borderLeft: 'none',
|
||||
},
|
||||
'&.ol-cm-toolbar-stretch': {
|
||||
flex: 1,
|
||||
},
|
||||
'&.overflow-hidden': {
|
||||
borderLeft: 'none',
|
||||
},
|
||||
},
|
||||
'&.overflow-hidden': {
|
||||
width: 0,
|
||||
padding: 0,
|
||||
},
|
||||
},
|
||||
'.formatting-buttons-wrapper': {
|
||||
flex: 1,
|
||||
},
|
||||
'.ol-cm-toolbar-button': {
|
||||
display: 'inline-flex',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
padding: '0',
|
||||
margin: '0 1px',
|
||||
backgroundColor: 'transparent',
|
||||
border: 'none',
|
||||
borderRadius: '1px',
|
||||
lineHeight: '1',
|
||||
width: '24px',
|
||||
height: '24px',
|
||||
overflow: 'hidden',
|
||||
'&:hover, &:focus, &:active, &.active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.1)',
|
||||
color: 'inherit',
|
||||
boxShadow: 'none',
|
||||
'&[aria-disabled="true"]': {
|
||||
opacity: '0.2',
|
||||
},
|
||||
},
|
||||
'&.active, &:active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
},
|
||||
'&[aria-disabled="true"]': {
|
||||
opacity: '0.2',
|
||||
cursor: 'not-allowed',
|
||||
},
|
||||
'.overflow-hidden &': {
|
||||
display: 'none',
|
||||
},
|
||||
'&.ol-cm-toolbar-button-math': {
|
||||
fontFamily: '"Noto Serif", serif',
|
||||
fontSize: '16px',
|
||||
fontWeight: 700,
|
||||
},
|
||||
},
|
||||
'&.overall-theme-dark .ol-cm-toolbar-button': {
|
||||
opacity: 0.8,
|
||||
'&:hover, &:focus, &:active, &.active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
},
|
||||
'&.active, &:active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.4)',
|
||||
},
|
||||
'&[aria-disabled="true"]': {
|
||||
opacity: 0.2,
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-end': {
|
||||
justifyContent: 'flex-end',
|
||||
'& .badge': {
|
||||
marginRight: '5px',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-overflow-toggle': {
|
||||
display: 'none',
|
||||
'&.ol-cm-toolbar-overflow-toggle-visible': {
|
||||
display: 'flex',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-menu-toggle': {
|
||||
background: 'transparent',
|
||||
boxShadow: 'none !important',
|
||||
border: 'none',
|
||||
whiteSpace: 'nowrap',
|
||||
color: 'inherit',
|
||||
borderRadius: '0',
|
||||
opacity: 0.8,
|
||||
width: '120px',
|
||||
fontSize: '13px',
|
||||
fontFamily: 'Lato',
|
||||
fontWeight: '700',
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'space-between',
|
||||
padding: '5px 6px',
|
||||
'&:hover, &:focus, &.active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.1)',
|
||||
opacity: '1',
|
||||
color: 'inherit',
|
||||
},
|
||||
'& .caret': {
|
||||
marginTop: '0',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-menu-popover': {
|
||||
border: 'none',
|
||||
borderRadius: '0',
|
||||
borderBottomLeftRadius: '4px',
|
||||
borderBottomRightRadius: '4px',
|
||||
boxShadow: '0 2px 5px rgb(0 0 0 / 20%)',
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
color: 'var(--toolbar-btn-color)',
|
||||
padding: '0',
|
||||
'&.bottom': {
|
||||
marginTop: '1px',
|
||||
},
|
||||
'&.top': {
|
||||
marginBottom: '1px',
|
||||
},
|
||||
'& .arrow': {
|
||||
display: 'none',
|
||||
},
|
||||
'& .popover-content': {
|
||||
padding: '0',
|
||||
},
|
||||
'& .ol-cm-toolbar-menu': {
|
||||
width: '120px',
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
boxSizing: 'border-box',
|
||||
fontSize: '14px',
|
||||
},
|
||||
'& .ol-cm-toolbar-menu-item': {
|
||||
border: 'none',
|
||||
background: 'none',
|
||||
padding: '4px 12px',
|
||||
height: '40px',
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
fontWeight: 'bold',
|
||||
'&.ol-cm-toolbar-menu-item-active': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.1)',
|
||||
},
|
||||
'&:hover': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
color: 'inherit',
|
||||
},
|
||||
'&.section-level-section': {
|
||||
fontSize: '1.44em',
|
||||
},
|
||||
'&.section-level-subsection': {
|
||||
fontSize: '1.2em',
|
||||
},
|
||||
'&.section-level-body': {
|
||||
fontWeight: 'normal',
|
||||
},
|
||||
},
|
||||
},
|
||||
'&.overall-theme-dark .ol-cm-toolbar-table-grid-popover': {
|
||||
color: '#fff',
|
||||
},
|
||||
'&.overall-theme-dark .ol-cm-toolbar-table-grid': {
|
||||
'& td.active': {
|
||||
outlineColor: 'white',
|
||||
background: 'rgb(125, 125, 125)',
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-table-grid': {
|
||||
borderCollapse: 'separate',
|
||||
tableLayout: 'fixed',
|
||||
fontSize: '6px',
|
||||
cursor: 'pointer',
|
||||
width: '160px',
|
||||
'& td': {
|
||||
outline: '1px solid #E7E9EE',
|
||||
outlineOffset: '-2px',
|
||||
width: '16px',
|
||||
height: '16px',
|
||||
|
||||
'&.active': {
|
||||
outlineColor: '#3265B2',
|
||||
background: '#F1F4F9',
|
||||
},
|
||||
},
|
||||
},
|
||||
'.ol-cm-toolbar-table-size-label': {
|
||||
maxWidth: '160px',
|
||||
fontFamily: 'Lato, sans-serif',
|
||||
fontSize: '12px',
|
||||
},
|
||||
'.ol-cm-toolbar-table-grid-popover': {
|
||||
maxWidth: 'unset',
|
||||
padding: '8px',
|
||||
boxShadow: '0 5px 10px rgba(0, 0, 0, 0.2)',
|
||||
borderRadius: '4px',
|
||||
backgroundColor: 'var(--editor-toolbar-bg)',
|
||||
pointerEvents: 'all',
|
||||
},
|
||||
'.ol-cm-toolbar-button-menu-popover-unstyled': {
|
||||
maxWidth: 'unset',
|
||||
background: 'transparent',
|
||||
border: 0,
|
||||
padding: '0 8px 8px 160px',
|
||||
boxShadow: 'none',
|
||||
pointerEvents: 'none',
|
||||
},
|
||||
}),
|
||||
]
|
||||
export const toolbarPanel = () => [toolbarState, toolbarTheme]
|
||||
|
|
|
@ -42,6 +42,59 @@ export const storePastedContent = (
|
|||
effects: pastedContentEffect.of({ content, formatted }),
|
||||
})
|
||||
|
||||
const pastedContentTheme = EditorView.baseTheme({
|
||||
'.ol-cm-pasted-content-menu-toggle': {
|
||||
background: 'none',
|
||||
borderRadius: '8px',
|
||||
border: '1px solid rgb(125, 125, 125)',
|
||||
margin: '0 4px',
|
||||
opacity: '0.7',
|
||||
'&:hover': {
|
||||
opacity: '1',
|
||||
},
|
||||
},
|
||||
'.ol-cm-pasted-content-menu-popover': {
|
||||
maxWidth: 'unset',
|
||||
'& .popover-content': {
|
||||
padding: 0,
|
||||
},
|
||||
},
|
||||
'&dark .ol-cm-pasted-content-menu-popover': {
|
||||
background: 'rgba(0, 0, 0)',
|
||||
},
|
||||
'.ol-cm-pasted-content-menu': {
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
boxSizing: 'border-box',
|
||||
fontSize: '14px',
|
||||
fontFamily: '"Lato", sans-serif',
|
||||
},
|
||||
'.ol-cm-pasted-content-menu-item': {
|
||||
border: 'none',
|
||||
background: 'none',
|
||||
padding: '8px 16px',
|
||||
width: '100%',
|
||||
display: 'flex',
|
||||
justifyContent: 'space-between',
|
||||
alignItems: 'center',
|
||||
whiteSpace: 'nowrap',
|
||||
gap: '12px',
|
||||
'&[aria-disabled="true"]': {
|
||||
color: 'rgba(125, 125, 125, 0.5)',
|
||||
},
|
||||
'&:hover': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
},
|
||||
},
|
||||
'.ol-cm-pasted-content-menu-item-label': {
|
||||
flex: 1,
|
||||
textAlign: 'left',
|
||||
},
|
||||
'.ol-cm-pasted-content-menu-item-shortcut': {
|
||||
textAlign: 'right',
|
||||
},
|
||||
})
|
||||
|
||||
export const pastedContent = StateField.define<{
|
||||
content: PastedContent
|
||||
formatted: boolean
|
||||
|
@ -88,58 +141,7 @@ export const pastedContent = StateField.define<{
|
|||
|
||||
return Decoration.set(decorations, true)
|
||||
}),
|
||||
EditorView.baseTheme({
|
||||
'.ol-cm-pasted-content-menu-toggle': {
|
||||
background: 'none',
|
||||
borderRadius: '8px',
|
||||
border: '1px solid rgb(125, 125, 125)',
|
||||
margin: '0 4px',
|
||||
opacity: '0.7',
|
||||
'&:hover': {
|
||||
opacity: '1',
|
||||
},
|
||||
},
|
||||
'.ol-cm-pasted-content-menu-popover': {
|
||||
maxWidth: 'unset',
|
||||
'& .popover-content': {
|
||||
padding: 0,
|
||||
},
|
||||
},
|
||||
'&dark .ol-cm-pasted-content-menu-popover': {
|
||||
background: 'rgba(0, 0, 0)',
|
||||
},
|
||||
'.ol-cm-pasted-content-menu': {
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
boxSizing: 'border-box',
|
||||
fontSize: '14px',
|
||||
fontFamily: '"Lato", sans-serif',
|
||||
},
|
||||
'.ol-cm-pasted-content-menu-item': {
|
||||
border: 'none',
|
||||
background: 'none',
|
||||
padding: '8px 16px',
|
||||
width: '100%',
|
||||
display: 'flex',
|
||||
justifyContent: 'space-between',
|
||||
alignItems: 'center',
|
||||
whiteSpace: 'nowrap',
|
||||
gap: '12px',
|
||||
'&[aria-disabled="true"]': {
|
||||
color: 'rgba(125, 125, 125, 0.5)',
|
||||
},
|
||||
'&:hover': {
|
||||
backgroundColor: 'rgba(125, 125, 125, 0.2)',
|
||||
},
|
||||
},
|
||||
'.ol-cm-pasted-content-menu-item-label': {
|
||||
flex: 1,
|
||||
textAlign: 'left',
|
||||
},
|
||||
'.ol-cm-pasted-content-menu-item-shortcut': {
|
||||
textAlign: 'right',
|
||||
},
|
||||
}),
|
||||
pastedContentTheme,
|
||||
]
|
||||
},
|
||||
})
|
||||
|
|
|
@ -439,10 +439,8 @@ const currentWidth = Facet.define<string, string>({
|
|||
function createContentWidthTheme(contentWidth: string) {
|
||||
return [
|
||||
currentWidth.of(contentWidth),
|
||||
EditorView.theme({
|
||||
'&.cm-editor': {
|
||||
'--content-width': contentWidth,
|
||||
},
|
||||
EditorView.editorAttributes.of({
|
||||
style: `--content-width: ${contentWidth}`,
|
||||
}),
|
||||
]
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue