@myissue/vue-website-page-builder 3.3.23 → 3.3.24
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/dist/vue-website-page-builder.css +1 -1
- package/dist/vue-website-page-builder.js +1818 -1765
- package/dist/vue-website-page-builder.umd.cjs +23 -23
- package/package.json +1 -1
- package/src/Components/PageBuilder/EditorMenu/Editables/Typography.vue +32 -28
- package/src/Components/PageBuilder/EditorMenu/RightSidebarEditor.vue +31 -2
- package/src/composables/PageBuilderService.ts +120 -56
- package/src/css/app.css +0 -7
package/package.json
CHANGED
|
@@ -103,33 +103,35 @@ watch(
|
|
|
103
103
|
<template #content>
|
|
104
104
|
<!-- FONT SIZES -->
|
|
105
105
|
<p class="pbx-myPrimaryParagraph pbx-font-medium pbx-py-0 pbx-my-4">Font Appearance</p>
|
|
106
|
-
<div class="pbx-my-2 pbx-py-2">
|
|
107
|
-
<label class="pbx-myPrimaryInputLabel"> Font Size </label>
|
|
108
|
-
<select
|
|
109
|
-
v-model="fontBase"
|
|
110
|
-
class="pbx-myPrimarySelect"
|
|
111
|
-
@change="pageBuilderService.handleFontSizeBase(fontBase)"
|
|
112
|
-
>
|
|
113
|
-
<option disabled value="">Select</option>
|
|
114
|
-
<option v-for="fontSize in tailwindFontSizes.fontBase" :key="fontSize">
|
|
115
|
-
{{ fontSize }}
|
|
116
|
-
</option>
|
|
117
|
-
</select>
|
|
118
|
-
</div>
|
|
119
106
|
<template v-if="false">
|
|
120
107
|
<div class="pbx-my-2 pbx-py-2">
|
|
121
|
-
<label class="pbx-myPrimaryInputLabel"> Font
|
|
108
|
+
<label class="pbx-myPrimaryInputLabel"> Font Size </label>
|
|
122
109
|
<select
|
|
123
|
-
v-model="
|
|
110
|
+
v-model="fontBase"
|
|
124
111
|
class="pbx-myPrimarySelect"
|
|
125
|
-
@change="pageBuilderService.
|
|
112
|
+
@change="pageBuilderService.handleFontSizeBase(fontBase)"
|
|
126
113
|
>
|
|
127
114
|
<option disabled value="">Select</option>
|
|
128
|
-
<option v-for="fontSize in tailwindFontSizes.
|
|
115
|
+
<option v-for="fontSize in tailwindFontSizes.fontBase" :key="fontSize">
|
|
129
116
|
{{ fontSize }}
|
|
130
117
|
</option>
|
|
131
118
|
</select>
|
|
132
119
|
</div>
|
|
120
|
+
</template>
|
|
121
|
+
<div class="pbx-my-2 pbx-py-2">
|
|
122
|
+
<label class="pbx-myPrimaryInputLabel"> Font size </label>
|
|
123
|
+
<select
|
|
124
|
+
v-model="fontDesktop"
|
|
125
|
+
class="pbx-myPrimarySelect"
|
|
126
|
+
@change="pageBuilderService.handleFontSizeDesktop(fontDesktop)"
|
|
127
|
+
>
|
|
128
|
+
<option disabled value="">Select</option>
|
|
129
|
+
<option v-for="fontSize in tailwindFontSizes.fontDesktop" :key="fontSize">
|
|
130
|
+
{{ fontSize }}
|
|
131
|
+
</option>
|
|
132
|
+
</select>
|
|
133
|
+
</div>
|
|
134
|
+
<template v-if="false">
|
|
133
135
|
<div class="pbx-my-2 pbx-py-2">
|
|
134
136
|
<label class="pbx-myPrimaryInputLabel"> Font tablet size </label>
|
|
135
137
|
<select
|
|
@@ -158,36 +160,38 @@ watch(
|
|
|
158
160
|
</div>
|
|
159
161
|
</template>
|
|
160
162
|
<hr />
|
|
161
|
-
|
|
163
|
+
|
|
162
164
|
<div class="pbx-my-2 pbx-py-2">
|
|
163
|
-
<label class="pbx-myPrimaryInputLabel"> Font
|
|
165
|
+
<label class="pbx-myPrimaryInputLabel"> Font weight </label>
|
|
164
166
|
<select
|
|
165
|
-
v-model="
|
|
167
|
+
v-model="fontWeight"
|
|
166
168
|
class="pbx-myPrimarySelect"
|
|
167
|
-
@change="pageBuilderService.
|
|
169
|
+
@change="pageBuilderService.handleFontWeight(fontWeight)"
|
|
168
170
|
>
|
|
169
171
|
<option disabled value="">Select</option>
|
|
170
|
-
<option v-for="
|
|
171
|
-
{{
|
|
172
|
+
<option v-for="fontWeight in tailwindFontStyles.fontWeight" :key="fontWeight">
|
|
173
|
+
{{ fontWeight }}
|
|
172
174
|
</option>
|
|
173
175
|
</select>
|
|
174
176
|
</div>
|
|
175
177
|
<hr />
|
|
176
178
|
|
|
179
|
+
<!-- FONT FAMILY -->
|
|
177
180
|
<div class="pbx-my-2 pbx-py-2">
|
|
178
|
-
<label class="pbx-myPrimaryInputLabel"> Font
|
|
181
|
+
<label class="pbx-myPrimaryInputLabel"> Font family </label>
|
|
179
182
|
<select
|
|
180
|
-
v-model="
|
|
183
|
+
v-model="fontFamily"
|
|
181
184
|
class="pbx-myPrimarySelect"
|
|
182
|
-
@change="pageBuilderService.
|
|
185
|
+
@change="pageBuilderService.handleFontFamily(fontFamily)"
|
|
183
186
|
>
|
|
184
187
|
<option disabled value="">Select</option>
|
|
185
|
-
<option v-for="
|
|
186
|
-
{{
|
|
188
|
+
<option v-for="fontFamily in tailwindFontStyles.fontFamily" :key="fontFamily">
|
|
189
|
+
{{ fontFamily }}
|
|
187
190
|
</option>
|
|
188
191
|
</select>
|
|
189
192
|
</div>
|
|
190
193
|
<hr />
|
|
194
|
+
|
|
191
195
|
<div class="pbx-my-2 pbx-py-2">
|
|
192
196
|
<label class="pbx-myPrimaryInputLabel"> Font Style </label>
|
|
193
197
|
<select
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
<script setup>
|
|
2
|
-
import { computed } from 'vue'
|
|
2
|
+
import { computed, ref, watch, nextTick } from 'vue'
|
|
3
3
|
import { sharedPageBuilderStore } from '../../../stores/shared-store'
|
|
4
4
|
import ClassEditor from './Editables/ClassEditor.vue'
|
|
5
5
|
import ImageEditor from './Editables/ImageEditor.vue'
|
|
@@ -38,6 +38,30 @@ const isHeadingElement = computed(() => {
|
|
|
38
38
|
getElement.value instanceof HTMLImageElement
|
|
39
39
|
)
|
|
40
40
|
})
|
|
41
|
+
|
|
42
|
+
const scrollContainer = ref(null)
|
|
43
|
+
let lastScrollTop = 0
|
|
44
|
+
|
|
45
|
+
// Watch for changes that cause re-render (e.g. dropdown value in store)
|
|
46
|
+
watch(
|
|
47
|
+
// or the specific value that triggers re-render
|
|
48
|
+
() => pageBuilderStateStore.getElement,
|
|
49
|
+
() => {
|
|
50
|
+
// Restore scroll after DOM updates
|
|
51
|
+
nextTick(() => {
|
|
52
|
+
if (scrollContainer.value) {
|
|
53
|
+
scrollContainer.value.scrollTop = lastScrollTop
|
|
54
|
+
}
|
|
55
|
+
})
|
|
56
|
+
},
|
|
57
|
+
)
|
|
58
|
+
|
|
59
|
+
// Save scroll position before update
|
|
60
|
+
function onScroll() {
|
|
61
|
+
if (scrollContainer.value) {
|
|
62
|
+
lastScrollTop = scrollContainer.value.scrollTop
|
|
63
|
+
}
|
|
64
|
+
}
|
|
41
65
|
</script>
|
|
42
66
|
|
|
43
67
|
<template>
|
|
@@ -58,7 +82,12 @@ const isHeadingElement = computed(() => {
|
|
|
58
82
|
</p>
|
|
59
83
|
</div>
|
|
60
84
|
|
|
61
|
-
<div
|
|
85
|
+
<div
|
|
86
|
+
v
|
|
87
|
+
ref="scrollContainer"
|
|
88
|
+
@scroll="onScroll"
|
|
89
|
+
class="pbx-pl-3 pbx-pr-3 pbx-mb-4 pbx-overflow-y-scroll"
|
|
90
|
+
>
|
|
62
91
|
<div v-show="getElement && pageBuilderService.isEditableElement(getElement)">
|
|
63
92
|
<article class="pbx-mb-1">
|
|
64
93
|
<ImageEditor> </ImageEditor>
|
|
@@ -24,6 +24,9 @@ import { isEmptyObject } from '../helpers/isEmptyObject'
|
|
|
24
24
|
|
|
25
25
|
export class PageBuilderService {
|
|
26
26
|
// Class properties with types
|
|
27
|
+
private fontSizeRegex =
|
|
28
|
+
/^(sm:|md:|lg:|xl:|2xl:)?pbx-text-(xs|sm|base|lg|xl|2xl|3xl|4xl|5xl|6xl|7xl|8xl|9xl)$/
|
|
29
|
+
|
|
27
30
|
private pageBuilderStateStore: ReturnType<typeof usePageBuilderStateStore>
|
|
28
31
|
private getLocalStorageItemName: ComputedRef<string | null>
|
|
29
32
|
private getApplyImageToSelection: ComputedRef<ImageObject>
|
|
@@ -289,10 +292,7 @@ export class PageBuilderService {
|
|
|
289
292
|
) {
|
|
290
293
|
this.pageBuilderStateStore.setHasLocalDraftForUpdate(true)
|
|
291
294
|
}
|
|
292
|
-
|
|
293
|
-
//
|
|
294
|
-
//
|
|
295
|
-
//
|
|
295
|
+
|
|
296
296
|
if (config && formType === 'update') {
|
|
297
297
|
if (this.pendingMountData) {
|
|
298
298
|
this.#completeBuilderInitialization(this.pendingMountData)
|
|
@@ -306,10 +306,6 @@ export class PageBuilderService {
|
|
|
306
306
|
return
|
|
307
307
|
}
|
|
308
308
|
|
|
309
|
-
//
|
|
310
|
-
//
|
|
311
|
-
//
|
|
312
|
-
//
|
|
313
309
|
// Wait for Vue to finish DOM updates before attaching event listeners. This ensure elements exist in the DOM.
|
|
314
310
|
await nextTick()
|
|
315
311
|
// Attach event listeners to all editable elements in the Builder
|
|
@@ -327,10 +323,6 @@ export class PageBuilderService {
|
|
|
327
323
|
return
|
|
328
324
|
}
|
|
329
325
|
|
|
330
|
-
//
|
|
331
|
-
//
|
|
332
|
-
//
|
|
333
|
-
//
|
|
334
326
|
// Wait for Vue to finish DOM updates before attaching event listeners. This ensure elements exist in the DOM.
|
|
335
327
|
await nextTick()
|
|
336
328
|
// Attach event listeners to all editable elements in the Builder
|
|
@@ -454,11 +446,12 @@ export class PageBuilderService {
|
|
|
454
446
|
}
|
|
455
447
|
|
|
456
448
|
#applyElementClassChanges(
|
|
457
|
-
|
|
449
|
+
cssUserSelection: string | undefined,
|
|
458
450
|
CSSArray: string[],
|
|
459
451
|
mutationName: string,
|
|
460
452
|
): string | undefined {
|
|
461
453
|
const currentHTMLElement = this.getElement.value
|
|
454
|
+
|
|
462
455
|
if (!currentHTMLElement) return
|
|
463
456
|
|
|
464
457
|
const currentCSS = CSSArray.find((CSS) => {
|
|
@@ -468,25 +461,29 @@ export class PageBuilderService {
|
|
|
468
461
|
// set to 'none' if undefined
|
|
469
462
|
let elementClass = currentCSS || 'none'
|
|
470
463
|
|
|
471
|
-
// If
|
|
472
|
-
if (
|
|
464
|
+
// If cssUserSelection is undefined, just set the current state and return
|
|
465
|
+
if (cssUserSelection === undefined) {
|
|
473
466
|
if (typeof mutationName === 'string' && mutationName.length > 2) {
|
|
474
467
|
;(this.pageBuilderStateStore as any)[mutationName](elementClass)
|
|
475
468
|
}
|
|
476
469
|
return currentCSS
|
|
477
470
|
}
|
|
478
471
|
|
|
479
|
-
//
|
|
480
|
-
if (typeof
|
|
472
|
+
// cssUserSelection examples: bg-zinc-200, px-10, rounded-full etc.
|
|
473
|
+
if (typeof cssUserSelection === 'string' && cssUserSelection !== 'none') {
|
|
481
474
|
if (elementClass && currentHTMLElement.classList.contains(elementClass)) {
|
|
482
475
|
currentHTMLElement.classList.remove(elementClass)
|
|
483
476
|
}
|
|
484
477
|
|
|
485
|
-
currentHTMLElement.classList.add(
|
|
486
|
-
elementClass =
|
|
487
|
-
} else if (
|
|
478
|
+
currentHTMLElement.classList.add(cssUserSelection)
|
|
479
|
+
elementClass = cssUserSelection
|
|
480
|
+
} else if (
|
|
481
|
+
typeof cssUserSelection === 'string' &&
|
|
482
|
+
cssUserSelection === 'none' &&
|
|
483
|
+
elementClass
|
|
484
|
+
) {
|
|
488
485
|
currentHTMLElement.classList.remove(elementClass)
|
|
489
|
-
elementClass =
|
|
486
|
+
elementClass = cssUserSelection
|
|
490
487
|
}
|
|
491
488
|
|
|
492
489
|
// Only call store mutations after all DOM manipulation is complete
|
|
@@ -498,6 +495,75 @@ export class PageBuilderService {
|
|
|
498
495
|
return currentCSS
|
|
499
496
|
}
|
|
500
497
|
|
|
498
|
+
handleFontWeight(userSelectedFontWeight?: string): void {
|
|
499
|
+
this.#applyElementClassChanges(
|
|
500
|
+
userSelectedFontWeight,
|
|
501
|
+
tailwindFontStyles.fontWeight,
|
|
502
|
+
'setFontWeight',
|
|
503
|
+
)
|
|
504
|
+
}
|
|
505
|
+
|
|
506
|
+
handleFontSizeBase(userSelectedFontSize?: string): void {
|
|
507
|
+
this.#applyElementClassChanges(userSelectedFontSize, tailwindFontSizes.fontBase, 'setFontBase')
|
|
508
|
+
}
|
|
509
|
+
|
|
510
|
+
handleFontSizeDesktop(userSelectedFontSize?: string): void {
|
|
511
|
+
const currentHTMLElement = this.getElement.value
|
|
512
|
+
if (!currentHTMLElement) return
|
|
513
|
+
|
|
514
|
+
// Hardcoded mapping: selected => base
|
|
515
|
+
const fontSizeBaseMap: Record<string, string> = {
|
|
516
|
+
'pbx-text-9xl': 'pbx-text-6xl',
|
|
517
|
+
'pbx-text-8xl': 'pbx-text-6xl',
|
|
518
|
+
'pbx-text-7xl': 'pbx-text-5xl',
|
|
519
|
+
'pbx-text-6xl': 'pbx-text-3xl',
|
|
520
|
+
'pbx-text-5xl': 'pbx-text-3xl',
|
|
521
|
+
'pbx-text-4xl': 'pbx-text-2xl',
|
|
522
|
+
'pbx-text-3xl': 'pbx-text-xl',
|
|
523
|
+
'pbx-text-2xl': 'pbx-text-lg',
|
|
524
|
+
'pbx-text-xl': 'pbx-text-base',
|
|
525
|
+
'pbx-text-lg': 'pbx-text-sm',
|
|
526
|
+
'pbx-text-base': 'pbx-text-xs',
|
|
527
|
+
'pbx-text-sm': 'pbx-text-xs',
|
|
528
|
+
'pbx-text-xs': 'pbx-text-xs',
|
|
529
|
+
}
|
|
530
|
+
|
|
531
|
+
if (userSelectedFontSize) {
|
|
532
|
+
// Remove all existing font size classes first
|
|
533
|
+
Array.from(currentHTMLElement.classList).forEach((cls) => {
|
|
534
|
+
if (this.fontSizeRegex.test(cls)) {
|
|
535
|
+
currentHTMLElement.classList.remove(cls)
|
|
536
|
+
}
|
|
537
|
+
})
|
|
538
|
+
|
|
539
|
+
// Extract the font size class (remove 'lg:' if present)
|
|
540
|
+
const fontSizeClass = userSelectedFontSize.replace(/^lg:/, '')
|
|
541
|
+
|
|
542
|
+
const baseClass = fontSizeBaseMap[fontSizeClass] || fontSizeClass
|
|
543
|
+
const lgClass = `lg:${fontSizeClass}`
|
|
544
|
+
|
|
545
|
+
if (baseClass !== fontSizeClass) {
|
|
546
|
+
currentHTMLElement.classList.add(baseClass, lgClass)
|
|
547
|
+
} else {
|
|
548
|
+
currentHTMLElement.classList.add(baseClass)
|
|
549
|
+
}
|
|
550
|
+
}
|
|
551
|
+
|
|
552
|
+
const currentCSS = tailwindFontSizes.fontDesktop.find((CSS) => {
|
|
553
|
+
return currentHTMLElement.classList.contains(CSS)
|
|
554
|
+
})
|
|
555
|
+
|
|
556
|
+
if (!userSelectedFontSize) {
|
|
557
|
+
this.pageBuilderStateStore.setFontDesktop('none')
|
|
558
|
+
}
|
|
559
|
+
|
|
560
|
+
if (currentCSS && !userSelectedFontSize) {
|
|
561
|
+
this.pageBuilderStateStore.setFontDesktop(currentCSS)
|
|
562
|
+
}
|
|
563
|
+
|
|
564
|
+
return currentCSS
|
|
565
|
+
}
|
|
566
|
+
|
|
501
567
|
#applyHelperCSSToElements(element: HTMLElement): void {
|
|
502
568
|
this.#wrapElementInDivIfExcluded(element)
|
|
503
569
|
|
|
@@ -505,14 +571,43 @@ export class PageBuilderService {
|
|
|
505
571
|
element.classList.add('smooth-transition')
|
|
506
572
|
}
|
|
507
573
|
|
|
508
|
-
//
|
|
509
|
-
if (
|
|
510
|
-
|
|
511
|
-
|
|
574
|
+
// If this is a DIV and its only/main child is a heading, apply font size classes to the DIV
|
|
575
|
+
if (
|
|
576
|
+
element.tagName === 'DIV' &&
|
|
577
|
+
element.children.length === 1 &&
|
|
578
|
+
['H1', 'H2', 'H3', 'H4', 'H5', 'H6'].includes(element.children[0].tagName)
|
|
579
|
+
) {
|
|
580
|
+
const heading = element.children[0] as HTMLElement
|
|
581
|
+
|
|
582
|
+
element.classList.forEach((cls) => {
|
|
583
|
+
if (this.fontSizeRegex.test(cls)) {
|
|
584
|
+
element.classList.remove(cls)
|
|
585
|
+
}
|
|
586
|
+
})
|
|
587
|
+
|
|
588
|
+
// Apply responsive font size classes based on heading type
|
|
589
|
+
if (heading.tagName === 'H2') {
|
|
590
|
+
element.classList.add('pbx-text-3xl', 'lg:pbx-text-6xl')
|
|
591
|
+
}
|
|
592
|
+
if (heading.tagName === 'H3') {
|
|
593
|
+
element.classList.add('pbx-text-2xl', 'lg:pbx-text-4xl')
|
|
512
594
|
}
|
|
513
595
|
}
|
|
514
596
|
}
|
|
515
597
|
|
|
598
|
+
async toggleTipTapModal(status: boolean): Promise<void> {
|
|
599
|
+
this.pageBuilderStateStore.setShowModalTipTap(status)
|
|
600
|
+
|
|
601
|
+
// Wait for Vue to finish DOM updates before attaching event listeners. This ensure elements exist in the DOM.
|
|
602
|
+
await nextTick()
|
|
603
|
+
// Attach event listeners to all editable elements in the Builder
|
|
604
|
+
await this.#addListenersToEditableElements()
|
|
605
|
+
|
|
606
|
+
if (!status) {
|
|
607
|
+
await this.handleAutoSave()
|
|
608
|
+
}
|
|
609
|
+
}
|
|
610
|
+
|
|
516
611
|
#wrapElementInDivIfExcluded(element: HTMLElement): void {
|
|
517
612
|
if (!element) return
|
|
518
613
|
|
|
@@ -792,13 +887,6 @@ export class PageBuilderService {
|
|
|
792
887
|
}
|
|
793
888
|
}
|
|
794
889
|
|
|
795
|
-
handleFontWeight(userSelectedFontWeight?: string): void {
|
|
796
|
-
this.#applyElementClassChanges(
|
|
797
|
-
userSelectedFontWeight,
|
|
798
|
-
tailwindFontStyles.fontWeight,
|
|
799
|
-
'setFontWeight',
|
|
800
|
-
)
|
|
801
|
-
}
|
|
802
890
|
handleFontFamily(userSelectedFontFamily?: string): void {
|
|
803
891
|
this.#applyElementClassChanges(
|
|
804
892
|
userSelectedFontFamily,
|
|
@@ -915,17 +1003,6 @@ export class PageBuilderService {
|
|
|
915
1003
|
}
|
|
916
1004
|
// border radius / end
|
|
917
1005
|
|
|
918
|
-
handleFontSizeBase(userSelectedFontSize?: string): void {
|
|
919
|
-
this.#applyElementClassChanges(userSelectedFontSize, tailwindFontSizes.fontBase, 'setFontBase')
|
|
920
|
-
}
|
|
921
|
-
|
|
922
|
-
handleFontSizeDesktop(userSelectedFontSize?: string): void {
|
|
923
|
-
this.#applyElementClassChanges(
|
|
924
|
-
userSelectedFontSize,
|
|
925
|
-
tailwindFontSizes.fontDesktop,
|
|
926
|
-
'setFontDesktop',
|
|
927
|
-
)
|
|
928
|
-
}
|
|
929
1006
|
handleFontSizeTablet(userSelectedFontSize?: string): void {
|
|
930
1007
|
this.#applyElementClassChanges(
|
|
931
1008
|
userSelectedFontSize,
|
|
@@ -2063,19 +2140,6 @@ export class PageBuilderService {
|
|
|
2063
2140
|
}
|
|
2064
2141
|
}
|
|
2065
2142
|
|
|
2066
|
-
async toggleTipTapModal(status: boolean): Promise<void> {
|
|
2067
|
-
this.pageBuilderStateStore.setShowModalTipTap(status)
|
|
2068
|
-
|
|
2069
|
-
// Wait for Vue to finish DOM updates before attaching event listeners. This ensure elements exist in the DOM.
|
|
2070
|
-
await nextTick()
|
|
2071
|
-
// Attach event listeners to all editable elements in the Builder
|
|
2072
|
-
await this.#addListenersToEditableElements()
|
|
2073
|
-
|
|
2074
|
-
if (!status) {
|
|
2075
|
-
await this.handleAutoSave()
|
|
2076
|
-
}
|
|
2077
|
-
}
|
|
2078
|
-
|
|
2079
2143
|
async initializeElementStyles(): Promise<void> {
|
|
2080
2144
|
// Wait for Vue to finish DOM updates before attaching event listeners.
|
|
2081
2145
|
// This ensure elements exist in the DOM.
|
package/src/css/app.css
CHANGED
|
@@ -366,13 +366,6 @@ a {
|
|
|
366
366
|
@apply pbx-text-myPrimaryLinkColor;
|
|
367
367
|
}
|
|
368
368
|
|
|
369
|
-
h2 {
|
|
370
|
-
@apply pbx-text-3xl pbx-mt-4 pbx-mb-3 pbx-font-medium;
|
|
371
|
-
}
|
|
372
|
-
h3 {
|
|
373
|
-
@apply pbx-text-2xl pbx-mt-4 pbx-mb-3 pbx-font-medium;
|
|
374
|
-
}
|
|
375
|
-
|
|
376
369
|
/* CSS for content inside page builder # start */
|
|
377
370
|
#page-builder-editor .tiptap {
|
|
378
371
|
outline: none !important;
|