ratatui_ruby 0.1.0 → 0.3.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.
Files changed (127) hide show
  1. checksums.yaml +4 -4
  2. data/.builds/ruby-3.2.yml +52 -0
  3. data/.builds/ruby-3.3.yml +52 -0
  4. data/.builds/ruby-3.4.yml +52 -0
  5. data/.builds/ruby-4.0.0.yml +53 -0
  6. data/.pre-commit-config.yaml +9 -2
  7. data/AGENTS.md +53 -5
  8. data/CHANGELOG.md +51 -1
  9. data/README.md +38 -18
  10. data/REUSE.toml +5 -0
  11. data/Rakefile +3 -100
  12. data/{docs → doc}/contributors/index.md +2 -1
  13. data/doc/custom.css +8 -0
  14. data/doc/images/examples-calendar_demo.rb.png +0 -0
  15. data/doc/images/examples-chart_demo.rb.png +0 -0
  16. data/doc/images/examples-custom_widget.rb.png +0 -0
  17. data/doc/images/examples-list_styles.rb.png +0 -0
  18. data/doc/images/examples-popup_demo.rb.gif +0 -0
  19. data/doc/images/examples-quickstart_lifecycle.rb.png +0 -0
  20. data/doc/images/examples-scroll_text.rb.png +0 -0
  21. data/doc/images/examples-stock_ticker.rb.png +0 -0
  22. data/doc/images/examples-table_select.rb.png +0 -0
  23. data/{docs → doc}/index.md +1 -1
  24. data/{docs → doc}/quickstart.md +81 -11
  25. data/examples/analytics.rb +2 -1
  26. data/examples/calendar_demo.rb +55 -0
  27. data/examples/chart_demo.rb +84 -0
  28. data/examples/custom_widget.rb +43 -0
  29. data/examples/list_styles.rb +66 -0
  30. data/examples/login_form.rb +2 -1
  31. data/examples/popup_demo.rb +105 -0
  32. data/examples/quickstart_dsl.rb +30 -0
  33. data/examples/quickstart_lifecycle.rb +40 -0
  34. data/examples/readme_usage.rb +21 -0
  35. data/examples/scroll_text.rb +74 -0
  36. data/examples/stock_ticker.rb +13 -5
  37. data/examples/system_monitor.rb +2 -1
  38. data/examples/table_select.rb +70 -0
  39. data/examples/test_calendar_demo.rb +66 -0
  40. data/examples/test_list_styles.rb +61 -0
  41. data/examples/test_popup_demo.rb +62 -0
  42. data/examples/test_scroll_text.rb +130 -0
  43. data/examples/test_table_select.rb +37 -0
  44. data/ext/ratatui_ruby/.cargo/config.toml +5 -0
  45. data/ext/ratatui_ruby/Cargo.lock +260 -50
  46. data/ext/ratatui_ruby/Cargo.toml +5 -4
  47. data/ext/ratatui_ruby/extconf.rb +1 -1
  48. data/ext/ratatui_ruby/src/buffer.rs +54 -0
  49. data/ext/ratatui_ruby/src/events.rs +115 -107
  50. data/ext/ratatui_ruby/src/lib.rs +15 -6
  51. data/ext/ratatui_ruby/src/rendering.rs +18 -1
  52. data/ext/ratatui_ruby/src/style.rs +2 -1
  53. data/ext/ratatui_ruby/src/terminal.rs +27 -24
  54. data/ext/ratatui_ruby/src/widgets/calendar.rs +82 -0
  55. data/ext/ratatui_ruby/src/widgets/canvas.rs +1 -2
  56. data/ext/ratatui_ruby/src/widgets/center.rs +0 -2
  57. data/ext/ratatui_ruby/src/widgets/chart.rs +260 -0
  58. data/ext/ratatui_ruby/src/widgets/clear.rs +37 -0
  59. data/ext/ratatui_ruby/src/widgets/cursor.rs +1 -1
  60. data/ext/ratatui_ruby/src/widgets/layout.rs +2 -1
  61. data/ext/ratatui_ruby/src/widgets/list.rs +44 -5
  62. data/ext/ratatui_ruby/src/widgets/mod.rs +3 -1
  63. data/ext/ratatui_ruby/src/widgets/overlay.rs +2 -1
  64. data/ext/ratatui_ruby/src/widgets/paragraph.rs +10 -0
  65. data/ext/ratatui_ruby/src/widgets/table.rs +25 -6
  66. data/ext/ratatui_ruby/src/widgets/tabs.rs +2 -1
  67. data/lib/ratatui_ruby/dsl.rb +64 -0
  68. data/lib/ratatui_ruby/schema/calendar.rb +26 -0
  69. data/lib/ratatui_ruby/schema/chart.rb +81 -0
  70. data/lib/ratatui_ruby/schema/clear.rb +83 -0
  71. data/lib/ratatui_ruby/schema/list.rb +8 -2
  72. data/lib/ratatui_ruby/schema/paragraph.rb +7 -4
  73. data/lib/ratatui_ruby/schema/rect.rb +24 -0
  74. data/lib/ratatui_ruby/schema/table.rb +8 -2
  75. data/lib/ratatui_ruby/version.rb +1 -1
  76. data/lib/ratatui_ruby.rb +24 -2
  77. data/mise.toml +8 -0
  78. data/sig/ratatui_ruby/buffer.rbs +11 -0
  79. data/sig/ratatui_ruby/schema/calendar.rbs +13 -0
  80. data/sig/ratatui_ruby/schema/{line_chart.rbs → chart.rbs} +20 -1
  81. data/sig/ratatui_ruby/schema/list.rbs +4 -1
  82. data/sig/ratatui_ruby/schema/rect.rbs +14 -0
  83. data/tasks/bump/cargo_lockfile.rb +19 -0
  84. data/tasks/bump/changelog.rb +37 -0
  85. data/tasks/bump/comparison_links.rb +41 -0
  86. data/tasks/bump/header.rb +30 -0
  87. data/tasks/bump/history.rb +30 -0
  88. data/tasks/bump/manifest.rb +31 -0
  89. data/tasks/bump/ruby_gem.rb +35 -0
  90. data/tasks/bump/sem_ver.rb +34 -0
  91. data/tasks/bump/unreleased_section.rb +38 -0
  92. data/tasks/bump.rake +49 -0
  93. data/tasks/doc.rake +25 -0
  94. data/tasks/extension.rake +12 -0
  95. data/tasks/lint.rake +49 -0
  96. data/tasks/rdoc_config.rb +15 -0
  97. data/tasks/resources/build.yml.erb +65 -0
  98. data/tasks/resources/index.html.erb +38 -0
  99. data/tasks/resources/rubies.yml +7 -0
  100. data/tasks/sourcehut.rake +38 -0
  101. data/tasks/test.rake +31 -0
  102. data/tasks/website/index_page.rb +28 -0
  103. data/tasks/website/version.rb +117 -0
  104. data/tasks/website/version_menu.rb +68 -0
  105. data/tasks/website/versioned_documentation.rb +49 -0
  106. data/tasks/website/website.rb +53 -0
  107. data/tasks/website.rake +26 -0
  108. metadata +119 -28
  109. data/.build.yml +0 -34
  110. data/.ruby-version +0 -1
  111. data/CODE_OF_CONDUCT.md +0 -30
  112. data/CONTRIBUTING.md +0 -40
  113. data/docs/images/examples-stock_ticker.rb.png +0 -0
  114. data/ext/ratatui_ruby/src/widgets/linechart.rs +0 -154
  115. data/lib/ratatui_ruby/schema/line_chart.rb +0 -41
  116. /data/{docs → doc}/application_testing.md +0 -0
  117. /data/{docs → doc}/contributors/design/ruby_frontend.md +0 -0
  118. /data/{docs → doc}/contributors/design/rust_backend.md +0 -0
  119. /data/{docs → doc}/contributors/design.md +0 -0
  120. /data/{docs → doc}/images/examples-analytics.rb.png +0 -0
  121. /data/{docs → doc}/images/examples-box_demo.rb.png +0 -0
  122. /data/{docs → doc}/images/examples-dashboard.rb.png +0 -0
  123. /data/{docs → doc}/images/examples-login_form.rb.png +0 -0
  124. /data/{docs → doc}/images/examples-map_demo.rb.png +0 -0
  125. /data/{docs → doc}/images/examples-mouse_events.rb.png +0 -0
  126. /data/{docs → doc}/images/examples-scrollbar_demo.rb.png +0 -0
  127. /data/{docs → doc}/images/examples-system_monitor.rb.png +0 -0
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 996cd8cc08b1f95614ad8ff31c735fcee9150cebaa35ced2d844088e34730390
4
- data.tar.gz: 4156030673a39867c6a99036cb6618910110c0d287c94500d601047163d87524
3
+ metadata.gz: 0e4a0958532fe7b493fcf0d9ee971bbc94194f5ff03fd420f895197597dac1c8
4
+ data.tar.gz: 480c3a5a467d478626a12c739064f894952e23d7a4574d0ad73a21dcc7b80ff5
5
5
  SHA512:
