]> git.saurik.com Git - wxWidgets.git/blame - src/generic/notebook.cpp
translate "Copy URL" string in the popup menu (feature request 1803958) (should have...
[wxWidgets.git] / src / generic / notebook.cpp
CommitLineData
1e6d9499 1///////////////////////////////////////////////////////////////////////////////
7fc65a03
WS
2// Name: src/generic/notebook.cpp
3// Purpose: generic implementation of wxNotebook
1e6d9499
JS
4// Author: Julian Smart
5// Modified by:
6// Created: 17/09/98
7// RCS-ID: $Id$
8// Copyright: (c) Julian Smart
65571936 9// Licence: wxWindows licence
1e6d9499
JS
10///////////////////////////////////////////////////////////////////////////////
11
12// ============================================================================
13// declarations
14// ============================================================================
15
16// ----------------------------------------------------------------------------
17// headers
18// ----------------------------------------------------------------------------
ffecfa5a 19
1e6d9499
JS
20// For compilers that support precompilation, includes "wx.h".
21#include "wx/wxprec.h"
22
23#ifdef __BORLANDC__
df91131c 24 #pragma hdrstop
1e6d9499
JS
25#endif
26
bc5a5239
WS
27#if wxUSE_NOTEBOOK
28
df91131c
WS
29#include "wx/notebook.h"
30
31#ifndef WX_PRECOMP
32 #include "wx/string.h"
e4db172a 33 #include "wx/log.h"
ed4b0fdc 34 #include "wx/dcclient.h"
9eddec69 35 #include "wx/settings.h"
df91131c 36#endif
4055ed82 37
1c36c09c 38#include "wx/imaglist.h"
00dd3b18 39#include "wx/generic/tabg.h"
1e6d9499
JS
40
41// ----------------------------------------------------------------------------
42// macros
43// ----------------------------------------------------------------------------
44
45// check that the page index is valid
0ea23391 46#define IS_VALID_PAGE(nPage) ((nPage) < GetPageCount())
1e6d9499
JS
47
48// ----------------------------------------------------------------------------
49// event table
50// ----------------------------------------------------------------------------
51
2e4df4bf
VZ
52DEFINE_EVENT_TYPE(wxEVT_COMMAND_NOTEBOOK_PAGE_CHANGED)
53DEFINE_EVENT_TYPE(wxEVT_COMMAND_NOTEBOOK_PAGE_CHANGING)
54
8dba4c72 55BEGIN_EVENT_TABLE(wxNotebook, wxBookCtrlBase)
ca65c044 56 EVT_NOTEBOOK_PAGE_CHANGED(wxID_ANY, wxNotebook::OnSelChange)
1e6d9499
JS
57 EVT_SIZE(wxNotebook::OnSize)
58 EVT_PAINT(wxNotebook::OnPaint)
59 EVT_MOUSE_EVENTS(wxNotebook::OnMouseEvent)
60 EVT_SET_FOCUS(wxNotebook::OnSetFocus)
61 EVT_NAVIGATION_KEY(wxNotebook::OnNavigationKey)
1e6d9499
JS
62END_EVENT_TABLE()
63
8dba4c72 64IMPLEMENT_DYNAMIC_CLASS(wxNotebook, wxBookCtrlBase)
1e6d9499 65IMPLEMENT_DYNAMIC_CLASS(wxNotebookEvent, wxCommandEvent)
1e6d9499
JS
66
67// ============================================================================
68// implementation
69// ============================================================================
70
00dd3b18
MB
71// ============================================================================
72// Private class
73// ============================================================================
74
dd5e8687
MW
75WX_DECLARE_HASH_MAP(int, wxNotebookPage*, wxIntegerHash, wxIntegerEqual,
76 wxIntToNotebookPageHashMap);
77
78WX_DECLARE_HASH_MAP(wxNotebookPage*, int, wxPointerHash, wxPointerEqual,
79 wxNotebookPageToIntHashMap);
80
00dd3b18
MB
81// This reuses wxTabView to draw the tabs.
82class WXDLLEXPORT wxNotebookTabView: public wxTabView
83{
84DECLARE_DYNAMIC_CLASS(wxNotebookTabView)
85public:
bc5a5239 86 wxNotebookTabView(wxNotebook* notebook, long style = wxTAB_STYLE_DRAW_BOX | wxTAB_STYLE_COLOUR_INTERIOR);
d3c7fc99 87 virtual ~wxNotebookTabView(void);
00dd3b18 88
bc5a5239
WS
89 // Called when a tab is activated
90 virtual void OnTabActivate(int activateId, int deactivateId);
91 // Allows vetoing
92 virtual bool OnTabPreActivate(int activateId, int deactivateId);
00dd3b18 93
dd5e8687
MW
94 // map integer ids used by wxTabView to wxNotebookPage pointers
95 int GetId(wxNotebookPage *page);
96 wxNotebookPage *GetPage(int id) { return m_idToPage[id]; }
97
00dd3b18 98protected:
dd5e8687
MW
99 wxNotebook* m_notebook;
100
101private:
102 wxIntToNotebookPageHashMap m_idToPage;
103 wxNotebookPageToIntHashMap m_pageToId;
104 int m_nextid;
00dd3b18
MB
105};
106
dd5e8687
MW
107static int GetPageId(wxTabView *tabview, wxNotebookPage *page)
108{
98b9b5ea 109 return wx_static_cast(wxNotebookTabView*, tabview)->GetId(page);
dd5e8687
MW
110}
111
1e6d9499
JS
112// ----------------------------------------------------------------------------
113// wxNotebook construction
114// ----------------------------------------------------------------------------
115
116// common part of all ctors
117void wxNotebook::Init()
118{
119 m_tabView = (wxNotebookTabView*) NULL;
1e6d9499
JS
120 m_nSelection = -1;
121}
122
123// default for dynamic class
124wxNotebook::wxNotebook()
125{
126 Init();
127}
128
129// the same arguments as for wxControl
130wxNotebook::wxNotebook(wxWindow *parent,
131 wxWindowID id,
132 const wxPoint& pos,
133 const wxSize& size,
134 long style,
135 const wxString& name)
136{
137 Init();
138
139 Create(parent, id, pos, size, style, name);
140}
141
142// Create() function
143bool wxNotebook::Create(wxWindow *parent,
144 wxWindowID id,
145 const wxPoint& pos,
146 const wxSize& size,
147 long style,
148 const wxString& name)
149{
150 // base init
151 SetName(name);
152
90f9b8ef
JS
153 if ( (style & wxBK_ALIGN_MASK) == wxBK_DEFAULT )
154 style |= wxBK_TOP;
6e271798 155
ca65c044 156 m_windowId = id == wxID_ANY ? NewControlId() : id;
1e6d9499 157
b4f8693c 158 if (!wxControl::Create(parent, id, pos, size, style|wxNO_BORDER, wxDefaultValidator, name))
ca65c044 159 return false;
1e6d9499
JS
160
161 SetTabView(new wxNotebookTabView(this));
162
ca65c044 163 return true;
1e6d9499
JS
164}
165
166// dtor
167wxNotebook::~wxNotebook()
168{
169 delete m_tabView;
170}
171
172// ----------------------------------------------------------------------------
173// wxNotebook accessors
174// ----------------------------------------------------------------------------
1e6d9499
JS
175int wxNotebook::GetRowCount() const
176{
177 // TODO
178 return 0;
179}
180
15aad3b9 181int wxNotebook::SetSelection(size_t nPage)
1e6d9499 182{
1e6d9499
JS
183 wxASSERT( IS_VALID_PAGE(nPage) );
184
185 wxNotebookPage* pPage = GetPage(nPage);
186
dd5e8687 187 m_tabView->SetTabSelection(GetPageId(m_tabView, pPage));
3a5bcc4d 188
1e6d9499
JS
189 // TODO
190 return 0;
191}
192
6e271798
VZ
193int wxNotebook::ChangeSelection(size_t nPage)
194{
195 // FIXME: currently it does generate events too
196 return SetSelection(nPage);
197}
198
45f22d48 199#if 0
1e6d9499
JS
200void wxNotebook::AdvanceSelection(bool bForward)
201{
202 int nSel = GetSelection();
203 int nMax = GetPageCount() - 1;
204 if ( bForward )
205 SetSelection(nSel == nMax ? 0 : nSel + 1);
206 else
207 SetSelection(nSel == 0 ? nMax : nSel - 1);
208}
45f22d48 209#endif
1e6d9499 210
15aad3b9 211bool wxNotebook::SetPageText(size_t nPage, const wxString& strText)
1e6d9499
JS
212{
213 wxASSERT( IS_VALID_PAGE(nPage) );
3a5bcc4d 214
1e6d9499
JS
215 wxNotebookPage* page = GetPage(nPage);
216 if (page)
217 {
dd5e8687 218 m_tabView->SetTabText(GetPageId(m_tabView, page), strText);
1e6d9499 219 Refresh();
ca65c044 220 return true;
1e6d9499 221 }
3a5bcc4d 222
ca65c044 223 return false;
1e6d9499
JS
224}
225
15aad3b9 226wxString wxNotebook::GetPageText(size_t nPage) const
1e6d9499
JS
227{
228 wxASSERT( IS_VALID_PAGE(nPage) );
229
230 wxNotebookPage* page = ((wxNotebook*)this)->GetPage(nPage);
231 if (page)
dd5e8687 232 return m_tabView->GetTabText(GetPageId(m_tabView, page));
1e6d9499
JS
233 else
234 return wxEmptyString;
235}
236
3f9ee1cd 237int wxNotebook::GetPageImage(size_t WXUNUSED_UNLESS_DEBUG(nPage)) const
1e6d9499
JS
238{
239 wxASSERT( IS_VALID_PAGE(nPage) );
240
241 // TODO
242 return 0;
243}
244
3f9ee1cd
VZ
245bool wxNotebook::SetPageImage(size_t WXUNUSED_UNLESS_DEBUG(nPage),
246 int WXUNUSED(nImage))
1e6d9499
JS
247{
248 wxASSERT( IS_VALID_PAGE(nPage) );
249
250 // TODO
ca65c044 251 return false;
1e6d9499
JS
252}
253
9806a47c 254// set the size (the same for all pages)
7fc65a03 255void wxNotebook::SetPageSize(const wxSize& WXUNUSED(size))
9806a47c
JS
256{
257 // TODO
258}
259
260// set the padding between tabs (in pixels)
7fc65a03 261void wxNotebook::SetPadding(const wxSize& WXUNUSED(padding))
9806a47c
JS
262{
263 // TODO
264}
265
266// set the size of the tabs for wxNB_FIXEDWIDTH controls
7fc65a03 267void wxNotebook::SetTabSize(const wxSize& WXUNUSED(sz))
9806a47c
JS
268{
269 // TODO
270}
271
1e6d9499
JS
272// ----------------------------------------------------------------------------
273// wxNotebook operations
274// ----------------------------------------------------------------------------
275
276// remove one page from the notebook and delete it
15aad3b9 277bool wxNotebook::DeletePage(size_t nPage)
1e6d9499 278{
ca65c044 279 wxCHECK( IS_VALID_PAGE(nPage), false );
1e6d9499
JS
280
281 if (m_nSelection != -1)
282 {
ca65c044 283 m_pages[m_nSelection]->Show(false);
45f22d48 284 m_pages[m_nSelection]->Lower();
1e6d9499
JS
285 }
286
287 wxNotebookPage* pPage = GetPage(nPage);
3a5bcc4d 288
dd5e8687 289 m_tabView->RemoveTab(GetPageId(m_tabView, pPage));
1e6d9499 290
45f22d48
JS
291 m_pages.Remove(pPage);
292 delete pPage;
1e6d9499 293
45f22d48 294 if (m_pages.GetCount() == 0)
1e6d9499 295 {
bc5a5239
WS
296 m_nSelection = -1;
297 m_tabView->SetTabSelection(-1, false);
1e6d9499
JS
298 }
299 else if (m_nSelection > -1)
300 {
bc5a5239 301 m_nSelection = -1;
3a5bcc4d 302
dd5e8687 303 m_tabView->SetTabSelection(GetPageId(m_tabView, GetPage(0)), false);
3a5bcc4d 304
bc5a5239
WS
305 if (m_nSelection != 0)
306 ChangePage(-1, 0);
1e6d9499
JS
307 }
308
ca65c044 309 RefreshLayout(false);
1e6d9499 310
ca65c044 311 return true;
1e6d9499
JS
312}
313
314bool wxNotebook::DeletePage(wxNotebookPage* page)
315{
316 int pagePos = FindPagePosition(page);
317 if (pagePos > -1)
318 return DeletePage(pagePos);
319 else
ca65c044 320 return false;
1e6d9499
JS
321}
322
15aad3b9 323bool wxNotebook::RemovePage(size_t nPage)
64b090c7
MB
324{
325 return DoRemovePage(nPage) != NULL;
326}
327
328// remove one page from the notebook
329wxWindow* wxNotebook::DoRemovePage(size_t nPage)
1e6d9499 330{
10f2222c 331 wxCHECK( IS_VALID_PAGE(nPage), NULL );
1e6d9499 332
ca65c044 333 m_pages[nPage]->Show(false);
45f22d48 334 // m_pages[nPage]->Lower();
1e6d9499
JS
335
336 wxNotebookPage* pPage = GetPage(nPage);
3a5bcc4d 337
dd5e8687 338 m_tabView->RemoveTab(GetPageId(m_tabView, pPage));
1e6d9499 339
45f22d48 340 m_pages.Remove(pPage);
1e6d9499 341
45f22d48 342 if (m_pages.GetCount() == 0)
1e6d9499
JS
343 {
344 m_nSelection = -1;
ca65c044 345 m_tabView->SetTabSelection(-1, true);
1e6d9499
JS
346 }
347 else if (m_nSelection > -1)
348 {
349 // Only change the selection if the page we
350 // deleted was the selection.
30d2b71d 351 if (nPage == (size_t)m_nSelection)
1e6d9499
JS
352 {
353 m_nSelection = -1;
354 // Select the first tab. Generates a ChangePage.
ca65c044 355 m_tabView->SetTabSelection(0, true);
1e6d9499
JS
356 }
357 else
358 {
ca65c044 359 // We must adjust which tab we think is selected.
1e6d9499
JS
360 // If greater than the page we deleted, it must be moved down
361 // a notch.
30d2b71d 362 if (size_t(m_nSelection) > nPage)
1e6d9499
JS
363 m_nSelection -- ;
364 }
365 }
366
ca65c044 367 RefreshLayout(false);
1e6d9499 368
64b090c7 369 return pPage;
1e6d9499
JS
370}
371
372bool wxNotebook::RemovePage(wxNotebookPage* page)
373{
374 int pagePos = FindPagePosition(page);
375 if (pagePos > -1)
376 return RemovePage(pagePos);
377 else
ca65c044 378 return false;
1e6d9499
JS
379}
380
381// Find the position of the wxNotebookPage, -1 if not found.
382int wxNotebook::FindPagePosition(wxNotebookPage* page) const
383{
15aad3b9
VZ
384 size_t nPageCount = GetPageCount();
385 size_t nPage;
1e6d9499 386 for ( nPage = 0; nPage < nPageCount; nPage++ )
45f22d48 387 if (m_pages[nPage] == page)
1e6d9499
JS
388 return nPage;
389 return -1;
390}
391
392// remove all pages
393bool wxNotebook::DeleteAllPages()
394{
ca65c044 395 m_tabView->ClearTabs(true);
1e6d9499 396
15aad3b9
VZ
397 size_t nPageCount = GetPageCount();
398 size_t nPage;
1e6d9499 399 for ( nPage = 0; nPage < nPageCount; nPage++ )
45f22d48 400 delete m_pages[nPage];
1e6d9499 401
45f22d48 402 m_pages.Clear();
1e6d9499 403
ca65c044 404 return true;
1e6d9499
JS
405}
406
1e6d9499 407// same as AddPage() but does it at given position
15aad3b9 408bool wxNotebook::InsertPage(size_t nPage,
1e6d9499
JS
409 wxNotebookPage *pPage,
410 const wxString& strText,
411 bool bSelect,
7fc65a03 412 int WXUNUSED(imageId))
1e6d9499
JS
413{
414 wxASSERT( pPage != NULL );
ca65c044 415 wxCHECK( IS_VALID_PAGE(nPage) || nPage == GetPageCount(), false );
1e6d9499 416
dd5e8687 417 m_tabView->AddTab(GetPageId(m_tabView, pPage), strText);
3a5bcc4d 418
1e6d9499 419 if (!bSelect)
ca65c044 420 pPage->Show(false);
1e6d9499
JS
421
422 // save the pointer to the page
45f22d48 423 m_pages.Insert(pPage, nPage);
1e6d9499
JS
424
425 if (bSelect)
426 {
427 // This will cause ChangePage to be called, via OnSelPage
3a5bcc4d 428
dd5e8687 429 m_tabView->SetTabSelection(GetPageId(m_tabView, pPage), true);
1e6d9499
JS
430 }
431
432 // some page must be selected: either this one or the first one if there is
433 // still no selection
434 if ( m_nSelection == -1 )
435 ChangePage(-1, 0);
436
ca65c044 437 RefreshLayout(false);
1e6d9499 438
ca65c044 439 return true;
1e6d9499
JS
440}
441
442// ----------------------------------------------------------------------------
443// wxNotebook callbacks
444// ----------------------------------------------------------------------------
445
446// @@@ OnSize() is used for setting the font when it's called for the first
447// time because doing it in ::Create() doesn't work (for unknown reasons)
448void wxNotebook::OnSize(wxSizeEvent& event)
449{
ca65c044 450 static bool s_bFirstTime = true;
1e6d9499
JS
451 if ( s_bFirstTime ) {
452 // TODO: any first-time-size processing.
ca65c044 453 s_bFirstTime = false;
1e6d9499
JS
454 }
455
456 RefreshLayout();
457
458 // Processing continues to next OnSize
459 event.Skip();
460}
461
462// This was supposed to cure the non-display of the notebook
463// until the user resizes the window.
464// What's going on?
5180055b 465void wxNotebook::OnInternalIdle()
1e6d9499 466{
5180055b
JS
467 wxWindow::OnInternalIdle();
468
ca65c044
WS
469#if 0
470 static bool s_bFirstTime = true;
1e6d9499
JS
471 if ( s_bFirstTime ) {
472 /*
473 wxSize sz(GetSize());
474 sz.x ++;
475 SetSize(sz);
476 sz.x --;
477 SetSize(sz);
478 */
479
480 /*
481 wxSize sz(GetSize());
482 wxSizeEvent sizeEvent(sz, GetId());
483 sizeEvent.SetEventObject(this);
484 GetEventHandler()->ProcessEvent(sizeEvent);
485 Refresh();
486 */
ca65c044 487 s_bFirstTime = false;
1e6d9499 488 }
5180055b 489#endif
1e6d9499
JS
490}
491
492// Implementation: calculate the layout of the view rect
493// and resize the children if required
494bool wxNotebook::RefreshLayout(bool force)
495{
496 if (m_tabView)
497 {
498 wxRect oldRect = m_tabView->GetViewRect();
499
500 int cw, ch;
501 GetClientSize(& cw, & ch);
502
503 int tabHeight = m_tabView->GetTotalTabHeight();
504 wxRect rect;
505 rect.x = 4;
506 rect.y = tabHeight + 4;
507 rect.width = cw - 8;
508 rect.height = ch - 4 - rect.y ;
2e4df4bf 509
1e6d9499
JS
510 m_tabView->SetViewRect(rect);
511
25889d3c 512 m_tabView->LayoutTabs();
1e6d9499
JS
513
514 // Need to do it a 2nd time to get the tab height with
515 // the new view width, since changing the view width changes the
516 // tab layout.
517 tabHeight = m_tabView->GetTotalTabHeight();
518 rect.x = 4;
519 rect.y = tabHeight + 4;
520 rect.width = cw - 8;
521 rect.height = ch - 4 - rect.y ;
2e4df4bf 522
1e6d9499
JS
523 m_tabView->SetViewRect(rect);
524
25889d3c 525 m_tabView->LayoutTabs();
1e6d9499
JS
526
527 if (!force && (rect == oldRect))
ca65c044 528 return false;
1e6d9499
JS
529
530 // fit the notebook page to the tab control's display area
531
15aad3b9
VZ
532 size_t nCount = m_pages.Count();
533 for ( size_t nPage = 0; nPage < nCount; nPage++ ) {
45f22d48 534 wxNotebookPage *pPage = m_pages[nPage];
10d1f413 535 wxRect clientRect = GetAvailableClientSize();
1e6d9499
JS
536 if (pPage->IsShown())
537 {
1e6d9499
JS
538 pPage->SetSize(clientRect.x, clientRect.y, clientRect.width, clientRect.height);
539 if ( pPage->GetAutoLayout() )
540 pPage->Layout();
541 }
542 }
543 Refresh();
544 }
ca65c044 545 return true;
1e6d9499
JS
546}
547
548void wxNotebook::OnSelChange(wxNotebookEvent& event)
549{
550 // is it our tab control?
551 if ( event.GetEventObject() == this )
552 {
553 if (event.GetSelection() != m_nSelection)
554 ChangePage(event.GetOldSelection(), event.GetSelection());
555 }
556
557 // we want to give others a chance to process this message as well
558 event.Skip();
559}
560
561void wxNotebook::OnSetFocus(wxFocusEvent& event)
562{
563 // set focus to the currently selected page if any
564 if ( m_nSelection != -1 )
45f22d48 565 m_pages[m_nSelection]->SetFocus();
1e6d9499
JS
566
567 event.Skip();
568}
569
570void wxNotebook::OnNavigationKey(wxNavigationKeyEvent& event)
571{
572 if ( event.IsWindowChange() ) {
573 // change pages
574 AdvanceSelection(event.GetDirection());
575 }
576 else {
577 // pass to the parent
578 if ( GetParent() ) {
579 event.SetCurrentFocus(this);
580 GetParent()->ProcessEvent(event);
581 }
582 }
583}
584
585// ----------------------------------------------------------------------------
586// wxNotebook base class virtuals
587// ----------------------------------------------------------------------------
588
589// override these 2 functions to do nothing: everything is done in OnSize
590
591void wxNotebook::SetConstraintSizes(bool /* recurse */)
592{
593 // don't set the sizes of the pages - their correct size is not yet known
ca65c044 594 wxControl::SetConstraintSizes(false);
1e6d9499
JS
595}
596
597bool wxNotebook::DoPhase(int /* nPhase */)
598{
ca65c044 599 return true;
1e6d9499
JS
600}
601
af111fc3 602void wxNotebook::Command(wxCommandEvent& WXUNUSED(event))
1e6d9499 603{
b0c0a393 604 wxFAIL_MSG(wxT("wxNotebook::Command not implemented"));
1e6d9499
JS
605}
606
607// ----------------------------------------------------------------------------
608// wxNotebook helper functions
609// ----------------------------------------------------------------------------
610
611// hide the currently active panel and show the new one
612void wxNotebook::ChangePage(int nOldSel, int nSel)
613{
614 // cout << "ChangePage: " << nOldSel << ", " << nSel << "\n";
615 wxASSERT( nOldSel != nSel ); // impossible
616
617 if ( nOldSel != -1 ) {
ca65c044 618 m_pages[nOldSel]->Show(false);
45f22d48 619 m_pages[nOldSel]->Lower();
1e6d9499
JS
620 }
621
45f22d48 622 wxNotebookPage *pPage = m_pages[nSel];
1e6d9499
JS
623
624 wxRect clientRect = GetAvailableClientSize();
625 pPage->SetSize(clientRect.x, clientRect.y, clientRect.width, clientRect.height);
626
f6bcfd97
BP
627 Refresh();
628
ca65c044 629 pPage->Show(true);
1e6d9499
JS
630 pPage->Raise();
631 pPage->SetFocus();
632
1e6d9499
JS
633 m_nSelection = nSel;
634}
635
636void wxNotebook::OnMouseEvent(wxMouseEvent& event)
637{
638 if (m_tabView)
639 m_tabView->OnEvent(event);
640}
641
642void wxNotebook::OnPaint(wxPaintEvent& WXUNUSED(event) )
643{
644 wxPaintDC dc(this);
645 if (m_tabView)
646 m_tabView->Draw(dc);
647}
648
6bae6726
MB
649wxSize wxNotebook::CalcSizeFromPage(const wxSize& sizePage) const
650{
651 // MBN: since the total tab height is really a function of the
652 // width, this should really call
653 // GetTotalTabHeightPretendingWidthIs(), but the current
654 // implementation will suffice, provided the wxNotebook has been
655 // created with a sensible initial width.
656 return wxSize( sizePage.x + 12,
657 sizePage.y + m_tabView->GetTotalTabHeight() + 6 + 4 );
658}
659
1e6d9499
JS
660wxRect wxNotebook::GetAvailableClientSize()
661{
662 int cw, ch;
663 GetClientSize(& cw, & ch);
664
665 int tabHeight = m_tabView->GetTotalTabHeight();
666
667 // TODO: these margins should be configurable.
668 wxRect rect;
669 rect.x = 6;
670 rect.y = tabHeight + 6;
671 rect.width = cw - 12;
672 rect.height = ch - 4 - rect.y ;
673
674 return rect;
675}
676
677/*
678 * wxNotebookTabView
679 */
2e4df4bf 680
1e6d9499
JS
681IMPLEMENT_CLASS(wxNotebookTabView, wxTabView)
682
dd5e8687
MW
683wxNotebookTabView::wxNotebookTabView(wxNotebook *notebook, long style)
684 : wxTabView(style), m_nextid(1)
1e6d9499
JS
685{
686 m_notebook = notebook;
687
688 m_notebook->SetTabView(this);
689
690 SetWindow(m_notebook);
691}
692
693wxNotebookTabView::~wxNotebookTabView(void)
694{
695}
696
dd5e8687
MW
697int wxNotebookTabView::GetId(wxNotebookPage *page)
698{
699 int& id = m_pageToId[page];
700
701 if (!id)
702 {
703 id = m_nextid++;
704 m_idToPage[id] = page;
705 }
706
707 return id;
708}
709
1e6d9499
JS
710// Called when a tab is activated
711void wxNotebookTabView::OnTabActivate(int activateId, int deactivateId)
712{
713 if (!m_notebook)
714 return;
715
716 wxNotebookEvent event(wxEVT_COMMAND_NOTEBOOK_PAGE_CHANGED, m_notebook->GetId());
717
718 // Translate from wxTabView's ids (which aren't position-dependent)
719 // to wxNotebook's (which are).
dd5e8687
MW
720 wxNotebookPage* pActive = GetPage(activateId);
721 wxNotebookPage* pDeactive = GetPage(deactivateId);
1e6d9499
JS
722
723 int activatePos = m_notebook->FindPagePosition(pActive);
724 int deactivatePos = m_notebook->FindPagePosition(pDeactive);
725
726 event.SetEventObject(m_notebook);
727 event.SetSelection(activatePos);
728 event.SetOldSelection(deactivatePos);
729 m_notebook->GetEventHandler()->ProcessEvent(event);
730}
731
1c507b17
JS
732// Allows Vetoing
733bool wxNotebookTabView::OnTabPreActivate(int activateId, int deactivateId)
734{
ca65c044
WS
735 bool retval = true;
736
1c507b17
JS
737 if (m_notebook)
738 {
739 wxNotebookEvent event(wxEVT_COMMAND_NOTEBOOK_PAGE_CHANGING, m_notebook->GetId());
740
1c507b17
JS
741 // Translate from wxTabView's ids (which aren't position-dependent)
742 // to wxNotebook's (which are).
dd5e8687
MW
743 wxNotebookPage* pActive = GetPage(activateId);
744 wxNotebookPage* pDeactive = GetPage(deactivateId);
1c507b17
JS
745
746 int activatePos = m_notebook->FindPagePosition(pActive);
747 int deactivatePos = m_notebook->FindPagePosition(pDeactive);
748
1c507b17
JS
749 event.SetEventObject(m_notebook);
750 event.SetSelection(activatePos);
751 event.SetOldSelection(deactivatePos);
752 if (m_notebook->GetEventHandler()->ProcessEvent(event))
753 {
754 retval = event.IsAllowed();
755 }
756 }
757 return retval;
ca65c044 758}
bc5a5239
WS
759
760#endif // wxUSE_NOTEBOOK