summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--main.c60
1 files changed, 51 insertions, 9 deletions
diff --git a/main.c b/main.c
index 46c440b..d5b913d 100644
--- a/main.c
+++ b/main.c
@@ -262,23 +262,37 @@ TxtLoc prev_func_end(TxtLoc l) {
return l;
}
+int empty_line(TxtLoc l) {
+ u8 b = txt_byte(start_of_line(l));
+ return b == '\n' || b == 0 /* last line of buffer */
+ ;
+}
+
+int match_func_start(TxtLoc l, TxtLoc *out) {
+ l = start_of_line(l);
+ if (txt_chr(l) != '}' || txt_chr(cnext(l)) != '\n') return 0;
+ for (;;) {
+ if (!empty_line(l) && !is_space(txt_chr(l)) && txt_chr(cprev(end_of_line(l))) == '{') {
+ *out = l;
+ return 1;
+ }
+ if (at_start(l)) return 0;
+ l = prev_line_start(l);
+ }
+ return 0;
+}
+
TxtLoc prev_func(TxtLoc l) {
- match_bracket(prev_func_end(l), &l, '}');
+ match_func_start(prev_func_end(l), &l);
return l;
}
TxtLoc next_func(TxtLoc l) {
match_bracket(l, &l, '{');
- match_bracket(next_func_end(l), &l, '}');
+ match_func_start(next_func_end(l), &l);
return l;
}
-int empty_line(TxtLoc l) {
- u8 b = txt_byte(start_of_line(l));
- return b == '\n' || b == 0 /* last line of buffer */
- ;
-}
-
TxtLoc next_par(TxtLoc l) {
while (!at_end(l) && empty_line(l)) l = next_newline(l);
while (!at_end(l) && !empty_line(l)) l = next_newline(l);
@@ -553,7 +567,7 @@ void draw_opts(Str *optv, u32 optc, u32 *optvi, u32 opti) {
u32 n = LINES;
u32 tn = n / 2;
u32 top = opti > tn ? opti - tn : 0;
- u32 bot = optc - top > n ? n : optc - top;
+ u32 bot = top + n > optc ? optc : top + n;
for (u32 i = top; i < bot; i++) {
VuiAttr a = A_DEFAULT;
if (i == opti) a |= A_REVERSE;
@@ -1237,6 +1251,30 @@ int select_buf(void) {
return o;
}
+int select_func(Txt *t, TxtLoc *out) {
+ TxtLoc l = txt_start(t);
+ DYNARR(TxtLoc) loc = { 0 };
+ while (!at_end(l)) {
+ l = next_func_end(l);
+ TxtLoc fn;
+ if (match_func_start(l, &fn)) {
+ DA_APUSH(&loc, &e.scratch, fn);
+ }
+ }
+ Str *opt = new_arr(&e.scratch, Str, loc.n);
+ for (u32 i = 0; i < loc.n; i++) {
+ opt[i] = txt_collect_range(start_of_line(loc.v[i]), end_of_line(loc.v[i]), &e.scratch);
+ ASSERT(opt[i].n > 0);
+ opt[i].n--;
+ while (opt[i].n > 0 && is_space(opt[i].s[opt[i].n - 1])) opt[i].n--;
+ opt[i].s[opt[i].n++] = ';';
+ }
+ int o = select_opt(opt, loc.n, S("Function: "));
+ if (o == -1) return 0;
+ *out = loc.v[o];
+ return 1;
+}
+
int main(int argc, const char **argv) {
ed_init(&e);
e.homedir = str_from_cstr(getenv("HOME"));
@@ -1409,6 +1447,10 @@ int main(int argc, const char **argv) {
int b = select_buf();
if (b != -1) e.bufi = b;
} break;
+ case 'j': {
+ TxtLoc l;
+ if (select_func(eb->txt, &l)) eb->cur = l;
+ } break;
case 'm':
build_file(eb->path, 1);
break;