@jhits/plugin-blog 0.0.19 → 0.0.20
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/api/categories.d.ts.map +1 -1
- package/dist/api/categories.js +42 -38
- package/dist/api/handler.d.ts +1 -26
- package/dist/api/handler.d.ts.map +1 -1
- package/dist/api/handler.js +81 -490
- package/dist/api/router.d.ts +0 -5
- package/dist/api/router.d.ts.map +1 -1
- package/dist/api/router.js +8 -35
- package/dist/api/service.d.ts +80 -0
- package/dist/api/service.d.ts.map +1 -0
- package/dist/api/service.js +219 -0
- package/dist/hooks/useAutoSave.d.ts +10 -0
- package/dist/hooks/useAutoSave.d.ts.map +1 -0
- package/dist/hooks/useAutoSave.js +57 -0
- package/dist/hooks/useCategories.d.ts +1 -1
- package/dist/hooks/useCategories.d.ts.map +1 -1
- package/dist/hooks/useCategories.js +15 -46
- package/dist/index.d.ts +24 -31
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +44 -201
- package/dist/init.d.ts +20 -7
- package/dist/init.d.ts.map +1 -1
- package/dist/init.js +8 -7
- package/dist/lib/blocks/BlockRenderer.d.ts.map +1 -1
- package/dist/lib/layouts/blocks/ColumnsBlock.d.ts.map +1 -1
- package/dist/lib/layouts/blocks/ColumnsBlock.js +30 -113
- package/dist/lib/layouts/blocks/SectionBlock.d.ts.map +1 -1
- package/dist/lib/layouts/blocks/SectionBlock.js +9 -21
- package/dist/lib/layouts/index.d.ts +3 -3
- package/dist/lib/layouts/index.js +4 -4
- package/dist/lib/mappers/apiMapper.d.ts +10 -0
- package/dist/lib/mappers/apiMapper.d.ts.map +1 -1
- package/dist/lib/mappers/apiMapper.js +47 -32
- package/dist/lib/rich-text/RichTextEditor.d.ts +4 -2
- package/dist/lib/rich-text/RichTextEditor.d.ts.map +1 -1
- package/dist/lib/rich-text/RichTextEditor.js +12 -9
- package/dist/lib/utils/config-resolver.d.ts +28 -0
- package/dist/lib/utils/config-resolver.d.ts.map +1 -0
- package/dist/lib/utils/config-resolver.js +46 -0
- package/dist/lib/utils/tree.d.ts +29 -0
- package/dist/lib/utils/tree.d.ts.map +1 -0
- package/dist/lib/utils/tree.js +129 -0
- package/dist/state/EditorContext.d.ts +3 -25
- package/dist/state/EditorContext.d.ts.map +1 -1
- package/dist/state/EditorContext.js +124 -174
- package/dist/state/reducer.d.ts +1 -5
- package/dist/state/reducer.d.ts.map +1 -1
- package/dist/state/reducer.js +128 -521
- package/dist/state/types.d.ts +12 -1
- package/dist/state/types.d.ts.map +1 -1
- package/dist/types/block.d.ts +9 -0
- package/dist/types/block.d.ts.map +1 -1
- package/dist/types/post.d.ts +17 -1
- package/dist/types/post.d.ts.map +1 -1
- package/dist/views/CanvasEditor/BlockWrapper.d.ts +5 -6
- package/dist/views/CanvasEditor/BlockWrapper.d.ts.map +1 -1
- package/dist/views/CanvasEditor/BlockWrapper.js +56 -264
- package/dist/views/CanvasEditor/CanvasEditorView.d.ts +5 -3
- package/dist/views/CanvasEditor/CanvasEditorView.d.ts.map +1 -1
- package/dist/views/CanvasEditor/CanvasEditorView.js +55 -315
- package/dist/views/CanvasEditor/EditorBody.d.ts +6 -8
- package/dist/views/CanvasEditor/EditorBody.d.ts.map +1 -1
- package/dist/views/CanvasEditor/EditorBody.js +34 -482
- package/dist/views/CanvasEditor/EditorHeader.d.ts.map +1 -1
- package/dist/views/CanvasEditor/EditorHeader.js +27 -63
- package/dist/views/CanvasEditor/LayoutContainer.d.ts.map +1 -1
- package/dist/views/CanvasEditor/LayoutContainer.js +49 -70
- package/dist/views/CanvasEditor/components/CustomBlockItem.js +1 -1
- package/dist/views/CanvasEditor/components/EditorCanvas.d.ts +15 -3
- package/dist/views/CanvasEditor/components/EditorCanvas.d.ts.map +1 -1
- package/dist/views/CanvasEditor/components/EditorCanvas.js +40 -18
- package/dist/views/CanvasEditor/components/EditorLibrary.d.ts +5 -1
- package/dist/views/CanvasEditor/components/EditorLibrary.d.ts.map +1 -1
- package/dist/views/CanvasEditor/components/EditorLibrary.js +11 -7
- package/dist/views/CanvasEditor/components/EditorSidebar.d.ts.map +1 -1
- package/dist/views/CanvasEditor/components/EditorSidebar.js +32 -14
- package/dist/views/CanvasEditor/components/FeaturedMediaSection.d.ts +0 -6
- package/dist/views/CanvasEditor/components/FeaturedMediaSection.d.ts.map +1 -1
- package/dist/views/CanvasEditor/components/FeaturedMediaSection.js +17 -128
- package/dist/views/CanvasEditor/components/JSONInspector.d.ts +9 -0
- package/dist/views/CanvasEditor/components/JSONInspector.d.ts.map +1 -0
- package/dist/views/CanvasEditor/components/JSONInspector.js +56 -0
- package/dist/views/CanvasEditor/components/LibraryItem.js +2 -2
- package/dist/views/CanvasEditor/components/PrivacySettingsSection.d.ts +0 -4
- package/dist/views/CanvasEditor/components/PrivacySettingsSection.d.ts.map +1 -1
- package/dist/views/CanvasEditor/components/PrivacySettingsSection.js +6 -28
- package/dist/views/CanvasEditor/components/index.d.ts +2 -0
- package/dist/views/CanvasEditor/components/index.d.ts.map +1 -1
- package/dist/views/CanvasEditor/components/index.js +1 -0
- package/dist/views/CanvasEditor/hooks/useHeroBlock.d.ts.map +1 -1
- package/dist/views/CanvasEditor/hooks/useHeroBlock.js +15 -18
- package/dist/views/CanvasEditor/hooks/usePostLoader.d.ts +3 -0
- package/dist/views/CanvasEditor/hooks/usePostLoader.d.ts.map +1 -1
- package/dist/views/CanvasEditor/hooks/usePostLoader.js +12 -13
- package/dist/views/CanvasEditor/hooks/useUnsavedChanges.js +0 -4
- package/dist/views/PostManager/EmptyState.d.ts +1 -1
- package/dist/views/PostManager/EmptyState.js +4 -4
- package/dist/views/PostManager/FilterDropdown.d.ts +21 -0
- package/dist/views/PostManager/FilterDropdown.d.ts.map +1 -0
- package/dist/views/PostManager/FilterDropdown.js +28 -0
- package/dist/views/PostManager/LanguageFlags.d.ts.map +1 -1
- package/dist/views/PostManager/LanguageFlags.js +4 -1
- package/dist/views/PostManager/PostCards.d.ts.map +1 -1
- package/dist/views/PostManager/PostCards.js +23 -40
- package/dist/views/PostManager/PostFilters.d.ts.map +1 -1
- package/dist/views/PostManager/PostFilters.js +34 -3
- package/dist/views/PostManager/PostManagerView.d.ts +1 -2
- package/dist/views/PostManager/PostManagerView.d.ts.map +1 -1
- package/dist/views/PostManager/PostManagerView.js +30 -96
- package/dist/views/PostManager/PostStats.d.ts.map +1 -1
- package/dist/views/PostManager/PostStats.js +10 -10
- package/dist/views/PostManager/PostTable.d.ts.map +1 -1
- package/dist/views/PostManager/PostTable.js +23 -40
- package/dist/views/Settings/SettingsView.d.ts +1 -1
- package/dist/views/Settings/SettingsView.d.ts.map +1 -1
- package/dist/views/Settings/SettingsView.js +12 -39
- package/dist/views/SlugSEO/SlugSEOManagerView.d.ts.map +1 -1
- package/dist/views/SlugSEO/SlugSEOManagerView.js +2 -2
- package/package.json +42 -6
- package/src/api/categories.ts +48 -52
- package/src/api/handler.ts +87 -594
- package/src/api/router.ts +15 -65
- package/src/api/service.ts +241 -0
- package/src/hooks/useAutoSave.ts +64 -0
- package/src/hooks/useCategories.ts +19 -47
- package/src/index.tsx +79 -293
- package/src/init.tsx +24 -11
- package/src/lib/blocks/BlockRenderer.tsx +1 -0
- package/src/lib/layouts/blocks/ColumnsBlock.tsx +60 -173
- package/src/lib/layouts/blocks/SectionBlock.tsx +22 -26
- package/src/lib/layouts/index.ts +4 -4
- package/src/lib/mappers/apiMapper.ts +63 -32
- package/src/lib/rich-text/RichTextEditor.tsx +16 -9
- package/src/lib/utils/config-resolver.ts +64 -0
- package/src/lib/utils/tree.ts +150 -0
- package/src/state/EditorContext.tsx +153 -232
- package/src/state/reducer.ts +141 -606
- package/src/state/types.ts +14 -1
- package/src/types/block.ts +10 -0
- package/src/types/post.ts +19 -1
- package/src/views/CanvasEditor/BlockWrapper.tsx +130 -460
- package/src/views/CanvasEditor/CanvasEditorView.tsx +145 -420
- package/src/views/CanvasEditor/EditorBody.tsx +98 -610
- package/src/views/CanvasEditor/EditorHeader.tsx +176 -196
- package/src/views/CanvasEditor/LayoutContainer.tsx +74 -89
- package/src/views/CanvasEditor/components/CustomBlockItem.tsx +7 -8
- package/src/views/CanvasEditor/components/EditorCanvas.tsx +139 -84
- package/src/views/CanvasEditor/components/EditorLibrary.tsx +25 -10
- package/src/views/CanvasEditor/components/EditorSidebar.tsx +196 -127
- package/src/views/CanvasEditor/components/FeaturedMediaSection.tsx +78 -210
- package/src/views/CanvasEditor/components/JSONInspector.tsx +125 -0
- package/src/views/CanvasEditor/components/LibraryItem.tsx +5 -6
- package/src/views/CanvasEditor/components/PrivacySettingsSection.tsx +73 -124
- package/src/views/CanvasEditor/components/index.ts +2 -1
- package/src/views/CanvasEditor/hooks/useHeroBlock.ts +15 -18
- package/src/views/CanvasEditor/hooks/usePostLoader.ts +21 -13
- package/src/views/CanvasEditor/hooks/useUnsavedChanges.ts +4 -4
- package/src/views/PostManager/EmptyState.tsx +9 -10
- package/src/views/PostManager/FilterDropdown.tsx +95 -0
- package/src/views/PostManager/LanguageFlags.tsx +6 -2
- package/src/views/PostManager/PostCards.tsx +127 -133
- package/src/views/PostManager/PostFilters.tsx +73 -68
- package/src/views/PostManager/PostManagerView.tsx +132 -179
- package/src/views/PostManager/PostStats.tsx +21 -20
- package/src/views/PostManager/PostTable.tsx +137 -165
- package/src/views/Settings/SettingsView.tsx +64 -180
- package/src/views/SlugSEO/SlugSEOManagerView.tsx +59 -44
- package/src/hooks/index.d.ts +0 -8
- package/src/hooks/index.d.ts.map +0 -1
- package/src/hooks/useBlog.d.ts +0 -31
- package/src/hooks/useBlog.d.ts.map +0 -1
- package/src/hooks/useBlogs.d.ts +0 -39
- package/src/hooks/useBlogs.d.ts.map +0 -1
- package/src/hooks/useCategories.d.ts +0 -9
- package/src/hooks/useCategories.d.ts.map +0 -1
- package/src/lib/blocks/BlockRenderer.d.ts +0 -54
- package/src/lib/blocks/BlockRenderer.d.ts.map +0 -1
- package/src/lib/config-storage.d.ts +0 -30
- package/src/lib/config-storage.d.ts.map +0 -1
- package/src/lib/layouts/blocks/ColumnsBlock.d.ts +0 -25
- package/src/lib/layouts/blocks/ColumnsBlock.d.ts.map +0 -1
- package/src/lib/layouts/blocks/SectionBlock.d.ts +0 -25
- package/src/lib/layouts/blocks/SectionBlock.d.ts.map +0 -1
- package/src/lib/layouts/index.d.ts +0 -23
- package/src/lib/layouts/index.d.ts.map +0 -1
- package/src/lib/layouts/registerLayoutBlocks.d.ts +0 -9
- package/src/lib/layouts/registerLayoutBlocks.d.ts.map +0 -1
- package/src/lib/mappers/apiMapper.d.ts +0 -66
- package/src/lib/mappers/apiMapper.d.ts.map +0 -1
- package/src/lib/rich-text/RichTextEditor.d.ts +0 -45
- package/src/lib/rich-text/RichTextEditor.d.ts.map +0 -1
- package/src/lib/rich-text/RichTextPreview.d.ts +0 -16
- package/src/lib/rich-text/RichTextPreview.d.ts.map +0 -1
- package/src/lib/rich-text/index.d.ts +0 -9
- package/src/lib/rich-text/index.d.ts.map +0 -1
- package/src/lib/utils/blockHelpers.d.ts +0 -23
- package/src/lib/utils/blockHelpers.d.ts.map +0 -1
- package/src/lib/utils/configValidation.d.ts +0 -23
- package/src/lib/utils/configValidation.d.ts.map +0 -1
- package/src/registry/BlockRegistry.d.ts +0 -62
- package/src/registry/BlockRegistry.d.ts.map +0 -1
- package/src/registry/index.d.ts +0 -6
- package/src/registry/index.d.ts.map +0 -1
- package/src/state/EditorContext.d.ts +0 -45
- package/src/state/EditorContext.d.ts.map +0 -1
- package/src/state/index.d.ts +0 -7
- package/src/state/index.d.ts.map +0 -1
- package/src/state/reducer.d.ts +0 -11
- package/src/state/reducer.d.ts.map +0 -1
- package/src/state/types.d.ts +0 -162
- package/src/state/types.d.ts.map +0 -1
- package/src/types/block.d.ts +0 -221
- package/src/types/block.d.ts.map +0 -1
- package/src/types/index.d.ts +0 -8
- package/src/types/index.d.ts.map +0 -1
- package/src/types/post.d.ts +0 -136
- package/src/types/post.d.ts.map +0 -1
- package/src/utils/client.d.ts +0 -48
- package/src/utils/client.d.ts.map +0 -1
- package/src/views/CanvasEditor/BlockWrapper.d.ts +0 -16
- package/src/views/CanvasEditor/BlockWrapper.d.ts.map +0 -1
- package/src/views/CanvasEditor/CanvasEditorView.d.ts +0 -14
- package/src/views/CanvasEditor/CanvasEditorView.d.ts.map +0 -1
- package/src/views/CanvasEditor/EditorBody.d.ts +0 -22
- package/src/views/CanvasEditor/EditorBody.d.ts.map +0 -1
- package/src/views/CanvasEditor/EditorHeader.d.ts +0 -18
- package/src/views/CanvasEditor/EditorHeader.d.ts.map +0 -1
- package/src/views/CanvasEditor/LayoutContainer.d.ts +0 -17
- package/src/views/CanvasEditor/LayoutContainer.d.ts.map +0 -1
- package/src/views/CanvasEditor/SaveConfirmationModal.d.ts +0 -13
- package/src/views/CanvasEditor/SaveConfirmationModal.d.ts.map +0 -1
- package/src/views/CanvasEditor/components/CustomBlockItem.d.ts +0 -14
- package/src/views/CanvasEditor/components/CustomBlockItem.d.ts.map +0 -1
- package/src/views/CanvasEditor/components/EditorCanvas.d.ts +0 -29
- package/src/views/CanvasEditor/components/EditorCanvas.d.ts.map +0 -1
- package/src/views/CanvasEditor/components/EditorLibrary.d.ts +0 -7
- package/src/views/CanvasEditor/components/EditorLibrary.d.ts.map +0 -1
- package/src/views/CanvasEditor/components/EditorSidebar.d.ts +0 -13
- package/src/views/CanvasEditor/components/EditorSidebar.d.ts.map +0 -1
- package/src/views/CanvasEditor/components/ErrorBanner.d.ts +0 -6
- package/src/views/CanvasEditor/components/ErrorBanner.d.ts.map +0 -1
- package/src/views/CanvasEditor/components/FeaturedMediaSection.d.ts +0 -25
- package/src/views/CanvasEditor/components/FeaturedMediaSection.d.ts.map +0 -1
- package/src/views/CanvasEditor/components/LibraryItem.d.ts +0 -14
- package/src/views/CanvasEditor/components/LibraryItem.d.ts.map +0 -1
- package/src/views/CanvasEditor/components/PrivacySettingsSection.d.ts +0 -15
- package/src/views/CanvasEditor/components/PrivacySettingsSection.d.ts.map +0 -1
- package/src/views/CanvasEditor/components/index.d.ts +0 -21
- package/src/views/CanvasEditor/components/index.d.ts.map +0 -1
- package/src/views/CanvasEditor/hooks/index.d.ts +0 -10
- package/src/views/CanvasEditor/hooks/index.d.ts.map +0 -1
- package/src/views/CanvasEditor/hooks/useHeroBlock.d.ts +0 -8
- package/src/views/CanvasEditor/hooks/useHeroBlock.d.ts.map +0 -1
- package/src/views/CanvasEditor/hooks/useKeyboardShortcuts.d.ts +0 -3
- package/src/views/CanvasEditor/hooks/useKeyboardShortcuts.d.ts.map +0 -1
- package/src/views/CanvasEditor/hooks/usePostLoader.d.ts +0 -5
- package/src/views/CanvasEditor/hooks/usePostLoader.d.ts.map +0 -1
- package/src/views/CanvasEditor/hooks/useRegisteredBlocks.d.ts +0 -2
- package/src/views/CanvasEditor/hooks/useRegisteredBlocks.d.ts.map +0 -1
- package/src/views/CanvasEditor/hooks/useUnsavedChanges.d.ts +0 -25
- package/src/views/CanvasEditor/hooks/useUnsavedChanges.d.ts.map +0 -1
- package/src/views/CanvasEditor/index.d.ts +0 -16
- package/src/views/CanvasEditor/index.d.ts.map +0 -1
- package/src/views/PostManager/EmptyState.d.ts +0 -10
- package/src/views/PostManager/EmptyState.d.ts.map +0 -1
- package/src/views/PostManager/PostActionsMenu.d.ts +0 -12
- package/src/views/PostManager/PostActionsMenu.d.ts.map +0 -1
- package/src/views/PostManager/PostCards.d.ts +0 -15
- package/src/views/PostManager/PostCards.d.ts.map +0 -1
- package/src/views/PostManager/PostFilters.d.ts +0 -16
- package/src/views/PostManager/PostFilters.d.ts.map +0 -1
- package/src/views/PostManager/PostManagerView.d.ts +0 -11
- package/src/views/PostManager/PostManagerView.d.ts.map +0 -1
- package/src/views/PostManager/PostStats.d.ts +0 -11
- package/src/views/PostManager/PostStats.d.ts.map +0 -1
- package/src/views/PostManager/PostTable.d.ts +0 -15
- package/src/views/PostManager/PostTable.d.ts.map +0 -1
- package/src/views/PostManager/index.d.ts +0 -12
- package/src/views/PostManager/index.d.ts.map +0 -1
- package/src/views/Preview/PreviewBridgeView.d.ts +0 -12
- package/src/views/Preview/PreviewBridgeView.d.ts.map +0 -1
- package/src/views/Preview/index.d.ts +0 -6
- package/src/views/Preview/index.d.ts.map +0 -1
- package/src/views/Settings/SettingsView.d.ts +0 -10
- package/src/views/Settings/SettingsView.d.ts.map +0 -1
- package/src/views/Settings/index.d.ts +0 -6
- package/src/views/Settings/index.d.ts.map +0 -1
- package/src/views/SlugSEO/SlugSEOManagerView.d.ts +0 -12
- package/src/views/SlugSEO/SlugSEOManagerView.d.ts.map +0 -1
- package/src/views/SlugSEO/index.d.ts +0 -6
- package/src/views/SlugSEO/index.d.ts.map +0 -1
|
@@ -32,8 +32,10 @@ export interface RichTextFormattingConfig {
|
|
|
32
32
|
}
|
|
33
33
|
|
|
34
34
|
export interface RichTextEditorProps {
|
|
35
|
+
/** HTML content value (alias for value) */
|
|
36
|
+
content?: string;
|
|
35
37
|
/** HTML content value */
|
|
36
|
-
value
|
|
38
|
+
value?: string;
|
|
37
39
|
/** Change handler */
|
|
38
40
|
onChange: (html: string) => void;
|
|
39
41
|
/** Placeholder text */
|
|
@@ -49,6 +51,7 @@ export interface RichTextEditorProps {
|
|
|
49
51
|
}
|
|
50
52
|
|
|
51
53
|
export function RichTextEditor({
|
|
54
|
+
content,
|
|
52
55
|
value,
|
|
53
56
|
onChange,
|
|
54
57
|
placeholder = 'Enter text...',
|
|
@@ -65,6 +68,9 @@ export function RichTextEditor({
|
|
|
65
68
|
const [showColorPicker, setShowColorPicker] = useState(false);
|
|
66
69
|
const [selectedText, setSelectedText] = useState('');
|
|
67
70
|
const [currentColor, setCurrentColor] = useState<string | null>(null);
|
|
71
|
+
const isMounted = useRef(false);
|
|
72
|
+
|
|
73
|
+
const actualContent = content ?? value ?? '';
|
|
68
74
|
|
|
69
75
|
// Check which formatting options are available
|
|
70
76
|
const hasBold = formatting?.bold !== false;
|
|
@@ -75,19 +81,20 @@ export function RichTextEditor({
|
|
|
75
81
|
|
|
76
82
|
// Initialize content when component mounts
|
|
77
83
|
useEffect(() => {
|
|
78
|
-
if (editorRef.current && !
|
|
79
|
-
editorRef.current.innerHTML =
|
|
84
|
+
if (editorRef.current && !isMounted.current && actualContent) {
|
|
85
|
+
editorRef.current.innerHTML = actualContent;
|
|
86
|
+
isMounted.current = true;
|
|
80
87
|
}
|
|
81
|
-
}, []); //
|
|
88
|
+
}, [actualContent]); // Run when content is available
|
|
82
89
|
|
|
83
|
-
// Update content when
|
|
90
|
+
// Update content when prop changes (but avoid if user is editing)
|
|
84
91
|
useEffect(() => {
|
|
85
92
|
if (editorRef.current && document.activeElement !== editorRef.current) {
|
|
86
|
-
if (editorRef.current.innerHTML !==
|
|
87
|
-
editorRef.current.innerHTML =
|
|
93
|
+
if (editorRef.current.innerHTML !== actualContent) {
|
|
94
|
+
editorRef.current.innerHTML = actualContent;
|
|
88
95
|
}
|
|
89
96
|
}
|
|
90
|
-
}, [
|
|
97
|
+
}, [actualContent]);
|
|
91
98
|
|
|
92
99
|
// Handle focus prop
|
|
93
100
|
useEffect(() => {
|
|
@@ -814,7 +821,7 @@ export function RichTextEditor({
|
|
|
814
821
|
}
|
|
815
822
|
}}
|
|
816
823
|
data-placeholder={placeholder}
|
|
817
|
-
className={`outline-none min-h-[24px] ${!
|
|
824
|
+
className={`outline-none min-h-[24px] ${!actualContent || actualContent === '<br>' || actualContent === '<div><br></div>'
|
|
818
825
|
? 'before:content-[attr(data-placeholder)] before:text-neutral-400 dark:before:text-neutral-500 before:pointer-events-none'
|
|
819
826
|
: ''
|
|
820
827
|
}`}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Plugin Configuration Resolver
|
|
3
|
+
* Centralizes the logic for resolving plugin settings from multiple sources
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { ClientBlockDefinition } from '../../types/block';
|
|
7
|
+
|
|
8
|
+
export interface ResolvedConfig {
|
|
9
|
+
customBlocks: ClientBlockDefinition[];
|
|
10
|
+
darkMode: boolean;
|
|
11
|
+
backgroundColors?: {
|
|
12
|
+
light: string;
|
|
13
|
+
dark?: string;
|
|
14
|
+
};
|
|
15
|
+
LayoutWrapper?: any;
|
|
16
|
+
translations?: Record<string, any>;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Resolves a specific configuration value from priority sources:
|
|
21
|
+
* 1. LocalStorage (Dev overrides)
|
|
22
|
+
* 2. Component Props
|
|
23
|
+
* 3. Window Global (__JHITS_PLUGIN_PROPS__)
|
|
24
|
+
* 4. Default Value
|
|
25
|
+
*/
|
|
26
|
+
export function resolveConfigValue<T>(
|
|
27
|
+
key: string,
|
|
28
|
+
propValue: T | undefined,
|
|
29
|
+
defaultValue: T
|
|
30
|
+
): T {
|
|
31
|
+
if (typeof window === 'undefined') return propValue ?? defaultValue;
|
|
32
|
+
|
|
33
|
+
// 1. Check LocalStorage (Dev priority)
|
|
34
|
+
try {
|
|
35
|
+
const saved = localStorage.getItem('__JHITS_PLUGIN_BLOG_CONFIG__');
|
|
36
|
+
if (saved) {
|
|
37
|
+
const config = JSON.parse(saved);
|
|
38
|
+
if (config[key] !== undefined) return config[key];
|
|
39
|
+
}
|
|
40
|
+
} catch (e) {}
|
|
41
|
+
|
|
42
|
+
// 2. Check Props
|
|
43
|
+
if (propValue !== undefined) return propValue;
|
|
44
|
+
|
|
45
|
+
// 3. Check Window Global
|
|
46
|
+
const globalProps = (window as any).__JHITS_PLUGIN_PROPS__?.['plugin-blog'];
|
|
47
|
+
if (globalProps && globalProps[key] !== undefined) return globalProps[key];
|
|
48
|
+
|
|
49
|
+
// 4. Default
|
|
50
|
+
return defaultValue;
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
/**
|
|
54
|
+
* Resolves all plugin configuration
|
|
55
|
+
*/
|
|
56
|
+
export function resolvePluginConfig(props: any): ResolvedConfig {
|
|
57
|
+
return {
|
|
58
|
+
customBlocks: resolveConfigValue('customBlocks', props.customBlocks, []),
|
|
59
|
+
darkMode: resolveConfigValue('darkMode', props.darkMode, true),
|
|
60
|
+
backgroundColors: resolveConfigValue('backgroundColors', props.backgroundColors, undefined),
|
|
61
|
+
LayoutWrapper: resolveConfigValue('LayoutWrapper', props.LayoutWrapper, undefined),
|
|
62
|
+
translations: resolveConfigValue('translations', props.translations, undefined),
|
|
63
|
+
};
|
|
64
|
+
}
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Tree Utility Functions
|
|
3
|
+
* Generic functions for manipulating nested block trees
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { Block } from '../../types/block';
|
|
7
|
+
|
|
8
|
+
/**
|
|
9
|
+
* Check if the children property contains actual Block objects (nested blocks)
|
|
10
|
+
* rather than just strings (like in the Recipe block)
|
|
11
|
+
*/
|
|
12
|
+
function hasNestedBlocks(node: Block): boolean {
|
|
13
|
+
return !!(node.children &&
|
|
14
|
+
Array.isArray(node.children) &&
|
|
15
|
+
node.children.length > 0 &&
|
|
16
|
+
typeof node.children[0] === 'object' &&
|
|
17
|
+
node.children[0] !== null);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* Find a node in the tree by ID
|
|
22
|
+
*/
|
|
23
|
+
export function findNode(nodes: Block[], id: string): Block | null {
|
|
24
|
+
for (const node of nodes) {
|
|
25
|
+
if (node.id === id) return node;
|
|
26
|
+
if (hasNestedBlocks(node)) {
|
|
27
|
+
const found = findNode(node.children as Block[], id);
|
|
28
|
+
if (found) return found;
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
return null;
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
/**
|
|
35
|
+
* Map over a tree and update nodes
|
|
36
|
+
*/
|
|
37
|
+
export function mapTree(nodes: Block[], mapper: (node: Block) => Block): Block[] {
|
|
38
|
+
return nodes.map(node => {
|
|
39
|
+
const mapped = mapper(node);
|
|
40
|
+
if (hasNestedBlocks(mapped)) {
|
|
41
|
+
return {
|
|
42
|
+
...mapped,
|
|
43
|
+
children: mapTree(mapped.children as Block[], mapper),
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
return mapped;
|
|
47
|
+
});
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
/**
|
|
51
|
+
* Filter a tree and remove nodes
|
|
52
|
+
*/
|
|
53
|
+
export function filterTree(nodes: Block[], predicate: (node: Block) => boolean): Block[] {
|
|
54
|
+
return nodes
|
|
55
|
+
.filter(predicate)
|
|
56
|
+
.map(node => {
|
|
57
|
+
if (hasNestedBlocks(node)) {
|
|
58
|
+
return {
|
|
59
|
+
...node,
|
|
60
|
+
children: filterTree(node.children as Block[], predicate),
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
return node;
|
|
64
|
+
});
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
* Remove a node and return both the new tree and the removed node
|
|
69
|
+
*/
|
|
70
|
+
export function removeNode(nodes: Block[], id: string): { updatedNodes: Block[]; removedNode: Block | null } {
|
|
71
|
+
let removedNode: Block | null = null;
|
|
72
|
+
|
|
73
|
+
// 1. Search at current level
|
|
74
|
+
const index = nodes.findIndex(n => n.id === id);
|
|
75
|
+
if (index !== -1) {
|
|
76
|
+
removedNode = nodes[index];
|
|
77
|
+
const updatedNodes = [...nodes];
|
|
78
|
+
updatedNodes.splice(index, 1);
|
|
79
|
+
return { updatedNodes, removedNode };
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
// 2. Search recursively in children
|
|
83
|
+
const updatedNodes = nodes.map(node => {
|
|
84
|
+
// If we already found the node in a previous iteration of this map, just return the node
|
|
85
|
+
if (removedNode) return node;
|
|
86
|
+
|
|
87
|
+
if (hasNestedBlocks(node)) {
|
|
88
|
+
const { updatedNodes: newChildren, removedNode: found } = removeNode(node.children as Block[], id);
|
|
89
|
+
if (found) {
|
|
90
|
+
removedNode = found;
|
|
91
|
+
return { ...node, children: newChildren };
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
return node;
|
|
95
|
+
});
|
|
96
|
+
|
|
97
|
+
return { updatedNodes, removedNode };
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
/**
|
|
101
|
+
* Add a node to a container at a specific index
|
|
102
|
+
*/
|
|
103
|
+
export function addNodeToContainer(
|
|
104
|
+
nodes: Block[],
|
|
105
|
+
containerId: string,
|
|
106
|
+
newNode: Block,
|
|
107
|
+
index?: number
|
|
108
|
+
): Block[] {
|
|
109
|
+
// 1. Safety check: Can't add a node to itself
|
|
110
|
+
if (newNode.id === containerId) return nodes;
|
|
111
|
+
|
|
112
|
+
// 2. Track if we found and updated the container
|
|
113
|
+
let found = false;
|
|
114
|
+
|
|
115
|
+
const result = mapTree(nodes, node => {
|
|
116
|
+
// Direct container match or column container match (e.g., "block-id-col-0")
|
|
117
|
+
const isMatch = node.id === containerId || containerId.startsWith(`${node.id}-col-`);
|
|
118
|
+
|
|
119
|
+
if (isMatch) {
|
|
120
|
+
found = true;
|
|
121
|
+
// If it's a column container, apply meta
|
|
122
|
+
if (containerId.startsWith(`${node.id}-col-`)) {
|
|
123
|
+
const columnIndex = parseInt(containerId.split('-col-')[1] || '0', 10);
|
|
124
|
+
newNode.meta = { ...newNode.meta, columnIndex };
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
const children = hasNestedBlocks(node)
|
|
128
|
+
? [...(node.children as Block[])]
|
|
129
|
+
: [];
|
|
130
|
+
|
|
131
|
+
// Ensure we don't have duplicates of the same ID in the children
|
|
132
|
+
const filteredChildren = children.filter(c => c.id !== newNode.id);
|
|
133
|
+
|
|
134
|
+
if (index !== undefined && index >= 0 && index <= filteredChildren.length) {
|
|
135
|
+
filteredChildren.splice(index, 0, newNode);
|
|
136
|
+
} else {
|
|
137
|
+
filteredChildren.push(newNode);
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
return { ...node, children: filteredChildren };
|
|
141
|
+
}
|
|
142
|
+
return node;
|
|
143
|
+
});
|
|
144
|
+
|
|
145
|
+
if (!found) {
|
|
146
|
+
throw new Error(`Container ${containerId} not found in the block tree.`);
|
|
147
|
+
}
|
|
148
|
+
|
|
149
|
+
return result;
|
|
150
|
+
}
|