Skip to content

Editor

A code editor with syntax highlighting in the theme colors (100+ languages), line numbers, git markers, auto-closing pairs, folding, a minimap and font zoom. It is uncontrolled: the text, cursor and undo history live in Rust, tied to id, and text is only the initial value. on_change receives the full text and on_cursor the (line, column). pz.code_editor is the base widget without the theme.

ui.editor · Category: Code and tools · Full reference →

EditorEditor
  • For code, configuration files, logs you can edit, or any long text.
  • Use the file path as id: each file keeps its cursor and history when you switch tabs.
  • To replace the text from code, return pz.Command.set_editor_text(id, text).
import pyzed as pz
from pyzed import ui
from pathlib import Path
class Editor(pz.App):
def __init__(self):
self.path = "main.py"
self.text = Path(self.path).read_text()
def save(self):
Path(self.path).write_text(self.text)
def view(self):
return ui.editor(self.path, self.text, path=self.path,
on_change=lambda text: setattr(self, "text", text))
Editor: path="counter.py"Editor: path="counter.py"
path="counter.py"
Code
pz.container(ui.editor("v-py", "class Counter(pz.App):\n count = 0\n\n def view(self):\n return ui.button('Add', self.add)", path="counter.py"), width=470, height=110)
Editor: language="rust"Editor: language="rust"
language="rust"
Code
pz.container(ui.editor("v-rs", "fn main() {\n println!(\"hi\");\n}\n", language="rust"),
width=420, height=90)
Editor: language="json"Editor: language="json"
language="json"
Code
pz.container(ui.editor("v-json", '{\n "name": "notes",\n "version": 2\n}\n', language="json"),
width=420, height=110)
Editor: gutter=FalseEditor: gutter=False
gutter=False
Code
pz.container(ui.editor("v-g", "class Counter(pz.App):\n count = 0\n\n def view(self):\n return ui.button('Add', self.add)", path="a.py", gutter=False), width=470, height=110)
Editor: markers=Editor: markers=
markers=
Code
pz.container(ui.editor("v-m", "class Counter(pz.App):\n count = 0\n\n def view(self):\n return ui.button('Add', self.add)", path="a.py", markers={2: "created", 5: "modified"}),
width=470, height=110)
Editor: minimap=TrueEditor: minimap=True
minimap=True
Code
pz.container(ui.editor("v-mm", "class Counter(pz.App):\n count = 0\n\n def view(self):\n return ui.button('Add', self.add)", path="a.py", minimap=True), width=470, height=124)
Editor: show_whitespace=TrueEditor: show_whitespace=True
show_whitespace=True
Code
pz.container(ui.editor("v-ws", "class Counter(pz.App):\n count = 0\n\n def view(self):\n return ui.button('Add', self.add)", path="a.py", show_whitespace=True), width=470, height=110)
Editor: placeholder=Editor: placeholder=
placeholder=
Code
pz.container(ui.editor("v-ph", "", placeholder="Write something…"), width=420, height=60)
Editor: font_size=16Editor: font_size=16
font_size=16
Code
pz.container(ui.editor("v-fs", "print(\"big\")\n", path="a.py", font_size=16), width=420, height=60)

Blocks fold by indentation (Ctrl+Shift+[ and ]), annotations adds a code lens above a line and minimap=True draws the overview on the right.

Editor: Folding, code lens and minimapEditor: Folding, code lens and minimap

cursor_shape is "bar", "block", "underline" or "hollow"; show_whitespace=True draws spaces and tabs; wrap=True wraps long lines.

Editor: Cursor and whitespaceEditor: Cursor and whitespace

Editor has 6 events of its own, listed below. Like every widget it also has the 18 common events (click, double_click, right_click, mouse_enter, drag, key_down, resize…), attached with .on(...): see Events and Events of every component.

Event Of Handler gets When
on_change ui.editor, pz.code_editor (text) Callable that receives the new value.
on_cursor ui.editor, pz.code_editor (line, column) Callable that receives (line, column).
on_scroll ui.editor, pz.code_editor (info) Called on scroll.
on_zoom ui.editor, pz.code_editor (step) Callable that receives 1, -1 or 0 for Ctrl+= / Ctrl+- / Ctrl+0 and Ctrl+wheel.
on_action ui.editor, pz.code_editor (name) Callable that receives the name of each editor action that runs ("undo", "select_next"…), e.g. to count them.
on_hover ui.editor, pz.code_editor () Callable that receives {line, column, start, end, x, y, height} (the word under the mouse, from 1, and its place in the editor) after the mouse rests on it, and None when it leaves (hover cards).

Handler gets is what Pyzed passes to your callable: () means nothing. Any handler can also be a message (a value that is not callable), which goes to update().

