aboutsummaryrefslogtreecommitdiffstats
path: root/pugl/pugl_win.c
diff options
context:
space:
mode:
authorDavid Robillard <d@drobilla.net>2019-07-26 00:57:49 +0200
committerDavid Robillard <d@drobilla.net>2019-07-26 01:05:37 +0200
commiteada1042452e8708ca6c65f7c23ac3c59e4c53f0 (patch)
tree2155469130ef05d42f49a02c0af3abedf66fe9f1 /pugl/pugl_win.c
parent55199fe97d7866a0c8998455e43bb5b1f2989eb7 (diff)
downloadpugl-eada1042452e8708ca6c65f7c23ac3c59e4c53f0.tar.gz
pugl-eada1042452e8708ca6c65f7c23ac3c59e4c53f0.tar.bz2
pugl-eada1042452e8708ca6c65f7c23ac3c59e4c53f0.zip
Windows: Implement size constraints
There are two possible approaches to take here: try to expand dimensions that are not being explicitly resized (for example expand the bottom when dragging right), or just stop single-dimension resizes if they would go out of range. I chose the latter here for two reasons: it's hard to always do something smooth and unsurprising with the first approach (and it would require more code), and it can be nice from the user's perspective to easily be able to resize the window to exactly one of its aspect ratio limits. For example, it is very easy to drag pugl_test to 1:1 or 16:9. In other words, simplicity and user power wins.
Diffstat (limited to 'pugl/pugl_win.c')
-rw-r--r--pugl/pugl_win.c45
1 files changed, 45 insertions, 0 deletions
diff --git a/pugl/pugl_win.c b/pugl/pugl_win.c
index 1c93ea6..b691295 100644
--- a/pugl/pugl_win.c
+++ b/pugl/pugl_win.c
@@ -634,6 +634,45 @@ stopFlashing(PuglView* view)
}
}
+static void
+constrainAspect(const PuglView* const view,
+ RECT* const size,
+ const WPARAM wParam)
+{
+ const float minAspect = view->min_aspect_x / (float)view->min_aspect_y;
+ const float maxAspect = view->max_aspect_x / (float)view->max_aspect_y;
+ const int w = size->right - size->left;
+ const int h = size->bottom - size->top;
+ const float a = w / (float)h;
+
+ switch (wParam) {
+ case WMSZ_TOP:
+ size->top = (a < minAspect ? (LONG)(size->bottom - w * minAspect) :
+ a > maxAspect ? (LONG)(size->bottom - w * maxAspect) :
+ size->top);
+ break;
+ case WMSZ_TOPRIGHT:
+ case WMSZ_RIGHT:
+ case WMSZ_BOTTOMRIGHT:
+ size->right = (a < minAspect ? (LONG)(size->left + h * minAspect) :
+ a > maxAspect ? (LONG)(size->left + h * maxAspect) :
+ size->right);
+ break;
+ case WMSZ_BOTTOM:
+ size->bottom = (a < minAspect ? (LONG)(size->top + w * minAspect) :
+ a > maxAspect ? (LONG)(size->top + w * maxAspect) :
+ size->bottom);
+ break;
+ case WMSZ_BOTTOMLEFT:
+ case WMSZ_LEFT:
+ case WMSZ_TOPLEFT:
+ size->left = (a < minAspect ? (LONG)(size->right - h * minAspect) :
+ a > maxAspect ? (LONG)(size->right - h * maxAspect) :
+ size->left);
+ break;
+ }
+}
+
static LRESULT
handleMessage(PuglView* view, UINT message, WPARAM wParam, LPARAM lParam)
{
@@ -661,6 +700,12 @@ handleMessage(PuglView* view, UINT message, WPARAM wParam, LPARAM lParam)
RDW_INVALIDATE|RDW_ALLCHILDREN|RDW_INTERNALPAINT|
RDW_UPDATENOW);
break;
+ case WM_SIZING:
+ if (view->min_aspect_x) {
+ constrainAspect(view, (RECT*)lParam, wParam);
+ return TRUE;
+ }
+ break;
case WM_ENTERSIZEMOVE:
view->impl->resizing = true;
SetTimer(view->impl->hwnd,