int gui_line_match_regex (struct t_gui_line_data *line_data, regex_t *regex_prefix, regex_t *regex_message) { char *prefix, *message; int match_prefix, match_message; if (!line_data || (!regex_prefix && !regex_message)) return 0; prefix = NULL; message = NULL; match_prefix = 1; match_message = 1; if (line_data->prefix) { prefix = gui_color_decode (line_data->prefix, NULL); if (!prefix || (regex_prefix && (regexec (regex_prefix, prefix, 0, NULL, 0) != 0))) match_prefix = 0; } else { if (regex_prefix) match_prefix = 0; } if (line_data->message) { message = gui_color_decode (line_data->message, NULL); if (!message || (regex_message && (regexec (regex_message, message, 0, NULL, 0) != 0))) match_message = 0; } else { if (regex_message) match_message = 0; } if (prefix) free (prefix); if (message) free (message); return (match_prefix && match_message); }
char * gui_chat_build_string_prefix_message (struct t_gui_line *line) { char *string, *string_without_colors; int length; length = 0; if (line->data->prefix) length += strlen (line->data->prefix); length++; if (line->data->message) length += strlen (line->data->message); length++; string = malloc (length); if (string) { string[0] = '\0'; if (line->data->prefix) strcat (string, line->data->prefix); strcat (string, "\t"); if (line->data->message) strcat (string, line->data->message); } if (string) { string_without_colors = gui_color_decode (string, NULL); if (string_without_colors) { free (string); string = string_without_colors; } } return string; }
struct t_hashtable * gui_focus_to_hashtable (struct t_gui_focus_info *focus_info, const char *key) { struct t_hashtable *hashtable; char str_value[128], *str_time, *str_prefix, *str_tags, *str_message; const char *nick; hashtable = hashtable_new (32, WEECHAT_HASHTABLE_STRING, WEECHAT_HASHTABLE_STRING, NULL, NULL); if (!hashtable) return NULL; /* key (key from keyboard or mouse event) */ FOCUS_STR("_key", key); /* x,y */ FOCUS_INT("_x", focus_info->x); FOCUS_INT("_y", focus_info->y); /* window */ FOCUS_PTR("_window", focus_info->window); if (focus_info->window) { FOCUS_INT("_window_number", (focus_info->window)->number); } else { FOCUS_STR("_window_number", "*"); } /* buffer */ FOCUS_PTR("_buffer", focus_info->buffer); if (focus_info->buffer) { FOCUS_INT("_buffer_number", (focus_info->buffer)->number); FOCUS_STR("_buffer_plugin", plugin_get_name ((focus_info->buffer)->plugin)); FOCUS_STR("_buffer_name", (focus_info->buffer)->name); FOCUS_STR("_buffer_full_name", (focus_info->buffer)->full_name); hashtable_map ((focus_info->buffer)->local_variables, &gui_focus_buffer_localvar_map_cb, hashtable); } else { FOCUS_PTR("_buffer", NULL); FOCUS_STR("_buffer_number", "-1"); FOCUS_STR("_buffer_plugin", ""); FOCUS_STR("_buffer_name", ""); FOCUS_STR("_buffer_full_name", ""); } /* chat area */ FOCUS_INT("_chat", focus_info->chat); str_time = NULL; str_prefix = NULL; if (focus_info->chat_line) { str_time = gui_color_decode (((focus_info->chat_line)->data)->str_time, NULL); str_prefix = gui_color_decode (((focus_info->chat_line)->data)->prefix, NULL); str_tags = string_build_with_split_string ((const char **)((focus_info->chat_line)->data)->tags_array, ","); str_message = gui_color_decode (((focus_info->chat_line)->data)->message, NULL); nick = gui_line_get_nick_tag (focus_info->chat_line); FOCUS_PTR("_chat_line", focus_info->chat_line); FOCUS_INT("_chat_line_x", focus_info->chat_line_x); FOCUS_INT("_chat_line_y", ((focus_info->chat_line)->data)->y); FOCUS_TIME("_chat_line_date", ((focus_info->chat_line)->data)->date); FOCUS_TIME("_chat_line_date_printed", ((focus_info->chat_line)->data)->date_printed); FOCUS_STR_VAR("_chat_line_time", str_time); FOCUS_STR_VAR("_chat_line_tags", str_tags); FOCUS_STR_VAR("_chat_line_nick", nick); FOCUS_STR_VAR("_chat_line_prefix", str_prefix); FOCUS_STR_VAR("_chat_line_message", str_message); if (str_time) free (str_time); if (str_prefix) free (str_prefix); if (str_tags) free (str_tags); if (str_message) free (str_message); } else { FOCUS_PTR("_chat_line", NULL); FOCUS_STR("_chat_line_x", "-1"); FOCUS_STR("_chat_line_y", "-1"); FOCUS_STR("_chat_line_date", "-1"); FOCUS_STR("_chat_line_date_printed", "-1"); FOCUS_STR("_chat_line_time", ""); FOCUS_STR("_chat_line_tags", ""); FOCUS_STR("_chat_line_nick", ""); FOCUS_STR("_chat_line_prefix", ""); FOCUS_STR("_chat_line_message", ""); } FOCUS_STR_VAR("_chat_word", focus_info->chat_word); FOCUS_STR_VAR("_chat_bol", focus_info->chat_bol); FOCUS_STR_VAR("_chat_eol", focus_info->chat_eol); /* bar/item */ if (focus_info->bar_window) { FOCUS_STR("_bar_name", ((focus_info->bar_window)->bar)->name); FOCUS_STR("_bar_filling", gui_bar_filling_string[gui_bar_get_filling ((focus_info->bar_window)->bar)]); } else { FOCUS_STR("_bar_name", ""); FOCUS_STR("_bar_filling", ""); } FOCUS_STR_VAR("_bar_item_name", focus_info->bar_item); FOCUS_INT("_bar_item_line", focus_info->bar_item_line); FOCUS_INT("_bar_item_col", focus_info->bar_item_col); return hashtable; }
int gui_line_has_highlight (struct t_gui_line *line) { int rc, i, j, no_highlight; char *msg_no_color, *highlight_words; /* * highlights are disabled on this buffer? (special value "-" means that * buffer does not want any highlight) */ if (line->data->buffer->highlight_words && (strcmp (line->data->buffer->highlight_words, "-") == 0)) return 0; /* * check if highlight is forced by a tag (with option highlight_tags) or * disabled for line */ no_highlight = 0; for (i = 0; i < line->data->tags_count; i++) { if (config_highlight_tags) { for (j = 0; j < config_num_highlight_tags; j++) { if (string_strcasecmp (line->data->tags_array[i], config_highlight_tags[j]) == 0) return 1; } } if (strcmp (line->data->tags_array[i], GUI_CHAT_TAG_NO_HIGHLIGHT) == 0) no_highlight = 1; } if (no_highlight) return 0; /* * check that line matches highlight tags, if any (if no tag is specified, * then any tag is allowed) */ if (line->data->buffer->highlight_tags_count > 0) { if (!gui_line_match_tags (line->data, line->data->buffer->highlight_tags_count, line->data->buffer->highlight_tags_array)) return 0; } /* remove color codes from line message */ msg_no_color = gui_color_decode (line->data->message, NULL); if (!msg_no_color) return 0; /* * there is highlight on line if one of buffer highlight words matches line * or one of global highlight words matches line */ highlight_words = gui_buffer_string_replace_local_var (line->data->buffer, line->data->buffer->highlight_words); rc = string_has_highlight (msg_no_color, (highlight_words) ? highlight_words : line->data->buffer->highlight_words); if (highlight_words) free (highlight_words); if (!rc) { highlight_words = gui_buffer_string_replace_local_var (line->data->buffer, CONFIG_STRING(config_look_highlight)); rc = string_has_highlight (msg_no_color, (highlight_words) ? highlight_words : CONFIG_STRING(config_look_highlight)); if (highlight_words) free (highlight_words); } if (!rc && config_highlight_regex) { rc = string_has_highlight_regex_compiled (msg_no_color, config_highlight_regex); } if (!rc && line->data->buffer->highlight_regex_compiled) { rc = string_has_highlight_regex_compiled (msg_no_color, line->data->buffer->highlight_regex_compiled); } free (msg_no_color); return rc; }
int gui_line_search_text (struct t_gui_buffer *buffer, struct t_gui_line *line) { char *prefix, *message; int rc; if (!line || !line->data->message || !buffer->input_buffer || !buffer->input_buffer[0]) { return 0; } rc = 0; if ((buffer->text_search_where & GUI_TEXT_SEARCH_IN_PREFIX) && line->data->prefix) { prefix = gui_color_decode (line->data->prefix, NULL); if (prefix) { if (buffer->text_search_regex) { if (buffer->text_search_regex_compiled) { if (regexec (buffer->text_search_regex_compiled, prefix, 0, NULL, 0) == 0) { rc = 1; } } } else if ((buffer->text_search_exact && (strstr (prefix, buffer->input_buffer))) || (!buffer->text_search_exact && (string_strcasestr (prefix, buffer->input_buffer)))) { rc = 1; } free (prefix); } } if (!rc && (buffer->text_search_where & GUI_TEXT_SEARCH_IN_MESSAGE)) { message = gui_color_decode (line->data->message, NULL); if (message) { if (buffer->text_search_regex) { if (buffer->text_search_regex_compiled) { if (regexec (buffer->text_search_regex_compiled, message, 0, NULL, 0) == 0) { rc = 1; } } } else if ((buffer->text_search_exact && (strstr (message, buffer->input_buffer))) || (!buffer->text_search_exact && (string_strcasestr (message, buffer->input_buffer)))) { rc = 1; } free (message); } } return rc; }
char * gui_color_emphasize (const char *string, const char *search, int case_sensitive, regex_t *regex) { regmatch_t regex_match; char *result, *result2, *string_no_color, *pos; const char *ptr_string, *ptr_no_color, *color_emphasis; int rc, length_search, length_emphasis, length_result; int pos1, pos2, real_pos1, real_pos2, count_emphasis; if (!string && !regex) return NULL; color_emphasis = gui_color_get_custom ("emphasis"); if (!color_emphasis) return NULL; length_emphasis = strlen (color_emphasis); /* * allocate space for 8 emphasized strings (8 before + 8 after = 16); * more space will be allocated later (if there are more than 8 emphasized * strings) */ length_result = strlen (string) + (length_emphasis * 2 * 8) + 1; result = malloc (length_result); if (!result) return NULL; result[0] = '\0'; /* * build a string without color codes to search in this one (then with the * position of text found, we will retrieve position in original string, * which can contain color codes) */ string_no_color = gui_color_decode (string, NULL); if (!string_no_color) { free (result); return NULL; } length_search = (search) ? strlen (search) : 0; ptr_string = string; ptr_no_color = string_no_color; count_emphasis = 0; while (ptr_no_color && ptr_no_color[0]) { if (regex) { /* search next match using the regex */ regex_match.rm_so = -1; rc = regexec (regex, ptr_no_color, 1, ®ex_match, 0); /* * no match found: exit the loop (if rm_no == 0, it is an empty * match at beginning of string: we consider there is no match, to * prevent an infinite loop) */ if ((rc != 0) || (regex_match.rm_so < 0) || (regex_match.rm_eo <= 0)) { strcat (result, ptr_string); break; } pos1 = regex_match.rm_so; pos2 = regex_match.rm_eo; } else { /* search next match in the string */ if (case_sensitive) pos = strstr (ptr_no_color, search); else pos = string_strcasestr (ptr_no_color, search); if (!pos) { strcat (result, ptr_string); break; } pos1 = pos - ptr_no_color; pos2 = pos1 + length_search; if (pos2 <= 0) { strcat (result, ptr_string); break; } } /* * find the position of match in the original string (which can contain * color codes) */ real_pos1 = gui_chat_string_real_pos (ptr_string, gui_chat_string_pos (ptr_no_color, pos1)); real_pos2 = gui_chat_string_real_pos (ptr_string, gui_chat_string_pos (ptr_no_color, pos2)); /* * concatenate following strings to the result: * - beginning of string (before match) * - emphasis color code * - the matching string * - emphasis color code */ if (real_pos1 > 0) strncat (result, ptr_string, real_pos1); strcat (result, color_emphasis); strncat (result, ptr_string + real_pos1, real_pos2 - real_pos1); strcat (result, color_emphasis); /* restart next loop after the matching string */ ptr_string += real_pos2; ptr_no_color += pos2; /* check if we should allocate more space for emphasis color codes */ count_emphasis++; if (count_emphasis == 8) { /* allocate more space for emphasis color codes */ length_result += (length_emphasis * 2 * 8); result2 = realloc (result, length_result); if (!result2) { free (result); return NULL; } result = result2; count_emphasis = 0; } } free (string_no_color); return result; }