From 0078f0a757eb263742cc4e8bab0b43c4d77ce56d Mon Sep 17 00:00:00 2001 From: "Kartik K. Agaram" Date: Sun, 1 Sep 2024 19:54:26 -0700 Subject: [PATCH] reuse get_rect in edit.draw --- edit.lua | 100 ++++++++++++++++++------------------------------------- move.lua | 6 ++-- 2 files changed, 36 insertions(+), 70 deletions(-) diff --git a/edit.lua b/edit.lua index e26c91b..7c2de02 100644 --- a/edit.lua +++ b/edit.lua @@ -117,40 +117,18 @@ function edit.draw(editor) cursor_or_mouse_loc = loc end end - - local do_it = function(x,y, w, line_index, pos, char) - if in_selection(editor, line_index, pos, cursor_or_mouse_loc) - or in_search(editor, line_index, pos) - then - App.color(Highlight_color) - love.graphics.rectangle('fill', x,y, w,editor.line_height) - end - App.color(Text_color) - love.graphics.print(char, x,y) - if line_index == editor.cursor.line and pos == editor.cursor.pos then - Text.draw_cursor(editor, x,y) - end - end - - -- I like to show the cursor in two places when it lies on the boundary - -- between screen lines of a wrapped line. This helps with that. - local draw_just_cursor = function(x,y, line_index, pos) - if line_index == editor.cursor.line and pos == editor.cursor.pos then - Text.draw_cursor(editor, x,y) - end - end - local y = editor.top for line_index, line in array.each(editor.lines, editor.screen_top.line) do - if line.mode == 'text' then - local x = editor.left - local initpos = 1 - if line_index == editor.screen_top.line then - initpos = editor.screen_top.pos - end ---? print('screen line', line_index, initpos, y) - if line.data == '' then - -- button to insert new drawing + local rect + if line_index == editor.screen_top.line then + rect = edit.get_rect(editor, editor.screen_top) + else + rect = edit.get_rect(editor, {mode=line.mode, line=line_index, pos=1}) + end + if rect.screen_line_rects then + -- text line + if #line.data == 0 then + -- empty line; just add a button to insert a new drawing button(editor, 'draw', {x=editor.left-Margin_left+4, y=y+4, w=12,h=12, bg={r=1,g=1,b=0}, icon = icon.insert_drawing, onpress1 = function() @@ -166,49 +144,37 @@ function edit.draw(editor) end, }) else - for pos,char in utf8chars(line.data, initpos) do - local w = editor.font:getWidth(char) - if char:match('%s') then - if Text.line_wrap_at_word_boundary(editor, x, line.data, pos) then - do_it(x,y, w, line_index, pos, char) - x = editor.left - y = y + editor.line_height - if y + editor.line_height > editor.bottom then - break - end ---? print('screen line', line_index, pos+1, y) - draw_just_cursor(x,y, line_index, pos) - else - do_it(x,y, w, line_index, pos, char) - x = x + w + for _,s in ipairs(rect.screen_line_rects) do + for _,c in ipairs(s.char_rects) do + if in_selection(editor, line_index, c.pos, cursor_or_mouse_loc) + or in_search(editor, line_index, c.pos) + then + App.color(Highlight_color) + love.graphics.rectangle('fill', editor.left+c.x, y+c.y, c.dx,c.dy) end - else - if x+w > editor.right then - draw_just_cursor(x,y, line_index, pos) - x = editor.left - y = y + editor.line_height - if y + editor.line_height > editor.bottom then - break - end ---? print('screen line', line_index, pos, y) - do_it(x,y, w, line_index, pos, char) - else - do_it(x,y, w, line_index, pos, char) + if c.data then + App.color(Text_color) + love.graphics.print(c.data, editor.left+c.x, y+c.y) + end + if line_index == editor.cursor.line then + if c.pos == editor.cursor.pos then + Text.draw_cursor(editor, editor.left+c.x, y+c.y) + end end - x = x + w end end end -- draw cursor if it's at end of line - do_it(x,y, 0, line_index, utf8.len(line.data)+1, '') - y = y + editor.line_height - elseif line.mode == 'drawing' then - local h = Drawing_padding_height + Drawing.pixels(line.h, editor.width) - Drawing.draw(editor, line_index, y+Drawing_padding_top) - y = y + h + if line_index == editor.cursor.line and editor.cursor.pos == utf8.len(line.data)+1 then + local s = rect.screen_line_rects + local c = s[#s].char_rects + Text.draw_cursor(editor, editor.left+c[#c].x, y+c[#c].y) + end else - assert(false, ('unknown line mode %s'):format(line.mode)) + -- drawing + Drawing.draw(editor, line_index, y+Drawing_padding_top) end + y = y + rect.dy if y + editor.line_height > editor.bottom then break end diff --git a/move.lua b/move.lua index da0981c..7d4e673 100644 --- a/move.lua +++ b/move.lua @@ -560,7 +560,7 @@ function Text.get_rect(editor, loc) if char:match('%s') then if Text.line_wrap_at_word_boundary(editor, editor.left + x, line.data, pos) then table.insert(curr_screen_line, - {x=x, y=y, dx=editor.width-x, dy=editor.line_height, pos=pos}) -- char+filler + {x=x, y=y, dx=editor.width-x, dy=editor.line_height, pos=pos, data=char}) -- char+filler table.insert(screen_lines, {x=0, y=y, dx=editor.width, dy=editor.line_height, pos=spos, dpos=pos-spos+1, char_rects=curr_screen_line}) @@ -573,7 +573,7 @@ function Text.get_rect(editor, loc) end else table.insert(curr_screen_line, - {x=x, y=y, dx=w, dy=editor.line_height, pos=pos}) + {x=x, y=y, dx=w, dy=editor.line_height, pos=pos, data=char}) x = x + w end else @@ -595,7 +595,7 @@ function Text.get_rect(editor, loc) -- nothing end table.insert(curr_screen_line, - {x=x, y=y, dx=w, dy=editor.line_height, pos=pos}) + {x=x, y=y, dx=w, dy=editor.line_height, pos=pos, data=char}) x = x + w end end