grmenu 0.1.4 → 2.0.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 (7) hide show
  1. checksums.yaml +4 -4
  2. data/GRmenu.rb +877 -110
  3. data/README.md +268 -126
  4. data/data/borders.json +85 -0
  5. data/data/colors.json +16 -0
  6. data/data/fonts.json +3005 -0
  7. metadata +9 -6
data/README.md CHANGED
@@ -1,18 +1,14 @@
1
1
  <div align="center">
2
2
 
3
- # GRmenu
3
+ # GRmenu (Ruby)
4
4
 
5
- **Menús de navegación por teclado para terminal, en modo TTY crudo**
5
+ **Menús interactivos por teclado para terminal en modo TTY crudo, con soporte para Banners ASCII 3D, barras de progreso, spinners animados, tooltips dinámicos, estilos y colores personalizados**
6
6
 
7
7
  Flechas arriba/abajo para moverte · `Enter` para elegir · `q` para salir
8
8
 
9
9
  [![Gem Version](https://badge.fury.io/rb/grmenu.svg)](https://badge.fury.io/rb/grmenu)
10
- [![PyPI version](https://img.shields.io/pypi/v/grmenu?color=blue&label=PyPI)](https://pypi.org/project/grmenu/)
11
- [![Ruby](https://img.shields.io/badge/ruby-%3E%3D%202.6-red.svg)](https://www.ruby-lang.org)
12
- [![Python versions](https://img.shields.io/pypi/pyversions/grmenu)](https://pypi.org/project/grmenu/)
13
10
  [![License: MIT](https://img.shields.io/github/license/JoseEduardoGR/GRmenu)](LICENSE)
14
- [![GitHub last commit](https://img.shields.io/github/last-commit/JoseEduardoGR/GRmenu)](https://github.com/JoseEduardoGR/GRmenu/commits/main)
15
- [![GitHub stars](https://img.shields.io/github/stars/JoseEduardoGR/GRmenu?style=social)](https://github.com/JoseEduardoGR/GRmenu/stargazers)
11
+ [![Platform](https://img.shields.io/badge/platform-Linux%20%7C%20macOS%20%7C%20Windows-blue)](https://github.com/JoseEduardoGR/GRmenu)
16
12
 
17
13
  </div>
18
14
 
@@ -20,84 +16,214 @@ Flechas arriba/abajo para moverte · `Enter` para elegir · `q` para salir
20
16
 
21
17
  ## ✨ Características
22
18
 
23
- - 🎮 **Navegación con flechas** — arriba/abajo para moverte, `Enter` para ejecutar, `q` para salir
24
- - 🎨 **20 estilos de borde** — desde ASCII clásico hasta caracteres Unicode y bloques
25
- - 🌈 **Colores personalizables** — borde, opciones y foco por separado, con 8 colores en 2 tonos cada uno
26
- - 📦 **Cero dependencias externas** — solo la librería estándar (`io/console` en Ruby, `termios`/`tty` en Python)
27
- - 💎 **Ruby & Python** — implementaciones disponibles tanto en RubyGems (`grmenu`) como en PyPI (`grmenu`)
28
- - 🐧 **Linux / macOS** — funciona en cualquier terminal POSIX
29
-
30
- > ⚠️ Requiere una terminal real (TTY) en Linux o macOS. En Ruby utiliza `io/console` en modo crudo (`raw`) y en Python `termios`/`tty` para capturar pulsaciones de teclas en tiempo real.
19
+ - 🎮 **Navegación con flechas** — arriba/abajo para moverte, `Enter` para ejecutar, `q` para salir.
20
+ - 🔤 **10 Fuentes ASCII 3D para Banners** — fuentes tridimensionales (ANSI Shadow, Slant, Doom, Graffiti, Modular, Wire, Block, Stars, etc.).
21
+ - 📜 **Auto-Paginación y Scroll Fluido** — calcula la altura de la terminal y crea una ventana deslizante con indicadores automáticos (`▲ (+N arriba)` / `▼ (+M abajo)`).
22
+ - 💡 **Descripciones y Tooltips Dinámicos** — muestra información explicativa en la parte inferior del recuadro al enfocar cada opción.
23
+ - **Spinners y Barras de Progreso** — helpers nativos `GRmenu.spinner` y `GRmenu.progress` dentro de recuadros con la misma estética visual.
24
+ - 🎨 **20 estilos de borde** — desde ASCII clásico hasta caracteres Unicode dobles, curvas redondeadas y bloques outline.
25
+ - 🌈 **Paleta de colores completa** — personalización individual de marco, título, banner, subtítulo, divisores, opciones y foco activo con 2 niveles de brillo.
26
+ - 📐 **Centrado simétrico automático** alinea y centra automáticamente subtítulos y menús de opciones respecto al ancho de banners grandes.
27
+ - 🛠️ **Helpers nativos en modo crudo** — `clear_screen`, `continue`, `banner`, `spinner`, `progress`, `div` y `help`.
28
+ - 💻 **100% Multiplataforma** — compatible con Linux, macOS y Windows (PowerShell, CMD, Windows Terminal, VS Code).
29
+ - 📦 **Cero dependencias externas** — utiliza únicamente la librería estándar `io/console` y `json`.
31
30
 
32
31
  ---
33
32
 
34
33
  ## 📦 Instalación
35
34
 
36
- ### Ruby (RubyGems)
37
-
38
35
  ```bash
39
36
  gem install grmenu
40
37
  ```
41
38
 
42
- O en tu `Gemfile`:
39
+ O si trabajás con el archivo directamente en tu proyecto:
43
40
 
44
41
  ```ruby
45
- gem 'grmenu'
42
+ require "GRmenu"
46
43
  ```
47
44
 
48
- ### Python (PyPI)
45
+ <sub>Requiere Ruby ≥ 2.6.</sub>
49
46
 
50
- ```bash
51
- pip install grmenu
47
+ ---
48
+
49
+ ## 💡 Cómo se pasan las opciones y todos los parámetros
50
+
51
+ `GRmenu` permite pasar métodos directos, símbolos, arreglos con nombres personalizados, bloques lambda/procs y **descripciones explicativas (tooltips)**:
52
+
53
+ ```ruby
54
+ menu = GRmenu.new(
55
+ [
56
+ method(:iniciar_servidor), # 1. Method (auto-capitaliza: "Iniciar Servidor")
57
+ :crear_respaldo, # 2. Symbol (auto-capitaliza: "Crear Respaldo")
58
+ ["Métricas del Sistema", method(:ver_metricas)], # 3. Array ["Nombre Personalizado", acción]
59
+ ["Crear Backup", method(:respaldo), "Genera dump SQL de la BD"], # 4. Con Tooltip descriptivo al pie del marco
60
+ ["Ejecutar Lambda", -> { puts Color.pink("Lambda!"); GRmenu.continue }, "Bloque anónimo Proc/Lambda"],
61
+ ["Probar Banner Helper", method(:prueba_banner_rapido)], # 5. Helper GRmenu.banner
62
+ ["Ver Ayuda y Referencia", method(:ver_ayuda_completa)], # 6. Helper GRmenu.help
63
+ method(:salir) # 7. Salir
64
+ ],
65
+ banner: "DEV OPS", # Texto gigante en arte ASCII 3D
66
+ title: "Panel de Control", # Título en el marco de opciones
67
+ subtitle: "Consola de Administración\nUsa las flechas y Enter", # Subtítulo (soporta saltos de línea \n)
68
+ font: 1, # Fuente del banner (1 al 10, default 1: ANSI Shadow 3D)
69
+ style: 7, # Estilo de marco de opciones (1 al 20, ej: 7=redondeado, 3=doble)
70
+ banner_style: 3, # Estilo de marco del banner (1 al 20, ej: 3=doble línea)
71
+ divider: true, # Líneas divisorias a la par del banner (true, false o número)
72
+ center: true, # Centrado automático del menú y subtítulo respecto al banner
73
+ page_size: 8 # (Opcional) Límite visible para auto-scroll y paginación
74
+ )
52
75
  ```
53
76
 
54
77
  ---
55
78
 
56
- ## 🚀 Uso rápido (Ruby)
79
+ ## 🌟 Ejemplo Completo de Uso (`e.rb`)
80
+
81
+ A continuación se muestra el archivo de ejemplo completo [`e.rb`](e.rb) con acciones originales, helpers de carga (`spinner` / `progress`), paginación, configuración de estilos, fuentes y colores:
57
82
 
58
83
  ```ruby
59
- require 'GRmenu'
84
+ # frozen_string_literal: true
60
85
 
61
- def opcion_uno
62
- puts "elegiste uno"
86
+ require "GRmenu"
87
+
88
+ # 1. Definición de acciones/métodos originales
89
+ def iniciar_servidor
90
+ GRmenu.clear_screen
91
+ puts Color.bright_green("-> Servidor iniciado correctamente en el puerto 3000.")
92
+ GRmenu.continue
63
93
  end
64
94
 
65
- def opcion_dos
66
- puts "elegiste dos"
95
+ def crear_respaldo
96
+ GRmenu.clear_screen
97
+ puts Color.bright_cyan("-> Creando respaldo de la base de datos...")
98
+ GRmenu.continue
67
99
  end
68
100
 
69
- menu = GRmenu.new(
70
- [method(:opcion_uno), method(:opcion_dos)],
71
- title: "Mi menu",
72
- style: 19
73
- )
101
+ def ver_metricas
102
+ GRmenu.clear_screen
103
+ puts Color.bright_magenta("-> CPU: 12% | RAM: 4.2 GB | Estado: Operativo")
104
+ GRmenu.continue
105
+ end
74
106
 
75
- menu.set_style.border("yellow")
76
- menu.set_style.options("green")
77
- menu.draw
78
- ```
107
+ def prueba_banner_rapido
108
+ GRmenu.clear_screen
109
+ GRmenu.banner("OK", 0, color: "green", level: 2, style: 3, font: 1)
110
+ GRmenu.div(40, "green", 1, "═")
111
+ puts Color.green(" Prueba completada con éxito.")
112
+ GRmenu.div(40, "green", 1, "═")
113
+ GRmenu.continue
114
+ end
79
115
 
80
- Cada elemento de la lista puede ser un `Method` (`method(:mi_metodo)`), un `Proc` / `lambda` (`-> { ... }`), un arreglo `["Nombre", callable]` o un `Symbol` (`:mi_metodo`). El nombre se toma automáticamente de la opción y al presionar `Enter` sobre ella, esa acción se ejecuta.
116
+ def ver_ayuda_completa
117
+ GRmenu.clear_screen
118
+ GRmenu.help
119
+ GRmenu.continue
120
+ end
81
121
 
82
- <details>
83
- <summary>🐍 <b>Ver ejemplo en Python</b></summary>
122
+ def salir
123
+ GRmenu.clear_screen
124
+ puts Color.bright_yellow("¡Sesión finalizada con éxito!")
125
+ exit(0)
126
+ end
84
127
 
85
- ```python
86
- from GRmenu import GRmenu
128
+ # 2. Nuevos ejemplos: Barra de Progreso, Spinner y Paginación
129
+ def demo_barra_progreso
130
+ GRmenu.clear_screen
131
+ # Fácil y rápido: pasas el total y bar.advance(1) en tu bucle
132
+ GRmenu.progress(10, title: "Descargando Paquetes", color: "cyan", style: 3) do |bar|
133
+ 10.times do |i|
134
+ sleep 0.1
135
+ bar.advance(1, status: "Paso #{i + 1} de 10 completado")
136
+ end
137
+ end
138
+ puts Color.bright_green("\n-> ¡Barra completada al 100%!")
139
+ GRmenu.continue
140
+ end
141
+
142
+ def demo_spinner
143
+ GRmenu.clear_screen
144
+ GRmenu.spinner("Conectando a la base de datos...", color: "green") do
145
+ sleep 1.2
146
+ end
147
+ puts Color.bright_green("\n-> Conexión establecida con éxito.")
148
+ GRmenu.continue
149
+ end
87
150
 
88
- def opcion_uno():
89
- print("elegiste uno")
151
+ def demo_paginacion
152
+ GRmenu.clear_screen
153
+ opciones_largas = (1..20).map do |n|
154
+ ["Elemento ##{n}", -> {
155
+ GRmenu.clear_screen
156
+ puts Color.bright_cyan("-> Has seleccionado el Elemento ##{n}")
157
+ GRmenu.continue
158
+ }, "Descripción opcional del elemento ##{n}"]
159
+ end
160
+
161
+ sub = GRmenu.new(
162
+ opciones_largas,
163
+ title: "Submenú Paginado",
164
+ subtitle: "Usa ↑ / ↓ para ver el auto-scroll",
165
+ style: 7,
166
+ page_size: 6
167
+ )
168
+ sub.draw(size_max: 38)
169
+ end
90
170
 
91
- def opcion_dos():
92
- print("elegiste dos")
171
+ # 3. Instanciación del menú con TODOS los parámetros disponibles
172
+ def main
173
+ menu = GRmenu.new(
174
+ [
175
+ method(:iniciar_servidor), # 1. Method (sin info)
176
+ :crear_respaldo, # 2. Symbol (sin info)
177
+ ["Métricas del Sistema", method(:ver_metricas)], # 3. Array (sin info)
178
+ ["Probar Barra de Progreso", method(:demo_barra_progreso), "Ejemplo fácil de GRmenu.progress al 100%"], # 4. CON Tooltip
179
+ ["Probar Spinner de Carga", method(:demo_spinner), "Animación en tiempo real para funciones pesadas"],
180
+ ["Probar Paginación (20 ítems)", method(:demo_paginacion), "Desplazamiento suave de opciones"],
181
+ ["Ejecutar Lambda", -> { puts Color.pink("¡Lambda!"); GRmenu.continue }], # 5. Lambda/Proc
182
+ ["Probar Banner Helper", method(:prueba_banner_rapido)], # 6. Helper GRmenu.banner
183
+ ["Ver Ayuda y Referencia", method(:ver_ayuda_completa), "Abre la guía de ayuda interactiva"], # 7. Helper GRmenu.help
184
+ method(:salir) # 8. Salir
185
+ ],
186
+ banner: " gr codE ",
187
+ title: "Panel de Control",
188
+ subtitle: "Consola de Administración TTY\nUsa ↑ / ↓ para navegar y Enter para seleccionar",
189
+ style: 3,
190
+ banner_style: 3,
191
+ divider: true,
192
+ center: true
193
+ )
194
+
195
+ # 4. Configuración completa de colores y estilos
196
+ menu.set_style.font(1) # 1 = ANSI Shadow 3D
197
+ menu.set_style.banner("cyan", 2) # Color del banner ASCII
198
+ menu.set_style.title("yellow", 2) # Color del título del recuadro
199
+ menu.set_style.subtitle("white", 1)# Color del subtítulo
200
+ menu.set_style.divider("blue", 1) # Color de las líneas divisorias
201
+ menu.set_style.border("yellow", 1) # Color del borde del marco de opciones
202
+ menu.set_style.options("white", 1) # Color de opciones no seleccionadas
203
+ menu.set_style.focus("green", 2) # Color y brillo de la opción resaltada
204
+
205
+ # 5. Dibujar y lanzar el menú interactivo
206
+ menu.draw(size_max: 38)
207
+ end
93
208
 
94
- menu = GRmenu([opcion_uno, opcion_dos], title="Mi menu", style=19)
95
- menu.SetStyle.Border("yellow")
96
- menu.SetStyle.Options("green")
97
- menu.draw()
209
+ main
98
210
  ```
99
211
 
100
- </details>
212
+ ---
213
+
214
+ ## 📖 Guía y Referencia Rápida en Consola (`GRmenu.help`)
215
+
216
+ Para consultar en cualquier momento la lista de helpers, colores, fuentes, marcos y sintaxis directamente desde la terminal, podés ejecutar:
217
+
218
+ ```ruby
219
+ GRmenu.help
220
+ ```
221
+
222
+ O desde una instancia:
223
+
224
+ ```ruby
225
+ menu.help
226
+ ```
101
227
 
102
228
  ---
103
229
 
@@ -112,111 +238,129 @@ menu.draw()
112
238
 
113
239
  ---
114
240
 
115
- ## 🎨 Personalización
116
-
117
- ### Colores (`set_style` / `SetStyle`)
118
-
119
- Cada zona del menú se personaliza por separado. `level: 1` es el tono normal y `level: 2` el brillante.
241
+ ## 🔤 Fuentes ASCII 3D para Banners (`font: 1` al `10`)
242
+
243
+ | ID | Estilo | Muestra (`RUBY`) |
244
+ |:--:|--------------------------|------------------|
245
+ | **`1`** | **ANSI Shadow 3D (Default)** | `██████╗ ██╗ ██╗ ██████╗ ██╗ ██╗` |
246
+ | **`2`** | **Slant 3D (FIGlet)** | ` ____ __ __ ____ __ __` |
247
+ | **`3`** | **Doom / Standard 3D** | ` ____ _ _ ____ __ __` |
248
+ | **`4`** | **Graffiti Shadow 3D** | ` ,---. ,--. ,--. ,---. ,--. ,--.` |
249
+ | **`5`** | **Small Slant / Mini 3D**| ` ___ _ _ ___ _ _` |
250
+ | **`6`** | **Modular Pipe 3D** | ` _____ _____ _____ _____` |
251
+ | **`7`** | **Bubble / Round Gothic**| ` ____ _ _ ____ _ _` |
252
+ | **`8`** | **Double-Line Wire 3D** | ` ╔═════╗ ║ ║ ╔════╗ ║ ║` |
253
+ | **`9`** | **Solid Fat 3D Block** | ` ██████▄ ██ ██ ██████▄ ██ ██` |
254
+ | **`10`**| **Arcade Stars Matrix** | ` ★★★★ ★ ★ ★★★★ ★ ★` |
120
255
 
121
- ```ruby
122
- # En Ruby:
123
- menu.set_style.border("cyan") # color del borde
124
- menu.set_style.options("white") # color de las opciones no seleccionadas
125
- menu.set_style.focus("green", 2) # color de la opción resaltada (brillante)
126
- ```
127
-
128
- Colores disponibles: `black`, `red`, `green`, `yellow`, `blue`, `magenta`, `cyan`, `white`.
129
-
130
- ### Estilos de borde (`style`)
256
+ ---
131
257
 
132
- El parámetro `style` acepta un número (1 al 20) que define cómo se dibuja el marco del menú:
258
+ ## 🖼️ Estilos de Marco (`style` / `banner_style: 1` al `20`)
133
259
 
134
260
  | `style` | Vista previa | `style` | Vista previa |
135
261
  |:---:|:---|:---:|:---|
136
262
  | 1 | `#===#` | 11 | `░░░░░` |
137
- | 2 | `┌───┐` | 12 | `█████` |
138
- | 3 | `╔═══╗` | 13 | `*****` |
139
- | 4 | `┏━━━┓` | 14 | `+++++` |
263
+ | 2 | `┌───┐` *(Línea simple)* | 12 | `█████` |
264
+ | 3 | `╔═══╗` *(Doble línea - Default banner)* | 13 | `*****` |
265
+ | 4 | `┏━━━┓` *(Línea gruesa)* | 14 | `+++++` |
140
266
  | 5 | `╒═══╕` | 15 | `=====` |
141
267
  | 6 | `╓───╖` | 16 | `~~~~~` |
142
- | 7 | `╭───╮` | 17 | `-----` |
143
- | 8 | `▛▀▀▀▜` | 18 | `◆◆◆◆◆` |
144
- | 9 | `▓▓▓▓▓` | 19 | `●●●●●` *(default)* |
145
- | 10 | `▒▒▒▒▒` | 20 | `★★★★★` |
268
+ | 7 | `╭───╮` *(Curvas redondeadas)* | 17 | `-----` |
269
+ | 8 | `▛▀▀▀▜` *(Bloques outline)* | 18 | `◆◆◆◆◆` |
270
+ | 9 | `▓▓▓▓▓` | 19 | `●○○○●` *(Círculos - Default opciones)* |
271
+ | 10 | `▒▒▒▒▒` | 20 | `★☆☆☆★` *(Estrellas)* |
146
272
 
147
- ```ruby
148
- menu = GRmenu.new([method(:opcion_uno), method(:opcion_dos)], title: "Mi menu", style: 7) # bordes redondeados
149
- ```
150
-
151
- ### Ancho del menú
273
+ ---
152
274
 
153
- `draw()` acepta `size_max` (o `min_width`), el ancho mínimo en caracteres del cuadro (se expande automáticamente si el título o las opciones son más largos):
275
+ ## 🎨 Paleta de Colores y Módulo `Color`
154
276
 
155
277
  ```ruby
156
- menu.draw(size_max: 30)
278
+ puts Color.green("Texto en verde")
279
+ puts Color.bright_cyan("Cian brillante")
280
+ puts Color.yellow("Texto en amarillo")
281
+ puts Color.bright_magenta("Magenta brillante")
282
+ puts Color.purple("Texto en morado")
283
+ puts Color.orange("Texto en naranja")
284
+ puts Color.pink("Texto en rosa")
285
+ puts Color.gray("Texto en gris")
157
286
  ```
158
287
 
288
+ Colores soportados: `black`, `gray`, `red`, `green`, `yellow`, `blue`, `magenta`, `purple`, `pink`, `cyan`, `aqua`, `orange`, `white`.
289
+
159
290
  ---
160
291
 
161
- ## 📖 Referencia de la API (Ruby)
292
+ ## 🛠️ Helpers Nativos en Modo Crudo
162
293
 
163
- ### `GRmenu.new(functions, title: "", style: 19)`
294
+ ```ruby
295
+ # 1. Limpia la pantalla al instante con secuencias ANSI
296
+ GRmenu.clear_screen # o GRmenu.clr
164
297
 
165
- | Parámetro | Tipo | Descripción |
166
- |-------------|---------------------------------------|---------------------------------------------------|
167
- | `functions` | `Array<Method, Proc, Symbol, Array>` | Métodos, procs o lambdas a mostrar como opciones. |
168
- | `title` | `String` (opcional) | Título mostrado en la cabecera del menú. |
169
- | `style` | `Integer` (opcional) | Número de estilo de borde (ver tabla arriba). |
298
+ # 2. Imprime un banner o logo gigante responsivo
299
+ GRmenu.banner("SECURE", 0, color: "magenta", style: 3, font: 1)
170
300
 
171
- ### `menu.draw(size_max: 20)`
301
+ # 3. Spinner animado en tiempo real mientras corre un bloque
302
+ GRmenu.spinner("Conectando al clúster...", color: "green") do
303
+ hacer_tarea_pesada()
304
+ end
172
305
 
173
- Dibuja el menú y bloquea el hilo hasta que el usuario elige una opción (`Enter`) o sale (`q`).
306
+ # 4. Barra de progreso porcentual dentro de un recuadro estilizado
307
+ GRmenu.progress(10, title: "Exportando Datos", color: "cyan") do |bar|
308
+ 10.times { |i| bar.advance(1, status: "Paso #{i + 1}/10") }
309
+ end
174
310
 
175
- ### `menu.set_style`
311
+ # 5. Línea divisoria horizontal adaptable
312
+ GRmenu.div(60, "blue")
176
313
 
177
- | Método | Descripción |
178
- |-------------------------------------|-------------------------------------------|
179
- | `set_style.border(color, level=1)` | Color del marco del menú. |
180
- | `set_style.options(color, level=1)` | Color de las opciones sin seleccionar. |
181
- | `set_style.focus(color, level=2)` | Color de la opción resaltada. |
314
+ # 6. Pausa de consola que espera una sola tecla en modo TTY crudo
315
+ GRmenu.continue("Presiona cualquier tecla para continuar...")
182
316
 
183
- *(Nota: también se soportan los métodos con alias `menu.SetStyle.Border(...)`, `menu.SetStyle.Options(...)`, `menu.SetStyle.Focus(...)` para compatibilidad de interfaz con la versión de Python).*
317
+ # 7. Guía interactiva en consola
318
+ GRmenu.help
319
+ ```
184
320
 
185
321
  ---
186
322
 
187
- ## 🧩 Ejemplo completo (Ruby)
323
+ ## 📖 Referencia de la API
188
324
 
189
- ```ruby
190
- require 'GRmenu'
325
+ ### `GRmenu.new(functions, ...)`
191
326
 
192
- def saludar
193
- puts "¡Hola desde Ruby!"
194
- end
327
+ | Parámetro | Tipo | Descripción |
328
+ |------------------|------------|-------------|
329
+ | `functions` | `Array` | Opciones a mostrar (`Method`, `Symbol`, `Array ["Nombre", acción, "Descripción"]`, `Proc`/`lambda`). |
330
+ | `banner:` | `String` | Texto gigante a renderizar en arte ASCII 3D arriba del menú. |
331
+ | `title:` | `String` | Título en la cabecera del marco de opciones. |
332
+ | `subtitle:` | `String` | Subtítulo o descripción (soporta múltiples líneas con `\n`). |
333
+ | `font:` | `Integer` | Fuente ASCII 3D del banner (1 al 10, default 1). |
334
+ | `style:` | `Integer` | Estilo de marco para las opciones (1 al 20, default 19). |
335
+ | `banner_style:` | `Integer` | Estilo de marco para el banner (1 al 20, default 3). |
336
+ | `divider:` | `Boolean` | Dibuja líneas divisorias a la par del ancho del banner. |
337
+ | `center:` | `Boolean` | Centra simétricamente el subtítulo y menú de opciones (default `true`). |
338
+ | `page_size:` | `Integer` | (Opcional) Número máximo de opciones visibles en pantalla para auto-paginación. |
195
339
 
196
- def salir_app
197
- puts "Hasta luego 👋"
198
- end
340
+ ### `GRmenu.spinner(message, color: "cyan", &block)`
199
341
 
200
- def acerca_de
201
- puts "GRmenu v0.1.4 — menú TTY para terminal"
202
- end
342
+ Ejecuta un bloque en segundo plano mientras dibuja una animación giratoria y muestra `✔ Mensaje ¡Listo!` al terminar.
203
343
 
204
- menu = GRmenu.new(
205
- [
206
- method(:saludar),
207
- method(:acerca_de),
208
- ["Personalizado", -> { puts "Opción con bloque lambda" }],
209
- method(:salir_app)
210
- ],
211
- title: "GRmenu Demo",
212
- style: 7
213
- )
344
+ ### `GRmenu.progress(total, title:, color:, style:, &block)`
214
345
 
215
- menu.set_style.border("magenta")
216
- menu.set_style.options("white")
217
- menu.set_style.focus("cyan", 2)
218
- menu.draw(size_max: 28)
219
- ```
346
+ Crea una barra de progreso porcentual dentro de un recuadro estilizado. El bloque recibe el objeto `bar` con los métodos `bar.advance(n, status:)` y `bar.set(valor, status:)`.
347
+
348
+ ### `menu.set_style`
349
+
350
+ | Método | Descripción |
351
+ |-------------------------------------|-------------------------------------------|
352
+ | `set_style.font(id)` | Cambia el tipo de fuente ASCII 3D (1..10). |
353
+ | `set_style.banner(color, level=2)` | Color y brillo del banner ASCII 3D. |
354
+ | `set_style.title(color, level=2)` | Color y brillo del título del marco. |
355
+ | `set_style.subtitle(color, level=1)`| Color y brillo del subtítulo. |
356
+ | `set_style.divider(color, level=1)` | Color y brillo de las líneas divisorias. |
357
+ | `set_style.border(color, level=1)` | Color y brillo del marco de opciones. |
358
+ | `set_style.options(color, level=1)` | Color y brillo de opciones no activas. |
359
+ | `set_style.focus(color, level=2)` | Color y brillo de la opción resaltada. |
360
+
361
+ ### `menu.draw(size_max: 20)`
362
+
363
+ Inicia el menú interactivo con navegación por teclado y bloquea el hilo hasta que el usuario elige una opción (`Enter`) o sale (`q`).
220
364
 
221
365
  ---
222
366
 
@@ -230,8 +374,6 @@ Las contribuciones son bienvenidas. Podés abrir un [issue](https://github.com/J
230
374
 
231
375
  Distribuido bajo licencia [MIT](LICENSE).
232
376
 
233
- ---
234
-
235
377
  <div align="center">
236
378
 
237
379
  Hecho por [grcode](https://github.com/JoseEduardoGR)
data/data/borders.json ADDED
@@ -0,0 +1,85 @@
1
+ {
2
+ "1": {
3
+ "h": "=-",
4
+ "v": "|",
5
+ "tl": "#",
6
+ "tr": "#",
7
+ "bl": "#",
8
+ "br": "#"
9
+ },
10
+ "2": {
11
+ "h": "\u2500",
12
+ "v": "\u2502",
13
+ "tl": "\u250c",
14
+ "tr": "\u2510",
15
+ "bl": "\u2514",
16
+ "br": "\u2518"
17
+ },
18
+ "3": {
19
+ "h": "\u2550",
20
+ "v": "\u2551",
21
+ "tl": "\u2554",
22
+ "tr": "\u2557",
23
+ "bl": "\u255a",
24
+ "br": "\u255d"
25
+ },
26
+ "4": {
27
+ "h": "\u2501",
28
+ "v": "\u2503",
29
+ "tl": "\u250f",
30
+ "tr": "\u2513",
31
+ "bl": "\u2517",
32
+ "br": "\u251b"
33
+ },
34
+ "5": {
35
+ "h": "\u2550",
36
+ "v": "\u2502",
37
+ "tl": "\u2552",
38
+ "tr": "\u2555",
39
+ "bl": "\u2558",
40
+ "br": "\u255b"
41
+ },
42
+ "6": {
43
+ "h": "\u2500",
44
+ "v": "\u2551",
45
+ "tl": "\u2553",
46
+ "tr": "\u2556",
47
+ "bl": "\u2559",
48
+ "br": "\u255c"
49
+ },
50
+ "7": {
51
+ "h": "\u2500",
52
+ "v": "\u2502",
53
+ "tl": "\u256d",
54
+ "tr": "\u256e",
55
+ "bl": "\u2570",
56
+ "br": "\u256f"
57
+ },
58
+ "8": {
59
+ "h": "\u2580",
60
+ "hb": "\u2584",
61
+ "v": "\u258c",
62
+ "vl": "\u258c",
63
+ "vr": "\u2590",
64
+ "tl": "\u259b",
65
+ "tr": "\u259c",
66
+ "bl": "\u2599",
67
+ "br": "\u259f"
68
+ },
69
+ "19": {
70
+ "h": "\u25cf\u25cb",
71
+ "v": "\u25cf",
72
+ "tl": "\u25cf",
73
+ "tr": "\u25cf",
74
+ "bl": "\u25cf",
75
+ "br": "\u25cf"
76
+ },
77
+ "20": {
78
+ "h": "\u2605\u2606",
79
+ "v": "\u2605",
80
+ "tl": "\u2605",
81
+ "tr": "\u2605",
82
+ "bl": "\u2605",
83
+ "br": "\u2605"
84
+ }
85
+ }
data/data/colors.json ADDED
@@ -0,0 +1,16 @@
1
+ {
2
+ "black": {"1": "30m", "2": "90m"},
3
+ "red": {"1": "31m", "2": "91m"},
4
+ "green": {"1": "32m", "2": "92m"},
5
+ "yellow": {"1": "33m", "2": "93m"},
6
+ "blue": {"1": "34m", "2": "94m"},
7
+ "magenta":{"1": "35m", "2": "95m"},
8
+ "cyan": {"1": "36m", "2": "96m"},
9
+ "white": {"1": "37m", "2": "97m"},
10
+ "gray": {"1": "90m", "2": "38;5;245m"},
11
+ "purple": {"1": "38;5;129m", "2": "38;5;141m"},
12
+ "pink": {"1": "38;5;205m", "2": "38;5;218m"},
13
+ "aqua": {"1": "38;5;45m", "2": "38;5;51m"},
14
+ "orange": {"1": "38;5;208m", "2": "38;5;214m"},
15
+ "reset": "0m"
16
+ }