6
- metadata.gz: 9d08516a876ec1265246ebbb2855e647e2fc50846756abb07a466a8506aaf1acf5b0547276faedc017b44795b9d237b4ac1003796209094868e627a482a0fbd3
7
- data.tar.gz: 573b6c07ba542e1f5399da620b502a09cc999f70ae4dfa14f49974994e3b22d3bff2458c2076aa920281c418a232984834fbb6f6fd306f1a2a951ac308158f91
6
+ metadata.gz: 28f9f71581859a3ddaecb62df012e942fa3617dfcac1634af88e84b676b13802d3bb0bf7443ebba96f2bc1a00f503e86b8a2e2d3d6f613864d35b7002d432dac
7
+ data.tar.gz: f08716e00372054fcbee63e44ecb39e692ec2cc0b23d6e5596243b6df5c248274bf5b750b376d004644d8cf7a91993bde3e7c5dc980856befe84e0ce680de7b5
@@ -0,0 +1,52 @@
1
+ # SPDX-FileCopyrightText: 2025 Kerrick Long <me@kerricklong.com>
2
+ # SPDX-License-Identifier: AGPL-3.0-or-later
3
+
4
+ image: alpine/edge
5
+ packages:
6
+ - bash
7
+ - build-base
8
+ - curl
9
+ - openssl-dev
10
+ - yaml-dev
11
+ - zlib-dev
12
+ - readline-dev
13
+ - gdbm-dev
14
+ - ncurses-dev
15
+ - libffi-dev
16
+ - clang-dev
17
+ - git
18
+ artifacts:
19
+ - ratatui_ruby/pkg/ratatui_ruby-0.3.0.gem
20
+ sources:
21
+ - https://git.sr.ht/~kerrick/ratatui_ruby
22
+ tasks:
23
+ - setup: |
24
+ curl https://mise.jdx.dev/install.sh | sh
25
+ echo 'export PATH="$HOME/.local/bin:$PATH"' >> ~/.buildenv
26
+ echo 'eval "$($HOME/.local/bin/mise activate bash)"' >> ~/.buildenv
27
+ . ~/.buildenv
28
+ export RUSTFLAGS="-C target-feature=-crt-static"
29
+ export CI="true"
30
+ cd ratatui_ruby
31
+ sed -i 's/ruby = .*/ruby = "3.2"/' mise.toml
32
+ mise install
33
+ mise x -- pip install reuse
34
+ mise x -- gem install bundler:2.6.9
35
+ mise reshim
36
+ mise x -- bundle config set --local frozen 'true'
37
+ mise x -- bundle install
38
+ mise x -- bundle exec rake compile
39
+ - test: |
40
+ . ~/.buildenv
41
+ cd ratatui_ruby
42
+ echo "Testing Ruby 3.2"
43
+ mise x -- bundle exec rake test
44
+ - lint: |
45
+ . ~/.buildenv
46
+ cd ratatui_ruby
47
+ echo "Linting Ruby 3.2"
48
+ mise x -- bundle exec rake lint
49
+ - package: |
50
+ . ~/.buildenv
51
+ cd ratatui_ruby
52
+ mise x -- bundle exec rake build
@@ -0,0 +1,52 @@
1
+ # SPDX-FileCopyrightText: 2025 Kerrick Long <me@kerricklong.com>
2
+ # SPDX-License-Identifier: AGPL-3.0-or-later
3
+
4
+ image: alpine/edge
5
+ packages:
6
+ - bash
7
+ - build-base
8
+ - curl
9
+ - openssl-dev
10
+ - yaml-dev
11
+ - zlib-dev
12
+ - readline-dev
13
+ - gdbm-dev
14
+ - ncurses-dev
15
+ - libffi-dev
16
+ - clang-dev
17
+ - git
18
+ artifacts:
19
+ - ratatui_ruby/pkg/ratatui_ruby-0.3.0.gem
20
+ sources:
21
+ - https://git.sr.ht/~kerrick/ratatui_ruby
22
+ tasks:
23
+ - setup: |
24
+ curl https://mise.jdx.dev/install.sh | sh
25
+ echo 'export PATH="$HOME/.local/bin:$PATH"' >> ~/.buildenv
26
+ echo 'eval "$($HOME/.local/bin/mise activate bash)"' >> ~/.buildenv
27
+ . ~/.buildenv
28
+ export RUSTFLAGS="-C target-feature=-crt-static"
29
+ export CI="true"
30
+ cd ratatui_ruby
31
+ sed -i 's/ruby = .*/ruby = "3.3"/' mise.toml
32
+ mise install
33
+ mise x -- pip install reuse
34
+ mise x -- gem install bundler:2.6.9
35
+ mise reshim
36
+ mise x -- bundle config set --local frozen 'true'
37
+ mise x -- bundle install
38
+ mise x -- bundle exec rake compile
39
+ - test: |
40
+ . ~/.buildenv
41
+ cd ratatui_ruby
42
+ echo "Testing Ruby 3.3"
43
+ mise x -- bundle exec rake test
44
+ - lint: |
45
+ . ~/.buildenv
46
+ cd ratatui_ruby
47
+ echo "Linting Ruby 3.3"
48
+ mise x -- bundle exec rake lint
49
+ - package: |
50
+ . ~/.buildenv
51
+ cd ratatui_ruby
52
+ mise x -- bundle exec rake build
@@ -0,0 +1,52 @@
1
+ # SPDX-FileCopyrightText: 2025 Kerrick Long <me@kerricklong.com>
2
+ # SPDX-License-Identifier: AGPL-3.0-or-later
3
+
4
+ image: alpine/edge
5
+ packages:
6
+ - bash
7
+ - build-base
8
+ - curl
9
+ - openssl-dev
10
+ - yaml-dev
11
+ - zlib-dev
12
+ - readline-dev
13
+ - gdbm-dev
14
+ - ncurses-dev
15
+ - libffi-dev
16
+ - clang-dev
17
+ - git
18
+ artifacts:
19
+ - ratatui_ruby/pkg/ratatui_ruby-0.3.0.gem
20
+ sources:
21
+ - https://git.sr.ht/~kerrick/ratatui_ruby
22
+ tasks:
23
+ - setup: |
24
+ curl https://mise.jdx.dev/install.sh | sh
25
+ echo 'export PATH="$HOME/.local/bin:$PATH"' >> ~/.buildenv
26
+ echo 'eval "$($HOME/.local/bin/mise activate bash)"' >> ~/.buildenv
27
+ . ~/.buildenv
28
+ export RUSTFLAGS="-C target-feature=-crt-static"
29
+ export CI="true"
30
+ cd ratatui_ruby
31
+ sed -i 's/ruby = .*/ruby = "3.4"/' mise.toml
32
+ mise install
33
+ mise x -- pip install reuse
34
+ mise x -- gem install bundler:2.6.9
35
+ mise reshim
36
+ mise x -- bundle config set --local frozen 'true'
37
+ mise x -- bundle install
38
+ mise x -- bundle exec rake compile
39
+ - test: |
40
+ . ~/.buildenv
41
+ cd ratatui_ruby
42
+ echo "Testing Ruby 3.4"
43
+ mise x -- bundle exec rake test
44
+ - lint: |
45
+ . ~/.buildenv
46
+ cd ratatui_ruby
47
+ echo "Linting Ruby 3.4"
48
+ mise x -- bundle exec rake lint
49
+ - package: |
50
+ . ~/.buildenv
51
+ cd ratatui_ruby
52
+ mise x -- bundle exec rake build
@@ -0,0 +1,53 @@
1
+ # SPDX-FileCopyrightText: 2025 Kerrick Long <me@kerricklong.com>
2
+ # SPDX-License-Identifier: AGPL-3.0-or-later
3
+
4
+ image: alpine/edge
5
+ packages:
6
+ - bash
7
+ - build-base
8
+ - curl
9
+ - openssl-dev
10
+ - yaml-dev
11
+ - zlib-dev
12
+ - readline-dev
13
+ - gdbm-dev
14
+ - ncurses-dev
15
+ - libffi-dev
16
+ - clang-dev
17
+ - git
18
+ artifacts:
19
+ - ratatui_ruby/pkg/ratatui_ruby-0.3.0.gem
20
+ sources:
21
+ - https://git.sr.ht/~kerrick/ratatui_ruby
22
+ tasks:
23
+ - setup: |
24
+ curl https://mise.jdx.dev/install.sh | sh
25
+ echo 'export PATH="$HOME/.local/bin:$PATH"' >> ~/.buildenv
26
+ echo 'eval "$($HOME/.local/bin/mise activate bash)"' >> ~/.buildenv
27
+ . ~/.buildenv
28
+ export RUSTFLAGS="-C target-feature=-crt-static"
29
+ export CI="true"
30
+ cd ratatui_ruby
31
+ sed -i 's/ruby = .*/ruby = "4.0.0"/' mise.toml
32
+ mise install
33
+ mise x -- pip install reuse
34
+ mise x -- gem install bundler:2.6.9
35
+ mise reshim
36
+ mise x -- bundle config set --local frozen 'true'
37
+ mise x -- bundle install
38
+ # We allow this to fail so we can see logs without stopping the CI pipeline
39
+ mise x -- bundle exec rake compile || echo "⚠️ Compilation failed (Allowed Failure)"
40
+ - test: |
41
+ . ~/.buildenv
42
+ cd ratatui_ruby
43
+ echo "Testing Ruby 4.0.0"
44
+ mise x -- bundle exec rake test || true
45
+ - lint: |
46
+ . ~/.buildenv
47
+ cd ratatui_ruby
48
+ echo "Linting Ruby 4.0.0"
49
+ mise x -- bundle exec rake lint || true
50
+ - package: |
51
+ . ~/.buildenv
52
+ cd ratatui_ruby
53
+ mise x -- bundle exec rake build
@@ -3,7 +3,14 @@
3
3
  repos:
