@sequent-org/moodboard 1.4.57 → 1.4.58
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/src/core/commands/UpdateContentCommand.js +48 -2
- package/src/services/text/TextBoxMetrics.js +133 -0
- package/src/tools/object-tools/selection/MindmapInlineEditorController.js +98 -7
- package/src/tools/object-tools/selection/SelectInputRouter.js +55 -2
- package/src/tools/object-tools/selection/TextEditorCaretService.js +113 -0
- package/src/tools/object-tools/selection/TextEditorDomFactory.js +37 -21
- package/src/tools/object-tools/selection/TextEditorInteractionController.js +86 -1
- package/src/tools/object-tools/selection/TextEditorPositioningService.js +19 -1
- package/src/tools/object-tools/selection/TextEditorSyncService.js +2 -1
- package/src/tools/object-tools/selection/TextInlineEditorController.js +68 -43
- package/src/tools/object-tools/selection/TransformInteractionController.js +7 -1
- package/src/ui/HtmlTextLayer.js +113 -70
- package/src/ui/TextPropertiesPanel.js +154 -7
- package/src/ui/handles/HandlesDomRenderer.js +2 -0
- package/src/ui/handles/HandlesInteractionController.js +40 -0
- package/src/ui/styles/workspace.css +64 -1
- package/src/ui/text-properties/TextPropertiesPanelBindings.js +8 -0
- package/src/ui/text-properties/TextPropertiesPanelMapper.js +29 -0
|
@@ -665,14 +665,45 @@
|
|
|
665
665
|
z-index: 10000;
|
|
666
666
|
}
|
|
667
667
|
|
|
668
|
+
.mb-custom-caret {
|
|
669
|
+
position: absolute;
|
|
670
|
+
background-color: #111;
|
|
671
|
+
width: 2px;
|
|
672
|
+
pointer-events: none;
|
|
673
|
+
z-index: 10001;
|
|
674
|
+
animation: mb-caret-blink 1s step-end infinite;
|
|
675
|
+
display: none;
|
|
676
|
+
border-radius: 1px;
|
|
677
|
+
}
|
|
678
|
+
|
|
679
|
+
@keyframes mb-caret-blink {
|
|
680
|
+
0%, 100% { opacity: 1; }
|
|
681
|
+
50% { opacity: 0; }
|
|
682
|
+
}
|
|
683
|
+
|
|
684
|
+
/* Панель свойств текста и её дропдауны — выше inline-редактора */
|
|
685
|
+
.text-properties-layer {
|
|
686
|
+
z-index: 10050;
|
|
687
|
+
}
|
|
688
|
+
|
|
689
|
+
.moodboard-text-input::selection {
|
|
690
|
+
background: rgba(33, 150, 243, 0.28);
|
|
691
|
+
}
|
|
692
|
+
|
|
693
|
+
.moodboard-text-input::-moz-selection {
|
|
694
|
+
background: rgba(33, 150, 243, 0.28);
|
|
695
|
+
}
|
|
696
|
+
|
|
668
697
|
.moodboard-text-input {
|
|
698
|
+
caret-color: transparent;
|
|
669
699
|
position: relative;
|
|
700
|
+
z-index: 2;
|
|
670
701
|
left: 0;
|
|
671
702
|
top: 0;
|
|
672
703
|
border: none;
|
|
673
704
|
padding: 0;
|
|
674
705
|
font-family: Caveat, Arial, cursive;
|
|
675
|
-
color:
|
|
706
|
+
color: transparent;
|
|
676
707
|
background: transparent;
|
|
677
708
|
outline: none;
|
|
678
709
|
resize: none;
|
|
@@ -685,7 +716,34 @@
|
|
|
685
716
|
padding-bottom: 0; /* без нижнего отступа */
|
|
686
717
|
letter-spacing: 0px;
|
|
687
718
|
font-kerning: normal;
|
|
719
|
+
text-rendering: optimizeLegibility;
|
|
720
|
+
margin: 0;
|
|
721
|
+
}
|
|
722
|
+
|
|
723
|
+
.moodboard-text-backdrop {
|
|
724
|
+
position: absolute;
|
|
725
|
+
z-index: 1;
|
|
726
|
+
left: 0;
|
|
727
|
+
top: 0;
|
|
728
|
+
width: 100%;
|
|
729
|
+
height: 100%;
|
|
730
|
+
border: none;
|
|
731
|
+
padding: 0;
|
|
732
|
+
font-family: Caveat, Arial, cursive;
|
|
733
|
+
color: #111;
|
|
734
|
+
background: transparent;
|
|
735
|
+
box-sizing: content-box;
|
|
736
|
+
overflow: hidden;
|
|
737
|
+
-webkit-font-smoothing: antialiased;
|
|
738
|
+
-moz-osx-font-smoothing: grayscale;
|
|
739
|
+
white-space: pre-wrap;
|
|
740
|
+
word-break: break-word;
|
|
741
|
+
padding-bottom: 0;
|
|
742
|
+
letter-spacing: 0px;
|
|
743
|
+
font-kerning: normal;
|
|
744
|
+
text-rendering: optimizeLegibility;
|
|
688
745
|
margin: 0;
|
|
746
|
+
pointer-events: none;
|
|
689
747
|
}
|
|
690
748
|
|
|
691
749
|
.text-properties-panel .font-select,
|
|
@@ -1576,6 +1634,11 @@
|
|
|
1576
1634
|
padding-bottom: 1px;
|
|
1577
1635
|
}
|
|
1578
1636
|
|
|
1637
|
+
.moodboard-text-backdrop {
|
|
1638
|
+
padding-top: 1px;
|
|
1639
|
+
padding-bottom: 1px;
|
|
1640
|
+
}
|
|
1641
|
+
|
|
1579
1642
|
.moodboard-text-input:focus {
|
|
1580
1643
|
outline: none;
|
|
1581
1644
|
}
|
|
@@ -111,6 +111,14 @@ export function bindTextPropertiesPanelControls(panel) {
|
|
|
111
111
|
document.addEventListener('click', panel._onColorDocumentClick);
|
|
112
112
|
|
|
113
113
|
if (panel.currentHighlightButton) {
|
|
114
|
+
// Снимок выделения textarea до ухода фокуса (capture-фаза, до click/blur).
|
|
115
|
+
// Покрывает и кнопку, и пресеты, и нативный color-input внутри контейнера.
|
|
116
|
+
if (panel._highlightSelectorContainer) {
|
|
117
|
+
panel._highlightSelectorContainer.addEventListener('mousedown', () => {
|
|
118
|
+
panel._snapshotTextSelection();
|
|
119
|
+
}, true);
|
|
120
|
+
}
|
|
121
|
+
|
|
114
122
|
panel.currentHighlightButton.addEventListener('click', (event) => {
|
|
115
123
|
event.stopPropagation();
|
|
116
124
|
panel._toggleHighlightDropdown();
|
|
@@ -170,6 +170,35 @@ export function buildPropertyUpdate(key, value) {
|
|
|
170
170
|
|
|
171
171
|
export function applyTextAppearanceToDom(objectId, properties) {
|
|
172
172
|
const htmlElement = document.querySelector(`[data-id="${objectId}"]`);
|
|
173
|
+
|
|
174
|
+
// Также обновляем активный редактор, если он открыт
|
|
175
|
+
const activeEditor = document.querySelector('.moodboard-text-editor');
|
|
176
|
+
if (activeEditor) {
|
|
177
|
+
const textarea = activeEditor.querySelector('.moodboard-text-input');
|
|
178
|
+
const backdrop = activeEditor.querySelector('.moodboard-text-backdrop');
|
|
179
|
+
|
|
180
|
+
if (textarea) {
|
|
181
|
+
if (properties.fontFamily) {
|
|
182
|
+
textarea.style.fontFamily = properties.fontFamily;
|
|
183
|
+
if (backdrop) backdrop.style.fontFamily = properties.fontFamily;
|
|
184
|
+
}
|
|
185
|
+
if (properties.fontSize) {
|
|
186
|
+
textarea.style.fontSize = `${properties.fontSize}px`;
|
|
187
|
+
if (backdrop) backdrop.style.fontSize = `${properties.fontSize}px`;
|
|
188
|
+
}
|
|
189
|
+
if (properties.textAlign !== undefined) {
|
|
190
|
+
textarea.style.textAlign = properties.textAlign;
|
|
191
|
+
if (backdrop) backdrop.style.textAlign = properties.textAlign;
|
|
192
|
+
}
|
|
193
|
+
if (properties.color && backdrop) {
|
|
194
|
+
backdrop.style.color = properties.color;
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
// Эмулируем событие input для перерисовки backdrop
|
|
198
|
+
textarea.dispatchEvent(new Event('input', { bubbles: true }));
|
|
199
|
+
}
|
|
200
|
+
}
|
|
201
|
+
|
|
173
202
|
if (!htmlElement) {
|
|
174
203
|
return;
|
|
175
204
|
}
|