add perl5 support to Vx6.9 for openssl-3.1.7 (#1)
Reviewed-on: http://13.234.246.121:3000/Neominds/ossl35vx69/pulls/1 Reviewed-by: Jayesh Babu <jayesh@neominds.in> Co-authored-by: siddhant <siddhant.singh@neominds.in> Co-committed-by: siddhant <siddhant.singh@neominds.in>
This commit is contained in:
@@ -0,0 +1,101 @@
|
||||
"""curses
|
||||
|
||||
The main package for curses support for Python. Normally used by importing
|
||||
the package, and perhaps a particular module inside it.
|
||||
|
||||
import curses
|
||||
from curses import textpad
|
||||
curses.initscr()
|
||||
...
|
||||
|
||||
"""
|
||||
|
||||
from _curses import *
|
||||
import os as _os
|
||||
import sys as _sys
|
||||
|
||||
# Some constants, most notably the ACS_* ones, are only added to the C
|
||||
# _curses module's dictionary after initscr() is called. (Some
|
||||
# versions of SGI's curses don't define values for those constants
|
||||
# until initscr() has been called.) This wrapper function calls the
|
||||
# underlying C initscr(), and then copies the constants from the
|
||||
# _curses module to the curses package's dictionary. Don't do 'from
|
||||
# curses import *' if you'll be needing the ACS_* constants.
|
||||
|
||||
def initscr():
|
||||
import _curses, curses
|
||||
# we call setupterm() here because it raises an error
|
||||
# instead of calling exit() in error cases.
|
||||
setupterm(term=_os.environ.get("TERM", "unknown"),
|
||||
fd=_sys.__stdout__.fileno())
|
||||
stdscr = _curses.initscr()
|
||||
for key, value in _curses.__dict__.items():
|
||||
if key[0:4] == 'ACS_' or key in ('LINES', 'COLS'):
|
||||
setattr(curses, key, value)
|
||||
|
||||
return stdscr
|
||||
|
||||
# This is a similar wrapper for start_color(), which adds the COLORS and
|
||||
# COLOR_PAIRS variables which are only available after start_color() is
|
||||
# called.
|
||||
|
||||
def start_color():
|
||||
import _curses, curses
|
||||
retval = _curses.start_color()
|
||||
if hasattr(_curses, 'COLORS'):
|
||||
curses.COLORS = _curses.COLORS
|
||||
if hasattr(_curses, 'COLOR_PAIRS'):
|
||||
curses.COLOR_PAIRS = _curses.COLOR_PAIRS
|
||||
return retval
|
||||
|
||||
# Import Python has_key() implementation if _curses doesn't contain has_key()
|
||||
|
||||
try:
|
||||
has_key
|
||||
except NameError:
|
||||
from .has_key import has_key
|
||||
|
||||
# Wrapper for the entire curses-based application. Runs a function which
|
||||
# should be the rest of your curses-based application. If the application
|
||||
# raises an exception, wrapper() will restore the terminal to a sane state so
|
||||
# you can read the resulting traceback.
|
||||
|
||||
def wrapper(func, /, *args, **kwds):
|
||||
"""Wrapper function that initializes curses and calls another function,
|
||||
restoring normal keyboard/screen behavior on error.
|
||||
The callable object 'func' is then passed the main window 'stdscr'
|
||||
as its first argument, followed by any other arguments passed to
|
||||
wrapper().
|
||||
"""
|
||||
|
||||
try:
|
||||
# Initialize curses
|
||||
stdscr = initscr()
|
||||
|
||||
# Turn off echoing of keys, and enter cbreak mode,
|
||||
# where no buffering is performed on keyboard input
|
||||
noecho()
|
||||
cbreak()
|
||||
|
||||
# In keypad mode, escape sequences for special keys
|
||||
# (like the cursor keys) will be interpreted and
|
||||
# a special value like curses.KEY_LEFT will be returned
|
||||
stdscr.keypad(1)
|
||||
|
||||
# Start color, too. Harmless if the terminal doesn't have
|
||||
# color; user can test with has_color() later on. The try/catch
|
||||
# works around a minor bit of over-conscientiousness in the curses
|
||||
# module -- the error return from C start_color() is ignorable.
|
||||
try:
|
||||
start_color()
|
||||
except:
|
||||
pass
|
||||
|
||||
return func(stdscr, *args, **kwds)
|
||||
finally:
|
||||
# Set everything back to normal
|
||||
if 'stdscr' in locals():
|
||||
stdscr.keypad(0)
|
||||
echo()
|
||||
nocbreak()
|
||||
endwin()
|
||||
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
@@ -0,0 +1,99 @@
|
||||
"""Constants and membership tests for ASCII characters"""
|
||||
|
||||
NUL = 0x00 # ^@
|
||||
SOH = 0x01 # ^A
|
||||
STX = 0x02 # ^B
|
||||
ETX = 0x03 # ^C
|
||||
EOT = 0x04 # ^D
|
||||
ENQ = 0x05 # ^E
|
||||
ACK = 0x06 # ^F
|
||||
BEL = 0x07 # ^G
|
||||
BS = 0x08 # ^H
|
||||
TAB = 0x09 # ^I
|
||||
HT = 0x09 # ^I
|
||||
LF = 0x0a # ^J
|
||||
NL = 0x0a # ^J
|
||||
VT = 0x0b # ^K
|
||||
FF = 0x0c # ^L
|
||||
CR = 0x0d # ^M
|
||||
SO = 0x0e # ^N
|
||||
SI = 0x0f # ^O
|
||||
DLE = 0x10 # ^P
|
||||
DC1 = 0x11 # ^Q
|
||||
DC2 = 0x12 # ^R
|
||||
DC3 = 0x13 # ^S
|
||||
DC4 = 0x14 # ^T
|
||||
NAK = 0x15 # ^U
|
||||
SYN = 0x16 # ^V
|
||||
ETB = 0x17 # ^W
|
||||
CAN = 0x18 # ^X
|
||||
EM = 0x19 # ^Y
|
||||
SUB = 0x1a # ^Z
|
||||
ESC = 0x1b # ^[
|
||||
FS = 0x1c # ^\
|
||||
GS = 0x1d # ^]
|
||||
RS = 0x1e # ^^
|
||||
US = 0x1f # ^_
|
||||
SP = 0x20 # space
|
||||
DEL = 0x7f # delete
|
||||
|
||||
controlnames = [
|
||||
"NUL", "SOH", "STX", "ETX", "EOT", "ENQ", "ACK", "BEL",
|
||||
"BS", "HT", "LF", "VT", "FF", "CR", "SO", "SI",
|
||||
"DLE", "DC1", "DC2", "DC3", "DC4", "NAK", "SYN", "ETB",
|
||||
"CAN", "EM", "SUB", "ESC", "FS", "GS", "RS", "US",
|
||||
"SP"
|
||||
]
|
||||
|
||||
def _ctoi(c):
|
||||
if type(c) == type(""):
|
||||
return ord(c)
|
||||
else:
|
||||
return c
|
||||
|
||||
def isalnum(c): return isalpha(c) or isdigit(c)
|
||||
def isalpha(c): return isupper(c) or islower(c)
|
||||
def isascii(c): return 0 <= _ctoi(c) <= 127 # ?
|
||||
def isblank(c): return _ctoi(c) in (9, 32)
|
||||
def iscntrl(c): return 0 <= _ctoi(c) <= 31 or _ctoi(c) == 127
|
||||
def isdigit(c): return 48 <= _ctoi(c) <= 57
|
||||
def isgraph(c): return 33 <= _ctoi(c) <= 126
|
||||
def islower(c): return 97 <= _ctoi(c) <= 122
|
||||
def isprint(c): return 32 <= _ctoi(c) <= 126
|
||||
def ispunct(c): return isgraph(c) and not isalnum(c)
|
||||
def isspace(c): return _ctoi(c) in (9, 10, 11, 12, 13, 32)
|
||||
def isupper(c): return 65 <= _ctoi(c) <= 90
|
||||
def isxdigit(c): return isdigit(c) or \
|
||||
(65 <= _ctoi(c) <= 70) or (97 <= _ctoi(c) <= 102)
|
||||
def isctrl(c): return 0 <= _ctoi(c) < 32
|
||||
def ismeta(c): return _ctoi(c) > 127
|
||||
|
||||
def ascii(c):
|
||||
if type(c) == type(""):
|
||||
return chr(_ctoi(c) & 0x7f)
|
||||
else:
|
||||
return _ctoi(c) & 0x7f
|
||||
|
||||
def ctrl(c):
|
||||
if type(c) == type(""):
|
||||
return chr(_ctoi(c) & 0x1f)
|
||||
else:
|
||||
return _ctoi(c) & 0x1f
|
||||
|
||||
def alt(c):
|
||||
if type(c) == type(""):
|
||||
return chr(_ctoi(c) | 0x80)
|
||||
else:
|
||||
return _ctoi(c) | 0x80
|
||||
|
||||
def unctrl(c):
|
||||
bits = _ctoi(c)
|
||||
if bits == 0x7f:
|
||||
rep = "^?"
|
||||
elif isprint(bits & 0x7f):
|
||||
rep = chr(bits & 0x7f)
|
||||
else:
|
||||
rep = "^" + chr(((bits & 0x7f) | 0x20) + 0x20)
|
||||
if bits & 0x80:
|
||||
return "!" + rep
|
||||
return rep
|
||||
@@ -0,0 +1,192 @@
|
||||
|
||||
#
|
||||
# Emulation of has_key() function for platforms that don't use ncurses
|
||||
#
|
||||
|
||||
import _curses
|
||||
|
||||
# Table mapping curses keys to the terminfo capability name
|
||||
|
||||
_capability_names = {
|
||||
_curses.KEY_A1: 'ka1',
|
||||
_curses.KEY_A3: 'ka3',
|
||||
_curses.KEY_B2: 'kb2',
|
||||
_curses.KEY_BACKSPACE: 'kbs',
|
||||
_curses.KEY_BEG: 'kbeg',
|
||||
_curses.KEY_BTAB: 'kcbt',
|
||||
_curses.KEY_C1: 'kc1',
|
||||
_curses.KEY_C3: 'kc3',
|
||||
_curses.KEY_CANCEL: 'kcan',
|
||||
_curses.KEY_CATAB: 'ktbc',
|
||||
_curses.KEY_CLEAR: 'kclr',
|
||||
_curses.KEY_CLOSE: 'kclo',
|
||||
_curses.KEY_COMMAND: 'kcmd',
|
||||
_curses.KEY_COPY: 'kcpy',
|
||||
_curses.KEY_CREATE: 'kcrt',
|
||||
_curses.KEY_CTAB: 'kctab',
|
||||
_curses.KEY_DC: 'kdch1',
|
||||
_curses.KEY_DL: 'kdl1',
|
||||
_curses.KEY_DOWN: 'kcud1',
|
||||
_curses.KEY_EIC: 'krmir',
|
||||
_curses.KEY_END: 'kend',
|
||||
_curses.KEY_ENTER: 'kent',
|
||||
_curses.KEY_EOL: 'kel',
|
||||
_curses.KEY_EOS: 'ked',
|
||||
_curses.KEY_EXIT: 'kext',
|
||||
_curses.KEY_F0: 'kf0',
|
||||
_curses.KEY_F1: 'kf1',
|
||||
_curses.KEY_F10: 'kf10',
|
||||
_curses.KEY_F11: 'kf11',
|
||||
_curses.KEY_F12: 'kf12',
|
||||
_curses.KEY_F13: 'kf13',
|
||||
_curses.KEY_F14: 'kf14',
|
||||
_curses.KEY_F15: 'kf15',
|
||||
_curses.KEY_F16: 'kf16',
|
||||
_curses.KEY_F17: 'kf17',
|
||||
_curses.KEY_F18: 'kf18',
|
||||
_curses.KEY_F19: 'kf19',
|
||||
_curses.KEY_F2: 'kf2',
|
||||
_curses.KEY_F20: 'kf20',
|
||||
_curses.KEY_F21: 'kf21',
|
||||
_curses.KEY_F22: 'kf22',
|
||||
_curses.KEY_F23: 'kf23',
|
||||
_curses.KEY_F24: 'kf24',
|
||||
_curses.KEY_F25: 'kf25',
|
||||
_curses.KEY_F26: 'kf26',
|
||||
_curses.KEY_F27: 'kf27',
|
||||
_curses.KEY_F28: 'kf28',
|
||||
_curses.KEY_F29: 'kf29',
|
||||
_curses.KEY_F3: 'kf3',
|
||||
_curses.KEY_F30: 'kf30',
|
||||
_curses.KEY_F31: 'kf31',
|
||||
_curses.KEY_F32: 'kf32',
|
||||
_curses.KEY_F33: 'kf33',
|
||||
_curses.KEY_F34: 'kf34',
|
||||
_curses.KEY_F35: 'kf35',
|
||||
_curses.KEY_F36: 'kf36',
|
||||
_curses.KEY_F37: 'kf37',
|
||||
_curses.KEY_F38: 'kf38',
|
||||
_curses.KEY_F39: 'kf39',
|
||||
_curses.KEY_F4: 'kf4',
|
||||
_curses.KEY_F40: 'kf40',
|
||||
_curses.KEY_F41: 'kf41',
|
||||
_curses.KEY_F42: 'kf42',
|
||||
_curses.KEY_F43: 'kf43',
|
||||
_curses.KEY_F44: 'kf44',
|
||||
_curses.KEY_F45: 'kf45',
|
||||
_curses.KEY_F46: 'kf46',
|
||||
_curses.KEY_F47: 'kf47',
|
||||
_curses.KEY_F48: 'kf48',
|
||||
_curses.KEY_F49: 'kf49',
|
||||
_curses.KEY_F5: 'kf5',
|
||||
_curses.KEY_F50: 'kf50',
|
||||
_curses.KEY_F51: 'kf51',
|
||||
_curses.KEY_F52: 'kf52',
|
||||
_curses.KEY_F53: 'kf53',
|
||||
_curses.KEY_F54: 'kf54',
|
||||
_curses.KEY_F55: 'kf55',
|
||||
_curses.KEY_F56: 'kf56',
|
||||
_curses.KEY_F57: 'kf57',
|
||||
_curses.KEY_F58: 'kf58',
|
||||
_curses.KEY_F59: 'kf59',
|
||||
_curses.KEY_F6: 'kf6',
|
||||
_curses.KEY_F60: 'kf60',
|
||||
_curses.KEY_F61: 'kf61',
|
||||
_curses.KEY_F62: 'kf62',
|
||||
_curses.KEY_F63: 'kf63',
|
||||
_curses.KEY_F7: 'kf7',
|
||||
_curses.KEY_F8: 'kf8',
|
||||
_curses.KEY_F9: 'kf9',
|
||||
_curses.KEY_FIND: 'kfnd',
|
||||
_curses.KEY_HELP: 'khlp',
|
||||
_curses.KEY_HOME: 'khome',
|
||||
_curses.KEY_IC: 'kich1',
|
||||
_curses.KEY_IL: 'kil1',
|
||||
_curses.KEY_LEFT: 'kcub1',
|
||||
_curses.KEY_LL: 'kll',
|
||||
_curses.KEY_MARK: 'kmrk',
|
||||
_curses.KEY_MESSAGE: 'kmsg',
|
||||
_curses.KEY_MOVE: 'kmov',
|
||||
_curses.KEY_NEXT: 'knxt',
|
||||
_curses.KEY_NPAGE: 'knp',
|
||||
_curses.KEY_OPEN: 'kopn',
|
||||
_curses.KEY_OPTIONS: 'kopt',
|
||||
_curses.KEY_PPAGE: 'kpp',
|
||||
_curses.KEY_PREVIOUS: 'kprv',
|
||||
_curses.KEY_PRINT: 'kprt',
|
||||
_curses.KEY_REDO: 'krdo',
|
||||
_curses.KEY_REFERENCE: 'kref',
|
||||
_curses.KEY_REFRESH: 'krfr',
|
||||
_curses.KEY_REPLACE: 'krpl',
|
||||
_curses.KEY_RESTART: 'krst',
|
||||
_curses.KEY_RESUME: 'kres',
|
||||
_curses.KEY_RIGHT: 'kcuf1',
|
||||
_curses.KEY_SAVE: 'ksav',
|
||||
_curses.KEY_SBEG: 'kBEG',
|
||||
_curses.KEY_SCANCEL: 'kCAN',
|
||||
_curses.KEY_SCOMMAND: 'kCMD',
|
||||
_curses.KEY_SCOPY: 'kCPY',
|
||||
_curses.KEY_SCREATE: 'kCRT',
|
||||
_curses.KEY_SDC: 'kDC',
|
||||
_curses.KEY_SDL: 'kDL',
|
||||
_curses.KEY_SELECT: 'kslt',
|
||||
_curses.KEY_SEND: 'kEND',
|
||||
_curses.KEY_SEOL: 'kEOL',
|
||||
_curses.KEY_SEXIT: 'kEXT',
|
||||
_curses.KEY_SF: 'kind',
|
||||
_curses.KEY_SFIND: 'kFND',
|
||||
_curses.KEY_SHELP: 'kHLP',
|
||||
_curses.KEY_SHOME: 'kHOM',
|
||||
_curses.KEY_SIC: 'kIC',
|
||||
_curses.KEY_SLEFT: 'kLFT',
|
||||
_curses.KEY_SMESSAGE: 'kMSG',
|
||||
_curses.KEY_SMOVE: 'kMOV',
|
||||
_curses.KEY_SNEXT: 'kNXT',
|
||||
_curses.KEY_SOPTIONS: 'kOPT',
|
||||
_curses.KEY_SPREVIOUS: 'kPRV',
|
||||
_curses.KEY_SPRINT: 'kPRT',
|
||||
_curses.KEY_SR: 'kri',
|
||||
_curses.KEY_SREDO: 'kRDO',
|
||||
_curses.KEY_SREPLACE: 'kRPL',
|
||||
_curses.KEY_SRIGHT: 'kRIT',
|
||||
_curses.KEY_SRSUME: 'kRES',
|
||||
_curses.KEY_SSAVE: 'kSAV',
|
||||
_curses.KEY_SSUSPEND: 'kSPD',
|
||||
_curses.KEY_STAB: 'khts',
|
||||
_curses.KEY_SUNDO: 'kUND',
|
||||
_curses.KEY_SUSPEND: 'kspd',
|
||||
_curses.KEY_UNDO: 'kund',
|
||||
_curses.KEY_UP: 'kcuu1'
|
||||
}
|
||||
|
||||
def has_key(ch):
|
||||
if isinstance(ch, str):
|
||||
ch = ord(ch)
|
||||
|
||||
# Figure out the correct capability name for the keycode.
|
||||
capability_name = _capability_names.get(ch)
|
||||
if capability_name is None:
|
||||
return False
|
||||
|
||||
#Check the current terminal description for that capability;
|
||||
#if present, return true, else return false.
|
||||
if _curses.tigetstr( capability_name ):
|
||||
return True
|
||||
else:
|
||||
return False
|
||||
|
||||
if __name__ == '__main__':
|
||||
# Compare the output of this implementation and the ncurses has_key,
|
||||
# on platforms where has_key is already available
|
||||
try:
|
||||
L = []
|
||||
_curses.initscr()
|
||||
for key in _capability_names.keys():
|
||||
system = _curses.has_key(key)
|
||||
python = has_key(key)
|
||||
if system != python:
|
||||
L.append( 'Mismatch for key %s, system=%i, Python=%i'
|
||||
% (_curses.keyname( key ), system, python) )
|
||||
finally:
|
||||
_curses.endwin()
|
||||
for i in L: print(i)
|
||||
@@ -0,0 +1,6 @@
|
||||
"""curses.panel
|
||||
|
||||
Module for using panels with curses.
|
||||
"""
|
||||
|
||||
from _curses_panel import *
|
||||
@@ -0,0 +1,201 @@
|
||||
"""Simple textbox editing widget with Emacs-like keybindings."""
|
||||
|
||||
import curses
|
||||
import curses.ascii
|
||||
|
||||
def rectangle(win, uly, ulx, lry, lrx):
|
||||
"""Draw a rectangle with corners at the provided upper-left
|
||||
and lower-right coordinates.
|
||||
"""
|
||||
win.vline(uly+1, ulx, curses.ACS_VLINE, lry - uly - 1)
|
||||
win.hline(uly, ulx+1, curses.ACS_HLINE, lrx - ulx - 1)
|
||||
win.hline(lry, ulx+1, curses.ACS_HLINE, lrx - ulx - 1)
|
||||
win.vline(uly+1, lrx, curses.ACS_VLINE, lry - uly - 1)
|
||||
win.addch(uly, ulx, curses.ACS_ULCORNER)
|
||||
win.addch(uly, lrx, curses.ACS_URCORNER)
|
||||
win.addch(lry, lrx, curses.ACS_LRCORNER)
|
||||
win.addch(lry, ulx, curses.ACS_LLCORNER)
|
||||
|
||||
class Textbox:
|
||||
"""Editing widget using the interior of a window object.
|
||||
Supports the following Emacs-like key bindings:
|
||||
|
||||
Ctrl-A Go to left edge of window.
|
||||
Ctrl-B Cursor left, wrapping to previous line if appropriate.
|
||||
Ctrl-D Delete character under cursor.
|
||||
Ctrl-E Go to right edge (stripspaces off) or end of line (stripspaces on).
|
||||
Ctrl-F Cursor right, wrapping to next line when appropriate.
|
||||
Ctrl-G Terminate, returning the window contents.
|
||||
Ctrl-H Delete character backward.
|
||||
Ctrl-J Terminate if the window is 1 line, otherwise insert newline.
|
||||
Ctrl-K If line is blank, delete it, otherwise clear to end of line.
|
||||
Ctrl-L Refresh screen.
|
||||
Ctrl-N Cursor down; move down one line.
|
||||
Ctrl-O Insert a blank line at cursor location.
|
||||
Ctrl-P Cursor up; move up one line.
|
||||
|
||||
Move operations do nothing if the cursor is at an edge where the movement
|
||||
is not possible. The following synonyms are supported where possible:
|
||||
|
||||
KEY_LEFT = Ctrl-B, KEY_RIGHT = Ctrl-F, KEY_UP = Ctrl-P, KEY_DOWN = Ctrl-N
|
||||
KEY_BACKSPACE = Ctrl-h
|
||||
"""
|
||||
def __init__(self, win, insert_mode=False):
|
||||
self.win = win
|
||||
self.insert_mode = insert_mode
|
||||
self._update_max_yx()
|
||||
self.stripspaces = 1
|
||||
self.lastcmd = None
|
||||
win.keypad(1)
|
||||
|
||||
def _update_max_yx(self):
|
||||
maxy, maxx = self.win.getmaxyx()
|
||||
self.maxy = maxy - 1
|
||||
self.maxx = maxx - 1
|
||||
|
||||
def _end_of_line(self, y):
|
||||
"""Go to the location of the first blank on the given line,
|
||||
returning the index of the last non-blank character."""
|
||||
self._update_max_yx()
|
||||
last = self.maxx
|
||||
while True:
|
||||
if curses.ascii.ascii(self.win.inch(y, last)) != curses.ascii.SP:
|
||||
last = min(self.maxx, last+1)
|
||||
break
|
||||
elif last == 0:
|
||||
break
|
||||
last = last - 1
|
||||
return last
|
||||
|
||||
def _insert_printable_char(self, ch):
|
||||
self._update_max_yx()
|
||||
(y, x) = self.win.getyx()
|
||||
backyx = None
|
||||
while y < self.maxy or x < self.maxx:
|
||||
if self.insert_mode:
|
||||
oldch = self.win.inch()
|
||||
# The try-catch ignores the error we trigger from some curses
|
||||
# versions by trying to write into the lowest-rightmost spot
|
||||
# in the window.
|
||||
try:
|
||||
self.win.addch(ch)
|
||||
except curses.error:
|
||||
pass
|
||||
if not self.insert_mode or not curses.ascii.isprint(oldch):
|
||||
break
|
||||
ch = oldch
|
||||
(y, x) = self.win.getyx()
|
||||
# Remember where to put the cursor back since we are in insert_mode
|
||||
if backyx is None:
|
||||
backyx = y, x
|
||||
|
||||
if backyx is not None:
|
||||
self.win.move(*backyx)
|
||||
|
||||
def do_command(self, ch):
|
||||
"Process a single editing command."
|
||||
self._update_max_yx()
|
||||
(y, x) = self.win.getyx()
|
||||
self.lastcmd = ch
|
||||
if curses.ascii.isprint(ch):
|
||||
if y < self.maxy or x < self.maxx:
|
||||
self._insert_printable_char(ch)
|
||||
elif ch == curses.ascii.SOH: # ^a
|
||||
self.win.move(y, 0)
|
||||
elif ch in (curses.ascii.STX,curses.KEY_LEFT, curses.ascii.BS,curses.KEY_BACKSPACE):
|
||||
if x > 0:
|
||||
self.win.move(y, x-1)
|
||||
elif y == 0:
|
||||
pass
|
||||
elif self.stripspaces:
|
||||
self.win.move(y-1, self._end_of_line(y-1))
|
||||
else:
|
||||
self.win.move(y-1, self.maxx)
|
||||
if ch in (curses.ascii.BS, curses.KEY_BACKSPACE):
|
||||
self.win.delch()
|
||||
elif ch == curses.ascii.EOT: # ^d
|
||||
self.win.delch()
|
||||
elif ch == curses.ascii.ENQ: # ^e
|
||||
if self.stripspaces:
|
||||
self.win.move(y, self._end_of_line(y))
|
||||
else:
|
||||
self.win.move(y, self.maxx)
|
||||
elif ch in (curses.ascii.ACK, curses.KEY_RIGHT): # ^f
|
||||
if x < self.maxx:
|
||||
self.win.move(y, x+1)
|
||||
elif y == self.maxy:
|
||||
pass
|
||||
else:
|
||||
self.win.move(y+1, 0)
|
||||
elif ch == curses.ascii.BEL: # ^g
|
||||
return 0
|
||||
elif ch == curses.ascii.NL: # ^j
|
||||
if self.maxy == 0:
|
||||
return 0
|
||||
elif y < self.maxy:
|
||||
self.win.move(y+1, 0)
|
||||
elif ch == curses.ascii.VT: # ^k
|
||||
if x == 0 and self._end_of_line(y) == 0:
|
||||
self.win.deleteln()
|
||||
else:
|
||||
# first undo the effect of self._end_of_line
|
||||
self.win.move(y, x)
|
||||
self.win.clrtoeol()
|
||||
elif ch == curses.ascii.FF: # ^l
|
||||
self.win.refresh()
|
||||
elif ch in (curses.ascii.SO, curses.KEY_DOWN): # ^n
|
||||
if y < self.maxy:
|
||||
self.win.move(y+1, x)
|
||||
if x > self._end_of_line(y+1):
|
||||
self.win.move(y+1, self._end_of_line(y+1))
|
||||
elif ch == curses.ascii.SI: # ^o
|
||||
self.win.insertln()
|
||||
elif ch in (curses.ascii.DLE, curses.KEY_UP): # ^p
|
||||
if y > 0:
|
||||
self.win.move(y-1, x)
|
||||
if x > self._end_of_line(y-1):
|
||||
self.win.move(y-1, self._end_of_line(y-1))
|
||||
return 1
|
||||
|
||||
def gather(self):
|
||||
"Collect and return the contents of the window."
|
||||
result = ""
|
||||
self._update_max_yx()
|
||||
for y in range(self.maxy+1):
|
||||
self.win.move(y, 0)
|
||||
stop = self._end_of_line(y)
|
||||
if stop == 0 and self.stripspaces:
|
||||
continue
|
||||
for x in range(self.maxx+1):
|
||||
if self.stripspaces and x > stop:
|
||||
break
|
||||
result = result + chr(curses.ascii.ascii(self.win.inch(y, x)))
|
||||
if self.maxy > 0:
|
||||
result = result + "\n"
|
||||
return result
|
||||
|
||||
def edit(self, validate=None):
|
||||
"Edit in the widget window and collect the results."
|
||||
while 1:
|
||||
ch = self.win.getch()
|
||||
if validate:
|
||||
ch = validate(ch)
|
||||
if not ch:
|
||||
continue
|
||||
if not self.do_command(ch):
|
||||
break
|
||||
self.win.refresh()
|
||||
return self.gather()
|
||||
|
||||
if __name__ == '__main__':
|
||||
def test_editbox(stdscr):
|
||||
ncols, nlines = 9, 4
|
||||
uly, ulx = 15, 20
|
||||
stdscr.addstr(uly-2, ulx, "Use Ctrl-G to end editing.")
|
||||
win = curses.newwin(nlines, ncols, uly, ulx)
|
||||
rectangle(stdscr, uly-1, ulx-1, uly + nlines, ulx + ncols)
|
||||
stdscr.refresh()
|
||||
return Textbox(win).edit()
|
||||
|
||||
str = curses.wrapper(test_editbox)
|
||||
print('Contents of text box:', repr(str))
|
||||
Reference in New Issue
Block a user