1 /////////////////////////////////////////////////////////////////////////////
3 // Purpose: Printing framework base class implementation
4 // Author: Julian Smart
8 // Copyright: (c) Julian Smart
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
12 #if defined(__GNUG__) && !defined(NO_GCC_PRAGMA)
13 #pragma implementation "prntbase.h"
14 #pragma implementation "printdlg.h"
17 // For compilers that support precompilation, includes "wx.h".
18 #include "wx/wxprec.h"
26 #if wxUSE_PRINTING_ARCHITECTURE
32 #include "wx/msgdlg.h"
33 #include "wx/layout.h"
34 #include "wx/choice.h"
35 #include "wx/button.h"
36 #include "wx/settings.h"
37 #include "wx/dcmemory.h"
38 #include "wx/stattext.h"
40 #include "wx/textdlg.h"
44 #include "wx/prntbase.h"
45 #include "wx/dcprint.h"
46 #include "wx/printdlg.h"
48 #include "wx/module.h"
54 #include "wx/msw/private.h"
62 IMPLEMENT_CLASS(wxPrintPreviewBase
, wxObject
)
64 //----------------------------------------------------------------------------
66 //----------------------------------------------------------------------------
68 wxPrintFactory
*wxPrintFactory::m_factory
= NULL
;
70 void wxPrintFactory::SetPrintFactory( wxPrintFactory
*factory
)
72 if (wxPrintFactory::m_factory
)
73 delete wxPrintFactory::m_factory
;
75 wxPrintFactory::m_factory
= factory
;
78 wxPrintFactory
*wxPrintFactory::GetFactory()
80 if (!wxPrintFactory::m_factory
)
81 wxPrintFactory::m_factory
= new wxNativePrintFactory
;
83 return wxPrintFactory::m_factory
;
86 //----------------------------------------------------------------------------
87 // wxNativePrintFactory
88 //----------------------------------------------------------------------------
90 wxPrinterBase
*wxNativePrintFactory::CreatePrinter( wxPrintDialogData
*data
)
92 #if defined(__WXMSW__) && !defined(__WXUNIVERSAL__)
93 return new wxWindowsPrinter( data
);
94 #elif defined(__WXMAC__)
95 return new wxMacPrinter( data
);
96 #elif defined(__WXPM__)
97 return new wxOS2Printer( data
);
99 return new wxPostScriptPrinter( data
);
103 wxPrintPreviewBase
*wxNativePrintFactory::CreatePrintPreview( wxPrintout
*preview
,
104 wxPrintout
*printout
, wxPrintDialogData
*data
)
106 #if defined(__WXMSW__) && !defined(__WXUNIVERSAL__)
107 return new wxWindowsPrintPreview( preview
, printout
, data
);
108 #elif defined(__WXMAC__)
109 return new wxMacPrintPreview( preview
, printout
, data
);
110 #elif defined(__WXPM__)
111 return new wxOS2PrintPreview( preview
, printout
, data
);
113 return new wxPostScriptPrintPreview( preview
, printout
, data
);
117 wxPrintPreviewBase
*wxNativePrintFactory::CreatePrintPreview( wxPrintout
*preview
,
118 wxPrintout
*printout
, wxPrintData
*data
)
120 #if defined(__WXMSW__) && !defined(__WXUNIVERSAL__)
121 return new wxWindowsPrintPreview( preview
, printout
, data
);
122 #elif defined(__WXMAC__)
123 return new wxMacPrintPreview( preview
, printout
, data
);
124 #elif defined(__WXPM__)
125 return new wxOS2PrintPreview( preview
, printout
, data
);
127 return new wxPostScriptPrintPreview( preview
, printout
, data
);
131 wxPrintDialogBase
*wxNativePrintFactory::CreatePrintDialog( wxWindow
*parent
,
132 wxPrintDialogData
*data
)
134 #if defined(__WXMSW__) && !defined(__WXUNIVERSAL__)
135 return new wxWindowsPrintDialog( parent
, data
);
136 #elif defined(__WXMAC__)
137 return new wxMacPrintDialog( parent
, data
);
139 return new wxGenericPrintDialog( parent
, data
);
143 wxPrintDialogBase
*wxNativePrintFactory::CreatePrintDialog( wxWindow
*parent
,
146 #if defined(__WXMSW__) && !defined(__WXUNIVERSAL__)
147 return new wxWindowsPrintDialog( parent
, data
);
148 #elif defined(__WXMAC__)
149 return new wxMacPrintDialog( parent
, data
);
151 return new wxGenericPrintDialog( parent
, data
);
155 bool wxNativePrintFactory::HasPrintSetupDialog()
157 #if defined(__WXMSW__) && !defined(__WXUNIVERSAL__)
159 #elif defined(__WXMAC__)
162 // Only here do we need to provide the print setup
163 // dialog ourselves, the other platforms either have
164 // none, don't make it accessible or let you configure
165 // the printer from the wxPrintDialog anyway.
171 wxDialog
*wxNativePrintFactory::CreatePrintSetupDialog( wxWindow
*parent
, wxPrintData
*data
)
173 #if defined(__WXMSW__) && !defined(__WXUNIVERSAL__)
177 #elif defined(__WXMAC__)
182 // Only here do we need to provide the print setup
183 // dialog ourselves, the other platforms either have
184 // none, don't make it accessible or let you configure
185 // the printer from the wxPrintDialog anyway.
186 return new wxGenericPrintSetupDialog( parent
, data
);
190 bool wxNativePrintFactory::HasOwnPrintToFile()
192 // Only relevant for PostScript and here the
193 // setup dialog provides no "print to file"
194 // option. In the GNOME setup dialog, the
195 // setup dialog has its own print to file.
199 bool wxNativePrintFactory::HasPrinterLine()
201 // Only relevant for PostScript for now
205 wxString
wxNativePrintFactory::CreatePrinterLine()
207 // Only relevant for PostScript for now
209 // We should query "lpstat -d" here
210 return _("Generic PostScript");
213 bool wxNativePrintFactory::HasStatusLine()
215 // Only relevant for PostScript for now
219 wxString
wxNativePrintFactory::CreateStatusLine()
221 // Only relevant for PostScript for now
223 // We should query "lpstat -r" or "lpstat -p" here
227 wxPrintNativeDataBase
*wxNativePrintFactory::CreatePrintNativeData()
229 #if defined(__WXMSW__) && !defined(__WXUNIVERSAL__)
230 return new wxWindowsPrintNativeData
;
231 #elif defined(__WXMAC__)
232 return new wxMacPrintNativeData
;
234 return new wxPostScriptPrintNativeData
;
238 //----------------------------------------------------------------------------
239 // wxPrintNativeDataBase
240 //----------------------------------------------------------------------------
242 IMPLEMENT_ABSTRACT_CLASS(wxPrintNativeDataBase
, wxObject
)
244 wxPrintNativeDataBase::wxPrintNativeDataBase()
249 //----------------------------------------------------------------------------
250 // wxPrintFactoryModule
251 //----------------------------------------------------------------------------
253 class wxPrintFactoryModule
: public wxModule
256 wxPrintFactoryModule() {}
257 bool OnInit() { return true; }
258 void OnExit() { wxPrintFactory::SetPrintFactory( NULL
); }
261 DECLARE_DYNAMIC_CLASS(wxPrintFactoryModule
)
264 IMPLEMENT_DYNAMIC_CLASS(wxPrintFactoryModule
, wxModule
)
266 //----------------------------------------------------------------------------
268 //----------------------------------------------------------------------------
270 IMPLEMENT_CLASS(wxPrinterBase
, wxObject
)
272 wxPrinterBase::wxPrinterBase(wxPrintDialogData
*data
)
274 m_currentPrintout
= (wxPrintout
*) NULL
;
275 sm_abortWindow
= (wxWindow
*) NULL
;
278 m_printDialogData
= (*data
);
279 sm_lastError
= wxPRINTER_NO_ERROR
;
282 wxWindow
*wxPrinterBase::sm_abortWindow
= (wxWindow
*) NULL
;
283 bool wxPrinterBase::sm_abortIt
= false;
284 wxPrinterError
wxPrinterBase::sm_lastError
= wxPRINTER_NO_ERROR
;
286 wxPrinterBase::~wxPrinterBase()
290 wxWindow
*wxPrinterBase::CreateAbortWindow(wxWindow
*parent
, wxPrintout
* printout
)
292 wxPrintAbortDialog
*dialog
= new wxPrintAbortDialog(parent
, _("Printing ") , wxDefaultPosition
, wxDefaultSize
, wxDEFAULT_DIALOG_STYLE
);
294 wxBoxSizer
*button_sizer
= new wxBoxSizer( wxVERTICAL
);
295 button_sizer
->Add( new wxStaticText(dialog
, wxID_ANY
, _("Please wait while printing\n") + printout
->GetTitle() ), 0, wxALL
, 10 );
296 button_sizer
->Add( new wxButton( dialog
, wxID_CANCEL
, wxT("Cancel") ), 0, wxALL
| wxALIGN_CENTER
, 10 );
298 dialog
->SetAutoLayout( true );
299 dialog
->SetSizer( button_sizer
);
301 button_sizer
->Fit(dialog
);
302 button_sizer
->SetSizeHints (dialog
) ;
307 void wxPrinterBase::ReportError(wxWindow
*parent
, wxPrintout
*WXUNUSED(printout
), const wxString
& message
)
309 wxMessageBox(message
, _("Printing Error"), wxOK
, parent
);
312 wxPrintDialogData
& wxPrinterBase::GetPrintDialogData() const
314 return (wxPrintDialogData
&) m_printDialogData
;
317 //----------------------------------------------------------------------------
319 //----------------------------------------------------------------------------
321 IMPLEMENT_CLASS(wxPrinter
, wxPrinterBase
)
323 wxPrinter::wxPrinter(wxPrintDialogData
*data
)
325 m_pimpl
= wxPrintFactory::GetFactory()->CreatePrinter( data
);
328 wxPrinter::~wxPrinter()
333 wxWindow
*wxPrinter::CreateAbortWindow(wxWindow
*parent
, wxPrintout
*printout
)
335 return m_pimpl
->CreateAbortWindow( parent
, printout
);
338 void wxPrinter::ReportError(wxWindow
*parent
, wxPrintout
*printout
, const wxString
& message
)
340 m_pimpl
->ReportError( parent
, printout
, message
);
343 bool wxPrinter::Setup(wxWindow
*parent
)
345 return m_pimpl
->Setup( parent
);
348 bool wxPrinter::Print(wxWindow
*parent
, wxPrintout
*printout
, bool prompt
)
350 return m_pimpl
->Print( parent
, printout
, prompt
);
353 wxDC
* wxPrinter::PrintDialog(wxWindow
*parent
)
355 return m_pimpl
->PrintDialog( parent
);
358 wxPrintDialogData
& wxPrinter::GetPrintDialogData() const
360 return m_pimpl
->GetPrintDialogData();
363 // ---------------------------------------------------------------------------
364 // wxPrintDialogBase: the common dialog for printing.
365 // ---------------------------------------------------------------------------
367 IMPLEMENT_ABSTRACT_CLASS(wxPrintDialogBase
, wxObject
)
369 wxPrintDialogBase::wxPrintDialogBase(wxWindow
*parent
,
371 const wxString
&title
,
379 title
.empty() ? wxString(_("Print")) : title
,
387 // ---------------------------------------------------------------------------
388 // wxPrintDialog: the common dialog for printing.
389 // ---------------------------------------------------------------------------
391 IMPLEMENT_CLASS(wxPrintDialog
, wxObject
)
393 wxPrintDialog::wxPrintDialog(wxWindow
*parent
, wxPrintDialogData
* data
)
395 m_pimpl
= wxPrintFactory::GetFactory()->CreatePrintDialog( parent
, data
);
398 wxPrintDialog::wxPrintDialog(wxWindow
*parent
, wxPrintData
* data
)
400 m_pimpl
= wxPrintFactory::GetFactory()->CreatePrintDialog( parent
, data
);
403 wxPrintDialog::~wxPrintDialog()
408 int wxPrintDialog::ShowModal()
410 return m_pimpl
->ShowModal();
413 wxPrintDialogData
& wxPrintDialog::GetPrintDialogData()
415 return m_pimpl
->GetPrintDialogData();
418 wxPrintData
& wxPrintDialog::GetPrintData()
420 return m_pimpl
->GetPrintData();
422 wxDC
*wxPrintDialog::GetPrintDC()
424 return m_pimpl
->GetPrintDC();
427 //----------------------------------------------------------------------------
428 // wxPrintAbortDialog
429 //----------------------------------------------------------------------------
431 BEGIN_EVENT_TABLE(wxPrintAbortDialog
, wxDialog
)
432 EVT_BUTTON(wxID_CANCEL
, wxPrintAbortDialog::OnCancel
)
435 void wxPrintAbortDialog::OnCancel(wxCommandEvent
& WXUNUSED(event
))
437 wxPrinterBase::sm_abortIt
= true;
438 wxPrinterBase::sm_abortWindow
->Show(false);
439 wxPrinterBase::sm_abortWindow
->Close(true);
440 wxPrinterBase::sm_abortWindow
= (wxWindow
*) NULL
;
443 //----------------------------------------------------------------------------
445 //----------------------------------------------------------------------------
447 IMPLEMENT_ABSTRACT_CLASS(wxPrintout
, wxObject
)
449 wxPrintout::wxPrintout(const wxString
& title
)
451 m_printoutTitle
= title
;
452 m_printoutDC
= (wxDC
*) NULL
;
455 m_pageWidthPixels
= 0;
456 m_pageHeightPixels
= 0;
464 wxPrintout::~wxPrintout()
468 bool wxPrintout::OnBeginDocument(int WXUNUSED(startPage
), int WXUNUSED(endPage
))
470 return GetDC()->StartDoc(_("Printing ") + m_printoutTitle
);
473 void wxPrintout::OnEndDocument()
478 void wxPrintout::OnBeginPrinting()
482 void wxPrintout::OnEndPrinting()
486 bool wxPrintout::HasPage(int page
)
491 void wxPrintout::GetPageInfo(int *minPage
, int *maxPage
, int *fromPage
, int *toPage
)
499 //----------------------------------------------------------------------------
501 //----------------------------------------------------------------------------
503 IMPLEMENT_CLASS(wxPreviewCanvas
, wxWindow
)
505 BEGIN_EVENT_TABLE(wxPreviewCanvas
, wxScrolledWindow
)
506 EVT_PAINT(wxPreviewCanvas::OnPaint
)
507 EVT_CHAR(wxPreviewCanvas::OnChar
)
508 EVT_SYS_COLOUR_CHANGED(wxPreviewCanvas::OnSysColourChanged
)
511 // VZ: the current code doesn't refresh properly without
512 // wxFULL_REPAINT_ON_RESIZE, this must be fixed as otherwise we have
513 // really horrible flicker when resizing the preview frame, but without
514 // this style it simply doesn't work correctly at all...
515 wxPreviewCanvas::wxPreviewCanvas(wxPrintPreviewBase
*preview
, wxWindow
*parent
,
516 const wxPoint
& pos
, const wxSize
& size
, long style
, const wxString
& name
):
517 wxScrolledWindow(parent
, wxID_ANY
, pos
, size
, style
| wxFULL_REPAINT_ON_RESIZE
, name
)
519 m_printPreview
= preview
;
521 // The app workspace colour is always white, but we should have
522 // a contrast with the page.
523 wxSystemColour colourIndex
= wxSYS_COLOUR_3DDKSHADOW
;
525 wxSystemColour colourIndex
= wxSYS_COLOUR_APPWORKSPACE
;
527 SetBackgroundColour(wxSystemSettings::GetColour(colourIndex
));
529 SetScrollbars(10, 10, 100, 100);
532 wxPreviewCanvas::~wxPreviewCanvas()
536 void wxPreviewCanvas::OnPaint(wxPaintEvent
& WXUNUSED(event
))
543 if (!GetUpdateRegion().IsEmpty())
544 dc.SetClippingRegion( GetUpdateRegion() );
550 m_printPreview
->PaintPage(this, dc
);
554 // Responds to colour changes, and passes event on to children.
555 void wxPreviewCanvas::OnSysColourChanged(wxSysColourChangedEvent
& event
)
558 // The app workspace colour is always white, but we should have
559 // a contrast with the page.
560 wxSystemColour colourIndex
= wxSYS_COLOUR_3DDKSHADOW
;
562 wxSystemColour colourIndex
= wxSYS_COLOUR_APPWORKSPACE
;
564 SetBackgroundColour(wxSystemSettings::GetColour(colourIndex
));
567 // Propagate the event to the non-top-level children
568 wxWindow::OnSysColourChanged(event
);
571 void wxPreviewCanvas::OnChar(wxKeyEvent
&event
)
573 wxPreviewControlBar
* controlBar
= ((wxPreviewFrame
*) GetParent())->GetControlBar();
574 if (event
.GetKeyCode() == WXK_ESCAPE
)
576 ((wxPreviewFrame
*) GetParent())->Close(true);
579 else if (event
.GetKeyCode() == WXK_TAB
)
581 controlBar
->OnGoto();
584 else if (event
.GetKeyCode() == WXK_RETURN
)
586 controlBar
->OnPrint();
590 if (!event
.ControlDown())
596 switch(event
.GetKeyCode())
599 controlBar
->OnNext(); break;
601 controlBar
->OnPrevious(); break;
603 controlBar
->OnFirst(); break;
605 controlBar
->OnLast(); break;
611 //----------------------------------------------------------------------------
612 // wxPreviewControlBar
613 //----------------------------------------------------------------------------
615 IMPLEMENT_CLASS(wxPreviewControlBar
, wxWindow
)
617 BEGIN_EVENT_TABLE(wxPreviewControlBar
, wxPanel
)
618 EVT_BUTTON(wxID_PREVIEW_CLOSE
, wxPreviewControlBar::OnWindowClose
)
619 EVT_BUTTON(wxID_PREVIEW_PRINT
, wxPreviewControlBar::OnPrintButton
)
620 EVT_BUTTON(wxID_PREVIEW_PREVIOUS
, wxPreviewControlBar::OnPreviousButton
)
621 EVT_BUTTON(wxID_PREVIEW_NEXT
, wxPreviewControlBar::OnNextButton
)
622 EVT_BUTTON(wxID_PREVIEW_FIRST
, wxPreviewControlBar::OnFirstButton
)
623 EVT_BUTTON(wxID_PREVIEW_LAST
, wxPreviewControlBar::OnLastButton
)
624 EVT_BUTTON(wxID_PREVIEW_GOTO
, wxPreviewControlBar::OnGotoButton
)
625 EVT_CHOICE(wxID_PREVIEW_ZOOM
, wxPreviewControlBar::OnZoom
)
626 EVT_PAINT(wxPreviewControlBar::OnPaint
)
629 wxPreviewControlBar::wxPreviewControlBar(wxPrintPreviewBase
*preview
, long buttons
,
630 wxWindow
*parent
, const wxPoint
& pos
, const wxSize
& size
,
631 long style
, const wxString
& name
):
632 wxPanel(parent
, wxID_ANY
, pos
, size
, style
, name
)
634 m_printPreview
= preview
;
635 m_closeButton
= (wxButton
*) NULL
;
636 m_nextPageButton
= (wxButton
*) NULL
;
637 m_previousPageButton
= (wxButton
*) NULL
;
638 m_printButton
= (wxButton
*) NULL
;
639 m_zoomControl
= (wxChoice
*) NULL
;
640 m_buttonFlags
= buttons
;
643 wxPreviewControlBar::~wxPreviewControlBar()
647 void wxPreviewControlBar::OnPaint(wxPaintEvent
& WXUNUSED(event
))
653 dc
.SetPen(*wxBLACK_PEN
);
654 dc
.SetBrush(*wxTRANSPARENT_BRUSH
);
655 dc
.DrawLine( 0, h
-1, w
, h
-1 );
658 void wxPreviewControlBar::OnWindowClose(wxCommandEvent
& WXUNUSED(event
))
660 wxPreviewFrame
*frame
= (wxPreviewFrame
*)GetParent();
664 void wxPreviewControlBar::OnPrint(void)
666 wxPrintPreviewBase
*preview
= GetPrintPreview();
667 preview
->Print(true);
670 void wxPreviewControlBar::OnNext(void)
672 wxPrintPreviewBase
*preview
= GetPrintPreview();
675 int currentPage
= preview
->GetCurrentPage();
676 if ((preview
->GetMaxPage() > 0) &&
677 (currentPage
< preview
->GetMaxPage()) &&
678 preview
->GetPrintout()->HasPage(currentPage
+ 1))
680 preview
->SetCurrentPage(currentPage
+ 1);
685 void wxPreviewControlBar::OnPrevious(void)
687 wxPrintPreviewBase
*preview
= GetPrintPreview();
690 int currentPage
= preview
->GetCurrentPage();
691 if ((preview
->GetMinPage() > 0) &&
692 (currentPage
> preview
->GetMinPage()) &&
693 preview
->GetPrintout()->HasPage(currentPage
- 1))
695 preview
->SetCurrentPage(currentPage
- 1);
700 void wxPreviewControlBar::OnFirst(void)
702 wxPrintPreviewBase
*preview
= GetPrintPreview();
705 int currentPage
= preview
->GetMinPage();
706 if (preview
->GetPrintout()->HasPage(currentPage
))
708 preview
->SetCurrentPage(currentPage
);
713 void wxPreviewControlBar::OnLast(void)
715 wxPrintPreviewBase
*preview
= GetPrintPreview();
718 int currentPage
= preview
->GetMaxPage();
719 if (preview
->GetPrintout()->HasPage(currentPage
))
721 preview
->SetCurrentPage(currentPage
);
726 void wxPreviewControlBar::OnGoto(void)
728 wxPrintPreviewBase
*preview
= GetPrintPreview();
733 if (preview
->GetMinPage() > 0)
738 strPrompt
.Printf( _("Enter a page number between %d and %d:"),
739 preview
->GetMinPage(), preview
->GetMaxPage());
740 strPage
.Printf( wxT("%d"), preview
->GetCurrentPage() );
743 wxGetTextFromUser( strPrompt
, _("Goto Page"), strPage
, GetParent());
745 if ( strPage
.ToLong( ¤tPage
) )
746 if (preview
->GetPrintout()->HasPage(currentPage
))
748 preview
->SetCurrentPage(currentPage
);
754 void wxPreviewControlBar::OnZoom(wxCommandEvent
& WXUNUSED(event
))
756 int zoom
= GetZoomControl();
757 if (GetPrintPreview())
758 GetPrintPreview()->SetZoom(zoom
);
761 void wxPreviewControlBar::CreateButtons()
763 SetSize(0, 0, 400, 40);
765 wxBoxSizer
*item0
= new wxBoxSizer( wxHORIZONTAL
);
767 m_closeButton
= new wxButton( this, wxID_PREVIEW_CLOSE
, _("&Close"), wxDefaultPosition
, wxDefaultSize
, 0 );
768 item0
->Add( m_closeButton
, 0, wxALIGN_CENTRE
|wxALL
, 5 );
770 if (m_buttonFlags
& wxPREVIEW_PRINT
)
772 m_printButton
= new wxButton( this, wxID_PREVIEW_PRINT
, _("&Print..."), wxDefaultPosition
, wxDefaultSize
, 0 );
773 item0
->Add( m_printButton
, 0, wxALIGN_CENTRE
|wxALL
, 5 );
776 if (m_buttonFlags
& wxPREVIEW_FIRST
)
778 m_firstPageButton
= new wxButton( this, wxID_PREVIEW_FIRST
, _("|<<"), wxDefaultPosition
, wxDefaultSize
, wxBU_EXACTFIT
);
779 item0
->Add( m_firstPageButton
, 0, wxALIGN_CENTRE
|wxALL
, 5 );
782 if (m_buttonFlags
& wxPREVIEW_PREVIOUS
)
784 m_previousPageButton
= new wxButton( this, wxID_PREVIEW_PREVIOUS
, _("<<"), wxDefaultPosition
, wxDefaultSize
, wxBU_EXACTFIT
);
785 item0
->Add( m_previousPageButton
, 0, wxALIGN_CENTRE
|wxRIGHT
|wxTOP
|wxBOTTOM
, 5 );
788 if (m_buttonFlags
& wxPREVIEW_NEXT
)
790 m_nextPageButton
= new wxButton( this, wxID_PREVIEW_NEXT
, _(">>"), wxDefaultPosition
, wxDefaultSize
, wxBU_EXACTFIT
);
791 item0
->Add( m_nextPageButton
, 0, wxALIGN_CENTRE
|wxRIGHT
|wxTOP
|wxBOTTOM
, 5 );
794 if (m_buttonFlags
& wxPREVIEW_LAST
)
796 m_lastPageButton
= new wxButton( this, wxID_PREVIEW_LAST
, _(">>|"), wxDefaultPosition
, wxDefaultSize
, wxBU_EXACTFIT
);
797 item0
->Add( m_lastPageButton
, 0, wxALIGN_CENTRE
|wxRIGHT
|wxTOP
|wxBOTTOM
, 5 );
800 if (m_buttonFlags
& wxPREVIEW_GOTO
)
802 m_gotoPageButton
= new wxButton( this, wxID_PREVIEW_GOTO
, _("&Goto..."), wxDefaultPosition
, wxDefaultSize
, 0 );
803 item0
->Add( m_gotoPageButton
, 0, wxALIGN_CENTRE
|wxALL
, 5 );
806 if (m_buttonFlags
& wxPREVIEW_ZOOM
)
810 wxT("10%"), wxT("15%"), wxT("20%"), wxT("25%"), wxT("30%"), wxT("35%"), wxT("40%"), wxT("45%"), wxT("50%"), wxT("55%"),
811 wxT("60%"), wxT("65%"), wxT("70%"), wxT("75%"), wxT("80%"), wxT("85%"), wxT("90%"), wxT("95%"), wxT("100%"), wxT("110%"),
812 wxT("120%"), wxT("150%"), wxT("200%")
814 int n
= WXSIZEOF(choices
);
816 m_zoomControl
= new wxChoice( this, wxID_PREVIEW_ZOOM
, wxDefaultPosition
, wxSize(70,wxDefaultCoord
), n
, choices
, 0 );
817 item0
->Add( m_zoomControl
, 0, wxALIGN_CENTRE
|wxALL
, 5 );
818 SetZoomControl(m_printPreview
->GetZoom());
825 void wxPreviewControlBar::SetZoomControl(int zoom
)
829 int n
, count
= m_zoomControl
->GetCount();
831 for (n
=0; n
<count
; n
++)
833 if (m_zoomControl
->GetString(n
).BeforeFirst(wxT('%')).ToLong(&val
) &&
836 m_zoomControl
->SetSelection(n
);
841 m_zoomControl
->SetSelection(count
-1);
845 int wxPreviewControlBar::GetZoomControl()
847 if (m_zoomControl
&& (m_zoomControl
->GetStringSelection() != wxEmptyString
))
850 if (m_zoomControl
->GetStringSelection().BeforeFirst(wxT('%')).ToLong(&val
))
862 IMPLEMENT_CLASS(wxPreviewFrame
, wxFrame
)
864 BEGIN_EVENT_TABLE(wxPreviewFrame
, wxFrame
)
865 EVT_CLOSE(wxPreviewFrame::OnCloseWindow
)
868 wxPreviewFrame::wxPreviewFrame(wxPrintPreviewBase
*preview
, wxWindow
*parent
, const wxString
& title
,
869 const wxPoint
& pos
, const wxSize
& size
, long style
, const wxString
& name
):
870 wxFrame(parent
, wxID_ANY
, title
, pos
, size
, style
, name
)
872 m_printPreview
= preview
;
874 m_previewCanvas
= NULL
;
875 m_windowDisabler
= NULL
;
877 // Give the application icon
879 wxFrame
* topFrame
= wxDynamicCast(wxTheApp
->GetTopWindow(), wxFrame
);
881 SetIcon(topFrame
->GetIcon());
885 wxPreviewFrame::~wxPreviewFrame()
889 void wxPreviewFrame::OnCloseWindow(wxCloseEvent
& WXUNUSED(event
))
891 if (m_windowDisabler
)
892 delete m_windowDisabler
;
894 // Need to delete the printout and the print preview
895 wxPrintout
*printout
= m_printPreview
->GetPrintout();
899 m_printPreview
->SetPrintout(NULL
);
900 m_printPreview
->SetCanvas(NULL
);
901 m_printPreview
->SetFrame(NULL
);
903 delete m_printPreview
;
908 void wxPreviewFrame::Initialize()
916 m_printPreview
->SetCanvas(m_previewCanvas
);
917 m_printPreview
->SetFrame(this);
919 wxBoxSizer
*item0
= new wxBoxSizer( wxVERTICAL
);
921 item0
->Add( m_controlBar
, 0, wxGROW
|wxALIGN_CENTER_VERTICAL
, 5 );
922 item0
->Add( m_previewCanvas
, 1, wxGROW
|wxALIGN_CENTER_VERTICAL
, 5 );
924 SetAutoLayout( true );
927 m_windowDisabler
= new wxWindowDisabler(this);
931 m_printPreview
->AdjustScrollbars(m_previewCanvas
);
932 m_previewCanvas
->SetFocus();
933 m_controlBar
->SetFocus();
936 void wxPreviewFrame::CreateCanvas()
938 m_previewCanvas
= new wxPreviewCanvas(m_printPreview
, this);
941 void wxPreviewFrame::CreateControlBar()
943 long buttons
= wxPREVIEW_DEFAULT
;
944 if (m_printPreview
->GetPrintoutForPrinting())
945 buttons
|= wxPREVIEW_PRINT
;
947 m_controlBar
= new wxPreviewControlBar(m_printPreview
, buttons
, this, wxPoint(0, 0), wxSize(400, 40));
948 m_controlBar
->CreateButtons();
955 wxPrintPreviewBase::wxPrintPreviewBase(wxPrintout
*printout
,
956 wxPrintout
*printoutForPrinting
,
960 m_printDialogData
= (*data
);
962 Init(printout
, printoutForPrinting
);
965 wxPrintPreviewBase::wxPrintPreviewBase(wxPrintout
*printout
,
966 wxPrintout
*printoutForPrinting
,
967 wxPrintDialogData
*data
)
970 m_printDialogData
= (*data
);
972 Init(printout
, printoutForPrinting
);
975 void wxPrintPreviewBase::Init(wxPrintout
*printout
,
976 wxPrintout
*printoutForPrinting
)
979 m_previewPrintout
= printout
;
980 if (m_previewPrintout
)
981 m_previewPrintout
->SetIsPreview(true);
983 m_printPrintout
= printoutForPrinting
;
985 m_previewCanvas
= NULL
;
986 m_previewFrame
= NULL
;
987 m_previewBitmap
= NULL
;
994 m_printingPrepared
= false;
999 wxPrintPreviewBase::~wxPrintPreviewBase()
1001 if (m_previewPrintout
)
1002 delete m_previewPrintout
;
1003 if (m_previewBitmap
)
1004 delete m_previewBitmap
;
1005 if (m_printPrintout
)
1006 delete m_printPrintout
;
1009 bool wxPrintPreviewBase::SetCurrentPage(int pageNum
)
1011 if (m_currentPage
== pageNum
)
1014 m_currentPage
= pageNum
;
1015 if (m_previewBitmap
)
1017 delete m_previewBitmap
;
1018 m_previewBitmap
= NULL
;
1021 if (m_previewCanvas
)
1023 AdjustScrollbars(m_previewCanvas
);
1025 if (!RenderPage(pageNum
))
1027 m_previewCanvas
->Refresh();
1028 m_previewCanvas
->SetFocus();
1033 int wxPrintPreviewBase::GetCurrentPage() const
1034 { return m_currentPage
; };
1035 void wxPrintPreviewBase::SetPrintout(wxPrintout
*printout
)
1036 { m_previewPrintout
= printout
; };
1037 wxPrintout
*wxPrintPreviewBase::GetPrintout() const
1038 { return m_previewPrintout
; };
1039 wxPrintout
*wxPrintPreviewBase::GetPrintoutForPrinting() const
1040 { return m_printPrintout
; };
1041 void wxPrintPreviewBase::SetFrame(wxFrame
*frame
)
1042 { m_previewFrame
= frame
; };
1043 void wxPrintPreviewBase::SetCanvas(wxPreviewCanvas
*canvas
)
1044 { m_previewCanvas
= canvas
; };
1045 wxFrame
*wxPrintPreviewBase::GetFrame() const
1046 { return m_previewFrame
; }
1047 wxPreviewCanvas
*wxPrintPreviewBase::GetCanvas() const
1048 { return m_previewCanvas
; }
1050 bool wxPrintPreviewBase::PaintPage(wxPreviewCanvas
*canvas
, wxDC
& dc
)
1052 DrawBlankPage(canvas
, dc
);
1054 if (!m_previewBitmap
)
1055 if (!RenderPage(m_currentPage
))
1058 if (!m_previewBitmap
)
1064 int canvasWidth
, canvasHeight
;
1065 canvas
->GetSize(&canvasWidth
, &canvasHeight
);
1067 double zoomScale
= ((float)m_currentZoom
/(float)100);
1068 double actualWidth
= (zoomScale
*m_pageWidth
*m_previewScale
);
1069 // float actualHeight = (float)(zoomScale*m_pageHeight*m_previewScale);
1071 int x
= (int) ((canvasWidth
- actualWidth
)/2.0);
1072 if (x
< m_leftMargin
)
1074 int y
= m_topMargin
;
1077 temp_dc
.SelectObject(*m_previewBitmap
);
1079 dc
.Blit(x
, y
, m_previewBitmap
->GetWidth(), m_previewBitmap
->GetHeight(), &temp_dc
, 0, 0);
1081 temp_dc
.SelectObject(wxNullBitmap
);
1086 // Adjusts the scrollbars for the current scale
1087 void wxPrintPreviewBase::AdjustScrollbars(wxPreviewCanvas
*canvas
)
1092 int canvasWidth
, canvasHeight
;
1093 canvas
->GetSize(&canvasWidth
, &canvasHeight
);
1095 double zoomScale
= ((float)m_currentZoom
/(float)100);
1096 double actualWidth
= (zoomScale
*m_pageWidth
*m_previewScale
);
1097 double actualHeight
= (zoomScale
*m_pageHeight
*m_previewScale
);
1099 // Set the scrollbars appropriately
1100 int totalWidth
= (int)(actualWidth
+ 2*m_leftMargin
);
1101 int totalHeight
= (int)(actualHeight
+ 2*m_topMargin
);
1102 int scrollUnitsX
= totalWidth
/10;
1103 int scrollUnitsY
= totalHeight
/10;
1104 wxSize virtualSize
= canvas
->GetVirtualSize();
1105 if (virtualSize
.GetWidth() != totalWidth
|| virtualSize
.GetHeight() != totalHeight
)
1106 canvas
->SetScrollbars(10, 10, scrollUnitsX
, scrollUnitsY
, 0, 0, true);
1109 bool wxPrintPreviewBase::RenderPage(int pageNum
)
1113 int canvasWidth
, canvasHeight
;
1115 if (!m_previewCanvas
)
1117 wxFAIL_MSG(_T("wxPrintPreviewBase::RenderPage: must use wxPrintPreviewBase::SetCanvas to let me know about the canvas!"));
1121 m_previewCanvas
->GetSize(&canvasWidth
, &canvasHeight
);
1123 double zoomScale
= (m_currentZoom
/100.0);
1124 int actualWidth
= (int)(zoomScale
*m_pageWidth
*m_previewScale
);
1125 int actualHeight
= (int)(zoomScale
*m_pageHeight
*m_previewScale
);
1127 if (!m_previewBitmap
)
1129 m_previewBitmap
= new wxBitmap((int)actualWidth
, (int)actualHeight
);
1130 if (!m_previewBitmap
|| !m_previewBitmap
->Ok())
1132 if (m_previewBitmap
) {
1133 delete m_previewBitmap
;
1134 m_previewBitmap
= NULL
;
1136 wxMessageBox(_("Sorry, not enough memory to create a preview."), _("Print Preview Failure"), wxOK
);
1141 wxMemoryDC memoryDC
;
1142 memoryDC
.SelectObject(*m_previewBitmap
);
1146 m_previewPrintout
->SetDC(&memoryDC
);
1147 m_previewPrintout
->SetPageSizePixels(m_pageWidth
, m_pageHeight
);
1149 // Need to delay OnPreparePrinting until here, so we have enough information.
1150 if (!m_printingPrepared
)
1152 m_previewPrintout
->OnPreparePrinting();
1154 m_previewPrintout
->GetPageInfo(&m_minPage
, &m_maxPage
, &selFrom
, &selTo
);
1155 m_printingPrepared
= true;
1158 m_previewPrintout
->OnBeginPrinting();
1160 if (!m_previewPrintout
->OnBeginDocument(m_printDialogData
.GetFromPage(), m_printDialogData
.GetToPage()))
1162 wxMessageBox(_("Could not start document preview."), _("Print Preview Failure"), wxOK
);
1164 memoryDC
.SelectObject(wxNullBitmap
);
1166 delete m_previewBitmap
;
1167 m_previewBitmap
= NULL
;
1171 m_previewPrintout
->OnPrintPage(pageNum
);
1172 m_previewPrintout
->OnEndDocument();
1173 m_previewPrintout
->OnEndPrinting();
1175 m_previewPrintout
->SetDC(NULL
);
1177 memoryDC
.SelectObject(wxNullBitmap
);
1182 status
= wxString::Format(_("Page %d of %d"), pageNum
, m_maxPage
);
1184 status
= wxString::Format(_("Page %d"), pageNum
);
1187 m_previewFrame
->SetStatusText(status
);
1194 bool wxPrintPreviewBase::DrawBlankPage(wxPreviewCanvas
*canvas
, wxDC
& dc
)
1196 int canvasWidth
, canvasHeight
;
1197 canvas
->GetSize(&canvasWidth
, &canvasHeight
);
1199 float zoomScale
= (float)((float)m_currentZoom
/(float)100);
1200 float actualWidth
= zoomScale
*m_pageWidth
*m_previewScale
;
1201 float actualHeight
= zoomScale
*m_pageHeight
*m_previewScale
;
1203 float x
= (float)((canvasWidth
- actualWidth
)/2.0);
1204 if (x
< m_leftMargin
)
1205 x
= (float)m_leftMargin
;
1206 float y
= (float)m_topMargin
;
1208 // Draw shadow, allowing for 1-pixel border AROUND the actual page
1209 int shadowOffset
= 4;
1210 dc
.SetPen(*wxBLACK_PEN
);
1211 dc
.SetBrush(*wxBLACK_BRUSH
);
1213 dc.DrawRectangle((int)(x-1 + shadowOffset), (int)(y-1 + shadowOffset), (int)(actualWidth+2), (int)(actualHeight+2));
1215 dc
.DrawRectangle((int)(x
+ shadowOffset
), (int)(y
+ actualHeight
+1), (int)(actualWidth
), shadowOffset
);
1216 dc
.DrawRectangle((int)(x
+ actualWidth
), (int)(y
+ shadowOffset
), shadowOffset
, (int)(actualHeight
));
1218 // Draw blank page allowing for 1-pixel border AROUND the actual page
1219 dc
.SetPen(*wxBLACK_PEN
);
1220 dc
.SetBrush(*wxWHITE_BRUSH
);
1223 wxRegion update_region = canvas->GetUpdateRegion();
1224 wxRect r = update_region.GetBox();
1226 printf( "x: %d y: %d w: %d h: %d.\n", (int)r.x, (int)r.y, (int)r.width, (int)r.height );
1229 dc
.DrawRectangle((int)(x
-2), (int)(y
-1), (int)(actualWidth
+3), (int)(actualHeight
+2));
1234 void wxPrintPreviewBase::SetZoom(int percent
)
1236 if (m_currentZoom
== percent
)
1239 m_currentZoom
= percent
;
1240 if (m_previewBitmap
)
1242 delete m_previewBitmap
;
1243 m_previewBitmap
= NULL
;
1246 if (m_previewCanvas
)
1248 AdjustScrollbars(m_previewCanvas
);
1249 RenderPage(m_currentPage
);
1250 ((wxScrolledWindow
*) m_previewCanvas
)->Scroll(0, 0);
1251 m_previewCanvas
->ClearBackground();
1252 m_previewCanvas
->Refresh();
1253 m_previewCanvas
->SetFocus();
1257 wxPrintDialogData
& wxPrintPreviewBase::GetPrintDialogData()
1259 return m_printDialogData
;
1262 int wxPrintPreviewBase::GetZoom() const
1263 { return m_currentZoom
; }
1264 int wxPrintPreviewBase::GetMaxPage() const
1265 { return m_maxPage
; }
1266 int wxPrintPreviewBase::GetMinPage() const
1267 { return m_minPage
; }
1268 bool wxPrintPreviewBase::Ok() const
1270 void wxPrintPreviewBase::SetOk(bool ok
)
1272 //----------------------------------------------------------------------------
1274 //----------------------------------------------------------------------------
1276 IMPLEMENT_CLASS(wxPrintPreview
, wxPrintPreviewBase
)
1278 wxPrintPreview::wxPrintPreview(wxPrintout
*printout
,
1279 wxPrintout
*printoutForPrinting
,
1280 wxPrintDialogData
*data
) :
1281 wxPrintPreviewBase( printout
, printoutForPrinting
, data
)
1283 m_pimpl
= wxPrintFactory::GetFactory()->
1284 CreatePrintPreview( printout
, printoutForPrinting
, data
);
1287 wxPrintPreview::wxPrintPreview(wxPrintout
*printout
,
1288 wxPrintout
*printoutForPrinting
,
1289 wxPrintData
*data
) :
1290 wxPrintPreviewBase( printout
, printoutForPrinting
, data
)
1292 m_pimpl
= wxPrintFactory::GetFactory()->
1293 CreatePrintPreview( printout
, printoutForPrinting
, data
);
1296 wxPrintPreview::~wxPrintPreview()
1300 // don't delete twice
1301 m_printPrintout
= NULL
;
1302 m_previewPrintout
= NULL
;
1303 m_previewBitmap
= NULL
;
1306 bool wxPrintPreview::SetCurrentPage(int pageNum
)
1308 return m_pimpl
->SetCurrentPage( pageNum
);
1311 int wxPrintPreview::GetCurrentPage() const
1313 return m_pimpl
->GetCurrentPage();
1316 void wxPrintPreview::SetPrintout(wxPrintout
*printout
)
1318 m_pimpl
->SetPrintout( printout
);
1321 wxPrintout
*wxPrintPreview::GetPrintout() const
1323 return m_pimpl
->GetPrintout();
1326 wxPrintout
*wxPrintPreview::GetPrintoutForPrinting() const
1328 return m_pimpl
->GetPrintoutForPrinting();
1331 void wxPrintPreview::SetFrame(wxFrame
*frame
)
1333 m_pimpl
->SetFrame( frame
);
1336 void wxPrintPreview::SetCanvas(wxPreviewCanvas
*canvas
)
1338 m_pimpl
->SetCanvas( canvas
);
1341 wxFrame
*wxPrintPreview::GetFrame() const
1343 return m_pimpl
->GetFrame();
1346 wxPreviewCanvas
*wxPrintPreview::GetCanvas() const
1348 return m_pimpl
->GetCanvas();
1351 bool wxPrintPreview::PaintPage(wxPreviewCanvas
*canvas
, wxDC
& dc
)
1353 return m_pimpl
->PaintPage( canvas
, dc
);
1356 bool wxPrintPreview::DrawBlankPage(wxPreviewCanvas
*canvas
, wxDC
& dc
)
1358 return m_pimpl
->DrawBlankPage( canvas
, dc
);
1361 void wxPrintPreview::AdjustScrollbars(wxPreviewCanvas
*canvas
)
1363 m_pimpl
->AdjustScrollbars( canvas
);
1366 bool wxPrintPreview::RenderPage(int pageNum
)
1368 return m_pimpl
->RenderPage( pageNum
);
1371 void wxPrintPreview::SetZoom(int percent
)
1373 m_pimpl
->SetZoom( percent
);
1376 wxPrintDialogData
& wxPrintPreview::GetPrintDialogData()
1378 return m_pimpl
->GetPrintDialogData();
1381 int wxPrintPreview::GetMaxPage() const
1383 return m_pimpl
->GetMaxPage();
1386 int wxPrintPreview::GetMinPage() const
1388 return m_pimpl
->GetMinPage();
1391 bool wxPrintPreview::Ok() const
1393 return m_pimpl
->Ok();
1396 void wxPrintPreview::SetOk(bool ok
)
1398 m_pimpl
->SetOk( ok
);
1401 bool wxPrintPreview::Print(bool interactive
)
1403 return m_pimpl
->Print( interactive
);
1406 void wxPrintPreview::DetermineScaling()
1408 m_pimpl
->DetermineScaling();
1412 #endif // wxUSE_PRINTING_ARCHITECTURE