Class: HackerTerm::UI

Inherits:
Object
  • Object
show all
Includes:
Curses
Defined in:
lib/hacker_term/ui.rb

Instance Method Summary collapse

Constructor Details

#initialize(opts = {}) ⇒ UI

Returns a new instance of UI.



7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
# File 'lib/hacker_term/ui.rb', line 7

def initialize(opts={})

  opts = defaults.merge(opts) # Ununsed for now

  raw # Intercept everything
  noecho # Do not echo user input to stdout
  stdscr.keypad(true) # Enable arrows

  if can_change_color?
    start_color
    # foreground / background colours
    init_pair(0, COLOR_WHITE, COLOR_BLACK)
    init_pair(1, COLOR_WHITE, COLOR_BLUE)
    init_pair(2, COLOR_WHITE, COLOR_RED)
    init_pair(3, COLOR_BLACK, COLOR_GREEN)
  end

  @total_width = cols
  @total_height = lines
  @padding_left = 2
  @title_width = 0
  @cols  = ['rank', 'title', 'score', 'comments']
  @line_num = -1

  clear!
end

Instance Method Details

#clear!Object



142
143
144
145
# File 'lib/hacker_term/ui.rb', line 142

def clear!
  setpos(0, 0)
  clear
end

#closeObject



138
139
140
# File 'lib/hacker_term/ui.rb', line 138

def close
  close_screen
end


73
74
75
76
77
78
79
80
# File 'lib/hacker_term/ui.rb', line 73

def draw_footer(sorted_by, mean, median, mode)
  output_divider(next_line_num) 
  attrset color_pair(1)
  formatted = sprintf("Sorted by: %7s | Scores: Mean: %4.2f | Median: %4.2f | Mode: %4.2f", 
    sorted_by, mean, median, mode)
  output_line(next_line_num, formatted)
  output_divider(next_line_num) 
end

#draw_headerObject



51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
# File 'lib/hacker_term/ui.rb', line 51

def draw_header
  output_divider(next_line_num) 
  attrset color_pair(1)
  output_line(next_line_num, "HACKER NEWS TERMINAL - thanks to http://hndroidapi.appspot.com") 
  output_line(next_line_num, "CMDS: Select (Arrows), Open Item (O), Open Item Discussion (D), Refresh (A)")
  output_line(next_line_num, "CMDS CONT: Sort by Rank (R), Score (S), Comments (C), Title (T) | Quit (Q)")
  output_divider(next_line_num) 

  # Get width_excl_title, i.e. width of all columns + some extra for |'s and spacing.
  # Once obtained, pad out the title column with the any width remaining
  # A nicer way to do this is always put the title last, and assume last column gets
  # remaining width. That way we can just loop through our cols, rather than hardcoding
  # them as per example below. I'm sticking to this because I want the title listed second.
  width_excl_title = @cols.inject(0) do |width, col| 
    width += (3 + col.length)
  end
  attrset color_pair(2)
  @title_width = @total_width - width_excl_title + 'title'.length
  output_line(next_line_num, "RANK | TITLE " + " " * (@total_width - width_excl_title) + "| SCORE | COMMENTS")
  output_divider(next_line_num) 
end

#draw_item_line(rank, data, selected) ⇒ Object



82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
# File 'lib/hacker_term/ui.rb', line 82

def draw_item_line(rank, data, selected)

  begin
    # Truncate if too long
    title = truncate_line! data

    # Format and output
    if selected
      rank = '> ' + rank
      attrset color_pair(3)
    else
      attrset color_pair(0)
    end

    formatted = sprintf("%4s | %-#{@title_width}s | %5s | %8s", rank, title, data['score'], data['comments'])
    output_line(next_line_num, formatted)
  rescue => ex
    p "error: #{ex.to_s}"
  end
end

#get_charObject



123
124
125
# File 'lib/hacker_term/ui.rb', line 123

def get_char
  interpret_char(getch)
end

#interpret_char(c) ⇒ Object



127
128
129
130
131
132
133
134
135
136
# File 'lib/hacker_term/ui.rb', line 127

def interpret_char(c)
  case c
  when Curses::Key::UP
    'up'
  when Curses::Key::DOWN
    'down'
  else
    c
  end
end

#next_line_numObject



34
35
36
# File 'lib/hacker_term/ui.rb', line 34

def next_line_num
  @line_num += 1
end

#output_divider(line_num) ⇒ Object



45
46
47
48
49
# File 'lib/hacker_term/ui.rb', line 45

def output_divider(line_num)
  setpos(line_num, 0)
  attrset color_pair(0)
  addstr('-' * @total_width)
end

#output_line(line_num, data) ⇒ Object



38
39
40
41
42
43
# File 'lib/hacker_term/ui.rb', line 38

def output_line(line_num, data)
  setpos(line_num, 0)
  padding_right = @total_width - data.length - @padding_left
  padding_right = 0 if padding_right < 0  
  addstr((" " * @padding_left) + data + (" " * padding_right))
end

#show(page_data) ⇒ Object



108
109
110
111
112
113
114
115
116
117
118
119
120
121
# File 'lib/hacker_term/ui.rb', line 108

def show(page_data)
  draw_header

  page_data.data.each_index do |i| 
    line_data = page_data.data.fetch(i)
    draw_item_line(line_data['rank'], line_data, page_data.line_pos == i + 1) 
  end

  draw_footer(page_data.sorted_by, 
    page_data.mean_score, 
    page_data.median_score, 
    page_data.mode_score
  )
end

#truncate_line!(data) ⇒ Object



103
104
105
106
# File 'lib/hacker_term/ui.rb', line 103

def truncate_line!(data)
  return data['title'][0, @title_width - 3] + '...' if data['title'].length >= @title_width
  data['title']
end