1 # frozen_string_literal: true
4 # Outputs code with highlighted lines
6 # Whatever is passed to this class will be rendered
7 # even if it is "marked invisible" any filtering of
8 # output should be done before calling this class.
10 # DisplayCodeWithLineNumbers.new(
12 # highlight_lines: [lines[2], lines[3]]
21 class DisplayCodeWithLineNumbers
22 TERMINAL_HIGHLIGHT = "\e[1;3m" # Bold, italics
23 TERMINAL_END = "\e[0m"
25 def initialize(lines:, highlight_lines: [], terminal: false)
26 @lines = Array(lines).sort
28 @highlight_line_hash = Array(highlight_lines).each_with_object({}) { |line, h| h[line] = true }
29 @digit_count = @lines.last&.line_number.to_s.length
38 private def format_line(code_line)
39 # Handle trailing slash lines
40 code_line.original.lines.map.with_index do |contents, i|
42 empty: code_line.empty?,
43 number: (code_line.number + i).to_s,
45 highlight: @highlight_line_hash[code_line]
50 private def format(contents:, number:, empty:, highlight: false)
52 string << if highlight
58 string << number.rjust(@digit_count).to_s
63 string << TERMINAL_HIGHLIGHT if @terminal && highlight
65 string << TERMINAL_END if @terminal