A React component for Ace Editor providing comprehensive code editing capabilities with syntax highlighting, themes, and customization options
—
Quality
Pending
Does it follow best practices?
Impact
Pending
No eval scenarios have been run
The primary AceEditor component provides comprehensive code editing functionality with syntax highlighting, themes, autocomplete, and extensive customization options. This is the core component that wraps the Ace Editor with React integration.
The main React component that renders an Ace Editor instance with full configuration and event handling support.
/**
* Main React-Ace editor component
* Renders a fully-featured code editor with syntax highlighting, themes, and customization
*/
declare class ReactAce extends React.Component<IAceEditorProps> {}
interface IAceEditorProps {
/** Unique identifier for the editor instance */
name?: string;
/** CSS styles for the editor container */
style?: React.CSSProperties;
/** Syntax highlighting mode (e.g., "javascript", "python", "java") */
mode?: string | object;
/** Editor theme (e.g., "github", "monokai", "twilight") */
theme?: string;
/** Editor height as CSS value */
height?: string;
/** Editor width as CSS value */
width?: string;
/** CSS class name for the editor container */
className?: string;
/** Font size for editor text */
fontSize?: number | string;
/** Line height for editor text */
lineHeight?: number | string;
/** Show line numbers in gutter */
showGutter?: boolean;
/** Show print margin indicator */
showPrintMargin?: boolean;
/** Highlight the currently active line */
highlightActiveLine?: boolean;
/** Auto-focus the editor on mount */
focus?: boolean;
/** Starting cursor position */
cursorStart?: number;
/** Enable line wrapping */
wrapEnabled?: boolean;
/** Make editor read-only */
readOnly?: boolean;
/** Minimum number of lines to display */
minLines?: number;
/** Maximum number of lines to display */
maxLines?: number;
/** Navigate cursor to end of file on load */
navigateToFileEnd?: boolean;
/** Debounce period for onChange events in milliseconds */
debounceChangePeriod?: number;
/** Enable basic autocompletion */
enableBasicAutocompletion?: boolean | string[];
/** Enable live autocompletion as you type */
enableLiveAutocompletion?: boolean | string[];
/** Enable mobile-friendly menu */
enableMobileMenu?: boolean;
/** Tab size in spaces */
tabSize?: number;
/** Current editor content */
value?: string;
/** Placeholder text when editor is empty */
placeholder?: string;
/** Default content when editor is first rendered */
defaultValue?: string;
/** Scroll margin for editor viewport */
scrollMargin?: number[];
/** Enable code snippets */
enableSnippets?: boolean;
/** Called when text selection changes */
onSelectionChange?: (value: any, event?: any) => void;
/** Called when cursor position changes */
onCursorChange?: (value: any, event?: any) => void;
/** Called on text input */
onInput?: (event?: any) => void;
/** Called when editor is fully loaded */
onLoad?: (editor: Ace.Editor) => void;
/** Called when syntax validation produces annotations */
onValidate?: (annotations: Ace.Annotation[]) => void;
/** Called before ace is loaded (for configuration) */
onBeforeLoad?: (ace: typeof AceBuilds) => void;
/** Called when editor content changes */
onChange?: (value: string, event?: any) => void;
/** Called when text is selected */
onSelection?: (selectedText: string, event?: any) => void;
/** Called when text is copied */
onCopy?: (value: string) => void;
/** Called when text is pasted */
onPaste?: (value: string) => void;
/** Called when editor gains focus */
onFocus?: (event: any, editor?: Ace.Editor) => void;
/** Called when editor loses focus */
onBlur?: (event: any, editor?: Ace.Editor) => void;
/** Called when editor is scrolled */
onScroll?: (editor: IEditorProps) => void;
/** Additional editor properties */
editorProps?: IEditorProps;
/** Ace editor configuration options */
setOptions?: IAceOptions;
/** Keyboard handler mode (e.g., "vim", "emacs") */
keyboardHandler?: string;
/** Custom editor commands */
commands?: ICommand[];
/** Syntax error/warning annotations */
annotations?: Ace.Annotation[];
/** Text highlighting markers */
markers?: IMarker[];
}Basic Editor Setup:
import React, { useState } from "react";
import AceEditor from "react-ace";
// Import required ace modules
import "ace-builds/src-noconflict/mode-javascript";
import "ace-builds/src-noconflict/theme-github";
function CodeEditor() {
const [code, setCode] = useState('function hello() {\n console.log("Hello World!");\n}');
return (
<AceEditor
mode="javascript"
theme="github"
onChange={setCode}
value={code}
name="basic-editor"
width="100%"
height="300px"
fontSize={14}
showPrintMargin={true}
showGutter={true}
highlightActiveLine={true}
/>
);
}Advanced Editor with All Features:
import React, { useState, useRef } from "react";
import AceEditor from "react-ace";
import { IAceEditorProps, ICommand, IMarker } from "react-ace";
// Import various ace modules
import "ace-builds/src-noconflict/mode-typescript";
import "ace-builds/src-noconflict/theme-monokai";
import "ace-builds/src-noconflict/ext-language_tools";
import "ace-builds/src-noconflict/keybinding-vim";
function AdvancedEditor() {
const [code, setCode] = useState('// TypeScript code here');
const [annotations, setAnnotations] = useState([]);
const editorRef = useRef(null);
const customCommands: ICommand[] = [
{
name: 'saveFile',
bindKey: {win: 'Ctrl-S', mac: 'Command-S'},
exec: (editor) => {
// Custom save logic
console.log('Saving file...');
}
}
];
const markers: IMarker[] = [
{
startRow: 0,
startCol: 0,
endRow: 0,
endCol: 10,
className: 'highlight-marker',
type: 'text'
}
];
const handleLoad = (editor) => {
editorRef.current = editor;
editor.focus();
};
const handleValidate = (annotations) => {
setAnnotations(annotations);
};
return (
<AceEditor
mode="typescript"
theme="monokai"
onChange={setCode}
value={code}
name="advanced-editor"
onLoad={handleLoad}
onValidate={handleValidate}
width="100%"
height="600px"
fontSize={16}
lineHeight={19}
showPrintMargin={true}
showGutter={true}
highlightActiveLine={true}
enableBasicAutocompletion={true}
enableLiveAutocompletion={true}
enableSnippets={true}
keyboardHandler="vim"
commands={customCommands}
annotations={annotations}
markers={markers}
setOptions={{
enableBasicAutocompletion: true,
enableLiveAutocompletion: true,
enableSnippets: true,
showLineNumbers: true,
tabSize: 2,
wrap: true,
fontSize: 16
}}
editorProps={{
$blockScrolling: true
}}
/>
);
}Read-Only Display:
import React from "react";
import AceEditor from "react-ace";
import "ace-builds/src-noconflict/mode-json";
import "ace-builds/src-noconflict/theme-github";
function ReadOnlyDisplay({ jsonData }) {
return (
<AceEditor
mode="json"
theme="github"
value={JSON.stringify(jsonData, null, 2)}
name="readonly-display"
readOnly={true}
width="100%"
height="400px"
showGutter={false}
highlightActiveLine={false}
setOptions={{
showLineNumbers: false,
showFoldWidgets: false
}}
/>
);
}The editor accepts extensive configuration through the setOptions prop and individual props:
interface IAceOptions {
/** Text selection style */
selectionStyle?: "line" | "text";
/** Highlight the currently active line */
highlightActiveLine?: boolean;
/** Highlight selected word occurrences */
highlightSelectedWord?: boolean;
/** Make editor read-only */
readOnly?: boolean;
/** Cursor appearance style */
cursorStyle?: "ace" | "slim" | "smooth" | "wide";
/** How to merge undo operations */
mergeUndoDeltas?: false | true | "always";
/** Enable automatic bracket matching */
behavioursEnabled?: boolean;
/** Enable wrap behaviors */
wrapBehavioursEnabled?: boolean;
/** Auto-scroll editor into view when inside scrollable page */
autoScrollEditorIntoView?: boolean;
/** Always show horizontal scrollbar */
hScrollBarAlwaysVisible?: boolean;
/** Always show vertical scrollbar */
vScrollBarAlwaysVisible?: boolean;
/** Highlight gutter line */
highlightGutterLine?: boolean;
/** Animate scrolling */
animatedScroll?: boolean;
/** Show invisible characters */
showInvisibles?: string | boolean;
/** Show print margin line */
showPrintMargin?: boolean;
/** Print margin column position */
printMarginColumn?: number;
/** Print margin setting */
printMargin?: boolean | number;
/** Fade fold widgets when not hovered */
fadeFoldWidgets?: boolean;
/** Show code folding widgets */
showFoldWidgets?: boolean;
/** Show line numbers */
showLineNumbers?: boolean;
/** Show editor gutter */
showGutter?: boolean;
/** Display indent guides */
displayIndentGuides?: boolean;
/** Font size (number or CSS string) */
fontSize?: number | string;
/** Font family CSS property */
fontFamily?: string;
/** Maximum lines to display */
maxLines?: number;
/** Minimum lines to display */
minLines?: number;
/** Allow scrolling past end of document */
scrollPastEnd?: boolean;
/** Use fixed width for gutter */
fixedWidthGutter?: boolean;
/** Theme path (e.g., "ace/theme/monokai") */
theme?: string;
/** Scroll speed multiplier */
scrollSpeed?: number;
/** Drag start delay in milliseconds */
dragDelay?: number;
/** Enable drag and drop */
dragEnabled?: boolean;
/** Focus timeout */
focusTimout?: number;
/** Tooltips follow mouse cursor */
tooltipFollowsMouse?: boolean;
/** First line number */
firstLineNumber?: number;
/** Overwrite mode */
overwrite?: boolean;
/** New line mode */
newLineMode?: "auto" | "unix" | "windows";
/** Use web worker for syntax checking */
useWorker?: boolean;
/** Use soft tabs (spaces) */
useSoftTabs?: boolean;
/** Tab size in spaces */
tabSize?: number;
/** Enable line wrapping */
wrap?: boolean;
/** Code folding style */
foldStyle?: "markbegin" | "markbeginend" | "manual";
/** Language mode path (e.g., "ace/mode/javascript") */
mode?: string;
/** Enable multi-selection */
enableMultiselect?: boolean;
/** Enable Emmet abbreviations */
enableEmmet?: boolean;
/** Enable basic autocompletion */
enableBasicAutocompletion?: boolean;
/** Enable live autocompletion */
enableLiveAutocompletion?: boolean;
/** Enable code snippets */
enableSnippets?: boolean;
/** Enable spell checking */
spellcheck?: boolean;
/** Use elastic tabstops */
useElasticTabstops?: boolean;
}All editor events provide detailed information about the change:
/** Called when editor content changes */
onChange?: (value: string, event?: {
start: { row: number; column: number };
end: { row: number; column: number };
action: "insert" | "remove";
lines: string[];
}) => void;
/** Called when text selection changes */
onSelectionChange?: (selection: {
start: { row: number; column: number };
end: { row: number; column: number };
}, event?: any) => void;
/** Called when cursor position changes */
onCursorChange?: (selection: {
start: { row: number; column: number };
end: { row: number; column: number };
}, event?: any) => void;Add custom keyboard shortcuts and commands:
interface ICommand {
/** Unique command name */
name: string;
/** Key binding configuration */
bindKey: ICommandBindKey;
/** Command execution function or string */
exec: string | ((editor: Ace.Editor, args?: any) => any);
/** Whether command works in read-only mode */
readOnly?: boolean;
}
interface ICommandBindKey {
/** Windows/Linux key combination */
win: string;
/** macOS key combination */
mac: string;
}Display syntax errors, warnings, and highlight text regions:
interface IAnnotation {
/** Line number (0-based) */
row: number;
/** Column number (0-based) */
column: number;
/** Annotation message text */
text: string;
/** Annotation severity level */
type: "error" | "info" | "warning";
}
interface IMarker {
/** Start line (0-based) */
startRow: number;
/** Start column (0-based) */
startCol: number;
/** End line (0-based) */
endRow: number;
/** End column (0-based) */
endCol: number;
/** CSS class for styling */
className: string;
/** Marker type */
type: "fullLine" | "screenLine" | "text" | Ace.MarkerRenderer;
/** Render marker in front of text */
inFront?: boolean;
}Install with Tessl CLI
npx tessl i tessl/npm-react-ace