]>
git.saurik.com Git - wxWidgets.git/blob - src/html/htmprint.cpp
1 /////////////////////////////////////////////////////////////////////////////
3 // Purpose: html printing classes
4 // Author: Vaclav Slavik
7 // Copyright: (c) Vaclav Slavik, 1999
8 // Licence: wxWindows licence
9 /////////////////////////////////////////////////////////////////////////////
13 #pragma implementation
16 // For compilers that support precompilation, includes "wx/wx.h".
17 #include "wx/wxprec.h"
29 #if wxUSE_HTML && wxUSE_PRINTING_ARCHITECTURE && wxUSE_STREAMS
32 #include "wx/printdlg.h"
33 #include "wx/html/htmprint.h"
34 #include "wx/wxhtml.h"
35 #include "wx/wfstream.h"
38 //--------------------------------------------------------------------------------
40 //--------------------------------------------------------------------------------
43 wxHtmlDCRenderer::wxHtmlDCRenderer() : wxObject()
46 m_Width
= m_Height
= 0;
48 m_Parser
= new wxHtmlWinParser(NULL
);
49 m_FS
= new wxFileSystem();
50 m_Parser
-> SetFS(m_FS
);
55 wxHtmlDCRenderer::~wxHtmlDCRenderer()
57 if (m_Cells
) delete m_Cells
;
58 if (m_Parser
) delete m_Parser
;
59 if (m_FS
) delete m_FS
;
64 void wxHtmlDCRenderer::SetDC(wxDC
*dc
, double pixel_scale
)
67 m_Parser
-> SetDC(m_DC
, pixel_scale
);
72 void wxHtmlDCRenderer::SetSize(int width
, int height
)
80 void wxHtmlDCRenderer::SetHtmlText(const wxString
& html
, const wxString
& basepath
, bool isdir
)
82 if (m_DC
== NULL
) return;
84 if (m_Cells
!= NULL
) delete m_Cells
;
86 m_FS
-> ChangePathTo(basepath
, isdir
);
87 m_Cells
= (wxHtmlContainerCell
*) m_Parser
-> Parse(html
);
88 m_Cells
-> SetIndent(0, wxHTML_INDENT_ALL
, wxHTML_UNITS_PIXELS
);
89 m_Cells
-> Layout(m_Width
);
94 int wxHtmlDCRenderer::Render(int x
, int y
, int from
, int dont_render
)
98 if (m_Cells
== NULL
|| m_DC
== NULL
) return 0;
100 pbreak
= (int)(from
+ m_Height
);
101 while (m_Cells
-> AdjustPagebreak(&pbreak
)) {}
102 hght
= pbreak
- from
;
105 m_DC
-> SetBrush(*wxWHITE_BRUSH
);
107 m_DC
-> SetClippingRegion(x
, y
, m_Width
, hght
);
108 m_Cells
-> Draw(*m_DC
,
110 y
, pbreak
+ (y
/*- from*/));
111 m_DC
-> DestroyClippingRegion();
114 if (pbreak
< m_Cells
-> GetHeight()) return pbreak
;
115 else return GetTotalHeight();
120 int wxHtmlDCRenderer::GetTotalHeight()
122 if (m_Cells
) return m_Cells
-> GetHeight();
141 //--------------------------------------------------------------------------------
143 //--------------------------------------------------------------------------------
147 wxHtmlPrintout::wxHtmlPrintout(const wxString
& title
) : wxPrintout(title
)
149 m_Renderer
= new wxHtmlDCRenderer
;
150 m_RendererHdr
= new wxHtmlDCRenderer
;
151 m_NumPages
= wxHTML_PRINT_MAX_PAGES
;
152 m_Document
= m_BasePath
= wxEmptyString
; m_BasePathIsDir
= TRUE
;
153 m_Headers
[0] = m_Headers
[1] = wxEmptyString
;
154 m_Footers
[0] = m_Footers
[1] = wxEmptyString
;
155 m_HeaderHeight
= m_FooterHeight
= 0;
156 SetMargins(); // to default values
161 wxHtmlPrintout::~wxHtmlPrintout()
164 delete m_RendererHdr
;
169 bool wxHtmlPrintout::OnBeginDocument(int startPage
, int endPage
)
171 int pageWidth
, pageHeight
, mm_w
, mm_h
, scr_w
, scr_h
, dc_w
, dc_h
;
172 float ppmm_h
, ppmm_v
;
174 if (!wxPrintout::OnBeginDocument(startPage
, endPage
)) return FALSE
;
176 GetPageSizePixels(&pageWidth
, &pageHeight
);
177 GetPageSizeMM(&mm_w
, &mm_h
);
178 ppmm_h
= (float)pageWidth
/ mm_w
;
179 ppmm_v
= (float)pageHeight
/ mm_h
;
181 int ppiPrinterX
, ppiPrinterY
;
182 GetPPIPrinter(&ppiPrinterX
, &ppiPrinterY
);
183 int ppiScreenX
, ppiScreenY
;
184 GetPPIScreen(&ppiScreenX
, &ppiScreenY
);
186 wxDisplaySize(&scr_w
, &scr_h
);
187 GetDC() -> GetSize(&dc_w
, &dc_h
);
189 GetDC() -> SetUserScale((double)dc_w
/ (double)pageWidth
, (double)dc_w
/ (double)pageWidth
);
191 /* prepare headers/footers renderer: */
193 m_RendererHdr
-> SetDC(GetDC(), (double)ppiPrinterY
/ (double)ppiScreenY
);
194 m_RendererHdr
-> SetSize((int) (ppmm_h
* (mm_w
- m_MarginLeft
- m_MarginTop
)),
195 (int) (ppmm_v
* (mm_h
- m_MarginTop
- m_MarginBottom
)));
196 if (m_Headers
[0] != wxEmptyString
) {
197 m_RendererHdr
-> SetHtmlText(TranslateHeader(m_Headers
[0], 1));
198 m_HeaderHeight
= m_RendererHdr
-> GetTotalHeight();
200 else if (m_Headers
[1] != wxEmptyString
) {
201 m_RendererHdr
-> SetHtmlText(TranslateHeader(m_Headers
[1], 1));
202 m_HeaderHeight
= m_RendererHdr
-> GetTotalHeight();
204 if (m_Footers
[0] != wxEmptyString
) {
205 m_RendererHdr
-> SetHtmlText(TranslateHeader(m_Footers
[0], 1));
206 m_FooterHeight
= m_RendererHdr
-> GetTotalHeight();
208 else if (m_Footers
[1] != wxEmptyString
) {
209 m_RendererHdr
-> SetHtmlText(TranslateHeader(m_Footers
[1], 1));
210 m_FooterHeight
= m_RendererHdr
-> GetTotalHeight();
213 /* prepare main renderer: */
214 m_Renderer
-> SetDC(GetDC(), (double)ppiPrinterY
/ (double)ppiScreenY
);
215 m_Renderer
-> SetSize((int) (ppmm_h
* (mm_w
- m_MarginLeft
- m_MarginTop
)),
216 (int) (ppmm_v
* (mm_h
- m_MarginTop
- m_MarginBottom
) -
217 m_FooterHeight
- m_HeaderHeight
-
218 ((m_HeaderHeight
== 0) ? 0 : m_MarginSpace
* ppmm_v
) -
219 ((m_FooterHeight
== 0) ? 0 : m_MarginSpace
* ppmm_v
)
221 m_Renderer
-> SetHtmlText(m_Document
, m_BasePath
, m_BasePathIsDir
);
227 bool wxHtmlPrintout::OnPrintPage(int page
)
232 RenderPage(dc
, page
);
239 void wxHtmlPrintout::GetPageInfo(int *minPage
, int *maxPage
, int *selPageFrom
, int *selPageTo
)
242 *maxPage
= wxHTML_PRINT_MAX_PAGES
;
244 *selPageTo
= wxHTML_PRINT_MAX_PAGES
;
249 bool wxHtmlPrintout::HasPage(int pageNum
)
251 return (pageNum
>= 1 && pageNum
<= m_NumPages
);
256 void wxHtmlPrintout::SetHtmlText(const wxString
& html
, const wxString
&basepath
, bool isdir
)
259 m_BasePath
= basepath
;
260 m_BasePathIsDir
= isdir
;
265 void wxHtmlPrintout::SetHtmlFile(const wxString
& htmlfile
)
268 wxFSFile
*ff
= fs
.OpenFile(htmlfile
);
272 wxLogError(htmlfile
+ _(": file does not exist!"));
276 wxInputStream
*st
= ff
-> GetStream();
277 char *t
= new char[st
-> GetSize() + 1];
278 st
-> Read(t
, st
-> GetSize());
279 t
[st
-> GetSize()] = 0;
281 wxString doc
= wxString(t
);
285 SetHtmlText(doc
, htmlfile
, FALSE
);
290 void wxHtmlPrintout::SetHeader(const wxString
& header
, int pg
)
292 if (pg
== wxPAGE_ALL
|| pg
== wxPAGE_EVEN
)
293 m_Headers
[0] = header
;
294 if (pg
== wxPAGE_ALL
|| pg
== wxPAGE_ODD
)
295 m_Headers
[1] = header
;
300 void wxHtmlPrintout::SetFooter(const wxString
& footer
, int pg
)
302 if (pg
== wxPAGE_ALL
|| pg
== wxPAGE_EVEN
)
303 m_Footers
[0] = footer
;
304 if (pg
== wxPAGE_ALL
|| pg
== wxPAGE_ODD
)
305 m_Footers
[1] = footer
;
310 void wxHtmlPrintout::CountPages()
313 int pageWidth
, pageHeight
, mm_w
, mm_h
;
314 float ppmm_h
, ppmm_v
;
316 GetPageSizePixels(&pageWidth
, &pageHeight
);
317 GetPageSizeMM(&mm_w
, &mm_h
);
318 ppmm_h
= (float)pageWidth
/ mm_w
;
319 ppmm_v
= (float)pageHeight
/ mm_h
;
327 pos
= m_Renderer
-> Render((int)( ppmm_h
* m_MarginLeft
),
328 (int) (ppmm_v
* (m_MarginTop
+ (m_HeaderHeight
== 0 ? 0 : m_MarginSpace
)) + m_HeaderHeight
),
330 m_PageBreaks
[++m_NumPages
] = pos
;
331 } while (pos
< m_Renderer
-> GetTotalHeight());
336 void wxHtmlPrintout::RenderPage(wxDC
*dc
, int page
)
340 int pageWidth
, pageHeight
, mm_w
, mm_h
, scr_w
, scr_h
, dc_w
, dc_h
;
341 float ppmm_h
, ppmm_v
;
343 GetPageSizePixels(&pageWidth
, &pageHeight
);
344 GetPageSizeMM(&mm_w
, &mm_h
);
345 ppmm_h
= (float)pageWidth
/ mm_w
;
346 ppmm_v
= (float)pageHeight
/ mm_h
;
347 wxDisplaySize(&scr_w
, &scr_h
);
348 dc
-> GetSize(&dc_w
, &dc_h
);
350 int ppiPrinterX
, ppiPrinterY
;
351 GetPPIPrinter(&ppiPrinterX
, &ppiPrinterY
);
352 int ppiScreenX
, ppiScreenY
;
353 GetPPIScreen(&ppiScreenX
, &ppiScreenY
);
355 dc
-> SetUserScale((double)dc_w
/ (double)pageWidth
, (double)dc_w
/ (double)pageWidth
);
357 m_Renderer
-> SetDC(dc
, (double)ppiPrinterY
/ (double)ppiScreenY
);
359 dc
-> SetBackgroundMode(wxTRANSPARENT
);
361 m_Renderer
-> Render((int) (ppmm_h
* m_MarginLeft
),
362 (int) (ppmm_v
* (m_MarginTop
+ (m_HeaderHeight
== 0 ? 0 : m_MarginSpace
)) + m_HeaderHeight
),
363 m_PageBreaks
[page
-1]);
365 m_RendererHdr
-> SetDC(dc
, (double)ppiPrinterY
/ (double)ppiScreenY
);
366 if (m_Headers
[page
% 2] != wxEmptyString
) {
367 m_RendererHdr
-> SetHtmlText(TranslateHeader(m_Headers
[page
% 2], page
));
368 m_RendererHdr
-> Render((int) (ppmm_h
* m_MarginLeft
), (int) (ppmm_v
* m_MarginTop
));
370 if (m_Footers
[page
% 2] != wxEmptyString
) {
371 m_RendererHdr
-> SetHtmlText(TranslateHeader(m_Footers
[page
% 2], page
));
372 m_RendererHdr
-> Render((int) (ppmm_h
* m_MarginLeft
), (int) (pageHeight
- ppmm_v
* m_MarginBottom
- m_FooterHeight
));
378 wxString
wxHtmlPrintout::TranslateHeader(const wxString
& instr
, int page
)
383 num
.Printf(wxT("%i"), page
);
384 r
.Replace(wxT("@PAGENUM@"), num
);
386 num
.Printf(wxT("%i"), m_NumPages
);
387 r
.Replace(wxT("@PAGESCNT@"), num
);
394 void wxHtmlPrintout::SetMargins(float top
, float bottom
, float left
, float right
, float spaces
)
397 m_MarginBottom
= bottom
;
399 m_MarginRight
= right
;
400 m_MarginSpace
= spaces
;
408 //--------------------------------------------------------------------------------
409 // wxHtmlEasyPrinting
410 //--------------------------------------------------------------------------------
413 wxHtmlEasyPrinting::wxHtmlEasyPrinting(const wxString
& name
, wxFrame
*parent_frame
)
415 m_Frame
= parent_frame
;
417 m_PrintData
= new wxPrintData
;
418 #if (defined __WXGTK__) || (defined __WXMOTIF__)
419 (*m_PrintData
) = (*wxThePrintSetupData
);
421 m_PageSetupData
= new wxPageSetupDialogData
;
422 m_Headers
[0] = m_Headers
[1] = m_Footers
[0] = m_Footers
[1] = wxEmptyString
;
424 m_PageSetupData
-> EnableMargins(TRUE
);
425 m_PageSetupData
-> SetMarginTopLeft(wxPoint(25, 25));
426 m_PageSetupData
-> SetMarginBottomRight(wxPoint(25, 25));
431 wxHtmlEasyPrinting::~wxHtmlEasyPrinting()
434 delete m_PageSetupData
;
439 bool wxHtmlEasyPrinting::PreviewFile(const wxString
&htmlfile
)
441 wxHtmlPrintout
*p1
= CreatePrintout();
442 p1
-> SetHtmlFile(htmlfile
);
443 wxHtmlPrintout
*p2
= CreatePrintout();
444 p2
-> SetHtmlFile(htmlfile
);
445 return DoPreview(p1
, p2
);
450 bool wxHtmlEasyPrinting::PreviewText(const wxString
&htmltext
, const wxString
&basepath
)
452 wxHtmlPrintout
*p1
= CreatePrintout();
453 p1
-> SetHtmlText(htmltext
, basepath
, TRUE
);
454 wxHtmlPrintout
*p2
= CreatePrintout();
455 p2
-> SetHtmlText(htmltext
, basepath
, TRUE
);
456 return DoPreview(p1
, p2
);
461 bool wxHtmlEasyPrinting::PrintFile(const wxString
&htmlfile
)
463 wxHtmlPrintout
*p
= CreatePrintout();
464 p
-> SetHtmlFile(htmlfile
);
470 bool wxHtmlEasyPrinting::PrintText(const wxString
&htmltext
, const wxString
&basepath
)
472 wxHtmlPrintout
*p
= CreatePrintout();
473 p
-> SetHtmlText(htmltext
, basepath
, TRUE
);
479 bool wxHtmlEasyPrinting::DoPreview(wxHtmlPrintout
*printout1
, wxHtmlPrintout
*printout2
)
481 // Pass two printout objects: for preview, and possible printing.
482 wxPrintDialogData
printDialogData(*m_PrintData
);
483 wxPrintPreview
*preview
= new wxPrintPreview(printout1
, printout2
, &printDialogData
);
484 if (!preview
-> Ok()) {
490 wxPreviewFrame
*frame
= new wxPreviewFrame(preview
, m_Frame
,
491 m_Name
+ _(" Preview"),
492 wxPoint(100, 100), wxSize(650, 500));
493 frame
-> Centre(wxBOTH
);
494 frame
-> Initialize();
502 bool wxHtmlEasyPrinting::DoPrint(wxHtmlPrintout
*printout
)
504 wxPrintDialogData
printDialogData(*m_PrintData
);
505 wxPrinter
printer(&printDialogData
);
507 if (!printer
.Print(m_Frame
, printout
, TRUE
))
513 (*m_PrintData
) = printer
.GetPrintDialogData().GetPrintData();
520 void wxHtmlEasyPrinting::PrinterSetup()
522 wxPrintDialogData
printDialogData(*m_PrintData
);
523 wxPrintDialog
printerDialog(m_Frame
, &printDialogData
);
525 printerDialog
.GetPrintDialogData().SetSetupDialog(TRUE
);
527 if (printerDialog
.ShowModal() == wxID_OK
)
528 (*m_PrintData
) = printerDialog
.GetPrintDialogData().GetPrintData();
533 void wxHtmlEasyPrinting::PageSetup()
535 m_PageSetupData
-> SetPrintData(*m_PrintData
);
536 wxPageSetupDialog
pageSetupDialog(m_Frame
, m_PageSetupData
);
538 if (pageSetupDialog
.ShowModal() == wxID_OK
) {
539 (*m_PrintData
) = pageSetupDialog
.GetPageSetupData().GetPrintData();
540 (*m_PageSetupData
) = pageSetupDialog
.GetPageSetupData();
546 void wxHtmlEasyPrinting::SetHeader(const wxString
& header
, int pg
)
548 if (pg
== wxPAGE_ALL
|| pg
== wxPAGE_EVEN
)
549 m_Headers
[0] = header
;
550 if (pg
== wxPAGE_ALL
|| pg
== wxPAGE_ODD
)
551 m_Headers
[1] = header
;
556 void wxHtmlEasyPrinting::SetFooter(const wxString
& footer
, int pg
)
558 if (pg
== wxPAGE_ALL
|| pg
== wxPAGE_EVEN
)
559 m_Footers
[0] = footer
;
560 if (pg
== wxPAGE_ALL
|| pg
== wxPAGE_ODD
)
561 m_Footers
[1] = footer
;
566 wxHtmlPrintout
*wxHtmlEasyPrinting::CreatePrintout()
568 wxHtmlPrintout
*p
= new wxHtmlPrintout(m_Name
);
570 p
-> SetHeader(m_Headers
[0], wxPAGE_EVEN
);
571 p
-> SetHeader(m_Headers
[1], wxPAGE_ODD
);
572 p
-> SetFooter(m_Footers
[0], wxPAGE_EVEN
);
573 p
-> SetFooter(m_Footers
[1], wxPAGE_ODD
);
575 p
-> SetMargins(m_PageSetupData
-> GetMarginTopLeft().y
,
576 m_PageSetupData
-> GetMarginBottomRight().y
,
577 m_PageSetupData
-> GetMarginTopLeft().x
,
578 m_PageSetupData
-> GetMarginBottomRight().x
);
585 #endif // wxUSE_HTML & wxUSE_PRINTING_ARCHITECTURE