From 202e42b568a50547e3c1b32f6eed41ad6ad071a3 Mon Sep 17 00:00:00 2001 From: Guldoman Date: Tue, 12 Apr 2022 02:37:21 +0200 Subject: [PATCH 1/5] Avoid calling `View:scrollbar_overlaps_point` uselessly `View:on_mouse_moved` already updated `self.hovered_scrollbar`, so use that instead. --- data/core/docview.lua | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/data/core/docview.lua b/data/core/docview.lua index 397b455e..a3f9ebd2 100644 --- a/data/core/docview.lua +++ b/data/core/docview.lua @@ -227,7 +227,7 @@ end function DocView:on_mouse_moved(x, y, ...) DocView.super.on_mouse_moved(self, x, y, ...) - if self:scrollbar_overlaps_point(x, y) or self.dragging_scrollbar then + if self.hovered_scrollbar or self.dragging_scrollbar then self.cursor = "arrow" else self.cursor = "ibeam" From 052c140787825f678dc7d181d01bd43d621072e7 Mon Sep 17 00:00:00 2001 From: Guldoman Date: Tue, 12 Apr 2022 02:38:30 +0200 Subject: [PATCH 2/5] Fix `DocView:on_mouse_released` not considering all parameters --- data/core/docview.lua | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/data/core/docview.lua b/data/core/docview.lua index a3f9ebd2..65a3778e 100644 --- a/data/core/docview.lua +++ b/data/core/docview.lua @@ -270,8 +270,8 @@ function DocView:mouse_selection(doc, snap_type, line1, col1, line2, col2) end -function DocView:on_mouse_released(button) - DocView.super.on_mouse_released(self, button) +function DocView:on_mouse_released(...) + DocView.super.on_mouse_released(self, ...) self.mouse_selecting = nil end From 48c371a638dede68ba4ca13846d1a4717b324437 Mon Sep 17 00:00:00 2001 From: Guldoman Date: Tue, 12 Apr 2022 02:49:11 +0200 Subject: [PATCH 3/5] Add scrollbar "track" and resize on hover --- data/core/style.lua | 2 + data/core/view.lua | 98 +++++++++++++++++++++++++++++++++++++++++---- 2 files changed, 92 insertions(+), 8 deletions(-) diff --git a/data/core/style.lua b/data/core/style.lua index 470a0904..70ad502c 100644 --- a/data/core/style.lua +++ b/data/core/style.lua @@ -4,6 +4,7 @@ local style = {} style.padding = { x = common.round(14 * SCALE), y = common.round(7 * SCALE) } style.divider_size = common.round(1 * SCALE) style.scrollbar_size = common.round(4 * SCALE) +style.expanded_scrollbar_size = common.round(12 * SCALE) style.caret_width = common.round(2 * SCALE) style.tab_width = common.round(170 * SCALE) @@ -43,6 +44,7 @@ style.line_number2 = { common.color "#83838f" } -- With cursor style.line_highlight = { common.color "#343438" } style.scrollbar = { common.color "#414146" } style.scrollbar2 = { common.color "#4b4b52" } -- Hovered +style.scrollbar_track = { common.color "#252529" } style.nagbar = { common.color "#FF0000" } style.nagbar_text = { common.color "#FFFFFF" } style.nagbar_dim = { common.color "rgba(0, 0, 0, 0.45)" } diff --git a/data/core/view.lua b/data/core/view.lua index a3664a55..9d305945 100644 --- a/data/core/view.lua +++ b/data/core/view.lua @@ -18,6 +18,13 @@ function View:new() self.scroll = { x = 0, y = 0, to = { x = 0, y = 0 } } self.cursor = "arrow" self.scrollable = false + self.scrollbar = { + x = { thumb = 0, track = 0 }, + y = { thumb = 0, track = 0 }, + w = { thumb = 0, track = 0, to = { thumb = 0, track = 0 } }, + h = { thumb = 0, track = 0 }, + } + self.scrollbar_alpha = { value = 0, to = 0 } end function View:move_towards(t, k, dest, rate) @@ -57,29 +64,62 @@ function View:get_scrollable_size() end +function View:get_scrollbar_track_rect() + local sz = self:get_scrollable_size() + if sz <= self.size.y or sz == math.huge then + return 0, 0, 0, 0 + end + local width = style.scrollbar_size + if self.hovered_scrollbar_track or self.dragging_scrollbar then + width = style.expanded_scrollbar_size + end + return + self.position.x + self.size.x - width, + self.position.y, + width, + self.size.y +end + + function View:get_scrollbar_rect() local sz = self:get_scrollable_size() if sz <= self.size.y or sz == math.huge then return 0, 0, 0, 0 end local h = math.max(20, self.size.y * self.size.y / sz) + local width = style.scrollbar_size + if self.hovered_scrollbar_track or self.dragging_scrollbar then + width = style.expanded_scrollbar_size + end return - self.position.x + self.size.x - style.scrollbar_size, + self.position.x + self.size.x - width, self.position.y + self.scroll.y * (self.size.y - h) / (sz - self.size.y), - style.scrollbar_size, + width, h end function View:scrollbar_overlaps_point(x, y) local sx, sy, sw, sh = self:get_scrollbar_rect() - return x >= sx - sw * 3 and x < sx + sw and y >= sy and y < sy + sh + return x >= sx - style.scrollbar_size * 3 and x < sx + sw and y >= sy and y < sy + sh +end + +function View:scrollbar_track_overlaps_point(x, y) + local sx, sy, sw, sh = self:get_scrollbar_track_rect() + return x >= sx - style.scrollbar_size * 3 and x < sx + sw and y >= sy and y < sy + sh end function View:on_mouse_pressed(button, x, y, clicks) - if self:scrollbar_overlaps_point(x, y) then - self.dragging_scrollbar = true + if self:scrollbar_track_overlaps_point(x, y) then + if self:scrollbar_overlaps_point(x, y) then + self.dragging_scrollbar = true + else + local _, _, _, sh = self:get_scrollbar_rect() + local ly = (y - self.position.y) - sh / 2 + local pct = common.clamp(ly / self.size.y, 0, 100) + self.scroll.to.y = self:get_scrollable_size() * pct + end return true end end @@ -96,6 +136,7 @@ function View:on_mouse_moved(x, y, dx, dy) self.scroll.to.y = self.scroll.to.y + delta end self.hovered_scrollbar = self:scrollbar_overlaps_point(x, y) + self.hovered_scrollbar_track = self.hovered_scrollbar or self:scrollbar_track_overlaps_point(x, y) end @@ -132,10 +173,33 @@ function View:clamp_scroll_position() end +function View:update_scrollbar() + local x, y, w, h = self:get_scrollbar_rect() + self.scrollbar.w.to.thumb = w + self:move_towards(self.scrollbar.w, "thumb", self.scrollbar.w.to.thumb, 0.3) + self.scrollbar.x.thumb = x + w - self.scrollbar.w.thumb + self.scrollbar.y.thumb = y + self.scrollbar.h.thumb = h + + local x, y, w, h = self:get_scrollbar_track_rect() + self.scrollbar.w.to.track = w + self:move_towards(self.scrollbar.w, "track", self.scrollbar.w.to.track, 0.3) + self.scrollbar.x.track = x + w - self.scrollbar.w.track + self.scrollbar.y.track = y + self.scrollbar.h.track = h + + -- we use 100 for a smoother transition + self.scrollbar_alpha.to = (self.hovered_scrollbar_track or self.dragging_scrollbar) and 100 or 0 + self:move_towards(self.scrollbar_alpha, "value", self.scrollbar_alpha.to, 0.3) +end + + function View:update() self:clamp_scroll_position() self:move_towards(self.scroll, "x", self.scroll.to.x, 0.3) self:move_towards(self.scroll, "y", self.scroll.to.y, 0.3) + + self:update_scrollbar() end @@ -146,11 +210,29 @@ function View:draw_background(color) end -function View:draw_scrollbar() - local x, y, w, h = self:get_scrollbar_rect() +function View:draw_scrollbar_track() + if not (self.hovered_scrollbar_track or self.dragging_scrollbar) + and self.scrollbar_alpha.value == 0 then + return + end + local color = { table.unpack(style.scrollbar_track) } + color[4] = color[4] * self.scrollbar_alpha.value / 100 + renderer.draw_rect(self.scrollbar.x.track, self.scrollbar.y.track, + self.scrollbar.w.track, self.scrollbar.h.track, color) +end + + +function View:draw_scrollbar_thumb() local highlight = self.hovered_scrollbar or self.dragging_scrollbar local color = highlight and style.scrollbar2 or style.scrollbar - renderer.draw_rect(x, y, w, h, color) + renderer.draw_rect(self.scrollbar.x.thumb, self.scrollbar.y.thumb, + self.scrollbar.w.thumb, self.scrollbar.h.thumb, color) +end + + +function View:draw_scrollbar() + self:draw_scrollbar_track() + self:draw_scrollbar_thumb() end From 4f434d1a414cbcc6768d53bf40b01454fe9f03b0 Mon Sep 17 00:00:00 2001 From: Guldoman Date: Tue, 12 Apr 2022 02:49:44 +0200 Subject: [PATCH 4/5] Show `arrow` cursor when hovering `DocView` scrollbar track --- data/core/docview.lua | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/data/core/docview.lua b/data/core/docview.lua index 65a3778e..1ed8f429 100644 --- a/data/core/docview.lua +++ b/data/core/docview.lua @@ -227,7 +227,7 @@ end function DocView:on_mouse_moved(x, y, ...) DocView.super.on_mouse_moved(self, x, y, ...) - if self.hovered_scrollbar or self.dragging_scrollbar then + if self.hovered_scrollbar_track or self.dragging_scrollbar then self.cursor = "arrow" else self.cursor = "ibeam" From 43086a9c24f663300c2555162b56642f3457c044 Mon Sep 17 00:00:00 2001 From: Guldoman Date: Tue, 12 Apr 2022 03:20:27 +0200 Subject: [PATCH 5/5] Fix missing pixel in scrollbar --- data/core/view.lua | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/data/core/view.lua b/data/core/view.lua index 9d305945..f1c9a949 100644 --- a/data/core/view.lua +++ b/data/core/view.lua @@ -101,12 +101,12 @@ end function View:scrollbar_overlaps_point(x, y) local sx, sy, sw, sh = self:get_scrollbar_rect() - return x >= sx - style.scrollbar_size * 3 and x < sx + sw and y >= sy and y < sy + sh + return x >= sx - style.scrollbar_size * 3 and x < sx + sw and y > sy and y <= sy + sh end function View:scrollbar_track_overlaps_point(x, y) local sx, sy, sw, sh = self:get_scrollbar_track_rect() - return x >= sx - style.scrollbar_size * 3 and x < sx + sw and y >= sy and y < sy + sh + return x >= sx - style.scrollbar_size * 3 and x < sx + sw and y > sy and y <= sy + sh end