Repository navigation
Roadmap
Planning for widgets wapyt does not have yet. The candidates come from the dhxpyt comparison. The order comes from what the apps built on wapyt hand-roll today. Counts are matching lines in each app's UI module on 2026-10-06 (Monguana / IguanaXterm / wAwesomeChat).
When one ships, move it to the shipped table in the Widget Catalog.
Shipped from this list: Sidebar groups (Priority 3, #40), Message, Toolbar, ContextMenu, ProgressBar, the Form field types, Pagination, resizable layout cells, Popup and tooltips and DataTable editing, frozen columns and CSV export, all 2026-10-06. Then ModalWindow events, DataTable row classes and hidden columns, Form.clear(), the MenuBar, Listbox and Kanban on 2026-10-07, and on 2026-10-08 the two-thumb range slider (#49), Toolbar dropdowns (#50) and the Form's buttons and left labels (#53), fieldsets (#54) and validators (#55), then the rest of Form parity (#56–#62: focus events, set_properties, whole-form disable, icons and disabled options, async validators, file and avatar fields, toggle groups) and Tree checkboxes and drag-and-drop (#63), and the movable, resizable Window (#64).
All four shipped on 2026-10-06: Message, Toolbar, ContextMenu and ProgressBar.
All shipped on 2026-10-06.
Form field types shipped on 2026-10-06: date, time, datetime-local,
color, range, radio, toggle and checkbox_group in
#31, and combo in #32 / #33. Follow-ups if an app asks: combo options loaded from
the server as you type, and a toggle group.
Also shipped on 2026-10-06: Pagination (#34),
resizable layout cells
(#35) and Popup and tooltips (#36).
Follow-ups if an app asks: linking a Pagination to a DataTable directly
(today the app calls page_rows), and saving splitter sizes for you.
DataTable: inline cell editing (#37; see DataTable), frozen columns (#38; see DataTable) and CSV export (#39; see DataTable). Follow-ups if an app asks: footer rows, Excel (.xlsx) export, and editors for the remaining Form field types (time, color, combo).
Added 2026-10-06 from the gap review of every 🟡 / 🔷 row. Three quick wins first, then two larger items.
Quick wins shipped 2026-10-07: ModalWindow events
(#41), DataTable row and cell classes
and hidden columns (#42), and
Form.clear() / reset() (#43).
The MenuBar shipped the same day (#44). The
two-thumb range slider shipped 2026-10-08
(#49), which completes Priority 2b.
Closing with ×, Escape or the backdrop tells the app nothing today, so it
cannot save a draft or clean up. on_show, on_hide and on_close (with
how it closed: button, escape, backdrop, code), matching dhxpyt's
afterShow / afterHide. A veto stays out, per wapyt's
act-then-revert shape.
datatable.js already honours an undocumented row["_class"]. Replace it
with a documented row_class (a row key naming the class) and
ColumnConfig(cell_class=...), so apps can tint overdue rows or flag cells
without CSS selectors on ids (dhxpyt's rowCss, add_row_css,
add_cell_css).
Form.clear(values=True, errors=True) to reset a form for the next entry.
ColumnConfig(hidden=True) plus hide_column / show_column /
is_column_hidden, kept in get_column_state so saved layouts restore it.
A horizontal MenuBar mounted in a cell (dhxpyt menu): top-level labels
that open the existing ContextMenu dropdowns, with
open-on-hover once one is open, Left / Right between menus, and the same
MenuItem model (shortcut hints, submenus, separators). Also gives
ContextMenu persistent enable / disable / show / hide by id and
checked items, which a menu bar needs.
FieldConfig(type="range", range=True) reading back [low, high], plus tick
marks (ticks, major_ticks, labels). One native input cannot have two
thumbs, so this is a small custom slider (pointer and keyboard, two
role="slider" thumbs); the single-thumb field can stay native.
Not scheduled; picked up when an app asks. Details per row are in the gap review.
-
DataTable: per-column header filters ·
scroll_to(row)· row drag-and-drop · cell templates and columnformat· hide/show rows · row spans · footer rows · per-cell click events · row height options · fit-to-content widths · xlsx / pdf export. -
Form: done for parity on 2026-10-08: buttons and left labels (#53),
fieldsets, spacers and static fields (#54), validators (#55, async in #60),
focus events (#56),
set_properties(#57), whole-form disable / hide (#58),max_length, icons and disabled options (#59), file and avatar fields (#61) and toggle groups (#62). Left if an app asks:on_keydown, a form title, combo item templates and server search, toggle-group full-width segments. -
ModalWindow → Window:shipped as a separate Window in #64. - ContextMenu: badge counts · placement relative to an element.
- Toolbar: a search input · a loading state on buttons · hotkeys · a date-picker button. Dropdown and split buttons shipped in #50.
- Pickers as custom widgets (likely in a Popup): date ranges, disabled and highlighted days, an inline month view (toward the Scheduler) · colour palettes and alpha · combo item templates, server search while typing, virtual list, select-all.
- Listbox: now its own item, Priority 2c.
- Cardflow: sortable, groupable row cards that expand in place.
-
Theming: set colour variables from Python ·
prefers-color-scheme· Chat, CardPanel and ResourceBoard on the tokens (also under Foundations).
Requested 2026-10-07: a proper Listbox widget, designed from the start to be
the column of a Kanban board. A one-column DataTable is not enough: items
must hold rich HTML and live widgets, and be dragged within and between lists.
Everything below shipped except virtual rendering for very long lists.
dhxpyt: listbox (drag modes, templates, virtual list), wapyt-only in what
items can hold.
-
Rich items, safely. Each item renders from an
item_template, escaped by default with the same{keyHtml}opt-out ResourceBoard uses, so app data cannot inject markup. Plaintitle/subtitle/icon/badge/metafields cover the common card without a template. -
Live widgets inside items.
list.item_body(id)returns an element to mount wapyt widgets into (a Toolbar, a ProgressBar, a small Form), likeModalWindow.body. DeclaredListActions (icon buttons on each item, shown on hover / focus) cover the simple case and fireon_action {id, action}. -
Interaction does not fight the drag. Buttons, inputs and links inside an
item stay clickable and focusable; a drag starts only from the item itself
or a
drag_handle=Truegrip, and only past a small movement threshold. -
Drag and drop: reorder within a list, and move between lists that share
a
groupname (withcopyandacceptrules per list). Pointer events, not HTML5 drag-and-drop, so it works on touch and shows a real placeholder; auto-scroll near the edges; Escape cancels. Keyboard too: Space picks an item up, arrows move it (Left / Right to the neighbouring list), Space drops, Escape cancels, with live-region announcements. -
The app decides. A drop applies at once and fires
on_move {id, from_list, to_list, from_index, to_index}; if the server refuses,move(id, to_list, index)/set_itemsputs it back. Same act-then-revert shape as DataTable editing; no veto events. -
List features: single / multi selection, keyboard navigation,
on_activate, a filter box, an empty state,add_item/update_item/remove_itemwithout a full redraw, and virtual rendering for long lists.
Everything below shipped except swimlanes.
dhxpyt: kanban. A row of Listbox columns sharing one drag group: column
headers with counts and optional WIP limits, add-card buttons, collapsible and
reorderable columns, horizontal scroll, and swimlanes later. A card is a
Listbox item, so everything above (templates, widgets in cards, keyboard
moves, revert on refusal) comes with it. on_move reports column changes and
order changes alike.
| Candidate | dhxpyt | Notes |
|---|---|---|
Chart |
chart |
Shipped as Chart in #65, on a vendored Chart.js (the CSP rules out a CDN) |
Scheduler |
calendar (picker only) |
Shipped as Scheduler in #67 (day / week / work week / month / agenda, iCal, print). Next: the resource timeline |
Window |
window |
Shipped as Window in #64 |
|
|
tree |
Checkboxes and drag-and-drop shipped in #63; inline rename, copy-drag and dragging between trees remain. See the Tree gaps |
| dhxpyt | Why |
|---|---|
ribbon |
Office-style ribbon; Toolbar with groups covers the need |
cardflow |
CardPanel and ResourceBoard cover card lists. Expand-in-place row cards stay in the backlog in case an app asks |
gpu |
A WebGPU helper, not a widget |
theme module |
wapyt themes through data-wapyt-theme and --wapyt-* CSS properties |
Housekeeping that makes the widgets above cheaper to build:
-
One theming system. Move Chat, CardPanel and ResourceBoard onto the
--wapyt-*tokens (Sidebar moved in #40), and addprefers-color-schemesupport. -
A shared base class.
_resolve_root,_bind_eventand_cleanare copied across widgets with three different event-argument behaviours; a_base.pymixin removes about 150 lines and makes payloads uniform. -
One
Noneconvention for configs, and a way to explicitly clear an optional field. -
Proxy lifetimes.
destroy()methods drop their event proxies without calling.destroy()on them, so they leak. -
Quiet imports.
chat.pyandcardpanel.pyprint to stdout on import.
wapyt is MIT-licensed · Repository · pyTincture · Issues
Getting started
Widgets
- Layout and MainWindow
- Tree
- DataTable
- Form
- ModalWindow
- Window
- TabWidget
- Toolbar
- Sidebar
- Chat
- Terminal
- CardPanel
- ResourceBoard
- File Transfer
- Message
- ContextMenu
- MenuBar
- Listbox
- Kanban
- ProgressBar
- Pagination
- Popup and tooltips
- Chart
- Scheduler
- MediaPlayer
Guides
Planning
Contributing