Many changes to the printing classes.
[wxWidgets.git] / src / generic / printps.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: printps.cpp
3 // Purpose: Postscript print/preview framework
4 // Author: Julian Smart
5 // Modified by:
6 // Created: 04/01/98
7 // RCS-ID: $Id$
8 // Copyright: (c) Julian Smart and Markus Holzem
9 // Licence: wxWindows license
10 /////////////////////////////////////////////////////////////////////////////
11
12 #ifdef __GNUG__
13 #pragma implementation "printps.h"
14 #endif
15
16 // For compilers that support precompilation, includes "wx.h".
17 #include "wx/wxprec.h"
18
19 #ifdef __BORLANDC__
20 #pragma hdrstop
21 #endif
22
23 #include "wx/defs.h"
24
25 #ifndef WX_PRECOMP
26 #include "wx/utils.h"
27 #include "wx/dc.h"
28 #include "wx/app.h"
29 #include "wx/msgdlg.h"
30 #include <wx/intl.h>
31 #endif
32
33 #include "wx/generic/printps.h"
34 #include "wx/dcprint.h"
35 #include "wx/printdlg.h"
36 #include "wx/generic/prntdlgg.h"
37 #include "wx/paper.h"
38
39 #include <stdlib.h>
40
41 #if !USE_SHARED_LIBRARY
42 IMPLEMENT_DYNAMIC_CLASS(wxPostScriptPrinter, wxPrinterBase)
43 IMPLEMENT_CLASS(wxPostScriptPrintPreview, wxPrintPreviewBase)
44 #endif
45
46 /*
47 * Printer
48 */
49
50 wxPostScriptPrinter::wxPostScriptPrinter(wxPrintDialogData *data):
51 wxPrinterBase(data)
52 {
53 }
54
55 wxPostScriptPrinter::~wxPostScriptPrinter(void)
56 {
57 }
58
59 bool wxPostScriptPrinter::Print(wxWindow *parent, wxPrintout *printout, bool prompt)
60 {
61 sm_abortIt = FALSE;
62 sm_abortWindow = (wxWindow *) NULL;
63
64 if (!printout)
65 return FALSE;
66
67 printout->SetIsPreview(FALSE);
68 printout->OnPreparePrinting();
69
70 // Get some parameters from the printout, if defined
71 int fromPage, toPage;
72 int minPage, maxPage;
73 printout->GetPageInfo(&minPage, &maxPage, &fromPage, &toPage);
74
75 if (maxPage == 0)
76 return FALSE;
77
78 m_printDialogData.SetMinPage(minPage);
79 m_printDialogData.SetMaxPage(maxPage);
80 if (fromPage != 0)
81 m_printDialogData.SetFromPage(fromPage);
82 if (toPage != 0)
83 m_printDialogData.SetToPage(toPage);
84
85 if (minPage != 0)
86 {
87 m_printDialogData.EnablePageNumbers(TRUE);
88 if (m_printDialogData.GetFromPage() < m_printDialogData.GetMinPage())
89 m_printDialogData.SetFromPage(m_printDialogData.GetMinPage());
90 else if (m_printDialogData.GetFromPage() > m_printDialogData.GetMaxPage())
91 m_printDialogData.SetFromPage(m_printDialogData.GetMaxPage());
92 if (m_printDialogData.GetToPage() > m_printDialogData.GetMaxPage())
93 m_printDialogData.SetToPage(m_printDialogData.GetMaxPage());
94 else if (m_printDialogData.GetToPage() < m_printDialogData.GetMinPage())
95 m_printDialogData.SetToPage(m_printDialogData.GetMinPage());
96 }
97 else
98 m_printDialogData.EnablePageNumbers(FALSE);
99
100 // Create a suitable device context
101 wxDC *dc = (wxDC *) NULL;
102 if (prompt)
103 {
104 dc = PrintDialog(parent);
105 if (!dc)
106 return FALSE;
107 }
108 else
109 {
110 dc = new wxPostScriptDC(wxThePrintSetupData->GetPrinterFile(), FALSE, (wxWindow *) NULL);
111 }
112
113 // May have pressed cancel.
114 if (!dc || !dc->Ok())
115 {
116 if (dc) delete dc;
117 return FALSE;
118 }
119
120 int logPPIScreenX = 0;
121 int logPPIScreenY = 0;
122 int logPPIPrinterX = 0;
123 int logPPIPrinterY = 0;
124
125 logPPIScreenX = 100;
126 logPPIScreenY = 100;
127
128 /*
129 // Correct values for X/PostScript?
130 logPPIPrinterX = 100;
131 logPPIPrinterY = 100;
132 */
133
134 logPPIPrinterX = 72;
135 logPPIPrinterY = 72;
136
137 printout->SetPPIScreen(logPPIScreenX, logPPIScreenY);
138 printout->SetPPIPrinter(logPPIPrinterX, logPPIPrinterY);
139
140 // Set printout parameters
141 printout->SetDC(dc);
142
143 int w, h;
144 dc->GetSize(&w, &h);
145 printout->SetPageSizePixels((int)w, (int)h);
146 dc->GetSizeMM(&w, &h);
147 printout->SetPageSizeMM((int)w, (int)h);
148
149 // Create an abort window
150 wxBeginBusyCursor();
151
152 printout->OnBeginPrinting();
153
154 bool keepGoing = TRUE;
155
156 int copyCount;
157 for (copyCount = 1; copyCount <= m_printDialogData.GetNoCopies(); copyCount ++)
158 {
159 if (!printout->OnBeginDocument(m_printDialogData.GetFromPage(), m_printDialogData.GetToPage()))
160 {
161 wxEndBusyCursor();
162 wxMessageBox(_("Could not start printing."), _("Print Error"), wxOK, parent);
163 break;
164 }
165 if (sm_abortIt)
166 break;
167
168 int pn;
169 for (pn = m_printDialogData.GetFromPage(); keepGoing && (pn <= m_printDialogData.GetToPage()) && printout->HasPage(pn);
170 pn++)
171 {
172 if (sm_abortIt)
173 {
174 keepGoing = FALSE;
175 break;
176 }
177 else
178 {
179 dc->StartPage();
180 printout->OnPrintPage(pn);
181 dc->EndPage();
182 }
183 }
184 printout->OnEndDocument();
185 }
186
187 printout->OnEndPrinting();
188
189 wxEndBusyCursor();
190
191 delete dc;
192
193 return TRUE;
194 }
195
196 wxDC* wxPostScriptPrinter::PrintDialog(wxWindow *parent)
197 {
198 wxDC* dc = (wxDC*) NULL;
199 wxGenericPrintDialog* dialog = new wxGenericPrintDialog(parent, & m_printDialogData);
200 int ret = dialog->ShowModal() ;
201 if (ret == wxID_OK)
202 {
203 dc = dialog->GetPrintDC();
204 m_printDialogData = dialog->GetPrintDialogData();
205 }
206 dialog->Destroy();
207
208 return dc;
209 }
210
211 bool wxPostScriptPrinter::Setup(wxWindow *parent)
212 {
213 wxGenericPrintDialog* dialog = new wxGenericPrintDialog(parent, & m_printDialogData);
214 dialog->GetPrintDialogData().SetSetupDialog(TRUE);
215
216 int ret = dialog->ShowModal();
217
218 if (ret == wxID_OK)
219 {
220 m_printDialogData = dialog->GetPrintDialogData();
221 }
222
223 dialog->Destroy();
224
225 return (ret == wxID_OK);
226 }
227
228 /*
229 * Print preview
230 */
231
232 wxPostScriptPrintPreview::wxPostScriptPrintPreview(wxPrintout *printout, wxPrintout *printoutForPrinting, wxPrintDialogData *data):
233 wxPrintPreviewBase(printout, printoutForPrinting, data)
234 {
235 // Have to call it here since base constructor can't call it
236 DetermineScaling();
237 }
238
239 wxPostScriptPrintPreview::~wxPostScriptPrintPreview(void)
240 {
241 }
242
243 bool wxPostScriptPrintPreview::Print(bool interactive)
244 {
245 if (!m_printPrintout)
246 return FALSE;
247 wxPostScriptPrinter printer(& m_printDialogData);
248 return printer.Print(m_previewFrame, m_printPrintout, interactive);
249 }
250
251 void wxPostScriptPrintPreview::DetermineScaling(void)
252 {
253 wxPaperSize paperType = m_printDialogData.GetPrintData().GetPaperId();
254 if (paperType == wxPAPER_NONE)
255 paperType = wxPAPER_NONE;
256
257 wxPrintPaperType *paper = wxThePrintPaperDatabase->FindPaperType(paperType);
258 if (!paper)
259 paper = wxThePrintPaperDatabase->FindPaperType(wxPAPER_A4);
260
261 if (paper)
262 {
263 m_previewPrintout->SetPPIScreen(100, 100);
264 // m_previewPrintout->SetPPIPrinter(100, 100);
265 m_previewPrintout->SetPPIPrinter(72, 72);
266
267 wxSize sizeDevUnits(paper->GetSizeDeviceUnits());
268 wxSize sizeTenthsMM(paper->GetSize());
269 wxSize sizeMM(sizeTenthsMM.x / 10, sizeTenthsMM.y / 10);
270
271 // If in landscape mode, we need to swap the width and height.
272 if ( m_printDialogData.GetPrintData().GetOrientation() == wxLANDSCAPE )
273 {
274 m_pageWidth = sizeDevUnits.y;
275 m_pageHeight = sizeDevUnits.x;
276 m_previewPrintout->SetPageSizeMM(sizeMM.y, sizeMM.x);
277 m_previewPrintout->SetPageSizePixels(m_pageWidth, m_pageHeight);
278 }
279 else
280 {
281 m_pageWidth = sizeDevUnits.x;
282 m_pageHeight = sizeDevUnits.y;
283 m_previewPrintout->SetPageSizeMM(sizeMM.x, sizeMM.y);
284 m_previewPrintout->SetPageSizePixels(m_pageWidth, m_pageHeight);
285 }
286
287 // At 100%, the page should look about page-size on the screen.
288 m_previewScale = (float)0.8;
289 }
290 }
291