4
4
  - repo: local
5
5
  hooks:
6
+ - id: bundle-check
7
+ name: Check Gemfile.lock
8
+ entry: bundle check
9
+ language: system
10
+ files: (Gemfile|Gemfile\.lock|ratatui_ruby\.gemspec)
11
+ pass_filenames: false
6
12
  - id: rake
7
13
  name: rake
8
- entry: rake
9
- language: ruby
14
+ entry: bundle exec rake
15
+ language: system
16
+ pass_filenames: false
data/AGENTS.md CHANGED
@@ -35,14 +35,14 @@ Every file must begin with an SPDX-compliant header. Use the following format:
35
35
 
36
36
  ### Ruby Standards
37
37
 
38
- - **Version:** Strict Ruby 3.4 compatibility (Target `3.4.7` as per cosmoruby).
39
- - **Linter:** Run via `rake lint`. You are not done until all linting passes.
38
+ - **Version:** Tested against the latest releases of Ruby 3.2, 3.3, and 3.4, and must work. Also tested in CI (with allowed failures) against the latest preview Ruby 4.0 to prepare for its release. Local development happens on the latest stable release.
39
+ - **Linter:** Run via `bundle exec rake lint`. You are not done until all linting passes.
40
40
  - **Style:**
41
41
  - Use `Data.define` for all value objects (UI Nodes). (Prefer `class Foo < Data.define()` over `Foo = Data.define() do`).
