123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145 |
- # Copyright 2024 Henrique Paone
- #
- # This file is part of Kitty-Tui.
- #
- # Kitty-Tui is free software: you can redistribute it and/or modify it under the
- # terms of the GNU General Public License as published by the Free Software
- # Foundation, either version 3 of the License, or (at your option) any later
- # version.
- #
- # Kitty-Tui is distributed in the hope that it will be useful, but WITHOUT ANY
- # WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
- # PARTICULAR PURPOSE. See the GNU General Public License for more details.
- #
- # You should have received a copy of the GNU General Public License along with
- # Kitty-Tui. If not, see <https://www.gnu.org/licenses/>.
- require_relative './tables.rb'
- module Kitty
- # Note: The order of these two constants are important for the translate_bits
- # function. Do not change it
- Modifiers = [ 'A', '', 'T', 'C', 'A', 'S']
- Kitty_flags = {
- :associated_text => 16,
- :all_escaped => 8,
- :alternate_keys => 4,
- :event_types => 2,
- :disambiguate_escape_codes => 1
- }
-
- Kitty_builtin_regex = /\x1b\]133;[ABC]\x1b\\/
- # Fetch and parse KITTY_PIPE_DATA set by kitty
- def get_kitty_data
- kitty_data = /(\d+):(\d+,?\d+):(\d+,?\d+)/.match ENV['KITTY_PIPE_DATA']
- scrolled = kitty_data[1].to_i
- cline, ccol = kitty_data[2].split(',').reverse.map! do |e| e.to_i end
- lines, cols = kitty_data[3].split(',').map! do |e| e.to_i end
- { scrolled: scrolled, cline: cline, ccol: ccol, lines: lines, cols: cols }
- end
-
- def hi_line(line, cstart, cend, color)
- printf "\e[2*x\e[%d;%d;%d;%d;48;5;#{ color }$r\e[*x", line, cstart, line, cend, color
- end
-
- def unscroll(amt)
- print "\e[#{ amt }+T"
- end
-
- def translate_bits(num, reference_array)
- translation = []
- bits = num.bit_length
- reference = reference_array.last(bits).reverse
- bits.downto 0 do |i|
- translation << reference[i] if num[i] == 1
- end
- translation
- end
-
- def kitty_query_keyboard_flags
- print "\e[?u"
- flags = translate_bits(get_escaped.first[1..-1].to_i, Kitty_flags.values)
- enabled = []
- Kitty_flags.each_pair do |k, v|
- enabled << k if flags.include?(v)
- end
- enabled
- end
-
- def kitty_keyboard_enable(*options)
- flags = []
- options.each do |opts|
- flags << Kitty_flags[opts ]if Kitty_flags.include? opts
- end
- print "\e[>#{ flags.sum }u"
- end
- def kitty_restore
- print "\e[<u"
- end
-
- # gets an escaped sequence terminated in either u or ~. this is specially
- # useful for getting input when using the flag disambiguate_escape_codes
- def get_escaped
- is_arrow = false
- escaped = ''
- loop do
- c = STDIN.getch
- break if ['u', '~'].include? c
- escaped += c
- if ('A'..'D').include? c
- is_arrow = true
- break
- end
- end
- has_mod = escaped.count(';') >= 1
- escaped =
- if is_arrow and has_mod
- escaped[(escaped.index(';') + 1..-1)].insert 1, ';'
- else escaped[2..-1]
- end.split ';'
- if is_arrow and has_mod
- escaped[0] = escaped[0].to_i
- escaped.reverse!
- end
- escaped
- end
- # This converts an escaped sequence using vi-like notation, for example, if
- # the user press ctrl+t, the function outputs <C-t>. Note that this requires
- # the disambiguate_escape_codes flag to be set in kitty
- def parse_escaped(escaped)
- ignore_shift = is_letter = false
- codepoint, mods, assoc_codep = escaped
- mods = mods.to_i - 1
- return nil if Ignore.include? codepoint
-
- key = if Functional_keys.include? codepoint
- Functional_keys[codepoint]
- else
- is_letter = true
- if codepoint == assoc_codep or assoc_codep.nil?
- '' << codepoint.to_i
- else
- ignore_shift = true
- '' << assoc_codep.to_i
- end
- end
- modifiers = []
- unless mods < 1
- modifiers = translate_bits(mods, Modifiers)
- modifiers.delete 'S' if ignore_shift
- end
-
- if modifiers.empty?
- is_letter ? key : "<#{ key }>"
- else
- "<#{ modifiers.join '-' }-#{ key }>"
- end
- end
- end
|