The same events written three ways. Imperative: methods of the app change self. Declarative: the handlers produce messages and one update() decides. Functional: a pure function draws an immutable state and asks for changes with set_state(...). See Imperative, declarative and functional.

class Editor(pz.App):
def __init__(self):
self.text = "print('hello')\n"
self.cursor = (1, 1)
self.font_size = 14
def zoom(self, step): # on_zoom: 1, -1 or 0 (Ctrl+=, Ctrl+-, Ctrl+0)
self.font_size = 14 if step == 0 else self.font_size + step
def view(self):
line, column = self.cursor
return pz.column([
ui.editor("main.py", self.text, path="main.py", font_size=self.font_size, height=200,
on_change=lambda text: setattr(self, "text", text), # every edit
on_cursor=lambda ln, col: setattr(self, "cursor", (ln, col)), # from 1
on_zoom=self.zoom,
on_action=lambda name: print("ran", name)), # "undo"...
ui.status_bar([], [ui.status_item(f"Ln {line}, Col {column}")]),
])
editor(
id,
text='',
*,
language=None,
path=None,
on_change=None,
on_cursor=None,
markers=None,
font_size=None,
line_height=None,
gutter=True,
wrap=False,
active_line=True,
height='fill',
placeholder=None,
annotations=None,
show_whitespace=False,
tab_size=None,
hard_tabs=False,
backspace_unindent=True,
repeat_delay=None,
repeat_rate=None,
capture_keys=(),
on_scroll=None,
auto_close=True,
folding=True,
minimap=False,
cursor_shape='bar',
cursor_blink=True,
cursor_width=2.0,
cursor_color=None,
on_zoom=None,
on_action=None,
highlights=None,
match_brackets=True,
selection_highlight=True,
font=None,
keymap=None,
scrollbar=True,
readonly=False,
on_hover=None,
hover_delay=500,
sticky_scroll=0,
theme=None,
)

A code editor: highlighting with the theme colors, line numbers and git markers.

Property Default Description
id required Identifies the buffer (use the file path).
text "" Initial text.
language None Language. If missing, it is inferred from path.
path None File path.
markers None {line: "created" | "modified" | "deleted"}.
font_size None Font size (defaults to the theme’s).
line_height None Line height.
gutter True Shows line numbers.
wrap False Line wrapping.
active_line True Background color of the cursor line.
height "fill" Height: pixels, "fill", "shrink" or "fill:N" (proportion).
placeholder None Hint text shown when empty.
annotations None {line: "text"} or {line: ("text", color)}: virtual text at the end of the line (code lens, diagnostics).
show_whitespace False Draws spaces as · and tabs as →.
tab_size None Tab inserts spaces up to the next multiple; Enter keeps the indentation (one more level after :); Backspace removes a level.
hard_tabs False With tab_size: Tab, Enter and indent (Ctrl+]) use tab characters instead of spaces.
backspace_unindent True With tab_size: Backspace in leading spaces removes a whole level (False: one space).
repeat_delay None Milliseconds Backspace and Delete wait, held down, before repeating (None: the system’s).
repeat_rate None Deletions per second at most while Backspace or Delete is held down (None: the system’s pace).
capture_keys () Keys the editor leaves to the app’s on_key ("up", "enter"…), e.g. while a completion list is open.
auto_close True Closes brackets and quotes as you type (and wraps the selection).
folding True Fold chevrons in the gutter; Ctrl+Shift+[ folds and Ctrl+Shift+] unfolds.
minimap False True (or a width in pixels) shows a minimap on the right.
cursor_shape "bar" "bar", "block", "underline" or "hollow".
cursor_blink True Whether the cursor blinks.
cursor_width 2.0 Width of the bar cursor.
cursor_color None Cursor color (the theme’s player color by default).
highlights None Ranges painted behind the text in the theme’s search color: [(line, column, end_line, end_column)], from 1, with exclusive ends.
match_brackets True Outlines the bracket that matches the one next to the cursor (Ctrl+M jumps to it).
selection_highlight True Highlights the other occurrences of the selected text (Ctrl+D adds the next one as a cursor).
font None Typeface: "mono" by default; "sans" makes a multi-line text box, like a chat’s message box.
keymap None Zed-style {binding: action} dict ({"ctrl-shift-d": "duplicate_line_down"}); None as the action removes a default key. Build it from per-action overrides with pyzed.ui.editor.keymap_for.
scrollbar True False hides the scrollbars.
readonly False True lets the text be selected and copied but not changed (a log, a traceback).
hover_delay 500 Milliseconds the mouse rests on a word before on_hover is called.
sticky_scroll 0 How many lines of the enclosing blocks (class, def, if…) stay pinned at the top while scrolling (0: none).
theme None Theme to use instead of the current one (pyzed.theme.current()).

Events: on_change, on_cursor, on_scroll, on_zoom, on_action, on_hover (events).

