ratatui_ruby 0.8.0 → 0.9.0
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 +53 -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 +15 -175
- 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 +3 -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/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.rb +26 -2
- data/lib/ratatui_ruby/frame.rb +74 -2
- data/lib/ratatui_ruby/layout/constraint.rb +58 -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/table_state.rb +10 -2
- data/lib/ratatui_ruby/terminal_lifecycle.rb +18 -3
- data/lib/ratatui_ruby/test_helper/event_injection.rb +34 -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 +90 -2
- 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 +6 -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 +13 -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: MIT-0
|
|
6
6
|
#++
|
|
7
7
|
|
|
8
8
|
$LOAD_PATH.unshift File.expand_path("../../lib", __dir__)
|
|
@@ -73,7 +73,7 @@ class WidgetTextWidth
|
|
|
73
73
|
block: @tui.block(
|
|
74
74
|
title: "Text Width Calculator",
|
|
75
75
|
borders: [:all],
|
|
76
|
-
|
|
76
|
+
border_style: { fg: "cyan" }
|
|
77
77
|
),
|
|
78
78
|
alignment: :left
|
|
79
79
|
)
|
|
@@ -88,7 +88,7 @@ class WidgetTextWidth
|
|
|
88
88
|
|
|
89
89
|
widget = @tui.paragraph(
|
|
90
90
|
text:,
|
|
91
|
-
block: @tui.block(borders: [:top],
|
|
91
|
+
block: @tui.block(borders: [:top], border_style: { fg: "gray" }),
|
|
92
92
|
alignment: :center
|
|
93
93
|
)
|
|
94
94
|
|
data/ext/ratatui_ruby/Cargo.lock
CHANGED
data/ext/ratatui_ruby/Cargo.toml
CHANGED
data/ext/ratatui_ruby/extconf.rb
CHANGED
|
@@ -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
|
require "mkmf"
|
|
@@ -53,7 +53,7 @@ pub fn render_node(frame: &mut Frame, area: Rect, node: Value) -> Result<(), Err
|
|
|
53
53
|
"RatatuiRuby::Widgets::Canvas" => widgets::canvas::render(frame, area, node)?,
|
|
54
54
|
"RatatuiRuby::Widgets::Calendar" => widgets::calendar::render(frame, area, node)?,
|
|
55
55
|
"RatatuiRuby::Widgets::Sparkline" => widgets::sparkline::render(frame, area, node)?,
|
|
56
|
-
"RatatuiRuby::Widgets::Chart"
|
|
56
|
+
"RatatuiRuby::Widgets::Chart" => {
|
|
57
57
|
widgets::chart::render(frame, area, node)?;
|
|
58
58
|
}
|
|
59
59
|
"RatatuiRuby::Widgets::RatatuiLogo" => widgets::ratatui_logo::render(frame, area, node),
|
|
@@ -398,14 +398,6 @@ fn parse_borders<'a>(
|
|
|
398
398
|
if let Ok(v) = block_val.funcall::<&str, _, Value>("border_style", ()) {
|
|
399
399
|
if !v.is_nil() {
|
|
400
400
|
block = block.border_style(parse_style(v)?);
|
|
401
|
-
} else if let Ok(color_val) = block_val.funcall::<&str, _, Value>("border_color", ()) {
|
|
402
|
-
if !color_val.is_nil() {
|
|
403
|
-
if let Ok(s) = color_val.funcall::<&str, _, String>("to_s", ()) {
|
|
404
|
-
if let Some(c) = parse_color(&s) {
|
|
405
|
-
block = block.border_style(Style::default().fg(c));
|
|
406
|
-
}
|
|
407
|
-
}
|
|
408
|
-
}
|
|
409
401
|
}
|
|
410
402
|
}
|
|
411
403
|
|
|
@@ -8,7 +8,6 @@ use magnus::{prelude::*, Error, Symbol, Value};
|
|
|
8
8
|
use ratatui::{
|
|
9
9
|
layout::Rect,
|
|
10
10
|
symbols,
|
|
11
|
-
text::Span,
|
|
12
11
|
widgets::{Axis, Chart, Dataset, GraphType, LegendPosition},
|
|
13
12
|
Frame,
|
|
14
13
|
};
|
|
@@ -17,12 +16,6 @@ use ratatui::{
|
|
|
17
16
|
pub fn render(frame: &mut Frame, area: Rect, node: Value) -> Result<(), Error> {
|
|
18
17
|
let bump = Bump::new();
|
|
19
18
|
let ruby = magnus::Ruby::get().unwrap();
|
|
20
|
-
// SAFETY: Immediate conversion to owned string avoids GC-unsafe borrowed reference.
|
|
21
|
-
let class_name = unsafe { node.class().name() }.into_owned();
|
|
22
|
-
|
|
23
|
-
if class_name == "RatatuiRuby::LineChart" {
|
|
24
|
-
return render_line_chart(frame, area, node);
|
|
25
|
-
}
|
|
26
19
|
|
|
27
20
|
let datasets_val: magnus::RArray = node.funcall("datasets", ())?;
|
|
28
21
|
let x_axis_val: Value = node.funcall("x_axis", ())?;
|
|
@@ -194,117 +187,6 @@ fn parse_axis(axis_val: Value) -> Result<Axis<'static>, Error> {
|
|
|
194
187
|
Ok(axis)
|
|
195
188
|
}
|
|
196
189
|
|
|
197
|
-
fn render_line_chart(frame: &mut Frame, area: Rect, node: Value) -> Result<(), Error> {
|
|
198
|
-
let bump = Bump::new();
|
|
199
|
-
let ruby = magnus::Ruby::get().unwrap();
|
|
200
|
-
let datasets_val: magnus::RArray = node.funcall("datasets", ())?;
|
|
201
|
-
let x_labels_val: magnus::RArray = node.funcall("x_labels", ())?;
|
|
202
|
-
let y_labels_val: magnus::RArray = node.funcall("y_labels", ())?;
|
|
203
|
-
let y_bounds_val: magnus::RArray = node.funcall("y_bounds", ())?;
|
|
204
|
-
let block_val: Value = node.funcall("block", ())?;
|
|
205
|
-
|
|
206
|
-
let mut datasets = Vec::new();
|
|
207
|
-
let mut data_storage: Vec<Vec<(f64, f64)>> = Vec::new();
|
|
208
|
-
|
|
209
|
-
for i in 0..datasets_val.len() {
|
|
210
|
-
let index = isize::try_from(i)
|
|
211
|
-
.map_err(|e| Error::new(ruby.exception_range_error(), e.to_string()))?;
|
|
212
|
-
let ds_val: Value = datasets_val.entry(index)?;
|
|
213
|
-
let data_array: magnus::RArray = ds_val.funcall("data", ())?;
|
|
214
|
-
|
|
215
|
-
let mut points = Vec::new();
|
|
216
|
-
for j in 0..data_array.len() {
|
|
217
|
-
let index = isize::try_from(j)
|
|
218
|
-
.map_err(|e| Error::new(ruby.exception_range_error(), e.to_string()))?;
|
|
219
|
-
let point_array_val: Value = data_array.entry(index)?;
|
|
220
|
-
let point_array = magnus::RArray::from_value(point_array_val).ok_or_else(|| {
|
|
221
|
-
Error::new(ruby.exception_type_error(), "expected array for point")
|
|
222
|
-
})?;
|
|
223
|
-
let x: f64 = point_array.entry(0)?;
|
|
224
|
-
let y: f64 = point_array.entry(1)?;
|
|
225
|
-
points.push((x, y));
|
|
226
|
-
}
|
|
227
|
-
data_storage.push(points);
|
|
228
|
-
}
|
|
229
|
-
|
|
230
|
-
for (i, points) in data_storage.iter().enumerate() {
|
|
231
|
-
let index = isize::try_from(i)
|
|
232
|
-
.map_err(|e| Error::new(ruby.exception_range_error(), e.to_string()))?;
|
|
233
|
-
let ds_val: Value = datasets_val.entry(index)?;
|
|
234
|
-
let name: String = ds_val.funcall("name", ())?;
|
|
235
|
-
|
|
236
|
-
let mut ds_style = ratatui::style::Style::default();
|
|
237
|
-
let style_val: Value = ds_val.funcall("style", ())?;
|
|
238
|
-
if !style_val.is_nil() {
|
|
239
|
-
ds_style = parse_style(style_val)?;
|
|
240
|
-
}
|
|
241
|
-
|
|
242
|
-
let ds = Dataset::default()
|
|
243
|
-
.name(name)
|
|
244
|
-
.marker(symbols::Marker::Braille)
|
|
245
|
-
.style(ds_style)
|
|
246
|
-
.data(points);
|
|
247
|
-
datasets.push(ds);
|
|
248
|
-
}
|
|
249
|
-
|
|
250
|
-
let mut x_labels = Vec::new();
|
|
251
|
-
for i in 0..x_labels_val.len() {
|
|
252
|
-
let index = isize::try_from(i)
|
|
253
|
-
.map_err(|e| Error::new(ruby.exception_range_error(), e.to_string()))?;
|
|
254
|
-
let label: String = x_labels_val.entry(index)?;
|
|
255
|
-
x_labels.push(Span::from(label));
|
|
256
|
-
}
|
|
257
|
-
|
|
258
|
-
let mut y_labels = Vec::new();
|
|
259
|
-
for i in 0..y_labels_val.len() {
|
|
260
|
-
let index = isize::try_from(i)
|
|
261
|
-
.map_err(|e| Error::new(ruby.exception_range_error(), e.to_string()))?;
|
|
262
|
-
let label: String = y_labels_val.entry(index)?;
|
|
263
|
-
y_labels.push(Span::from(label));
|
|
264
|
-
}
|
|
265
|
-
// Ratatui 0.29+ requires labels to be present for the axis line to render
|
|
266
|
-
if y_labels.is_empty() {
|
|
267
|
-
y_labels.push(Span::from(""));
|
|
268
|
-
y_labels.push(Span::from(""));
|
|
269
|
-
}
|
|
270
|
-
|
|
271
|
-
let y_bounds: [f64; 2] = [y_bounds_val.entry(0)?, y_bounds_val.entry(1)?];
|
|
272
|
-
|
|
273
|
-
let mut min_x = 0.0;
|
|
274
|
-
let mut max_x = 0.0;
|
|
275
|
-
let mut first = true;
|
|
276
|
-
for ds_data in &data_storage {
|
|
277
|
-
for (x, _) in ds_data {
|
|
278
|
-
if first {
|
|
279
|
-
min_x = *x;
|
|
280
|
-
max_x = *x;
|
|
281
|
-
first = false;
|
|
282
|
-
} else {
|
|
283
|
-
if *x < min_x {
|
|
284
|
-
min_x = *x;
|
|
285
|
-
}
|
|
286
|
-
if *x > max_x {
|
|
287
|
-
max_x = *x;
|
|
288
|
-
}
|
|
289
|
-
}
|
|
290
|
-
}
|
|
291
|
-
}
|
|
292
|
-
if (min_x - max_x).abs() < f64::EPSILON {
|
|
293
|
-
max_x = min_x + 1.0;
|
|
294
|
-
}
|
|
295
|
-
|
|
296
|
-
let x_axis = Axis::default().labels(x_labels).bounds([min_x, max_x]);
|
|
297
|
-
let y_axis = Axis::default().labels(y_labels).bounds(y_bounds);
|
|
298
|
-
|
|
299
|
-
let mut chart = Chart::new(datasets).x_axis(x_axis).y_axis(y_axis);
|
|
300
|
-
if !block_val.is_nil() {
|
|
301
|
-
chart = chart.block(parse_block(block_val, &bump)?);
|
|
302
|
-
}
|
|
303
|
-
|
|
304
|
-
frame.render_widget(chart, area);
|
|
305
|
-
Ok(())
|
|
306
|
-
}
|
|
307
|
-
|
|
308
190
|
#[cfg(test)]
|
|
309
191
|
mod tests {
|
|
310
192
|
use super::*;
|
|
@@ -78,6 +78,35 @@ impl RubyListState {
|
|
|
78
78
|
self.inner.borrow_mut().scroll_up_by(amount);
|
|
79
79
|
}
|
|
80
80
|
|
|
81
|
+
/// Selects the next item or the first one if no item is selected.
|
|
82
|
+
///
|
|
83
|
+
/// Note: until the list is rendered, the number of items is not known, so the index
|
|
84
|
+
/// is set to 0 and will be corrected when the list is rendered.
|
|
85
|
+
pub fn select_next(&self) {
|
|
86
|
+
self.inner.borrow_mut().select_next();
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
/// Selects the previous item or the last one if no item is selected.
|
|
90
|
+
///
|
|
91
|
+
/// Note: until the list is rendered, the number of items is not known, so the index
|
|
92
|
+
/// is set to `usize::MAX` and will be corrected when the list is rendered.
|
|
93
|
+
pub fn select_previous(&self) {
|
|
94
|
+
self.inner.borrow_mut().select_previous();
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
/// Selects the first item.
|
|
98
|
+
pub fn select_first(&self) {
|
|
99
|
+
self.inner.borrow_mut().select_first();
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
/// Selects the last item.
|
|
103
|
+
///
|
|
104
|
+
/// Note: until the list is rendered, the number of items is not known, so the index
|
|
105
|
+
/// is set to `usize::MAX` and will be corrected when the list is rendered.
|
|
106
|
+
pub fn select_last(&self) {
|
|
107
|
+
self.inner.borrow_mut().select_last();
|
|
108
|
+
}
|
|
109
|
+
|
|
81
110
|
/// Borrows the inner `ListState` mutably for rendering.
|
|
82
111
|
///
|
|
83
112
|
/// # Safety
|
|
@@ -98,6 +127,13 @@ pub fn register(ruby: &Ruby, module: magnus::RModule) -> Result<(), Error> {
|
|
|
98
127
|
class.define_method("offset", method!(RubyListState::offset, 0))?;
|
|
99
128
|
class.define_method("scroll_down_by", method!(RubyListState::scroll_down_by, 1))?;
|
|
100
129
|
class.define_method("scroll_up_by", method!(RubyListState::scroll_up_by, 1))?;
|
|
130
|
+
class.define_method("select_next", method!(RubyListState::select_next, 0))?;
|
|
131
|
+
class.define_method(
|
|
132
|
+
"select_previous",
|
|
133
|
+
method!(RubyListState::select_previous, 0),
|
|
134
|
+
)?;
|
|
135
|
+
class.define_method("select_first", method!(RubyListState::select_first, 0))?;
|
|
136
|
+
class.define_method("select_last", method!(RubyListState::select_last, 0))?;
|
|
101
137
|
Ok(())
|
|
102
138
|
}
|
|
103
139
|
|
|
@@ -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
|
|
@@ -18,11 +18,19 @@ module RatatuiRuby
|
|
|
18
18
|
#
|
|
19
19
|
# === Examples
|
|
20
20
|
#
|
|
21
|
+
#--
|
|
22
|
+
# SPDX-SnippetBegin
|
|
23
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
24
|
+
# SPDX-License-Identifier: MIT-0
|
|
25
|
+
#++
|
|
21
26
|
# cell = RatatuiRuby.get_cell_at(0, 0)
|
|
22
27
|
# cell.char # => "H"
|
|
23
28
|
# cell.fg # => :red
|
|
24
29
|
# cell.bold? # => true
|
|
25
30
|
#
|
|
31
|
+
#--
|
|
32
|
+
# SPDX-SnippetEnd
|
|
33
|
+
#++
|
|
26
34
|
class Cell
|
|
27
35
|
# The character displayed in the cell.
|
|
28
36
|
#
|
|
@@ -45,8 +53,16 @@ module RatatuiRuby
|
|
|
45
53
|
#
|
|
46
54
|
# === Example
|
|
47
55
|
#
|
|
56
|
+
#--
|
|
57
|
+
# SPDX-SnippetBegin
|
|
58
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
59
|
+
# SPDX-License-Identifier: MIT-0
|
|
60
|
+
#++
|
|
48
61
|
# Buffer::Cell.empty # => #<RatatuiRuby::Buffer::Cell char=" ">
|
|
49
62
|
#
|
|
63
|
+
#--
|
|
64
|
+
# SPDX-SnippetEnd
|
|
65
|
+
#++
|
|
50
66
|
def self.empty
|
|
51
67
|
new(symbol: " ", fg: nil, bg: nil, modifiers: [])
|
|
52
68
|
end
|
|
@@ -55,8 +71,16 @@ module RatatuiRuby
|
|
|
55
71
|
#
|
|
56
72
|
# === Example
|
|
57
73
|
#
|
|
74
|
+
#--
|
|
75
|
+
# SPDX-SnippetBegin
|
|
76
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
77
|
+
# SPDX-License-Identifier: MIT-0
|
|
78
|
+
#++
|
|
58
79
|
# Buffer::Cell.default # => #<RatatuiRuby::Buffer::Cell char=" ">
|
|
59
80
|
#
|
|
81
|
+
#--
|
|
82
|
+
# SPDX-SnippetEnd
|
|
83
|
+
#++
|
|
60
84
|
def self.default
|
|
61
85
|
empty
|
|
62
86
|
end
|
|
@@ -67,8 +91,16 @@ module RatatuiRuby
|
|
|
67
91
|
#
|
|
68
92
|
# === Example
|
|
69
93
|
#
|
|
94
|
+
#--
|
|
95
|
+
# SPDX-SnippetBegin
|
|
96
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
97
|
+
# SPDX-License-Identifier: MIT-0
|
|
98
|
+
#++
|
|
70
99
|
# Buffer::Cell.symbol("X") # => #<RatatuiRuby::Buffer::Cell symbol="X">
|
|
71
100
|
#
|
|
101
|
+
#--
|
|
102
|
+
# SPDX-SnippetEnd
|
|
103
|
+
#++
|
|
72
104
|
def self.symbol(symbol)
|
|
73
105
|
new(symbol:, fg: nil, bg: nil, modifiers: [])
|
|
74
106
|
end
|
data/lib/ratatui_ruby/buffer.rb
CHANGED
|
@@ -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
|
data/lib/ratatui_ruby/cell.rb
CHANGED
|
@@ -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,11 +17,19 @@ module RatatuiRuby
|
|
|
17
17
|
#
|
|
18
18
|
# === Examples
|
|
19
19
|
#
|
|
20
|
+
#--
|
|
21
|
+
# SPDX-SnippetBegin
|
|
22
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
23
|
+
# SPDX-License-Identifier: MIT-0
|
|
24
|
+
#++
|
|
20
25
|
# cell = RatatuiRuby.get_cell_at(0, 0)
|
|
21
26
|
# cell.char # => "H"
|
|
22
27
|
# cell.fg # => :red
|
|
23
28
|
# cell.bold? # => true
|
|
24
29
|
#
|
|
30
|
+
#--
|
|
31
|
+
# SPDX-SnippetEnd
|
|
32
|
+
#++
|
|
25
33
|
class Cell
|
|
26
34
|
# The character displayed in the cell.
|
|
27
35
|
#
|
|
@@ -44,8 +52,16 @@ module RatatuiRuby
|
|
|
44
52
|
#
|
|
45
53
|
# === Example
|
|
46
54
|
#
|
|
55
|
+
#--
|
|
56
|
+
# SPDX-SnippetBegin
|
|
57
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
58
|
+
# SPDX-License-Identifier: MIT-0
|
|
59
|
+
#++
|
|
47
60
|
# Cell.empty # => #<RatatuiRuby::Cell char=" ">
|
|
48
61
|
#
|
|
62
|
+
#--
|
|
63
|
+
# SPDX-SnippetEnd
|
|
64
|
+
#++
|
|
49
65
|
def self.empty
|
|
50
66
|
new(symbol: " ", fg: nil, bg: nil, modifiers: [])
|
|
51
67
|
end
|
|
@@ -54,8 +70,16 @@ module RatatuiRuby
|
|
|
54
70
|
#
|
|
55
71
|
# === Example
|
|
56
72
|
#
|
|
73
|
+
#--
|
|
74
|
+
# SPDX-SnippetBegin
|
|
75
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
76
|
+
# SPDX-License-Identifier: MIT-0
|
|
77
|
+
#++
|
|
57
78
|
# Cell.default # => #<RatatuiRuby::Cell char=" ">
|
|
58
79
|
#
|
|
80
|
+
#--
|
|
81
|
+
# SPDX-SnippetEnd
|
|
82
|
+
#++
|
|
59
83
|
def self.default
|
|
60
84
|
empty
|
|
61
85
|
end
|
|
@@ -66,8 +90,16 @@ module RatatuiRuby
|
|
|
66
90
|
#
|
|
67
91
|
# === Example
|
|
68
92
|
#
|
|
93
|
+
#--
|
|
94
|
+
# SPDX-SnippetBegin
|
|
95
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
96
|
+
# SPDX-License-Identifier: MIT-0
|
|
97
|
+
#++
|
|
69
98
|
# Cell.symbol("X") # => #<RatatuiRuby::Cell symbol="X">
|
|
70
99
|
#
|
|
100
|
+
#--
|
|
101
|
+
# SPDX-SnippetEnd
|
|
102
|
+
#++
|
|
71
103
|
def self.symbol(symbol)
|
|
72
104
|
new(symbol:, fg: nil, bg: nil, modifiers: [])
|
|
73
105
|
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
|
|
@@ -19,24 +19,48 @@ module RatatuiRuby
|
|
|
19
19
|
#
|
|
20
20
|
# === Example
|
|
21
21
|
#
|
|
22
|
+
#--
|
|
23
|
+
# SPDX-SnippetBegin
|
|
24
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
25
|
+
# SPDX-License-Identifier: MIT-0
|
|
26
|
+
#++
|
|
22
27
|
# if event.focus_gained?
|
|
23
28
|
# puts "Focus gained"
|
|
24
29
|
# end
|
|
30
|
+
#--
|
|
31
|
+
# SPDX-SnippetEnd
|
|
32
|
+
#++
|
|
25
33
|
class FocusGained < Event
|
|
26
34
|
# Returns true for FocusGained events.
|
|
27
35
|
#
|
|
36
|
+
#--
|
|
37
|
+
# SPDX-SnippetBegin
|
|
38
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
39
|
+
# SPDX-License-Identifier: MIT-0
|
|
40
|
+
#++
|
|
28
41
|
# event.focus_gained? # => true
|
|
29
42
|
# event.key? # => false
|
|
43
|
+
#--
|
|
44
|
+
# SPDX-SnippetEnd
|
|
45
|
+
#++
|
|
30
46
|
def focus_gained?
|
|
31
47
|
true
|
|
32
48
|
end
|
|
33
49
|
|
|
34
50
|
# Deconstructs the event for pattern matching.
|
|
35
51
|
#
|
|
52
|
+
#--
|
|
53
|
+
# SPDX-SnippetBegin
|
|
54
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
55
|
+
# SPDX-License-Identifier: MIT-0
|
|
56
|
+
#++
|
|
36
57
|
# case event
|
|
37
58
|
# in type: :focus_gained
|
|
38
59
|
# puts "Application gained focus"
|
|
39
60
|
# end
|
|
61
|
+
#--
|
|
62
|
+
# SPDX-SnippetEnd
|
|
63
|
+
#++
|
|
40
64
|
def deconstruct_keys(keys)
|
|
41
65
|
{ type: :focus_gained }
|
|
42
66
|
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
|
|
@@ -20,24 +20,48 @@ module RatatuiRuby
|
|
|
20
20
|
#
|
|
21
21
|
# === Example
|
|
22
22
|
#
|
|
23
|
+
#--
|
|
24
|
+
# SPDX-SnippetBegin
|
|
25
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
26
|
+
# SPDX-License-Identifier: MIT-0
|
|
27
|
+
#++
|
|
23
28
|
# if event.focus_lost?
|
|
24
29
|
# puts "Focus lost"
|
|
25
30
|
# end
|
|
31
|
+
#--
|
|
32
|
+
# SPDX-SnippetEnd
|
|
33
|
+
#++
|
|
26
34
|
class FocusLost < Event
|
|
27
35
|
# Returns true for FocusLost events.
|
|
28
36
|
#
|
|
37
|
+
#--
|
|
38
|
+
# SPDX-SnippetBegin
|
|
39
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
40
|
+
# SPDX-License-Identifier: MIT-0
|
|
41
|
+
#++
|
|
29
42
|
# event.focus_lost? # => true
|
|
30
43
|
# event.key? # => false
|
|
44
|
+
#--
|
|
45
|
+
# SPDX-SnippetEnd
|
|
46
|
+
#++
|
|
31
47
|
def focus_lost?
|
|
32
48
|
true
|
|
33
49
|
end
|
|
34
50
|
|
|
35
51
|
# Deconstructs the event for pattern matching.
|
|
36
52
|
#
|
|
53
|
+
#--
|
|
54
|
+
# SPDX-SnippetBegin
|
|
55
|
+
# SPDX-FileCopyrightText: 2025 Kerrick Long
|
|
56
|
+
# SPDX-License-Identifier: MIT-0
|
|
57
|
+
#++
|
|
37
58
|
# case event
|
|
38
59
|
# in type: :focus_lost
|
|
39
60
|
# puts "Application lost focus"
|
|
40
61
|
# end
|
|
62
|
+
#--
|
|
63
|
+
# SPDX-SnippetEnd
|
|
64
|
+
#++
|
|
41
65
|
def deconstruct_keys(keys)
|
|
42
66
|
{ type: :focus_lost }
|
|
43
67
|
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
|
|
@@ -12,9 +12,17 @@ module RatatuiRuby
|
|
|
12
12
|
module Character
|
|
13
13
|
# Returns true if the key represents a single printable character.
|
|
14
14
|
#
|
|
15
|
+
#--
|
|
16
|
+
# SPDX-SnippetBegin
|
|
17
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
18
|
+
# SPDX-License-Identifier: MIT-0
|
|
19
|
+
#++
|
|
15
20
|
# RatatuiRuby::Event::Key.new(code: "a").text? # => true
|
|
16
21
|
# RatatuiRuby::Event::Key.new(code: "enter").text? # => false
|
|
17
22
|
# RatatuiRuby::Event::Key.new(code: "space").text? # => false ("space" is not 1 char, " " is)
|
|
23
|
+
#--
|
|
24
|
+
# SPDX-SnippetEnd
|
|
25
|
+
#++
|
|
18
26
|
def text?
|
|
19
27
|
@code.length == 1
|
|
20
28
|
end
|
|
@@ -24,10 +32,18 @@ module RatatuiRuby
|
|
|
24
32
|
# [Printable Characters]
|
|
25
33
|
# Returns the character itself (e.g., <tt>"a"</tt>, <tt>"1"</tt>, <tt>" "</tt>).
|
|
26
34
|
# [Special Keys]
|
|
35
|
+
#--
|
|
36
|
+
# SPDX-SnippetBegin
|
|
37
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
38
|
+
# SPDX-License-Identifier: MIT-0
|
|
39
|
+
#++
|
|
27
40
|
# Returns <tt>nil</tt> (e.g., <tt>"enter"</tt>, <tt>"up"</tt>, <tt>"f1"</tt>).
|
|
28
41
|
#
|
|
29
42
|
# RatatuiRuby::Event::Key.new(code: "a").char # => "a"
|
|
30
43
|
# RatatuiRuby::Event::Key.new(code: "enter").char # => nil
|
|
44
|
+
#--
|
|
45
|
+
# SPDX-SnippetEnd
|
|
46
|
+
#++
|
|
31
47
|
def char
|
|
32
48
|
text? ? @code : nil
|
|
33
49
|
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
|
|
@@ -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
|
|
@@ -66,9 +66,17 @@ module RatatuiRuby
|
|
|
66
66
|
#
|
|
67
67
|
# === Example
|
|
68
68
|
#
|
|
69
|
+
#--
|
|
70
|
+
# SPDX-SnippetBegin
|
|
71
|
+
# SPDX-FileCopyrightText: 2026 Kerrick Long
|
|
72
|
+
# SPDX-License-Identifier: MIT-0
|
|
73
|
+
#++
|
|
69
74
|
# if event.modifier?
|
|
70
75
|
# # Handle solo modifier key press
|
|
71
76
|
# end
|
|
77
|
+
#--
|
|
78
|
+
# SPDX-SnippetEnd
|
|
79
|
+
#++
|
|
72
80
|
def modifier?
|
|
73
81
|
@kind == :modifier
|
|
74
82
|
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
|
|
@@ -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
|