mirror of
https://github.com/Tha14/toxic.git
synced 2024-11-23 02:23:02 +01:00
allow line editing via arrow keys in chat/groupchat windows
This commit is contained in:
parent
c25296e65a
commit
bb6b28b7c3
40
src/chat.c
40
src/chat.c
@ -283,13 +283,27 @@ static void chat_onKey(ToxWindow *self, Tox *m, wint_t key)
|
|||||||
/* BACKSPACE key: Remove one character from line */
|
/* BACKSPACE key: Remove one character from line */
|
||||||
if (key == 0x107 || key == 0x8 || key == 0x7f) {
|
if (key == 0x107 || key == 0x8 || key == 0x7f) {
|
||||||
if (ctx->pos > 0) {
|
if (ctx->pos > 0) {
|
||||||
ctx->line[--ctx->pos] = L'\0';
|
del_char_from_buf(key, ctx->line, &ctx->pos, &ctx->len);
|
||||||
|
|
||||||
if (x == 0)
|
if (x == 0)
|
||||||
mvwdelch(self->window, y - 1, x2 - 1);
|
wmove(self->window, y-1, x2-1);
|
||||||
else
|
else
|
||||||
mvwdelch(self->window, y, x - 1);
|
wmove(self->window, y, x-1);
|
||||||
}
|
}
|
||||||
|
} else if (key == KEY_LEFT && ctx->pos > 0) {
|
||||||
|
--ctx->pos;
|
||||||
|
|
||||||
|
if (x == 0)
|
||||||
|
wmove(self->window, y-1, x2-1);
|
||||||
|
else
|
||||||
|
wmove(self->window, y, x-1);
|
||||||
|
} else if (key == KEY_RIGHT && ctx->line[ctx->pos] != L'\0') {
|
||||||
|
++ctx->pos;
|
||||||
|
|
||||||
|
if (x == x2-1)
|
||||||
|
wmove(self->window, y+1, 0);
|
||||||
|
else
|
||||||
|
wmove(self->window, y, x+1);
|
||||||
} else
|
} else
|
||||||
/* Add printable chars to buffer and print on input space */
|
/* Add printable chars to buffer and print on input space */
|
||||||
#if HAVE_WIDECHAR
|
#if HAVE_WIDECHAR
|
||||||
@ -297,11 +311,14 @@ static void chat_onKey(ToxWindow *self, Tox *m, wint_t key)
|
|||||||
#else
|
#else
|
||||||
if (isprint(key))
|
if (isprint(key))
|
||||||
#endif
|
#endif
|
||||||
{
|
{ /* prevents buffer overflows and strange behaviour when cursor goes past the window */
|
||||||
if (ctx->pos < (MAX_STR_SIZE-1)) {
|
if ( (ctx->len < MAX_STR_SIZE-1) && (ctx->len < (x2 * (CHATBOX_HEIGHT - 1)-1)) ) {
|
||||||
mvwaddstr(self->window, y, x, wc_to_char(key));
|
add_char_to_buf(key, ctx->line, &ctx->pos, &ctx->len);
|
||||||
ctx->line[ctx->pos++] = key;
|
|
||||||
ctx->line[ctx->pos] = L'\0';
|
if (x == x2-1)
|
||||||
|
wmove(self->window, y+1, 0);
|
||||||
|
else
|
||||||
|
wmove(self->window, y, x+1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/* RETURN key: Execute command or print line */
|
/* RETURN key: Execute command or print line */
|
||||||
@ -354,8 +371,7 @@ static void chat_onKey(ToxWindow *self, Tox *m, wint_t key)
|
|||||||
free(ctx);
|
free(ctx);
|
||||||
free(statusbar);
|
free(statusbar);
|
||||||
} else {
|
} else {
|
||||||
ctx->line[0] = L'\0';
|
reset_buf(ctx->line, &ctx->pos, &ctx->len);
|
||||||
ctx->pos = 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
free(line);
|
free(line);
|
||||||
@ -370,6 +386,9 @@ static void chat_onDraw(ToxWindow *self, Tox *m)
|
|||||||
|
|
||||||
ChatContext *ctx = self->chatwin;
|
ChatContext *ctx = self->chatwin;
|
||||||
|
|
||||||
|
wclear(ctx->linewin);
|
||||||
|
mvwprintw(ctx->linewin, 1, 0, "%s\n", wcs_to_char(ctx->line));
|
||||||
|
|
||||||
/* Draw status bar */
|
/* Draw status bar */
|
||||||
StatusBar *statusbar = self->stb;
|
StatusBar *statusbar = self->stb;
|
||||||
mvwhline(statusbar->topline, 1, 0, ACS_HLINE, x);
|
mvwhline(statusbar->topline, 1, 0, ACS_HLINE, x);
|
||||||
@ -434,7 +453,6 @@ static void chat_onDraw(ToxWindow *self, Tox *m)
|
|||||||
}
|
}
|
||||||
|
|
||||||
wprintw(statusbar->topline, "\n");
|
wprintw(statusbar->topline, "\n");
|
||||||
|
|
||||||
mvwhline(ctx->linewin, 0, 0, ACS_HLINE, x);
|
mvwhline(ctx->linewin, 0, 0, ACS_HLINE, x);
|
||||||
wrefresh(self->window);
|
wrefresh(self->window);
|
||||||
}
|
}
|
||||||
|
@ -223,25 +223,41 @@ static void groupchat_onKey(ToxWindow *self, Tox *m, wint_t key)
|
|||||||
/* BACKSPACE key: Remove one character from line */
|
/* BACKSPACE key: Remove one character from line */
|
||||||
if (key == 0x107 || key == 0x8 || key == 0x7f) {
|
if (key == 0x107 || key == 0x8 || key == 0x7f) {
|
||||||
if (ctx->pos > 0) {
|
if (ctx->pos > 0) {
|
||||||
ctx->line[--ctx->pos] = L'\0';
|
del_char_from_buf(key, ctx->line, &ctx->pos, &ctx->len);
|
||||||
|
|
||||||
if (x == 0)
|
if (x == 0)
|
||||||
mvwdelch(self->window, y - 1, x2 - 1);
|
wmove(self->window, y-1, x2-1);
|
||||||
else
|
else
|
||||||
mvwdelch(self->window, y, x - 1);
|
wmove(self->window, y, x-1);
|
||||||
}
|
}
|
||||||
|
} else if (key == KEY_LEFT && ctx->pos > 0) {
|
||||||
|
--ctx->pos;
|
||||||
|
|
||||||
|
if (x == 0)
|
||||||
|
wmove(self->window, y-1, x2-1);
|
||||||
|
else
|
||||||
|
wmove(self->window, y, x-1);
|
||||||
|
} else if (key == KEY_RIGHT && ctx->line[ctx->pos] != L'\0') {
|
||||||
|
++ctx->pos;
|
||||||
|
|
||||||
|
if (x == x2-1)
|
||||||
|
wmove(self->window, y+1, 0);
|
||||||
|
else
|
||||||
|
wmove(self->window, y, x+1);
|
||||||
} else
|
} else
|
||||||
/* Add printable chars to buffer and print on input space */
|
|
||||||
#if HAVE_WIDECHAR
|
#if HAVE_WIDECHAR
|
||||||
if (iswprint(key))
|
if (iswprint(key))
|
||||||
#else
|
#else
|
||||||
if (isprint(key))
|
if (isprint(key))
|
||||||
#endif
|
#endif
|
||||||
{
|
{ /* prevents buffer overflows and strange behaviour when cursor goes past the window */
|
||||||
if (ctx->pos < (MAX_STR_SIZE-1)) {
|
if ( (ctx->len < MAX_STR_SIZE-1) && (ctx->len < (x2 * (CHATBOX_HEIGHT - 1)-1)) ) {
|
||||||
mvwaddstr(self->window, y, x, wc_to_char(key));
|
add_char_to_buf(key, ctx->line, &ctx->pos, &ctx->len);
|
||||||
ctx->line[ctx->pos++] = key;
|
|
||||||
ctx->line[ctx->pos] = L'\0';
|
if (x == x2-1)
|
||||||
|
wmove(self->window, y+1, 0);
|
||||||
|
else
|
||||||
|
wmove(self->window, y, x+1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -287,8 +303,7 @@ static void groupchat_onKey(ToxWindow *self, Tox *m, wint_t key)
|
|||||||
if (close_win)
|
if (close_win)
|
||||||
free(ctx);
|
free(ctx);
|
||||||
else {
|
else {
|
||||||
ctx->line[0] = L'\0';
|
reset_buf(ctx->line, &ctx->pos, &ctx->len);
|
||||||
ctx->pos = 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
free(line);
|
free(line);
|
||||||
@ -302,6 +317,10 @@ static void groupchat_onDraw(ToxWindow *self, Tox *m)
|
|||||||
getmaxyx(self->window, y, x);
|
getmaxyx(self->window, y, x);
|
||||||
|
|
||||||
ChatContext *ctx = self->chatwin;
|
ChatContext *ctx = self->chatwin;
|
||||||
|
|
||||||
|
wclear(ctx->linewin);
|
||||||
|
mvwprintw(ctx->linewin, 1, 0, "%s\n", wcs_to_char(ctx->line));
|
||||||
|
|
||||||
wclrtobot(ctx->sidebar);
|
wclrtobot(ctx->sidebar);
|
||||||
mvwhline(ctx->linewin, 0, 0, ACS_HLINE, x);
|
mvwhline(ctx->linewin, 0, 0, ACS_HLINE, x);
|
||||||
mvwvline(ctx->sidebar, 0, 0, ACS_VLINE, y-CHATBOX_HEIGHT);
|
mvwvline(ctx->sidebar, 0, 0, ACS_VLINE, y-CHATBOX_HEIGHT);
|
||||||
@ -338,7 +357,7 @@ static void groupchat_onInit(ToxWindow *self, Tox *m)
|
|||||||
ChatContext *ctx = self->chatwin;
|
ChatContext *ctx = self->chatwin;
|
||||||
ctx->history = subwin(self->window, y-CHATBOX_HEIGHT+1, x-SIDEBAR_WIDTH-1, 0, 0);
|
ctx->history = subwin(self->window, y-CHATBOX_HEIGHT+1, x-SIDEBAR_WIDTH-1, 0, 0);
|
||||||
scrollok(ctx->history, 1);
|
scrollok(ctx->history, 1);
|
||||||
ctx->linewin = subwin(self->window, 2, x, y-CHATBOX_HEIGHT, 0);
|
ctx->linewin = subwin(self->window, CHATBOX_HEIGHT, x, y-CHATBOX_HEIGHT, 0);
|
||||||
ctx->sidebar = subwin(self->window, y-CHATBOX_HEIGHT+1, SIDEBAR_WIDTH, 0, x-SIDEBAR_WIDTH);
|
ctx->sidebar = subwin(self->window, y-CHATBOX_HEIGHT+1, SIDEBAR_WIDTH, 0, x-SIDEBAR_WIDTH);
|
||||||
|
|
||||||
print_groupchat_help(ctx);
|
print_groupchat_help(ctx);
|
||||||
|
@ -8,6 +8,7 @@
|
|||||||
#include <limits.h>
|
#include <limits.h>
|
||||||
|
|
||||||
#include "toxic_windows.h"
|
#include "toxic_windows.h"
|
||||||
|
#include "misc_tools.h"
|
||||||
|
|
||||||
// XXX: FIX
|
// XXX: FIX
|
||||||
unsigned char *hex_string_to_bin(char hex_string[])
|
unsigned char *hex_string_to_bin(char hex_string[])
|
||||||
@ -158,3 +159,62 @@ bool valid_nick(uint8_t *nick)
|
|||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Buffer helper tools. Assumes buffers are no larger than MAX_STR_SIZE
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Adds char to buffer at pos */
|
||||||
|
void add_char_to_buf(wint_t ch, wchar_t *buf, size_t *pos, size_t *len)
|
||||||
|
{
|
||||||
|
if (*pos < 0 || *len >= MAX_STR_SIZE)
|
||||||
|
return;
|
||||||
|
|
||||||
|
/* if cursor is at end of line simply insert char at last position and increment */
|
||||||
|
if (buf[*pos] == L'\0') {
|
||||||
|
buf[(*pos)++] = ch;
|
||||||
|
buf[*pos] = L'\0';
|
||||||
|
++(*len);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* move all chars in front of pos one space forward and insert char in pos */
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = *len; i >= *pos && i >= 0; --i)
|
||||||
|
buf[i+1] = buf[i];
|
||||||
|
|
||||||
|
buf[(*pos)++] = ch;
|
||||||
|
++(*len);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Deletes the character before pos via the backspace key */
|
||||||
|
void del_char_from_buf(wint_t ch, wchar_t *buf, size_t *pos, size_t *len)
|
||||||
|
{
|
||||||
|
if (*pos <= 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
/* if cursor is at end of line delete previous char */
|
||||||
|
if (buf[*pos] == L'\0') {
|
||||||
|
buf[--(*pos)] = L'\0';
|
||||||
|
--(*len);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
int i;
|
||||||
|
|
||||||
|
/* similar to add_char_to_buf but deletes a char */
|
||||||
|
for (i = *pos-1; i <= *len; ++i)
|
||||||
|
buf[i] = buf[i+1];
|
||||||
|
|
||||||
|
--(*pos);
|
||||||
|
--(*len);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* sets pos and len to 0 */
|
||||||
|
void reset_buf(wchar_t *buf, size_t *pos, size_t *len)
|
||||||
|
{
|
||||||
|
buf[0] = L'\0';
|
||||||
|
*pos = 0;
|
||||||
|
*len = 0;
|
||||||
|
}
|
||||||
|
@ -36,3 +36,16 @@ int name_compare(const void *nick1, const void *nick2);
|
|||||||
- cannot start with a space
|
- cannot start with a space
|
||||||
- must not contain contiguous spaces */
|
- must not contain contiguous spaces */
|
||||||
bool valid_nick(uint8_t *nick);
|
bool valid_nick(uint8_t *nick);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Buffer helper tools.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Adds char to buffer at pos */
|
||||||
|
void add_char_to_buf(wint_t ch, wchar_t *buf, size_t *pos, size_t *len);
|
||||||
|
|
||||||
|
/* Deletes the character before pos via the backspace key */
|
||||||
|
void del_char_from_buf(wint_t ch, wchar_t *buf, size_t *pos, size_t *len);
|
||||||
|
|
||||||
|
/* sets pos and len to 0 */
|
||||||
|
void reset_buf(wchar_t *buf, size_t *pos, size_t *len);
|
@ -99,6 +99,7 @@ struct StatusBar {
|
|||||||
struct ChatContext {
|
struct ChatContext {
|
||||||
wchar_t line[MAX_STR_SIZE];
|
wchar_t line[MAX_STR_SIZE];
|
||||||
size_t pos;
|
size_t pos;
|
||||||
|
size_t len;
|
||||||
WINDOW *history;
|
WINDOW *history;
|
||||||
WINDOW *linewin;
|
WINDOW *linewin;
|
||||||
WINDOW *sidebar;
|
WINDOW *sidebar;
|
||||||
|
Loading…
Reference in New Issue
Block a user