/// Add the digraphs in the argument to the digraph table. /// format: {c1}{c2} char {c1}{c2} char ... /// /// @param str void putdigraph(char_u *str) { char_u char1, char2; digr_T *dp; while (*str != NUL) { str = skipwhite(str); if (*str == NUL) { return; } char1 = *str++; char2 = *str++; if (char2 == 0) { EMSG(_(e_invarg)); return; } if ((char1 == ESC) || (char2 == ESC)) { EMSG(_("E104: Escape not allowed in digraph")); return; } str = skipwhite(str); if (!ascii_isdigit(*str)) { EMSG(_(e_number_exp)); return; } int n = getdigits_int(&str); // If the digraph already exists, replace the result. dp = (digr_T *)user_digraphs.ga_data; int i; for (i = 0; i < user_digraphs.ga_len; ++i) { if (((int)dp->char1 == char1) && ((int)dp->char2 == char2)) { dp->result = n; break; } ++dp; } // Add a new digraph to the table. if (i == user_digraphs.ga_len) { dp = GA_APPEND_VIA_PTR(digr_T, &user_digraphs); dp->char1 = char1; dp->char2 = char2; dp->result = n; } } }
/* * ":menutrans". * This function is also defined without the +multi_lang feature, in which * case the commands are ignored. */ void ex_menutranslate(exarg_T *eap) { char_u *arg = eap->arg; char_u *from, *from_noamp, *to; if (menutrans_ga.ga_itemsize == 0) ga_init(&menutrans_ga, (int)sizeof(menutrans_T), 5); /* * ":menutrans clear": clear all translations. */ if (STRNCMP(arg, "clear", 5) == 0 && ends_excmd(*skipwhite(arg + 5))) { menutrans_T *tp = (menutrans_T *)menutrans_ga.ga_data; for (int i = 0; i < menutrans_ga.ga_len; ++i) { free(tp[i].from); free(tp[i].from_noamp); free(tp[i].to); } ga_clear(&menutrans_ga); /* Delete all "menutrans_" global variables. */ del_menutrans_vars(); } else { /* ":menutrans from to": add translation */ from = arg; arg = menu_skip_part(arg); to = skipwhite(arg); *arg = NUL; arg = menu_skip_part(to); if (arg == to) EMSG(_(e_invarg)); else { from = vim_strsave(from); from_noamp = menu_text(from, NULL, NULL); to = vim_strnsave(to, (int)(arg - to)); if (from_noamp != NULL) { menu_translate_tab_and_shift(from); menu_translate_tab_and_shift(to); menu_unescape_name(from); menu_unescape_name(to); menutrans_T* tp = GA_APPEND_VIA_PTR(menutrans_T, &menutrans_ga); tp->from = from; tp->from_noamp = from_noamp; tp->to = to; } else { free(from); free(from_noamp); free(to); } } } }
/// ":loadkeymap" command: load the following lines as the keymap. /// /// @param eap void ex_loadkeymap(exarg_T *eap) { char_u *line; char_u *p; char_u *s; #define KMAP_LLEN 200 // max length of "to" and "from" together char_u buf[KMAP_LLEN + 11]; char_u *save_cpo = p_cpo; if (!getline_equal(eap->getline, eap->cookie, getsourceline)) { EMSG(_("E105: Using :loadkeymap not in a sourced file")); return; } // Stop any active keymap and clear the table. keymap_unload(); curbuf->b_kmap_state = 0; ga_init(&curbuf->b_kmap_ga, (int)sizeof(kmap_T), 20); // Set 'cpoptions' to "C" to avoid line continuation. p_cpo = (char_u *)"C"; // Get each line of the sourced file, break at the end. for (;;) { line = eap->getline(0, eap->cookie, 0); if (line == NULL) { break; } p = skipwhite(line); if ((*p != '"') && (*p != NUL)) { kmap_T *kp = GA_APPEND_VIA_PTR(kmap_T, &curbuf->b_kmap_ga); s = skiptowhite(p); kp->from = vim_strnsave(p, (size_t)(s - p)); p = skipwhite(s); s = skiptowhite(p); kp->to = vim_strnsave(p, (size_t)(s - p)); if ((STRLEN(kp->from) + STRLEN(kp->to) >= KMAP_LLEN) || (*kp->from == NUL) || (*kp->to == NUL)) { if (*kp->to == NUL) { EMSG(_("E791: Empty keymap entry")); } xfree(kp->from); xfree(kp->to); --curbuf->b_kmap_ga.ga_len; } } xfree(line); } // setup ":lnoremap" to map the keys for (int i = 0; i < curbuf->b_kmap_ga.ga_len; ++i) { vim_snprintf((char *)buf, sizeof(buf), "<buffer> %s %s", ((kmap_T *)curbuf->b_kmap_ga.ga_data)[i].from, ((kmap_T *)curbuf->b_kmap_ga.ga_data)[i].to); (void)do_map(2, buf, LANGMAP, FALSE); } p_cpo = save_cpo; curbuf->b_kmap_state |= KEYMAP_LOADED; status_redraw_curbuf(); }