42
42
  - Prefer `frozen_string_literal: true`.
43
43
  - Use `Minitest` for testing.
44
44
  - Define types in `.rbs` files. Don't use `untyped` just because it's easy; be comprehensive and accurate. Do not include `initialize` in `.rbs` files; use `self.new` for constructors instead.
45
- - Every line of Ruby must be covered by tests that would stand up to mutation testing. This includes all examples in the `examples/` directory; they should have corresponding tests in `examples/` to ensure they continue to work as intended and serve as reliable documentation. Tests must be meaningful and verify specific behavior or rendering output; simply verifying that code "doesn't crash" is insufficient and unacceptable.
45
+ - Every line of Ruby must be covered by tests that would stand up to mutation testing. This includes all examples in the `examples/` directory; they should have corresponding tests in `examples/` to ensure they continue to work as intended and serve as reliable documentation. Tests must be meaningful and verify specific behavior or rendering output; simply verifying that code "doesn't crash" is insufficient and unacceptable. For UI widgets, this means using `with_test_terminal` to verify every character of the terminal buffer's content.
46
46
  - Every public Ruby class/method must be documented for humans in RDoc (preferred)--**not** YARD--or markdown files (fallback), and must have `*.rbs` types defined.
47
47
  - Every significant architectural and design decision must be documented for contributors in markdown files. Mermaid is allowed.
48
48
 
@@ -94,14 +94,15 @@ The project follows a standard Gem layout with an `ext/` directory for Rust code
94
94
  ### Development Environment
95
95
 
96
96
  - **Setup:** `bin/setup` must handle both Bundler and Cargo dependencies.
97
- - **Pre-commit:** Use `.pre-commit-config.yaml` to enforce `rake` and `cargo fmt`.
97
+ - **Pre-commit:** Use `.pre-commit-config.yaml` to enforce `bundle exec rake` and `cargo fmt`.
98
98
 
99
99
  ### Documentation
100
100
 
101
101
  - Follow the `docs/` structure: `index.md` -> `contributors/` | `quickstart.md`.
102
102
  - Documentation should separate "User Guide" (Ruby API for TUI developers) from "Contributor Guide" (Ruby/Rust/Magnus internals).
103
103
  - Don't write .md files for something RDoc (Ruby) or rustdoc (Rust) can generate.
104
- - **Never edit the `doc/` folder directly.** It is automatically generated by `rake rerdoc`. If you need to refresh the generated documentation, run that command instead.
104
+ - **The `doc/` folder contains source markdown files** that are included in RDoc output. You can edit these files.
105
+ - **The `tmp/rdoc/` folder is auto-generated** by `bundle exec rake rerdoc`. Never edit files in `tmp/rdoc/` directly.
105
106
 
106
107
  ## 4. The Ruby <-> Rust Bridge Contract
107
108
 
@@ -117,3 +118,50 @@ The project follows a standard Gem layout with an `ext/` directory for Rust code
117
118
 
118
119
  - The gem builds a native extension.
119
120
  - Artifact naming: Ensure the output shared library matches Ruby's expectation on macOS (rename `.dylib`to `.bundle` if necessary during the build process in `extconf.rb` or `Rakefile`).
