diff --git a/src/twc-bootstrap.c b/src/twc-bootstrap.c index 61e46ae..70abfec 100644 --- a/src/twc-bootstrap.c +++ b/src/twc-bootstrap.c @@ -24,37 +24,72 @@ #include "twc-bootstrap.h" char *twc_bootstrap_addresses[] = { - "192.254.75.98", - "31.7.57.236", - "107.161.17.51", - "144.76.60.215", - "23.226.230.47", - "37.59.102.176", - "37.187.46.132", - "178.21.112.187", - "192.210.149.121", - "54.199.139.199", - "63.165.243.15", + "178.62.250.138", + "130.133.110.14", + "104.167.101.29", + "205.185.116.116", + "198.98.51.198", + "108.61.165.198", + "194.249.212.109", + "185.25.116.107", + "192.99.168.140", + "95.215.46.114", + "5.189.176.217", + "148.251.23.146", + "104.223.122.15", + "81.4.110.149", + "95.31.20.151", + "104.233.104.126", + "51.254.84.212", + "5.135.59.163", + "185.58.206.164", + "91.121.66.124", + "92.54.84.70", + "195.93.190.6", + "95.215.44.78", + "163.172.136.118", + "37.97.185.116", + "193.124.186.205", + "80.87.193.193", + "46.229.52.198" }; uint16_t twc_bootstrap_ports[] = { - 33445, 443, 33445, 33445, 33445, - 33445, 33445, 33445, 33445, 33445, - 443, + 33445, 33445, 33445, 33445, 33445, 33445, 33445, 33445, + 33445, 33445, 5190, 2306, 33445, 33445, 33445, 33445, + 33445, 33445, 33445, 33445, 33445, 33445, 33445, 33445, + 33445, 5228, 33445, 33445 }; char *twc_bootstrap_keys[] = { - "951C88B7E75C867418ACDB5D273821372BB5BD652740BCDF623A4FA293E75D2F", - "2A4B50D1D525DA2E669592A20C327B5FAD6C7E5962DC69296F9FEC77C4436E4E", - "7BE3951B97CA4B9ECDDA768E8C52BA19E9E2690AB584787BF4C90E04DBB75111", - "04119E835DF3E78BACF0F84235B300546AF8B936F035185E2A8E9E0A67C8924F", - "A09162D68618E742FFBCA1C2C70385E6679604B2D80EA6E84AD0996A1AC8A074", - "B98A2CEAA6C6A2FADC2C3632D284318B60FE5375CCB41EFA081AB67F500C1B0B", - "5EB67C51D3FF5A9D528D242B669036ED2A30F8A60E674C45E7D43010CB2E1331", - "4B2C19E924972CB9B57732FB172F8A8604DE13EEDA2A6234E348983344B23057", - "F404ABAA1C99A9D37D61AB54898F56793E1DEF8BD46B1038B9D822E8460FAB67", - "7F9C31FE850E97CEFD4C4591DF93FC757C7C12549DDD55F8EEAECC34FE76C029", - "8CD087E31C67568103E8C2A28653337E90E6B8EDA0D765D57C6B5172B4F1F04C", + "788236D34978D1D5BD822F0A5BEBD2C53C64CC31CD3149350EE27D4D9A2F9B6B", + "461FA3776EF0FA655F1A05477DF1B3B614F7D6B124F7DB1DD4FE3C08B03B640F", + "5918AC3C06955962A75AD7DF4F80A5D7C34F7DB9E1498D2E0495DE35B3FE8A57", + "A179B09749AC826FF01F37A9613F6B57118AE014D4196A0E1105A98F93A54702", + "1D5A5F2F5D6233058BF0259B09622FB40B482E4FA0931EB8FD3AB8E7BF7DAF6F", + "8E7D0B859922EF569298B4D261A8CCB5FEA14FB91ED412A7603A585A25698832", + "3CEE1F054081E7A011234883BC4FC39F661A55B73637A5AC293DDF1251D9432B", + "DA4E4ED4B697F2E9B000EEFE3A34B554ACD3F45F5C96EAEA2516DD7FF9AF7B43", + "6A4D0607A296838434A6A7DDF99F50EF9D60A2C510BBF31FE538A25CB6B4652F", + "5823FB947FF24CF83DDFAC3F3BAA18F96EA2018B16CC08429CB97FA502F40C23", + "2B2137E094F743AC8BD44652C55F41DFACC502F125E99E4FE24D40537489E32F", + "7AED21F94D82B05774F697B209628CD5A9AD17E0C073D9329076A4C28ED28147", + "0FB96EEBFB1650DDB52E70CF773DDFCABE25A95CC3BB50FC251082E4B63EF82A", + "9E7BD4793FFECA7F32238FA2361040C09025ED3333744483CA6F3039BFF0211E", + "9CA69BB74DE7C056D1CC6B16AB8A0A38725C0349D187D8996766958584D39340", + "EDEE8F2E839A57820DE3DA4156D88350E53D4161447068A3457EE8F59F362414", + "AEC204B9A4501412D5F0BB67D9C81B5DB3EE6ADA64122D32A3E9B093D544327D", + "2D320F971EF2CA18004416C2AAE7BA52BF7949DB34EA8E2E21AF67BD367BE211", + "24156472041E5F220D1FA11D9DF32F7AD697D59845701CDD7BE7D1785EB9DB39", + "4E3F7D37295664BBD0741B6DBCB6431D6CD77FC4105338C2FC31567BF5C8224A", + "5625A62618CB4FCA70E147A71B29695F38CC65FF0CBD68AD46254585BE564802", + "FB4CE0DDEFEED45F26917053E5D24BDDA0FA0A3D83A672A9DA2375928B37023D", + "672DBE27B4ADB9D5FB105A6BB648B2F8FDB89B3323486A7A21968316E012023C", + "2C289F9F37C20D09DA83565588BF496FAB3764853FA38141817A72E3F18ACA0B", + "E59A0E71ADA20D35BD1B0957059D7EF7E7792B3D680AE25C6F4DBBA09114D165", + "9906D65F2A4751068A59D30505C5FC8AE1A95E0843AE9372EAFA3BAB6AC16C2C", + "B38255EE4B054924F6D79A5E6E5889EC94B6ADF6FE9906F97A3D01E3D083223A", + "813C8F4187833EF0655B10F7752141A352248462A567529A38B6BBF73E979307" }; int twc_bootstrap_count = sizeof(twc_bootstrap_addresses) diff --git a/src/twc-chat.c b/src/twc-chat.c index 0419da7..f095d1f 100644 --- a/src/twc-chat.c +++ b/src/twc-chat.c @@ -45,25 +45,6 @@ twc_chat_buffer_close_callback(const void *pointer, void *data, struct t_gui_buffer *weechat_buffer); -/** - * Hash a Tox ID for the nicklist hashtable in group chat objects. - */ -unsigned long long -twc_tox_id_hash_callback(struct t_hashtable *hashtable, const void *key) -{ - return twc_hash_tox_id(key); -} - -/** - * Compare two Tox IDs for the nicklist hashtable in group chat objects. - */ -int -twc_tox_id_compare_callback(struct t_hashtable *hashtable, - const void *id1, const void *id2) -{ - return memcmp(id1, id2, TOX_PUBLIC_KEY_SIZE); -} - /** * Create a new chat. */ @@ -81,9 +62,25 @@ twc_chat_new(struct t_twc_profile *profile, const char *name) size_t full_name_size = strlen(profile->name) + 1 + strlen(name) + 1; char *full_name = malloc(full_name_size); snprintf(full_name, full_name_size, "%s/%s", profile->name, name); - chat->buffer = weechat_buffer_new(full_name, - twc_chat_buffer_input_callback, chat, NULL, - twc_chat_buffer_close_callback, chat, NULL); + chat->buffer = weechat_buffer_search("tox", full_name); + if (!(chat->buffer)) + { + chat->buffer = weechat_buffer_new(full_name, + twc_chat_buffer_input_callback, chat, NULL, + twc_chat_buffer_close_callback, chat, NULL); + } + else + { + weechat_buffer_set_pointer(chat->buffer, + "input_callback", + twc_chat_buffer_input_callback); + weechat_buffer_set_pointer(chat->buffer, "input_callback_pointer", chat); + weechat_buffer_set_pointer(chat->buffer, + "close_callback", + twc_chat_buffer_close_callback); + weechat_buffer_set_pointer(chat->buffer, "close_callback_pointer", chat); + } + free(full_name); if (!(chat->buffer)) @@ -136,11 +133,7 @@ twc_chat_new_group(struct t_twc_profile *profile, int32_t group_number) chat->nicklist_group = weechat_nicklist_add_group(chat->buffer, NULL, NULL, NULL, true); - chat->nicks = weechat_hashtable_new(32, - WEECHAT_HASHTABLE_BUFFER, - WEECHAT_HASHTABLE_POINTER, - twc_tox_id_hash_callback, - twc_tox_id_compare_callback); + chat->nicks = weechat_list_new(); weechat_buffer_set(chat->buffer, "nicklist", "1"); } @@ -156,6 +149,9 @@ twc_chat_refresh(const struct t_twc_chat *chat) { char *name = NULL; char *title = NULL; + bool rc = false; + TOX_ERR_CONFERENCE_TITLE err = TOX_ERR_CONFERENCE_TITLE_OK; + if (chat->friend_number >= 0) { name = twc_get_name_nt(chat->profile->tox, @@ -166,10 +162,12 @@ twc_chat_refresh(const struct t_twc_chat *chat) else if (chat->group_number >= 0) { char group_name[TOX_MAX_NAME_LENGTH + 1] = {0}; - int len = tox_group_get_title(chat->profile->tox, chat->group_number, - (uint8_t *)group_name, - TOX_MAX_NAME_LENGTH); - if (len <= 0) + int len = tox_conference_get_title_size(chat->profile->tox, chat->group_number, + &err); + if ((err == TOX_ERR_CONFERENCE_TITLE_OK) && (len <= TOX_MAX_NAME_LENGTH)) + rc = tox_conference_get_title(chat->profile->tox, chat->group_number, + (uint8_t *)group_name, &err); + if (!rc) sprintf(group_name, "Group Chat %d", chat->group_number); name = title = strdup((char *)group_name); @@ -282,18 +280,18 @@ twc_chat_print_message(struct t_twc_chat *chat, const char *color, const char *sender, const char *message, - enum TWC_MESSAGE_TYPE message_type) + TOX_MESSAGE_TYPE message_type) { switch (message_type) { - case TWC_MESSAGE_TYPE_MESSAGE: - weechat_printf_tags(chat->buffer, tags, + case TOX_MESSAGE_TYPE_NORMAL: + weechat_printf_date_tags(chat->buffer, 0, tags, "%s%s%s\t%s", color, sender, weechat_color("reset"), message); break; - case TWC_MESSAGE_TYPE_ACTION: - weechat_printf_tags(chat->buffer, tags, + case TOX_MESSAGE_TYPE_ACTION: + weechat_printf_date_tags(chat->buffer, 0, tags, "%s%s%s%s %s", weechat_prefix("action"), color, sender, @@ -307,27 +305,44 @@ twc_chat_print_message(struct t_twc_chat *chat, */ void twc_chat_send_message(struct t_twc_chat *chat, const char *message, - enum TWC_MESSAGE_TYPE message_type) + TOX_MESSAGE_TYPE message_type) { + TOX_ERR_CONFERENCE_SEND_MESSAGE err = TOX_ERR_CONFERENCE_SEND_MESSAGE_OK; if (chat->friend_number >= 0) { twc_message_queue_add_friend_message(chat->profile, chat->friend_number, message, message_type); char *name = twc_get_self_name_nt(chat->profile->tox); - twc_chat_print_message(chat, "", + twc_chat_print_message(chat, "notify_message", weechat_color("chat_nick_self"), name, message, message_type); free(name); } else if (chat->group_number >= 0) { - if (message_type == TWC_MESSAGE_TYPE_MESSAGE) - tox_group_message_send(chat->profile->tox, chat->group_number, - (uint8_t *)message, strlen(message)); - else if (message_type == TWC_MESSAGE_TYPE_ACTION) - tox_group_action_send(chat->profile->tox, chat->group_number, - (uint8_t *)message, strlen(message)); + int len = strlen(message); + while (len > 0) + { + int fit_len = twc_fit_utf8(message, TWC_MAX_GROUP_MESSAGE_LENGTH); + err = TOX_ERR_CONFERENCE_SEND_MESSAGE_OK; + tox_conference_send_message(chat->profile->tox, chat->group_number, + message_type, (uint8_t *)message, fit_len, + &err); + if (err != TOX_ERR_CONFERENCE_SEND_MESSAGE_OK) + break; + message += fit_len; + len -= fit_len; + } + if (err != TOX_ERR_CONFERENCE_SEND_MESSAGE_OK) + { + weechat_printf(chat->buffer, + "%s%sFailed to send message with error %d%s", + weechat_prefix("error"), + weechat_color("chat_highlight"), + err, + weechat_color("reset")); + } } } @@ -341,7 +356,7 @@ twc_chat_buffer_input_callback(const void *pointer, void *data, { /* TODO: don't strip the const */ struct t_twc_chat *chat = (void *)pointer; - twc_chat_send_message(chat, input_data, TWC_MESSAGE_TYPE_MESSAGE); + twc_chat_send_message(chat, input_data, TOX_MESSAGE_TYPE_NORMAL); return WEECHAT_RC_OK; } @@ -354,16 +369,17 @@ twc_chat_buffer_close_callback(const void *pointer, void *data, struct t_gui_buffer *weechat_buffer) { /* TODO: don't strip the const */ + TOX_ERR_CONFERENCE_DELETE err = TOX_ERR_CONFERENCE_DELETE_OK; struct t_twc_chat *chat = (void *)pointer; if (chat->profile->tox && chat->group_number >= 0) { - int rc = tox_del_groupchat(chat->profile->tox, chat->group_number); - if (rc != 0) + tox_conference_delete(chat->profile->tox, chat->group_number, &err); + if (err != TOX_ERR_CONFERENCE_DELETE_OK) { weechat_printf(chat->profile->buffer, - "%swarning: failed to leave group chat", - weechat_prefix("error")); + "%swarning: failed to leave group chat with error %d", + weechat_prefix("error"), err); } } @@ -379,8 +395,12 @@ twc_chat_buffer_close_callback(const void *pointer, void *data, void twc_chat_free(struct t_twc_chat *chat) { + weechat_nicklist_remove_all(chat->buffer); if (chat->nicks) - weechat_hashtable_free(chat->nicks); + { + weechat_list_remove_all(chat->nicks); + weechat_list_free(chat->nicks); + } free(chat); } diff --git a/src/twc-chat.h b/src/twc-chat.h index f87d026..35845ac 100644 --- a/src/twc-chat.h +++ b/src/twc-chat.h @@ -29,12 +29,6 @@ extern const char *twc_tag_unsent_message; extern const char *twc_tag_sent_message; extern const char *twc_tag_received_message; -enum TWC_MESSAGE_TYPE -{ - TWC_MESSAGE_TYPE_MESSAGE, - TWC_MESSAGE_TYPE_ACTION, -}; - struct t_twc_chat { struct t_twc_profile *profile; @@ -44,7 +38,7 @@ struct t_twc_chat int32_t group_number; struct t_gui_nick_group *nicklist_group; - struct t_hashtable *nicks; + struct t_weelist *nicks; }; struct t_twc_chat * @@ -64,11 +58,11 @@ twc_chat_print_message(struct t_twc_chat *chat, const char *color, const char *sender, const char *message, - enum TWC_MESSAGE_TYPE message_type); + TOX_MESSAGE_TYPE message_type); void twc_chat_send_message(struct t_twc_chat *chat, const char *message, - enum TWC_MESSAGE_TYPE message_type); + TOX_MESSAGE_TYPE message_type); void twc_chat_queue_refresh(struct t_twc_chat *chat); diff --git a/src/twc-commands.c b/src/twc-commands.c index 260dd91..c547778 100644 --- a/src/twc-commands.c +++ b/src/twc-commands.c @@ -242,7 +242,7 @@ twc_cmd_friend(const void *pointer, void *data, struct t_gui_buffer *buffer, } weechat_printf(profile->buffer, - "%s[#] Name [Tox ID (short)]", + "%s[#] Name [Tox ID (short)] Status", weechat_prefix("network")); for (size_t i = 0; i < friend_count; ++i) @@ -252,12 +252,16 @@ twc_cmd_friend(const void *pointer, void *data, struct t_gui_buffer *buffer, char *hex_address = twc_get_friend_id_short(profile->tox, friend_number); + char *status = twc_get_status_message_nt(profile->tox, friend_number); + char *online_color = + (tox_friend_get_connection_status(profile->tox, friend_number, NULL) != TOX_CONNECTION_NONE) ? "chat_nick" : "chat_nick_offline"; weechat_printf(profile->buffer, - "%s[%d] %s [%s]", + "%s[%d] %s%s [%s]%s %s", weechat_prefix("network"), - friend_number, name, hex_address); + friend_number, weechat_color(online_color), name, hex_address, weechat_color("reset"), status); free(name); + free(status); free(hex_address); } @@ -380,7 +384,7 @@ twc_cmd_friend(const void *pointer, void *data, struct t_gui_buffer *buffer, TWC_CHECK_FRIEND_NUMBER(profile, friend_number, argv[2]); char *name = twc_get_name_nt(profile->tox, friend_number); - if (tox_friend_delete(profile->tox, friend_number, NULL) == 0) + if (tox_friend_delete(profile->tox, friend_number, NULL)) { weechat_printf(profile->buffer, "%sRemoved %s from friend list.", @@ -464,7 +468,7 @@ twc_cmd_friend(const void *pointer, void *data, struct t_gui_buffer *buffer, if (accept) { - if (twc_friend_request_accept(request)) + if (!twc_friend_request_accept(request)) { weechat_printf(profile->buffer, "%sCould not accept friend request from %s", @@ -530,19 +534,20 @@ twc_cmd_group(const void *pointer, void *data, struct t_gui_buffer *buffer, int argc, char **argv, char **argv_eol) { struct t_twc_profile *profile = twc_profile_search_buffer(buffer); + TOX_ERR_CONFERENCE_NEW err = TOX_ERR_CONFERENCE_NEW_OK; TWC_CHECK_PROFILE(profile); TWC_CHECK_PROFILE_LOADED(profile); // /group create if (argc == 2 && weechat_strcasecmp(argv[1], "create") == 0) { - int rc = tox_add_groupchat(profile->tox); - if (rc >= 0) + int rc = tox_conference_new(profile->tox, &err); + if (err == TOX_ERR_CONFERENCE_NEW_OK) twc_chat_search_group(profile, rc, true); else weechat_printf(profile->buffer, - "%sCould not create group chat (unknown error)", - weechat_prefix("error")); + "%sCould not create group chat with error %d", + weechat_prefix("error"), err); return WEECHAT_RC_OK; } @@ -622,6 +627,7 @@ twc_cmd_invite(const void *pointer, void *data, struct t_gui_buffer *buffer, if (argc == 1) return WEECHAT_RC_ERROR; + TOX_ERR_CONFERENCE_INVITE err = TOX_ERR_CONFERENCE_INVITE_OK; struct t_twc_chat *chat = twc_chat_search_buffer(buffer); TWC_CHECK_PROFILE_LOADED(chat->profile); @@ -630,10 +636,9 @@ twc_cmd_invite(const void *pointer, void *data, struct t_gui_buffer *buffer, int32_t friend_number = twc_match_friend(chat->profile, argv_eol[1]); TWC_CHECK_FRIEND_NUMBER(chat->profile, friend_number, argv_eol[1]); - int rc = tox_invite_friend(chat->profile->tox, - friend_number, chat->group_number); + tox_conference_invite(chat->profile->tox, friend_number, chat->group_number, &err); - if (rc == 0) + if (err == TOX_ERR_CONFERENCE_INVITE_OK) { char *friend_name = twc_get_name_nt(chat->profile->tox, friend_number); weechat_printf(chat->buffer, "%sInvited %s to the group chat.", @@ -643,8 +648,8 @@ twc_cmd_invite(const void *pointer, void *data, struct t_gui_buffer *buffer, else { weechat_printf(chat->buffer, - "%sFailed to send group chat invite (unknown error)", - weechat_prefix("error")); + "%sFailed to send group chat invite with error %d", + weechat_prefix("error"), err); } return WEECHAT_RC_OK; @@ -664,7 +669,7 @@ twc_cmd_me(const void *pointer, void *data, struct t_gui_buffer *buffer, TWC_CHECK_CHAT(chat); TWC_CHECK_PROFILE_LOADED(chat->profile); - twc_chat_send_message(chat, argv_eol[1], TWC_MESSAGE_TYPE_ACTION); + twc_chat_send_message(chat, argv_eol[1], TOX_MESSAGE_TYPE_ACTION); return WEECHAT_RC_OK; } @@ -710,7 +715,7 @@ twc_cmd_msg(const void *pointer, void *data, struct t_gui_buffer *buffer, if (message) twc_chat_send_message(chat, weechat_string_strip(message, 1, 1, " "), - TWC_MESSAGE_TYPE_MESSAGE); + TOX_MESSAGE_TYPE_NORMAL); return WEECHAT_RC_OK; } @@ -856,11 +861,12 @@ twc_cmd_part(const void *pointer, void *data, struct t_gui_buffer *buffer, int argc, char **argv, char **argv_eol) { struct t_twc_chat *chat = twc_chat_search_buffer(buffer); + TOX_ERR_CONFERENCE_DELETE err = TOX_ERR_CONFERENCE_DELETE_OK; TWC_CHECK_PROFILE_LOADED(chat->profile); TWC_CHECK_GROUP_CHAT(chat); - int rc = tox_del_groupchat(chat->profile->tox, chat->group_number); - if (rc == 0) + tox_conference_delete(chat->profile->tox, chat->group_number, &err); + if (err == TOX_ERR_CONFERENCE_DELETE_OK) { weechat_printf(chat->buffer, "%sYou have left the group chat", @@ -869,8 +875,8 @@ twc_cmd_part(const void *pointer, void *data, struct t_gui_buffer *buffer, else { weechat_printf(chat->buffer, - "%sFailed to leave group chat", - weechat_prefix("error")); + "%sFailed to leave group chat with error %d", + weechat_prefix("error"), err); } weechat_buffer_set_pointer(chat->buffer, "input_callback", NULL); @@ -992,6 +998,8 @@ twc_cmd_topic(const void *pointer, void *data, struct t_gui_buffer *buffer, if (argc == 1) return WEECHAT_RC_ERROR; + TOX_ERR_CONFERENCE_TITLE err = TOX_ERR_CONFERENCE_TITLE_OK; + struct t_twc_chat *chat = twc_chat_search_buffer(buffer); TWC_CHECK_CHAT(chat); TWC_CHECK_PROFILE_LOADED(chat->profile); @@ -1007,9 +1015,9 @@ twc_cmd_topic(const void *pointer, void *data, struct t_gui_buffer *buffer, char *topic = argv_eol[1]; - int result = tox_group_set_title(chat->profile->tox, chat->group_number, - (uint8_t *)topic, strlen(topic)); - if (result == -1) + tox_conference_set_title(chat->profile->tox, chat->group_number, + (uint8_t *)topic, strlen(topic), &err); + if (err != TOX_ERR_CONFERENCE_TITLE_OK) { weechat_printf(chat->buffer, "%s%s", weechat_prefix("error"), "Could not set topic."); diff --git a/src/twc-config.c b/src/twc-config.c index b6d1c50..3e55916 100644 --- a/src/twc-config.c +++ b/src/twc-config.c @@ -42,6 +42,7 @@ char *twc_profile_option_names[TWC_PROFILE_NUM_OPTIONS] = { "save_file", "autoload", + "autojoin", "max_friend_requests", "proxy_address", "proxy_port", @@ -198,6 +199,12 @@ twc_config_init_option(struct t_config_section *section, "network when WeeChat starts"; default_value = "off"; break; + case TWC_PROFILE_OPTION_AUTOJOIN: + type = "boolean"; + description = "automatically join all groups you are invited in " + "by your friends"; + default_value = "off"; + break; case TWC_PROFILE_OPTION_IPV6: type = "boolean"; description = "use IPv6 as well as IPv4 to connect to the Tox " diff --git a/src/twc-friend-request.c b/src/twc-friend-request.c index 9045aa8..28ad623 100644 --- a/src/twc-friend-request.c +++ b/src/twc-friend-request.c @@ -67,7 +67,7 @@ twc_friend_request_add(struct t_twc_profile *profile, bool twc_friend_request_accept(struct t_twc_friend_request *request) { - TOX_ERR_FRIEND_ADD err; + TOX_ERR_FRIEND_ADD err = TOX_ERR_FRIEND_ADD_OK; tox_friend_add_norequest(request->profile->tox, request->tox_id, &err); twc_friend_request_remove(request); diff --git a/src/twc-group-invite.c b/src/twc-group-invite.c index 7694f14..b2822fb 100644 --- a/src/twc-group-invite.c +++ b/src/twc-group-invite.c @@ -71,15 +71,15 @@ int twc_group_chat_invite_join(struct t_twc_group_chat_invite *invite) { int rc; + TOX_ERR_CONFERENCE_JOIN err = TOX_ERR_CONFERENCE_JOIN_OK; switch (invite->group_chat_type) { - case TOX_GROUPCHAT_TYPE_TEXT: - rc = tox_join_groupchat(invite->profile->tox, - invite->friend_number, - invite->data, invite->data_size); + case TOX_CONFERENCE_TYPE_TEXT: + rc = tox_conference_join(invite->profile->tox, invite->friend_number, + invite->data, invite->data_size, &err); break; #ifdef TOXAV_ENABLED - case TOX_GROUPCHAT_TYPE_AV: + case TOX_CONFERENCE_TYPE_AV: rc = toxav_join_av_groupchat(invite->profile->tox, invite->friend_number, invite->data, invite->data_size, @@ -93,6 +93,8 @@ twc_group_chat_invite_join(struct t_twc_group_chat_invite *invite) twc_group_chat_invite_remove(invite); + if (err != TOX_ERR_CONFERENCE_JOIN_OK) + return -1; return rc; } diff --git a/src/twc-group-invite.h b/src/twc-group-invite.h index 1dc86e7..98d192d 100644 --- a/src/twc-group-invite.h +++ b/src/twc-group-invite.h @@ -33,7 +33,7 @@ struct t_twc_group_chat_invite { struct t_twc_profile *profile; - int32_t friend_number; + uint32_t friend_number; uint8_t group_chat_type; uint8_t *data; size_t data_size; diff --git a/src/twc-message-queue.c b/src/twc-message-queue.c index 9e121f5..b849649 100644 --- a/src/twc-message-queue.c +++ b/src/twc-message-queue.c @@ -56,23 +56,32 @@ void twc_message_queue_add_friend_message(struct t_twc_profile *profile, int32_t friend_number, const char *message, - enum TWC_MESSAGE_TYPE message_type) + TOX_MESSAGE_TYPE message_type) { - struct t_twc_queued_message *queued_message - = malloc(sizeof(struct t_twc_queued_message)); + int len = strlen(message); + while (len > 0) + { + int fit_len = twc_fit_utf8(message, TWC_MAX_FRIEND_MESSAGE_LENGTH); - time_t rawtime = time(NULL); - queued_message->time = malloc(sizeof(struct tm)); - memcpy(queued_message->time, gmtime(&rawtime), sizeof(struct tm)); + struct t_twc_queued_message *queued_message + = malloc(sizeof(struct t_twc_queued_message)); - queued_message->message = strdup(message); - queued_message->message_type = message_type; + time_t rawtime = time(NULL); + queued_message->time = malloc(sizeof(struct tm)); + memcpy(queued_message->time, gmtime(&rawtime), sizeof(struct tm)); - // create a queue if needed and add message - struct t_twc_list *message_queue - = twc_message_queue_get_or_create(profile, friend_number); - twc_list_item_new_data_add(message_queue, queued_message); + queued_message->message = strndup(message, fit_len); + queued_message->message_type = message_type; + message += fit_len; + len -= fit_len; + + // create a queue if needed and add message + struct t_twc_list *message_queue + = twc_message_queue_get_or_create(profile, friend_number); + twc_list_item_new_data_add(message_queue, queued_message); + } + // flush if friend is online if (profile->tox && (tox_friend_get_connection_status(profile->tox, friend_number, NULL) != TOX_CONNECTION_NONE)) @@ -88,7 +97,6 @@ twc_message_queue_flush_friend(struct t_twc_profile *profile, { struct t_twc_list *message_queue = twc_message_queue_get_or_create(profile, friend_number); - size_t index; struct t_twc_list_item *item; twc_list_foreach(message_queue, index, item) @@ -99,21 +107,55 @@ twc_message_queue_flush_friend(struct t_twc_profile *profile, TOX_ERR_FRIEND_SEND_MESSAGE err; (void)tox_friend_send_message(profile->tox, friend_number, - queued_message->message_type == TWC_MESSAGE_TYPE_MESSAGE? - TOX_MESSAGE_TYPE_NORMAL: - TOX_MESSAGE_TYPE_ACTION, + queued_message->message_type, (uint8_t *)queued_message->message, strlen(queued_message->message), &err); - if (err != TOX_ERR_FRIEND_SEND_MESSAGE_OK) + if (err == TOX_ERR_FRIEND_SEND_MESSAGE_FRIEND_NOT_CONNECTED) { // break if message send failed break; } else { - // message was sent, free it + char *err_str; + // check if error occured + switch (err) + { + case TOX_ERR_FRIEND_SEND_MESSAGE_TOO_LONG: + err_str = "message too long"; + break; + case TOX_ERR_FRIEND_SEND_MESSAGE_NULL: + err_str = "NULL fields for tox_friend_send_message"; + break; + case TOX_ERR_FRIEND_SEND_MESSAGE_FRIEND_NOT_FOUND: + err_str = "friend not found"; + break; + case TOX_ERR_FRIEND_SEND_MESSAGE_SENDQ: + err_str = "queue allocation error"; + break; + case TOX_ERR_FRIEND_SEND_MESSAGE_EMPTY: + err_str = "tried to send empty message"; + break; + case TOX_ERR_FRIEND_SEND_MESSAGE_OK: + err_str = "no error"; + break; + default: + err_str = "unknown error"; + } + if (err != TOX_ERR_FRIEND_SEND_MESSAGE_OK) + { + struct t_twc_chat *friend_chat + = twc_chat_search_friend(profile, friend_number, true); + + weechat_printf(friend_chat->buffer, + "%s%sFailed to send message: %s%s", + weechat_prefix("error"), + weechat_color("chat_highlight"), + err_str, + weechat_color("reset")); + } twc_message_queue_free_message(queued_message); item->queued_message = NULL; } diff --git a/src/twc-message-queue.h b/src/twc-message-queue.h index 949c267..9bc3327 100644 --- a/src/twc-message-queue.h +++ b/src/twc-message-queue.h @@ -33,14 +33,14 @@ struct t_twc_queued_message { struct tm *time; char *message; - enum TWC_MESSAGE_TYPE message_type; + TOX_MESSAGE_TYPE message_type; }; void twc_message_queue_add_friend_message(struct t_twc_profile *profile, int32_t friend_number, const char *message, - enum TWC_MESSAGE_TYPE message_type); + TOX_MESSAGE_TYPE message_type); void twc_message_queue_flush_friend(struct t_twc_profile *profile, diff --git a/src/twc-profile.c b/src/twc-profile.c index 820ab3c..ccdcf64 100644 --- a/src/twc-profile.c +++ b/src/twc-profile.c @@ -285,6 +285,10 @@ twc_profile_load(struct t_twc_profile *profile) profile, NULL); if (!(profile->buffer)) return TWC_RC_ERROR; + + profile->nicklist_group = weechat_nicklist_add_group(profile->buffer, NULL, + NULL, NULL, true); + weechat_buffer_set(profile->buffer, "nicklist", "1"); } weechat_printf(profile->buffer, @@ -412,17 +416,16 @@ twc_profile_load(struct t_twc_profile *profile) twc_do_timer_cb(profile, NULL, 0); // register Tox callbacks - tox_callback_friend_message(profile->tox, twc_friend_message_callback, profile); - tox_callback_friend_connection_status(profile->tox, twc_connection_status_callback, profile); - tox_callback_friend_name(profile->tox, twc_name_change_callback, profile); - tox_callback_friend_status(profile->tox, twc_user_status_callback, profile); - tox_callback_friend_status_message(profile->tox, twc_status_message_callback, profile); - tox_callback_friend_request(profile->tox, twc_friend_request_callback, profile); - tox_callback_group_invite(profile->tox, twc_group_invite_callback, profile); - tox_callback_group_message(profile->tox, twc_group_message_callback, profile); - tox_callback_group_action(profile->tox, twc_group_action_callback, profile); - tox_callback_group_namelist_change(profile->tox, twc_group_namelist_change_callback, profile); - tox_callback_group_title(profile->tox, twc_group_title_callback, profile); + tox_callback_friend_message(profile->tox, twc_friend_message_callback); + tox_callback_friend_connection_status(profile->tox, twc_connection_status_callback); + tox_callback_friend_name(profile->tox, twc_name_change_callback); + tox_callback_friend_status(profile->tox, twc_user_status_callback); + tox_callback_friend_status_message(profile->tox, twc_status_message_callback); + tox_callback_friend_request(profile->tox, twc_friend_request_callback); + tox_callback_conference_invite(profile->tox, twc_group_invite_callback); + tox_callback_conference_message(profile->tox, twc_group_message_callback); + tox_callback_conference_namelist_change(profile->tox, twc_group_namelist_change_callback); + tox_callback_conference_title(profile->tox, twc_group_title_callback); return TWC_RC_OK; } diff --git a/src/twc-profile.h b/src/twc-profile.h index 1245928..d94fbbd 100644 --- a/src/twc-profile.h +++ b/src/twc-profile.h @@ -30,6 +30,7 @@ enum t_twc_profile_option { TWC_PROFILE_OPTION_SAVEFILE = 0, TWC_PROFILE_OPTION_AUTOLOAD, + TWC_PROFILE_OPTION_AUTOJOIN, TWC_PROFILE_OPTION_MAX_FRIEND_REQUESTS, TWC_PROFILE_OPTION_PROXY_ADDRESS, TWC_PROFILE_OPTION_PROXY_PORT, @@ -50,6 +51,7 @@ struct t_twc_profile int tox_online; struct t_gui_buffer *buffer; + struct t_gui_nick_group *nicklist_group; struct t_hook *tox_do_timer; struct t_twc_list *chats; diff --git a/src/twc-tox-callbacks.c b/src/twc-tox-callbacks.c index 9862424..0202ee8 100644 --- a/src/twc-tox-callbacks.c +++ b/src/twc-tox-callbacks.c @@ -22,6 +22,10 @@ #include #include +#ifdef TOXAV_ENABLED + #include +#endif // TOXAV_ENABLED + #include "twc.h" #include "twc-profile.h" #include "twc-chat.h" @@ -39,7 +43,7 @@ twc_do_timer_cb(const void *pointer, void *data, /* TODO: don't strip the const */ struct t_twc_profile *profile = (void *)pointer; - tox_iterate(profile->tox); + tox_iterate(profile->tox, profile); struct t_hook *hook = weechat_hook_timer(tox_iteration_interval(profile->tox), 0, 1, twc_do_timer_cb, profile, NULL); profile->tox_do_timer = hook; @@ -67,7 +71,7 @@ twc_friend_message_callback(Tox *tox, uint32_t friend_number, char *name = twc_get_name_nt(profile->tox, friend_number); char *message_nt = twc_null_terminate(message, length); - twc_chat_print_message(chat, "", weechat_color("chat_nick_other"), name, + twc_chat_print_message(chat, "notify_private", weechat_color("chat_nick_other"), name, message_nt, type); free(name); @@ -80,21 +84,47 @@ twc_connection_status_callback(Tox *tox, uint32_t friend_number, { struct t_twc_profile *profile = data; char *name = twc_get_name_nt(profile->tox, friend_number); + struct t_gui_nick *nick = NULL; + struct t_twc_chat *chat = twc_chat_search_friend(profile, + friend_number, + false); // TODO: print in friend's buffer if it exists if (status == 0) { + nick = weechat_nicklist_search_nick(profile->buffer, + profile->nicklist_group, name); + if (nick) + weechat_nicklist_remove_nick(profile->buffer, nick); + weechat_printf(profile->buffer, "%s%s just went offline.", weechat_prefix("network"), name); + if (chat) + { + weechat_printf(chat->buffer, + "%s%s just went offline.", + weechat_prefix("network"), + name); + } } else if (status == 1) { + weechat_nicklist_add_nick(profile->buffer, profile->nicklist_group, + name, NULL, NULL, NULL, 1); + weechat_printf(profile->buffer, "%s%s just came online.", weechat_prefix("network"), name); + if (chat) + { + weechat_printf(chat->buffer, + "%s%s just came online.", + weechat_prefix("network"), + name); + } twc_message_queue_flush_friend(profile, friend_number); } free(name); @@ -106,6 +136,7 @@ twc_name_change_callback(Tox *tox, uint32_t friend_number, void *data) { struct t_twc_profile *profile = data; + struct t_gui_nick *nick = NULL; struct t_twc_chat *chat = twc_chat_search_friend(profile, friend_number, false); @@ -125,6 +156,14 @@ twc_name_change_callback(Tox *tox, uint32_t friend_number, old_name, new_name); } + nick = weechat_nicklist_search_nick(profile->buffer, + profile->nicklist_group, old_name); + if (nick) + weechat_nicklist_remove_nick(profile->buffer, nick); + + weechat_nicklist_add_nick(profile->buffer, profile->nicklist_group, + new_name, NULL, NULL, NULL, 1); + weechat_printf(profile->buffer, "%s%s is now known as %s", weechat_prefix("network"), @@ -172,7 +211,7 @@ twc_friend_request_callback(Tox *tox, const uint8_t *public_key, if (rc == -1) { - weechat_printf(profile->buffer, + weechat_printf_date_tags(profile->buffer, 0, "notify_highlight", "%sReceived a friend request, but your friend request list is full!", weechat_prefix("warning")); } @@ -181,7 +220,7 @@ twc_friend_request_callback(Tox *tox, const uint8_t *public_key, char hex_address[TOX_PUBLIC_KEY_SIZE * 2 + 1]; twc_bin2hex(public_key, TOX_PUBLIC_KEY_SIZE, hex_address); - weechat_printf(profile->buffer, + weechat_printf_date_tags(profile->buffer, 0, "notify_highlight", "%sReceived a friend request from %s with message \"%s\"; " "accept it with \"/friend accept %d\"", weechat_prefix("network"), @@ -189,7 +228,7 @@ twc_friend_request_callback(Tox *tox, const uint8_t *public_key, if (rc == -2) { - weechat_printf(profile->buffer, + weechat_printf_date_tags(profile->buffer, 0, "notify_highlight", "%sFailed to save friend request, try manually " "accepting with /friend add", weechat_prefix("error")); @@ -201,48 +240,134 @@ twc_friend_request_callback(Tox *tox, const uint8_t *public_key, void twc_group_invite_callback(Tox *tox, - int32_t friend_number, uint8_t type, - const uint8_t *invite_data, uint16_t length, + uint32_t friend_number, TOX_CONFERENCE_TYPE type, + const uint8_t *invite_data, size_t length, void *data) { + TOX_ERR_CONFERENCE_JOIN err = TOX_ERR_CONFERENCE_JOIN_OK; struct t_twc_profile *profile = data; char *friend_name = twc_get_name_nt(profile->tox, friend_number); struct t_twc_chat *friend_chat - = twc_chat_search_friend(profile, friend_number, true); - - int64_t rc = twc_group_chat_invite_add(profile, friend_number, type, - (uint8_t *)invite_data, length); + = twc_chat_search_friend(profile, friend_number, false); + int64_t rc; + char *tags; char *type_str; switch (type) { - case TOX_GROUPCHAT_TYPE_TEXT: + case TOX_CONFERENCE_TYPE_TEXT: type_str = "a text-only group chat"; break; - case TOX_GROUPCHAT_TYPE_AV: - type_str = "an audio/video group chat"; break; + case TOX_CONFERENCE_TYPE_AV: + type_str = "an audio/vikdeo group chat"; break; default: type_str = "a group chat"; break; } - if (rc >= 0) + if (TWC_PROFILE_OPTION_BOOLEAN(profile, TWC_PROFILE_OPTION_AUTOJOIN)) { - weechat_printf(friend_chat->buffer, - "%s%s%s%s invites you to join %s. Type " - "\"/group join %d\" to accept.", - weechat_prefix("network"), - weechat_color("chat_nick_other"), friend_name, - weechat_color("reset"), type_str, rc); + switch (type) + { + case TOX_CONFERENCE_TYPE_TEXT: + rc = tox_conference_join(tox, friend_number, + invite_data, length, &err); + break; +#ifdef TOXAV_ENABLED + case TOX_CONFERENCE_TYPE_AV: + rc = toxav_join_av_groupchat(tox, friend_number, + invite_data, length, + NULL, NULL); + break; +#endif + default: + rc = -1; + break; + } + + if (rc >= 0 && err == TOX_ERR_CONFERENCE_JOIN_OK) + { + tags = "notify_private"; + if (friend_chat) + { + weechat_printf_date_tags(friend_chat->buffer, 0, tags, + "%sWe joined the %s%s%s's invite to %s.", + weechat_prefix("network"), + weechat_color("chat_nick_other"), friend_name, + weechat_color("reset"), type_str); + tags = ""; + } + weechat_printf_date_tags(profile->buffer, 0, tags, + "%sWe joined the %s%s%s's invite to %s.", + weechat_prefix("network"), + weechat_color("chat_nick_other"), friend_name, + weechat_color("reset"), type_str); + } + else + { + tags = "notify_highlight"; + if (friend_chat) + { + weechat_printf_date_tags(friend_chat->buffer, 0, tags, + "%s%s%s%s invites you to join %s, but we failed to " + "process the invite. Please try again.", + weechat_prefix("network"), + weechat_color("chat_nick_other"), friend_name, + weechat_color("reset")); + tags = ""; + } + weechat_printf_date_tags(profile->buffer, 0, tags, + "%s%s%s%s invites you to join %s, but we failed to " + "process the invite. Please try again.", + weechat_prefix("network"), + weechat_color("chat_nick_other"), friend_name, + weechat_color("reset")); + } } else { - weechat_printf(friend_chat->buffer, - "%s%s%s%s invites you to join %s, but we failed to " - "process the invite. Please try again.", - weechat_prefix("network"), - weechat_color("chat_nick_other"), friend_name, - weechat_color("reset"), rc); - } + rc = twc_group_chat_invite_add(profile, friend_number, type, + (uint8_t *)invite_data, length); + if (rc >= 0) + { + tags = "notify_highlight"; + if (friend_chat) + { + weechat_printf_date_tags(friend_chat->buffer, 0, tags, + "%s%s%s%s invites you to join %s. Type " + "\"/group join %d\" to accept.", + weechat_prefix("network"), + weechat_color("chat_nick_other"), friend_name, + weechat_color("reset"), type_str, rc); + tags = ""; + } + weechat_printf_date_tags(profile->buffer, 0, tags, + "%s%s%s%s invites you to join %s. Type " + "\"/group join %d\" to accept.", + weechat_prefix("network"), + weechat_color("chat_nick_other"), friend_name, + weechat_color("reset"), type_str, rc); + } + else + { + tags = "notify_highlight"; + if (friend_chat) + { + weechat_printf_date_tags(friend_chat->buffer, 0, tags, + "%s%s%s%s invites you to join %s, but we failed to " + "process the invite with error %d. Please try again.", + weechat_prefix("network"), + weechat_color("chat_nick_other"), friend_name, + weechat_color("reset"), rc, err); + tags = ""; + } + weechat_printf_date_tags(profile->buffer, 0, tags, + "%s%s%s%s invites you to join %s, but we failed to " + "process the invite. Please try again.", + weechat_prefix("network"), + weechat_color("chat_nick_other"), friend_name, + weechat_color("reset"), rc); + } + } free(friend_name); } @@ -251,35 +376,43 @@ twc_handle_group_message(Tox *tox, int32_t group_number, int32_t peer_number, const uint8_t *message, uint16_t length, void *data, - enum TWC_MESSAGE_TYPE message_type) + TOX_MESSAGE_TYPE message_type) { + TOX_ERR_CONFERENCE_PEER_QUERY err = TOX_ERR_CONFERENCE_PEER_QUERY_OK; + bool rc; struct t_twc_profile *profile = data; struct t_twc_chat *chat = twc_chat_search_group(profile, group_number, true); + char *myname = twc_get_self_name_nt(profile->tox); char *name = twc_get_peer_name_nt(profile->tox, group_number, peer_number); + char *tags = "notify_message"; char *message_nt = twc_null_terminate(message, length); const char *nick_color; - if (tox_group_peernumber_is_ours(tox, group_number, peer_number)) + rc = tox_conference_peer_number_is_ours(tox, group_number, peer_number, &err); + if (rc && (err == TOX_ERR_CONFERENCE_PEER_QUERY_OK)) nick_color = weechat_color("chat_nick_self"); else nick_color = weechat_info_get("nick_color", name); - twc_chat_print_message(chat, "", nick_color, name, + if (weechat_string_has_highlight(message_nt, myname)) + tags = "notify_highlight"; + twc_chat_print_message(chat, tags, nick_color, name, message_nt, message_type); free(name); + free(myname); free(message_nt); } void twc_group_message_callback(Tox *tox, - int32_t group_number, int32_t peer_number, - const uint8_t *message, uint16_t length, - void *data) + uint32_t group_number, uint32_t peer_number, + TOX_MESSAGE_TYPE type, const uint8_t *message, + size_t length, void *data) { twc_handle_group_message(tox, group_number, @@ -287,28 +420,13 @@ twc_group_message_callback(Tox *tox, message, length, data, - TWC_MESSAGE_TYPE_MESSAGE); -} - -void -twc_group_action_callback(Tox *tox, - int32_t group_number, int32_t peer_number, - const uint8_t *message, uint16_t length, - void *data) -{ - twc_handle_group_message(tox, - group_number, - peer_number, - message, - length, - data, - TWC_MESSAGE_TYPE_ACTION); + type); } void twc_group_namelist_change_callback(Tox *tox, - int group_number, int peer_number, - uint8_t change_type, + uint32_t group_number, uint32_t peer_number, + TOX_CONFERENCE_STATE_CHANGE change_type, void *data) { struct t_twc_profile *profile = data; @@ -317,66 +435,70 @@ twc_group_namelist_change_callback(Tox *tox, true); struct t_gui_nick *nick = NULL; - char *name = twc_get_peer_name_nt(profile->tox, group_number, peer_number); - char *prev_name = NULL; + int i, npeers; + TOX_ERR_CONFERENCE_PEER_QUERY err = TOX_ERR_CONFERENCE_PEER_QUERY_OK; - uint8_t pubkey[TOX_PUBLIC_KEY_SIZE]; - int pkrc = tox_group_peer_pubkey(profile->tox, group_number, - peer_number, pubkey); - if (pkrc == 0) + struct t_weelist *new_nicks; + struct t_weelist_item *n; + + npeers = tox_conference_peer_count(profile->tox, group_number, &err); + + if (err == TOX_ERR_CONFERENCE_PEER_QUERY_OK) { - if (change_type == TOX_CHAT_CHANGE_PEER_DEL - || change_type == TOX_CHAT_CHANGE_PEER_NAME) + new_nicks = weechat_list_new(); + for (i = 0; i < npeers; i++) { - nick = weechat_hashtable_get(chat->nicks, pubkey); - if (nick) - { - prev_name = strdup(weechat_nicklist_nick_get_string(chat->buffer, - nick, "name")); - weechat_nicklist_remove_nick(chat->buffer, nick); - weechat_hashtable_remove(chat->nicks, pubkey); - } - } - - if (change_type == TOX_CHAT_CHANGE_PEER_ADD - || change_type == TOX_CHAT_CHANGE_PEER_NAME) - { - nick = weechat_nicklist_add_nick(chat->buffer, chat->nicklist_group, - name, NULL, NULL, NULL, 1); - if (nick) - weechat_hashtable_set_with_size(chat->nicks, - pubkey, TOX_PUBLIC_KEY_SIZE, - nick, 0); + char *name = twc_get_peer_name_nt(profile->tox, group_number, i); + weechat_list_add(new_nicks, name, WEECHAT_LIST_POS_SORT, NULL); + free(name); } } + else + return; - switch (change_type) + // searching for exits + n = weechat_list_get(chat->nicks, 0); + + while (n) { - case TOX_CHAT_CHANGE_PEER_NAME: - if (prev_name && name) - weechat_printf(chat->buffer, "%s%s is now known as %s", - weechat_prefix("network"), prev_name, name); - break; - case TOX_CHAT_CHANGE_PEER_ADD: - if (name) - weechat_printf(chat->buffer, "%s%s just joined the group chat", - weechat_prefix("join"), name); - break; - case TOX_CHAT_CHANGE_PEER_DEL: - if (prev_name) - weechat_printf(chat->buffer, "%s%s just left the group chat", - weechat_prefix("quit"), prev_name); - break; + const char *name = weechat_list_string(n); + if (!weechat_list_search(new_nicks, name)) + { + weechat_printf(chat->buffer, "%s%s just left the group chat", + weechat_prefix("quit"), name); + nick = weechat_nicklist_search_nick(chat->buffer, + chat->nicklist_group, + name); + weechat_nicklist_remove_nick(chat->buffer, nick); + } + n = weechat_list_next(n); } - if (prev_name) - free(prev_name); + // searching for joins + n = weechat_list_get(new_nicks, 0); + + while (n) + { + const char *name = weechat_list_string(n); + if (!weechat_list_search(chat->nicks, name)) + { + weechat_printf(chat->buffer, "%s%s just joined the group chat", + weechat_prefix("join"), name); + weechat_nicklist_add_nick(chat->buffer, chat->nicklist_group, + name, NULL, NULL, NULL, 1); + } + n = weechat_list_next(n); + } + + weechat_list_remove_all(chat->nicks); + weechat_list_free(chat->nicks); + chat->nicks = new_nicks; } void twc_group_title_callback(Tox *tox, - int group_number, int peer_number, - const uint8_t *title, uint8_t length, + uint32_t group_number, uint32_t peer_number, + const uint8_t *title, size_t length, void *data) { struct t_twc_profile *profile = data; @@ -385,14 +507,11 @@ twc_group_title_callback(Tox *tox, true); twc_chat_queue_refresh(chat); - if (peer_number >= 0) - { - char *name = twc_get_peer_name_nt(profile->tox, group_number, peer_number); + char *name = twc_get_peer_name_nt(profile->tox, group_number, peer_number); - char *topic = strndup((char *)title, length); - weechat_printf(chat->buffer, "%s%s has changed the topic to \"%s\"", - weechat_prefix("network"), name, topic); - free(topic); - } + char *topic = strndup((char *)title, length); + weechat_printf(chat->buffer, "%s%s has changed the topic to \"%s\"", + weechat_prefix("network"), name, topic); + free(topic); } diff --git a/src/twc-tox-callbacks.h b/src/twc-tox-callbacks.h index 7c4d8b2..883c21f 100644 --- a/src/twc-tox-callbacks.h +++ b/src/twc-tox-callbacks.h @@ -28,9 +28,8 @@ twc_do_timer_cb(const void *pointer, void *data, void twc_friend_message_callback(Tox *tox, uint32_t friend_number, - TOX_MESSAGE_TYPE type, - const uint8_t *message, size_t length, - void *data); + TOX_MESSAGE_TYPE type, const uint8_t *message, + size_t length, void *data); void twc_connection_status_callback(Tox *tox, uint32_t friend_number, @@ -57,32 +56,26 @@ twc_friend_request_callback(Tox *tox, const uint8_t *public_key, void twc_group_invite_callback(Tox *tox, - int32_t friend_number, uint8_t type, - const uint8_t *invite_data, uint16_t length, + uint32_t friend_number, TOX_CONFERENCE_TYPE type, + const uint8_t *invite_data, size_t length, void *data); void twc_group_message_callback(Tox *tox, - int32_t group_number, int32_t peer_number, - const uint8_t *message, uint16_t length, - void *data); - -void -twc_group_action_callback(Tox *tox, - int32_t group_number, int32_t peer_number, - const uint8_t *message, uint16_t length, - void *data); + uint32_t group_number, uint32_t peer_number, + TOX_MESSAGE_TYPE type, const uint8_t *message, + size_t length, void *data); void twc_group_namelist_change_callback(Tox *tox, - int group_number, int peer_number, - uint8_t change_type, + uint32_t group_number, uint32_t peer_number, + TOX_CONFERENCE_STATE_CHANGE change_type, void *data); void twc_group_title_callback(Tox *tox, - int group_number, int peer_number, - const uint8_t *title, uint8_t length, + uint32_t group_number, uint32_t peer_number, + const uint8_t *title, size_t length, void *data); #endif // TOX_WEECHAT_TOX_CALLBACKS_H diff --git a/src/twc-utils.c b/src/twc-utils.c index 0b11537..04c4d83 100644 --- a/src/twc-utils.c +++ b/src/twc-utils.c @@ -123,11 +123,18 @@ twc_get_status_message_nt(Tox *tox, int32_t friend_number) char * twc_get_peer_name_nt(Tox *tox, int32_t group_number, int32_t peer_number) { - uint8_t name[TOX_MAX_NAME_LENGTH] = {0}; + uint8_t name[TOX_MAX_NAME_LENGTH+1] = {0}; + TOX_ERR_CONFERENCE_PEER_QUERY err = TOX_ERR_CONFERENCE_PEER_QUERY_OK; - int length = tox_group_peername(tox, group_number, peer_number, name); - if (length >= 0) - return twc_null_terminate(name, length); + int length = tox_conference_peer_get_name_size(tox, group_number, peer_number, &err); + if ((err == TOX_ERR_CONFERENCE_PEER_QUERY_OK) && (length <= TOX_MAX_NAME_LENGTH)) + { + tox_conference_peer_get_name(tox, group_number, peer_number, name, &err); + if (err == TOX_ERR_CONFERENCE_PEER_QUERY_OK) + return twc_null_terminate(name, length); + else + return ""; + } else return ""; } @@ -186,15 +193,10 @@ twc_uint32_reverse_bytes(uint32_t num) } /** - * Hash a Tox ID of size TOX_PUBLIC_KEY_SIZE bytes using a modified djb2 hash. + * Fit correct unicode string into max chars. Return number of bytes */ -unsigned long long -twc_hash_tox_id(const uint8_t *tox_id) +int +twc_fit_utf8(const char *str, int max) { - unsigned long long hash = 5381; - - for (size_t i = 0; i < TOX_PUBLIC_KEY_SIZE; ++i) - hash ^= (hash << 5) + (hash >> 2) + tox_id[i]; - - return hash; + return weechat_utf8_real_pos(str, weechat_utf8_strnlen(str, max)); } diff --git a/src/twc-utils.h b/src/twc-utils.h index b15933c..2a4587e 100644 --- a/src/twc-utils.h +++ b/src/twc-utils.h @@ -51,8 +51,8 @@ twc_get_friend_id_short(Tox *tox, int32_t friend_number); uint32_t twc_uint32_reverse_bytes(uint32_t num); -unsigned long long -twc_hash_tox_id(const uint8_t *tox_id); +int +twc_fit_utf8(const char *str, int max); #endif // TOX_WEECHAT_UTILS_H diff --git a/src/twc.h b/src/twc.h index 56d3ecf..2f8aa84 100644 --- a/src/twc.h +++ b/src/twc.h @@ -32,5 +32,8 @@ enum t_twc_rc TWC_RC_ERROR_MALLOC = -2, }; +#define TWC_MAX_FRIEND_MESSAGE_LENGTH (TOX_MAX_MESSAGE_LENGTH-1) +#define TWC_MAX_GROUP_MESSAGE_LENGTH (TOX_MAX_MESSAGE_LENGTH-16) + #endif // TOX_WEECHAT_H