Mercurial > vim
comparison src/sign.c @ 17366:9843fbfa0ee5 v8.1.1682
patch 8.1.1682: placing a larger number of signs is slow
commit https://github.com/vim/vim/commit/809ce4d317fe12db0b2c17f16b4f77200fb060c4
Author: Bram Moolenaar <Bram@vim.org>
Date: Sat Jul 13 21:21:40 2019 +0200
patch 8.1.1682: placing a larger number of signs is slow
Problem: Placing a larger number of signs is slow.
Solution: Add functions for dealing with a list of signs. (Yegappan
Lakshmanan, closes #4636)
author | Bram Moolenaar <Bram@vim.org> |
---|---|
date | Sat, 13 Jul 2019 21:30:04 +0200 |
parents | 82b5d981fe59 |
children | a5874fdc8f3a |
comparison
equal
deleted
inserted
replaced
17365:c6491636f12e | 17366:9843fbfa0ee5 |
---|---|
440 static linenr_T | 440 static linenr_T |
441 buf_change_sign_type( | 441 buf_change_sign_type( |
442 buf_T *buf, // buffer to store sign in | 442 buf_T *buf, // buffer to store sign in |
443 int markId, // sign ID | 443 int markId, // sign ID |
444 char_u *group, // sign group | 444 char_u *group, // sign group |
445 int typenr) // typenr of sign we are adding | 445 int typenr, // typenr of sign we are adding |
446 int prio) // sign priority | |
446 { | 447 { |
447 signlist_T *sign; // a sign in the signlist | 448 signlist_T *sign; // a sign in the signlist |
448 | 449 |
449 FOR_ALL_SIGNS_IN_BUF(buf, sign) | 450 FOR_ALL_SIGNS_IN_BUF(buf, sign) |
450 { | 451 { |
451 if (sign->id == markId && sign_in_group(sign, group)) | 452 if (sign->id == markId && sign_in_group(sign, group)) |
452 { | 453 { |
453 sign->typenr = typenr; | 454 sign->typenr = typenr; |
455 sign->priority = prio; | |
456 sign_sort_by_prio_on_line(buf, sign); | |
454 return sign->lnum; | 457 return sign->lnum; |
455 } | 458 } |
456 } | 459 } |
457 | 460 |
458 return (linenr_T)0; | 461 return (linenr_T)0; |
1102 if (lnum > 0) | 1105 if (lnum > 0) |
1103 // ":sign place {id} line={lnum} name={name} file={fname}": | 1106 // ":sign place {id} line={lnum} name={name} file={fname}": |
1104 // place a sign | 1107 // place a sign |
1105 buf_addsign(buf, *sign_id, sign_group, prio, lnum, sp->sn_typenr); | 1108 buf_addsign(buf, *sign_id, sign_group, prio, lnum, sp->sn_typenr); |
1106 else | 1109 else |
1107 // ":sign place {id} file={fname}": change sign type | 1110 // ":sign place {id} file={fname}": change sign type and/or priority |
1108 lnum = buf_change_sign_type(buf, *sign_id, sign_group, sp->sn_typenr); | 1111 lnum = buf_change_sign_type(buf, *sign_id, sign_group, sp->sn_typenr, |
1112 prio); | |
1109 if (lnum > 0) | 1113 if (lnum > 0) |
1110 { | 1114 { |
1111 redraw_buf_line_later(buf, lnum); | 1115 redraw_buf_line_later(buf, lnum); |
1112 | 1116 |
1113 // When displaying signs in the 'number' column, if the width of the | 1117 // When displaying signs in the 'number' column, if the width of the |
2094 } | 2098 } |
2095 } | 2099 } |
2096 # endif | 2100 # endif |
2097 | 2101 |
2098 /* | 2102 /* |
2099 * "sign_define()" function | 2103 * Define a sign using the attributes in 'dict'. Returns 0 on success and -1 on |
2100 */ | 2104 * failure. |
2101 void | 2105 */ |
2102 f_sign_define(typval_T *argvars, typval_T *rettv) | 2106 static int |
2103 { | 2107 sign_define_from_dict(char_u *name_arg, dict_T *dict) |
2104 char_u *name; | 2108 { |
2105 dict_T *dict; | 2109 char_u *name = NULL; |
2106 char_u *icon = NULL; | 2110 char_u *icon = NULL; |
2107 char_u *linehl = NULL; | 2111 char_u *linehl = NULL; |
2108 char_u *text = NULL; | 2112 char_u *text = NULL; |
2109 char_u *texthl = NULL; | 2113 char_u *texthl = NULL; |
2110 | 2114 int retval = -1; |
2111 rettv->vval.v_number = -1; | 2115 |
2112 | 2116 if (name_arg == NULL) |
2113 name = tv_get_string_chk(&argvars[0]); | 2117 { |
2114 if (name == NULL) | 2118 if (dict == NULL) |
2115 return; | 2119 return -1; |
2116 | 2120 name = dict_get_string(dict, (char_u *)"name", TRUE); |
2117 if (argvars[1].v_type != VAR_UNKNOWN) | 2121 } |
2118 { | 2122 else |
2119 if (argvars[1].v_type != VAR_DICT) | 2123 name = vim_strsave(name_arg); |
2120 { | 2124 if (name == NULL || name[0] == NUL) |
2121 emsg(_(e_dictreq)); | 2125 goto cleanup; |
2122 return; | 2126 if (dict != NULL) |
2123 } | 2127 { |
2124 | 2128 icon = dict_get_string(dict, (char_u *)"icon", TRUE); |
2125 // sign attributes | 2129 linehl = dict_get_string(dict, (char_u *)"linehl", TRUE); |
2126 dict = argvars[1].vval.v_dict; | 2130 text = dict_get_string(dict, (char_u *)"text", TRUE); |
2127 if (dict_find(dict, (char_u *)"icon", -1) != NULL) | 2131 texthl = dict_get_string(dict, (char_u *)"texthl", TRUE); |
2128 icon = dict_get_string(dict, (char_u *)"icon", TRUE); | |
2129 if (dict_find(dict, (char_u *)"linehl", -1) != NULL) | |
2130 linehl = dict_get_string(dict, (char_u *)"linehl", TRUE); | |
2131 if (dict_find(dict, (char_u *)"text", -1) != NULL) | |
2132 text = dict_get_string(dict, (char_u *)"text", TRUE); | |
2133 if (dict_find(dict, (char_u *)"texthl", -1) != NULL) | |
2134 texthl = dict_get_string(dict, (char_u *)"texthl", TRUE); | |
2135 } | 2132 } |
2136 | 2133 |
2137 if (sign_define_by_name(name, icon, linehl, text, texthl) == OK) | 2134 if (sign_define_by_name(name, icon, linehl, text, texthl) == OK) |
2138 rettv->vval.v_number = 0; | 2135 retval = 0; |
2139 | 2136 |
2137 cleanup: | |
2138 vim_free(name); | |
2140 vim_free(icon); | 2139 vim_free(icon); |
2141 vim_free(linehl); | 2140 vim_free(linehl); |
2142 vim_free(text); | 2141 vim_free(text); |
2143 vim_free(texthl); | 2142 vim_free(texthl); |
2143 | |
2144 return retval; | |
2145 } | |
2146 | |
2147 /* | |
2148 * Define multiple signs using attributes from list 'l' and store the return | |
2149 * values in 'retlist'. | |
2150 */ | |
2151 static void | |
2152 sign_define_multiple(list_T *l, list_T *retlist) | |
2153 { | |
2154 listitem_T *li; | |
2155 int retval; | |
2156 | |
2157 for (li = l->lv_first; li != NULL; li = li->li_next) | |
2158 { | |
2159 retval = -1; | |
2160 if (li->li_tv.v_type == VAR_DICT) | |
2161 retval = sign_define_from_dict(NULL, li->li_tv.vval.v_dict); | |
2162 else | |
2163 emsg(_(e_dictreq)); | |
2164 list_append_number(retlist, retval); | |
2165 } | |
2166 } | |
2167 | |
2168 /* | |
2169 * "sign_define()" function | |
2170 */ | |
2171 void | |
2172 f_sign_define(typval_T *argvars, typval_T *rettv) | |
2173 { | |
2174 char_u *name; | |
2175 | |
2176 if (argvars[0].v_type == VAR_LIST && argvars[1].v_type == VAR_UNKNOWN) | |
2177 { | |
2178 // Define multiple signs | |
2179 if (rettv_list_alloc(rettv) != OK) | |
2180 return; | |
2181 | |
2182 sign_define_multiple(argvars[0].vval.v_list, rettv->vval.v_list); | |
2183 return; | |
2184 } | |
2185 | |
2186 // Define a single sign | |
2187 rettv->vval.v_number = -1; | |
2188 | |
2189 name = tv_get_string_chk(&argvars[0]); | |
2190 if (name == NULL) | |
2191 return; | |
2192 | |
2193 if (argvars[1].v_type != VAR_UNKNOWN && argvars[1].v_type != VAR_DICT) | |
2194 { | |
2195 emsg(_(e_dictreq)); | |
2196 return; | |
2197 } | |
2198 | |
2199 rettv->vval.v_number = sign_define_from_dict(name, | |
2200 argvars[1].v_type == VAR_DICT ? argvars[1].vval.v_dict : NULL); | |
2144 } | 2201 } |
2145 | 2202 |
2146 /* | 2203 /* |
2147 * "sign_getdefined()" function | 2204 * "sign_getdefined()" function |
2148 */ | 2205 */ |
2267 cleanup: | 2324 cleanup: |
2268 vim_free(sign_group); | 2325 vim_free(sign_group); |
2269 } | 2326 } |
2270 | 2327 |
2271 /* | 2328 /* |
2272 * "sign_place()" function | 2329 * Place a new sign using the values specified in dict 'dict'. Returns the sign |
2273 */ | 2330 * identifier if successfully placed, otherwise returns 0. |
2274 void | 2331 */ |
2275 f_sign_place(typval_T *argvars, typval_T *rettv) | 2332 static int |
2276 { | 2333 sign_place_from_dict( |
2277 int sign_id; | 2334 typval_T *id_tv, |
2335 typval_T *group_tv, | |
2336 typval_T *name_tv, | |
2337 typval_T *buf_tv, | |
2338 dict_T *dict) | |
2339 { | |
2340 int sign_id = 0; | |
2278 char_u *group = NULL; | 2341 char_u *group = NULL; |
2279 char_u *sign_name; | 2342 char_u *sign_name = NULL; |
2280 buf_T *buf; | 2343 buf_T *buf = NULL; |
2281 dict_T *dict; | |
2282 dictitem_T *di; | 2344 dictitem_T *di; |
2283 linenr_T lnum = 0; | 2345 linenr_T lnum = 0; |
2284 int prio = SIGN_DEF_PRIO; | 2346 int prio = SIGN_DEF_PRIO; |
2285 int notanum = FALSE; | 2347 int notanum = FALSE; |
2286 | 2348 int ret_sign_id = -1; |
2287 rettv->vval.v_number = -1; | 2349 |
2288 | 2350 // sign identifier |
2289 // Sign identifier | 2351 if (id_tv == NULL) |
2290 sign_id = (int)tv_get_number_chk(&argvars[0], ¬anum); | 2352 { |
2291 if (notanum) | 2353 di = dict_find(dict, (char_u *)"id", -1); |
2292 return; | 2354 if (di != NULL) |
2293 if (sign_id < 0) | 2355 id_tv = &di->di_tv; |
2294 { | 2356 } |
2295 emsg(_(e_invarg)); | 2357 if (id_tv == NULL) |
2296 return; | 2358 sign_id = 0; |
2297 } | |
2298 | |
2299 // Sign group | |
2300 group = tv_get_string_chk(&argvars[1]); | |
2301 if (group == NULL) | |
2302 return; | |
2303 if (group[0] == '\0') | |
2304 group = NULL; // global sign group | |
2305 else | 2359 else |
2306 { | 2360 { |
2307 group = vim_strsave(group); | 2361 sign_id = tv_get_number_chk(id_tv, ¬anum); |
2362 if (notanum) | |
2363 return -1; | |
2364 if (sign_id < 0) | |
2365 { | |
2366 emsg(_(e_invarg)); | |
2367 return -1; | |
2368 } | |
2369 } | |
2370 | |
2371 // sign group | |
2372 if (group_tv == NULL) | |
2373 { | |
2374 di = dict_find(dict, (char_u *)"group", -1); | |
2375 if (di != NULL) | |
2376 group_tv = &di->di_tv; | |
2377 } | |
2378 if (group_tv == NULL) | |
2379 group = NULL; // global group | |
2380 else | |
2381 { | |
2382 group = tv_get_string_chk(group_tv); | |
2308 if (group == NULL) | 2383 if (group == NULL) |
2309 return; | 2384 goto cleanup; |
2310 } | 2385 if (group[0] == '\0') // global sign group |
2311 | 2386 group = NULL; |
2312 // Sign name | 2387 else |
2313 sign_name = tv_get_string_chk(&argvars[2]); | 2388 { |
2389 group = vim_strsave(group); | |
2390 if (group == NULL) | |
2391 return -1; | |
2392 } | |
2393 } | |
2394 | |
2395 // sign name | |
2396 if (name_tv == NULL) | |
2397 { | |
2398 di = dict_find(dict, (char_u *)"name", -1); | |
2399 if (di != NULL) | |
2400 name_tv = &di->di_tv; | |
2401 } | |
2402 if (name_tv == NULL) | |
2403 goto cleanup; | |
2404 sign_name = tv_get_string_chk(name_tv); | |
2314 if (sign_name == NULL) | 2405 if (sign_name == NULL) |
2315 goto cleanup; | 2406 goto cleanup; |
2316 | 2407 |
2317 // Buffer to place the sign | 2408 // buffer to place the sign |
2318 buf = get_buf_arg(&argvars[3]); | 2409 if (buf_tv == NULL) |
2410 { | |
2411 di = dict_find(dict, (char_u *)"buffer", -1); | |
2412 if (di != NULL) | |
2413 buf_tv = &di->di_tv; | |
2414 } | |
2415 if (buf_tv == NULL) | |
2416 goto cleanup; | |
2417 buf = get_buf_arg(buf_tv); | |
2319 if (buf == NULL) | 2418 if (buf == NULL) |
2320 goto cleanup; | 2419 goto cleanup; |
2321 | 2420 |
2322 if (argvars[4].v_type != VAR_UNKNOWN) | 2421 // line number of the sign |
2323 { | 2422 di = dict_find(dict, (char_u *)"lnum", -1); |
2324 if (argvars[4].v_type != VAR_DICT || | 2423 if (di != NULL) |
2325 ((dict = argvars[4].vval.v_dict) == NULL)) | 2424 { |
2326 { | 2425 lnum = (int)tv_get_number_chk(&di->di_tv, ¬anum); |
2327 emsg(_(e_dictreq)); | 2426 if (notanum) |
2328 goto cleanup; | 2427 goto cleanup; |
2329 } | 2428 } |
2330 | 2429 |
2331 // Line number where the sign is to be placed | 2430 // sign priority |
2332 if ((di = dict_find(dict, (char_u *)"lnum", -1)) != NULL) | 2431 di = dict_find(dict, (char_u *)"priority", -1); |
2333 { | 2432 if (di != NULL) |
2334 (void)tv_get_number_chk(&di->di_tv, ¬anum); | 2433 { |
2335 if (notanum) | 2434 prio = (int)tv_get_number_chk(&di->di_tv, ¬anum); |
2336 goto cleanup; | 2435 if (notanum) |
2337 lnum = tv_get_lnum(&di->di_tv); | 2436 goto cleanup; |
2338 } | |
2339 if ((di = dict_find(dict, (char_u *)"priority", -1)) != NULL) | |
2340 { | |
2341 // Sign priority | |
2342 prio = (int)tv_get_number_chk(&di->di_tv, ¬anum); | |
2343 if (notanum) | |
2344 goto cleanup; | |
2345 } | |
2346 } | 2437 } |
2347 | 2438 |
2348 if (sign_place(&sign_id, group, sign_name, buf, lnum, prio) == OK) | 2439 if (sign_place(&sign_id, group, sign_name, buf, lnum, prio) == OK) |
2349 rettv->vval.v_number = sign_id; | 2440 ret_sign_id = sign_id; |
2350 | 2441 |
2351 cleanup: | 2442 cleanup: |
2352 vim_free(group); | 2443 vim_free(group); |
2444 | |
2445 return ret_sign_id; | |
2446 } | |
2447 | |
2448 /* | |
2449 * "sign_place()" function | |
2450 */ | |
2451 void | |
2452 f_sign_place(typval_T *argvars, typval_T *rettv) | |
2453 { | |
2454 dict_T *dict = NULL; | |
2455 | |
2456 rettv->vval.v_number = -1; | |
2457 | |
2458 if (argvars[4].v_type != VAR_UNKNOWN | |
2459 && (argvars[4].v_type != VAR_DICT | |
2460 || ((dict = argvars[4].vval.v_dict) == NULL))) | |
2461 { | |
2462 emsg(_(e_dictreq)); | |
2463 return; | |
2464 } | |
2465 | |
2466 rettv->vval.v_number = sign_place_from_dict(&argvars[0], &argvars[1], | |
2467 &argvars[2], &argvars[3], dict); | |
2468 } | |
2469 | |
2470 /* | |
2471 * "sign_placelist()" function. Place multiple signs. | |
2472 */ | |
2473 void | |
2474 f_sign_placelist(typval_T *argvars, typval_T *rettv) | |
2475 { | |
2476 listitem_T *li; | |
2477 int sign_id; | |
2478 | |
2479 if (rettv_list_alloc(rettv) != OK) | |
2480 return; | |
2481 | |
2482 if (argvars[0].v_type != VAR_LIST) | |
2483 { | |
2484 emsg(_(e_listreq)); | |
2485 return; | |
2486 } | |
2487 | |
2488 // Process the List of sign attributes | |
2489 for (li = argvars[0].vval.v_list->lv_first; li != NULL; li = li->li_next) | |
2490 { | |
2491 sign_id = -1; | |
2492 if (li->li_tv.v_type == VAR_DICT) | |
2493 sign_id = sign_place_from_dict(NULL, NULL, NULL, NULL, | |
2494 li->li_tv.vval.v_dict); | |
2495 else | |
2496 emsg(_(e_dictreq)); | |
2497 list_append_number(rettv->vval.v_list, sign_id); | |
2498 } | |
2499 } | |
2500 | |
2501 /* | |
2502 * Undefine multiple signs | |
2503 */ | |
2504 static void | |
2505 sign_undefine_multiple(list_T *l, list_T *retlist) | |
2506 { | |
2507 char_u *name; | |
2508 listitem_T *li; | |
2509 int retval; | |
2510 | |
2511 for (li = l->lv_first; li != NULL; li = li->li_next) | |
2512 { | |
2513 retval = -1; | |
2514 name = tv_get_string_chk(&li->li_tv); | |
2515 if (name != NULL && (sign_undefine_by_name(name) == OK)) | |
2516 retval = 0; | |
2517 list_append_number(retlist, retval); | |
2518 } | |
2353 } | 2519 } |
2354 | 2520 |
2355 /* | 2521 /* |
2356 * "sign_undefine()" function | 2522 * "sign_undefine()" function |
2357 */ | 2523 */ |
2358 void | 2524 void |
2359 f_sign_undefine(typval_T *argvars, typval_T *rettv) | 2525 f_sign_undefine(typval_T *argvars, typval_T *rettv) |
2360 { | 2526 { |
2361 char_u *name; | 2527 char_u *name; |
2528 | |
2529 if (argvars[0].v_type == VAR_LIST && argvars[1].v_type == VAR_UNKNOWN) | |
2530 { | |
2531 // Undefine multiple signs | |
2532 if (rettv_list_alloc(rettv) != OK) | |
2533 return; | |
2534 | |
2535 sign_undefine_multiple(argvars[0].vval.v_list, rettv->vval.v_list); | |
2536 return; | |
2537 } | |
2362 | 2538 |
2363 rettv->vval.v_number = -1; | 2539 rettv->vval.v_number = -1; |
2364 | 2540 |
2365 if (argvars[0].v_type == VAR_UNKNOWN) | 2541 if (argvars[0].v_type == VAR_UNKNOWN) |
2366 { | 2542 { |
2379 rettv->vval.v_number = 0; | 2555 rettv->vval.v_number = 0; |
2380 } | 2556 } |
2381 } | 2557 } |
2382 | 2558 |
2383 /* | 2559 /* |
2384 * "sign_unplace()" function | 2560 * Unplace the sign with attributes specified in 'dict'. Returns 0 on success |
2385 */ | 2561 * and -1 on failure. |
2386 void | 2562 */ |
2387 f_sign_unplace(typval_T *argvars, typval_T *rettv) | 2563 static int |
2388 { | 2564 sign_unplace_from_dict(typval_T *group_tv, dict_T *dict) |
2389 dict_T *dict; | 2565 { |
2390 dictitem_T *di; | 2566 dictitem_T *di; |
2391 int sign_id = 0; | 2567 int sign_id = 0; |
2392 buf_T *buf = NULL; | 2568 buf_T *buf = NULL; |
2393 char_u *group = NULL; | 2569 char_u *group = NULL; |
2394 | 2570 int retval = -1; |
2395 rettv->vval.v_number = -1; | 2571 |
2396 | 2572 // sign group |
2397 if (argvars[0].v_type != VAR_STRING) | 2573 if (group_tv != NULL) |
2398 { | 2574 group = tv_get_string(group_tv); |
2399 emsg(_(e_invarg)); | |
2400 return; | |
2401 } | |
2402 | |
2403 group = tv_get_string(&argvars[0]); | |
2404 if (group[0] == '\0') | |
2405 group = NULL; // global sign group | |
2406 else | 2575 else |
2407 { | 2576 group = dict_get_string(dict, (char_u *)"group", FALSE); |
2408 group = vim_strsave(group); | 2577 if (group != NULL) |
2409 if (group == NULL) | 2578 { |
2410 return; | 2579 if (group[0] == '\0') // global sign group |
2411 } | 2580 group = NULL; |
2412 | 2581 else |
2413 if (argvars[1].v_type != VAR_UNKNOWN) | 2582 { |
2414 { | 2583 group = vim_strsave(group); |
2415 if (argvars[1].v_type != VAR_DICT) | 2584 if (group == NULL) |
2416 { | 2585 return -1; |
2417 emsg(_(e_dictreq)); | 2586 } |
2418 goto cleanup; | 2587 } |
2419 } | 2588 |
2420 dict = argvars[1].vval.v_dict; | 2589 if (dict != NULL) |
2421 | 2590 { |
2422 if ((di = dict_find(dict, (char_u *)"buffer", -1)) != NULL) | 2591 if ((di = dict_find(dict, (char_u *)"buffer", -1)) != NULL) |
2423 { | 2592 { |
2424 buf = get_buf_arg(&di->di_tv); | 2593 buf = get_buf_arg(&di->di_tv); |
2425 if (buf == NULL) | 2594 if (buf == NULL) |
2426 goto cleanup; | 2595 goto cleanup; |
2427 } | 2596 } |
2428 if (dict_find(dict, (char_u *)"id", -1) != NULL) | 2597 if (dict_find(dict, (char_u *)"id", -1) != NULL) |
2598 { | |
2429 sign_id = dict_get_number(dict, (char_u *)"id"); | 2599 sign_id = dict_get_number(dict, (char_u *)"id"); |
2600 if (sign_id <= 0) | |
2601 { | |
2602 emsg(_(e_invarg)); | |
2603 goto cleanup; | |
2604 } | |
2605 } | |
2430 } | 2606 } |
2431 | 2607 |
2432 if (buf == NULL) | 2608 if (buf == NULL) |
2433 { | 2609 { |
2434 // Delete the sign in all the buffers | 2610 // Delete the sign in all the buffers |
2611 retval = 0; | |
2435 FOR_ALL_BUFFERS(buf) | 2612 FOR_ALL_BUFFERS(buf) |
2436 if (sign_unplace(sign_id, group, buf, 0) == OK) | 2613 if (sign_unplace(sign_id, group, buf, 0) != OK) |
2437 rettv->vval.v_number = 0; | 2614 retval = -1; |
2438 } | 2615 } |
2439 else | 2616 else if (sign_unplace(sign_id, group, buf, 0) == OK) |
2440 { | 2617 retval = 0; |
2441 if (sign_unplace(sign_id, group, buf, 0) == OK) | |
2442 rettv->vval.v_number = 0; | |
2443 } | |
2444 | 2618 |
2445 cleanup: | 2619 cleanup: |
2446 vim_free(group); | 2620 vim_free(group); |
2621 | |
2622 return retval; | |
2623 } | |
2624 | |
2625 /* | |
2626 * "sign_unplace()" function | |
2627 */ | |
2628 void | |
2629 f_sign_unplace(typval_T *argvars, typval_T *rettv) | |
2630 { | |
2631 dict_T *dict = NULL; | |
2632 | |
2633 rettv->vval.v_number = -1; | |
2634 | |
2635 if (argvars[0].v_type != VAR_STRING) | |
2636 { | |
2637 emsg(_(e_invarg)); | |
2638 return; | |
2639 } | |
2640 | |
2641 if (argvars[1].v_type != VAR_UNKNOWN) | |
2642 { | |
2643 if (argvars[1].v_type != VAR_DICT) | |
2644 { | |
2645 emsg(_(e_dictreq)); | |
2646 return; | |
2647 } | |
2648 dict = argvars[1].vval.v_dict; | |
2649 } | |
2650 | |
2651 rettv->vval.v_number = sign_unplace_from_dict(&argvars[0], dict); | |
2652 } | |
2653 | |
2654 /* | |
2655 * "sign_unplacelist()" function | |
2656 */ | |
2657 void | |
2658 f_sign_unplacelist(typval_T *argvars, typval_T *rettv) | |
2659 { | |
2660 listitem_T *li; | |
2661 int retval; | |
2662 | |
2663 if (rettv_list_alloc(rettv) != OK) | |
2664 return; | |
2665 | |
2666 if (argvars[0].v_type != VAR_LIST) | |
2667 { | |
2668 emsg(_(e_listreq)); | |
2669 return; | |
2670 } | |
2671 | |
2672 for (li = argvars[0].vval.v_list->lv_first; li != NULL; li = li->li_next) | |
2673 { | |
2674 retval = -1; | |
2675 if (li->li_tv.v_type == VAR_DICT) | |
2676 retval = sign_unplace_from_dict(NULL, li->li_tv.vval.v_dict); | |
2677 else | |
2678 emsg(_(e_dictreq)); | |
2679 list_append_number(rettv->vval.v_list, retval); | |
2680 } | |
2447 } | 2681 } |
2448 | 2682 |
2449 #endif /* FEAT_SIGNS */ | 2683 #endif /* FEAT_SIGNS */ |