ratatui_ruby 0.8.0 → 0.9.1
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.
- checksums.yaml +4 -4
- data/.builds/ruby-3.2.yml +2 -2
- data/.builds/ruby-3.3.yml +2 -2
- data/.builds/ruby-3.4.yml +2 -2
- data/.builds/ruby-4.0.0.yml +2 -2
- data/.pre-commit-config.yaml +1 -1
- data/AGENTS.md +3 -3
- data/CHANGELOG.md +77 -1
- data/LICENSES/LGPL-3.0-or-later.txt +304 -0
- data/LICENSES/MIT-0.txt +16 -0
- data/README.md +33 -5
- data/Rakefile +1 -1
- data/doc/concepts/application_architecture.md +44 -3
- data/doc/concepts/application_testing.md +43 -1
- data/doc/concepts/async.md +32 -2
- data/doc/concepts/custom_widgets.md +247 -0
- data/doc/concepts/event_handling.md +32 -3
- data/doc/concepts/interactive_design.md +32 -2
- data/doc/contributors/auditing/parity.md +7 -1
- data/doc/contributors/design/ruby_frontend.md +85 -1
- data/doc/contributors/design/rust_backend.md +67 -1
- data/doc/contributors/developing_examples.md +56 -2
- data/doc/contributors/documentation_style.md +20 -3
- data/doc/contributors/future_work.md +169 -0
- data/doc/contributors/index.md +1 -1
- data/doc/contributors/v1.0.0_blockers.md +19 -185
- data/doc/getting_started/quickstart.md +22 -4
- data/doc/getting_started/why.md +1 -1
- data/doc/index.md +2 -1
- data/doc/troubleshooting/debugging.md +32 -2
- data/doc/troubleshooting/terminal_limitations.md +8 -2
- data/doc/troubleshooting/tui_output.md +42 -0
- data/examples/app_all_events/README.md +14 -2
- data/examples/app_all_events/app.rb +1 -1
- data/examples/app_all_events/model/app_model.rb +1 -1
- data/examples/app_all_events/model/event_color_cycle.rb +1 -1
- data/examples/app_all_events/model/event_entry.rb +1 -1
- data/examples/app_all_events/model/msg.rb +1 -1
- data/examples/app_all_events/model/timestamp.rb +1 -1
- data/examples/app_all_events/update.rb +1 -1
- data/examples/app_all_events/view/app_view.rb +1 -1
- data/examples/app_all_events/view/controls_view.rb +1 -1
- data/examples/app_all_events/view/counts_view.rb +1 -1
- data/examples/app_all_events/view/live_view.rb +1 -1
- data/examples/app_all_events/view/log_view.rb +1 -1
- data/examples/app_all_events/view.rb +1 -1
- data/examples/app_color_picker/README.md +20 -2
- data/examples/app_color_picker/app.rb +1 -1
- data/examples/app_color_picker/clipboard.rb +1 -1
- data/examples/app_color_picker/color.rb +1 -1
- data/examples/app_color_picker/controls.rb +1 -1
- data/examples/app_color_picker/copy_dialog.rb +1 -1
- data/examples/app_color_picker/export_pane.rb +1 -1
- data/examples/app_color_picker/harmony.rb +1 -1
- data/examples/app_color_picker/input.rb +1 -1
- data/examples/app_color_picker/main_container.rb +1 -1
- data/examples/app_color_picker/palette.rb +1 -1
- data/examples/app_login_form/README.md +8 -2
- data/examples/app_login_form/app.rb +1 -1
- data/examples/app_stateful_interaction/README.md +2 -2
- data/examples/app_stateful_interaction/app.rb +71 -17
- data/examples/timeout_demo.rb +1 -1
- data/examples/verify_quickstart_dsl/README.md +6 -0
- data/examples/verify_quickstart_dsl/app.rb +3 -3
- data/examples/verify_quickstart_layout/README.md +6 -0
- data/examples/verify_quickstart_layout/app.rb +3 -3
- data/examples/verify_quickstart_lifecycle/README.md +6 -0
- data/examples/verify_quickstart_lifecycle/app.rb +3 -3
- data/examples/verify_readme_usage/README.md +6 -0
- data/examples/verify_readme_usage/app.rb +3 -3
- data/examples/widget_barchart/README.md +6 -0
- data/examples/widget_barchart/app.rb +2 -2
- data/examples/widget_block/README.md +7 -1
- data/examples/widget_block/app.rb +2 -2
- data/examples/widget_box/README.md +6 -0
- data/examples/widget_box/app.rb +9 -6
- data/examples/widget_calendar/README.md +6 -0
- data/examples/widget_calendar/app.rb +2 -2
- data/examples/widget_canvas/README.md +4 -0
- data/examples/widget_canvas/app.rb +2 -2
- data/examples/widget_cell/README.md +6 -0
- data/examples/widget_cell/app.rb +2 -3
- data/examples/widget_center/README.md +4 -0
- data/examples/widget_center/app.rb +2 -2
- data/examples/widget_chart/README.md +6 -0
- data/examples/widget_chart/app.rb +2 -2
- data/examples/widget_gauge/README.md +6 -0
- data/examples/widget_gauge/app.rb +2 -2
- data/examples/widget_layout_split/README.md +6 -0
- data/examples/widget_layout_split/app.rb +9 -3
- data/examples/widget_line_gauge/README.md +6 -0
- data/examples/widget_line_gauge/app.rb +2 -2
- data/examples/widget_list/README.md +6 -0
- data/examples/widget_list/app.rb +2 -2
- data/examples/widget_map/README.md +8 -2
- data/examples/widget_map/app.rb +2 -2
- data/examples/widget_overlay/README.md +7 -1
- data/examples/widget_overlay/app.rb +2 -2
- data/examples/widget_popup/README.md +6 -0
- data/examples/widget_popup/app.rb +2 -2
- data/examples/widget_ratatui_logo/README.md +6 -0
- data/examples/widget_ratatui_logo/app.rb +2 -3
- data/examples/widget_ratatui_mascot/README.md +6 -0
- data/examples/widget_ratatui_mascot/app.rb +2 -2
- data/examples/widget_rect/README.md +12 -0
- data/examples/widget_rect/app.rb +40 -26
- data/examples/widget_render/README.md +6 -0
- data/examples/widget_render/app.rb +2 -2
- data/examples/widget_render/app.rbs +41 -0
- data/examples/widget_rich_text/README.md +6 -0
- data/examples/widget_rich_text/app.rb +2 -2
- data/examples/widget_scroll_text/README.md +6 -0
- data/examples/widget_scroll_text/app.rb +2 -2
- data/examples/widget_scrollbar/README.md +6 -0
- data/examples/widget_scrollbar/app.rb +2 -2
- data/examples/widget_sparkline/README.md +6 -0
- data/examples/widget_sparkline/app.rb +2 -2
- data/examples/widget_style_colors/README.md +6 -0
- data/examples/widget_style_colors/app.rb +2 -2
- data/examples/widget_table/README.md +8 -2
- data/examples/widget_table/app.rb +2 -2
- data/examples/widget_tabs/README.md +6 -0
- data/examples/widget_tabs/app.rb +2 -2
- data/examples/widget_text_width/README.md +6 -0
- data/examples/widget_text_width/app.rb +4 -4
- data/ext/ratatui_ruby/Cargo.lock +1 -1
- data/ext/ratatui_ruby/Cargo.toml +1 -1
- data/ext/ratatui_ruby/extconf.rb +2 -2
- data/ext/ratatui_ruby/src/events.rs +1 -0
- data/ext/ratatui_ruby/src/rendering.rs +1 -1
- data/ext/ratatui_ruby/src/style.rs +0 -8
- data/ext/ratatui_ruby/src/widgets/chart.rs +0 -118
- data/ext/ratatui_ruby/src/widgets/list_state.rs +36 -0
- data/lib/ratatui_ruby/buffer/cell.rb +34 -2
- data/lib/ratatui_ruby/buffer.rb +2 -2
- data/lib/ratatui_ruby/cell.rb +34 -2
- data/lib/ratatui_ruby/event/focus_gained.rb +26 -2
- data/lib/ratatui_ruby/event/focus_lost.rb +26 -2
- data/lib/ratatui_ruby/event/key/character.rb +18 -2
- data/lib/ratatui_ruby/event/key/media.rb +2 -2
- data/lib/ratatui_ruby/event/key/modifier.rb +10 -2
- data/lib/ratatui_ruby/event/key/navigation.rb +2 -2
- data/lib/ratatui_ruby/event/key/system.rb +2 -2
- data/lib/ratatui_ruby/event/key.rb +114 -2
- data/lib/ratatui_ruby/event/mouse.rb +42 -2
- data/lib/ratatui_ruby/event/none.rb +10 -2
- data/lib/ratatui_ruby/event/paste.rb +34 -2
- data/lib/ratatui_ruby/event/resize.rb +34 -2
- data/lib/ratatui_ruby/event/sync.rb +52 -0
- data/lib/ratatui_ruby/event.rb +32 -2
- data/lib/ratatui_ruby/frame.rb +74 -2
- data/lib/ratatui_ruby/layout/constraint.rb +193 -2
- data/lib/ratatui_ruby/layout/layout.rb +47 -2
- data/lib/ratatui_ruby/layout/rect.rb +403 -2
- data/lib/ratatui_ruby/layout.rb +2 -2
- data/lib/ratatui_ruby/list_state.rb +113 -2
- data/lib/ratatui_ruby/output_guard.rb +26 -3
- data/lib/ratatui_ruby/schema/bar_chart/bar.rb +2 -2
- data/lib/ratatui_ruby/schema/bar_chart/bar_group.rb +2 -2
- data/lib/ratatui_ruby/schema/bar_chart.rb +50 -2
- data/lib/ratatui_ruby/schema/block.rb +21 -15
- data/lib/ratatui_ruby/schema/calendar.rb +2 -2
- data/lib/ratatui_ruby/schema/canvas.rb +10 -2
- data/lib/ratatui_ruby/schema/center.rb +10 -2
- data/lib/ratatui_ruby/schema/chart.rb +2 -28
- data/lib/ratatui_ruby/schema/clear.rb +10 -2
- data/lib/ratatui_ruby/schema/constraint.rb +58 -2
- data/lib/ratatui_ruby/schema/cursor.rb +10 -2
- data/lib/ratatui_ruby/schema/draw.rb +10 -2
- data/lib/ratatui_ruby/schema/gauge.rb +2 -2
- data/lib/ratatui_ruby/schema/layout.rb +18 -2
- data/lib/ratatui_ruby/schema/line_gauge.rb +2 -2
- data/lib/ratatui_ruby/schema/list.rb +10 -2
- data/lib/ratatui_ruby/schema/list_item.rb +10 -2
- data/lib/ratatui_ruby/schema/overlay.rb +10 -2
- data/lib/ratatui_ruby/schema/paragraph.rb +10 -2
- data/lib/ratatui_ruby/schema/ratatui_logo.rb +2 -2
- data/lib/ratatui_ruby/schema/ratatui_mascot.rb +2 -2
- data/lib/ratatui_ruby/schema/rect.rb +58 -2
- data/lib/ratatui_ruby/schema/row.rb +10 -2
- data/lib/ratatui_ruby/schema/scrollbar.rb +2 -2
- data/lib/ratatui_ruby/schema/shape/label.rb +10 -2
- data/lib/ratatui_ruby/schema/sparkline.rb +10 -2
- data/lib/ratatui_ruby/schema/style.rb +18 -2
- data/lib/ratatui_ruby/schema/table.rb +2 -2
- data/lib/ratatui_ruby/schema/tabs.rb +2 -2
- data/lib/ratatui_ruby/schema/text.rb +34 -2
- data/lib/ratatui_ruby/scrollbar_state.rb +10 -2
- data/lib/ratatui_ruby/style/style.rb +18 -2
- data/lib/ratatui_ruby/style.rb +2 -2
- data/lib/ratatui_ruby/synthetic_events.rb +86 -0
- data/lib/ratatui_ruby/table_state.rb +10 -2
- data/lib/ratatui_ruby/terminal_lifecycle.rb +18 -3
- data/lib/ratatui_ruby/test_helper/event_injection.rb +62 -2
- data/lib/ratatui_ruby/test_helper/snapshot.rb +74 -9
- data/lib/ratatui_ruby/test_helper/style_assertions.rb +98 -2
- data/lib/ratatui_ruby/test_helper/terminal.rb +50 -2
- data/lib/ratatui_ruby/test_helper/test_doubles.rb +18 -2
- data/lib/ratatui_ruby/test_helper.rb +10 -2
- data/lib/ratatui_ruby/tui/buffer_factories.rb +2 -2
- data/lib/ratatui_ruby/tui/canvas_factories.rb +2 -2
- data/lib/ratatui_ruby/tui/core.rb +2 -2
- data/lib/ratatui_ruby/tui/layout_factories.rb +32 -2
- data/lib/ratatui_ruby/tui/state_factories.rb +2 -2
- data/lib/ratatui_ruby/tui/style_factories.rb +2 -2
- data/lib/ratatui_ruby/tui/text_factories.rb +2 -2
- data/lib/ratatui_ruby/tui/widget_factories.rb +2 -2
- data/lib/ratatui_ruby/tui.rb +11 -3
- data/lib/ratatui_ruby/version.rb +3 -3
- data/lib/ratatui_ruby/widgets/bar_chart/bar.rb +2 -2
- data/lib/ratatui_ruby/widgets/bar_chart/bar_group.rb +2 -2
- data/lib/ratatui_ruby/widgets/bar_chart.rb +58 -2
- data/lib/ratatui_ruby/widgets/block.rb +37 -15
- data/lib/ratatui_ruby/widgets/calendar.rb +2 -2
- data/lib/ratatui_ruby/widgets/canvas.rb +10 -2
- data/lib/ratatui_ruby/widgets/cell.rb +10 -2
- data/lib/ratatui_ruby/widgets/center.rb +10 -2
- data/lib/ratatui_ruby/widgets/chart.rb +2 -28
- data/lib/ratatui_ruby/widgets/clear.rb +10 -2
- data/lib/ratatui_ruby/widgets/cursor.rb +10 -2
- data/lib/ratatui_ruby/widgets/gauge.rb +16 -2
- data/lib/ratatui_ruby/widgets/line_gauge.rb +16 -2
- data/lib/ratatui_ruby/widgets/list.rb +41 -2
- data/lib/ratatui_ruby/widgets/list_item.rb +10 -2
- data/lib/ratatui_ruby/widgets/overlay.rb +10 -2
- data/lib/ratatui_ruby/widgets/paragraph.rb +10 -2
- data/lib/ratatui_ruby/widgets/ratatui_logo.rb +2 -2
- data/lib/ratatui_ruby/widgets/ratatui_mascot.rb +2 -2
- data/lib/ratatui_ruby/widgets/row.rb +10 -2
- data/lib/ratatui_ruby/widgets/scrollbar.rb +2 -2
- data/lib/ratatui_ruby/widgets/shape/label.rb +10 -2
- data/lib/ratatui_ruby/widgets/sparkline.rb +10 -2
- data/lib/ratatui_ruby/widgets/table.rb +62 -2
- data/lib/ratatui_ruby/widgets/tabs.rb +2 -2
- data/lib/ratatui_ruby/widgets.rb +2 -2
- data/lib/ratatui_ruby.rb +101 -9
- data/sig/examples/app_all_events/view.rbs +7 -1
- data/sig/examples/app_all_events/view_state.rbs +7 -1
- data/sig/examples/app_color_picker/app.rbs +5 -0
- data/sig/examples/app_stateful_interaction/app.rbs +7 -1
- data/sig/examples/verify_quickstart_dsl/app.rbs +7 -1
- data/sig/examples/verify_quickstart_lifecycle/app.rbs +7 -1
- data/sig/examples/verify_readme_usage/app.rbs +7 -1
- data/sig/examples/widget_block_demo/app.rbs +6 -0
- data/sig/examples/widget_box_demo/app.rbs +7 -1
- data/sig/examples/widget_calendar_demo/app.rbs +7 -1
- data/sig/examples/widget_cell_demo/app.rbs +7 -1
- data/sig/examples/widget_chart_demo/app.rbs +7 -1
- data/sig/examples/widget_gauge_demo/app.rbs +7 -1
- data/sig/examples/widget_layout_split/app.rbs +7 -1
- data/sig/examples/widget_line_gauge_demo/app.rbs +7 -1
- data/sig/examples/widget_list_demo/app.rbs +5 -0
- data/sig/examples/widget_map_demo/app.rbs +7 -1
- data/sig/examples/widget_popup_demo/app.rbs +7 -1
- data/sig/examples/widget_ratatui_logo_demo/app.rbs +7 -1
- data/sig/examples/widget_ratatui_mascot_demo/app.rbs +7 -1
- data/sig/examples/widget_rect/app.rbs +7 -1
- data/sig/examples/widget_render/app.rbs +7 -1
- data/sig/examples/widget_rich_text/app.rbs +7 -1
- data/sig/examples/widget_scroll_text/app.rbs +7 -1
- data/sig/examples/widget_scrollbar_demo/app.rbs +7 -1
- data/sig/examples/widget_sparkline_demo/app.rbs +7 -1
- data/sig/examples/widget_style_colors/app.rbs +7 -1
- data/sig/examples/widget_table_demo/app.rbs +7 -1
- data/sig/examples/widget_text_width/app.rbs +7 -1
- data/sig/ratatui_ruby/event.rbs +7 -1
- data/sig/ratatui_ruby/frame.rbs +15 -3
- data/sig/ratatui_ruby/list_state.rbs +11 -1
- data/sig/ratatui_ruby/ratatui_ruby.rbs +8 -2
- data/sig/ratatui_ruby/schema/bar_chart/bar.rbs +7 -1
- data/sig/ratatui_ruby/schema/bar_chart/bar_group.rbs +6 -0
- data/sig/ratatui_ruby/schema/bar_chart.rbs +6 -0
- data/sig/ratatui_ruby/schema/block.rbs +7 -1
- data/sig/ratatui_ruby/schema/calendar.rbs +6 -0
- data/sig/ratatui_ruby/schema/canvas.rbs +6 -0
- data/sig/ratatui_ruby/schema/center.rbs +6 -0
- data/sig/ratatui_ruby/schema/chart.rbs +6 -9
- data/sig/ratatui_ruby/schema/constraint.rbs +14 -0
- data/sig/ratatui_ruby/schema/cursor.rbs +6 -0
- data/sig/ratatui_ruby/schema/draw.rbs +6 -0
- data/sig/ratatui_ruby/schema/gauge.rbs +9 -1
- data/sig/ratatui_ruby/schema/layout.rbs +6 -0
- data/sig/ratatui_ruby/schema/line_gauge.rbs +9 -1
- data/sig/ratatui_ruby/schema/list.rbs +9 -1
- data/sig/ratatui_ruby/schema/list_item.rbs +7 -1
- data/sig/ratatui_ruby/schema/overlay.rbs +6 -0
- data/sig/ratatui_ruby/schema/paragraph.rbs +6 -0
- data/sig/ratatui_ruby/schema/ratatui_logo.rbs +6 -0
- data/sig/ratatui_ruby/schema/ratatui_mascot.rbs +5 -0
- data/sig/ratatui_ruby/schema/rect.rbs +30 -0
- data/sig/ratatui_ruby/schema/row.rbs +7 -1
- data/sig/ratatui_ruby/schema/scrollbar.rbs +6 -0
- data/sig/ratatui_ruby/schema/sparkline.rbs +6 -0
- data/sig/ratatui_ruby/schema/style.rbs +7 -1
- data/sig/ratatui_ruby/schema/table.rbs +11 -1
- data/sig/ratatui_ruby/schema/tabs.rbs +6 -0
- data/sig/ratatui_ruby/schema/text.rbs +7 -1
- data/sig/ratatui_ruby/scrollbar_state.rbs +7 -1
- data/sig/ratatui_ruby/session.rbs +7 -1
- data/sig/ratatui_ruby/table_state.rbs +7 -1
- data/sig/ratatui_ruby/test_helper/event_injection.rbs +7 -1
- data/sig/ratatui_ruby/test_helper/snapshot.rbs +7 -1
- data/sig/ratatui_ruby/test_helper/style_assertions.rbs +7 -1
- data/sig/ratatui_ruby/test_helper/terminal.rbs +7 -1
- data/sig/ratatui_ruby/test_helper/test_doubles.rbs +7 -1
- data/sig/ratatui_ruby/test_helper.rbs +7 -1
- data/sig/ratatui_ruby/tui/buffer_factories.rbs +7 -1
- data/sig/ratatui_ruby/tui/canvas_factories.rbs +7 -1
- data/sig/ratatui_ruby/tui/core.rbs +7 -1
- data/sig/ratatui_ruby/tui/layout_factories.rbs +7 -1
- data/sig/ratatui_ruby/tui/state_factories.rbs +7 -1
- data/sig/ratatui_ruby/tui/style_factories.rbs +7 -1
- data/sig/ratatui_ruby/tui/text_factories.rbs +7 -1
- data/sig/ratatui_ruby/tui/widget_factories.rbs +7 -1
- data/sig/ratatui_ruby/tui.rbs +7 -1
- data/sig/ratatui_ruby/version.rbs +6 -0
- data/tasks/autodoc/examples.rb +1 -1
- data/tasks/autodoc/member.rb +1 -1
- data/tasks/autodoc/name.rb +1 -1
- data/tasks/bump/cargo_lockfile.rb +1 -1
- data/tasks/bump/changelog.rb +1 -1
- data/tasks/bump/header.rb +1 -1
- data/tasks/bump/history.rb +1 -1
- data/tasks/bump/links.rb +1 -1
- data/tasks/bump/manifest.rb +1 -1
- data/tasks/bump/ruby_gem.rb +1 -1
- data/tasks/bump/sem_ver.rb +1 -1
- data/tasks/bump/unreleased_section.rb +1 -1
- data/tasks/license/headers_md.rb +223 -0
- data/tasks/license/headers_rb.rb +210 -0
- data/tasks/license/license_utils.rb +130 -0
- data/tasks/license/snippets_md.rb +315 -0
- data/tasks/license/snippets_rdoc.rb +150 -0
- data/tasks/license.rake +91 -0
- data/tasks/rdoc_config.rb +1 -1
- data/tasks/resources/build.yml.erb +13 -7
- data/tasks/sourcehut.rake +3 -1
- data/tasks/terminal_preview/app_screenshot.rb +1 -1
- data/tasks/terminal_preview/crash_report.rb +1 -1
- data/tasks/terminal_preview/example_app.rb +1 -1
- data/tasks/terminal_preview/launcher_script.rb +1 -1
- data/tasks/terminal_preview/preview_collection.rb +1 -1
- data/tasks/terminal_preview/preview_timing.rb +1 -1
- data/tasks/terminal_preview/safety_confirmation.rb +1 -1
- data/tasks/terminal_preview/saved_screenshot.rb +1 -1
- data/tasks/terminal_preview/system_appearance.rb +1 -1
- data/tasks/terminal_preview/terminal_window.rb +1 -1
- data/tasks/terminal_preview/window_id.rb +1 -1
- data/tasks/website/index_page.rb +1 -1
- data/tasks/website/version.rb +1 -1
- data/tasks/website/version_menu.rb +1 -1
- data/tasks/website/versioned_documentation.rb +1 -1
- data/tasks/website/website.rb +1 -1
- metadata +15 -3
- data/doc/migration/v0_7_0.md +0 -236
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
3
|
#--
|
|
4
|
-
# SPDX-FileCopyrightText:
|
|
5
|
-
# SPDX-License-Identifier:
|
|
4
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
|
|
5
|
+
# SPDX-License-Identifier: LGPL-3.0-or-later
|
|
6
6
|
#++
|
|
7
7
|
|
|
8
8
|
module RatatuiRuby
|
|
@@ -17,10 +17,18 @@ module RatatuiRuby
|
|
|
17
17
|
#
|
|
18
18
|
# === Examples
|
|
19
19
|
#
|
|
20
|
+
#--
|
|
21
|
+
# SPDX-SnippetBegin
|
|
22
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
23
|
+
# SPDX-License-Identifier: MIT-0
|
|
24
|
+
#++
|
|
20
25
|
# Layout::Constraint.length(5) # Exactly 5 cells
|
|
21
26
|
# Layout::Constraint.percentage(50) # Half the available space
|
|
22
27
|
# Layout::Constraint.min(10) # At least 10 cells, maybe more
|
|
23
28
|
# Layout::Constraint.fill(1) # Fill remaining space (weight 1)
|
|
29
|
+
#--
|
|
30
|
+
# SPDX-SnippetEnd
|
|
31
|
+
#++
|
|
24
32
|
class Constraint < Data.define(:type, :value)
|
|
25
33
|
##
|
|
26
34
|
# :attr_reader: type
|
|
@@ -34,8 +42,16 @@ module RatatuiRuby
|
|
|
34
42
|
|
|
35
43
|
# Requests a fixed size.
|
|
36
44
|
#
|
|
45
|
+
#--
|
|
46
|
+
# SPDX-SnippetBegin
|
|
47
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
48
|
+
# SPDX-License-Identifier: MIT-0
|
|
49
|
+
#++
|
|
37
50
|
# Layout::Constraint.length(10) # 10 characters wide/high
|
|
38
51
|
#
|
|
52
|
+
#--
|
|
53
|
+
# SPDX-SnippetEnd
|
|
54
|
+
#++
|
|
39
55
|
# [v] Number of cells (Integer).
|
|
40
56
|
def self.length(v)
|
|
41
57
|
new(type: :length, value: Integer(v))
|
|
@@ -43,8 +59,16 @@ module RatatuiRuby
|
|
|
43
59
|
|
|
44
60
|
# Requests a percentage of available space.
|
|
45
61
|
#
|
|
62
|
+
#--
|
|
63
|
+
# SPDX-SnippetBegin
|
|
64
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
65
|
+
# SPDX-License-Identifier: MIT-0
|
|
66
|
+
#++
|
|
46
67
|
# Layout::Constraint.percentage(25) # 25% of the area
|
|
47
68
|
#
|
|
69
|
+
#--
|
|
70
|
+
# SPDX-SnippetEnd
|
|
71
|
+
#++
|
|
48
72
|
# [v] Percentage 0-100 (Integer).
|
|
49
73
|
def self.percentage(v)
|
|
50
74
|
new(type: :percentage, value: Integer(v))
|
|
@@ -52,8 +76,16 @@ module RatatuiRuby
|
|
|
52
76
|
|
|
53
77
|
# Enforces a minimum size.
|
|
54
78
|
#
|
|
79
|
+
#--
|
|
80
|
+
# SPDX-SnippetBegin
|
|
81
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
82
|
+
# SPDX-License-Identifier: MIT-0
|
|
83
|
+
#++
|
|
55
84
|
# Layout::Constraint.min(5) # At least 5 cells
|
|
56
85
|
#
|
|
86
|
+
#--
|
|
87
|
+
# SPDX-SnippetEnd
|
|
88
|
+
#++
|
|
57
89
|
# This section will grow if space permits, but never shrink below +v+.
|
|
58
90
|
#
|
|
59
91
|
# [v] Minimum cells (Integer).
|
|
@@ -63,8 +95,16 @@ module RatatuiRuby
|
|
|
63
95
|
|
|
64
96
|
# Enforces a maximum size.
|
|
65
97
|
#
|
|
98
|
+
#--
|
|
99
|
+
# SPDX-SnippetBegin
|
|
100
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
101
|
+
# SPDX-License-Identifier: MIT-0
|
|
102
|
+
#++
|
|
66
103
|
# Layout::Constraint.max(10) # At most 10 cells
|
|
67
104
|
#
|
|
105
|
+
#--
|
|
106
|
+
# SPDX-SnippetEnd
|
|
107
|
+
#++
|
|
68
108
|
# [v] Maximum cells (Integer).
|
|
69
109
|
def self.max(v)
|
|
70
110
|
new(type: :max, value: Integer(v))
|
|
@@ -72,9 +112,17 @@ module RatatuiRuby
|
|
|
72
112
|
|
|
73
113
|
# Fills remaining space proportionally.
|
|
74
114
|
#
|
|
115
|
+
#--
|
|
116
|
+
# SPDX-SnippetBegin
|
|
117
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
118
|
+
# SPDX-License-Identifier: MIT-0
|
|
119
|
+
#++
|
|
75
120
|
# Layout::Constraint.fill(1) # Equal share
|
|
76
121
|
# Layout::Constraint.fill(2) # Double share
|
|
77
122
|
#
|
|
123
|
+
#--
|
|
124
|
+
# SPDX-SnippetEnd
|
|
125
|
+
#++
|
|
78
126
|
# Fill constraints distribute any space left after satisfying strict rules.
|
|
79
127
|
# They behave like flex-grow. A fill(2) takes twice as much space as a fill(1).
|
|
80
128
|
#
|
|
@@ -85,13 +133,156 @@ module RatatuiRuby
|
|
|
85
133
|
|
|
86
134
|
# Requests a specific ratio of the total space.
|
|
87
135
|
#
|
|
136
|
+
#--
|
|
137
|
+
# SPDX-SnippetBegin
|
|
138
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
139
|
+
# SPDX-License-Identifier: MIT-0
|
|
140
|
+
#++
|
|
88
141
|
# Layout::Constraint.ratio(1, 3) # 1/3rd of the area
|
|
89
142
|
#
|
|
143
|
+
#--
|
|
144
|
+
# SPDX-SnippetEnd
|
|
145
|
+
#++
|
|
90
146
|
# [numerator] Top part of fraction (Integer).
|
|
91
147
|
# [denominator] Bottom part of fraction (Integer).
|
|
92
148
|
def self.ratio(numerator, denominator)
|
|
93
149
|
new(type: :ratio, value: [Integer(numerator), Integer(denominator)])
|
|
94
150
|
end
|
|
151
|
+
|
|
152
|
+
# Converts an array of lengths into an array of Length constraints.
|
|
153
|
+
#
|
|
154
|
+
# Complex layouts often use multiple fixed-size sections. Manually creating each constraint
|
|
155
|
+
# clutters the code.
|
|
156
|
+
#
|
|
157
|
+
# This method maps over the input, returning a constraint array in one call.
|
|
158
|
+
#
|
|
159
|
+
# === Example
|
|
160
|
+
#
|
|
161
|
+
#--
|
|
162
|
+
# SPDX-SnippetBegin
|
|
163
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
164
|
+
# SPDX-License-Identifier: MIT-0
|
|
165
|
+
#++
|
|
166
|
+
# Constraint.from_lengths([10, 20, 10])
|
|
167
|
+
# # => [Constraint.length(10), Constraint.length(20), Constraint.length(10)]
|
|
168
|
+
#
|
|
169
|
+
#--
|
|
170
|
+
# SPDX-SnippetEnd
|
|
171
|
+
#++
|
|
172
|
+
# [values] Enumerable of Integers.
|
|
173
|
+
def self.from_lengths(values)
|
|
174
|
+
values.map { |v| length(v) }
|
|
175
|
+
end
|
|
176
|
+
|
|
177
|
+
# Converts an array of percentages into an array of Percentage constraints.
|
|
178
|
+
#
|
|
179
|
+
# Percentage-based layouts distribute space proportionally. This method batches the creation.
|
|
180
|
+
#
|
|
181
|
+
# === Example
|
|
182
|
+
#
|
|
183
|
+
#--
|
|
184
|
+
# SPDX-SnippetBegin
|
|
185
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
186
|
+
# SPDX-License-Identifier: MIT-0
|
|
187
|
+
#++
|
|
188
|
+
# Constraint.from_percentages([25, 50, 25])
|
|
189
|
+
# # => [Constraint.percentage(25), Constraint.percentage(50), Constraint.percentage(25)]
|
|
190
|
+
#
|
|
191
|
+
#--
|
|
192
|
+
# SPDX-SnippetEnd
|
|
193
|
+
#++
|
|
194
|
+
# [values] Enumerable of Integers (0-100).
|
|
195
|
+
def self.from_percentages(values)
|
|
196
|
+
values.map { |v| percentage(v) }
|
|
197
|
+
end
|
|
198
|
+
|
|
199
|
+
# Converts an array of minimums into an array of Min constraints.
|
|
200
|
+
#
|
|
201
|
+
# Minimum constraints ensure sections never shrink below a threshold. Batch them here.
|
|
202
|
+
#
|
|
203
|
+
# === Example
|
|
204
|
+
#
|
|
205
|
+
#--
|
|
206
|
+
# SPDX-SnippetBegin
|
|
207
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
208
|
+
# SPDX-License-Identifier: MIT-0
|
|
209
|
+
#++
|
|
210
|
+
# Constraint.from_mins([5, 10, 5])
|
|
211
|
+
# # => [Constraint.min(5), Constraint.min(10), Constraint.min(5)]
|
|
212
|
+
#
|
|
213
|
+
#--
|
|
214
|
+
# SPDX-SnippetEnd
|
|
215
|
+
#++
|
|
216
|
+
# [values] Enumerable of Integers.
|
|
217
|
+
def self.from_mins(values)
|
|
218
|
+
values.map { |v| min(v) }
|
|
219
|
+
end
|
|
220
|
+
|
|
221
|
+
# Converts an array of maximums into an array of Max constraints.
|
|
222
|
+
#
|
|
223
|
+
# Maximum constraints cap section sizes. Batch them here.
|
|
224
|
+
#
|
|
225
|
+
# === Example
|
|
226
|
+
#
|
|
227
|
+
#--
|
|
228
|
+
# SPDX-SnippetBegin
|
|
229
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
230
|
+
# SPDX-License-Identifier: MIT-0
|
|
231
|
+
#++
|
|
232
|
+
# Constraint.from_maxes([20, 30, 40])
|
|
233
|
+
# # => [Constraint.max(20), Constraint.max(30), Constraint.max(40)]
|
|
234
|
+
#
|
|
235
|
+
#--
|
|
236
|
+
# SPDX-SnippetEnd
|
|
237
|
+
#++
|
|
238
|
+
# [values] Enumerable of Integers.
|
|
239
|
+
def self.from_maxes(values)
|
|
240
|
+
values.map { |v| max(v) }
|
|
241
|
+
end
|
|
242
|
+
|
|
243
|
+
# Converts an array of weights into an array of Fill constraints.
|
|
244
|
+
#
|
|
245
|
+
# Fill constraints distribute remaining space by weight. Batch them here.
|
|
246
|
+
#
|
|
247
|
+
# === Example
|
|
248
|
+
#
|
|
249
|
+
#--
|
|
250
|
+
# SPDX-SnippetBegin
|
|
251
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
252
|
+
# SPDX-License-Identifier: MIT-0
|
|
253
|
+
#++
|
|
254
|
+
# Constraint.from_fills([1, 2, 1])
|
|
255
|
+
# # => [Constraint.fill(1), Constraint.fill(2), Constraint.fill(1)]
|
|
256
|
+
#
|
|
257
|
+
#--
|
|
258
|
+
# SPDX-SnippetEnd
|
|
259
|
+
#++
|
|
260
|
+
# [values] Enumerable of Integers.
|
|
261
|
+
def self.from_fills(values)
|
|
262
|
+
values.map { |v| fill(v) }
|
|
263
|
+
end
|
|
264
|
+
|
|
265
|
+
# Converts an array of ratio pairs into an array of Ratio constraints.
|
|
266
|
+
#
|
|
267
|
+
# Ratio constraints define exact fractions of space. Batch them here.
|
|
268
|
+
#
|
|
269
|
+
# === Example
|
|
270
|
+
#
|
|
271
|
+
#--
|
|
272
|
+
# SPDX-SnippetBegin
|
|
273
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
274
|
+
# SPDX-License-Identifier: MIT-0
|
|
275
|
+
#++
|
|
276
|
+
# Constraint.from_ratios([[1, 4], [2, 4], [1, 4]])
|
|
277
|
+
# # => [Constraint.ratio(1, 4), Constraint.ratio(2, 4), Constraint.ratio(1, 4)]
|
|
278
|
+
#
|
|
279
|
+
#--
|
|
280
|
+
# SPDX-SnippetEnd
|
|
281
|
+
#++
|
|
282
|
+
# [pairs] Enumerable of <tt>[numerator, denominator]</tt> arrays.
|
|
283
|
+
def self.from_ratios(pairs)
|
|
284
|
+
pairs.map { |n, d| ratio(n, d) }
|
|
285
|
+
end
|
|
95
286
|
end
|
|
96
287
|
end
|
|
97
288
|
end
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
3
|
#--
|
|
4
|
-
# SPDX-FileCopyrightText:
|
|
5
|
-
# SPDX-License-Identifier:
|
|
4
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
|
|
5
|
+
# SPDX-License-Identifier: LGPL-3.0-or-later
|
|
6
6
|
#++
|
|
7
7
|
|
|
8
8
|
module RatatuiRuby
|
|
@@ -52,6 +52,35 @@ module RatatuiRuby
|
|
|
52
52
|
# :nodoc:
|
|
53
53
|
FLEX_MODES = %i[legacy start center end space_between space_around space_evenly].freeze
|
|
54
54
|
|
|
55
|
+
##
|
|
56
|
+
# Direction: split vertically (top to bottom).
|
|
57
|
+
DIRECTION_VERTICAL = :vertical
|
|
58
|
+
##
|
|
59
|
+
# Direction: split horizontally (left to right).
|
|
60
|
+
DIRECTION_HORIZONTAL = :horizontal
|
|
61
|
+
|
|
62
|
+
##
|
|
63
|
+
# Flex: use legacy sizing (default).
|
|
64
|
+
FLEX_LEGACY = :legacy
|
|
65
|
+
##
|
|
66
|
+
# Flex: align to start.
|
|
67
|
+
FLEX_START = :start
|
|
68
|
+
##
|
|
69
|
+
# Flex: center alignment.
|
|
70
|
+
FLEX_CENTER = :center
|
|
71
|
+
##
|
|
72
|
+
# Flex: align to end.
|
|
73
|
+
FLEX_END = :end
|
|
74
|
+
##
|
|
75
|
+
# Flex: space between elements.
|
|
76
|
+
FLEX_SPACE_BETWEEN = :space_between
|
|
77
|
+
##
|
|
78
|
+
# Flex: space around elements.
|
|
79
|
+
FLEX_SPACE_AROUND = :space_around
|
|
80
|
+
##
|
|
81
|
+
# Flex: space evenly between elements.
|
|
82
|
+
FLEX_SPACE_EVENLY = :space_evenly
|
|
83
|
+
|
|
55
84
|
# Creates a new Layout.
|
|
56
85
|
#
|
|
57
86
|
# [direction]
|
|
@@ -71,6 +100,11 @@ module RatatuiRuby
|
|
|
71
100
|
# This is a pure calculation helper for hit testing. It computes where
|
|
72
101
|
# widgets *would* be placed without actually rendering them.
|
|
73
102
|
#
|
|
103
|
+
#--
|
|
104
|
+
# SPDX-SnippetBegin
|
|
105
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
106
|
+
# SPDX-License-Identifier: MIT-0
|
|
107
|
+
#++
|
|
74
108
|
# rects = Layout::Layout.split(
|
|
75
109
|
# area,
|
|
76
110
|
# direction: :horizontal,
|
|
@@ -78,6 +112,9 @@ module RatatuiRuby
|
|
|
78
112
|
# )
|
|
79
113
|
# left, right = rects
|
|
80
114
|
#
|
|
115
|
+
#--
|
|
116
|
+
# SPDX-SnippetEnd
|
|
117
|
+
#++
|
|
81
118
|
# [area]
|
|
82
119
|
# The area to split. Can be a <tt>Rect</tt> or a <tt>Hash</tt> containing <tt>:x</tt>, <tt>:y</tt>, <tt>:width</tt>, and <tt>:height</tt>.
|
|
83
120
|
# [direction]
|
|
@@ -85,8 +122,16 @@ module RatatuiRuby
|
|
|
85
122
|
# [constraints]
|
|
86
123
|
# Array of <tt>Constraint</tt> objects defining section sizes.
|
|
87
124
|
# [flex]
|
|
125
|
+
#--
|
|
126
|
+
# SPDX-SnippetBegin
|
|
127
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
128
|
+
# SPDX-License-Identifier: MIT-0
|
|
129
|
+
#++
|
|
88
130
|
# Flex mode for spacing (default: <tt>:legacy</tt>).
|
|
89
131
|
#
|
|
132
|
+
#--
|
|
133
|
+
# SPDX-SnippetEnd
|
|
134
|
+
#++
|
|
90
135
|
# Returns an Array of <tt>Rect</tt> objects.
|
|
91
136
|
def self.split(area, direction: :vertical, constraints:, flex: :legacy)
|
|
92
137
|
# Duck-typing: If it lacks geometry methods but can be a Hash, convert it.
|