diff options
author | Jaakko Keränen <jaakko.keranen@iki.fi> | 2021-09-19 07:54:46 +0300 |
---|---|---|
committer | Jaakko Keränen <jaakko.keranen@iki.fi> | 2021-09-19 07:54:46 +0300 |
commit | 4002d7198341e8b2540646c8b69ca7e8dd0840ec (patch) | |
tree | ff39fd743621273515d915a22004773184b9fd5b /src/ui/widget.c | |
parent | 68508e54e5707d6ab69cabf8413d58cd89531a38 (diff) |
Widget: Scrollable widgets will draw a scrollbar
A proper scrollbar would be grabbable, but this is just a visual indication that a menu/dialog/panel can be scrolled.
IssueID #337
Diffstat (limited to 'src/ui/widget.c')
-rw-r--r-- | src/ui/widget.c | 36 |
1 files changed, 36 insertions, 0 deletions
diff --git a/src/ui/widget.c b/src/ui/widget.c index 9ec70d07..c1fb9e95 100644 --- a/src/ui/widget.c +++ b/src/ui/widget.c | |||
@@ -1084,6 +1084,27 @@ iBool dispatchEvent_Widget(iWidget *d, const SDL_Event *ev) { | |||
1084 | return iFalse; | 1084 | return iFalse; |
1085 | } | 1085 | } |
1086 | 1086 | ||
1087 | void scrollInfo_Widget(const iWidget *d, iWidgetScrollInfo *info) { | ||
1088 | iRect bounds = boundsWithoutVisualOffset_Widget(d); | ||
1089 | const iRect winRect = adjusted_Rect(safeRect_Root(d->root), | ||
1090 | zero_I2(), | ||
1091 | init_I2(0, -get_Window()->keyboardHeight)); | ||
1092 | info->height = bounds.size.y; | ||
1093 | info->avail = height_Rect(winRect); | ||
1094 | if (info->avail >= info->height) { | ||
1095 | info->normScroll = 0.0f; | ||
1096 | info->thumbY = 0; | ||
1097 | info->thumbHeight = 0; | ||
1098 | } | ||
1099 | else { | ||
1100 | int scroll = top_Rect(winRect) - top_Rect(bounds); | ||
1101 | info->normScroll = scroll / (float) (info->height - info->avail); | ||
1102 | info->normScroll = iClamp(info->normScroll, 0.0f, 1.0f); | ||
1103 | info->thumbHeight = iMin(info->avail / 2, info->avail * info->avail / info->height); | ||
1104 | info->thumbY = top_Rect(winRect) + (info->avail - info->thumbHeight) * info->normScroll; | ||
1105 | } | ||
1106 | } | ||
1107 | |||
1087 | iBool scrollOverflow_Widget(iWidget *d, int delta) { | 1108 | iBool scrollOverflow_Widget(iWidget *d, int delta) { |
1088 | iRect bounds = boundsWithoutVisualOffset_Widget(d); | 1109 | iRect bounds = boundsWithoutVisualOffset_Widget(d); |
1089 | const iRect winRect = adjusted_Rect(safeRect_Root(d->root), | 1110 | const iRect winRect = adjusted_Rect(safeRect_Root(d->root), |
@@ -1539,6 +1560,21 @@ void draw_Widget(const iWidget *d) { | |||
1539 | &(SDL_Rect){ bounds.pos.x, bounds.pos.y, | 1560 | &(SDL_Rect){ bounds.pos.x, bounds.pos.y, |
1540 | d->drawBuf->size.x, d->drawBuf->size.y }); | 1561 | d->drawBuf->size.x, d->drawBuf->size.y }); |
1541 | } | 1562 | } |
1563 | if (d->flags & overflowScrollable_WidgetFlag) { | ||
1564 | iWidgetScrollInfo info; | ||
1565 | scrollInfo_Widget(d, &info); | ||
1566 | if (info.thumbHeight > 0) { | ||
1567 | iPaint p; | ||
1568 | init_Paint(&p); | ||
1569 | const int scrollWidth = gap_UI / 2; | ||
1570 | iRect bounds = bounds_Widget(d); | ||
1571 | bounds.pos.x = right_Rect(bounds) - scrollWidth * 3; | ||
1572 | bounds.size.x = scrollWidth; | ||
1573 | bounds.pos.y = info.thumbY; | ||
1574 | bounds.size.y = info.thumbHeight; | ||
1575 | fillRect_Paint(&p, bounds, tmQuote_ColorId); | ||
1576 | } | ||
1577 | } | ||
1542 | } | 1578 | } |
1543 | 1579 | ||
1544 | iAny *addChild_Widget(iWidget *d, iAnyObject *child) { | 1580 | iAny *addChild_Widget(iWidget *d, iAnyObject *child) { |