### Install Generic Editor and Dependencies Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/README.md Install the Generic Editor package along with necessary UI and utility libraries using npm. ```bash npm install @1urso/generic-editor @radix-ui/themes @radix-ui/react-icons react-resizable-panels re-resizable framer-motion @dnd-kit/core ``` -------------------------------- ### Minimal Generic Editor Setup Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Basic setup for the Generic Editor component, including necessary imports for the editor and CSS. ```typescript import { EditorContent } from '@1urso/generic-editor'; import '@1urso/generic-editor/dist/generic-editor.css'; import '@radix-ui/themes/styles.css'; export function MyApp() { const layout = { name: 'My Layout', isList: false, props: [ { name: 'Name', dataName: 'name' }, { name: 'Email', dataName: 'email' } ] }; return (
); } ``` -------------------------------- ### Style Bindings Example (JSON) Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/README.md Example of how to configure style bindings for an element in JSON format. This allows linking element styles like color and background to data variables. ```json { "type": "text", "content": "Preço: {{price}}", "x": 50, "y": 50, "width": 200, "height": 40, "styleBindings": { "color": "priceColor", "backgroundColor": "tagBg" } } ``` -------------------------------- ### Install Generic Editor Package Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/README.md Install the Generic Editor package using npm or yarn. ```bash npm install @1urso/generic-editor # or yarn add @1urso/generic-editor ``` -------------------------------- ### Install Peer Dependencies Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/README.md Install the required peer dependencies for the Generic Editor to ensure proper functionality and performance. ```bash npm install @radix-ui/themes @radix-ui/react-icons react-resizable-panels re-resizable framer-motion @dnd-kit/core ``` -------------------------------- ### Default List Settings Example Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/09-json-structure-and-state.md An example JSON object representing default settings for a list, including sorting, positioning, scrolling, dimensions, and entry animation. ```json { "sortProp": "timestamp", "sortOrder": "desc", "newestPosition": "top", "scrollDirection": "up", "containerHeight": 600, "entryAnimation": { "type": "slideInUp", "duration": 0.5, "delay": 0, "timingFunction": "ease-out" } } ``` -------------------------------- ### Complete Single-Item Layout Example Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/09-json-structure-and-state.md An example JSON object representing a saved state for a single-item layout. It includes element definitions, mock data for a single item, and list settings. ```json { "isList": false, "elements": [ { "id": "550e8400-e29b-41d4-a716-446655440001", "type": "box", "name": "Background", "content": "", "x": 0, "y": 0, "width": 300, "height": 400, "rotation": 0, "style": { "backgroundColor": "#ffffff", "borderRadius": "8px" }, "locked": false, "hidden": false }, { "id": "550e8400-e29b-41d4-a716-446655440002", "type": "image", "name": "Profile Photo", "content": "data:image/jpeg;base64,/9j/4AAQSkZJRgABAQEA...", "x": 75, "y": 20, "width": 150, "height": 150, "rotation": 0, "style": { "borderRadius": "50%" } }, { "id": "550e8400-e29b-41d4-a716-446655440003", "type": "text", "name": "Employee Name", "content": "{{fullName}}", "x": 20, "y": 190, "width": 260, "height": 40, "rotation": 0, "style": { "fontSize": "24px", "fontFamily": "Roboto", "fontWeight": "bold", "color": "#000000", "textAlign": "center" }, "dataBinding": "fullName", "formatting": { "type": "text" } }, { "id": "550e8400-e29b-41d4-a716-446655440004", "type": "text", "name": "Department", "content": "{{department}}", "x": 20, "y": 240, "width": 260, "height": 30, "style": { "fontSize": "14px", "fontFamily": "Arial", "color": "#666666", "textAlign": "center" }, "formatting": { "type": "text" } }, { "id": "550e8400-e29b-41d4-a716-446655440005", "type": "text", "name": "Employee ID", "content": "ID: {{employeeId}}", "x": 20, "y": 350, "width": 260, "height": 20, "style": { "fontSize": "12px", "fontFamily": "Courier New", "color": "#999999", "textAlign": "center" } } ], "singleMockData": { "fullName": "John Doe", "department": "Engineering", "employeeId": "E12345" }, "listSettings": { "sortOrder": "asc" }, "gridSize": 0 } ``` -------------------------------- ### EditorContent Usage Example Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/01-components-and-exports.md Demonstrates how to integrate the `EditorContent` component into a React application. It shows basic setup with layout configuration and an `onSave` callback. ```typescript import { EditorContent } from '@1urso/generic-editor'; const MyEditor = () => { const layout = { name: 'Employee ID Card', isList: false, props: [ { name: 'Full Name', dataName: 'nome' }, { name: 'Job Title', dataName: 'cargo' }, { name: 'Avatar URL', dataName: 'fotoUrl' } ] }; return ( { console.log('Saved layout:', json); // Send to backend }} initialState={previouslySavedState} /> ); }; ``` -------------------------------- ### Configure Date Formatting Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/02-types-and-interfaces.md Example of `IElementFormatting` for dates. Specify the type and the desired date format pattern. ```typescript // Date formatting const dateFormat: IElementFormatting = { type: 'date', dateFormat: 'DD/MM/YYYY HH:mm' }; ``` -------------------------------- ### Initialize Generic Editor with Configuration Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/README.md Configure the editor's layout, including single/list mode and available variables. This setup dictates the user interface and data structure. ```tsx import { EditorContent } from "@1urso/generic-editor"; const config = { isList: false, // Single mode (e.g., ID Card) or List (e.g., Catalog) name: "Employee ID Card", props: [ // Define the variables that will appear in the "Insert Variable" button { name: "Full Name", dataName: "nome" }, { name: "Role", dataName: "cargo" }, { name: "Profile Picture", dataName: "fotoUrl" }, ], }; function App() { return (
saveToBackend(json)} theme="light" // Optional: 'light' or 'dark' />
); } ``` -------------------------------- ### Example IElementCondition Usage Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/02-types-and-interfaces.md Illustrates how to create an IElementCondition object to apply specific styles when a data property meets a certain criteria. This example sets text to red and bold if the price exceeds 100. ```typescript const priceCondition: IElementCondition = { id: 'rule-1', property: 'price', operator: 'greaterThan', value: '100', style: { color: '#ff0000', fontWeight: 'bold' } // Red and bold if price > 100 }; ``` -------------------------------- ### Configure Currency Formatting Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/02-types-and-interfaces.md Example of `IElementFormatting` for currency. Specify the type, number format, currency symbol, and decimal places for monetary values. ```typescript // Currency formatting const currencyFormat: IElementFormatting = { type: 'number', numberFormat: 'currency', currencySymbol: '$', decimalPlaces: 2 }; ``` -------------------------------- ### Combining Bindings and Formatting Example Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/05-data-binding-and-formatting.md Demonstrates how content interpolation, style bindings, and conditions work together. 'dataBinding' is not used when 'content' interpolation is present. ```typescript { type: 'text-container', content: 'Status: {{status}} - Price: {{price}}', dataBinding: undefined, // Not used when content interpolation exists formatting: { type: 'text' // Applies to content interpolation }, styleBindings: { 'color': 'statusColor' }, conditions: [ { property: 'price', operator: 'greaterThan', value: '1000', style: { fontWeight: 'bold' } } ], style: { fontSize: '16px', fontFamily: 'Arial' } } ``` ```javascript { status: 'Active', price: 1500, statusColor: '#00aa00' } ``` -------------------------------- ### setSnapLines Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/03-context-api.md Set visual alignment guides (snap lines) for the canvas. ```APIDOC ## setSnapLines ### Description Sets visual alignment guides. ### Method `setSnapLines(lines: { orientation: 'horizontal' | 'vertical', position: number }[])` ### Parameters #### Request Body - **lines** (array) - Required - An array of snap line objects. - **orientation** (string) - Required - The orientation of the snap line ('horizontal' or 'vertical'). - **position** (number) - Required - The position of the snap line. ``` -------------------------------- ### Set Visual Alignment Guides Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/03-context-api.md Configures visual snap lines for alignment. Accepts an array of objects specifying orientation and position. ```typescript setSnapLines: (lines: { orientation: 'horizontal' | 'vertical', position: number }[]) => void; ``` -------------------------------- ### Configure Boolean Formatting Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/02-types-and-interfaces.md Example of `IElementFormatting` for booleans. Customize the display text for true and false values. ```typescript // Boolean formatting const booleanFormat: IElementFormatting = { type: 'boolean', trueLabel: 'Active', falseLabel: 'Inactive' }; ``` -------------------------------- ### Configure Map Formatting Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/02-types-and-interfaces.md Example of `IElementFormatting` for mapped values. Define a mapping object to translate specific keys into display strings. ```typescript // Map formatting const statusFormat: IElementFormatting = { type: 'map', mapping: { 'active': 'Active', 'pending': 'Pending', 'inactive': 'Inactive' } }; ``` -------------------------------- ### Complete Example with Conditional Formatting Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/05-data-binding-and-formatting.md Applies number formatting and conditional styles to a text element based on its 'price' property. The first matching condition determines the applied style. ```typescript { type: 'text', content: 'Price: {{price}}', formatting: { type: 'number', numberFormat: 'currency', currencySymbol: '$', decimalPlaces: 2 }, conditions: [ { id: 'high-price', property: 'price', operator: 'greaterThan', value: '100', style: { color: '#ff0000', fontWeight: 'bold' } }, { id: 'low-price', property: 'price', operator: 'lessThan', value: '50', style: { color: '#00aa00', fontStyle: 'italic' } } ] } ``` -------------------------------- ### Complete List Layout JSON Example Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/09-json-structure-and-state.md This JSON defines a list layout with various elements, including text and containers, along with mock data and list settings for dynamic rendering. ```json { "isList": true, "canvasHeight": 120, "elements": [ { "id": "550e8400-e29b-41d4-a716-446655440001", "type": "box", "name": "Item Container", "content": "", "x": 0, "y": 0, "width": 400, "height": 120, "style": { "backgroundColor": "#f5f5f5", "borderBottom": "1px solid #e0e0e0" } }, { "id": "550e8400-e29b-41d4-a716-446655440002", "type": "text", "name": "Product Name", "content": "{{productName}}", "x": 20, "y": 20, "width": 200, "height": 30, "style": { "fontSize": "16px", "fontWeight": "bold", "color": "#000000" }, "formatting": { "type": "text" } }, { "id": "550e8400-e29b-41d4-a716-446655440003", "type": "text", "name": "Price", "content": "{{price}}", "x": 300, "y": 20, "width": 80, "height": 30, "style": { "fontSize": "16px", "fontWeight": "bold", "color": "#0066ff", "textAlign": "right" }, "formatting": { "type": "number", "numberFormat": "currency", "currencySymbol": "$", "decimalPlaces": 2 }, "conditions": [ { "id": "cond-1", "property": "price", "operator": "greaterThan", "value": "100", "style": { "color": "#ff0000" } } ] }, { "id": "550e8400-e29b-41d4-a716-446655440004", "type": "text", "name": "Description", "content": "{{description}}", "x": 20, "y": 60, "width": 360, "height": 40, "style": { "fontSize": "12px", "color": "#666666" } } ], "mockData": [ { "productName": "Widget A", "price": 50, "description": "High-quality widget, perfect for everyday use" }, { "productName": "Widget B", "price": 150, "description": "Premium widget with advanced features" } ], "listSettings": { "sortProp": "price", "sortOrder": "asc", "newestPosition": "bottom", "scrollDirection": "down", "containerHeight": 480, "entryAnimation": { "type": "slideInUp", "duration": 0.5, "delay": 0, "timingFunction": "ease-out" } }, "gridSize": 0 } ``` -------------------------------- ### Static HTML Player with Pure JavaScript Renderer Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/INTEGRATION.md This example shows the structure of a static HTML file that uses a pure JavaScript renderer function to display content. The `renderTemplate` function, obtained via `getRendererCode()` or copied directly, is used to generate HTML based on configuration and incoming data, typically from a socket or event listener. ```html
``` -------------------------------- ### Generic Editor with Theme and Portal Container Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Advanced setup for the Generic Editor, allowing custom theming and specifying a portal container for modals or dropdowns. Requires `useState` and `useRef` hooks. ```typescript export function EditorPage() { const [theme, setTheme] = useState<'light' | 'dark'>('light'); const portalRef = useRef(null); const layout = { name: 'Employee ID Card', isList: false, props: [ { name: 'Full Name', dataName: 'fullName' }, { name: 'Department', dataName: 'department' }, { name: 'Badge Number', dataName: 'badgeNumber' }, { name: 'Photo URL', dataName: 'photoUrl' } ] }; return ( <> { // Handle save }} />
); } ``` -------------------------------- ### Variable Interpolation Mismatch Example Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/10-troubleshooting-and-advanced.md Illustrates the correct way to match data keys with variables used in content for proper interpolation. Ensure case-sensitivity and exact key names. ```typescript // ❌ Wrong - data key doesn't match const data = { name: 'John' }; const content = 'Hello {{userName}}'; // ✅ Correct const data = { userName: 'John' }; const content = 'Hello {{userName}}'; ``` -------------------------------- ### Minimal Element Object Structure Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/09-json-structure-and-state.md Represents the basic required properties for a minimal element. Use this as a starting point for simple elements. ```json { "id": "unique-uuid", "type": "text", "content": "Static text", "x": 0, "y": 0, "width": 200, "height": 40 } ``` -------------------------------- ### Animation Delay Examples Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Specifies the wait time before an animation begins, measured in seconds. Useful for staggering animations or creating delayed effects. ```typescript delay: 0 // Start immediately delay: 0.1 // 100ms delay delay: 0.5 // 500ms delay delay: 1.0 // 1 second delay ``` -------------------------------- ### Test Data Binding Resolution Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/10-troubleshooting-and-advanced.md This TypeScript example demonstrates how to test data binding by resolving placeholders in a string using a provided data object. It logs the resolved string to the console. ```typescript // Test if variable resolves correctly const testData = { name: 'Test', price: 100 }; const content = 'Hello {{name}}, Price: {{price}}'; const resolved = content.replace(/\{\{\w+\}\\/g, (m, key) => testData[key] || m); console.log(resolved); // "Hello Test, Price: 100" ``` -------------------------------- ### Get CSS Animation Style Properties Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/04-utility-functions.md Converts animation configuration into CSS animation properties. ```typescript const getElementAnimationStyle = (animation?: IElementAnimation) => {}; ``` -------------------------------- ### showPrompt Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/03-context-api.md Show a text input dialog. This dialog allows users to enter text, with options for submission and cancellation, and a default value. ```APIDOC ## showPrompt ### Description Shows a text input dialog. ### Method `showPrompt(message: string, onSubmit: (value: string) => void, onCancel?: () => void, defaultValue?: string)` ### Parameters #### Path Parameters - **message** (string) - Required - The message to display in the prompt dialog. - **onSubmit** (function) - Required - The callback function to execute when the user submits a value. It receives the submitted string value. - **onCancel** (function) - Optional - The callback function to execute when the user cancels. - **defaultValue** (string) - Optional - The default value to pre-fill the input field. ``` -------------------------------- ### Project File Structure Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/README.md Overview of the source code directory structure for the Generic Editor project. ```tree src/ ├── index.ts # Export point ├── editor/ │ ├── index.tsx # Main component │ ├── context.tsx # Editor context and state │ ├── types.ts # Public types │ ├── components/ # UI components │ └── utils/ │ ├── htmlGenerator.tsx # HTML generation │ ├── helpers.ts # Utility functions │ ├── colorUtils.ts # Color parsing │ └── layoutEngine.ts # Layout processing ``` -------------------------------- ### Animation Iteration Count Examples Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Determines how many times an animation will repeat. Can be a number or 'infinite' for continuous looping. ```typescript iterationCount: 1 // Once (default for entry animations) iterationCount: 2 // Twice iterationCount: 3 // Three times iterationCount: 'infinite' // Repeat forever ``` -------------------------------- ### Avoided Variable Naming Conventions Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/05-data-binding-and-formatting.md Shows examples of variable naming conventions that should be avoided, including kebab-case, PascalCase, and snake_case. ```typescript props: [ { name: 'First Name', dataName: 'first-name' }, // kebab-case { name: 'First Name', dataName: 'FirstName' }, // PascalCase { name: 'First Name', dataName: 'first_name' } // snake_case ] ``` -------------------------------- ### Import Editor and Radix UI Styles Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/README.md Import the essential CSS files for the Generic Editor and Radix UI in your application's entry point. This is required for the context menu and overall styling. ```tsx import "@1urso/generic-editor/dist/generic-editor.css"; // Essential for the editor to work import "@radix-ui/themes/styles.css"; ``` -------------------------------- ### OBS Overlay Integration Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Integrate the editor's output as an overlay for OBS (Open Broadcaster Software). This pattern involves opening a new window and dynamically updating its content. ```typescript // In browser, after generating HTML const overlayWindow = window.open('about:blank', 'overlay'); const html = generateHTML(elements, {}, { isList: true }); overlayWindow.document.write(html); // When new alerts come from WebSocket socket.on('alert', (alertData) => { overlayWindow.window.addItem(alertData); }); ``` -------------------------------- ### setGridSize Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/03-context-api.md Enable or disable snap-to-grid functionality. Users can set a pixel size for the grid or pass 0 to disable it. ```APIDOC ## setGridSize ### Description Enables or disables snap-to-grid functionality. ### Method `setGridSize(size: number)` ### Parameters #### Path Parameters - **size** (number) - Required - The grid size in pixels. Pass 0 to disable. ``` -------------------------------- ### Animation Timing Function Examples Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Defines the speed curve of an animation, controlling its acceleration and deceleration. Common values include 'linear', 'ease', and 'bounce'. ```typescript timingFunction: 'linear' // Constant speed timingFunction: 'ease' // Slow start, fast middle, slow end (default) timingFunction: 'ease-in' // Slow start, accelerates timingFunction: 'ease-out' // Fast start, decelerates timingFunction: 'ease-in-out' // Slow start and end, fast middle timingFunction: 'bounce' // Bouncy effect with overshoot ``` -------------------------------- ### Animation Duration Examples Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Controls how long an animation takes to complete in seconds. Shorter durations create snappier animations, while longer ones are more dramatic. ```typescript duration: 0.3 // 300 milliseconds (fast) duration: 0.5 // 500 milliseconds (standard) duration: 1.0 // 1 second (slow) duration: 2.0 // 2 seconds (very slow) ``` -------------------------------- ### Data Management Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/03-context-api.md Methods for managing mock data and list settings. ```APIDOC ## setMockData ### Description Updates both list and single-item mock data used for preview. ### Method `setMockData` ### Parameters - `data` (array) - Required - Array of objects for list mode preview. - `singleData` (object) - Required - Single object for single-item mode preview. ``` ```APIDOC ## updateListSettings ### Description Updates list configuration (sorting, positioning, animation). ### Method `updateListSettings` ### Parameters - `settings` (object) - Required - Partial object with updated list settings. ### Example ```typescript updateListSettings({ sortProp: 'price', sortOrder: 'desc', containerHeight: 600 }); ``` ``` ```APIDOC ## setCanvasHeight ### Description Sets the height constraint for list items. ### Method `setCanvasHeight` ### Parameters - `height` (number) - Required - The new canvas height constraint. ``` -------------------------------- ### Implement a Reusable Template System Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/10-troubleshooting-and-advanced.md Create a template system by defining layout structures in a `TEMPLATES` object and allowing users to select and load them. This enables the creation of reusable editor configurations. ```typescript const TEMPLATES = { simple: { elements: [ { id: '1', type: 'text', content: '{{title}}', x: 0, y: 0, width: 300, height: 50, style: { fontSize: '24px' } } ] }, detailed: { elements: [ // More complex layout ] } }; function TemplateEditor() { const [template, setTemplate] = useState('simple'); const layout = TEMPLATES[template]; return ( <> ); } ``` -------------------------------- ### Basic List Rendering with EditorContent Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Defines a list layout and mock data for rendering a basic price list using the EditorContent component. The onSave callback generates HTML for the list. ```typescript const listLayout = { name: 'Price List', isList: true, props: [ { name: 'Product Name', dataName: 'productName' }, { name: 'Price', dataName: 'price' } ] }; const products = [ { productName: 'Widget A', price: 100 }, { productName: 'Widget B', price: 200 }, { productName: 'Widget C', price: 150 } ]; { const state = JSON.parse(json); const html = generateHTML(state.elements, products, { isList: true, listSettings: state.listSettings }); }} /> ``` -------------------------------- ### Import Layout State Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/07-keyboard-shortcuts-and-features.md To import a layout, use the `initialState` prop when creating the `EditorContent` component. Ensure the JSON file content is parsed before passing it. ```typescript ``` -------------------------------- ### showConfirm Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/03-context-api.md Show a confirmation dialog with OK and Cancel buttons. It accepts a message and optional callback functions for confirmation and cancellation. ```APIDOC ## showConfirm ### Description Shows a confirmation dialog with OK/Cancel options. ### Method `showConfirm(message: string, onConfirm: () => void, onCancel?: () => void)` ### Parameters #### Path Parameters - **message** (string) - Required - The message to display in the confirmation dialog. - **onConfirm** (function) - Required - The callback function to execute when the user confirms. - **onCancel** (function) - Optional - The callback function to execute when the user cancels. ``` -------------------------------- ### Sync Editor State with Real-Time Collaboration Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/10-troubleshooting-and-advanced.md Implement real-time collaboration by opening a WebSocket connection to sync editor state across clients. This involves listening for remote state updates and broadcasting local changes. ```typescript function CollaborativeEditor() { const [state, setState] = useState(null); const editorRef = useRef(null); useEffect(() => { const connection = openWebSocket('ws://server/editor'); connection.on('state-update', (remoteState) => { // Merge or replace local state setState(remoteState); }); return () => connection.close(); }, []); const handleSave = (json) => { // Broadcast to other clients connection.send({ type: 'state-update', payload: json }); }; return ( ); } ``` -------------------------------- ### Server-Side Rendering with Node.js Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Use this pattern to render HTML content on the server using Node.js. It's suitable for dynamic content generation before sending it to the client. ```typescript import { generateHTML } from '@1urso/generic-editor'; // In your backend (Node.js) app.post('/api/render', (req, res) => { const { layout, data } = req.body; const html = generateHTML(layout.elements, data, { isList: layout.isList, listSettings: layout.listSettings, canvasHeight: layout.canvasHeight }); res.set('Content-Type', 'text/html'); res.send(html); }); ``` -------------------------------- ### BounceIn Animation Configuration Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Configures an entrance animation with a bounce effect, where the scale overshoots before settling. Use for playful interactions or confirmations. ```typescript { type: 'bounceIn', duration: 0.6, delay: 0, timingFunction: 'bounce' } ``` -------------------------------- ### Basic Editor Content Usage Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/README.md Demonstrates how to integrate the EditorContent component into a React application. Ensure all necessary CSS and themes are imported. ```typescript import { EditorContent } from '@1urso/generic-editor'; import '@1urso/generic-editor/dist/generic-editor.css'; import '@radix-ui/themes/styles.css'; export function App() { const layout = { name: 'My Layout', isList: false, props: [ { name: 'Name', dataName: 'name' }, { name: 'Email', dataName: 'email' } ] }; return (
console.log('Saved:', json)} />
); } ``` -------------------------------- ### PopIn Animation Configuration Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Configures a quick scale pop effect for snappy animations. Ideal for instant confirmations or quick visual feedback. ```typescript { type: 'popIn', duration: 0.3, delay: 0, timingFunction: 'ease-out' } ``` -------------------------------- ### Define ILayout Interface Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/02-types-and-interfaces.md Represents the configuration passed to the editor component. Use this to define layout properties and behavior. ```typescript interface ILayout { name: string; props: IProp[]; isList?: boolean; } ``` -------------------------------- ### Zustand Integration for Layout State Management Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Utilize Zustand for a simpler state management solution. Define a store to manage layout state, including actions for saving and loading layouts. ```typescript import create from 'zustand'; const useLayoutStore = create(set => ({ layout: null, saveLayout: (json) => set({ layout: JSON.parse(json) }), loadLayout: (id) => { // Fetch from API const layout = fetch(`/api/layouts/${id}`).then(r => r.json()); set({ layout }); } })); function LayoutEditor() { const { layout, saveLayout } = useLayoutStore(); return ( ); } ``` -------------------------------- ### Optimize with Memoization using useMemo Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Employ the `useMemo` hook to memoize expensive calculations, such as generating HTML from elements and data. This prevents re-computation on every render if the dependencies (`elements`, `data`) have not changed. ```typescript import { useMemo } from 'react'; function LayoutEditor({ data }) { const html = useMemo(() => { return generateHTML(elements, data); }, [elements, data]); return
; } ``` -------------------------------- ### Export as Downloadable HTML Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Implement this client-side pattern to allow users to download the generated HTML content directly from the browser. It creates a Blob and triggers a download. ```typescript async function exportAsHTML() { const { state, handleExport } = useEditor(); const html = generateHTML(state.elements, state.singleMockData, { isList: state.isList, listSettings: state.listSettings }); const blob = new Blob([html], { type: 'text/html' }); const url = URL.createObjectURL(blob); const a = document.createElement('a'); a.href = url; a.download = 'layout.html'; document.body.appendChild(a); a.click(); document.body.removeChild(a); URL.revokeObjectURL(url); } ``` -------------------------------- ### BlurIn Animation Configuration Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Configures a transition from a blurred state to a clear focus. Useful for loading states or emphasis on clarity. ```typescript { type: 'blurIn', duration: 0.4, delay: 0 } ``` -------------------------------- ### Staggered List Item Animations Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Demonstrates how to apply staggered animations to individual list items by manually increasing the delay for each subsequent item. This creates a sequential entry effect. ```typescript // First item { type: 'text-container', content: '{{itemName}}', animation: { type: 'slideInUp', duration: 0.5, delay: 0 } }, // Second item { type: 'text-container', content: '{{itemPrice}}', animation: { type: 'slideInUp', duration: 0.5, delay: 0.1 // 100ms later } }, // Third item { type: 'text-container', content: '{{itemDescription}}', animation: { type: 'slideInUp', duration: 0.5, delay: 0.2 // 200ms later } } ``` -------------------------------- ### Valid Image URL Formats Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/10-troubleshooting-and-advanced.md Demonstrates valid and invalid formats for image URLs used within the editor. Ensure URLs are absolute, data URIs, or correctly relative paths. Avoid protocols like 'file://'. ```typescript // ✅ Valid formats 'https://example.com/image.jpg' 'data:image/png;base64,...' '/images/photo.jpg' // ❌ Invalid 'image.jpg' // Relative without / 'file:///path/to/image' // File protocol blocked ``` -------------------------------- ### Show Confirmation Dialog Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/03-context-api.md Displays a confirmation dialog with OK and Cancel buttons. Requires a message and optional onConfirm/onCancel callbacks. ```typescript showConfirm: (message: string, onConfirm: () => void, onCancel?: () => void) => void; ``` -------------------------------- ### Complete Element Object with All Properties Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/09-json-structure-and-state.md Illustrates a comprehensive element object including all optional and advanced properties. This structure is useful for complex elements with dynamic content, styling, data binding, conditions, and animations. ```json { "id": "550e8400-e29b-41d4-a716-446655440000", "type": "text-container", "name": "Dynamic Text Box", "groupId": "group-123", "content": "Hello {{firstName}} {{lastName}}", "x": 50, "y": 100, "width": 300, "height": 150, "rotation": 15, "style": { "color": "#000000", "backgroundColor": "#ffffff", "fontSize": "16px", "fontFamily": "Roboto", "fontWeight": "bold", "textAlign": "center", "textAlignVertical": "middle", "borderRadius": "8px", "borderWidth": "2px", "borderColor": "#cccccc", "padding": "10px", "lineHeight": "1.5" }, "dataBinding": "fullName", "formatting": { "type": "text" }, "conditions": [ { "id": "rule-1", "property": "status", "operator": "equals", "value": "active", "style": { "color": "#00aa00", "fontWeight": "bold" } } ], "autoGrow": true, "containerExpansion": "vertical", "animation": { "type": "slideInUp", "duration": 0.5, "delay": 0.2, "iterationCount": 1, "timingFunction": "ease-out" }, "styleBindings": { "color": "textColor", "backgroundColor": "bgColor" }, "locked": false, "hidden": false } ``` -------------------------------- ### Virtual Scrolling for List Previews Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/10-troubleshooting-and-advanced.md Implement virtual scrolling using `react-window` for previews of long lists to enhance performance. This ensures only the visible items are rendered, improving responsiveness. ```typescript import { FixedSizeList } from 'react-window'; function VirtualListPreview({ items, template }) { return ( {({ index, style }) => (
{generateHTML([template], items[index])}
)}
); } ``` -------------------------------- ### Context Methods Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/INDEX.md Methods available through the Editor Context API. ```APIDOC ## Context Methods ### Description Methods available through the Editor Context API for managing editor state and functionality. ### Categories #### Element Management - addElement - removeElement - updateElement - etc. #### Selection - selectElement - setSelectedElements #### Grouping - groupElements - ungroupElements - renameElement - etc. #### Data - setMockData - updateListSettings - setCanvasHeight #### History - undo - redo - jumpToHistory - loadState #### UI - setGridSize - setZoom - setPan - setSnapLines #### Assets - addAsset - removeAsset #### Dialogs - showAlert - showConfirm - showPrompt - clearFeedback ``` -------------------------------- ### Show Text Input Dialog Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/03-context-api.md Presents a dialog for text input. Accepts a message, onSubmit callback, optional onCancel callback, and a default value. ```typescript showPrompt: (message: string, onSubmit: (value: string) => void, onCancel?: () => void, defaultValue?: string) => void; ``` -------------------------------- ### Date Formatting Object Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/09-json-structure-and-state.md JSON object for date formatting, specifying the desired date format string. ```json { "type": "date", "dateFormat": "DD/MM/YYYY HH:mm" } ``` -------------------------------- ### Manage Loading States with useEffect and useState Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Implement loading states using `useState` and `useEffect` to manage asynchronous data fetching. This pattern provides visual feedback to the user while data is being retrieved, preventing UI inconsistencies. ```typescript const [loading, setLoading] = useState(true); const [layout, setLayout] = useState(null); useEffect(() => { fetch('/api/layout') .then(r => r.json()) .then(data => { setLayout(data); setLoading(false); }) .catch(err => { console.error('Failed to load layout:', err); setLoading(false); }); }, []); return loading ? ( ) : ( ); ``` -------------------------------- ### Spin Animation Configuration Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Configures a continuous 360° rotation. Ideal for loading spinners or rotating icons. ```typescript { type: 'spin', duration: 1, delay: 0, iterationCount: 'infinite', timingFunction: 'linear' } ``` -------------------------------- ### Animated List Entries Configuration Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/06-integration-patterns.md Applies a 'slideInUp' animation to list entries with specified duration and timing. Also sets a fixed container height. ```typescript listSettings: { entryAnimation: { type: 'slideInUp', duration: 0.5, delay: 0, timingFunction: 'ease-out' }, containerHeight: 500 } ``` -------------------------------- ### Spinning Loading Indicator Animation Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md Sets up a continuous spinning animation for a box element, suitable for loading indicators. Configure duration, iteration count for infinite looping, and linear timing. ```typescript { type: 'box', content: '', animation: { type: 'spin', duration: 1, delay: 0, iterationCount: 'infinite', timingFunction: 'linear' } } ``` -------------------------------- ### Configure Percent Number Formatting Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/05-data-binding-and-formatting.md Format numbers as percentages with a specified number of decimal places using `type: 'number'` and `numberFormat: 'percent'`. Ensure the input value is a decimal between 0 and 1. ```typescript formatting: { type: 'number', numberFormat: 'percent', decimalPlaces: 1 } ``` -------------------------------- ### Generate HTML from Layout and Data Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/README.md Use the `generateHTML` function to create the final HTML output for backend or printing purposes. Ensure to pass the correct layout mode and data. ```typescript import { generateHTML } from "@1urso/generic-editor"; // 1. Load layout and data const layout = JSON.parse(db.getLayout()); const dados = db.getFuncionarios(); // Array or Object // 2. Generate HTML const htmlString = generateHTML(layout.elements, dados, { isList: layout.isList, // Important to pass the correct mode listSettings: layout.listSettings, canvasHeight: layout.canvasHeight, // Optional: Force item height }); // 3. Inject where needed document.getElementById("preview").innerHTML = htmlString; ``` -------------------------------- ### Image Element Configuration Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/02-types-and-interfaces.md Configures an image element, specifying the content URL or Base64 data and optional data binding for dynamic image sources. ```typescript { type: 'image', content: 'https://example.com/image.jpg', // or Base64 data URL dataBinding: 'imageUrl' } ``` -------------------------------- ### IListSettings Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/02-types-and-interfaces.md Controls how repeated items are sorted, positioned, and animated in list mode. This interface is used to configure sorting properties, item order, and animation for list entries. ```APIDOC ## Interface: IListSettings ### Description Controls how repeated items are sorted, positioned, and animated in list mode. ### Fields - **sortProp** (`string`) - Optional - Property to sort items by (e.g., `"price"`). - **sortOrder** (`'asc' | 'desc'`) - Required - Ascending or descending order. - **newestPosition** (`'top' | 'bottom'`) - Optional - Where new items appear (default: `'bottom'`). - **scrollDirection** (`'up' | 'down'`) - Optional - Scroll behavior, `'up'` is chat-like (default: `'down'`). - **containerHeight** (`number`) - Optional - Fixed height with scrollbar, or undefined for flexible height. - **entryAnimation** (`IElementAnimation`) - Optional - Animation applied to new items (with `window.addItem()`). ``` -------------------------------- ### Dynamic Item Addition Animation Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/08-animation-reference.md When new items are added to the list using `window.addItem()`, they animate in immediately with the configured entry animation. ```typescript // In generated HTML window.addItem({ name: 'New Subscriber', amount: 5.00 }); // Element slides in with configured animation ``` -------------------------------- ### Define Text Formatting Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/05-data-binding-and-formatting.md Configure text formatting with `type: 'text'` for simple content display. No transformation is applied by default. ```typescript { type: 'text', content: '{{description}}', formatting: { type: 'text' } } ``` -------------------------------- ### Server-Side Rendering for Large Lists Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/10-troubleshooting-and-advanced.md For lists with over 1000 items, use server-side rendering to improve performance. The client sends the layout and basic data, and the server returns the rendered HTML. ```typescript // Client: Send layout and basic data async function renderLargeList(layout, dataArray) { const response = await fetch('/api/render-large-list', { method: 'POST', body: JSON.stringify({ elements: layout.elements, dataArray, listSettings: layout.listSettings }) }); const html = await response.text(); return html; } ``` -------------------------------- ### Configure Currency Number Formatting Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/05-data-binding-and-formatting.md Format numbers as currency by specifying the `currencySymbol` and `decimalPlaces`. Use `numberFormat: 'currency'` for monetary values. ```typescript formatting: { type: 'number', numberFormat: 'currency', currencySymbol: '$', decimalPlaces: 2 } ``` -------------------------------- ### Configure List Settings Source: https://github.com/gabrieltbeserra/genericeditor/blob/main/_autodocs/02-types-and-interfaces.md Use `IListSettings` to control sorting, item positioning, and animations for lists. This interface allows customization of sort properties, order, newest item placement, and scroll direction. ```typescript interface IListSettings { sortProp?: string; sortOrder: 'asc' | 'desc'; newestPosition?: 'top' | 'bottom'; scrollDirection?: 'up' | 'down'; containerHeight?: number; entryAnimation?: IElementAnimation; } ```