@ramesesinc/platform-core 0.1.5 → 0.1.8

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.
Files changed (91) hide show
  1. package/dist/components/action/LookupPage.js +9 -31
  2. package/dist/components/action/ViewPage.d.ts +2 -0
  3. package/dist/components/action/ViewPage.js +25 -31
  4. package/dist/components/common/UIComponent.js +4 -3
  5. package/dist/components/index.d.ts +1 -1
  6. package/dist/components/index.js +1 -1
  7. package/dist/components/table/DataList.js +2 -2
  8. package/dist/components/view/PopupView.d.ts +13 -0
  9. package/dist/components/view/PopupView.js +25 -20
  10. package/dist/core/DataContext.d.ts +7 -4
  11. package/dist/core/DataContext.js +16 -4
  12. package/dist/core/Page.js +25 -26
  13. package/dist/core/PageCache.js +16 -3
  14. package/dist/core/PageContext.js +90 -18
  15. package/dist/core/PageViewContext.d.ts +13 -1
  16. package/dist/core/PageViewContext.js +89 -5
  17. package/dist/core/PopupContext.d.ts +49 -0
  18. package/dist/core/PopupContext.js +380 -0
  19. package/dist/core/RowContext.js +1 -1
  20. package/dist/core/WindowContext.d.ts +15 -0
  21. package/dist/core/WindowContext.js +28 -0
  22. package/dist/core/index.d.ts +16 -0
  23. package/dist/index.css +25 -7
  24. package/dist/lib/utils/BeanUtils.js +7 -7
  25. package/dist/templates/DataListTemplate.js +7 -2
  26. package/dist/templates/ExplorerTemplate.js +1 -1
  27. package/package.json +5 -5
  28. package/dist/components/action/AlertMessage.tsx +0 -38
  29. package/dist/components/action/Button.tsx +0 -230
  30. package/dist/components/action/CancelEdit.tsx +0 -40
  31. package/dist/components/action/DeleteData.tsx +0 -73
  32. package/dist/components/action/Edit.tsx +0 -40
  33. package/dist/components/action/LookupPage.tsx +0 -113
  34. package/dist/components/action/ProcessRunner.tsx +0 -337
  35. package/dist/components/action/Refresh.tsx +0 -35
  36. package/dist/components/action/SaveData.tsx +0 -74
  37. package/dist/components/action/SelectData.tsx +0 -47
  38. package/dist/components/action/Undo.tsx +0 -50
  39. package/dist/components/action/UpdateContext.tsx +0 -40
  40. package/dist/components/action/UpdateData.tsx +0 -49
  41. package/dist/components/action/ViewBackPage.tsx +0 -46
  42. package/dist/components/action/ViewPage.tsx +0 -141
  43. package/dist/components/common/UIComponent.tsx +0 -86
  44. package/dist/components/common/UIInput.tsx +0 -49
  45. package/dist/components/common/UIMenu.tsx +0 -91
  46. package/dist/components/index.ts +0 -51
  47. package/dist/components/input/CodeEditor.tsx +0 -188
  48. package/dist/components/input/DateField.tsx +0 -274
  49. package/dist/components/input/DayPicker.tsx +0 -5
  50. package/dist/components/input/HtmlCode.tsx +0 -203
  51. package/dist/components/input/JsonCode.tsx +0 -205
  52. package/dist/components/input/MonthPicker.tsx +0 -5
  53. package/dist/components/input/ScriptCode.tsx +0 -195
  54. package/dist/components/input/Select.tsx +0 -78
  55. package/dist/components/input/SqlCode.tsx +0 -162
  56. package/dist/components/input/StringDecision.tsx +0 -64
  57. package/dist/components/input/Text.tsx +0 -57
  58. package/dist/components/input/YearPicker.tsx +0 -81
  59. package/dist/components/list/IconMenu.tsx +0 -115
  60. package/dist/components/list/TabMenu.tsx +0 -127
  61. package/dist/components/list/TreeMenu.tsx +0 -279
  62. package/dist/components/list/TxnTaskList.tsx +0 -198
  63. package/dist/components/output/Label.tsx +0 -50
  64. package/dist/components/table/DataList.tsx +0 -820
  65. package/dist/components/table/DataTable.tsx +0 -572
  66. package/dist/components/table/ListHandler.ts +0 -276
  67. package/dist/components/table/TableContext.tsx +0 -122
  68. package/dist/components/view/ComponentView.tsx +0 -102
  69. package/dist/components/view/FilterView.tsx +0 -21
  70. package/dist/components/view/HtmlForm.tsx +0 -176
  71. package/dist/components/view/HtmlView.tsx +0 -98
  72. package/dist/components/view/IFrameView.tsx +0 -48
  73. package/dist/components/view/Modal.tsx +0 -72
  74. package/dist/components/view/PageView.tsx +0 -131
  75. package/dist/components/view/PopupView.tsx +0 -160
  76. package/dist/components/view/RootView.tsx +0 -109
  77. package/dist/components/view/WizardView.tsx +0 -48
  78. package/dist/lib/layouts/BorderLayout.tsx +0 -31
  79. package/dist/lib/layouts/CardLayout.tsx +0 -73
  80. package/dist/lib/layouts/CenterLayout.tsx +0 -20
  81. package/dist/lib/layouts/GridLayout.tsx +0 -20
  82. package/dist/lib/layouts/HPanel.tsx +0 -31
  83. package/dist/lib/layouts/HorizontalLayout.tsx +0 -29
  84. package/dist/lib/layouts/MainLayout.tsx +0 -16
  85. package/dist/lib/layouts/PageLayout.tsx +0 -29
  86. package/dist/lib/layouts/VPanel.tsx +0 -27
  87. package/dist/lib/layouts/XLayout.tsx +0 -29
  88. package/dist/lib/layouts/YLayout.tsx +0 -29
  89. package/dist/lib/layouts/index.ts +0 -13
  90. /package/dist/components/action/{UpdateContext.d.ts → UpdateState.d.ts} +0 -0
  91. /package/dist/components/action/{UpdateContext.js → UpdateState.js} +0 -0
