diff options
Diffstat (limited to 'src/ui/sidebarwidget.c')
-rw-r--r-- | src/ui/sidebarwidget.c | 54 |
1 files changed, 41 insertions, 13 deletions
diff --git a/src/ui/sidebarwidget.c b/src/ui/sidebarwidget.c index 872d3f4a..fa550176 100644 --- a/src/ui/sidebarwidget.c +++ b/src/ui/sidebarwidget.c | |||
@@ -61,6 +61,31 @@ static void clearItems_SidebarWidget_(iSidebarWidget *d) { | |||
61 | clear_Array(&d->items); | 61 | clear_Array(&d->items); |
62 | } | 62 | } |
63 | 63 | ||
64 | static iRect contentBounds_SidebarWidget_(const iSidebarWidget *d) { | ||
65 | iRect bounds = bounds_Widget(constAs_Widget(d)); | ||
66 | adjustEdges_Rect(&bounds, as_Widget(d->modeButtons[0])->rect.size.y + gap_UI, | ||
67 | -constAs_Widget(d->scroll)->rect.size.x, -gap_UI, 0); | ||
68 | return bounds; | ||
69 | } | ||
70 | |||
71 | static int scrollMax_SidebarWidget_(const iSidebarWidget *d) { | ||
72 | return iMax(0, | ||
73 | (int) size_Array(&d->items) * d->itemHeight - | ||
74 | height_Rect(contentBounds_SidebarWidget_(d))); | ||
75 | } | ||
76 | |||
77 | static void updateVisible_SidebarWidget_(iSidebarWidget *d) { | ||
78 | // iWidget *w = as_Widget(d); | ||
79 | const int contentSize = size_Array(&d->items) * d->itemHeight; | ||
80 | const iRect bounds = contentBounds_SidebarWidget_(d); | ||
81 | setRange_ScrollWidget(d->scroll, (iRangei){ 0, scrollMax_SidebarWidget_(d) }); | ||
82 | setThumb_ScrollWidget(d->scroll, | ||
83 | d->scrollY, | ||
84 | contentSize > 0 ? height_Rect(bounds_Widget(as_Widget(d->scroll))) * | ||
85 | height_Rect(bounds) / contentSize | ||
86 | : 0); | ||
87 | } | ||
88 | |||
64 | static void updateItems_SidebarWidget_(iSidebarWidget *d) { | 89 | static void updateItems_SidebarWidget_(iSidebarWidget *d) { |
65 | clearItems_SidebarWidget_(d); | 90 | clearItems_SidebarWidget_(d); |
66 | switch (d->mode) { | 91 | switch (d->mode) { |
@@ -84,6 +109,7 @@ static void updateItems_SidebarWidget_(iSidebarWidget *d) { | |||
84 | default: | 109 | default: |
85 | break; | 110 | break; |
86 | } | 111 | } |
112 | updateVisible_SidebarWidget_(d); | ||
87 | refresh_Widget(as_Widget(d)); | 113 | refresh_Widget(as_Widget(d)); |
88 | } | 114 | } |
89 | 115 | ||
@@ -131,12 +157,6 @@ void deinit_SidebarWidget(iSidebarWidget *d) { | |||
131 | deinit_Array(&d->items); | 157 | deinit_Array(&d->items); |
132 | } | 158 | } |
133 | 159 | ||
134 | static iRect contentBounds_SidebarWidget_(const iSidebarWidget *d) { | ||
135 | iRect bounds = bounds_Widget(constAs_Widget(d)); | ||
136 | adjustEdges_Rect(&bounds, as_Widget(d->modeButtons[0])->rect.size.y + gap_UI, 0, 0, 0); | ||
137 | return bounds; | ||
138 | } | ||
139 | |||
140 | static int visCount_SidebarWidget_(const iSidebarWidget *d) { | 160 | static int visCount_SidebarWidget_(const iSidebarWidget *d) { |
141 | return iMin(height_Rect(bounds_Widget(constAs_Widget(d))) / d->itemHeight, | 161 | return iMin(height_Rect(bounds_Widget(constAs_Widget(d))) / d->itemHeight, |
142 | (int) size_Array(&d->items)); | 162 | (int) size_Array(&d->items)); |
@@ -174,17 +194,25 @@ static void scroll_SidebarWidget_(iSidebarWidget *d, int offset) { | |||
174 | if (d->scrollY < 0) { | 194 | if (d->scrollY < 0) { |
175 | d->scrollY = 0; | 195 | d->scrollY = 0; |
176 | } | 196 | } |
177 | const int scrollMax = iMax(0, | 197 | const int scrollMax = scrollMax_SidebarWidget_(d); |
178 | (int) size_Array(&d->items) * d->itemHeight - | ||
179 | height_Rect(contentBounds_SidebarWidget_(d))); | ||
180 | d->scrollY = iMin(d->scrollY, scrollMax); | 198 | d->scrollY = iMin(d->scrollY, scrollMax); |
199 | updateVisible_SidebarWidget_(d); | ||
181 | refresh_Widget(as_Widget(d)); | 200 | refresh_Widget(as_Widget(d)); |
182 | } | 201 | } |
183 | 202 | ||
184 | static iBool processEvent_SidebarWidget_(iSidebarWidget *d, const SDL_Event *ev) { | 203 | static iBool processEvent_SidebarWidget_(iSidebarWidget *d, const SDL_Event *ev) { |
185 | iWidget *w = as_Widget(d); | 204 | iWidget *w = as_Widget(d); |
186 | /* Handle commands. */ | 205 | /* Handle commands. */ |
187 | if (ev->type == SDL_USEREVENT && ev->user.code == command_UserEventCode) { | 206 | if (isResize_UserEvent(ev)) { |
207 | updateVisible_SidebarWidget_(d); | ||
208 | } | ||
209 | else if (isCommand_Widget(w, ev, "scroll.moved")) { | ||
210 | d->scrollY = arg_Command(command_UserEvent(ev)); | ||
211 | d->hoverItem = iInvalidPos; | ||
212 | refresh_Widget(w); | ||
213 | return iTrue; | ||
214 | } | ||
215 | else if (ev->type == SDL_USEREVENT && ev->user.code == command_UserEventCode) { | ||
188 | const char *cmd = command_UserEvent(ev); | 216 | const char *cmd = command_UserEvent(ev); |
189 | if (isCommand_Widget(w, ev, "sidebar.mode")) { | 217 | if (isCommand_Widget(w, ev, "sidebar.mode")) { |
190 | setMode_SidebarWidget(d, arg_Command(cmd)); | 218 | setMode_SidebarWidget(d, arg_Command(cmd)); |
@@ -240,7 +268,6 @@ static void draw_SidebarWidget_(const iSidebarWidget *d) { | |||
240 | init_Paint(&p); | 268 | init_Paint(&p); |
241 | /* Draw the items. */ { | 269 | /* Draw the items. */ { |
242 | const int font = default_FontId; | 270 | const int font = default_FontId; |
243 | // /iConstForEach(Array, i, &d->items) { | ||
244 | const iRanges visRange = visRange_SidebarWidget_(d); | 271 | const iRanges visRange = visRange_SidebarWidget_(d); |
245 | iInt2 pos = addY_I2(topLeft_Rect(bounds), -(d->scrollY % d->itemHeight)); | 272 | iInt2 pos = addY_I2(topLeft_Rect(bounds), -(d->scrollY % d->itemHeight)); |
246 | for (size_t i = visRange.start; i < visRange.end; i++) { | 273 | for (size_t i = visRange.start; i < visRange.end; i++) { |
@@ -250,9 +277,10 @@ static void draw_SidebarWidget_(const iSidebarWidget *d) { | |||
250 | if (isHover) { | 277 | if (isHover) { |
251 | fillRect_Paint(&p, itemRect, isPressing ? orange_ColorId : teal_ColorId); | 278 | fillRect_Paint(&p, itemRect, isPressing ? orange_ColorId : teal_ColorId); |
252 | } | 279 | } |
253 | setClip_Paint(&p, itemRect); | 280 | setClip_Paint(&p, intersect_Rect(itemRect, bounds)); |
254 | const int fg = isHover ? (isPressing ? black_ColorId : white_ColorId) : gray75_ColorId; | ||
255 | if (d->mode == documentOutline_SidebarMode) { | 281 | if (d->mode == documentOutline_SidebarMode) { |
282 | const int fg = isHover ? (isPressing ? black_ColorId : white_ColorId) : | ||
283 | (item->indent == 0 ? white_ColorId : gray75_ColorId); | ||
256 | drawRange_Text(font, init_I2(pos.x + 3 * gap_UI + item->indent, | 284 | drawRange_Text(font, init_I2(pos.x + 3 * gap_UI + item->indent, |
257 | mid_Rect(itemRect).y - lineHeight_Text(font) / 2), | 285 | mid_Rect(itemRect).y - lineHeight_Text(font) / 2), |
258 | fg, range_String(&item->label)); | 286 | fg, range_String(&item->label)); |