121
+
122
+ ## 6. Source Control Standards
123
+
124
+ - **Commits:**
125
+ - Who commits: Only humans should affect the git index and history. Rather than staging and/or committing, you should suggest a commit message.
126
+ - When: At the end of each task, before reporting the task as complete to the user, suggest the commit message.
127
+ - **Format:**
128
+ - Subject line: Concise summary (50 chars or less).
129
+ - Body: Detailed explanation if necessary (wrap at 72 chars). Explain why this is the implementation, as opposed to other possible implementations. Skip the body entirely if it's rote, a duplication of the diff, or otherwise unhelpful. **Do not simply list the files changed or the minor edits made to them.** Do not use markdown, except as required in AI Attribution.
130
+ - Footer: AI attribution if generated by an agent, sourcehut ticket if implemented by a ticket, or both.
131
+ - **AI Attribution:**
132
+ - **Antigravity:**
133
+ Specify the model used in the footer. Examples:
134
+ ```
135
+ Generated with [Antigravity](https://antigravity.google)
136
+
137
+ Co-Authored-By: Gemini 3 Pro (High) <noreply@google.com>
138
+ ```
139
+ ```
140
+ Generated with [Antigravity](https://antigravity.google)
141
+
142
+ Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
143
+ ```
144
+ - **Gemini 3:**
145
+ ```
146
+ Generated with [Gemini 3 Pro](https://gemini.google.com/)
147
+
148
+ Co-Authored-By: Gemini 3 Pro <noreply@google.com>
149
+ ```
150
+ - **JetBrains Junie:**
151
+ ```
152
+ Generated with [JetBrains Junie](https://www.jetbrains.com/ai/)
153
+
154
+ Co-Authored-By: Junie <junie@jetbrains.com>
155
+ ```
156
+ - **Sourcehut Tickets:**
157
+ - If the commit implements a specific ticket, include a footer: `Implements: https://todo.sr.ht/~kerrick/ratatui_ruby/<id>`
158
+ - This must be the **last** item in the footer, if present.
159
+
160
+ ## 7. Definition of Done
161
+
162
+ Before considering a task complete and returning control to the user, you **MUST** ensure:
163
+
164
+ 1. **Tests & Linting Pass:** Run `bundle exec rake` and confirm it passes. No new errors **or warnings** should be introduced.
165
+ 2. **Documentation Updated:** If public APIs or observable behavior changed, update relevant `doc/` files, `README.md`, and/or `ratatui_ruby-wiki` files,.
166
+ 3. **Changelog Updated:** If public APIs, observable behavior, or gemspec dependencies changed, update [CHANGELOG.md](CHANGELOG.md)'s **Unreleased** section according to the [Semantic Versioning](https://semver.org/) and [Keep a Changelog](https://keepachangelog.com/en/1.1.0/) specifications. Changelogs should be useful to human users of the library, not simple restatements of diffs or commit messages. **Do not add entries for internal tooling, CI, or build configuration changes that do not affect the distributed gem.**
167
+ 4. **Commit Message Suggested:** You **MUST** ensure the final message to the user includes a suggested commit message block. This is NOT optional.
data/CHANGELOG.md CHANGED
@@ -12,4 +12,54 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm
12
12
 
13
13
  ### Added
14
14
 
