summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLeo Tenenbaum <pommicket@gmail.com>2021-02-03 18:48:26 -0500
committerLeo Tenenbaum <pommicket@gmail.com>2021-02-03 18:48:52 -0500
commit5a207b62cebb4673eb3422001e8d9435fca9f545 (patch)
tree802a86a4ea6ea05f036e293a3c2eba607457f644
parentb72ce9a3fdfe956f566c8bdde1fceebe7601c59f (diff)
line numbering!
-rw-r--r--buffer.c68
-rw-r--r--colors.h7
-rw-r--r--config.c1
-rw-r--r--keywords.h2
-rwxr-xr-xkeywords.py3
-rw-r--r--main.c3
-rw-r--r--math.c8
-rw-r--r--ted.cfg6
-rw-r--r--ted.h1
9 files changed, 75 insertions, 24 deletions
diff --git a/buffer.c b/buffer.c
index 53d8201..9df8b65 100644
--- a/buffer.c
+++ b/buffer.c
@@ -1898,8 +1898,8 @@ void buffer_render(TextBuffer *buffer, Rect r) {
Ted *ted = buffer->ted;
Settings const *settings = buffer_settings(buffer);
u32 const *colors = settings->colors;
-
- float border_thickness = settings->border_thickness;
+ float const padding = settings->padding;
+ float const border_thickness = settings->border_thickness;
u32 border_color = colors[COLOR_BORDER]; // color of border around buffer
@@ -1914,19 +1914,46 @@ void buffer_render(TextBuffer *buffer, Rect r) {
x2 -= border_thickness * 0.5f;
y2 -= border_thickness * 0.5f;
+ u32 start_line = (u32)buffer->scroll_y; // line to start rendering from
+ float render_start_y = y1 - (float)(buffer->scroll_y - start_line) * char_height; // where the 1st line is rendered
+
+ // line numbering
+ if (!buffer->is_line_buffer && settings->line_numbers) {
+ float line_number_width = ndigits_u64(buffer->nlines) * char_width + padding;
+
+ TextRenderState text_state = text_render_state_default;
+ text_state.min_y = y1;
+ text_state.max_y = y2;
+
+ float y = render_start_y;
+ text_chars_begin(font);
+ gl_color_rgba(colors[COLOR_LINE_NUMBERS]);
+ for (u32 line = start_line; line < buffer->nlines; ++line) {
+ char str[32] = {0};
+ strbuf_printf(str, U32_FMT, line + 1); // convert line number to string
+ float x = x1 + line_number_width - (float)strlen(str) * char_width; // right justify
+ text_render_with_state(font, &text_state, str, x, y);
+ y += char_height;
+ if (y > y2) break;
+ }
+ text_chars_end(font);
+
+ x1 += line_number_width;
+ x1 += 2; // a little bit of padding
+ // line separating line numbers from text
+ glBegin(GL_LINES);
+ gl_color_rgba(colors[COLOR_LINE_NUMBERS_SEPARATOR]);
+ glVertex2f(x1, y1);
+ glVertex2f(x1, y2);
+ glEnd();
+ x1 += padding;
+ }
// get screen coordinates of cursor
v2 cursor_display_pos = buffer_pos_to_pixels(buffer, buffer->cursor_pos);
// the rectangle that the cursor is rendered as
Rect cursor_rect = rect(cursor_display_pos, V2(settings->cursor_width, char_height));
- TextRenderState text_state = {
- .x = 0, .y = 0,
- .min_x = x1, .min_y = y1,
- .max_x = x2, .max_y = y2,
- .render = true
- };
-
buffer->x1 = x1; buffer->y1 = y1; buffer->x2 = x2; buffer->y2 = y2;
@@ -1945,7 +1972,6 @@ void buffer_render(TextBuffer *buffer, Rect r) {
float render_start_x = x1 - (float)buffer->scroll_x * char_width;
u32 column = 0;
- u32 start_line = (u32)buffer->scroll_y; // line to start rendering from
if (buffer->selection) { // draw selection
glBegin(GL_QUADS);
@@ -1992,17 +2018,6 @@ void buffer_render(TextBuffer *buffer, Rect r) {
}
- text_chars_begin(font);
-
- text_state = (TextRenderState){
- .x = render_start_x, .y = y1,
- .min_x = x1, .min_y = y1,
- .max_x = x2, .max_y = y2,
- .render = true
- };
-
- text_state.y -= (float)(buffer->scroll_y - start_line) * char_height;
-
Language language = buffer_language(buffer);
// dynamic array of character types, to be filled by syntax_highlight
SyntaxCharType *char_types = NULL;
@@ -2035,6 +2050,17 @@ void buffer_render(TextBuffer *buffer, Rect r) {
buffer->longest_line_on_screen = 0;
+
+ text_chars_begin(font);
+
+ TextRenderState text_state = text_render_state_default;
+ text_state.x = render_start_x;
+ text_state.y = render_start_y;
+ text_state.min_x = x1;
+ text_state.min_y = y1;
+ text_state.max_x = x2;
+ text_state.max_y = y2;
+
for (u32 line_idx = start_line; line_idx < nlines; ++line_idx) {
Line *line = &lines[line_idx];
buffer->longest_line_on_screen = max_u32(buffer->longest_line_on_screen, line->len);
diff --git a/colors.h b/colors.h
index 28f9951..374d652 100644
--- a/colors.h
+++ b/colors.h
@@ -31,6 +31,9 @@ ENUM_U16 {
COLOR_CHARACTER,
COLOR_CONSTANT,
+ COLOR_LINE_NUMBERS,
+ COLOR_LINE_NUMBERS_SEPARATOR,
+
COLOR_COUNT
} ENUM_U16_END(ColorSetting);
@@ -67,7 +70,9 @@ static ColorName const color_names[COLOR_COUNT] = {
{COLOR_CONSTANT, "constant"},
{COLOR_YES, "yes"},
{COLOR_NO, "no"},
- {COLOR_CANCEL, "cancel"}
+ {COLOR_CANCEL, "cancel"},
+ {COLOR_LINE_NUMBERS, "line-numbers"},
+ {COLOR_LINE_NUMBERS_SEPARATOR, "line-numbers-separator"},
};
static ColorSetting color_setting_from_str(char const *str) {
diff --git a/config.c b/config.c
index 15b787d..b389867 100644
--- a/config.c
+++ b/config.c
@@ -175,6 +175,7 @@ void config_read(Ted *ted, char const *filename) {
{"auto-indent", &settings->auto_indent},
{"auto-add-newline", &settings->auto_add_newline},
{"syntax-highlighting", &settings->syntax_highlighting},
+ {"line-numbers", &settings->line_numbers},
};
OptionU8 const options_u8[] = {
{"tab-width", &settings->tab_width, 1, 100},
diff --git a/keywords.h b/keywords.h
index 56417c4..5906c6f 100644
--- a/keywords.h
+++ b/keywords.h
@@ -1,3 +1,5 @@
+// keywords for all languages ted supports
+// This file was auto-generated by keywords.py
typedef struct {
char const *str;
SyntaxCharType type;
diff --git a/keywords.py b/keywords.py
index cbe704e..951f3b2 100755
--- a/keywords.py
+++ b/keywords.py
@@ -217,6 +217,9 @@ builtins_python = ['ArithmeticError', 'AssertionError', 'AttributeError', 'BaseE
]
file = open('keywords.h', 'w')
+file.write('''// keywords for all languages ted supports
+// This file was auto-generated by keywords.py
+''')
file.write('''typedef struct {
char const *str;
SyntaxCharType type;
diff --git a/main.c b/main.c
index 3ad3786..2a7fc1a 100644
--- a/main.c
+++ b/main.c
@@ -1,9 +1,10 @@
// @TODO:
-// - line numbering
// - popup to reload files and config on change
+// - shouldn't be possible to open the same file twice
// - find & replace (with regex)
// - split
// - completion
+// - view-only
// - Windows installation
#include "base.h"
no_warn_start
diff --git a/math.c b/math.c
index c177eef..1443267 100644
--- a/math.c
+++ b/math.c
@@ -70,6 +70,14 @@ static inline u32 clamp_u32(u32 x, u32 a, u32 b) {
return x;
}
+static inline u8 ndigits_u64(u64 x) {
+ u8 ndigits = 1;
+ while (x > 9) {
+ x /= 10;
+ ++ndigits;
+ }
+ return ndigits;
+}
// remap x from the interval [from_a, from_b] to the interval [to_a, to_b], NOT clamping if x is outside the "from" interval.
static inline float remapf(float x, float from_a, float from_b, float to_a, float to_b) {
diff --git a/ted.cfg b/ted.cfg
index 6091a47..325c444 100644
--- a/ted.cfg
+++ b/ted.cfg
@@ -20,6 +20,7 @@ auto-indent = on
# automatically add a newline at the end of the file on save
auto-add-newline = on
syntax-highlighting = on
+line-numbers = on
[keyboard]
# motion and selection
@@ -140,8 +141,11 @@ builtin = #a7f
comment = #999
constant = #8ff
+line-numbers = #779
+line-numbers-separator = #fff3
+
[extensions]
C = .c, .h
C++ = .cpp, .hpp, .C, .H, .cxx, .hxx, .cc, .hh
Rust = .rs
-Python = .py \ No newline at end of file
+Python = .py
diff --git a/ted.h b/ted.h
index 646da6d..b0e6f6a 100644
--- a/ted.h
+++ b/ted.h
@@ -70,6 +70,7 @@ typedef struct {
bool auto_indent;
bool auto_add_newline;
bool syntax_highlighting;
+ bool line_numbers;
u8 tab_width;
u8 cursor_width;
u8 undo_save_time;