mirror of
https://git.code.sf.net/p/quake/quakeforge
synced 2024-11-10 15:22:04 +00:00
[qwaq] Implement resizing
Terminal resize is detected and the views adjust appropriately (well, those for which I've set grow flags: the window title bar doesn't adjust yet).
This commit is contained in:
parent
d0c8d75e92
commit
9bc91cd7d1
17 changed files with 339 additions and 6 deletions
|
@ -16,6 +16,7 @@ typedef enum {
|
|||
typedef enum {
|
||||
qe_command = 0x0200, // application level command
|
||||
qe_broadcast = 0x0400,
|
||||
qe_resize = 0x0800, // screen resized
|
||||
} qwaq_message_event;
|
||||
|
||||
typedef enum {
|
||||
|
@ -46,6 +47,11 @@ typedef struct qwaq_kevent_s {
|
|||
int shift;
|
||||
} qwaq_kevent_t;
|
||||
|
||||
typedef struct qwaq_resize_s {
|
||||
int width;
|
||||
int height;
|
||||
} qwaq_resize_t;
|
||||
|
||||
typedef struct qwaq_message_s {
|
||||
qwaq_command command;
|
||||
} qwaq_message_t;
|
||||
|
@ -57,6 +63,7 @@ typedef struct qwaq_event_s {
|
|||
qwaq_kevent_t key;
|
||||
qwaq_mevent_t mouse;
|
||||
qwaq_message_t message;
|
||||
qwaq_resize_t resize;
|
||||
};
|
||||
} qwaq_event_t;
|
||||
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
#include <Object.h>
|
||||
|
||||
#include "event.h"
|
||||
#include "qwaq-rect.h"
|
||||
|
||||
@class Group;
|
||||
@class TextContext;
|
||||
|
@ -16,6 +17,7 @@
|
|||
Group *objects;
|
||||
|
||||
TextContext *screen;
|
||||
Extent screenSize;
|
||||
int autocount;
|
||||
}
|
||||
-run;
|
||||
|
|
|
@ -47,11 +47,13 @@ arp_end (void)
|
|||
init_pair (4, COLOR_YELLOW, COLOR_RED);
|
||||
|
||||
screen = [TextContext screen];
|
||||
screenSize = [screen size];
|
||||
printf ("screenSize = %d x %d", screenSize.width, screenSize.height);
|
||||
objects = [[Group alloc] initWithContext: screen owner: nil];
|
||||
|
||||
[screen bkgd: COLOR_PAIR (1)];
|
||||
[screen scrollok: 1];
|
||||
Rect r = { nil, [screen size] };
|
||||
Rect r = {nil, screenSize};
|
||||
r.offset.x = r.extent.width / 4;
|
||||
r.offset.y = r.extent.height / 4;
|
||||
r.extent.width /= 2;
|
||||
|
@ -88,8 +90,23 @@ arp_end (void)
|
|||
|
||||
-handleEvent: (qwaq_event_t *) event
|
||||
{
|
||||
if (event.what == qe_resize) {
|
||||
Extent delta;
|
||||
delta.width = event.resize.width - screenSize.width;
|
||||
delta.height = event.resize.height - screenSize.height;
|
||||
|
||||
resizeterm (event.resize.width, event.resize.height);
|
||||
[screen resizeTo: {event.resize.width, event.resize.height}];
|
||||
screenSize = [screen size];
|
||||
[screen printf:"resized to %d x %d, delta: %d x %d\n", event.resize.width, event.resize.height, delta.width, delta.height];
|
||||
[objects resize: delta];
|
||||
[screen refresh];
|
||||
event.what = qe_none;
|
||||
return self;
|
||||
}
|
||||
[objects handleEvent: event];
|
||||
if (event.what == qe_key && event.key.code == '\x18') {
|
||||
if (event.what == qe_key
|
||||
&& (event.key.code == '\x18' || event.key.code == '\x11')) {
|
||||
event.what = qe_command;
|
||||
event.message.command = qc_exit;
|
||||
}
|
||||
|
|
|
@ -66,6 +66,7 @@ typedef enum qwaq_commands_e {
|
|||
qwaq_cmd_bottom_panel,
|
||||
qwaq_cmd_move_panel,
|
||||
qwaq_cmd_panel_window,
|
||||
qwaq_cmd_replace_panel,
|
||||
qwaq_cmd_update_panels,
|
||||
qwaq_cmd_doupdate,
|
||||
qwaq_cmd_mvwaddstr,
|
||||
|
@ -81,6 +82,8 @@ typedef enum qwaq_commands_e {
|
|||
qwaq_cmd_curs_set,
|
||||
qwaq_cmd_wborder,
|
||||
qwaq_cmd_mvwblit_line,
|
||||
qwaq_cmd_wresize,
|
||||
qwaq_cmd_resizeterm,
|
||||
} qwaq_commands;
|
||||
|
||||
static const char *qwaq_command_names[]= {
|
||||
|
@ -95,6 +98,7 @@ static const char *qwaq_command_names[]= {
|
|||
"bottom_panel",
|
||||
"move_panel",
|
||||
"panel_window",
|
||||
"replace_panel",
|
||||
"update_panels",
|
||||
"doupdate",
|
||||
"mvwaddstr",
|
||||
|
@ -110,6 +114,8 @@ static const char *qwaq_command_names[]= {
|
|||
"curs_set",
|
||||
"wborder",
|
||||
"mvwblit_line",
|
||||
"wresize",
|
||||
"resizeterm",
|
||||
};
|
||||
|
||||
static window_t *
|
||||
|
@ -398,6 +404,18 @@ cmd_panel_window (qwaq_resources_t *res)
|
|||
qwaq_submit_result (res, cmd_result, CMD_SIZE (cmd_result));
|
||||
}
|
||||
|
||||
static void
|
||||
cmd_replace_panel (qwaq_resources_t *res)
|
||||
{
|
||||
int panel_id = RB_PEEK_DATA (res->command_queue, 2);
|
||||
int window_id = RB_PEEK_DATA (res->command_queue, 3);
|
||||
|
||||
panel_t *panel = get_panel (res, __FUNCTION__, panel_id);
|
||||
window_t *window = get_window (res, __FUNCTION__, window_id);
|
||||
|
||||
replace_panel (panel->panel, window->win);
|
||||
}
|
||||
|
||||
static void
|
||||
cmd_update_panels (qwaq_resources_t *res)
|
||||
{
|
||||
|
@ -561,10 +579,30 @@ cmd_mvwblit_line (qwaq_resources_t *res)
|
|||
release_string (res, chs_id);
|
||||
}
|
||||
|
||||
static void
|
||||
cmd_wresize (qwaq_resources_t *res)
|
||||
{
|
||||
int window_id = RB_PEEK_DATA (res->command_queue, 2);
|
||||
int width = RB_PEEK_DATA (res->command_queue, 3);
|
||||
int height = RB_PEEK_DATA (res->command_queue, 4);
|
||||
|
||||
window_t *window = get_window (res, __FUNCTION__, window_id);
|
||||
wresize (window->win, height, width);
|
||||
}
|
||||
|
||||
static void
|
||||
cmd_resizeterm (qwaq_resources_t *res)
|
||||
{
|
||||
int width = RB_PEEK_DATA (res->command_queue, 2);
|
||||
int height = RB_PEEK_DATA (res->command_queue, 3);
|
||||
|
||||
resizeterm (height, width);
|
||||
}
|
||||
|
||||
static void
|
||||
dump_command (qwaq_resources_t *res, int len)
|
||||
{
|
||||
if (0) {
|
||||
if (1) {
|
||||
qwaq_commands cmd = RB_PEEK_DATA (res->command_queue, 0);
|
||||
Sys_Printf ("%s[%d]", qwaq_command_names[cmd], len);
|
||||
for (int i = 2; i < len; i++) {
|
||||
|
@ -642,6 +680,9 @@ process_commands (qwaq_resources_t *res)
|
|||
case qwaq_cmd_panel_window:
|
||||
cmd_panel_window (res);
|
||||
break;
|
||||
case qwaq_cmd_replace_panel:
|
||||
cmd_replace_panel (res);
|
||||
break;
|
||||
case qwaq_cmd_update_panels:
|
||||
cmd_update_panels (res);
|
||||
break;
|
||||
|
@ -687,6 +728,12 @@ process_commands (qwaq_resources_t *res)
|
|||
case qwaq_cmd_mvwblit_line:
|
||||
cmd_mvwblit_line (res);
|
||||
break;
|
||||
case qwaq_cmd_wresize:
|
||||
cmd_wresize (res);
|
||||
break;
|
||||
case qwaq_cmd_resizeterm:
|
||||
cmd_resizeterm (res);
|
||||
break;
|
||||
}
|
||||
pthread_mutex_lock (&res->command_cond.mut);
|
||||
RB_DROP_DATA (res->command_queue, len);
|
||||
|
@ -892,6 +939,22 @@ bi_panel_window (progs_t *pr)
|
|||
}
|
||||
}
|
||||
|
||||
static void
|
||||
bi_replace_panel (progs_t *pr)
|
||||
{
|
||||
qwaq_resources_t *res = PR_Resources_Find (pr, "qwaq");
|
||||
int panel_id = P_INT (pr, 0);
|
||||
int window_id = P_INT (pr, 1);
|
||||
|
||||
if (get_panel (res, __FUNCTION__, panel_id)
|
||||
&& get_window (res, __FUNCTION__, window_id)) {
|
||||
int command[] = { qwaq_cmd_replace_panel, 0,
|
||||
panel_id, window_id};
|
||||
command[1] = CMD_SIZE(command);
|
||||
qwaq_submit_command (res, command);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
qwaq_update_panels (progs_t *pr)
|
||||
{
|
||||
|
@ -950,6 +1013,50 @@ bi_waddstr (progs_t *pr)
|
|||
qwaq_waddstr (pr, window_id, str);
|
||||
}
|
||||
|
||||
static void
|
||||
qwaq_wresize (progs_t *pr, int window_id, int width, int height)
|
||||
{
|
||||
qwaq_resources_t *res = PR_Resources_Find (pr, "qwaq");
|
||||
|
||||
if (get_window (res, __FUNCTION__, window_id)) {
|
||||
int command[] = {
|
||||
qwaq_cmd_wresize, 0,
|
||||
window_id, width, height
|
||||
};
|
||||
|
||||
command[1] = CMD_SIZE(command);
|
||||
qwaq_submit_command (res, command);
|
||||
}
|
||||
}
|
||||
static void
|
||||
bi_wresize (progs_t *pr)
|
||||
{
|
||||
int window_id = P_STRUCT (pr, qwaq_textcontext_t, 0).window;
|
||||
int width = P_INT (pr, 1);
|
||||
int height = P_INT (pr, 2);
|
||||
|
||||
qwaq_wresize (pr, window_id, width, height);
|
||||
}
|
||||
|
||||
static void
|
||||
qwaq_resizeterm (progs_t *pr, int width, int height)
|
||||
{
|
||||
qwaq_resources_t *res = PR_Resources_Find (pr, "qwaq");
|
||||
|
||||
int command[] = { qwaq_cmd_resizeterm, 0, width, height };
|
||||
|
||||
command[1] = CMD_SIZE(command);
|
||||
qwaq_submit_command (res, command);
|
||||
}
|
||||
static void
|
||||
bi_resizeterm (progs_t *pr)
|
||||
{
|
||||
int width = P_INT (pr, 0);
|
||||
int height = P_INT (pr, 1);
|
||||
|
||||
qwaq_resizeterm (pr, width, height);
|
||||
}
|
||||
|
||||
static void
|
||||
qwaq_mvwaddstr (progs_t *pr, int window_id, int x, int y, const char *str)
|
||||
{
|
||||
|
@ -1572,6 +1679,19 @@ bi_i_TextContext__mvvprintf_ (progs_t *pr)
|
|||
qwaq_mvwvprintf (pr, pos->x, pos->y, window_id, fmt, args);
|
||||
}
|
||||
|
||||
static void
|
||||
bi_i_TextContext__resizeTo_ (progs_t *pr)
|
||||
{
|
||||
__auto_type self = &P_STRUCT (pr, qwaq_textcontext_t, 0);
|
||||
int window_id = self->window;
|
||||
|
||||
self->size = P_PACKED (pr, Extent, 2);
|
||||
qwaq_wresize (pr, window_id, self->size.width, self->size.height);
|
||||
if (window_id == 1) {
|
||||
qwaq_wbkgd (pr, window_id, self->background);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
bi_c_TextContext__refresh (progs_t *pr)
|
||||
{
|
||||
|
@ -1614,9 +1734,11 @@ bi_i_TextContext__mvaddstr_ (progs_t *pr)
|
|||
static void
|
||||
bi_i_TextContext__bkgd_ (progs_t *pr)
|
||||
{
|
||||
int window_id = P_STRUCT (pr, qwaq_textcontext_t, 0).window;
|
||||
__auto_type self = &P_STRUCT (pr, qwaq_textcontext_t, 0);
|
||||
int window_id = self->window;
|
||||
int ch = P_INT (pr, 2);
|
||||
|
||||
self->background = ch;
|
||||
qwaq_wbkgd (pr, window_id, ch);
|
||||
}
|
||||
|
||||
|
@ -1675,6 +1797,7 @@ static builtin_t builtins[] = {
|
|||
{"bottom_panel", bi_bottom_panel, -1},
|
||||
{"move_panel", bi_move_panel, -1},
|
||||
{"panel_window", bi_panel_window, -1},
|
||||
{"replace_panel", bi_replace_panel, -1},
|
||||
{"update_panels", bi_update_panels, -1},
|
||||
{"doupdate", bi_doupdate, -1},
|
||||
{"mvwprintf", bi_mvwprintf, -1},
|
||||
|
@ -1698,6 +1821,8 @@ static builtin_t builtins[] = {
|
|||
{"curs_set", bi_curs_set, -1},
|
||||
{"wborder", bi_wborder, -1},
|
||||
{"mvwblit_line", bi_mvwblit_line, -1},
|
||||
{"wresize", bi_wresize, -1},
|
||||
{"resizeterm", bi_resizeterm, -1},
|
||||
|
||||
{"printf", bi_printf, -1},
|
||||
|
||||
|
@ -1715,6 +1840,7 @@ static builtin_t builtins[] = {
|
|||
{"_i_TextContext__addch_", bi_i_TextContext__addch_, -1},
|
||||
{"_i_TextContext__addstr_", bi_i_TextContext__addstr_, -1},
|
||||
{"_i_TextContext__mvvprintf_", bi_i_TextContext__mvvprintf_, -1},
|
||||
{"_i_TextContext__resizeTo_", bi_i_TextContext__resizeTo_, -1},
|
||||
{"_c_TextContext__refresh", bi_c_TextContext__refresh, -1},
|
||||
{"_i_TextContext__refresh", bi_i_TextContext__refresh, -1},
|
||||
{"_i_TextContext__mvaddch_", bi_i_TextContext__mvaddch_, -1},
|
||||
|
|
|
@ -109,6 +109,7 @@ typedef struct panel_s *panel_t;
|
|||
@extern void move_panel (panel_t panel, int x, int y);
|
||||
@extern window_t panel_window (panel_t panel);
|
||||
@extern void update_panels (void);
|
||||
@extern void replace_panel (panel_t panel, window_t window);
|
||||
@extern void doupdate (void);
|
||||
|
||||
@extern int get_event (qwaq_event_t *event);
|
||||
|
@ -126,6 +127,8 @@ typedef struct panel_s *panel_t;
|
|||
@extern void wborder (window_t window,
|
||||
box_sides_t sides, box_corners_t corners);
|
||||
@extern void mvwblit_line (window_t window, int x, int y, int *wch, int len);
|
||||
@extern void wresize (window_t window, int width, int height);
|
||||
@extern void resizeterm (int width, int height);
|
||||
|
||||
@extern Rect getwrect (struct window_s *window);
|
||||
|
||||
|
|
|
@ -17,6 +17,7 @@
|
|||
@protocol TextContext
|
||||
- blitFromBuffer: (DrawBuffer *) srcBuffer to: (Point) pos from: (Rect) rect;
|
||||
- (Extent) size;
|
||||
- (void) resizeTo: (Extent) newSize; // absolute size
|
||||
|
||||
- (void) bkgd: (int) ch;
|
||||
- (void) clear;
|
||||
|
|
|
@ -25,6 +25,12 @@
|
|||
return size;
|
||||
}
|
||||
|
||||
- (void) resizeTo: (Extent) newSize
|
||||
{
|
||||
size = newSize;
|
||||
buffer = obj_realloc (buffer, size.width * size.height);
|
||||
}
|
||||
|
||||
- (int *) buffer
|
||||
{
|
||||
return buffer;
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
buffer = [[EditBuffer alloc] initWithFile: filename];
|
||||
line_count = [buffer countLines: {0, [buffer textSize]}];
|
||||
linebuffer = [DrawBuffer buffer: { xlen, 1 }];
|
||||
growMode = gfGrowHi;
|
||||
return self;
|
||||
}
|
||||
|
||||
|
@ -28,6 +29,13 @@
|
|||
return self;
|
||||
}
|
||||
|
||||
-resize: (Extent) delta
|
||||
{
|
||||
[super resize: delta];
|
||||
[linebuffer resizeTo: {xlen, 1}];
|
||||
return self;
|
||||
}
|
||||
|
||||
-handleEvent:(qwaq_event_t *) event
|
||||
{
|
||||
if (event.what & qe_mouse) {
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
-(Extent) size;
|
||||
-draw;
|
||||
-redraw;
|
||||
-resize: (Extent) delta;
|
||||
-handleEvent: (qwaq_event_t *) event;
|
||||
-(void) grabMouse;
|
||||
-(void) releaseMouse;
|
||||
|
|
|
@ -100,6 +100,14 @@ not_dont_draw (id aView, void *aGroup)
|
|||
return self;
|
||||
}
|
||||
|
||||
-resize: (Extent) delta
|
||||
{
|
||||
for (int i = [views count]; i-- > 0; ) {
|
||||
[[views objectAtIndex: i] grow: delta];
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
static View *
|
||||
find_mouse_view(Group *group, Point pos)
|
||||
{
|
||||
|
|
|
@ -31,9 +31,11 @@
|
|||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#include <sys/ioctl.h>
|
||||
#include <ctype.h>
|
||||
#include <errno.h>
|
||||
#include <pthread.h>
|
||||
#include <signal.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <termios.h>
|
||||
|
@ -162,6 +164,16 @@ static qwaq_key_t default_keys[] = {
|
|||
{ "\033[1;6D", QFK_LEFT, 5 },
|
||||
};
|
||||
|
||||
static struct sigaction save_winch;
|
||||
static sigset_t winch_mask;
|
||||
static volatile sig_atomic_t winch_arrived;
|
||||
|
||||
static void
|
||||
handle_winch (int sig)
|
||||
{
|
||||
winch_arrived = 1;
|
||||
}
|
||||
|
||||
static void
|
||||
add_event (qwaq_resources_t *res, qwaq_event_t *event)
|
||||
{
|
||||
|
@ -194,6 +206,20 @@ add_event (qwaq_resources_t *res, qwaq_event_t *event)
|
|||
pthread_mutex_unlock (&res->event_cond.mut);
|
||||
}
|
||||
|
||||
static void
|
||||
resize_event (qwaq_resources_t *res)
|
||||
{
|
||||
qwaq_event_t event = {};
|
||||
struct winsize size;
|
||||
if (ioctl (fileno (stdout), TIOCGWINSZ, &size) != 0) {
|
||||
return;
|
||||
}
|
||||
event.what = qe_resize;
|
||||
event.resize.width = size.ws_col;
|
||||
event.resize.height = size.ws_row;
|
||||
add_event (res, &event);
|
||||
}
|
||||
|
||||
static void
|
||||
key_event (qwaq_resources_t *res, int key, unsigned shift)
|
||||
{
|
||||
|
@ -396,6 +422,13 @@ void qwaq_input_init (qwaq_resources_t *res)
|
|||
i++) {
|
||||
Hash_Add (res->key_sequences, &default_keys[i]);
|
||||
}
|
||||
|
||||
sigemptyset (&winch_mask);
|
||||
sigaddset (&winch_mask, SIGWINCH);
|
||||
struct sigaction action = {};
|
||||
action.sa_handler = handle_winch;
|
||||
sigaction (SIGWINCH, &action, &save_winch);
|
||||
|
||||
// ncurses takes care of input mode for us, so need only tell xterm
|
||||
// what we need
|
||||
write(1, MOUSE_MOVES_ON, sizeof (MOUSE_MOVES_ON) - 1);
|
||||
|
@ -408,13 +441,24 @@ void qwaq_input_shutdown (qwaq_resources_t *res)
|
|||
// what we need
|
||||
write(1, SGR_OFF, sizeof (SGR_OFF) - 1);
|
||||
write(1, MOUSE_MOVES_OFF, sizeof (MOUSE_MOVES_OFF) - 1);
|
||||
|
||||
sigaction (SIGWINCH, &save_winch, 0);
|
||||
}
|
||||
|
||||
void qwaq_process_input (qwaq_resources_t *res)
|
||||
{
|
||||
char buf[256];
|
||||
int len;
|
||||
sigset_t save_set;
|
||||
int saw_winch;
|
||||
|
||||
pthread_sigmask (SIG_BLOCK, &winch_mask, &save_set);
|
||||
saw_winch = winch_arrived;
|
||||
winch_arrived = 0;
|
||||
pthread_sigmask (SIG_SETMASK, &save_set, 0);
|
||||
if (saw_winch) {
|
||||
resize_event (res);
|
||||
}
|
||||
while (Sys_CheckInput (1, -1)) {
|
||||
len = read(0, buf, sizeof (buf));
|
||||
for (int i = 0; i < len; i++) {
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
#ifndef __qwaq_rect_h
|
||||
#define __qwaq_rect_h
|
||||
|
||||
typedef struct {
|
||||
typedef struct Point_s {
|
||||
int x;
|
||||
int y;
|
||||
} Point;
|
||||
|
||||
typedef struct {
|
||||
typedef struct Extent_s {
|
||||
int width;
|
||||
int height;
|
||||
} Extent;
|
||||
|
|
|
@ -58,6 +58,20 @@
|
|||
typedef struct qwaq_textcontext_s {
|
||||
pr_id_t isa;
|
||||
pointer_t window;
|
||||
union {
|
||||
Rect rect;
|
||||
struct {
|
||||
Point offset;
|
||||
Extent size;
|
||||
};
|
||||
struct {
|
||||
int xpos;
|
||||
int ypos;
|
||||
int xlen;
|
||||
int ylen;
|
||||
};
|
||||
};
|
||||
int background;
|
||||
} qwaq_textcontext_t;
|
||||
|
||||
#endif
|
||||
|
|
|
@ -111,6 +111,7 @@ static TextContext *screen;
|
|||
- (void) mvaddch: (Point) pos, int ch = #0;
|
||||
- (void) mvaddstr: (Point) pos, string str = #0;
|
||||
|
||||
- (void) resizeTo: (Extent) newSize = #0; // absolute size
|
||||
- (void) refresh = #0;
|
||||
+ (void) refresh = #0;
|
||||
|
||||
|
@ -152,6 +153,7 @@ void top_panel (panel_t panel) = #0;
|
|||
void bottom_panel (panel_t panel) = #0;
|
||||
void move_panel (panel_t panel, int x, int y) = #0;
|
||||
window_t panel_window (panel_t panel) = #0;
|
||||
void replace_panel (panel_t panel, window_t window) = #0;
|
||||
void update_panels (void) = #0;
|
||||
|
||||
void doupdate (void) = #0;
|
||||
|
@ -159,6 +161,8 @@ int curs_set (int visibility) = #0;
|
|||
int move (int x, int y) = #0;
|
||||
void wborder (window_t window, box_sides_t sides, box_corners_t corners) = #0;
|
||||
void mvwblit_line (window_t window, int x, int y, int *wch, int len) = #0;
|
||||
void wresize (window_t window, int width, int height) = #0;
|
||||
void resizeterm (int width, int height) = #0;
|
||||
Rect getwrect (window_t window) = #0;
|
||||
|
||||
void printf(string fmt, ...) = #0;
|
||||
|
|
|
@ -31,6 +31,18 @@ enum {
|
|||
sfLocked =0x0010,
|
||||
};
|
||||
|
||||
enum {
|
||||
gfGrowLoX = 0x0001,
|
||||
gfGrowLoY = 0x0002,
|
||||
gfGrowHiX = 0x0004,
|
||||
gfGrowHiY = 0x0008,
|
||||
gfGrowRel = 0x0010,
|
||||
gfGrowLo = gfGrowLoX | gfGrowLoY,
|
||||
gfGrowHi = gfGrowHiX | gfGrowHiY,
|
||||
gfGrowX = gfGrowLoX | gfGrowHiX,
|
||||
gfGrowY = gfGrowLoY | gfGrowHiY,
|
||||
gfGrowAll = gfGrowX | gfGrowY,
|
||||
};
|
||||
@interface View: Object
|
||||
{
|
||||
union {
|
||||
|
@ -52,6 +64,7 @@ enum {
|
|||
id<TextContext> textContext;
|
||||
int state;
|
||||
int options;
|
||||
int growMode;
|
||||
int cursorState;
|
||||
Point cursor;
|
||||
}
|
||||
|
@ -73,6 +86,9 @@ enum {
|
|||
-setContext: (id<TextContext>) context;
|
||||
-draw;
|
||||
-redraw;
|
||||
-move: (Point) delta;
|
||||
-resize: (Extent) delta;
|
||||
-grow: (Extent) delta;
|
||||
-handleEvent: (qwaq_event_t *) event;
|
||||
|
||||
- (void) onMouseEnter: (Point) pos;
|
||||
|
|
|
@ -165,6 +165,69 @@ updateScreenCursor (View *view)
|
|||
[textContext mvaddch: pos, ch];
|
||||
}
|
||||
|
||||
-move: (Point) delta
|
||||
{
|
||||
xpos += delta.x;
|
||||
ypos += delta.y;
|
||||
if (xpos + xlen < 1) {
|
||||
xpos = 1 - xlen;
|
||||
}
|
||||
if (ypos < 0) {
|
||||
ypos = 0;
|
||||
}
|
||||
if (owner) {
|
||||
Extent s = [owner size];
|
||||
if (xpos > s.width - 1) {
|
||||
xpos = s.width - 1;
|
||||
}
|
||||
if (ypos > s.height - 1) {
|
||||
ypos = s.height - 1;
|
||||
}
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
-resize: (Extent) delta
|
||||
{
|
||||
xlen += delta.width;
|
||||
ylen += delta.height;
|
||||
if (xlen < 1) {
|
||||
xlen = 1;
|
||||
}
|
||||
if (ylen < 1) {
|
||||
ylen = 1;
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
-grow: (Extent) delta
|
||||
{
|
||||
Point dpos = {};
|
||||
Extent dsize = {};
|
||||
|
||||
if (growMode & gfGrowLoX) {
|
||||
dpos.x += delta.width;
|
||||
dsize.width -= delta.width;
|
||||
}
|
||||
if (growMode & gfGrowHiX) {
|
||||
dsize.width += delta.width;
|
||||
}
|
||||
if (growMode & gfGrowLoY) {
|
||||
dpos.y += delta.height;
|
||||
dsize.height -= delta.height;
|
||||
}
|
||||
if (growMode & gfGrowHiY) {
|
||||
dsize.height += delta.height;
|
||||
}
|
||||
int save_state = state;
|
||||
state &= ~sfDrawn;
|
||||
[self move: dpos];
|
||||
[self resize: dsize];
|
||||
state = save_state;
|
||||
[self redraw];
|
||||
return self;
|
||||
}
|
||||
|
||||
-handleEvent: (qwaq_event_t *) event
|
||||
{
|
||||
return self;
|
||||
|
|
|
@ -40,6 +40,8 @@
|
|||
[buf mvaddstr: {0, 0}, "XOX"];
|
||||
[buf mvaddstr: {0, 1}, "OXO"];
|
||||
[buf mvaddstr: {0, 2}, "XOX"];
|
||||
|
||||
growMode = gfGrowHi;
|
||||
return self;
|
||||
}
|
||||
|
||||
|
@ -71,6 +73,17 @@
|
|||
return self;
|
||||
}
|
||||
|
||||
-resize: (Extent) delta
|
||||
{
|
||||
Extent size = self.size;
|
||||
[super resize:delta];
|
||||
delta = {self.size.width - size.width, self.size.height - size.height};
|
||||
[(id)textContext resizeTo: self.size];
|
||||
replace_panel (panel, [(id)textContext window]);
|
||||
[objects resize:delta];
|
||||
return self;
|
||||
}
|
||||
|
||||
-handleEvent: (qwaq_event_t *) event
|
||||
{
|
||||
[objects handleEvent: event];
|
||||
|
|
Loading…
Reference in a new issue