@@ -1,141 +0,0 @@
1
- "use client";
2
-
3
- import React, { forwardRef, memo, useImperativeHandle, useRef, useState } from "react";
4
- import { useDataContext } from "../../core/DataContext";
5
- import { usePageContext } from "../../core/PageContext";
6
- import { usePageViewContext } from "../../core/PageViewContext";
7
- import { substituteExpr } from "../../lib/utils/BeanUtils";
8
- import { getUrlPageParams, parseHashUrl } from "../../lib/utils/PageUtils";
9
- import { AbstractComponent } from "../../types/component";
10
- import PopupView from "../view/PopupView";
11
-
12
- /* ------------------------------------------------------------------ */
13
- /* Types */
14
-
15
- interface ViewPageProps extends AbstractComponent {
16
- url: string;
17
- mode?: "popup" | "window";
18
- className?: string;
19
- title?: string;
20
- icon?: string | React.ReactNode;
21
- opt?: Record<string, any>;
22
- iconOnly?: boolean;
23
- popupClassName?: string;
24
- }
25
-
26
- /* ------------------------------------------------------------------ */
27
- /* Component */
28
-
29
- const ViewPage = (props: ViewPageProps) => {
30
- const { url, mode, className = "", title, icon, opt = {}, popupClassName = "", iconOnly = false } = props ?? {};
31
- const { data = {} } = opt;
32
-
33
- const dataContext = useDataContext();
34
- const pageView = usePageViewContext();
35
- const pageContext = usePageContext();
36
- const slotRef = useRef<ChildrenSlotHandle>(null);
37
-
38
- /* ---------------------- Events ---------------------- */
39
-
40
- const onClose = () => {
41
- slotRef.current?.update(null);
42
- };
43
-
44
- const handleClick = (e: React.MouseEvent) => {
45
- e.preventDefault();
46
-
47
- if (!url) return;
48
-
49
- const getUrlParams = () => {
50
- let result = null;
51
- if (pageView.isStandalone()) {
52
- const { params } = parseHashUrl(url);
53
- result = params;
54
- } else {
55
- const { params } = getUrlPageParams();
56
- result = params;
57
- }
58
- return result ?? {};
59
- };
60
-
61
- const getUrlData = () => {
62
- let result = null;
63
- if (dataContext == null) {
64
- // use data received from props
65
- const fullData = {
66
- ...pageContext.getAllData(),
67
- ...data,
68
- };
69
- result = fullData;
70
- } else {
71
- result = dataContext.getData();
72
- }
73
- return result ?? {};
74
- };
75
-
76
- const urlParams = getUrlParams();
77
- const urlData = getUrlData();
78
- const surl = substituteExpr(url, { ...urlParams, ...urlData });
79
-
80
- if (mode === "popup") {
81
- const handler = {
82
- onSave: (itm: any) => {
83
- onClose();
84
- pageContext.notifyDepends();
85
- },
86
- refresh: () => {
87
- pageContext.notifyDepends();
88
- },
89
- };
90
-
91
- slotRef.current?.update(<PopupView url={surl} onClose={onClose} eventHandler={handler} />);
92
- } else if (mode === "window") {
93
- pageView.setPage(surl, { mode });
94
- } else {
95
- pageView.pushPage(surl);
96
- }
97
- };
98
-
99
- /* ---------------------- Render ---------------------- */
100
- return (
101
- <>
102
- {iconOnly ? (
103
- <span onClick={handleClick} className={`cursor-pointer ${className}`}>
104
- {icon}
105
- </span>
106
- ) : (
107
- <button onClick={handleClick} className={`px-4 py-2 bg-blue-600 text-white rounded-md hover:bg-blue-700 transition-colors ${className}`}>
108
- {icon && <span className="dl-action-icon">{icon}</span>}
109
- {title || "View Page"}
110
- </button>
111
- )}
112
-
113
- <ChildrenSlot ref={slotRef} />
114
- </>
115
- );
116
- };
117
-
118
- export default ViewPage;
119
-
120
- type ChildrenSlotHandle = {
121
- update: (content: React.ReactNode) => void;
122
- };
123
-
124
- const ChildrenSlot = memo(
125
- forwardRef<ChildrenSlotHandle>((_, ref) => {
126
- const [content, setContent] = useState<React.ReactNode>(null);
127
-
128
- useImperativeHandle(
129
- ref,
130
- () => ({
131
- update: (content: React.ReactNode) => {
132
- // console.log("view page children slot", content);
133
- setContent(content);
134
- },
135
- }),
136
- [],
137
- );
138
-
139
- return <>{content == null ? null : content}</>;
140
- }),
141
- );
@@ -1,86 +0,0 @@
1
- import { compile } from "expression-eval";
2
- import { useEffect, useState } from "react";
3
- import { usePageContext } from "../../core/PageContext";
4
-
5
- export type UIComponentProps = {
6
- name?: string;
7
- title?: string;
8
- depends?: string;
9
- visibleWhen?: string;
10
- children?: React.ReactNode;
11
- labelPosition?: "top" | "left";
12
- style?: string;
13
- };
14
-
15
- const UIComponent = (props: UIComponentProps) => {
16
- const { name, title, depends, children, visibleWhen, labelPosition = "top", style } = props ?? {};
17
- const pageContext = usePageContext();
18
-
19
- const evaluateVisible = (): boolean => {
20
- if (!visibleWhen) return true;
21
- try {
22
- const context = pageContext?.getAllData() ?? {};
23
- const stripped = visibleWhen.replace(/^\s*\{([\s\S]*)\}\s*$/, "$1").trim();
24
- const jsExpr = stripped.replace(/\{\{([\s\S]+?)\}\}/g, (_, path) => {
25
- const val = path
26
- .trim()
27
- .split(".")
28
- .reduce((obj: any, key: string) => obj?.[key], context);
29
- return JSON.stringify(val ?? null);
30
- });
31
- // eslint-disable-next-line no-new-func
32
- // return Boolean(new Function(`return (${jsExpr})`)());
33
- return Boolean(compile(jsExpr)(context));
34
- } catch (e) {
35
- console.warn("visibleWhen eval error:", e);
36
- return true;
37
- }
38
- };
39
-
40
- const [visible, setVisible] = useState(() => evaluateVisible());
41
-
42
- const dependHandler = (val: any) => {
43
- // for visibleWhen
44
- setVisible(evaluateVisible());
45
- };
46
-
47
- useEffect(() => {
48
- const unsubscribe = pageContext?.dependsTo(depends || "", dependHandler);
49
- return unsubscribe;
50
- }, [depends]);
51
-
52
- // Re-evaluate when binding changes (same pattern as Label)
53
- useEffect(() => {
54
- setVisible(evaluateVisible());
55
- }, [pageContext?.binding?.raw, visibleWhen]);
56
-
57
- if (!visible) return null;
58
-
59
- // Top layout (default)
60
- if (labelPosition === "top") {
61
- return (
62
- <div className="flex flex-col gap-1 mb-4">
63
- {title && (
64
- <label htmlFor={name} className="text-sm font-medium text-gray-700">
65
- {title}
66
- </label>
67
- )}
68
- {children}
69
- </div>
70
- );
71
- }
72
-
73
- // Left layout
74
- return (
75
- <div className="flex items-center gap-2 mb-4">
76
- {title && (
77
- <label htmlFor={name} className="text-sm font-medium text-gray-700 min-w-[50px]">
78
- {title}
79
- </label>
80
- )}
81
- <div className="flex-1">{children}</div>
82
- </div>
83
- );
84
- };
85
-
86
- export default UIComponent;
@@ -1,49 +0,0 @@
1
- import { useEffect } from "react";
2
- import { usePageContext } from "../../core/PageContext";
3
-
4
- export type UIInputProps = {
5
- name: string;
6
- depends?: string;
7
- onRefresh: () => void;
8
- };
9
-
10
- const useUIInput = (props: UIInputProps) => {
11
- const { name, depends, onRefresh } = props ?? {};
12
- const pageContext = usePageContext();
13
- // console.log("useIUInput re-render", name, depends, onRefresh);
14
- const binding = pageContext?.binding;
15
-
16
- const getValue = () => {
17
- const val = pageContext?.get(name) ?? "";
18
- // console.log("ui input, get value", name, val, pageContext.getData());
19
- return val;
20
- };
21
-
22
- const setValue = (value: any) => {
23
- pageContext?.set(name, value);
24
- // console.log("after set value", name, pageContext?.get(name));
25
- };
26
-
27
- const initialValue = pageContext?.get(name) ?? "";
28
- // console.log("ui input init", name, initialValue);
29
- useEffect(() => {
30
- if (onRefresh) {
31
- onRefresh();
32
- }
33
- }, [binding?.raw, initialValue]);
34
-
35
- const dependHandler = (val: any) => {
36
- if (onRefresh) {
37
- onRefresh();
38
- }
39
- };
40
-
41
- useEffect(() => {
42
- const unsubscribe = pageContext?.dependsTo(depends || "", dependHandler);
43
- return unsubscribe;
44
- }, [depends]);
45
-
46
- return { initialValue, setValue, getValue, binding };
47
- };
48
-
49
- export default useUIInput;
@@ -1,91 +0,0 @@
1
- import { useEffect, useState } from "react";
2
- import { usePageContext } from "../../core/PageContext";
3
-
4
- export type MenuItem = {
5
- title: string;
6
- page?: string;
7
- icon?: React.ReactNode | string;
8
- mode?: string;
9
- };
10
-
11
- export type MenuGroup = {
12
- title: string;
13
- icon?: React.ReactNode | string;
14
- items: MenuItem[];
15
- };
16
-
17
- export type UIMenuProps = {
18
- items?: Record<string, any>[];
19
- data?: Record<string, any>;
20
- menugroup?: string;
21
- opt?: Record<string, any>;
22
- };
23
-
24
- const useUIMenu = (props: UIMenuProps) => {
25
- const { items: itemMenus, data, menugroup, opt = {} } = props ?? {};
26
-
27
- const pageContext = usePageContext();
28
-
29
- const [menus, setMenus] = useState<MenuGroup[]>([]);
30
- const [loading, setLoading] = useState(false);
31
- const [error, setError] = useState<string | null>(null);
32
-
33
- useEffect(() => {
34
- // 1️⃣ Static items
35
- if (Array.isArray(itemMenus) && itemMenus.length > 0) {
36
- // Check if already grouped (has items array) or flat
37
- const isGrouped = itemMenus.every((item) => Array.isArray(item.items));
38
- if (isGrouped) {
39
- setMenus(itemMenus as MenuGroup[]);
40
- } else {
41
- setMenus([{ title: "", items: itemMenus as MenuItem[] }]); // ✅ wrap in single group
42
- }
43
- return;
44
- }
45
-
46
- const fetchMenus = async () => {
47
- setLoading(true);
48
- setError(null);
49
-
50
- try {
51
- // 2️⃣ Custom API
52
- if (data?.api) {
53
- const res = await pageContext?.execService(data.api, data.params ?? {});
54
- setMenus(Array.isArray(res) ? (res as MenuGroup[]) : []);
55
- return;
56
- }
57
-
58
- // 3️⃣ Menugroup — fetch categories + items, map to MenuGroup[]
59
- if (menugroup != null) {
60
- const menuGroup = await pageContext?.getMgmt("menugroups", menugroup);
61
- const { categories = [] } = menuGroup || {};
62
-
63
- const menusRes = await pageContext?.postMgmt("menus", "list", {
64
- filter: { menugroup },
65
- sort: { sortorder: 1 },
66
- });
67
-
68
- const sorted = Array.isArray(menusRes) ? [...menusRes].sort((a, b) => (a.sortorder ?? 0) - (b.sortorder ?? 0)) : [];
69
-
70
- const mappedItems: MenuGroup[] = categories.map((cat: any) => ({
71
- title: cat.title,
72
- icon: cat.icon,
73
- items: sorted.filter((m: any) => m.category === cat.id),
74
- }));
75
-
76
- setMenus(mappedItems);
77
- }
78
- } catch (err: any) {
79
- setError(err?.message ?? "Failed to load menus");
80
- } finally {
81
- setLoading(false);
82
- }
83
- };
84
-
85
- fetchMenus();
86
- }, [itemMenus, data, menugroup]);
87
-
88
- return { items: menus, loading, error };
89
- };
90
-
91
- export default useUIMenu;
@@ -1,51 +0,0 @@
1
- export { default as Button } from "./action/Button";
2
- //inputs
3
- export { default as DateField } from "./input/DateField";
4
- export { default as DayPicker } from "./input/DayPicker";
5
-
6
- export { default as MonthPicker } from "./input/MonthPicker";
7
- export { default as Select } from "./input/Select";
8
- export { default as Text } from "./input/Text";
9
- export { default as YearPicker } from "./input/YearPicker";
10
-
11
- //codes
12
- export { default as HtmlCode } from "./input/HtmlCode";
13
- export { default as JsonCode } from "./input/JsonCode";
14
- export { default as ScriptCode } from "./input/ScriptCode";
15
- export { default as SqlCode } from "./input/SqlCode";
16
-
17
- //conditions
18
- export { default as StringDecision } from "./input/StringDecision";
19
-
20
- //export { default as YearPicker } from "./input/YearPicker";
21
- export { default as TabMenu } from "./list/TabMenu";
22
- export { default as TreeMenu } from "./list/TreeMenu";
23
- export { default as Label } from "./output/Label";
24
- export { default as DataList } from "./table/DataList";
25
-
26
- //views
27
- export { default as ComponentView } from "./view/ComponentView";
28
- export { default as FilterView } from "./view/FilterView";
29
- export { default as HtmlForm } from "./view/HtmlForm";
30
- export { default as HtmlView } from "./view/HtmlView";
31
- export { default as IFrameView } from "./view/IFrameView";
32
- export { default as RootView } from "./view/RootView";
33
- export { default as WizardView } from "./view/WizardView";
34
- //actions
35
- export { default as AlertMessage } from "./action/AlertMessage";
36
- export { default as DeleteData } from "./action/DeleteData";
37
- export { default as Edit } from "./action/Edit";
38
- export { default as ProcessRunner } from "./action/ProcessRunner";
39
- export { default as Refresh } from "./action/Refresh";
40
- export { default as SaveData } from "./action/SaveData";
41
- export { default as SelectData } from "./action/SelectData";
42
-
43
- export { default as LookupPage } from "./action/LookupPage";
44
- export { default as UpdateContext } from "./action/UpdateContext";
45
- export { default as ViewBackPage } from "./action/ViewBackPage";
46
- export { default as ViewPage } from "./action/ViewPage";
47
- export { default as PageView } from "./view/PageView";
48
-
49
- //lists
50
- export { default as IconMenu } from "./list/IconMenu";
51
- export { default as TxnTaskList } from "./list/TxnTaskList";
@@ -1,188 +0,0 @@
1
- import { useRef, useState, useCallback, useEffect } from "react";
2
- import Editor from "@monaco-editor/react";
3
- import UIComponent from "../common/UIComponent";
4
- import useUIInput, { UIInputProps } from "../common/UIInput";
5
- //import CopyButton from "../ui/CopyButton";
6
-
7
- type CodeEditorType = "sql" | "json" | "java" | "javascript" | "html" | "css" | "typescript" | "xml" | "yaml" | "markdown" | "plaintext";
8
-
9
- const languageMap: Record<CodeEditorType, string> = {
10
- sql: "sql",
11
- json: "json",
12
- java: "groovy",
13
- javascript: "javascript",
14
- html: "html",
15
- css: "css",
16
- typescript: "typescript",
17
- xml: "xml",
18
- yaml: "yaml",
19
- markdown: "markdown",
20
- plaintext: "plaintext",
21
- };
22
-
23
- type CodeEditorProps = UIInputProps & {
24
- type?: CodeEditorType;
25
- height?: number | string;
26
- width?: number | string;
27
- readOnly?: boolean;
28
- immediate?: boolean;
29
- showCopy?: boolean;
30
- };
31
-
32
- const CodeEditor = (props: CodeEditorProps) => {
33
- const {
34
- type = "plaintext",
35
- height = 300,
36
- width = "100%",
37
- readOnly = false,
38
- immediate = true,
39
- showCopy = true,
40
- } = props ?? {};
41
-
42
- const editorRef = useRef<any>(null);
43
- const valueRef = useRef<string>("");
44
- const [fontSize, setFontSize] = useState(14);
45
- const [error, setError] = useState("");
46
-
47
- const language = languageMap[type] ?? type;
48
-
49
- const onRefresh = () => {
50
- setEditorValue(getValue());
51
- };
52
-
53
- const { initialValue, getValue, setValue } = useUIInput({ ...props, onRefresh });
54
- valueRef.current = initialValue ?? "";
55
- const [editorValue, setEditorValue] = useState(valueRef.current);
56
-
57
- // Font size keyboard shortcuts
58
- const handleKeyDown = useCallback((e: KeyboardEvent) => {
59
- if (e.ctrlKey && e.key === "=") {
60
- e.preventDefault();
61
- setFontSize((prev) => Math.min(prev + 1, 40));
62
- }
63
- if (e.ctrlKey && e.key === "-") {
64
- e.preventDefault();
65
- setFontSize((prev) => Math.max(prev - 1, 8));
66
- }
67
- if (e.ctrlKey && e.key === "0") {
68
- e.preventDefault();
69
- setFontSize(14);
70
- }
71
- }, []);
72
-
73
- useEffect(() => {
74
- window.addEventListener("keydown", handleKeyDown);
75
- return () => window.removeEventListener("keydown", handleKeyDown);
76
- }, [handleKeyDown]);
77
-
78
- // JSON-specific validation
79
- const validateJson = (value: string) => {
80
- if (!value.trim()) {
81
- setError("");
82
- return;
83
- }
84
- try {
85
- JSON.parse(value);
86
- setError("");
87
- } catch (e: any) {
88
- setError(e.message);
89
- }
90
- };
91
-
92
- const handleEditorChange = (value?: string) => {
93
- const safeValue = value ?? "";
94
- setEditorValue(safeValue);
95
-
96
- if (type === "json") {
97
- validateJson(safeValue);
98
- }
99
-
100
- if (immediate) {
101
- setValue(safeValue);
102
- }
103
- };
104
-
105
- const handleEditorDidMount = (editor: any, monaco: any) => {
106
- editorRef.current = editor;
107
-
108
- if (type === "json") {
109
- monaco.languages.json.jsonDefaults.setDiagnosticsOptions({
110
- validate: true,
111
- allowComments: false,
112
- schemas: [],
113
- enableSchemaRequest: true,
114
- });
115
- }
116
-
117
- editor.updateOptions({
118
- minimap: { enabled: false },
119
- fontSize,
120
- lineNumbers: "on",
121
- renderWhitespace: "selection",
122
- folding: true,
123
- bracketPairColorization: { enabled: true },
124
- formatOnPaste: true,
125
- formatOnType: true,
126
- });
127
- };
128
-
129
- // Sync font size if editor already mounted
130
- useEffect(() => {
131
- editorRef.current?.updateOptions({ fontSize });
132
- }, [fontSize]);
133
-
134
- /*
135
- //<CopyButton
136
- // item={editorValue}
137
- // copySize={15}
138
- // copiedSize={10}
139
- // classNameCopied="!px-[15px] !py-[10px]"
140
- ///>
141
- */
142
-
143
- return (
144
- <UIComponent {...(props ?? {})}>
145
- <div className="relative w-full bg-white">
146
- {showCopy && (
147
- <div className="absolute top-2 right-4 z-50">
148
- </div>
149
- )}
150
- <Editor
151
- height={height}
152
- width={width}
153
- language={language}
154
- value={editorValue}
155
- onChange={handleEditorChange}
156
- onMount={handleEditorDidMount}
157
- theme="vs-dark"
158
- options={{
159
- readOnly,
160
- domReadOnly: readOnly,
161
- padding: { top: 10 },
162
- selectOnLineNumbers: true,
163
- automaticLayout: true,
164
- minimap: { enabled: false },
165
- fontSize,
166
- wordWrap: "off",
167
- lineNumbers: "on",
168
- renderWhitespace: "selection",
169
- folding: true,
170
- bracketPairColorization: { enabled: true },
171
- formatOnPaste: true,
172
- formatOnType: true,
173
- scrollBeyondLastLine: false,
174
- smoothScrolling: true,
175
- cursorBlinking: "smooth",
176
- renderLineHighlight: "all",
177
- scrollbar: { vertical: "visible", horizontal: "visible" },
178
- }}
179
- />
180
- {error && type === "json" && (
181
- <p className="text-red-500 text-xs mt-1 px-1">{error}</p>
182
- )}
183
- </div>
184
- </UIComponent>
185
- );
186
- };
187
-
188
- export default CodeEditor;