15
- - Created the gem
15
+ ### Changed
16
+
17
+ ### Fixed
18
+
19
+ ### Removed
20
+
21
+ ## [0.3.0] - 2025-12-28
22
+
23
+ ### Added
24
+
25
+ - **The Escape Hatch (Ruby Render Callback)**: Added the ability to define custom widgets in pure Ruby by implementing a `render(area, buffer)` method. The `Buffer` object provides low-level drawing primitives like `set_string`, allowing developers to create custom TUI components without writing Rust code.
26
+ - **Clear Widget**: Added the `Clear` widget, which resets the terminal buffer in the area it is rendered. This is essential for creating opaque popups and modals that prevent background styles from "bleeding" through transparent widgets.
27
+ - **Interactive Table Selection**: The `Table` widget now supports row selection with `selected_row`, `highlight_style`, and `highlight_symbol` parameters. This enables building interactive data grids and file explorers where users can navigate through rows using keyboard input.
28
+ - **Scrollable Paragraphs**: The `Paragraph` widget now supports a `scroll` parameter that accepts a `(y, x)` array to scroll content vertically and horizontally. This enables viewing long text content that exceeds the visible area, such as logs or documents. The parameter order matches ratatui's convention.
29
+
30
+ ### Changed
31
+
32
+ - **Center Widget**: Removed the implicit `Clear` call from the `Center` widget. `Center` is now a pure layout widget, requiring an explicit `Clear` widget if background clearing is desired. This restores correct behavior for transparent overlays.
33
+
34
+ ## [0.2.0] - 2025-12-24
35
+
36
+ ### Added
37
+
38
+ - **DSL for Simpler Apps**: Introduced `RatatuiRuby.main_loop`, a new entrypoint that simplifies application structure when you don't need control of the event loop or application lifecycle.
39
+ - **Calendar Widget**: Added the `Calendar` widget, allowing you to display monthly views and visualize date-based information.
40
+ - **Generic Charts**: Implemented the full `Chart` widget, which supersedes the now-deprecated `LineChart` and `BarChart` widgets, giving you more freedom to visualize data sets.
41
+ - **Enhanced List Styling**: You can now customize the appearance of selected items in a `List` using `highlight_style` and `highlight_symbol`.
42
+ - **Broader Ruby Support**: Added support for a wider range of Ruby versions: every non-EOL version. The latest preview of Ruby 4.0 is tested in CI, but not supported.
43
+ - **Dev Tools**: Added internal Rake tasks for managing historical documentation and SemVer checks.
44
+
45
+ ## [0.1.0] - 2025-12-22
46
+
47
+ ### Added
48
+
49
+ - **First Release**: Initial public release of `ratatui_ruby`, bringing the power of the Rust [ratatui](https://github.com/ratatui-org/ratatui) library to Rubyists!
50
+ - **Core Widget Set**: Includes a comprehensive suite of widgets to get you started:
51
+ - `Block`, `Borders`, and `Paragraph` for basic content.
52
+ - `List` and `Table` for structured data.
53
+ - `Gauge` and `Sparkline` for progress and metrics.
54
+ - `Tabs` for navigation.
55
+ - `Canvas` for drawing shapes (Lines, Circles, Rectangles, Maps).
56
+ - **Layout System**: A flexible layout engine using `Flex`, `Layout`, and `Constraints` to build responsive interfaces that adapt to any terminal size.
57
+ - **Forms & Layers**: Primitives like `Overlay` and `Center` for creating modal dialogs, plus a `Cursor` widget for text input interactions.
58
+ - **Styling**: Full support for `Ratatui`'s styling primitives, including modifiers and RGB/ANSI colors.
59
+ - **Input Handling**: Robust handling for both Keyboard and Mouse events.
60
+ - **Testing Support**: Included `RatatuiRuby::TestHelper` and RSpec integration to make testing your TUI applications possible.
61
+
62
+ [Unreleased]: https://git.sr.ht/~kerrick/ratatui_ruby/compare/v0.3.0...HEAD
63
+ [0.3.0]: https://git.sr.ht/~kerrick/ratatui_ruby/compare/v0.2.0...v0.3.0
64
+ [0.2.0]: https://git.sr.ht/~kerrick/ratatui_ruby/compare/v0.1.0...v0.2.0
65
+ [0.1.0]: https://git.sr.ht/~kerrick/ratatui_ruby/tree/v0.1.0
data/README.md CHANGED
@@ -4,18 +4,26 @@
4
4
  -->
5
5
  # ratatui_ruby
6
6
 
7
- > [!NOTE]
8
- > **ratatui_ruby** is a community wrapper that is not affiliated with [the Ratatui team](https://github.com/orgs/ratatui/people).
7
+ [![
8
+ builds.sr.ht status](https://builds.sr.ht/~kerrick/ratatui_ruby.svg)](https://builds.sr.ht/~kerrick/ratatui_ruby?) [![
9
+ License](https://img.shields.io/badge/dynamic/regex?url=https%3A%2F%2Fgit.sr.ht%2F~kerrick%2Fratatui_ruby%2Fblob%2Fmain%2Fratatui_ruby.gemspec&search=spec%5C.license%20%3D%20%22(.*)%22&replace=%241&label=License&color=a2c93e)](https://spdx.org/licenses/AGPL-3.0-or-later.html) [![
10
+ Gem Total Downloads](https://img.shields.io/gem/dt/ratatui_ruby)](https://rubygems.org/gems/ratatui_ruby) [![
11
+ Gem Version](https://img.shields.io/gem/v/ratatui_ruby)](https://rubygems.org/gems/ratatui_ruby) [![
12
+ Ratatui Version](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fgit.sr.ht%2F~kerrick%2Fratatui_ruby%2Fblob%2Fmain%2Fext%2Fratatui_ruby%2FCargo.toml&query=%24.dependencies.ratatui.version&prefix=v&logo=ratatui&label=Ratatui)](https://crates.io/crates/ratatui/0.26.3) [![
13
+ Mailing List: Discussion](https://img.shields.io/badge/mailing_list-discussion-5865F2.svg?logo=data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiBmaWxsPSJub25lIiBzdHJva2U9IiNmZmZmZmYiIHN0cm9rZS13aWR0aD0iMiIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIiBjbGFzcz0iaWNvbiBpY29uLXRhYmxlciBpY29ucy10YWJsZXItb3V0bGluZSBpY29uLXRhYmxlci1tYWlsIj48cGF0aCBzdHJva2U9Im5vbmUiIGQ9Ik0wIDBoMjR2MjRIMHoiIGZpbGw9Im5vbmUiLz48cGF0aCBkPSJNMyA3YTIgMiAwIDAgMSAyIC0yaDE0YTIgMiAwIDAgMSAyIDJ2MTBhMiAyIDAgMCAxIC0yIDJoLTE0YTIgMiAwIDAgMSAtMiAtMnYtMTB6IiAvPjxwYXRoIGQ9Ik0zIDdsOSA2bDkgLTYiIC8+PC9zdmc+Cg==)](https://lists.sr.ht/~kerrick/ratatui_ruby-discuss) [![
14
+ Mailing List: Development](https://img.shields.io/badge/mailing_list-development-4954d5.svg?logo=data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiBmaWxsPSJub25lIiBzdHJva2U9IiNmZmZmZmYiIHN0cm9rZS13aWR0aD0iMiIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIiBjbGFzcz0iaWNvbiBpY29uLXRhYmxlciBpY29ucy10YWJsZXItb3V0bGluZSBpY29uLXRhYmxlci1tYWlsIj48cGF0aCBzdHJva2U9Im5vbmUiIGQ9Ik0wIDBoMjR2MjRIMHoiIGZpbGw9Im5vbmUiLz48cGF0aCBkPSJNMyA3YTIgMiAwIDAgMSAyIC0yaDE0YTIgMiAwIDAgMSAyIDJ2MTBhMiAyIDAgMCAxIC0yIDJoLTE0YTIgMiAwIDAgMSAtMiAtMnYtMTB6IiAvPjxwYXRoIGQ9Ik0zIDdsOSA2bDkgLTYiIC8+PC9zdmc+Cg==)](https://lists.sr.ht/~kerrick/ratatui_ruby-devel) [![
15
+ Mailing List: Announcements](https://img.shields.io/badge/mailing_list-announcements-3b44ac.svg?logo=data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiBmaWxsPSJub25lIiBzdHJva2U9IiNmZmZmZmYiIHN0cm9rZS13aWR0aD0iMiIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIiBjbGFzcz0iaWNvbiBpY29uLXRhYmxlciBpY29ucy10YWJsZXItb3V0bGluZSBpY29uLXRhYmxlci1tYWlsIj48cGF0aCBzdHJva2U9Im5vbmUiIGQ9Ik0wIDBoMjR2MjRIMHoiIGZpbGw9Im5vbmUiLz48cGF0aCBkPSJNMyA3YTIgMiAwIDAgMSAyIC0yaDE0YTIgMiAwIDAgMSAyIDJ2MTBhMiAyIDAgMCAxIC0yIDJoLTE0YTIgMiAwIDAgMSAtMiAtMnYtMTB6IiAvPjxwYXRoIGQ9Ik0zIDdsOSA2bDkgLTYiIC8+PC9zdmc+Cg==)](https://lists.sr.ht/~kerrick/ratatui_ruby-announce)
9
16
 
10
17
 
11
18
  ## Introduction
12
19
 
13
20
  **ratatui_ruby** is a Ruby wrapper for [Ratatui](https://ratatui.rs). It allows you to cook up Terminal User Interfaces in Ruby.
21
+ **ratatui_ruby** is a community wrapper that is not affiliated with [the Ratatui team](https://github.com/orgs/ratatui/people).
14
22
 
15
23
  > [!WARNING]
16
24
  > **ratatui_ruby** is currently in an early stage of development. Use at your own risk.
17
25
 
18
- Please join our **announce** mailing list at https://lists.sr.ht/~kerrick/ratatui_ruby-announce to stay up-to-date on new releases and announcements.
26
+ Please join the **announce** mailing list at https://lists.sr.ht/~kerrick/ratatui_ruby-announce to stay up-to-date on new releases and announcements.
19
27
 
20
28
 
21
29
  ## Compatibility
@@ -25,13 +33,17 @@ Please join our **announce** mailing list at https://lists.sr.ht/~kerrick/ratatu
25
33
  - GNU/Linux, macOS, Windows, OpenBSD, and FreeBSD; and
26
34
  - x86_64 (AMD, Intel) and ARM (Apple Silicon, Raspberry Pi).
27
35
 
36
+ We support the latest minor version of every
37
+ [non-eol Ruby version](https://www.ruby-lang.org/en/downloads/branches/).
38
+ Support for Ruby 4 is coming soon.
39
+
28
40
 
29
41
  ## Installation
30
42
 
31
43
  Add this line to your application's Gemfile:
32
44
 
33
45
  ```ruby
34
- gem 'ratatui_ruby'
46
+ gem "ratatui_ruby"
35
47
  ```
36
48
 
37
49
  And then execute:
@@ -40,7 +52,7 @@ And then execute:
40
52
  bundle install
41
53
  ```
42
54
 
43
- Or install it yourself as:
55
+ Or install it yourself with:
44
56
 
45
57
  ```bash
46
58
  gem install ratatui_ruby
@@ -49,38 +61,46 @@ gem install ratatui_ruby
49
61
 
50
62
  ## Usage
51
63
 
52
- **ratatui_ruby** uses an immediate-mode API. You describe your UI using Ruby `Data` objects and call `draw` in a loop.
64
+ **ratatui_ruby** uses an immediate-mode API. You describe your UI using Ruby objects and call `draw` in a loop.
53
65
 
54
66
  ```ruby
55
- RatatuiRuby.init_terminal
56
- begin
57
- view = RatatuiRuby::Paragraph.new(text: "Hello World", block: RatatuiRuby::Block.new(borders: [:all]))
58
- RatatuiRuby.draw(view)
59
- sleep 2
60
- ensure
61
- RatatuiRuby.restore_terminal
67
+ require "ratatui_ruby"
68
+ RatatuiRuby.main_loop do |tui|
69
+ tui.draw \
70
+ tui.paragraph \
71
+ text: "Hello, Ratatui! Press 'q' to quit.",
72
+ align: :center,
73
+ block: tui.block(
74
+ title: "My Ruby TUI App",
75
+ borders: [:all],
76
+ border_color: "cyan"
77
+ )
78
+ event = tui.poll_event
79
+ break if event && event[:type] == :key && event[:code] == "q"
62
80
  end
63
81
  ```
64
82
 
65
- For a full tutorial, see [the Quickstart](./docs/quickstart.md).
83
+ For a full tutorial, see [the Quickstart](./doc/quickstart.md).
66
84
 
67
85
 
68
86
  ## Documentation
69
87
 
70
- For the full documentation on how to use **ratatui_ruby**, see our [docs](./docs/index.md).
88
+ For the full documentation on how to use **ratatui_ruby**, see the [documentation](./doc/index.md). For other information, see the [wiki](https://man.sr.ht/~kerrick/ratatui_ruby).
71
89
 
72
90
 
73
91
  ## Contributing
74
92
 
75
- Bug reports and pull requests are welcome on [sourcehut](https://sourcehut.org) at https://sr.ht/~kerrick/ratatui_ruby/. This project is intended to be a safe, productive collaboration, and contributors are expected to adhere to the [Ruby Community Conduct Guideline](https://www.ruby-lang.org/en/conduct/).
93
+ Bug reports and pull requests are welcome on [sourcehut](https://sourcehut.org) at https://sr.ht/~kerrick/ratatui_ruby/. This project is intended to be a safe, productive collaboration, and contributors are expected to adhere to the [Code of Conduct](https://man.sr.ht/~kerrick/ratatui_ruby/code_of_conduct.md).
76
94
 
77
95
  Issues for the underlying Rust library should be filed at [ratatui/ratatui](https://github.com/ratatui/ratatui).
78
96
 
79
- Want to help develop **ratatui_ruby**? Check out our [contribution guide](./CONTRIBUTING.md).
97
+ Want to help develop **ratatui_ruby**? Check out the [contribution guide on the wiki](https://man.sr.ht/~kerrick/ratatui_ruby/contributing.md).
80
98
 
81
99
 
82
100
  ## Copyright & License
83
101
 
84
102
  **ratatui_ruby** is copyright 2025, Kerrick Long. **ratatui_ruby** is licensed under the GNU Affero General Public License v3.0 or later; see [LICENSES/AGPL-3.0-or-later.txt](./LICENSES/AGPL-3.0-or-later) for the full text.
85
103
 
86
- Some parts of this program are copied from other sources under appropriate reuse licenses, and the copyright belongs to their respective owners. See the [REUSE Specification – Version 3.3](https://reuse.software/spec-3.3/) for information about how we comply with attribution and licensing requirements.
104
+ Some parts of this program are copied from other sources under appropriate reuse licenses, and the copyright belongs to their respective owners. See the [REUSE Specification – Version 3.3](https://reuse.software/spec-3.3/) for information about how we comply with attribution and licensing requirements.
105
+
106
+ This program was created with significant assistance from multiple LLMs. The process was human-controlled through creative prompts, with human contributions to each commit. See commit footers for model attribution. [declare-ai.org](https://declare-ai.org/1.0.0/creative.html)
data/REUSE.toml CHANGED
@@ -15,3 +15,8 @@ SPDX-License-Identifier = "CC0-1.0"
15
15
  path = 'ext/ratatui_ruby/Cargo.lock'
16
16
  SPDX-FileCopyrightText = "2025 Kerrick Long <me@kerricklong.com>"
17
17
  SPDX-License-Identifier = "CC0-1.0"
18
+
19
+ [[annotations]]
20
+ path = 'doc/images/*.png'
21
+ SPDX-FileCopyrightText = "2025 Kerrick Long <me@kerricklong.com>"
22
+ SPDX-License-Identifier = "CC-BY-SA-4.0"
data/Rakefile CHANGED
@@ -4,105 +4,8 @@
4
4
  # SPDX-License-Identifier: AGPL-3.0-or-later
5
5
 
6
6
  require "bundler/gem_tasks"
7
- require "minitest/test_task"
8
7
 
9
- # Ruby tests are handled by test:ruby
10
- # Cargo tests are handled by test:rust
8
+ # Import all tasks from the tasks/ directory
9
+ Dir.glob("tasks/*.rake").each { |r| import r }
11
10
 
12
- require "rake/extensiontask"
13
-
14
- spec = Gem::Specification.load("ratatui_ruby.gemspec")
15
- Rake::ExtensionTask.new("ratatui_ruby", spec) do |ext|
16
- ext.lib_dir = "lib/ratatui_ruby"
17
- ext.ext_dir = "ext/ratatui_ruby"
18
- end
19
-
20
- # The :compile task is now provided by rake-compiler
21
-
22
- require "rubocop/rake_task"
23
-
24
- RuboCop::RakeTask.new
25
-
26
- require "rdoc/task"
27
-
28
- RDoc::Task.new do |rdoc|
29
- rdoc.rdoc_dir = "doc"
30
- rdoc.main = "README.md"
31
- rdoc.rdoc_files.include("**/*.md", "**/*.rdoc", "lib/**/*.rb", "exe/**/*")
32
- end
33
-
34
- Rake::Task[:rdoc].enhance do
35
- FileUtils.mkdir_p "doc/docs/images"
36
- FileUtils.cp_r FileList["docs/images/*.png"], "doc/docs/images"
37
- end
38
-
39
- Rake::Task[:rerdoc].enhance do
40
- FileUtils.mkdir_p "doc/docs/images"
41
- FileUtils.cp_r FileList["docs/images/*.png"], "doc/docs/images"
42
- end
43
-
44
- require "rubycritic/rake_task"
45
-
46
- RubyCritic::RakeTask.new do |task|
47
- task.options = "--no-browser"
48
- task.paths = FileList.new.include("exe/**/*.rb", "lib/**/*.rb", "sig/**/*.rbs")
49
- end
50
-
51
- require "inch/rake"
52
-
53
- Inch::Rake::Suggest.new("doc:suggest", "exe/**/*.rb", "lib/**/*.rb", "sig/**/*.rbs") do |suggest|
54
- suggest.args << ""
55
- end
56
-
57
- namespace :cargo do
58
- desc "Run cargo fmt"
59
- task :fmt do
60
- sh "cd ext/ratatui_ruby && cargo fmt --all -- --check"
61
- end
62
-
63
- desc "Run cargo clippy"
64
- task :clippy do
65
- sh "cd ext/ratatui_ruby && cargo clippy -- -D warnings"
66
- end
67
-
68
- desc "Run cargo tests"
69
- task :test do
70
- sh "cd ext/ratatui_ruby && cargo test"
71
- end
72
- end
73
-
74
- namespace :reuse do
75
- desc "Run the REUSE Tool to confirm REUSE compliance"
76
- task :lint do
77
- sh "pipx run reuse lint"
78
- end
79
- end
80
- task(:reuse) { Rake::Task["reuse:lint"].invoke }
81
-
82
- namespace :lint do
83
- multitask docs: %i[rubycritic rdoc:coverage reuse:lint]
84
- multitask code: %i[rubocop rubycritic cargo:fmt cargo:clippy cargo:test]
85
- multitask licenses: %i[reuse:lint]
86
- multitask all: %i[docs code licenses]
87
- end
88
- task(:lint) { Rake::Task["lint:all"].invoke }
89
-
90
- # Clear the default test task created by Minitest::TestTask
91
- Rake::Task["test"].clear
92
-
93
- desc "Run all tests (Ruby and Rust)"
94
- task test: %w[test:ruby test:rust]
95
-
96
- namespace :test do
97
- desc "Run Rust tests"
98
- task :rust do
99
- Rake::Task["cargo:test"].invoke
100
- end
101
-
102
- # Create a specific Minitest task for Ruby tests
103
- Minitest::TestTask.create(:ruby) do |t|
104
- t.test_globs = ["test/**/test_*.rb", "examples/**/test_*.rb"]
105
- end
106
- end
107
-
108
- multitask default: %i[test lint]
11
+ task default: %w[sourcehut test lint]
@@ -7,7 +7,8 @@
7
7
 
8
8
  ## Documentation for Contributors
9
9
 
10
- - [Contributing Guidelines](../../CONTRIBUTING.md)
10
+ - [Contributing Guidelines](https://man.sr.ht/~kerrick/ratatui_ruby/contributing.md)
11
+ - [Documentation Guide](https://man.sr.ht/~kerrick/ratatui_ruby/documentation_guide.md)
11
12
  - [The Design of **ratatui_ruby**](./design.md)
12
13
 
13
14
  ## Documentation for Users
data/doc/custom.css ADDED
@@ -0,0 +1,8 @@
1
+ img {
2
+ max-width: 100%;
3
+ height: auto;
4
+ }
5
+
6
+ .theme-toggle {
7
+ margin-left: 0 !important;
8
+ }