How to Use (N)Curses in Ruby

How do I use (n)curses in Ruby?

You might be able to get some implementation ideas from the Ruby/ProgressBar library, which generates text progress bars. I stumbled across it a couple of months back but haven't made any use of it.

Creating a menu with curses

there is no need for threads in your example.

you can see how this can be done here: https://gist.github.com/phoet/6988038

require "curses"
include Curses

init_screen
start_color
noecho

def draw_menu(menu, active_index=nil)
4.times do |i|
menu.setpos(i + 1, 1)
menu.attrset(i == active_index ? A_STANDOUT : A_NORMAL)
menu.addstr "item_#{i}"
end
end

def draw_info(menu, text)
menu.setpos(1, 10)
menu.attrset(A_NORMAL)
menu.addstr text
end

position = 0

menu = Window.new(7,40,7,2)
menu.box('|', '-')
draw_menu(menu, position)
while ch = menu.getch
case ch
when 'w'
draw_info menu, 'move up'
position -= 1
when 's'
draw_info menu, 'move down'
position += 1
when 'x'
exit
end
position = 3 if position < 0
position = 0 if position > 3
draw_menu(menu, position)
end

Ruby curses: how to get pure white

Most of the terminals which implement "ANSI color" use a more intense foreground color when told to render bold. But there is no corresponding workaround for the background.

However, the majority of these also implement SGR 39 and SGR 49, which reset the foreground and background to its "default" colors. Using that would get your original terminal background (which is likely what you want). That is a feature of ncurses called use_default_colors, which I see is available in ruby.

Using that feature, your example would

  • call the Curses.use_default_colors method,
  • not bother (for example) to create a color pair, since the default pair 0 would draw using the terminal's default colors.
  • other color pairs (1 through the maximum number of pairs) would work just like regular curses.

The example given uses color pair 1. If you were using the default-colors extension, you could initialize Curses with the use_default_colors method. Then, using the default color pair 0, you would see on most terminals the original terminal colors. This method is from the underlying ncurses library irregardless of whether the Ruby package is called "curses" or "ncurses".

Color pair 0 is special (see manpage). It cannot be set to specific colors by your application. As an extension, ncurses provides a way to alter this in a useful way.

Ruby curses colors

There are examples of curses usage in the ruby source code, see, e.g. here.

Your code could be something like:

require 'curses'
include Curses

Curses.noecho # do not show typed keys
Curses.init_screen
Curses.stdscr.keypad(true) # enable arrow keys (required for pageup/down)
Curses.start_color
# Determines the colors in the 'attron' below
Curses.init_pair(COLOR_BLUE,COLOR_BLUE,COLOR_BLACK)
Curses.init_pair(COLOR_RED,COLOR_RED,COLOR_BLACK)

loop do

case Curses.getch

when Curses::Key::PPAGE
Curses.clear
Curses.setpos(0,0)
# Use colors defined color_init
Curses.attron(color_pair(COLOR_RED)|A_NORMAL){
Curses.addstr("Page Up")
}
when Curses::Key::NPAGE
Curses.clear
Curses.setpos(0,0)
Curses.attron(color_pair(COLOR_BLUE)|A_NORMAL){
Curses.addstr("Page Down")
}
end
end

Getting 256 colors out of ruby-ncurses

njsf: You were partially right here, and after tinkering a lot more I eventually got it to work. Thanks for your help. The story: XTerm (and rxvt, and Eterm) support 256 colors via escape sequences (what I was seeing) but 'tput colors' will say '8' and ncurses won't be able to get at them, because ncurses is playing nice and attempting to access via terminfo.

For the benefit of anyone with similar pain:

I found I need to install the ncurses-term (Ubuntu) package to get /lib/terminfo/x/xterm-256color and other 256-color terminfo files. Then I set my TERM to xterm-256color and added the line '*customization: -color' to my ~/.Xdefaults, ran 'xrdb -merge ~/.Xdefaults' to load it, and from then on I have proper 256 color support in new xterms.



Related Topics



Leave a reply



Submit