This commit is contained in:
Víctor Losada Hernández
2026-08-27 20:33:48 +02:00
parent a321402556
commit c747b60bb7
6 changed files with 117 additions and 134 deletions
@@ -251,13 +251,13 @@ function tokenizeCustomMarkdown(text) {
);
if(match) endCh = match.index + match[0].length;
const closingMatch = lineText.match(/ *(}})/d);
if(closingMatch) {
tokens.push({ line: lineNumber, from: closingMatch.indices[1][0], to: closingMatch.indices[1][1], type: customTags.block });
} else {
tokens.push({ line: lineNumber, type: customTags.block });
}
}
});
@@ -350,10 +350,10 @@ class ImageWidget extends WidgetType {
toDOM() {
const img = document.createElement('img');
img.loading = "lazy";
img.loading = 'lazy';
img.className = 'cm-preview';
img.src = this.url;
img.onerror = ()=>{
img.src = 'client/icons/broken-image.jpg';
@@ -403,8 +403,8 @@ export function customHighlightPlugin(renderer, tab, settings) {
const url = getUrl(node, view.state.doc);
const widgetPosition = node.node.lastChild.from;
//this is not exactly standard, but should hold,
//and is the shortest way i could find of positioning
//this is not exactly standard, but should hold,
//and is the shortest way i could find of positioning
//the image inside the cm-image node
if(!url) return;
+18 -19
View File
@@ -14,7 +14,6 @@ const EDITOR_SETTINGS_KEY = 'HB_edit_settings';
import defaultCM5Theme from '@themes/codeMirror/default.js';
import darkbrewery from '@themes/codeMirror/darkbrewery.js';
import cm5Themes from 'codemirror-5-themes';
import { autoCloseTags } from '@codemirror/lang-javascript';
const themes = { default: defaultCM5Theme, ...cm5Themes, darkbrewery };
@@ -88,13 +87,13 @@ const Editor = forwardRef(
const [view, setView] = useState('text'); // 'text', 'style', 'meta', 'snippet'
const [snippetBarHeight, setSnippetBarHeight] = useState(26);
const [editorSettings, setEditorSettings] = useState({
autoCloseBrackets: true,
showImagePreviews: true,
activeLineShading: true,
lineNumbers: true,
fontSize: 13,
editorTheme: 'default',
})
autoCloseBrackets : true,
showImagePreviews : true,
activeLineShading : true,
lineNumbers : true,
fontSize : 13,
editorTheme : 'default',
});
const editor = useRef(null);
const codeEditor = useRef(null);
@@ -115,10 +114,10 @@ const Editor = forwardRef(
const localEditorTheme = window.localStorage.getItem(EDITOR_THEME_KEY);
if(localEditorTheme && EditorThemes.includes(localEditorTheme)) {
setEditorSettings({...editorSettings , editorTheme: localEditorTheme})
} else setEditorSettings({...editorSettings , editorTheme: 'default'});
setEditorSettings({ ...editorSettings, editorTheme: localEditorTheme });
} else setEditorSettings({ ...editorSettings, editorTheme: 'default' });
const localEditorSettings = window.localStorage.getItem(EDITOR_SETTINGS_KEY);
if (localEditorSettings) setEditorSettings(JSON.parse(localEditorSettings));
if(localEditorSettings) setEditorSettings(JSON.parse(localEditorSettings));
const snippetBar = document.querySelector('.editor > .snippetBar');
if(!snippetBar) return;
@@ -235,13 +234,13 @@ const Editor = forwardRef(
const updateEditorTheme = (newTheme)=>{
window.localStorage.setItem(EDITOR_THEME_KEY, newTheme);
setEditorSettings({...editorSettings , editorTheme: newTheme})
setEditorSettings({ ...editorSettings, editorTheme: newTheme });
};
const updateEditorSettings = (newEditorSettings) => {
const updateEditorSettings = (newEditorSettings)=>{
window.localStorage.setItem(EDITOR_SETTINGS_KEY, JSON.stringify(newEditorSettings));
setEditorSettings(newEditorSettings);
}
};
const renderEditor = ()=>{
if(isText()) {
@@ -324,14 +323,14 @@ const Editor = forwardRef(
if(isSettings()){
return (
<>
<CodeEditor
key='codeEditor'
<CodeEditor
key='codeEditor'
tab='brewSettings' //necessary or the brew object loses its contents, culprit possibly on the tab dependent useEffect in codeEditor.jsx
view={view}
view={view}
style={{ display: 'none' }}
settings={editorSettings}
/>
<SettingsEditor
<SettingsEditor
settings={editorSettings}
EditorThemeNameList={EditorThemeNameList}
updateSettings={updateEditorSettings}
@@ -1,5 +1,5 @@
import '../uiEditor.less';
import React, { useState, useEffect} from 'react';
import React from 'react';
const SettingsEditor = ({ settings, updateSettings = ()=>{}, EditorThemeNameList })=>{
@@ -56,7 +56,7 @@ const SettingsEditor = ({ settings, updateSettings = ()=>{}, EditorThemeNameList
Select your Editor Theme
</label>
<div className='value'>
<select id="changeEditorTheme" value={settings.editorTheme} onChange={(e)=>handleFieldChange('editorTheme', e)} >
<select id='changeEditorTheme' value={settings.editorTheme} onChange={(e)=>handleFieldChange('editorTheme', e)} >
{EditorThemeNameList.map((theme, key)=>{
return <option key={key} value={theme}>{theme}</option>;
})}
@@ -127,7 +127,7 @@ const SettingsEditor = ({ settings, updateSettings = ()=>{}, EditorThemeNameList
<label htmlFor='fontSize'>
Editor Font Size
</label>
<div className='value'>
<small>from 9px to 30px</small>
<input
@@ -35,21 +35,21 @@ const Snippetbar = createReactClass({
displayName : 'SnippetBar',
getDefaultProps : function() {
return {
brew : {},
view : 'text',
onViewChange : ()=>{},
onInject : ()=>{},
onToggle : ()=>{},
showEditButtons : true,
renderer : 'legacy',
undo : ()=>{},
redo : ()=>{},
historySize : ()=>{},
foldCode : ()=>{},
unfoldCode : ()=>{},
cursorPos : {},
themeBundle : [],
updateBrew : ()=>{}
brew : {},
view : 'text',
onViewChange : ()=>{},
onInject : ()=>{},
onToggle : ()=>{},
showEditButtons : true,
renderer : 'legacy',
undo : ()=>{},
redo : ()=>{},
historySize : ()=>{},
foldCode : ()=>{},
unfoldCode : ()=>{},
cursorPos : {},
themeBundle : [],
updateBrew : ()=>{}
};
},
@@ -294,7 +294,7 @@ const SnippetGroup = createReactClass({
<Dropdown groupName={snippet.name} icon={snippet.icon} key={snippet.name}>
{this.renderSnippets(snippet.subsnippets)}
</Dropdown>
)
);
}
});
@@ -3,26 +3,26 @@
@import (less) '@themes/fonts/5e/fonts.less';
.snippetBar {
--activeTriggerColor: inherit;
--menuColor : #DDDDDD;
--activeTriggerColor : inherit;
--menuColor : #DDDDDD;
@menuHeight : 25px;
position : relative;
display : flex;
flex-wrap : wrap-reverse;
justify-content : space-between;
height : auto;
color : black;
background-color : #DDDDDD;
font-size : .65rem;
font-family: 'Open Sans', sans-serif;
text-transform: uppercase;
font-weight: 800;
position : relative;
display : flex;
flex-wrap : wrap-reverse;
justify-content : space-between;
height : auto;
font-family : 'Open Sans', sans-serif;
font-size : 0.65rem;
font-weight : 800;
color : black;
text-transform : uppercase;
background-color : #DDDDDD;
.editors {
display : flex;
justify-content : flex-end;
min-width : 275px; //must be controlled every time an item is added, must be hardcoded for the wrapping as it is applied
font-size: .85rem;
font-size : 0.85rem;
&:only-child {min-width : unset; margin-left : auto;}
>div {
@@ -130,36 +130,32 @@
}
// removed caret for top level items, by request (makes buttons too wide).
.menu-wrapper .menu-item:is(.snippets > .menu-wrapper > .menu-item):first-child .caret { display: none; }
.menu-wrapper .menu-item:is(.snippets > .menu-wrapper > .menu-item):first-child .caret { display : none; }
.menu-item {
position : relative;
display : flex;
justify-content: space-between;
align-items : center;
min-width : max-content;
padding : 5px;
cursor : pointer;
width: 100%;
&:is(.menu-list .menu-item) [class*="name"] {
padding-inline: 8px; // additional space between icon and name (helpful in Fonts menu especially).
position : relative;
display : flex;
align-items : center;
justify-content : space-between;
width : 100%;
min-width : max-content;
padding : 5px;
cursor : pointer;
&:is(.menu-list .menu-item) [class*='name'] {
padding-inline : 8px; // additional space between icon and name (helpful in Fonts menu especially).
}
.menu-name {
flex: 1;
text-align: left;
text-box-trim: trim-end;
flex : 1;
text-align : left;
text-box-trim : trim-end;
}
i {
min-width : 25px;
height : .85rem;
height : 0.85rem;
font-size : 1.2em;
text-align : center;
&.caret {
margin-right: 0;
}
&.caret:is(.menu-wrapper .menu-wrapper * ) {
text-align: right;
}
&.caret { margin-right : 0; }
&.caret:is(.menu-wrapper .menu-wrapper *) { text-align : right; }
/* Fonts */
&.font {
height : auto;
@@ -198,13 +194,11 @@
background : grey;
border-radius : 12px;
}
&:hover {
background-color : #999999;
}
&:hover { background-color : #999999; }
&:disabled {
color: gray;
cursor: not-allowed;
&:hover { background-color: unset; }
color : gray;
cursor : not-allowed;
&:hover { background-color : unset; }
}
}
}
+39 -49
View File
@@ -64,19 +64,17 @@
&[data-tooltip-right] { max-width : 380px; }
&:invalid { background : #FFB9B9; }
small {
display : block;
font-size : 0.9em;
font-style : italic;
line-height : 1.4em;
display : block;
width : fit-content;
margin-inline : 5px;
font-size : 0.9em;
font-style : italic;
line-height : 1.4em;
}
small {
width:fit-content;
margin-inline:5px;
}
input[type='checkbox'], input[type='number'] {
float:right;
text-align:end;
float : right;
text-align : end;
}
}
input[type='text'], textarea {
@@ -185,47 +183,41 @@
}
.authors.field {
.tag {
font-weight:300;
transition:background-color 0.2s;
font-weight : 300;
transition : background-color 0.2s;
&.owner {
position: relative;
background-color:@silverLight;
min-width:25px;
display:grid;
place-items:center;
font-weight: 900;
position : relative;
display : grid;
place-items : center;
min-width : 25px;
font-weight : 900;
background-color : @silverLight;
&::after {
content: "\f521";
font-family: "Font Awesome 6 Free";
color:gold;
position: absolute;
top: 0;
left: 0;
width:15px;
height:15px;
rotate:-25deg;
translate:-30% -50%;
transform: scaleY(0.7);
position : absolute;
top : 0;
left : 0;
width : 15px;
height : 15px;
font-family : 'Font Awesome 6 Free';
color : gold;
content : '\f521';
transform : scaleY(0.7);
rotate : -25deg;
translate : -30% -50%;
}
}
&:has(button) a {
padding-right:5px;
}
&:has(button:hover) {
background:#d97d7d;
}
&:has(button) a { padding-right : 5px; }
&:has(button:hover) { background : #D97D7D; }
button {
color:@red;
}
button { color : @red; }
}
a {
color:black;
text-decoration:unset;
color : black;
text-decoration : unset;
}
}
@@ -337,9 +329,7 @@
.icon { #groupedIcon; }
button {
cursor : pointer;
}
button { cursor : pointer; }
}
.input-group {
@@ -385,17 +375,17 @@
.settingsEditor .field {
border-bottom:1px solid black;
padding-bottom:10px;
padding-bottom : 10px;
border-bottom : 1px solid black;
.value {
display:flex;
justify-content: end;
display : flex;
justify-content : end;
}
> label {
width:fit-content;
max-width:calc(100% - 200px);
width : fit-content;
max-width : calc(100% - 200px);
}
}