about summary refs log tree commit diff stats
path: root/search.lua
diff options
context:
space:
mode:
authorKartik K. Agaram <vc@akkartik.com>2022-06-03 14:14:53 -0700
committerKartik K. Agaram <vc@akkartik.com>2022-06-03 14:17:41 -0700
commit0d52962b3e6f91e458fbf858e62e684494373af8 (patch)
treedfb7a44f830e595a585bfbdd17d4789c8f046fb7 /search.lua
parent06e6ecdf8f8f8f8489b2e0d1145698a52a7c3ae5 (diff)
downloadlines.love-0d52962b3e6f91e458fbf858e62e684494373af8.tar.gz
extract a couple of files
Diffstat (limited to 'search.lua')
-rw-r--r--search.lua114
1 files changed, 114 insertions, 0 deletions
diff --git a/search.lua b/search.lua
new file mode 100644
index 0000000..29dd8dd
--- /dev/null
+++ b/search.lua
@@ -0,0 +1,114 @@
+-- helpers for the search bar (C-f)
+
+function Text.draw_search_bar()
+  local h = Line_height+2
+  local y = App.screen.height-h
+  love.graphics.setColor(0.9,0.9,0.9)
+  love.graphics.rectangle('fill', 0, y-10, App.screen.width-1, h+8)
+  love.graphics.setColor(0.6,0.6,0.6)
+  love.graphics.line(0, y-10, App.screen.width-1, y-10)
+  love.graphics.setColor(1,1,1)
+  love.graphics.rectangle('fill', 20, y-6, App.screen.width-40, h+2, 2,2)
+  love.graphics.setColor(0.6,0.6,0.6)
+  love.graphics.rectangle('line', 20, y-6, App.screen.width-40, h+2, 2,2)
+  love.graphics.setColor(0,0,0)
+  App.screen.print(Search_term, 25,y-5)
+  love.graphics.setColor(1,0,0)
+  if Search_text == nil then
+    Search_text = App.newText(love.graphics.getFont(), Search_term)
+  end
+  love.graphics.circle('fill', 25+App.width(Search_text),y-5+h, 2)
+  love.graphics.setColor(0,0,0)
+end
+
+function Text.search_next()
+  -- search current line
+  local pos = Lines[Cursor1.line].data:find(Search_term, Cursor1.pos)
+  if pos then
+    Cursor1.pos = pos
+  end
+  if pos == nil then
+    for i=Cursor1.line+1,#Lines do
+      pos = Lines[i].data:find(Search_term)
+      if pos then
+        Cursor1.line = i
+        Cursor1.pos = pos
+        break
+      end
+    end
+  end
+  if pos == nil then
+    -- wrap around
+    for i=1,Cursor1.line-1 do
+      pos = Lines[i].data:find(Search_term)
+      if pos then
+        Cursor1.line = i
+        Cursor1.pos = pos
+        break
+      end
+    end
+  end
+  if pos == nil then
+    Cursor1.line = Search_backup.cursor.line
+    Cursor1.pos = Search_backup.cursor.pos
+    Screen_top1.line = Search_backup.screen_top.line
+    Screen_top1.pos = Search_backup.screen_top.pos
+  end
+  if Text.lt1(Cursor1, Screen_top1) or Text.lt1(Screen_bottom1, Cursor1) then
+    Screen_top1.line = Cursor1.line
+    local _, pos = Text.pos_at_start_of_cursor_screen_line()
+    Screen_top1.pos = pos
+  end
+end
+
+function Text.search_previous()
+  -- search current line
+  local pos = rfind(Lines[Cursor1.line].data, Search_term, Cursor1.pos)
+  if pos then
+    Cursor1.pos = pos
+  end
+  if pos == nil then
+    for i=Cursor1.line-1,1,-1 do
+      pos = rfind(Lines[i].data, Search_term)
+      if pos then
+        Cursor1.line = i
+        Cursor1.pos = pos
+        break
+      end
+    end
+  end
+  if pos == nil then
+    -- wrap around
+    for i=#Lines,Cursor1.line+1,-1 do
+      pos = rfind(Lines[i].data, Search_term)
+      if pos then
+        Cursor1.line = i
+        Cursor1.pos = pos
+        break
+      end
+    end
+  end
+  if pos == nil then
+    Cursor1.line = Search_backup.cursor.line
+    Cursor1.pos = Search_backup.cursor.pos
+    Screen_top1.line = Search_backup.screen_top.line
+    Screen_top1.pos = Search_backup.screen_top.pos
+  end
+  if Text.lt1(Cursor1, Screen_top1) or Text.lt1(Screen_bottom1, Cursor1) then
+    Screen_top1.line = Cursor1.line
+    local _, pos = Text.pos_at_start_of_cursor_screen_line()
+    Screen_top1.pos = pos
+  end
+end
+
+function rfind(s, pat, i)
+  local rs = s:reverse()
+  local rpat = pat:reverse()
+  if i == nil then i = #s end
+  local ri = #s - i + 1
+  local rendpos = rs:find(rpat, ri)
+  if rendpos == nil then return nil end
+  local endpos = #s - rendpos + 1
+  assert (endpos >= #pat)
+  return endpos-#pat+1
+end