summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTOMITA Masahiro <tommy@tmtm.org>2021-09-26 15:39:45 +0900
committergit <svn-admin@ruby-lang.org>2021-10-03 14:26:53 +0900
commitef350b3a5645a97270cbc72356eba671a1a41c20 (patch)
treea3c3d7ad0374e112e3a202688227a2b6ed7e07e8
parent2a3d0fbe172d52be9a64e0bd366c5f74177bd881 (diff)
[ruby/reline] Simplify SIGWINCH handler to avoid aborting when resizing.
https://github.com/ruby/reline/commit/481add0537
-rw-r--r--lib/reline/ansi.rb4
-rw-r--r--lib/reline/line_editor.rb75
2 files changed, 43 insertions, 36 deletions
diff --git a/lib/reline/ansi.rb b/lib/reline/ansi.rb
index f34d0b53fe..ae6961e29f 100644
--- a/lib/reline/ansi.rb
+++ b/lib/reline/ansi.rb
@@ -126,8 +126,8 @@ class Reline::ANSI
unless @@buf.empty?
return @@buf.shift
end
- until c = @@input.raw(intr: true, &:getbyte)
- sleep 0.1
+ until c = @@input.raw(intr: true) { select([@@input], [], [], 0.1) && @@input.getbyte }
+ Reline.core.line_editor.resize
end
(c == 0x16 && @@input.raw(min: 0, tim: 0, &:getbyte)) || c
rescue Errno::EIO
diff --git a/lib/reline/line_editor.rb b/lib/reline/line_editor.rb
index f041233df4..afb0b49f1c 100644
--- a/lib/reline/line_editor.rb
+++ b/lib/reline/line_editor.rb
@@ -178,43 +178,49 @@ class Reline::LineEditor
rescue ArgumentError
end
Reline::IOGate.set_winch_handler do
- @rest_height = (Reline::IOGate.get_screen_size.first - 1) - Reline::IOGate.cursor_pos.y
- old_screen_size = @screen_size
- @screen_size = Reline::IOGate.get_screen_size
- @screen_height = @screen_size.first
- if old_screen_size.last < @screen_size.last # columns increase
- @rerender_all = true
- rerender
- else
- back = 0
- new_buffer = whole_lines
- prompt, prompt_width, prompt_list = check_multiline_prompt(new_buffer, prompt)
- new_buffer.each_with_index do |line, index|
- prompt_width = calculate_width(prompt_list[index], true) if @prompt_proc
- width = prompt_width + calculate_width(line)
- height = calculate_height_by_width(width)
- back += height
- end
- @highest_in_all = back
- @highest_in_this = calculate_height_by_width(prompt_width + @cursor_max)
- @first_line_started_from =
- if @line_index.zero?
- 0
- else
- calculate_height_by_lines(@buffer_of_lines[0..(@line_index - 1)], prompt_list || prompt)
- end
- if @prompt_proc
- prompt = prompt_list[@line_index]
- prompt_width = calculate_width(prompt, true)
+ @resized = true
+ end
+ @block_elem_width = Reline::Unicode.calculate_width('█')
+ end
+
+ def resize
+ return unless @resized
+ @resized = false
+ @rest_height = (Reline::IOGate.get_screen_size.first - 1) - Reline::IOGate.cursor_pos.y
+ old_screen_size = @screen_size
+ @screen_size = Reline::IOGate.get_screen_size
+ @screen_height = @screen_size.first
+ if old_screen_size.last < @screen_size.last # columns increase
+ @rerender_all = true
+ rerender
+ else
+ back = 0
+ new_buffer = whole_lines
+ prompt, prompt_width, prompt_list = check_multiline_prompt(new_buffer, prompt)
+ new_buffer.each_with_index do |line, index|
+ prompt_width = calculate_width(prompt_list[index], true) if @prompt_proc
+ width = prompt_width + calculate_width(line)
+ height = calculate_height_by_width(width)
+ back += height
+ end
+ @highest_in_all = back
+ @highest_in_this = calculate_height_by_width(prompt_width + @cursor_max)
+ @first_line_started_from =
+ if @line_index.zero?
+ 0
+ else
+ calculate_height_by_lines(@buffer_of_lines[0..(@line_index - 1)], prompt_list || prompt)
end
- calculate_nearest_cursor
- @started_from = calculate_height_by_width(prompt_width + @cursor) - 1
- Reline::IOGate.move_cursor_column((prompt_width + @cursor) % @screen_size.last)
- @highest_in_this = calculate_height_by_width(prompt_width + @cursor_max)
- @rerender_all = true
+ if @prompt_proc
+ prompt = prompt_list[@line_index]
+ prompt_width = calculate_width(prompt, true)
end
+ calculate_nearest_cursor
+ @started_from = calculate_height_by_width(prompt_width + @cursor) - 1
+ Reline::IOGate.move_cursor_column((prompt_width + @cursor) % @screen_size.last)
+ @highest_in_this = calculate_height_by_width(prompt_width + @cursor_max)
+ @rerender_all = true
end
- @block_elem_width = Reline::Unicode.calculate_width('█')
end
def finalize
@@ -264,6 +270,7 @@ class Reline::LineEditor
@auto_indent_proc = nil
@dialogs = []
@last_key = nil
+ @resized = false
reset_line
end