]> git.saurik.com Git - wxWidgets.git/blob - src/os2/slider.cpp
Prevent crash when m_defGridAttr is NULL
[wxWidgets.git] / src / os2 / slider.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: slider.cpp
3 // Purpose: wxSlider
4 // Author: David Webster
5 // Modified by:
6 // Created: 10/15/99
7 // RCS-ID: $Id$
8 // Copyright: (c) David Webster
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
11
12 // For compilers that support precompilation, includes "wx.h".
13 #include "wx/wxprec.h"
14
15 #ifdef __BORLANDC__
16 #pragma hdrstop
17 #endif
18
19 #ifndef WX_PRECOMP
20 #include <stdio.h>
21 #include <wx/utils.h>
22 #include <wx/brush.h>
23 #endif
24
25 #include "wx/slider.h"
26 #include "wx/os2/private.h"
27
28 IMPLEMENT_DYNAMIC_CLASS(wxSlider, wxControl)
29
30 wxSlider::wxSlider()
31 {
32 m_hStaticValue = 0L;
33 m_hStaticMin = 0L;
34 m_hStaticMax = 0L;
35 m_nPageSize = 1;
36 m_nLineSize = 1;
37 m_nRangeMax = 0;
38 m_nRangeMin = 0;
39 m_nTickFreq = 0;
40 } // end of wxSlider::wxSlider
41
42 wxSlider::~wxSlider()
43 {
44 if (m_hStaticMin)
45 ::WinDestroyWindow((HWND)m_hStaticMin);
46 if (m_hStaticMax)
47 ::WinDestroyWindow((HWND)m_hStaticMax);
48 if (m_hStaticValue)
49 ::WinDestroyWindow((HWND)m_hStaticValue);
50 } // end of wxSlider::~wxSlider
51
52 void wxSlider::AdjustSubControls(
53 int nX
54 , int nY
55 , int nWidth
56 , int nHeight
57 , int nSizeFlags
58 )
59 {
60 SWP vSwp;
61 int nXOffset = nX;
62 int nYOffset = nY;
63 int nCx; // slider,min,max sizes
64 int nCy;
65 int nCyf;
66 char zBuf[300];
67
68 wxGetCharSize( GetHWND()
69 ,&nCx
70 ,&nCy
71 ,&this->GetFont()
72 );
73
74 if ((m_windowStyle & wxSL_VERTICAL) != wxSL_VERTICAL)
75 {
76 if (m_windowStyle & wxSL_LABELS )
77 {
78 int nMinLen = 0;
79 int nMaxLen = 0;
80
81 ::WinQueryWindowText((HWND)m_hStaticMin, 300, zBuf);
82 GetTextExtent(zBuf, &nMinLen, &nCyf, NULL, NULL, &this->GetFont());
83
84 ::WinQueryWindowText((HWND)m_hStaticMax, 300, zBuf);
85 GetTextExtent(zBuf, &nMaxLen, &nCyf, NULL, NULL, &this->GetFont());
86
87 if (m_hStaticValue)
88 {
89 int nNewWidth = wxMax(nMinLen, nMaxLen);
90 int nValueHeight = nCyf;
91
92 ::WinSetWindowPos( (HWND)m_hStaticValue
93 ,HWND_TOP
94 ,(LONG)nXOffset - (nNewWidth + nCx + nMinLen + nCx)
95 ,(LONG)nYOffset
96 ,(LONG)nNewWidth
97 ,(LONG)nValueHeight
98 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
99 );
100 }
101 ::WinSetWindowPos( (HWND)m_hStaticMin
102 ,HWND_TOP
103 ,(LONG)nXOffset - (nMinLen + nCx)
104 ,(LONG)nYOffset
105 ,(LONG)nMinLen
106 ,(LONG)nCy
107 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
108 );
109 nXOffset += nWidth + nCx;
110
111 ::WinSetWindowPos( (HWND)m_hStaticMax
112 ,HWND_TOP
113 ,(LONG)nXOffset
114 ,(LONG)nYOffset
115 ,(LONG)nMaxLen
116 ,(LONG)nCy
117 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
118 );
119 }
120 }
121 //
122 // Now deal with a vertical slider -- OS/2 doesn't have vertical sliders
123 //
124 } // end of wxSlider::AdjustSubControls
125
126 void wxSlider::ClearSel()
127 {
128 } // end of wxSlider::ClearSel
129
130 void wxSlider::ClearTicks()
131 {
132 } // end of wxSlider::ClearTicks
133
134 void wxSlider::Command (
135 wxCommandEvent& rEvent
136 )
137 {
138 SetValue(rEvent.GetInt());
139 ProcessCommand(rEvent);
140 } // end of wxSlider::Command
141
142 bool wxSlider::ContainsHWND(
143 WXHWND hWnd
144 ) const
145 {
146 return ( hWnd == GetStaticMin() ||
147 hWnd == GetStaticMax() ||
148 hWnd == GetEditValue()
149 );
150 } // end of wxSlider::ContainsHWND
151
152 bool wxSlider::Create(
153 wxWindow* pParent
154 , wxWindowID vId
155 , int nValue
156 , int nMinValue
157 , int nMaxValue
158 , const wxPoint& rPos
159 , const wxSize& rSize
160 , long lStyle
161 #if wxUSE_VALIDATORS
162 , const wxValidator& rValidator
163 #endif
164 , const wxString& rsName
165 )
166 {
167 int nX = rPos.x;
168 int nY = rPos.y;
169 int nWidth = rSize.x;
170 int nHeight = rSize.y;
171 long lMsStyle = 0L;
172 long lWstyle = 0L;
173
174 SetName(rsName);
175 #if wxUSE_VALIDATORS
176 SetValidator(rValidator);
177 #endif
178 if (pParent)
179 pParent->AddChild(this);
180 SetBackgroundColour(pParent->GetBackgroundColour()) ;
181 SetForegroundColour(pParent->GetForegroundColour()) ;
182
183 m_hStaticValue = 0L;
184 m_hStaticMin = 0L;
185 m_hStaticMax = 0L;
186 m_nPageSize = 1;
187 m_nLineSize = 1;
188 m_windowStyle = lStyle;
189 m_nTickFreq = 0;
190
191 if (vId == -1)
192 m_windowId = (int)NewControlId();
193 else
194 m_windowId = vId;
195
196 if (m_windowStyle & wxCLIP_SIBLINGS )
197 lMsStyle |= WS_CLIPSIBLINGS;
198
199 if (m_windowStyle & wxSL_LABELS)
200 {
201 lMsStyle |= WS_VISIBLE | SS_TEXT | DT_VCENTER;
202
203 //
204 // If the parent is a scrolled window the controls must
205 // have this style or they will overlap the scrollbars
206 //
207 if (pParent)
208 if (pParent->IsKindOf(CLASSINFO(wxScrolledWindow)) ||
209 pParent->IsKindOf(CLASSINFO(wxGenericScrolledWindow)))
210 lMsStyle |= WS_CLIPSIBLINGS;
211
212 m_hStaticValue = (WXHWND)::WinCreateWindow( (HWND)GetHwndOf(pParent) // Parent window handle
213 ,WC_STATIC // Window class
214 ,(PSZ)NULL // Initial Text
215 ,(ULONG)lMsStyle // Style flags
216 ,0L, 0L, 0L, 0L // Origin -- 0 size
217 ,(HWND)GetHwndOf(pParent) // owner window handle (same as parent
218 ,HWND_TOP // initial z position
219 ,(ULONG)NewControlId() // Window identifier
220 ,NULL // no control data
221 ,NULL // no Presentation parameters
222 );
223
224 //
225 // Now create min static control
226 //
227 sprintf(wxBuffer, "%d", nMinValue);
228 lWstyle = SS_TEXT|DT_LEFT|WS_VISIBLE;
229 if (m_windowStyle & wxCLIP_SIBLINGS)
230 lWstyle |= WS_CLIPSIBLINGS;
231 //
232 // If the parent is a scrolled window the controls must
233 // have this style or they will overlap the scrollbars
234 //
235 if (pParent)
236 if (pParent->IsKindOf(CLASSINFO(wxScrolledWindow)) ||
237 pParent->IsKindOf(CLASSINFO(wxGenericScrolledWindow)))
238 lWstyle |= WS_CLIPSIBLINGS;
239
240 m_hStaticMin = (WXHWND)::WinCreateWindow( (HWND)GetHwndOf(pParent) // Parent window handle
241 ,WC_STATIC // Window class
242 ,(PSZ)wxBuffer // Initial Text
243 ,(ULONG)lWstyle // Style flags
244 ,0L, 0L, 0L, 0L // Origin -- 0 size
245 ,(HWND)GetHwndOf(pParent) // owner window handle (same as parent
246 ,HWND_TOP // initial z position
247 ,(ULONG)NewControlId() // Window identifier
248 ,NULL // no control data
249 ,NULL // no Presentation parameters
250 );
251 }
252 lMsStyle = 0;
253
254 SLDCDATA vSlData;
255
256 vSlData.cbSize = sizeof(SLDCDATA);
257 if (m_windowStyle & wxSL_VERTICAL)
258 lMsStyle = SLS_VERTICAL | WS_VISIBLE | WS_TABSTOP;
259 else
260 lMsStyle = SLS_HORIZONTAL | WS_VISIBLE | WS_TABSTOP;
261
262 if (m_windowStyle & wxCLIP_SIBLINGS)
263 lMsStyle |= WS_CLIPSIBLINGS;
264
265 if (m_windowStyle & wxSL_AUTOTICKS)
266 {
267 vSlData.usScale1Spacing = 0;
268 vSlData.usScale2Spacing = 0;
269 }
270
271 if (m_windowStyle & wxSL_LEFT)
272 lMsStyle |= SLS_PRIMARYSCALE2; // if SLS_VERTICAL then SCALE2 is to the left
273 else if (m_windowStyle & wxSL_RIGHT)
274 lMsStyle |= SLS_PRIMARYSCALE1; // if SLS_VERTICAL then SCALE2 is to the right
275 else if (m_windowStyle & wxSL_TOP)
276 lMsStyle |= SLS_PRIMARYSCALE1; // if SLS_HORIZONTAL then SCALE1 is to the top
277 else if (m_windowStyle & wxSL_BOTTOM )
278 lMsStyle |= SLS_PRIMARYSCALE2; // if SLS_HORIZONTAL then SCALE1 is to the bottom
279 else if ( m_windowStyle & wxSL_BOTH )
280 lMsStyle |= SLS_PRIMARYSCALE1 | SLS_PRIMARYSCALE2;
281 else
282 lMsStyle |= SLS_PRIMARYSCALE2;
283
284 //
285 // If the parent is a scrolled window the controls must
286 // have this style or they will overlap the scrollbars
287 //
288 if (pParent)
289 if (pParent->IsKindOf(CLASSINFO(wxScrolledWindow)) ||
290 pParent->IsKindOf(CLASSINFO(wxGenericScrolledWindow)))
291 lMsStyle |= WS_CLIPSIBLINGS;
292
293 m_nPageSize = ((nMaxValue - nMinValue)/10);
294 vSlData.usScale1Increments = m_nPageSize;
295 vSlData.usScale2Increments = m_nPageSize;
296
297 HWND hScrollBar = ::WinCreateWindow( (HWND)GetHwndOf(pParent) // Parent window handle
298 ,WC_SLIDER // Window class
299 ,(PSZ)wxBuffer // Initial Text
300 ,(ULONG)lMsStyle // Style flags
301 ,0L, 0L, 0L, 0L // Origin -- 0 size
302 ,(HWND)GetHwndOf(pParent) // owner window handle (same as parent
303 ,HWND_TOP // initial z position
304 ,(HMENU)m_windowId // Window identifier
305 ,&vSlData // Slider control data
306 ,NULL // no Presentation parameters
307 );
308 m_nRangeMax = nMaxValue;
309 m_nRangeMin = nMinValue;
310
311 //
312 // Set the size of the ticks ... default to 6 pixels
313 //
314 ::WinSendMsg( hScrollBar
315 ,SLM_SETTICKSIZE
316 ,MPFROM2SHORT(SMA_SETALLTICKS, 6)
317 ,NULL
318 );
319 //
320 // Set the position to the initial value
321 //
322 ::WinSendMsg( hScrollBar
323 ,SLM_SETSLIDERINFO
324 ,MPFROM2SHORT(SMA_SLIDERARMPOSITION, SMA_RANGEVALUE)
325 ,(MPARAM)nValue
326 );
327
328 m_hWnd = (WXHWND)hScrollBar;
329 SubclassWin(GetHWND());
330 ::WinSetWindowText((HWND)m_hWnd, "");
331 SetFont(pParent->GetFont());
332 if (m_windowStyle & wxSL_LABELS)
333 {
334 //
335 // Finally, create max value static item
336 //
337 sprintf(wxBuffer, "%d", nMaxValue);
338 lWstyle = SS_TEXT|DT_LEFT|WS_VISIBLE;
339 if (m_windowStyle & wxCLIP_SIBLINGS)
340 lMsStyle |= WS_CLIPSIBLINGS;
341 //
342 // If the parent is a scrolled window the controls must
343 // have this style or they will overlap the scrollbars
344 //
345 if (pParent)
346 if (pParent->IsKindOf(CLASSINFO(wxScrolledWindow)) ||
347 pParent->IsKindOf(CLASSINFO(wxGenericScrolledWindow)))
348 lWstyle |= WS_CLIPSIBLINGS;
349
350 m_hStaticMax = (WXHWND)::WinCreateWindow( (HWND)GetHwndOf(pParent) // Parent window handle
351 ,WC_STATIC // Window class
352 ,(PSZ)wxBuffer // Initial Text
353 ,(ULONG)lWstyle // Style flags
354 ,0L, 0L, 0L, 0L // Origin -- 0 size
355 ,(HWND)GetHwndOf(pParent) // owner window handle (same as parent
356 ,HWND_TOP // initial z position
357 ,(ULONG)NewControlId() // Window identifier
358 ,NULL // no control data
359 ,NULL // no Presentation parameters
360 );
361 if (GetFont().Ok())
362 {
363 if (GetFont().GetResourceHandle())
364 {
365 if (m_hStaticMin)
366 wxOS2SetFont( m_hStaticMin
367 ,GetFont()
368 );
369 if (m_hStaticMax)
370 wxOS2SetFont( m_hStaticMax
371 ,GetFont()
372 );
373 if (m_hStaticValue)
374 wxOS2SetFont( m_hStaticValue
375 ,GetFont()
376 );
377 }
378 }
379 }
380
381 SetSize( nX
382 ,nY
383 ,nWidth
384 ,nHeight
385 );
386 m_nThumbLength = SHORT1FROMMR(::WinSendMsg( GetHwnd()
387 ,SLM_QUERYSLIDERINFO
388 ,MPFROM2SHORT( SMA_SLIDERARMDIMENSIONS
389 ,SMA_RANGEVALUE
390 )
391 ,(MPARAM)0
392 )
393 ) + 4; // for bordersizes
394
395 wxColour vColour;
396
397 vColour.Set(wxString("BLACK"));
398
399 LONG lColor = (LONG)vColour.GetPixel();
400
401 ::WinSetPresParam( m_hStaticMin
402 ,PP_FOREGROUNDCOLOR
403 ,sizeof(LONG)
404 ,(PVOID)&lColor
405 );
406 ::WinSetPresParam( m_hStaticMax
407 ,PP_FOREGROUNDCOLOR
408 ,sizeof(LONG)
409 ,(PVOID)&lColor
410 );
411 ::WinSetPresParam( m_hStaticValue
412 ,PP_FOREGROUNDCOLOR
413 ,sizeof(LONG)
414 ,(PVOID)&lColor
415 );
416 ::WinSetPresParam( m_hWnd
417 ,PP_FOREGROUNDCOLOR
418 ,sizeof(LONG)
419 ,(PVOID)&lColor
420 );
421 lColor = (LONG)m_backgroundColour.GetPixel();
422 ::WinSetPresParam( m_hStaticMin
423 ,PP_BACKGROUNDCOLOR
424 ,sizeof(LONG)
425 ,(PVOID)&lColor
426 );
427 ::WinSetPresParam( m_hStaticMax
428 ,PP_BACKGROUNDCOLOR
429 ,sizeof(LONG)
430 ,(PVOID)&lColor
431 );
432 ::WinSetPresParam( m_hStaticValue
433 ,PP_BACKGROUNDCOLOR
434 ,sizeof(LONG)
435 ,(PVOID)&lColor
436 );
437 ::WinSetPresParam( m_hWnd
438 ,PP_BACKGROUNDCOLOR
439 ,sizeof(LONG)
440 ,(PVOID)&lColor
441 );
442 SetValue(nValue);
443 return TRUE;
444 } // end of wxSlider::Create
445
446 void wxSlider::DoSetSize(
447 int nX
448 , int nY
449 , int nWidth
450 , int nHeight
451 , int nSizeFlags
452 )
453 {
454 int nX1 = nX;
455 int nY1 = nY;
456 int nWidth1 = nWidth;
457 int nHeight1 = nHeight;
458 int nXOffset = nX;
459 int nYOffset = nY;
460 int nCx; // slider,min,max sizes
461 int nCy;
462 int nCyf;
463 int nCurrentX;
464 int nCurrentY;
465 char zBuf[300];
466
467 //
468 // Adjust for OS/2's reverse coordinate system
469 //
470 wxWindowOS2* pParent = (wxWindowOS2*)GetParent();
471 int nUsedHeight = 0;
472 int nOS2Height = nHeight;
473
474 if (nOS2Height < 0)
475 nOS2Height = 20;
476
477 if (pParent)
478 {
479 int nOS2ParentHeight = GetOS2ParentHeight(pParent);
480
481 nYOffset = nOS2ParentHeight - (nYOffset + nOS2Height);
482 if (nY != -1)
483 nY1 = nOS2ParentHeight - (nY1 + nOS2Height);
484 }
485 else
486 {
487 RECTL vRect;
488
489 ::WinQueryWindowRect(HWND_DESKTOP, &vRect);
490 nYOffset = vRect.yTop - (nYOffset + nOS2Height);
491 if (nY != -1)
492 nY1 = vRect.yTop - (nY1 + nOS2Height);
493 }
494 m_nSizeFlags = nSizeFlags;
495
496 GetPosition( &nCurrentX
497 ,&nCurrentY
498 );
499 if (nX == -1 && !(nSizeFlags & wxSIZE_ALLOW_MINUS_ONE))
500 nX1 = nCurrentX;
501 if (nY == -1 && !(nSizeFlags & wxSIZE_ALLOW_MINUS_ONE))
502 nY1 = nCurrentY;
503
504 AdjustForParentClientOrigin( nX1
505 ,nY1
506 ,nSizeFlags
507 );
508 wxGetCharSize( GetHWND()
509 ,&nCx
510 ,&nCy
511 ,&this->GetFont()
512 );
513
514 if ((m_windowStyle & wxSL_VERTICAL) != wxSL_VERTICAL)
515 {
516 if (m_windowStyle & wxSL_LABELS )
517 {
518 int nMinLen = 0;
519 int nMaxLen = 0;
520
521 ::WinQueryWindowText((HWND)m_hStaticMin, 300, zBuf);
522 GetTextExtent(zBuf, &nMinLen, &nCyf, NULL, NULL, &this->GetFont());
523 ::WinQueryWindowText((HWND)m_hStaticMax, 300, zBuf);
524 GetTextExtent(zBuf, &nMaxLen, &nCyf, NULL, NULL, &this->GetFont());
525
526 if (m_hStaticValue)
527 {
528 int nNewWidth = (wxMax(nMinLen, nMaxLen));
529 int nValueHeight = nCyf;
530
531 ::WinSetWindowPos( (HWND)m_hStaticValue
532 ,HWND_TOP
533 ,(LONG)nXOffset
534 ,(LONG)nYOffset - (nCyf * 1.2)
535 ,(LONG)nNewWidth
536 ,(LONG)nValueHeight
537 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
538 );
539 nXOffset += nNewWidth + nCx;
540 }
541 ::WinSetWindowPos( (HWND)m_hStaticMin
542 ,HWND_TOP
543 ,(LONG)nXOffset
544 ,(LONG)nYOffset - nCyf
545 ,(LONG)nMinLen
546 ,(LONG)nCy
547 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
548 );
549 nXOffset += nMinLen + nCx;
550
551 int nSliderLength = nWidth1 - nXOffset - nMaxLen - nCx;
552 int nSliderHeight = nHeight1;
553
554 if (nSliderHeight < 0)
555 nSliderHeight = 20;
556
557 //
558 // Slider must have a minimum/default length/height
559 //
560 if (nSliderLength < 100)
561 nSliderLength = 100;
562
563 ::WinSetWindowPos( GetHwnd()
564 ,HWND_TOP
565 ,(LONG)nXOffset
566 ,(LONG)nYOffset
567 ,(LONG)nSliderLength
568 ,(LONG)nSliderHeight
569 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
570 );
571 nXOffset += nSliderLength + nCx;
572
573 ::WinSetWindowPos( (HWND)m_hStaticMax
574 ,HWND_TOP
575 ,(LONG)nXOffset
576 ,(LONG)nYOffset - nCyf
577 ,(LONG)nMaxLen
578 ,(LONG)nCy
579 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
580 );
581 }
582 else
583 {
584 //
585 // No labels
586 // If we're prepared to use the existing size, then...
587 //
588 if (nWidth == -1 && nHeight == -1 &&
589 ((nSizeFlags & wxSIZE_AUTO) != wxSIZE_AUTO))
590 {
591 GetSize( &nWidth1
592 ,&nHeight1
593 );
594 }
595 if (nWidth1 < 0)
596 nWidth1 = 200;
597 if (nHeight1 < 0)
598 nHeight1 = 20;
599 ::WinSetWindowPos( GetHwnd()
600 ,HWND_TOP
601 ,(LONG)nX1
602 ,(LONG)nY1
603 ,(LONG)nWidth1
604 ,(LONG)nHeight1
605 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
606 );
607 }
608 }
609
610 //
611 // Now deal with a vertical slider
612 //
613 else
614 {
615 if (m_windowStyle & wxSL_LABELS )
616 {
617 int nMinLen;
618 int nMaxLen;
619
620 ::WinQueryWindowText((HWND)m_hStaticMin, 300, zBuf);
621 GetTextExtent(zBuf, &nMinLen, &nCyf, NULL, NULL, &this->GetFont());
622 ::WinQueryWindowText((HWND)m_hStaticMax, 300, zBuf);
623 GetTextExtent(zBuf, &nMaxLen, &nCyf, NULL, NULL, &this->GetFont());
624 if (m_hStaticValue)
625 {
626 int nNewWidth = wxMax(nMinLen, nMaxLen);
627 int nValueHeight = nCyf;
628
629 nNewWidth += nCx;
630
631 //
632 // The height needs to be a bit bigger under Win95 if using native
633 // 3D effects.
634 //
635 nValueHeight = (int)(nValueHeight * 1.5);
636 ::WinSetWindowPos( (HWND)m_hStaticValue
637 ,HWND_TOP
638 ,(LONG)nXOffset
639 ,(LONG)nYOffset
640 ,(LONG)nNewWidth
641 ,(LONG)nValueHeight
642 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
643 );
644 nYOffset -= nValueHeight;
645 nUsedHeight += nValueHeight;
646 }
647 ::WinSetWindowPos( (HWND)m_hStaticMin
648 ,HWND_TOP
649 ,(LONG)nXOffset
650 ,(LONG)nYOffset
651 ,(LONG)nMinLen
652 ,(LONG)nCy
653 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
654 );
655 nYOffset -= nCy;
656 nUsedHeight += nCy;
657
658 int nSliderLength = nHeight1 - (nUsedHeight + (2 * nCy));
659 int nSliderWidth = nWidth1;
660
661 if (nSliderWidth < 0)
662 nSliderWidth = 20;
663
664 //
665 // Slider must have a minimum/default length
666 //
667 if (nSliderLength < 100)
668 nSliderLength = 100;
669
670 ::WinSetWindowPos( (HWND)m_hStaticMin
671 ,HWND_TOP
672 ,(LONG)nXOffset
673 ,(LONG)nYOffset
674 ,(LONG)nSliderWidth
675 ,(LONG)nSliderLength
676 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
677 );
678 nYOffset -= nSliderLength;
679 nUsedHeight += nSliderLength;
680 ::WinSetWindowPos( (HWND)m_hStaticMax
681 ,HWND_TOP
682 ,(LONG)nXOffset
683 ,(LONG)nYOffset
684 ,(LONG)nMaxLen
685 ,(LONG)nCy
686 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
687 );
688 }
689 else
690 {
691 //
692 // No labels
693 // If we're prepared to use the existing size, then...
694 //
695 if (nWidth == -1 && nHeight == -1 &&
696 ((nSizeFlags & wxSIZE_AUTO) != wxSIZE_AUTO))
697 {
698 GetSize( &nWidth1
699 ,&nHeight1
700 );
701 }
702 if (nWidth1 < 0)
703 nWidth1 = 20;
704 if (nHeight1 < 0)
705 nHeight1 = 200;
706 ::WinSetWindowPos( GetHwnd()
707 ,HWND_TOP
708 ,(LONG)nX1
709 ,(LONG)nY1
710 ,(LONG)nWidth1
711 ,(LONG)nHeight1
712 ,SWP_ZORDER | SWP_SIZE | SWP_MOVE | SWP_SHOW
713 );
714 }
715 }
716 } // end of void wxSlider::DoSetSize
717
718 int wxSlider::GetLineSize() const
719 {
720 return 1;
721 } // end of wxSlider::GetLineSize
722
723 int wxSlider::GetPageSize() const
724 {
725 return m_nPageSize;
726 } // end of wxSlider::GetPageSize
727
728 void wxSlider::GetPosition(
729 int* pnX
730 , int* pnY
731 ) const
732 {
733 wxWindowOS2* pParent = GetParent();
734 RECTL vRect;
735
736 vRect.xLeft = -1;
737 vRect.xRight = -1;
738 vRect.yTop = -1;
739 vRect.yBottom = -1;
740 wxFindMaxSize( GetHWND()
741 ,&vRect
742 );
743
744 if (m_hStaticMin)
745 wxFindMaxSize( m_hStaticMin
746 ,&vRect
747 );
748 if (m_hStaticMax)
749 wxFindMaxSize( m_hStaticMax
750 ,&vRect
751 );
752 if (m_hStaticValue)
753 wxFindMaxSize( m_hStaticValue
754 ,&vRect
755 );
756
757 //
758 // Since we now have the absolute screen coords,
759 // if there's a parent we must subtract its top left corner
760 //
761 POINTL vPoint;
762
763 vPoint.x = vRect.xLeft;
764 vPoint.y = vRect.yTop;
765
766 if (pParent)
767 {
768 SWP vSwp;
769
770 ::WinQueryWindowPos((HWND)pParent->GetHWND(), &vSwp);
771 vPoint.x = vSwp.x;
772 vPoint.y = vSwp.y;
773 }
774
775 //
776 // We may be faking the client origin.
777 // So a window that's really at (0, 30) may appear
778 // (to wxWin apps) to be at (0, 0).
779 //
780 if (GetParent())
781 {
782 wxPoint vPt(GetParent()->GetClientAreaOrigin());
783
784 vPoint.x -= vPt.x;
785 vPoint.y -= vPt.y;
786 }
787 *pnX = vPoint.x;
788 *pnY = vPoint.y;
789 } // end of wxSlider::GetPosition
790
791 int wxSlider::GetSelEnd() const
792 {
793 return 0;
794 } // end of wxSlider::GetSelEnd
795
796 int wxSlider::GetSelStart() const
797 {
798 return 0;
799 } // end of wxSlider::GetSelStart
800
801 void wxSlider::GetSize(
802 int* pnWidth
803 , int* pnHeight
804 ) const
805 {
806 RECTL vRect;
807
808 vRect.xLeft = -1;
809 vRect.xRight = -1;
810 vRect.yTop = -1;
811 vRect.yBottom = -1;
812
813 wxFindMaxSize( GetHWND()
814 ,&vRect
815 );
816
817 if (m_hStaticMin)
818 wxFindMaxSize( m_hStaticMin
819 ,&vRect
820 );
821 if (m_hStaticMax)
822 wxFindMaxSize( m_hStaticMax
823 ,&vRect
824 );
825 if (m_hStaticValue)
826 wxFindMaxSize( m_hStaticValue
827 ,&vRect
828 );
829 *pnWidth = vRect.xRight - vRect.xLeft;
830 *pnHeight = vRect.yBottom - vRect.yTop;
831 } // end of wxSlider::GetSize
832
833 int wxSlider::GetThumbLength() const
834 {
835 return m_nThumbLength;
836 } // end of wxSlider::GetThumbLength
837
838 int wxSlider::GetValue() const
839 {
840 int nPixelRange = SHORT1FROMMR(::WinSendMsg( GetHwnd()
841 ,SLM_QUERYSLIDERINFO
842 ,MPFROM2SHORT( SMA_SHAFTDIMENSIONS
843 ,SMA_RANGEVALUE
844 )
845 ,(MPARAM)0
846 )
847 );
848 double dPixelToRange = (double)(nPixelRange - m_nThumbLength)/(double)(m_nRangeMax - m_nRangeMin);
849 int nNewPos = 0;
850 int nPixelPos = SHORT1FROMMR(::WinSendMsg( GetHwnd()
851 ,SLM_QUERYSLIDERINFO
852 ,MPFROM2SHORT( SMA_SLIDERARMPOSITION
853 ,SMA_RANGEVALUE
854 )
855 ,(MPARAM)0
856 )
857 );
858 nNewPos = (int)(nPixelPos/dPixelToRange);
859 if (nNewPos > (m_nRangeMax - m_nRangeMin)/2)
860 nNewPos++;
861 return nNewPos;
862 } // end of wxSlider::GetValue
863
864 WXHBRUSH wxSlider::OnCtlColor(
865 WXHDC hDC
866 , WXHWND hWnd
867 , WXUINT uCtlColor
868 , WXUINT uMessage
869 , WXWPARAM wParam
870 , WXLPARAM lParam
871 )
872 {
873 return (wxControl::OnCtlColor( hDC
874 ,hWnd
875 ,uCtlColor
876 ,uMessage
877 ,wParam
878 ,lParam
879 )
880 );
881 } // end of wxSlider::OnCtlColor
882
883 bool wxSlider::OS2OnScroll(
884 int WXUNUSED(nOrientation)
885 , WXWORD wParam
886 , WXWORD wPos
887 , WXHWND hControl
888 )
889 {
890 wxEventType eScrollEvent = wxEVT_NULL;
891
892 switch (wParam)
893 {
894 case SLN_CHANGE:
895 if (m_windowStyle & wxSL_TOP)
896 eScrollEvent = wxEVT_SCROLL_TOP;
897 else if (m_windowStyle & wxSL_BOTTOM)
898 eScrollEvent = wxEVT_SCROLL_BOTTOM;
899 break;
900
901 case SLN_SLIDERTRACK:
902 eScrollEvent = wxEVT_SCROLL_THUMBTRACK;
903 break;
904
905 default:
906 return FALSE;
907 }
908
909 int nPixelRange = SHORT1FROMMR(::WinSendMsg( GetHwnd()
910 ,SLM_QUERYSLIDERINFO
911 ,MPFROM2SHORT( SMA_SHAFTDIMENSIONS
912 ,SMA_RANGEVALUE
913 )
914 ,(MPARAM)0
915 )
916 );
917 m_dPixelToRange = (double)(nPixelRange - m_nThumbLength)/(double)(m_nRangeMax - m_nRangeMin);
918 int nNewPos = 0;
919 int nPixelPos = SHORT1FROMMR(::WinSendMsg( GetHwnd()
920 ,SLM_QUERYSLIDERINFO
921 ,MPFROM2SHORT( SMA_SLIDERARMPOSITION
922 ,SMA_RANGEVALUE
923 )
924 ,(MPARAM)0
925 )
926 );
927 nNewPos = (nPixelPos/m_dPixelToRange);
928 if (nNewPos > (m_nRangeMax - m_nRangeMin)/2)
929 nNewPos++;
930 if ((nNewPos < GetMin()) || (nNewPos > GetMax()))
931 {
932 //
933 // Out of range - but we did process it
934 //
935 return TRUE;
936 }
937 SetValue(nNewPos);
938
939 wxScrollEvent vEvent( eScrollEvent
940 ,m_windowId
941 );
942
943 vEvent.SetPosition(nNewPos);
944 vEvent.SetEventObject(this);
945 GetEventHandler()->ProcessEvent(vEvent);
946
947 wxCommandEvent vCevent( wxEVT_COMMAND_SLIDER_UPDATED
948 ,GetId()
949 );
950
951 vCevent.SetInt(nNewPos);
952 vCevent.SetEventObject(this);
953 return (GetEventHandler()->ProcessEvent(vCevent));
954 } // end of wxSlider::OS2OnScroll
955
956 void wxSlider::SetLineSize(
957 int nLineSize
958 )
959 {
960 m_nLineSize = nLineSize;
961 } // end of wxSlider::SetLineSize
962
963
964 void wxSlider::SetPageSize(
965 int nPageSize
966 )
967 {
968 m_nPageSize = nPageSize;
969 } // end of wxSlider::SetPageSize
970
971 void wxSlider::SetRange(
972 int nMinValue
973 , int nMaxValue
974 )
975 {
976 wxChar zBuf[10];
977
978 m_nRangeMin = nMinValue;
979 m_nRangeMax = nMaxValue;
980
981 int nPixelRange = SHORT1FROMMR(::WinSendMsg( GetHwnd()
982 ,SLM_QUERYSLIDERINFO
983 ,MPFROM2SHORT( SMA_SHAFTDIMENSIONS
984 ,SMA_RANGEVALUE
985 )
986 ,(MPARAM)0
987 )
988 );
989 m_dPixelToRange = (double)(nPixelRange - m_nThumbLength)/(double)(m_nRangeMax - m_nRangeMin);
990 if (m_hStaticMin)
991 {
992 wxSprintf(zBuf, wxT("%d"), m_nRangeMin);
993 ::WinSetWindowText((HWND)m_hStaticMin, zBuf);
994 }
995
996 if (m_hStaticMax)
997 {
998 wxSprintf(zBuf, wxT("%d"), m_nRangeMax);
999 ::WinSetWindowText((HWND)m_hStaticMax, zBuf);
1000 }
1001 } // end of wxSlider::SetRange
1002
1003 void wxSlider::SetSelection(
1004 int WXUNUSED(nMinPos)
1005 , int WXUNUSED(nMaxPos)
1006 )
1007 {
1008 } // end of wxSlider::SetSelection
1009
1010 void wxSlider::SetThumbLength(
1011 int nLen
1012 )
1013 {
1014 int nBreadth;
1015
1016 m_nThumbLength = SHORT1FROMMR(::WinSendMsg( GetHwnd()
1017 ,SLM_QUERYSLIDERINFO
1018 ,MPFROM2SHORT( SMA_SLIDERARMDIMENSIONS
1019 ,SMA_RANGEVALUE
1020 )
1021 ,(MPARAM)0
1022 )
1023 ) + 4; // for bordersizes
1024 nBreadth = SHORT2FROMMR(::WinSendMsg( GetHwnd()
1025 ,SLM_QUERYSLIDERINFO
1026 ,MPFROM2SHORT( SMA_SLIDERARMDIMENSIONS
1027 ,SMA_RANGEVALUE
1028 )
1029 ,(MPARAM)0
1030 )
1031 );
1032 ::WinSendMsg( GetHwnd()
1033 ,SLM_SETSLIDERINFO
1034 ,MPFROM2SHORT( SMA_SLIDERARMDIMENSIONS
1035 ,SMA_RANGEVALUE
1036 )
1037 ,MPFROM2SHORT(nLen, nBreadth)
1038 );
1039 m_nThumbLength = nLen + 4; // Borders
1040 } // end of wxSlider::SetThumbLength
1041
1042 void wxSlider::SetTick(
1043 int nTickPos
1044 )
1045 {
1046 nTickPos *= m_dPixelToRange;
1047 ::WinSendMsg( GetHwnd()
1048 ,SLM_ADDDETENT
1049 ,MPFROMSHORT(nTickPos)
1050 ,NULL
1051 );
1052 } // end of wxSlider::SetTick
1053
1054 // For trackbars only
1055 void wxSlider::SetTickFreq(
1056 int n
1057 , int nPos
1058 )
1059 {
1060 SLDCDATA vSlData;
1061 WNDPARAMS vWndParams;
1062 int nPixelPos;
1063 int i;
1064
1065 vSlData.cbSize = sizeof(SLDCDATA);
1066 if (m_windowStyle & wxSL_AUTOTICKS)
1067 {
1068 vSlData.usScale1Spacing = 0;
1069 vSlData.usScale2Spacing = 0;
1070 }
1071 vSlData.usScale1Increments = (m_nRangeMax - m_nRangeMin)/n;
1072 vSlData.usScale2Increments = (m_nRangeMax - m_nRangeMin)/n;
1073
1074 vWndParams.fsStatus = WPM_CTLDATA;
1075 vWndParams.cchText = 0L;
1076 vWndParams.pszText = NULL;
1077 vWndParams.cbPresParams = 0L;
1078 vWndParams.pPresParams = NULL;
1079 vWndParams.cbCtlData = vSlData.cbSize;
1080 vWndParams.pCtlData = (PVOID)&vSlData;
1081 ::WinSendMsg(GetHwnd(), WM_SETWINDOWPARAMS, (MPARAM)&vWndParams, (MPARAM)0);
1082 for (i = 1; i < (m_nRangeMax - m_nRangeMin)/n; i++)
1083 {
1084 nPixelPos = i * n * m_dPixelToRange;
1085 ::WinSendMsg( GetHwnd()
1086 ,SLM_ADDDETENT
1087 ,MPFROMSHORT(nPixelPos)
1088 ,NULL
1089 );
1090 }
1091 } // end of wxSlider::SetTickFreq
1092
1093 void wxSlider::SetValue(
1094 int nValue
1095 )
1096 {
1097 int nPixelPos = SHORT1FROMMR(::WinSendMsg( GetHwnd()
1098 ,SLM_QUERYSLIDERINFO
1099 ,MPFROM2SHORT( SMA_SLIDERARMPOSITION
1100 ,SMA_RANGEVALUE
1101 )
1102 ,(MPARAM)0
1103 )
1104 );
1105 int nPixelRange = SHORT1FROMMR(::WinSendMsg( GetHwnd()
1106 ,SLM_QUERYSLIDERINFO
1107 ,MPFROM2SHORT( SMA_SHAFTDIMENSIONS
1108 ,SMA_RANGEVALUE
1109 )
1110 ,(MPARAM)0
1111 )
1112 );
1113 m_dPixelToRange = (double)(nPixelRange - m_nThumbLength)/(double)(m_nRangeMax - m_nRangeMin);
1114 int nNewPos = (int)(nValue * m_dPixelToRange);
1115
1116 ::WinSendMsg( GetHwnd()
1117 ,SLM_SETSLIDERINFO
1118 ,MPFROM2SHORT( SMA_SLIDERARMPOSITION
1119 ,SMA_RANGEVALUE
1120 )
1121 ,(MPARAM)nNewPos
1122 );
1123 if (m_hStaticValue)
1124 {
1125 wxSprintf(wxBuffer, wxT("%d"), nValue);
1126 ::WinSetWindowText((HWND)m_hStaticValue, wxBuffer);
1127 }
1128 } // end of wxSlider::SetValue
1129
1130 bool wxSlider::Show(
1131 bool bShow
1132 )
1133 {
1134 wxWindowOS2::Show(bShow);
1135 if(m_hStaticValue)
1136 ::WinShowWindow((HWND)m_hStaticValue, bShow);
1137 if(m_hStaticMin)
1138 ::WinShowWindow((HWND)m_hStaticMin, bShow);
1139 if(m_hStaticMax)
1140 ::WinShowWindow((HWND)m_hStaticMax, bShow);
1141 return TRUE;
1142 } // end of wxSlider::Show
1143