Full reference →

language_token(path)

Returns the highlighter language token for a path ("main.rs" → "rs").

Property Default Description
path required File path.

Full reference →

code_editor(
id,
text='',
*,
language='txt',
size=14.0,
line_height=None,
font=None,
width=None,
height=None,
padding=None,
syntax=None,
bg=None,
color=None,
selection_color=None,
placeholder=None,
placeholder_color=None,
gutter=True,
gutter_color=None,
gutter_active_color=None,
gutter_width=None,
markers=None,
wrap=False,
on_change=None,
on_cursor=None,
active_line=None,
scrollbar_color=None,
annotations=None,
whitespace=None,
tab_size=None,
capture_keys=None,
on_scroll=None,
auto_close=False,
folding=False,
minimap=None,
minimap_thumb=None,
cursor_shape='bar',
cursor_width=2.0,
cursor_blink=True,
cursor_color=None,
on_zoom=None,
on_action=None,
highlights=None,
highlight_color=None,
match_brackets=True,
selection_highlight=True,
keymap=None,
scrollbar=True,
readonly=False,
hard_tabs=False,
backspace_unindent=True,
repeat_delay=None,
repeat_rate=None,
on_hover=None,
hover_delay=500.0,
sticky_scroll=0,
)

A code editor with syntax highlighting, line numbers and git markers, based on Iced’s text_editor. It is uncontrolled: text is only the initial value for that id; the text, cursor and history live in Rust. Use Command.set_editor_text to replace it. For the themed editor use ui.editor.

Property Default Description
id required Identifies the buffer. Reuse it to keep state across renders.
text "" Initial text.
language "txt" Language extension or name ("py", "rs", "json"…).
size 14.0 Font size.
line_height None Line height in pixels.
font None Family (monospace by default).
width None Width: pixels, "fill", "shrink" or "fill:N" (proportion).
height None Height: pixels, "fill", "shrink" or "fill:N" (proportion).
padding None Inner padding: 8, (vertical, horizontal) or (top, right, bottom, left).
syntax None Map of TextMate scopes to colors (provided by Theme.syntax_scopes()).
bg None Background color ("#rrggbb[aa]", (r, g, b[, a]) or "transparent").
color None Text or icon color.
selection_color None Selection color.
placeholder None Hint text shown when empty.
placeholder_color None Placeholder color.
gutter True Shows line numbers.
gutter_color None Line number color.
gutter_active_color None Color of the cursor line’s number.
gutter_width None Gutter width (automatic by default).
markers None {line: color} for git markers in the gutter (lines from 1).
wrap False Line wrapping.
active_line None Background color of the cursor line.
scrollbar_color None Scrollbar color.
annotations None {line: "text"} or {line: ("text", color)}: virtual text at the end of the line (code lens, diagnostics).
whitespace None Draws spaces as · and tabs as → in this color.
tab_size None Tab inserts spaces up to the next multiple; Enter keeps the indentation; Backspace removes a level.
capture_keys None Keys the editor leaves to the app’s on_key ("up", "enter"…), e.g. while a completion list is open.
auto_close False Typing a bracket or quote also inserts its closing pair.
folding False Fold chevrons in the gutter and Ctrl+Shift+[ / ].
minimap None Width of the minimap in pixels (None: no minimap).
minimap_thumb None Color of the minimap’s visible-area highlight.
cursor_shape "bar" "bar", "block", "underline" or "hollow".
cursor_width 2.0 Width of the bar cursor.
cursor_blink True Whether the cursor blinks.
cursor_color None Cursor color.
highlights None Ranges painted behind the text (search results): [(line, column, end_line, end_column)], from 1, with exclusive ends.
highlight_color None Color of highlights.
match_brackets True Outlines the bracket that matches the one next to the cursor.
selection_highlight True Highlights the other occurrences of the selected text.
keymap None Zed-style {binding: action} dict; None as the action removes a default key (pyzed.ui.editor.keymap_for builds one from per-action overrides).
scrollbar True False hides the scrollbars.
readonly False True lets the text be selected and copied but not changed (a log, a traceback).
hard_tabs False With tab_size: Tab, Enter and indent (Ctrl+]) use tab characters instead of spaces.
backspace_unindent True With tab_size: Backspace in leading spaces removes a whole level (False: one space).
repeat_delay None Milliseconds Backspace and Delete wait, held down, before repeating (None: the system’s).
repeat_rate None Deletions per second at most while Backspace or Delete is held down (None: the system’s pace).
hover_delay 500.0 Milliseconds the mouse rests on a word before on_hover is called.
sticky_scroll 0 How many lines of the enclosing blocks (class, def, if…) stay pinned at the top while scrolling (0: none).

Events: on_change, on_cursor, on_scroll, on_zoom, on_action, on_hover (events).

Full reference →