From 7a86dc92cb243f17a5f2fbd39631c5c958cbe9b2 Mon Sep 17 00:00:00 2001 From: Pietro Gagliardi Date: Wed, 20 May 2015 12:24:06 -0400 Subject: [PATCH] More spinbox and slider work. --- redo/test/page4.c | 2 ++ redo/ui.idl | 7 +++++-- redo/windows/slider.c | 9 +++++++++ redo/windows/spinbox.c | 33 +++++++++++++++++++++++++++++---- 4 files changed, 45 insertions(+), 6 deletions(-) diff --git a/redo/test/page4.c b/redo/test/page4.c index 81d8a0d0..d445f5af 100644 --- a/redo/test/page4.c +++ b/redo/test/page4.c @@ -11,6 +11,8 @@ static uiProgressBar *pbar; uintmax_t value; \ printf("on %s changed\n", #what); \ value = ui ## what ## Value(this); \ + uiSpinboxSetValue(spinbox, value); \ + uiSliderSetValue(slider, value); \ uiProgressBarSetValue(pbar, value); \ } CHANGED(Spinbox) diff --git a/redo/ui.idl b/redo/ui.idl index 1412f1cb..38b2bba2 100644 --- a/redo/ui.idl +++ b/redo/ui.idl @@ -141,9 +141,12 @@ interface Group from Control { }; func NewGroup(text *const char) *Group; +// spinbox/slider rules: +// setting value outside of range will automatically clamp + interface Spinbox from Control { func Value(void) intmax_t; - // TODO SetValue() + func SetValue(value intmax_t); func OnChanged(f *func(s *Spinbox, data *void), data *void); }; func NewSpinbox(void) *Spinbox; @@ -156,7 +159,7 @@ func NewProgressBar(void) *ProgressBar; interface Slider from Control { func Value(void) intmax_t; - // TODO SetValue() + func SetValue(value intmax_t); func OnChanged(f *func(s *Slider, data *void), data *void); }; func NewSlider(void) *Slider; diff --git a/redo/windows/slider.c b/redo/windows/slider.c index 8267d2b3..59705f7f 100644 --- a/redo/windows/slider.c +++ b/redo/windows/slider.c @@ -62,6 +62,14 @@ static intmax_t sliderValue(uiSlider *ss) return (intmax_t) SendMessageW(s->hwnd, TBM_GETPOS, 0, 0); } +static void sliderSetValue(uiSlider *ss, intmax_t value) +{ + struct slider *s = (struct slider *) ss; + + // don't use TBM_SETPOSNOTIFY; that triggers an event + SendMessageW(s->hwnd, TBM_SETPOS, (WPARAM) TRUE, (LPARAM) value); +} + static void sliderOnChanged(uiSlider *ss, void (*f)(uiSlider *, void *), void *data) { struct slider *s = (struct slider *) ss; @@ -103,6 +111,7 @@ uiSlider *uiNewSlider(void) uiControl(s)->PreferredSize = sliderPreferredSize; uiSlider(s)->Value = sliderValue; + uiSlider(s)->SetValue = sliderSetValue; uiSlider(s)->OnChanged = sliderOnChanged; return uiSlider(s); diff --git a/redo/windows/spinbox.c b/redo/windows/spinbox.c index 462a1ac2..63278141 100644 --- a/redo/windows/spinbox.c +++ b/redo/windows/spinbox.c @@ -81,11 +81,20 @@ static void spinboxPreferredSize(uiControl *c, uiSizing *d, intmax_t *width, int static void recreateUpDown(struct spinbox *s) { HWND parent; + BOOL preserve = FALSE; + intmax_t current; + // wine uses this type + INT min, max; parent = GetAncestor(s->hwnd, GA_PARENT); - if (s->updown != NULL) + if (s->updown != NULL) { + preserve = TRUE; + current = value(s); + SendMessageW(s->updown, UDM_GETRANGE32, (WPARAM) (&min), (LPARAM) (&max)); if (DestroyWindow(s->updown) == 0) logLastError("error destroying old updown in recreateUpDown()"); + } + s->inhibitChanged = TRUE; s->updown = CreateWindowExW(0, UPDOWN_CLASSW, L"", // no WS_VISIBLE; we set visibility ourselves @@ -98,11 +107,17 @@ static void recreateUpDown(struct spinbox *s) if (s->updown == NULL) logLastError("error creating updown in recreateUpDown()"); SendMessageW(s->updown, UDM_SETBUDDY, (WPARAM) (s->hwnd), 0); - // TODO - SendMessageW(s->updown, UDM_SETRANGE32, 0, 100); - SendMessageW(s->updown, UDM_SETPOS32, 0, 0); + if (preserve) { + SendMessageW(s->updown, UDM_SETRANGE32, (WPARAM) min, (LPARAM) max); + SendMessageW(s->updown, UDM_SETPOS32, 0, (LPARAM) current); + } else { + // TODO + SendMessageW(s->updown, UDM_SETRANGE32, 0, 100); + SendMessageW(s->updown, UDM_SETPOS32, 0, 0); + } if (uiControlContainerVisible(uiControl(s))) ShowWindow(s->updown, SW_SHOW); + s->inhibitChanged = FALSE; } static void spinboxResize(uiControl *c, intmax_t x, intmax_t y, intmax_t width, intmax_t height, uiSizing *d) @@ -126,6 +141,15 @@ static intmax_t spinboxValue(uiSpinbox *ss) return value(s); } +static void spinboxSetValue(uiSpinbox *ss, intmax_t value) +{ + struct spinbox *s = (struct spinbox *) ss; + + s->inhibitChanged = TRUE; + SendMessageW(s->updown, UDM_SETPOS32, 0, (LPARAM) value); + s->inhibitChanged = FALSE; +} + static void spinboxOnChanged(uiSpinbox *ss, void (*f)(uiSpinbox *, void *), void *data) { struct spinbox *s = (struct spinbox *) ss; @@ -167,6 +191,7 @@ uiSpinbox *uiNewSpinbox(void) uiControl(s)->Resize = spinboxResize; uiSpinbox(s)->Value = spinboxValue; + uiSpinbox(s)->SetValue = spinboxSetValue; uiSpinbox(s)->OnChanged = spinboxOnChanged; return uiSpinbox(s);