comparison src/sign.c @ 15418:51b3c36b0523 v8.1.0717

patch 8.1.0717: there is no function for the ":sign jump" command commit https://github.com/vim/vim/commit/6b7b7190aa9e5c4f51bceaebf9275aa5097cfea1 Author: Bram Moolenaar <Bram@vim.org> Date: Fri Jan 11 13:42:41 2019 +0100 patch 8.1.0717: there is no function for the ":sign jump" command Problem: There is no function for the ":sign jump" command. Solution: Add the sign_jump() function. (Yegappan Lakshmanan, closes https://github.com/vim/vim/issues/3780)
author Bram Moolenaar <Bram@vim.org>
date Fri, 11 Jan 2019 13:45:06 +0100
parents c17b5e30a0af
children 55ccc2d353bd
comparison
equal deleted inserted replaced
15417:50a5ad000845 15418:51b3c36b0523
20 */ 20 */
21 typedef struct sign sign_T; 21 typedef struct sign sign_T;
22 22
23 struct sign 23 struct sign
24 { 24 {
25 sign_T *sn_next; /* next sign in list */ 25 sign_T *sn_next; // next sign in list
26 int sn_typenr; /* type number of sign */ 26 int sn_typenr; // type number of sign
27 char_u *sn_name; /* name of sign */ 27 char_u *sn_name; // name of sign
28 char_u *sn_icon; /* name of pixmap */ 28 char_u *sn_icon; // name of pixmap
29 # ifdef FEAT_SIGN_ICONS 29 # ifdef FEAT_SIGN_ICONS
30 void *sn_image; /* icon image */ 30 void *sn_image; // icon image
31 # endif 31 # endif
32 char_u *sn_text; /* text used instead of pixmap */ 32 char_u *sn_text; // text used instead of pixmap
33 int sn_line_hl; /* highlight ID for line */ 33 int sn_line_hl; // highlight ID for line
34 int sn_text_hl; /* highlight ID for text */ 34 int sn_text_hl; // highlight ID for text
35 }; 35 };
36 36
37 static sign_T *first_sign = NULL; 37 static sign_T *first_sign = NULL;
38 static int next_sign_typenr = 1; 38 static int next_sign_typenr = 1;
39 39
379 */ 379 */
380 int 380 int
381 buf_getsigntype( 381 buf_getsigntype(
382 buf_T *buf, 382 buf_T *buf,
383 linenr_T lnum, 383 linenr_T lnum,
384 int type) /* SIGN_ICON, SIGN_TEXT, SIGN_ANY, SIGN_LINEHL */ 384 int type) // SIGN_ICON, SIGN_TEXT, SIGN_ANY, SIGN_LINEHL
385 { 385 {
386 signlist_T *sign; /* a sign in a b_signlist */ 386 signlist_T *sign; // a sign in a b_signlist
387 387
388 FOR_ALL_SIGNS_IN_BUF(buf, sign) 388 FOR_ALL_SIGNS_IN_BUF(buf, sign)
389 if (sign->lnum == lnum 389 if (sign->lnum == lnum
390 && (type == SIGN_ANY 390 && (type == SIGN_ANY
391 # ifdef FEAT_SIGN_ICONS 391 # ifdef FEAT_SIGN_ICONS
524 /* 524 /*
525 * See if a given type of sign exists on a specific line. 525 * See if a given type of sign exists on a specific line.
526 */ 526 */
527 int 527 int
528 buf_findsigntype_id( 528 buf_findsigntype_id(
529 buf_T *buf, /* buffer whose sign we are searching for */ 529 buf_T *buf, // buffer whose sign we are searching for
530 linenr_T lnum, /* line number of sign */ 530 linenr_T lnum, // line number of sign
531 int typenr) /* sign type number */ 531 int typenr) // sign type number
532 { 532 {
533 signlist_T *sign; /* a sign in the signlist */ 533 signlist_T *sign; // a sign in the signlist
534 534
535 FOR_ALL_SIGNS_IN_BUF(buf, sign) 535 FOR_ALL_SIGNS_IN_BUF(buf, sign)
536 if (sign->lnum == lnum && sign->typenr == typenr) 536 if (sign->lnum == lnum && sign->typenr == typenr)
537 return sign->id; 537 return sign->id;
538 538
654 linenr_T line1, 654 linenr_T line1,
655 linenr_T line2, 655 linenr_T line2,
656 long amount, 656 long amount,
657 long amount_after) 657 long amount_after)
658 { 658 {
659 signlist_T *sign; /* a sign in a b_signlist */ 659 signlist_T *sign; // a sign in a b_signlist
660 660
661 FOR_ALL_SIGNS_IN_BUF(curbuf, sign) 661 FOR_ALL_SIGNS_IN_BUF(curbuf, sign)
662 { 662 {
663 if (sign->lnum >= line1 && sign->lnum <= line2) 663 if (sign->lnum >= line1 && sign->lnum <= line2)
664 { 664 {
676 * Find index of a ":sign" subcmd from its name. 676 * Find index of a ":sign" subcmd from its name.
677 * "*end_cmd" must be writable. 677 * "*end_cmd" must be writable.
678 */ 678 */
679 static int 679 static int
680 sign_cmd_idx( 680 sign_cmd_idx(
681 char_u *begin_cmd, /* begin of sign subcmd */ 681 char_u *begin_cmd, // begin of sign subcmd
682 char_u *end_cmd) /* just after sign subcmd */ 682 char_u *end_cmd) // just after sign subcmd
683 { 683 {
684 int idx; 684 int idx;
685 char save = *end_cmd; 685 char save = *end_cmd;
686 686
687 *end_cmd = NUL; 687 *end_cmd = NUL;
982 else 982 else
983 EMSG(_("E159: Missing sign number")); 983 EMSG(_("E159: Missing sign number"));
984 } 984 }
985 985
986 /* 986 /*
987 * sign define command 987 * Jump to a sign.
988 * ":sign define {name} ..." 988 */
989 linenr_T
990 sign_jump(int sign_id, char_u *sign_group, buf_T *buf)
991 {
992 linenr_T lnum;
993
994 if ((lnum = buf_findsign(buf, sign_id, sign_group)) <= 0)
995 {
996 EMSGN(_("E157: Invalid sign ID: %ld"), sign_id);
997 return -1;
998 }
999
1000 // goto a sign ...
1001 if (buf_jump_open_win(buf) != NULL)
1002 { // ... in a current window
1003 curwin->w_cursor.lnum = lnum;
1004 check_cursor_lnum();
1005 beginline(BL_WHITE);
1006 }
1007 else
1008 { // ... not currently in a window
1009 char_u *cmd;
1010
1011 if (buf->b_fname == NULL)
1012 {
1013 EMSG(_("E934: Cannot jump to a buffer that does not have a name"));
1014 return -1;
1015 }
1016 cmd = alloc((unsigned)STRLEN(buf->b_fname) + 25);
1017 if (cmd == NULL)
1018 return -1;
1019 sprintf((char *)cmd, "e +%ld %s", (long)lnum, buf->b_fname);
1020 do_cmdline_cmd(cmd);
1021 vim_free(cmd);
1022 }
1023 # ifdef FEAT_FOLDING
1024 foldOpenCursor();
1025 # endif
1026
1027 return lnum;
1028 }
1029
1030 /*
1031 * ":sign define {name} ..." command
989 */ 1032 */
990 static void 1033 static void
991 sign_define_cmd(char_u *sign_name, char_u *cmdline) 1034 sign_define_cmd(char_u *sign_name, char_u *cmdline)
992 { 1035 {
993 char_u *arg; 1036 char_u *arg;
1041 vim_free(linehl); 1084 vim_free(linehl);
1042 vim_free(texthl); 1085 vim_free(texthl);
1043 } 1086 }
1044 1087
1045 /* 1088 /*
1046 * :sign place command 1089 * ":sign place" command
1047 */ 1090 */
1048 static void 1091 static void
1049 sign_place_cmd( 1092 sign_place_cmd(
1050 buf_T *buf, 1093 buf_T *buf,
1051 linenr_T lnum, 1094 linenr_T lnum,
1085 sign_place(&id, group, sign_name, buf, lnum, prio); 1128 sign_place(&id, group, sign_name, buf, lnum, prio);
1086 } 1129 }
1087 } 1130 }
1088 1131
1089 /* 1132 /*
1090 * :sign unplace command 1133 * ":sign unplace" command
1091 */ 1134 */
1092 static void 1135 static void
1093 sign_unplace_cmd( 1136 sign_unplace_cmd(
1094 buf_T *buf, 1137 buf_T *buf,
1095 linenr_T lnum, 1138 linenr_T lnum,
1150 } 1193 }
1151 } 1194 }
1152 } 1195 }
1153 1196
1154 /* 1197 /*
1155 * Jump to a placed sign 1198 * Jump to a placed sign commands:
1156 * :sign jump {id} file={fname} 1199 * :sign jump {id} file={fname}
1157 * :sign jump {id} buffer={nr} 1200 * :sign jump {id} buffer={nr}
1158 * :sign jump {id} group={group} file={fname} 1201 * :sign jump {id} group={group} file={fname}
1159 * :sign jump {id} group={group} buffer={nr} 1202 * :sign jump {id} group={group} buffer={nr}
1160 */ 1203 */
1178 // File or buffer is not specified or an empty group is used 1221 // File or buffer is not specified or an empty group is used
1179 // or a line number or a sign name is specified. 1222 // or a line number or a sign name is specified.
1180 EMSG(_(e_invarg)); 1223 EMSG(_(e_invarg));
1181 return; 1224 return;
1182 } 1225 }
1183 1226 (void)sign_jump(id, group, buf);
1184 if ((lnum = buf_findsign(buf, id, group)) <= 0)
1185 {
1186 EMSGN(_("E157: Invalid sign ID: %ld"), id);
1187 return;
1188 }
1189
1190 // goto a sign ...
1191 if (buf_jump_open_win(buf) != NULL)
1192 { // ... in a current window
1193 curwin->w_cursor.lnum = lnum;
1194 check_cursor_lnum();
1195 beginline(BL_WHITE);
1196 }
1197 else
1198 { // ... not currently in a window
1199 char_u *cmd;
1200
1201 if (buf->b_fname == NULL)
1202 {
1203 EMSG(_("E934: Cannot jump to a buffer that does not have a name"));
1204 return;
1205 }
1206 cmd = alloc((unsigned)STRLEN(buf->b_fname) + 25);
1207 if (cmd == NULL)
1208 return;
1209 sprintf((char *)cmd, "e +%ld %s", (long)lnum, buf->b_fname);
1210 do_cmdline_cmd(cmd);
1211 vim_free(cmd);
1212 }
1213 # ifdef FEAT_FOLDING
1214 foldOpenCursor();
1215 # endif
1216 } 1227 }
1217 1228
1218 /* 1229 /*
1219 * Parse the command line arguments for the ":sign place", ":sign unplace" and 1230 * Parse the command line arguments for the ":sign place", ":sign unplace" and
1220 * ":sign jump" commands. 1231 * ":sign jump" commands.
1683 } 1694 }
1684 1695
1685 # if defined(FEAT_SIGN_ICONS) || defined(PROTO) 1696 # if defined(FEAT_SIGN_ICONS) || defined(PROTO)
1686 void * 1697 void *
1687 sign_get_image( 1698 sign_get_image(
1688 int typenr) /* the attribute which may have a sign */ 1699 int typenr) // the attribute which may have a sign
1689 { 1700 {
1690 sign_T *sp; 1701 sign_T *sp;
1691 1702
1692 for (sp = first_sign; sp != NULL; sp = sp->sn_next) 1703 for (sp = first_sign; sp != NULL; sp = sp->sn_next)
1693 if (sp->sn_typenr == typenr) 1704 if (sp->sn_typenr == typenr)
1707 } 1718 }
1708 1719
1709 # if defined(FEAT_CMDL_COMPL) || defined(PROTO) 1720 # if defined(FEAT_CMDL_COMPL) || defined(PROTO)
1710 static enum 1721 static enum
1711 { 1722 {
1712 EXP_SUBCMD, /* expand :sign sub-commands */ 1723 EXP_SUBCMD, // expand :sign sub-commands
1713 EXP_DEFINE, /* expand :sign define {name} args */ 1724 EXP_DEFINE, // expand :sign define {name} args
1714 EXP_PLACE, /* expand :sign place {id} args */ 1725 EXP_PLACE, // expand :sign place {id} args
1715 EXP_UNPLACE, /* expand :sign unplace" */ 1726 EXP_UNPLACE, // expand :sign unplace"
1716 EXP_SIGN_NAMES /* expand with name of placed signs */ 1727 EXP_SIGN_NAMES // expand with name of placed signs
1717 } expand_what; 1728 } expand_what;
1718 1729
1719 /* 1730 /*
1720 * Function given to ExpandGeneric() to obtain the sign command 1731 * Function given to ExpandGeneric() to obtain the sign command
1721 * expansion. 1732 * expansion.
1751 { 1762 {
1752 char *unplace_arg[] = { "group=", "file=", "buffer=", NULL }; 1763 char *unplace_arg[] = { "group=", "file=", "buffer=", NULL };
1753 return (char_u *)unplace_arg[idx]; 1764 return (char_u *)unplace_arg[idx];
1754 } 1765 }
1755 case EXP_SIGN_NAMES: 1766 case EXP_SIGN_NAMES:
1756 /* Complete with name of signs already defined */ 1767 // Complete with name of signs already defined
1757 current_idx = 0; 1768 current_idx = 0;
1758 for (sp = first_sign; sp != NULL; sp = sp->sn_next) 1769 for (sp = first_sign; sp != NULL; sp = sp->sn_next)
1759 if (current_idx++ == idx) 1770 if (current_idx++ == idx)
1760 return sp->sn_name; 1771 return sp->sn_name;
1761 return NULL; 1772 return NULL;
1774 char_u *end_subcmd; 1785 char_u *end_subcmd;
1775 char_u *last; 1786 char_u *last;
1776 int cmd_idx; 1787 int cmd_idx;
1777 char_u *begin_subcmd_args; 1788 char_u *begin_subcmd_args;
1778 1789
1779 /* Default: expand subcommands. */ 1790 // Default: expand subcommands.
1780 xp->xp_context = EXPAND_SIGN; 1791 xp->xp_context = EXPAND_SIGN;
1781 expand_what = EXP_SUBCMD; 1792 expand_what = EXP_SUBCMD;
1782 xp->xp_pattern = arg; 1793 xp->xp_pattern = arg;
1783 1794
1784 end_subcmd = skiptowhite(arg); 1795 end_subcmd = skiptowhite(arg);
1785 if (*end_subcmd == NUL) 1796 if (*end_subcmd == NUL)
1786 /* expand subcmd name 1797 // expand subcmd name
1787 * :sign {subcmd}<CTRL-D>*/ 1798 // :sign {subcmd}<CTRL-D>
1788 return; 1799 return;
1789 1800
1790 cmd_idx = sign_cmd_idx(arg, end_subcmd); 1801 cmd_idx = sign_cmd_idx(arg, end_subcmd);
1791 1802
1792 /* :sign {subcmd} {subcmd_args} 1803 // :sign {subcmd} {subcmd_args}
1793 * | 1804 // |
1794 * begin_subcmd_args */ 1805 // begin_subcmd_args
1795 begin_subcmd_args = skipwhite(end_subcmd); 1806 begin_subcmd_args = skipwhite(end_subcmd);
1796 p = skiptowhite(begin_subcmd_args); 1807 p = skiptowhite(begin_subcmd_args);
1797 if (*p == NUL) 1808 if (*p == NUL)
1798 { 1809 {
1799 /* 1810 //
1800 * Expand first argument of subcmd when possible. 1811 // Expand first argument of subcmd when possible.
1801 * For ":jump {id}" and ":unplace {id}", we could 1812 // For ":jump {id}" and ":unplace {id}", we could
1802 * possibly expand the ids of all signs already placed. 1813 // possibly expand the ids of all signs already placed.
1803 */ 1814 //
1804 xp->xp_pattern = begin_subcmd_args; 1815 xp->xp_pattern = begin_subcmd_args;
1805 switch (cmd_idx) 1816 switch (cmd_idx)
1806 { 1817 {
1807 case SIGNCMD_LIST: 1818 case SIGNCMD_LIST:
1808 case SIGNCMD_UNDEFINE: 1819 case SIGNCMD_UNDEFINE:
1809 /* :sign list <CTRL-D> 1820 // :sign list <CTRL-D>
1810 * :sign undefine <CTRL-D> */ 1821 // :sign undefine <CTRL-D>
1811 expand_what = EXP_SIGN_NAMES; 1822 expand_what = EXP_SIGN_NAMES;
1812 break; 1823 break;
1813 default: 1824 default:
1814 xp->xp_context = EXPAND_NOTHING; 1825 xp->xp_context = EXPAND_NOTHING;
1815 } 1826 }
1816 return; 1827 return;
1817 } 1828 }
1818 1829
1819 /* expand last argument of subcmd */ 1830 // expand last argument of subcmd
1820 1831
1821 /* :sign define {name} {args}... 1832 // :sign define {name} {args}...
1822 * | 1833 // |
1823 * p */ 1834 // p
1824 1835
1825 /* Loop until reaching last argument. */ 1836 // Loop until reaching last argument.
1826 do 1837 do
1827 { 1838 {
1828 p = skipwhite(p); 1839 p = skipwhite(p);
1829 last = p; 1840 last = p;
1830 p = skiptowhite(p); 1841 p = skiptowhite(p);
1831 } while (*p != NUL); 1842 } while (*p != NUL);
1832 1843
1833 p = vim_strchr(last, '='); 1844 p = vim_strchr(last, '=');
1834 1845
1835 /* :sign define {name} {args}... {last}= 1846 // :sign define {name} {args}... {last}=
1836 * | | 1847 // | |
1837 * last p */ 1848 // last p
1838 if (p == NULL) 1849 if (p == NULL)
1839 { 1850 {
1840 /* Expand last argument name (before equal sign). */ 1851 // Expand last argument name (before equal sign).
1841 xp->xp_pattern = last; 1852 xp->xp_pattern = last;
1842 switch (cmd_idx) 1853 switch (cmd_idx)
1843 { 1854 {
1844 case SIGNCMD_DEFINE: 1855 case SIGNCMD_DEFINE:
1845 expand_what = EXP_DEFINE; 1856 expand_what = EXP_DEFINE;
1855 xp->xp_context = EXPAND_NOTHING; 1866 xp->xp_context = EXPAND_NOTHING;
1856 } 1867 }
1857 } 1868 }
1858 else 1869 else
1859 { 1870 {
1860 /* Expand last argument value (after equal sign). */ 1871 // Expand last argument value (after equal sign).
1861 xp->xp_pattern = p + 1; 1872 xp->xp_pattern = p + 1;
1862 switch (cmd_idx) 1873 switch (cmd_idx)
1863 { 1874 {
1864 case SIGNCMD_DEFINE: 1875 case SIGNCMD_DEFINE:
1865 if (STRNCMP(last, "texthl", p - last) == 0 1876 if (STRNCMP(last, "texthl", p - last) == 0