File: main.py

package info (click to toggle)
kitty 0.44.0-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 29,540 kB
  • sloc: ansic: 84,052; python: 57,643; objc: 5,365; sh: 1,319; xml: 364; makefile: 144; javascript: 78
file content (133 lines) | stat: -rw-r--r-- 4,871 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
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
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
#!/usr/bin/env python
# License: GPL v3 Copyright: 2018, Kovid Goyal <kovid at kovidgoyal.net>


import sys
from typing import Any

from kitty.cli import parse_args
from kitty.cli_stub import RCOptions, ResizeCLIOptions
from kitty.constants import version
from kitty.key_encoding import CTRL, EventType, KeyEvent
from kitty.rc.base import command_for_name, parse_subcommand_cli
from kitty.remote_control import encode_send, parse_rc_args
from kitty.utils import ScreenSize

from ..tui.handler import Handler
from ..tui.loop import Loop
from ..tui.operations import styled

global_opts = RCOptions()


class Resize(Handler):

    print_on_fail: str | None = None

    def __init__(self, opts: ResizeCLIOptions):
        self.opts = opts

    def initialize(self) -> None:
        global global_opts
        global_opts = parse_rc_args(['kitty', '@resize-window'])[0]
        self.original_size = self.screen_size
        self.cmd.set_cursor_visible(False)
        self.cmd.set_line_wrapping(False)
        self.draw_screen()

    def do_window_resize(self, is_decrease: bool = False, is_horizontal: bool = True, reset: bool = False, multiplier: int = 1) -> None:
        resize_window = command_for_name('resize_window')
        increment = self.opts.horizontal_increment if is_horizontal else self.opts.vertical_increment
        increment *= multiplier
        if is_decrease:
            increment *= -1
        axis = 'reset' if reset else ('horizontal' if is_horizontal else 'vertical')
        cmdline = [resize_window.name, '--self', f'--increment={increment}', '--axis=' + axis]
        opts, items = parse_subcommand_cli(resize_window, cmdline)
        payload = resize_window.message_to_kitty(global_opts, opts, items)
        send = {'cmd': resize_window.name, 'version': version, 'payload': payload, 'no_response': False}
        self.write(encode_send(send))

    def on_kitty_cmd_response(self, response: dict[str, Any]) -> None:
        if not response.get('ok'):
            err = response['error']
            if response.get('tb'):
                err += '\n' + response['tb']
            self.print_on_fail = err
            self.quit_loop(1)
            return
        res = response.get('data')
        if res:
            self.cmd.bell()

    def on_text(self, text: str, in_bracketed_paste: bool = False) -> None:
        text = text.upper()
        if text in 'WNTSR':
            self.do_window_resize(is_decrease=text in 'NS', is_horizontal=text in 'WN', reset=text == 'R')
        elif text == 'Q':
            self.quit_loop(0)

    def on_key(self, key_event: KeyEvent) -> None:
        if key_event.type is EventType.RELEASE:
            return
        if key_event.matches('esc'):
            self.quit_loop(0)
            return
        if key_event.key in ('w', 'n', 't', 's') and key_event.mods_without_locks == CTRL:
            self.do_window_resize(is_decrease=key_event.key in 'ns', is_horizontal=key_event.key in 'wn', multiplier=2)

    def on_resize(self, new_size: ScreenSize) -> None:
        self.draw_screen()

    def draw_screen(self) -> None:
        self.cmd.clear_screen()
        print = self.print
        print(styled('Resize this window', bold=True, fg='gray', fg_intense=True))
        print()
        print('Press one of the following keys:')
        print('  {}ider'.format(styled('W', fg='green')))
        print('  {}arrower'.format(styled('N', fg='green')))
        print('  {}aller'.format(styled('T', fg='green')))
        print('  {}horter'.format(styled('S', fg='green')))
        print('  {}eset'.format(styled('R', fg='red')))
        print()
        print('Press {} to quit resize mode'.format(styled('Esc', italic=True)))
        print('Hold down {} to double step size'.format(styled('Ctrl', italic=True)))
        print()
        print(styled('Sizes', bold=True, fg='white', fg_intense=True))
        print(f'Original: {self.original_size.rows} rows {self.original_size.cols} cols')
        print('Current:  {} rows {} cols'.format(
            styled(str(self.screen_size.rows), fg='magenta'), styled(str(self.screen_size.cols), fg='magenta')))


OPTIONS = r'''
--horizontal-increment
default=2
type=int
The base horizontal increment.


--vertical-increment
default=2
type=int
The base vertical increment.
'''.format


def main(args: list[str]) -> None:
    msg = 'Resize the current window'
    try:
        cli_opts, items = parse_args(args[1:], OPTIONS, '', msg, 'resize_window', result_class=ResizeCLIOptions)
    except SystemExit as e:
        if e.code != 0:
            print(e.args[0], file=sys.stderr)
            input('Press Enter to quit')
        return

    loop = Loop()
    handler = Resize(cli_opts)
    loop.loop(handler)
    if handler.print_on_fail:
        print(handler.print_on_fail, file=sys.stderr)
        input('Press Enter to quit')
    raise SystemExit(loop.return_code)