hirc

IRC client
Log | Files | Refs

commit 2025ea4e39a7ac782c6d0543b7fbdc0c6a249a04
parent 5c0cf35e0b54bce9d7e1862165a0a7359b9afdab
Author: hhvn <dev@hhvn.uk>
Date:   Sun, 24 Oct 2021 17:49:56 +0100

handle.c hirc.h main.c nick.c ui.c: rudimentary nicklist

Diffstat:
Mhandle.c | 36+++++++++++++++++++++++++++++-------
Mhirc.h | 1+
Mmain.c | 15+++++++++++----
Mnick.c | 1+
Mui.c | 42+++++++++++++++++++++++++++++-------------
5 files changed, 71 insertions(+), 24 deletions(-)

diff --git a/handle.c b/handle.c @@ -14,6 +14,7 @@ struct Handler handlers[] = { { "NOTICE", handle_PRIVMSG }, { "005", handle_ISUPPORT }, { "353", handle_NAMREPLY }, + { "366", NULL /* end of names */ }, { "433", handle_NICKNAMEINUSE }, { NULL, NULL }, }; @@ -49,10 +50,15 @@ handle_JOIN(char *msg, char **params, struct Server *server, time_t timestamp) { hist_add(server, server->history, nick, msg, params, Activity_status, timestamp, HIST_LOG); hist_add(server, chan->history, nick, msg, params, Activity_status, timestamp, HIST_SHOW); - nick_free(nick); - selected_server = server; - selected_channel = chan; + if (nick_isself(nick)) { + selected_server = server; + selected_channel = chan; + } else if (selected_channel == chan) { + ui_draw_nicklist(); + } + + nick_free(nick); } void @@ -72,8 +78,12 @@ handle_PART(char *msg, char **params, struct Server *server, time_t timestamp) { if (nick_isself(nick)) { chan_setold(chan, 1); nick_free_list(&chan->nicks); + if (chan == selected_channel) + selected_channel = NULL; } else { nick_remove(&chan->nicks, nick->nick); + if (chan == selected_channel) + ui_draw_nicklist(); } hist_add(server, server->history, nick, msg, params, Activity_status, timestamp, HIST_LOG); @@ -100,6 +110,8 @@ handle_QUIT(char *msg, char **params, struct Server *server, time_t timestamp) { if (nick_get(&chan->nicks, nick->nick) != NULL) { nick_remove(&chan->nicks, nick->nick); hist_add(server, chan->history, nick, msg, params, Activity_status, timestamp, HIST_SHOW); + if (chan == selected_channel) + ui_draw_nicklist(); } } @@ -181,6 +193,7 @@ handle_ISUPPORT(char *msg, char **params, struct Server *server, time_t timestam void handle_NAMREPLY(char *msg, char **params, struct Server *server, time_t timestamp) { struct Channel *chan; + struct Nick *oldnick; char *nick, priv, *target; char **nicks, **nicksref; char *supportedprivs; @@ -198,7 +211,11 @@ handle_NAMREPLY(char *msg, char **params, struct Server *server, time_t timestam chan = chan_add(server, &server->channels, target); params++; - supportedprivs = struntil(support_get(server, "PREFIX"), ')') + 1; + supportedprivs = strchr(support_get(server, "PREFIX"), ')'); + if (supportedprivs == NULL || supportedprivs[0] == '\0') + supportedprivs = ""; + else + supportedprivs++; nicksref = nicks = param_create(*params); for (; *nicks && **nicks; nicks++) { @@ -209,11 +226,14 @@ handle_NAMREPLY(char *msg, char **params, struct Server *server, time_t timestam while (chrcmp(*nick, supportedprivs)) nick++; } - if (nick_get(&chan->nicks, nick) != NULL) - nick_remove(&chan->nicks, nick); - nick_add(&chan->nicks, nick, priv, server); + if ((oldnick = nick_get(&chan->nicks, nick)) == NULL) + nick_add(&chan->nicks, nick, priv, server); + else + oldnick->priv = priv; } + if (selected_channel == chan) + ui_draw_nicklist(); param_free(nicksref); } @@ -255,6 +275,8 @@ handle_NICK(char *msg, char **params, struct Server *server, time_t timestamp) { if ((chnick = nick_get(&chan->nicks, nick->nick)) != NULL) { nick_add(&chan->nicks, newnick, chnick->priv, server); nick_remove(&chan->nicks, nick->nick); + if (selected_channel == chan) + ui_draw_nicklist(); } } } diff --git a/hirc.h b/hirc.h @@ -93,6 +93,7 @@ void ui_init(void); void ui_read(void); void ui_redraw(void); void ui_draw_input(void); +void ui_draw_nicklist(void); void ui_error_(char *file, int line, char *format, ...); #define ui_error(format, ...) ui_error_(__FILE__, __LINE__, format, __VA_ARGS__); void ui_perror_(char *file, int line, char *str); diff --git a/main.c b/main.c @@ -176,6 +176,8 @@ sighandler(int signal) { int main(int argc, char **argv) { + struct Channel *old_selected_channel; + struct Server *old_selected_server; struct Server *sp; FILE *file; struct pollfd fds[] = { @@ -226,13 +228,18 @@ main(int argc, char **argv) { } } - ui_read(); - wrefresh(nicklist.window); + if (old_selected_channel != selected_channel || old_selected_server != selected_server) { + ui_draw_nicklist(); + wrefresh(nicklist.window); + } + wrefresh(winlist.window); wrefresh(mainwindow.window); - /* always refresh input last */ - wrefresh(inputwindow.window); + ui_read(); + + old_selected_channel = selected_channel; + old_selected_server = selected_server; } return 0; diff --git a/nick.c b/nick.c @@ -177,6 +177,7 @@ nick_remove(struct Nick **head, char *nick) { if (p->next != NULL) p->next->prev = p->prev; nick_free(p); + return 1; } diff --git a/ui.c b/ui.c @@ -98,7 +98,6 @@ ui_init(void) { ui_redraw(); - wprintw(nicklist.window, "nicklist"); wprintw(winlist.window, "winlist"); } @@ -116,37 +115,32 @@ ui_read(void) { int key; switch (key = wgetch(stdscr)) { + case ERR: + /* this happens due to nodelay */ + return; case KEY_RESIZE: ui_redraw(); - break; + return; case KEY_BACKSPACE: if (input.counter) { memmove(&input.string[input.counter - 1], &input.string[input.counter], strlen(&input.string[input.counter]) + 1); input.counter--; - ui_draw_input(); } break; case KEY_LEFT: - if (input.counter) { + if (input.counter) input.counter--; - ui_draw_input(); - } break; case KEY_RIGHT: - if (input.string[input.counter]) { + if (input.string[input.counter]) input.counter++; - ui_draw_input(); - } break; case '\n': - exit(0); - } command_eval(input.string); memset(input.string, '\0', sizeof(input.string)); input.counter = 0; - ui_draw_input(); break; default: if (isprint(key) || iscntrl(key)) { @@ -154,9 +148,10 @@ ui_read(void) { &input.string[input.counter], strlen(&input.string[input.counter])); input.string[input.counter++] = key; - ui_draw_input(); } } + + ui_draw_input(); } void @@ -212,6 +207,7 @@ ui_redraw(void) { mvhline(LINES - 2, x, '-', COLS - x - rx); + ui_draw_nicklist(); ui_draw_input(); } @@ -235,4 +231,24 @@ ui_draw_input(void) { } else waddnstr(inputwindow.window, p, 1); } wmove(inputwindow.window, 0, input.counter - offset); + wrefresh(inputwindow.window); +} + +void +ui_draw_nicklist(void) { + struct Nick *p; + + wclear(nicklist.window); + if (!selected_channel || !nicklist.location) + return; + + wmove(nicklist.window, 0, 0); + + /* TODO: sort nicks here + * TODO: more nicks than screen height? */ + for (p = selected_channel->nicks; p; p = p->next) { + /* TODO: colourize nicks */ + wprintw(nicklist.window, "%c%s\n", p->priv, p->nick); + } + wrefresh(nicklist.window); }