]> git.saurik.com Git - wxWidgets.git/blame - src/os2/notebook.cpp
check for NULL pointer returned by wxFontEnumerator::GetFacenames() (it actually...
[wxWidgets.git] / src / os2 / notebook.cpp
CommitLineData
0e320a79
DW
1///////////////////////////////////////////////////////////////////////////////
2// Name: notebook.cpp
3// Purpose: implementation of wxNotebook
cdf1e714 4// Author: David Webster
fb46a9a6 5// Modified by:
cdf1e714 6// Created: 10/12/99
0e320a79 7// RCS-ID: $Id$
cdf1e714 8// Copyright: (c) David Webster
0e320a79
DW
9// Licence: wxWindows licence
10///////////////////////////////////////////////////////////////////////////////
11
cdf1e714
DW
12// For compilers that support precompilation, includes "wx.h".
13#include "wx/wxprec.h"
0e320a79 14
f289196b
DW
15#if wxUSE_NOTEBOOK
16
cdf1e714
DW
17// wxWindows
18#ifndef WX_PRECOMP
1a75e76f 19 #include "wx/app.h"
3979bf6b 20 #include "wx/dcclient.h"
1a75e76f
SN
21 #include "wx/string.h"
22 #include "wx/settings.h"
cdf1e714 23#endif // WX_PRECOMP
0e320a79 24
f289196b
DW
25#include "wx/log.h"
26#include "wx/imaglist.h"
27#include "wx/event.h"
28#include "wx/control.h"
29#include "wx/notebook.h"
cdf1e714 30
f289196b 31#include "wx/os2/private.h"
cdf1e714 32
0e320a79
DW
33// ----------------------------------------------------------------------------
34// macros
35// ----------------------------------------------------------------------------
f289196b 36
0e320a79
DW
37// check that the page index is valid
38#define IS_VALID_PAGE(nPage) (((nPage) >= 0) && ((nPage) < GetPageCount()))
39
cdf1e714 40// hide the ugly cast
f289196b 41#define m_hWnd (HWND)GetHWND()
cdf1e714
DW
42
43// ----------------------------------------------------------------------------
44// constants
45// ----------------------------------------------------------------------------
46
0e320a79
DW
47// ----------------------------------------------------------------------------
48// event table
49// ----------------------------------------------------------------------------
50
8546f11e
DW
51DEFINE_EVENT_TYPE(wxEVT_COMMAND_NOTEBOOK_PAGE_CHANGED)
52DEFINE_EVENT_TYPE(wxEVT_COMMAND_NOTEBOOK_PAGE_CHANGING)
53
54BEGIN_EVENT_TABLE(wxNotebook, wxControl)
0e320a79 55 EVT_NOTEBOOK_PAGE_CHANGED(-1, wxNotebook::OnSelChange)
0e320a79
DW
56 EVT_SIZE(wxNotebook::OnSize)
57 EVT_SET_FOCUS(wxNotebook::OnSetFocus)
58 EVT_NAVIGATION_KEY(wxNotebook::OnNavigationKey)
8546f11e 59END_EVENT_TABLE()
0e320a79 60
8546f11e
DW
61IMPLEMENT_DYNAMIC_CLASS(wxNotebook, wxControl)
62IMPLEMENT_DYNAMIC_CLASS(wxNotebookEvent, wxNotifyEvent)
0e320a79
DW
63
64// ============================================================================
65// implementation
66// ============================================================================
67
68// ----------------------------------------------------------------------------
69// wxNotebook construction
70// ----------------------------------------------------------------------------
71
f289196b
DW
72//
73// Common part of all ctors
74//
0e320a79
DW
75void wxNotebook::Init()
76{
f289196b 77 m_imageList = NULL;
0e320a79 78 m_nSelection = -1;
f289196b
DW
79 m_nTabSize = 0;
80} // end of wxNotebook::Init
0e320a79 81
f289196b
DW
82//
83// Default for dynamic class
84//
0e320a79
DW
85wxNotebook::wxNotebook()
86{
87 Init();
f289196b
DW
88} // end of wxNotebook::wxNotebook
89
90//
91// The same arguments as for wxControl
92//
93wxNotebook::wxNotebook(
94 wxWindow* pParent
95, wxWindowID vId
96, const wxPoint& rPos
97, const wxSize& rSize
98, long lStyle
99, const wxString& rsName
100)
0e320a79
DW
101{
102 Init();
f289196b
DW
103 Create( pParent
104 ,vId
105 ,rPos
106 ,rSize
107 ,lStyle
108 ,rsName
109 );
110} // end of wxNotebook::wxNotebook
111
112//
0e320a79 113// Create() function
f289196b
DW
114//
115bool wxNotebook::Create(
116 wxWindow* pParent
117, wxWindowID vId
118, const wxPoint& rPos
119, const wxSize& rSize
120, long lStyle
121, const wxString& rsName
122)
0e320a79 123{
f289196b
DW
124 //
125 // Base init
126 //
127 if (!CreateControl( pParent
128 ,vId
129 ,rPos
130 ,rSize
131 ,lStyle
132 ,wxDefaultValidator
133 ,rsName
134 ))
135 return FALSE;
136
137 //
138 // Notebook, so explicitly specify 0 as last parameter
139 //
140 if (!OS2CreateControl( "NOTEBOOK"
141 ,_T("")
142 ,rPos
143 ,rSize
144 ,lStyle | wxTAB_TRAVERSAL
145 ))
146 return FALSE;
147
148 SetBackgroundColour(wxColour(wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE)));
149 return TRUE;
150} // end of wxNotebook::Create
151
152WXDWORD wxNotebook::OS2GetStyle (
153 long lStyle
154, WXDWORD* pdwExstyle
155) const
0e320a79 156{
f289196b
DW
157 WXDWORD dwTabStyle = wxControl::OS2GetStyle( lStyle
158 ,pdwExstyle
159 );
160
161 dwTabStyle |= WS_TABSTOP | BKS_SOLIDBIND | BKS_ROUNDEDTABS | BKS_TABTEXTCENTER;
162
163 if (lStyle & wxNB_BOTTOM)
164 dwTabStyle |= BKS_MAJORTABBOTTOM | BKS_BACKPAGESBL;
165 else if (lStyle & wxNB_RIGHT)
166 dwTabStyle |= BKS_MAJORTABRIGHT | BKS_BACKPAGESBR;
167 else if (lStyle & wxNB_LEFT)
168 dwTabStyle |= BKS_MAJORTABLEFT | BKS_BACKPAGESTL;
169 else // default to top
170 dwTabStyle |= BKS_MAJORTABTOP | BKS_BACKPAGESTR;
171
172 //
173 // Ex style
174 //
175 if (pdwExstyle )
176 {
177 //
178 // Note that we never want to have the default WS_EX_CLIENTEDGE style
179 // as it looks too ugly for the notebooks
180 //
181 *pdwExstyle = 0;
182 }
183 return dwTabStyle;
184} // end of wxNotebook::OS2GetStyle
0e320a79
DW
185
186// ----------------------------------------------------------------------------
187// wxNotebook accessors
188// ----------------------------------------------------------------------------
f289196b 189
21323df7 190size_t wxNotebook::GetPageCount() const
0e320a79 191{
f289196b
DW
192 int nPageInternal = m_pages.Count();
193 int nPageAPI = (int)::WinSendMsg(GetHWND(), BKM_QUERYPAGECOUNT, (MPARAM)0, (MPARAM)BKA_END);
194
195 //
196 // Consistency check
197 //
198 wxASSERT((int)m_pages.Count() == (int)::WinSendMsg(GetHWND(), BKM_QUERYPAGECOUNT, (MPARAM)0, (MPARAM)BKA_END));
199 return m_pages.Count();
200} // end of wxNotebook::GetPageCount
0e320a79
DW
201
202int wxNotebook::GetRowCount() const
203{
f289196b
DW
204 return (int)::WinSendMsg( GetHWND()
205 ,BKM_QUERYPAGECOUNT
206 ,(MPARAM)0
207 ,(MPARAM)BKA_MAJOR
208 );
209} // end of wxNotebook::GetRowCount
210
211int wxNotebook::SetSelection(
3979bf6b 212 size_t nPage
f289196b 213)
0e320a79 214{
cdf1e714 215 wxCHECK_MSG( IS_VALID_PAGE(nPage), -1, wxT("notebook page out of range") );
f289196b 216
2b5f62a0
VZ
217 if (nPage != m_nSelection)
218 {
219 wxNotebookEvent vEvent( wxEVT_COMMAND_NOTEBOOK_PAGE_CHANGING
220 ,m_windowId
221 );
f289196b 222
2b5f62a0
VZ
223 vEvent.SetSelection(nPage);
224 vEvent.SetOldSelection(m_nSelection);
225 vEvent.SetEventObject(this);
226 if (!GetEventHandler()->ProcessEvent(vEvent) || vEvent.IsAllowed())
227 {
f289196b 228
2b5f62a0
VZ
229 //
230 // Program allows the page change
231 //
232 vEvent.SetEventType(wxEVT_COMMAND_NOTEBOOK_PAGE_CHANGED);
233 GetEventHandler()->ProcessEvent(vEvent);
234
235 ULONG ulPageId = (ULONG)m_alPageId[nPage];
236
237 ::WinSendMsg( GetHWND()
238 ,BKM_TURNTOPAGE
239 ,MPFROMLONG((ULONG)m_alPageId[nPage])
240 ,(MPARAM)0
241 );
242 }
243 }
f289196b
DW
244 m_nSelection = nPage;
245 return nPage;
246} // end of wxNotebook::SetSelection
247
248bool wxNotebook::SetPageText(
3979bf6b 249 size_t nPage
f289196b
DW
250, const wxString& rsStrText
251)
252{
253 wxCHECK_MSG( IS_VALID_PAGE(nPage), FALSE, wxT("notebook page out of range") );
0e320a79 254
0e320a79 255
f289196b 256 ULONG ulPageId = (ULONG)m_alPageId[nPage];
0e320a79 257
f289196b
DW
258 return (bool)::WinSendMsg( m_hWnd
259 ,BKM_SETTABTEXT
260 ,MPFROMLONG((ULONG)m_alPageId[nPage])
261 ,MPFROMP((PSZ)rsStrText.c_str())
262 );
263} // end of wxNotebook::SetPageText
0e320a79 264
f289196b 265wxString wxNotebook::GetPageText (
3979bf6b 266 size_t nPage
f289196b 267) const
0e320a79 268{
f289196b
DW
269 BOOKTEXT vBookText;
270 wxChar zBuf[256];
271 wxString sStr;
272 ULONG ulRc;
0e320a79 273
cdf1e714 274 wxCHECK_MSG( IS_VALID_PAGE(nPage), wxT(""), wxT("notebook page out of range") );
0e320a79 275
0e320a79 276
f289196b
DW
277 ULONG ulPageId = (ULONG)m_alPageId[nPage];
278
279 memset(&vBookText, '\0', sizeof(BOOKTEXT));
280 vBookText.textLen = 0; // This will get the length
281 ulRc = LONGFROMMR(::WinSendMsg( m_hWnd
282 ,BKM_QUERYTABTEXT
283 ,MPFROMLONG((ULONG)m_alPageId[nPage])
284 ,MPFROMP(&vBookText)
285 ));
286 if (ulRc == BOOKERR_INVALID_PARAMETERS || ulRc == 0L)
287 {
288 if (ulRc == BOOKERR_INVALID_PARAMETERS)
289 {
290 wxLogError(wxT("Invalid Page Id for page text querry."));
291 }
292 return wxEmptyString;
293 }
294 vBookText.textLen = ulRc + 1; // To get the null terminator
295 vBookText.pString = zBuf;
296
297 //
298 // Now get the actual text
299 //
300 ulRc = LONGFROMMR(::WinSendMsg( m_hWnd
301 ,BKM_QUERYTABTEXT
302 ,MPFROMLONG((ULONG)m_alPageId[nPage])
303 ,MPFROMP(&vBookText)
304 ));
305 if (ulRc == BOOKERR_INVALID_PARAMETERS || ulRc == 0L)
306 {
307 return wxEmptyString;
308 }
309 if (ulRc > 255L)
310 ulRc = 255L;
311
312 vBookText.pString[ulRc] = '\0';
313 sStr = vBookText.pString;
314 return sStr;
315} // end of wxNotebook::GetPageText
316
317int wxNotebook::GetPageImage (
3979bf6b 318 size_t nPage
f289196b 319) const
0e320a79 320{
cdf1e714 321 wxCHECK_MSG( IS_VALID_PAGE(nPage), -1, wxT("notebook page out of range") );
0e320a79 322
f289196b
DW
323 //
324 // For OS/2 just return the page
325 //
326 return nPage;
327} // end of wxNotebook::GetPageImage
0e320a79 328
f289196b 329bool wxNotebook::SetPageImage (
3979bf6b 330 size_t nPage
f289196b
DW
331, int nImage
332)
0e320a79 333{
f289196b 334 wxBitmap* pBitmap = (wxBitmap*)m_imageList->GetBitmap(nImage);
0e320a79 335
0e320a79 336
f289196b 337 ULONG ulPageId = (ULONG)m_alPageId[nPage];
0e320a79 338
f289196b
DW
339 return (bool)::WinSendMsg( GetHWND()
340 ,BKM_SETTABBITMAP
341 ,MPFROMLONG((ULONG)m_alPageId[nPage])
342 ,(MPARAM)pBitmap->GetHBITMAP()
343 );
344} // end of wxNotebook::SetPageImage
345
346void wxNotebook::SetImageList (
347 wxImageList* WXUNUSED(pImageList)
348)
cdf1e714 349{
f289196b
DW
350 //
351 // Does nothing under OS/2
352 //
353} // end of wxNotebook::SetImageList
cdf1e714 354
0e320a79 355// ----------------------------------------------------------------------------
f289196b 356// wxNotebook size settings
0e320a79 357// ----------------------------------------------------------------------------
f289196b
DW
358void wxNotebook::SetPageSize (
359 const wxSize& rSize
360)
0367c1c0 361{
f289196b
DW
362 RECTL vRect;
363
364 //
365 // Transform the page size into the notebook size
366 //
367 vRect.xLeft = vRect.yTop = 0;
368 vRect.xRight = rSize.x;
369 vRect.yBottom = rSize.y;
370
371
372 //
373 // And now set it
374 //
375 SetSize( vRect.xRight - vRect.xLeft
376 ,vRect.yBottom - vRect.yTop
377 );
378} // end of wxNotebook::SetPageSize
379
380void wxNotebook::SetPadding (
381 const wxSize& WXUNUSED(rPadding)
382)
0367c1c0 383{
f289196b
DW
384 //
385 // No padding in OS/2
386 //
387} // end of wxNotebook::SetPadding
388
389void wxNotebook::SetTabSize (
390 const wxSize& rSize
391)
392{
393 ::WinSendMsg( GetHWND()
394 ,BKM_SETDIMENSIONS
395 ,MPFROM2SHORT( (USHORT)rSize.x
396 ,(USHORT)rSize.y
397 )
398 ,(MPARAM)BKA_MAJORTAB
399 );
400} // end of wxNotebook::SetTabSize
401
402// ----------------------------------------------------------------------------
403// wxNotebook operations
404// ----------------------------------------------------------------------------
0367c1c0 405
f289196b
DW
406//
407// Remove one page from the notebook, without deleting
408//
409wxNotebookPage* wxNotebook::DoRemovePage (
3979bf6b 410 size_t nPage
f289196b 411)
0e320a79 412{
f289196b 413 wxNotebookPage* pPageRemoved = wxNotebookBase::DoRemovePage(nPage);
0e320a79 414
f289196b
DW
415 if (!pPageRemoved)
416 return NULL;
0e320a79 417
0e320a79 418
f289196b 419 ULONG ulPageId = (ULONG)m_alPageId[nPage];
0e320a79 420
f289196b
DW
421 ::WinSendMsg( GetHWND()
422 ,BKM_DELETEPAGE
423 ,MPFROMLONG((ULONG)m_alPageId[nPage])
424 ,(MPARAM)BKA_TAB
425 );
426 if (m_pages.IsEmpty())
427 {
428 //
429 // No selection any more, the notebook becamse empty
430 //
431 m_nSelection = -1;
432 }
433 else // notebook still not empty
434 {
435 //
436 // Change the selected page if it was deleted or became invalid
437 //
438 int nSelNew;
0e320a79 439
f289196b
DW
440 if (m_nSelection == GetPageCount())
441 {
442 //
443 // Last page deleted, make the new last page the new selection
444 //
445 nSelNew = m_nSelection - 1;
446 }
447 else if (nPage <= m_nSelection)
448 {
449 //
450 // We must show another page, even if it has the same index
451 //
452 nSelNew = m_nSelection;
453 }
454 else // nothing changes for the currently selected page
455 {
456 nSelNew = -1;
457
458 //
459 // We still must refresh the current page: this needs to be done
460 // for some unknown reason if the tab control shows the up-down
461 // control (i.e. when there are too many pages) -- otherwise after
462 // deleting a page nothing at all is shown
463 //
464 m_pages[m_nSelection]->Refresh();
465 }
0e320a79 466
f289196b
DW
467 if (nSelNew != -1)
468 {
469 //
470 // m_nSelection must be always valid so reset it before calling
471 // SetSelection()
472 //
473 m_nSelection = -1;
474 SetSelection(nSelNew);
475 }
476 }
477 return pPageRemoved;
478} // end of wxNotebook::DoRemovePage
0e320a79 479
f289196b
DW
480//
481// Remove all pages
482//
0e320a79
DW
483bool wxNotebook::DeleteAllPages()
484{
f289196b
DW
485 int nPageCount = GetPageCount();
486 int nPage;
487
488 for (nPage = 0; nPage < nPageCount; nPage++)
489 delete m_pages[nPage];
490 m_pages.Clear();
491 ::WinSendMsg( GetHWND()
492 ,BKM_DELETEPAGE
493 ,(MPARAM)0
494 ,(MPARAM)BKA_ALL
495 );
496 m_nSelection = -1;
0e320a79 497 return TRUE;
f289196b
DW
498} // end of wxNotebook::DeleteAllPages
499
500//
501// Add a page to the notebook
502//
503bool wxNotebook::AddPage (
504 wxNotebookPage* pPage
505, const wxString& rStrText
506, bool bSelect
507, int nImageId
508)
0e320a79 509{
f289196b
DW
510 return InsertPage( GetPageCount()
511 ,pPage
512 ,rStrText
513 ,bSelect
514 ,nImageId
515 );
516} // end of wxNotebook::AddPage
517
518//
519// Same as AddPage() but does it at given position
520//
521bool wxNotebook::InsertPage (
3979bf6b 522 size_t nPage
f289196b
DW
523, wxNotebookPage* pPage
524, const wxString& rsStrText
525, bool bSelect
526, int nImageId
527)
0e320a79 528{
f289196b
DW
529 ULONG ulApiPage;
530
0e320a79
DW
531 wxASSERT( pPage != NULL );
532 wxCHECK( IS_VALID_PAGE(nPage) || nPage == GetPageCount(), FALSE );
533
f289196b
DW
534 //
535 // Under OS/2 we can only insert FIRST, LAST, NEXT or PREV. Requires
536 // two different calls to the API. Page 1 uses the BKA_FIRST. Subsequent
537 // pages use the previous page ID coupled with a BKA_NEXT call. Unlike
538 // Windows, OS/2 uses an internal Page ID to ID the pages.
539 //
540 // OS/2 also has a nice auto-size feature that automatically sizes the
541 // the attached window so we don't have to worry about the size of the
542 // window on the page.
543 //
544 if (nPage == 0)
545 {
546 ulApiPage = LONGFROMMR(::WinSendMsg( GetHWND()
547 ,BKM_INSERTPAGE
548 ,(MPARAM)0
549 ,MPFROM2SHORT(BKA_AUTOPAGESIZE | BKA_MAJOR, BKA_FIRST)
550 ));
551 if (ulApiPage == 0L)
552 {
553 ERRORID vError;
554 wxString sError;
0e320a79 555
f289196b
DW
556 vError = ::WinGetLastError(vHabmain);
557 sError = wxPMErrorToStr(vError);
558 return FALSE;
559 }
560 m_alPageId.Insert((long)ulApiPage, nPage);
561 }
562 else
563 {
564 ulApiPage = LONGFROMMR(::WinSendMsg( GetHWND()
565 ,BKM_INSERTPAGE
566 ,MPFROMLONG((ULONG)m_alPageId[nPage - 1])
567 ,MPFROM2SHORT(BKA_AUTOPAGESIZE | BKA_MAJOR, BKA_NEXT)
568 ));
569 if (ulApiPage == 0L)
570 {
571 ERRORID vError;
572 wxString sError;
0e320a79 573
f289196b
DW
574 vError = ::WinGetLastError(vHabmain);
575 sError = wxPMErrorToStr(vError);
576 return FALSE;
577 }
578 m_alPageId.Insert((long)ulApiPage, nPage);
579 }
0e320a79 580
f289196b
DW
581 //
582 // Associate a window handle with the page
583 //
584 if (pPage)
585 {
586 if (!::WinSendMsg( GetHWND()
587 ,BKM_SETPAGEWINDOWHWND
588 ,MPFROMLONG((ULONG)m_alPageId[nPage])
589 ,MPFROMHWND(pPage->GetHWND())
590 ))
591 return FALSE;
592 }
593 //
594 // If the inserted page is before the selected one, we must update the
595 // index of the selected page
596 //
597 if (nPage <= m_nSelection)
598 {
599 //
600 // One extra page added
601 //
602 m_nSelection++;
603 }
0e320a79 604
f289196b
DW
605 if (pPage)
606 {
607 //
608 // Save the pointer to the page
609 //
610 m_pages.Insert( pPage
611 ,nPage
612 );
0e320a79
DW
613 }
614
f289196b
DW
615 //
616 // Now set TAB dimenstions
617 //
0e320a79 618
f289196b
DW
619 wxWindowDC vDC(this);
620 wxCoord nTextX;
621 wxCoord nTextY;
0e320a79 622
f289196b
DW
623 vDC.GetTextExtent(rsStrText, &nTextX, &nTextY);
624 nTextY *= 2;
625 nTextX *= 1.3;
626 if (nTextX > m_nTabSize)
627 {
628 m_nTabSize = nTextX;
629 ::WinSendMsg( GetHWND()
630 ,BKM_SETDIMENSIONS
631 ,MPFROM2SHORT((USHORT)m_nTabSize, (USHORT)nTextY)
632 ,(MPARAM)BKA_MAJORTAB
633 );
634 }
635 //
636 // Now set any TAB text
637 //
638 if (!rsStrText.IsEmpty())
639 {
640 if (!SetPageText( nPage
641 ,rsStrText
642 ))
643 return FALSE;
644 }
0e320a79 645
f289196b
DW
646 //
647 // Now set any TAB bitmap image
648 //
649 if (nImageId != -1)
650 {
651 if (!SetPageImage( nPage
652 ,nImageId
653 ))
654 return FALSE;
655 }
7e99520b 656
f289196b
DW
657 if (pPage)
658 {
659 //
660 // Don't show pages by default (we'll need to adjust their size first)
661 //
662 HWND hWnd = GetWinHwnd(pPage);
663
664 WinSetWindowULong( hWnd
665 ,QWL_STYLE
666 ,WinQueryWindowULong( hWnd
667 ,QWL_STYLE
668 ) & ~WS_VISIBLE
669 );
670
671 //
672 // This updates internal flag too - otherwise it will get out of sync
673 //
674 pPage->Show(FALSE);
0e320a79
DW
675 }
676
f289196b
DW
677 //
678 // Some page should be selected: either this one or the first one if there is
679 // still no selection
680 //
681 int nSelNew = -1;
682
683 if (bSelect)
684 nSelNew = nPage;
685 else if ( m_nSelection == -1 )
686 nSelNew = 0;
0e320a79 687
f289196b
DW
688 if (nSelNew != -1)
689 SetSelection(nSelNew);
690 return TRUE;
691} // end of wxNotebook::InsertPage
692
693// ----------------------------------------------------------------------------
694// wxNotebook callbacks
695// ----------------------------------------------------------------------------
696void wxNotebook::OnSize(
697 wxSizeEvent& rEvent
698)
0e320a79 699{
1de4baa3
DW
700 int nPage;
701 int nCount = (int)m_pages.Count();
702
703 for (nPage = 0; nPage < nCount; nPage++)
704 {
705 if (m_nSelection == nPage)
706 m_pages[nPage]->Refresh();
707 else
708 ::WinSetWindowPos(m_pages[nPage]->GetHWND()
709 ,NULLHANDLE
710 ,0,0,0,0
711 ,SWP_HIDE
712 );
713 }
f289196b
DW
714 rEvent.Skip();
715} // end of wxNotebook::OnSize
716
717void wxNotebook::OnSelChange (
718 wxNotebookEvent& rEvent
719)
720{
721 //
722 // Is it our tab control?
723 //
724 if (rEvent.GetEventObject() == this)
cdf1e714 725 {
1de4baa3
DW
726 int nPageCount = GetPageCount();
727 int nSel;
728 ULONG ulOS2Sel = (ULONG)rEvent.GetOldSelection();
729 bool bFound = FALSE;
fb46a9a6 730
1de4baa3 731 for (nSel = 0; nSel < nPageCount; nSel++)
f289196b 732 {
1de4baa3
DW
733 if (ulOS2Sel == m_alPageId[nSel])
734 {
735 bFound = TRUE;
736 break;
737 }
f289196b 738 }
f289196b 739
1de4baa3
DW
740 if (!bFound)
741 return;
742
743 m_pages[nSel]->Show(FALSE);
744
745 ulOS2Sel = (ULONG)rEvent.GetSelection();
746
747 bFound = FALSE;
748
749 for (nSel = 0; nSel < nPageCount; nSel++)
750 {
751 if (ulOS2Sel == m_alPageId[nSel])
752 {
753 bFound = TRUE;
754 break;
755 }
cdf1e714 756 }
1de4baa3
DW
757
758 if (!bFound)
759 return;
760
761 wxNotebookPage* pPage = m_pages[nSel];
762
763 pPage->Show(TRUE);
f289196b
DW
764 m_nSelection = nSel;
765 }
fb46a9a6 766
f289196b
DW
767 //
768 // We want to give others a chance to process this message as well
769 //
770 rEvent.Skip();
771} // end of wxNotebook::OnSelChange
0e320a79 772
f289196b
DW
773void wxNotebook::OnSetFocus (
774 wxFocusEvent& rEvent
775)
0e320a79 776{
f289196b
DW
777 //
778 // This function is only called when the focus is explicitly set (i.e. from
779 // the program) to the notebook - in this case we don't need the
780 // complicated OnNavigationKey() logic because the programmer knows better
781 // what [s]he wants
782 //
0e320a79 783 // set focus to the currently selected page if any
f289196b
DW
784 //
785 if (m_nSelection != -1)
786 m_pages[m_nSelection]->SetFocus();
787 rEvent.Skip();
788} // end of wxNotebook::OnSetFocus
789
790void wxNotebook::OnNavigationKey (
791 wxNavigationKeyEvent& rEvent
792)
0e320a79 793{
f289196b
DW
794 if (rEvent.IsWindowChange())
795 {
796 //
797 // Change pages
798 //
799 AdvanceSelection(rEvent.GetDirection());
0e320a79 800 }
f289196b
DW
801 else
802 {
803 //
804 // We get this event in 2 cases
805 //
806 // a) one of our pages might have generated it because the user TABbed
807 // out from it in which case we should propagate the event upwards and
808 // our parent will take care of setting the focus to prev/next sibling
809 //
810 // or
811 //
812 // b) the parent panel wants to give the focus to us so that we
813 // forward it to our selected page. We can't deal with this in
814 // OnSetFocus() because we don't know which direction the focus came
815 // from in this case and so can't choose between setting the focus to
816 // first or last panel child
817 //
818 wxWindow* pParent = GetParent();
819
820 if (rEvent.GetEventObject() == pParent)
821 {
822 //
823 // No, it doesn't come from child, case (b): forward to a page
824 //
825 if (m_nSelection != -1)
826 {
827 //
828 // So that the page knows that the event comes from it's parent
829 // and is being propagated downwards
830 //
831 rEvent.SetEventObject(this);
832
833 wxWindow* pPage = m_pages[m_nSelection];
834
835 if (!pPage->GetEventHandler()->ProcessEvent(rEvent))
836 {
837 pPage->SetFocus();
838 }
839 //else: page manages focus inside it itself
840 }
841 else
842 {
843 //
844 // We have no pages - still have to give focus to _something_
845 //
846 SetFocus();
847 }
848 }
849 else
850 {
851 //
852 // It comes from our child, case (a), pass to the parent
853 //
854 if (pParent)
855 {
856 rEvent.SetCurrentFocus(this);
857 pParent->GetEventHandler()->ProcessEvent(rEvent);
858 }
0e320a79
DW
859 }
860 }
f289196b 861} // end of wxNotebook::OnNavigationKey
0e320a79
DW
862
863// ----------------------------------------------------------------------------
864// wxNotebook base class virtuals
865// ----------------------------------------------------------------------------
866
f289196b
DW
867//
868// Override these 2 functions to do nothing: everything is done in OnSize
869//
870void wxNotebook::SetConstraintSizes(
871 bool WXUNUSED(bRecurse)
872)
0e320a79 873{
f289196b
DW
874 //
875 // Don't set the sizes of the pages - their correct size is not yet known
876 //
0e320a79 877 wxControl::SetConstraintSizes(FALSE);
f289196b 878} // end of wxNotebook::SetConstraintSizes
0e320a79 879
f289196b
DW
880bool wxNotebook::DoPhase (
881 int WXUNUSED(nPhase)
882)
0e320a79
DW
883{
884 return TRUE;
f289196b 885} // end of wxNotebook::DoPhase
0e320a79 886
f289196b
DW
887// ----------------------------------------------------------------------------
888// wxNotebook Windows message handlers
889// ----------------------------------------------------------------------------
890bool wxNotebook::OS2OnScroll (
891 int nOrientation
892, WXWORD wSBCode
893, WXWORD wPos
894, WXHWND wControl
895)
0e320a79 896{
f289196b
DW
897 //
898 // Don't generate EVT_SCROLLWIN events for the WM_SCROLLs coming from the
899 // up-down control
900 //
901 if (wControl)
902 return FALSE;
903 return wxNotebookBase::OS2OnScroll( nOrientation
904 ,wSBCode
905 ,wPos
906 ,wControl
907 );
908} // end of wxNotebook::OS2OnScroll
0e320a79 909
f289196b 910#endif // wxUSE_NOTEBOOK
0e320a79 911