Class: TuiTui::List

Inherits:
Object
  • Object
show all
Defined in:
lib/tui_tui/list.rb

Overview

Drawing companion for ScrollList. Row content comes from the caller, keeping the list domain-agnostic.

Instance Method Summary collapse

Constructor Details

#initialize(scroll) ⇒ List

Returns a new instance of List.



11
12
13
# File 'lib/tui_tui/list.rb', line 11

def initialize(scroll)
  @scroll = scroll
end

Instance Method Details

#draw(canvas, rect, highlight: nil, scrollbar: nil, auto: false) ⇒ Object



15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
# File 'lib/tui_tui/list.rb', line 15

def draw(canvas, rect, highlight: nil, scrollbar: nil, auto: false)
  # With auto:, reserve the gutter only when the content overflows the rect.
  show_bar = scrollbar && !(auto && @scroll.count <= rect.rows)
  body, gutter = show_bar ? rect.split_gutter : [rect, nil]
  @scroll.ensure_visible(body.rows)
  @scroll.each_visible(body.rows) do |index, offset|
    row = body.row + offset
    selected = index == @scroll.cursor
    canvas.fill(Rect.new(row: row, col: body.col, rows: 1, cols: body.cols), highlight) if highlight && selected
    canvas.line(row, body.col, as_line(yield(index, selected)).truncate(body.cols))
  end

  draw_scrollbar(canvas, gutter, scrollbar) if gutter
  canvas
end

#index_at(rect, event, scrollbar: nil) ⇒ Object

Map a MouseEvent to the list index under it, or nil. Pass the same ‘rect` and `scrollbar:` used for `draw` so the gutter column is excluded and the scroll offset matches what was rendered. Returns nil for clicks outside the body or below the last item.



35
36
37
38
39
40
41
# File 'lib/tui_tui/list.rb', line 35

def index_at(rect, event, scrollbar: nil)
  body = scrollbar ? rect.split_gutter.first : rect
  return nil unless body.hit?(event)

  index = @scroll.top + (event.row - body.row)
  index < @scroll.count ? index : nil
end