]> git.saurik.com Git - wxWidgets.git/blame_incremental - src/gtk/gnome/gprint.cpp
chop off the unwanted \r from GetLineText() return value for richedit 2.0 controls...
[wxWidgets.git] / src / gtk / gnome / gprint.cpp
... / ...
CommitLineData
1/////////////////////////////////////////////////////////////////////////////
2// Name: src/gtk/gnome/gprint.cpp
3// Author: Robert Roebling
4// Purpose: Implement GNOME printing support
5// Created: 09/20/04
6// RCS-ID: $Id$
7// Copyright: Robert Roebling
8// Licence: wxWindows Licence
9/////////////////////////////////////////////////////////////////////////////
10
11// For compilers that support precompilation, includes "wx/wx.h".
12#include "wx/wxprec.h"
13
14#ifdef __BORLANDC__
15 #pragma hdrstop
16#endif
17
18#if wxUSE_LIBGNOMEPRINT
19
20#include "wx/gtk/gnome/gprint.h"
21
22#ifndef WX_PRECOMP
23 #include "wx/log.h"
24 #include "wx/dcmemory.h"
25 #include "wx/icon.h"
26 #include "wx/math.h"
27 #include "wx/image.h"
28 #include "wx/module.h"
29#endif
30
31#include "wx/fontutil.h"
32#include "wx/gtk/private.h"
33#include "wx/dynlib.h"
34#include "wx/paper.h"
35
36#include <libgnomeprint/gnome-print.h>
37#include <libgnomeprint/gnome-print-pango.h>
38#include <libgnomeprint/gnome-print-config.h>
39#include <libgnomeprintui/gnome-print-dialog.h>
40#include <libgnomeprintui/gnome-print-job-preview.h>
41#include <libgnomeprintui/gnome-print-paper-selector.h>
42
43static const double RAD2DEG = 180.0 / M_PI;
44
45#include "wx/link.h"
46wxFORCE_LINK_THIS_MODULE(gnome_print)
47
48//----------------------------------------------------------------------------
49// wxGnomePrintLibrary
50//----------------------------------------------------------------------------
51
52class wxGnomePrintLibrary
53{
54public:
55 wxGnomePrintLibrary();
56 ~wxGnomePrintLibrary();
57
58private:
59 bool IsOk();
60 bool InitializeMethods();
61
62 wxDynamicLibrary m_libGnomePrint;
63 wxDynamicLibrary m_libGnomePrintUI;
64
65 // only true if we successfully loaded both libraries
66 //
67 // don't rename this field, it's used by wxDL_XXX macros internally
68 bool m_ok;
69
70public:
71 wxDL_METHOD_DEFINE( gint, gnome_print_newpath,
72 (GnomePrintContext *pc), (pc), 0 )
73 wxDL_METHOD_DEFINE( gint, gnome_print_moveto,
74 (GnomePrintContext *pc, gdouble x, gdouble y), (pc, x, y), 0 )
75 wxDL_METHOD_DEFINE( gint, gnome_print_lineto,
76 (GnomePrintContext *pc, gdouble x, gdouble y), (pc, x, y), 0 )
77 wxDL_METHOD_DEFINE( gint, gnome_print_arcto,
78 (GnomePrintContext *pc, gdouble x, gdouble y, gdouble radius, gdouble angle1, gdouble angle2, gint direction ), (pc, x, y, radius, angle1, angle2, direction), 0 )
79 wxDL_METHOD_DEFINE( gint, gnome_print_curveto,
80 (GnomePrintContext *pc, gdouble x1, gdouble y1, gdouble x2, gdouble y2, gdouble x3, gdouble y3), (pc, x1, y1, x2, y2, x3, y3), 0 )
81 wxDL_METHOD_DEFINE( gint, gnome_print_closepath,
82 (GnomePrintContext *pc), (pc), 0 )
83 wxDL_METHOD_DEFINE( gint, gnome_print_stroke,
84 (GnomePrintContext *pc), (pc), 0 )
85 wxDL_METHOD_DEFINE( gint, gnome_print_fill,
86 (GnomePrintContext *pc), (pc), 0 )
87 wxDL_METHOD_DEFINE( gint, gnome_print_setrgbcolor,
88 (GnomePrintContext *pc, gdouble r, gdouble g, gdouble b), (pc, r, g, b), 0 )
89 wxDL_METHOD_DEFINE( gint, gnome_print_setlinewidth,
90 (GnomePrintContext *pc, gdouble width), (pc, width), 0 )
91 wxDL_METHOD_DEFINE( gint, gnome_print_setdash,
92 (GnomePrintContext *pc, gint n_values, const gdouble *values, gdouble offset), (pc, n_values, values, offset), 0 )
93
94 wxDL_METHOD_DEFINE( gint, gnome_print_rgbimage,
95 (GnomePrintContext *pc, const guchar *data, gint width, gint height, gint rowstride), (pc, data, width, height, rowstride ), 0 )
96 wxDL_METHOD_DEFINE( gint, gnome_print_rgbaimage,
97 (GnomePrintContext *pc, const guchar *data, gint width, gint height, gint rowstride), (pc, data, width, height, rowstride ), 0 )
98
99 wxDL_METHOD_DEFINE( gint, gnome_print_concat,
100 (GnomePrintContext *pc, const gdouble *matrix), (pc, matrix), 0 )
101 wxDL_METHOD_DEFINE( gint, gnome_print_scale,
102 (GnomePrintContext *pc, gdouble sx, gdouble sy), (pc, sx, sy), 0 )
103 wxDL_METHOD_DEFINE( gint, gnome_print_rotate,
104 (GnomePrintContext *pc, gdouble theta), (pc, theta), 0 )
105 wxDL_METHOD_DEFINE( gint, gnome_print_translate,
106 (GnomePrintContext *pc, gdouble x, gdouble y), (pc, x, y), 0 )
107
108 wxDL_METHOD_DEFINE( gint, gnome_print_gsave,
109 (GnomePrintContext *pc), (pc), 0 )
110 wxDL_METHOD_DEFINE( gint, gnome_print_grestore,
111 (GnomePrintContext *pc), (pc), 0 )
112
113 wxDL_METHOD_DEFINE( gint, gnome_print_clip,
114 (GnomePrintContext *pc), (pc), 0 )
115 wxDL_METHOD_DEFINE( gint, gnome_print_eoclip,
116 (GnomePrintContext *pc), (pc), 0 )
117
118 wxDL_METHOD_DEFINE( gint, gnome_print_beginpage,
119 (GnomePrintContext *pc, const guchar* name), (pc, name), 0 )
120 wxDL_METHOD_DEFINE( gint, gnome_print_showpage,
121 (GnomePrintContext *pc), (pc), 0 )
122 wxDL_METHOD_DEFINE( gint, gnome_print_end_doc,
123 (GnomePrintContext *pc), (pc), 0 )
124
125 wxDL_METHOD_DEFINE( PangoLayout*, gnome_print_pango_create_layout,
126 (GnomePrintContext *gpc), (gpc), NULL )
127 wxDL_METHOD_DEFINE( void, gnome_print_pango_layout,
128 (GnomePrintContext *gpc, PangoLayout *layout), (gpc, layout), /**/ )
129
130 wxDL_METHOD_DEFINE( GnomePrintJob*, gnome_print_job_new,
131 (GnomePrintConfig *config), (config), NULL )
132 wxDL_METHOD_DEFINE( GnomePrintContext*, gnome_print_job_get_context,
133 (GnomePrintJob *job), (job), NULL )
134 wxDL_METHOD_DEFINE( gint, gnome_print_job_close,
135 (GnomePrintJob *job), (job), 0 )
136 wxDL_METHOD_DEFINE( gint, gnome_print_job_print,
137 (GnomePrintJob *job), (job), 0 )
138 wxDL_METHOD_DEFINE( gboolean, gnome_print_job_get_page_size,
139 (GnomePrintJob *job, gdouble *width, gdouble *height), (job, width, height), 0 )
140
141 wxDL_METHOD_DEFINE( GnomePrintUnit*, gnome_print_unit_get_by_abbreviation,
142 (const guchar *abbreviation), (abbreviation), NULL )
143 wxDL_METHOD_DEFINE( gboolean, gnome_print_convert_distance,
144 (gdouble *distance, const GnomePrintUnit *from, const GnomePrintUnit *to), (distance, from, to), false )
145
146 wxDL_METHOD_DEFINE( GnomePrintConfig*, gnome_print_config_default,
147 (void), (), NULL )
148 wxDL_METHOD_DEFINE( gboolean, gnome_print_config_set,
149 (GnomePrintConfig *config, const guchar *key, const guchar *value), (config, key, value), false )
150 wxDL_METHOD_DEFINE( gboolean, gnome_print_config_set_double,
151 (GnomePrintConfig *config, const guchar *key, gdouble value), (config, key, value), false )
152 wxDL_METHOD_DEFINE( gboolean, gnome_print_config_set_int,
153 (GnomePrintConfig *config, const guchar *key, gint value), (config, key, value), false )
154 wxDL_METHOD_DEFINE( gboolean, gnome_print_config_set_boolean,
155 (GnomePrintConfig *config, const guchar *key, gboolean value), (config, key, value), false )
156 wxDL_METHOD_DEFINE( gboolean, gnome_print_config_set_length,
157 (GnomePrintConfig *config, const guchar *key, gdouble value, const GnomePrintUnit *unit), (config, key, value, unit), false )
158
159 wxDL_METHOD_DEFINE( guchar*, gnome_print_config_get,
160 (GnomePrintConfig *config, const guchar *key), (config, key), NULL )
161 wxDL_METHOD_DEFINE( gboolean, gnome_print_config_get_length,
162 (GnomePrintConfig *config, const guchar *key, gdouble *val, const GnomePrintUnit **unit), (config, key, val, unit), false )
163
164 wxDL_METHOD_DEFINE( GtkWidget*, gnome_print_dialog_new,
165 (GnomePrintJob *gpj, const guchar *title, gint flags), (gpj, title, flags), NULL )
166 wxDL_METHOD_DEFINE( void, gnome_print_dialog_construct_range_page,
167 (GnomePrintDialog *gpd, gint flags, gint start, gint end,
168 const guchar *currentlabel, const guchar *rangelabel),
169 (gpd, flags, start, end, currentlabel, rangelabel), /**/ )
170 wxDL_METHOD_DEFINE( void, gnome_print_dialog_get_copies,
171 (GnomePrintDialog *gpd, gint *copies, gboolean *collate), (gpd, copies, collate), /**/ )
172 wxDL_METHOD_DEFINE( void, gnome_print_dialog_set_copies,
173 (GnomePrintDialog *gpd, gint copies, gint collate), (gpd, copies, collate), /**/ )
174 wxDL_METHOD_DEFINE( GnomePrintRangeType, gnome_print_dialog_get_range,
175 (GnomePrintDialog *gpd), (gpd), GNOME_PRINT_RANGETYPE_NONE )
176 wxDL_METHOD_DEFINE( int, gnome_print_dialog_get_range_page,
177 (GnomePrintDialog *gpd, gint *start, gint *end), (gpd, start, end), 0 )
178
179 wxDL_METHOD_DEFINE( GtkWidget*, gnome_paper_selector_new_with_flags,
180 (GnomePrintConfig *config, gint flags), (config, flags), NULL )
181
182 wxDL_METHOD_DEFINE( GtkWidget*, gnome_print_job_preview_new,
183 (GnomePrintJob *gpm, const guchar *title), (gpm, title), NULL )
184
185 DECLARE_NO_COPY_CLASS(wxGnomePrintLibrary)
186};
187
188wxGnomePrintLibrary::wxGnomePrintLibrary()
189{
190 wxLogNull log;
191
192 m_libGnomePrint.Load("libgnomeprint-2-2.so.0");
193 m_ok = m_libGnomePrint.IsLoaded();
194 if ( !m_ok )
195 return;
196
197 m_libGnomePrintUI.Load("libgnomeprintui-2-2.so.0");
198 m_ok = m_libGnomePrintUI->IsLoaded();
199 if ( !m_ok )
200 {
201 m_libGnomePrint.Unload();
202 return;
203 }
204
205 m_ok = InitializeMethods();
206}
207
208wxGnomePrintLibrary::~wxGnomePrintLibrary()
209{
210}
211
212bool wxGnomePrintLibrary::IsOk()
213{
214 return m_ok;
215}
216
217bool wxGnomePrintLibrary::InitializeMethods()
218{
219 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_newpath )
220 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_moveto )
221 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_lineto )
222 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_curveto )
223 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_arcto )
224 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_closepath )
225 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_stroke )
226 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_fill )
227 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_setrgbcolor )
228 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_setlinewidth )
229 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_setdash )
230
231 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_rgbimage )
232 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_rgbaimage )
233
234 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_concat )
235 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_scale )
236 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_rotate )
237 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_translate )
238
239 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_gsave )
240 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_grestore )
241
242 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_clip )
243 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_eoclip )
244
245 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_beginpage )
246 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_showpage )
247 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_end_doc )
248
249 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_pango_create_layout )
250 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_pango_layout )
251
252 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_job_new )
253 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_job_get_context )
254 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_job_close )
255 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_job_print )
256 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_job_get_page_size )
257
258 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_unit_get_by_abbreviation )
259 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_convert_distance )
260
261 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_config_default )
262 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_config_set )
263 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_config_set_boolean )
264 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_config_set_double )
265 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_config_set_int )
266 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_config_set_length )
267
268 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_config_get )
269 wxDL_METHOD_LOAD( m_libGnomePrint, gnome_print_config_get_length )
270
271 wxDL_METHOD_LOAD( m_libGnomePrintUI, gnome_print_dialog_new )
272 wxDL_METHOD_LOAD( m_libGnomePrintUI, gnome_print_dialog_construct_range_page )
273 wxDL_METHOD_LOAD( m_libGnomePrintUI, gnome_print_dialog_get_copies )
274 wxDL_METHOD_LOAD( m_libGnomePrintUI, gnome_print_dialog_set_copies )
275 wxDL_METHOD_LOAD( m_libGnomePrintUI, gnome_print_dialog_get_range )
276 wxDL_METHOD_LOAD( m_libGnomePrintUI, gnome_print_dialog_get_range_page )
277
278 wxDL_METHOD_LOAD( m_libGnomePrintUI, gnome_paper_selector_new_with_flags )
279
280 wxDL_METHOD_LOAD( m_libGnomePrintUI, gnome_print_job_preview_new )
281
282 return true;
283}
284
285static wxGnomePrintLibrary* gs_libGnomePrint = NULL;
286
287//----------------------------------------------------------------------------
288// wxGnomePrintNativeData
289//----------------------------------------------------------------------------
290
291IMPLEMENT_CLASS(wxGnomePrintNativeData, wxPrintNativeDataBase)
292
293wxGnomePrintNativeData::wxGnomePrintNativeData()
294{
295 m_config = gs_libGnomePrint->gnome_print_config_default();
296 m_job = gs_libGnomePrint->gnome_print_job_new( m_config );
297}
298
299wxGnomePrintNativeData::~wxGnomePrintNativeData()
300{
301 g_object_unref (m_config);
302}
303
304bool wxGnomePrintNativeData::TransferTo( wxPrintData &data )
305{
306 guchar *res = gs_libGnomePrint->gnome_print_config_get( m_config,
307 (guchar*)(char*)GNOME_PRINT_KEY_PAGE_ORIENTATION );
308 if (g_ascii_strcasecmp((const gchar *)res,"R90") == 0)
309 data.SetOrientation( wxLANDSCAPE );
310 else
311 data.SetOrientation( wxPORTRAIT );
312 g_free( res );
313
314 return true;
315}
316
317bool wxGnomePrintNativeData::TransferFrom( const wxPrintData &data )
318{
319 if (data.GetOrientation() == wxLANDSCAPE)
320 {
321 gs_libGnomePrint->gnome_print_config_set( m_config,
322 (guchar*)(char*)GNOME_PRINT_KEY_PAGE_ORIENTATION,
323 (guchar*)(char*)"R90" );
324 }
325 else
326 {
327 gs_libGnomePrint->gnome_print_config_set( m_config,
328 (guchar*)(char*)GNOME_PRINT_KEY_PAGE_ORIENTATION,
329 (guchar*)(char*)"R0" );
330 }
331
332 if (data.GetCollate())
333 {
334 gs_libGnomePrint->gnome_print_config_set_boolean( m_config,
335 (guchar*)(char*)GNOME_PRINT_KEY_COLLATE,
336 TRUE );
337 }
338 else
339 {
340 gs_libGnomePrint->gnome_print_config_set_boolean( m_config,
341 (guchar*)(char*)GNOME_PRINT_KEY_COLLATE,
342 FALSE );
343 }
344
345 switch (data.GetPaperId())
346 {
347 case wxPAPER_A3: gs_libGnomePrint->gnome_print_config_set( m_config,
348 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
349 (guchar*)(char*)"A3" );
350 break;
351 case wxPAPER_A5: gs_libGnomePrint->gnome_print_config_set( m_config,
352 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
353 (guchar*)(char*)"A5" );
354 break;
355 case wxPAPER_B4: gs_libGnomePrint->gnome_print_config_set( m_config,
356 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
357 (guchar*)(char*)"B4" );
358 break;
359 case wxPAPER_B5: gs_libGnomePrint->gnome_print_config_set( m_config,
360 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
361 (guchar*)(char*)"B5" );
362 break;
363 case wxPAPER_LETTER: gs_libGnomePrint->gnome_print_config_set( m_config,
364 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
365 (guchar*)(char*)"USLetter" );
366 break;
367 case wxPAPER_LEGAL: gs_libGnomePrint->gnome_print_config_set( m_config,
368 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
369 (guchar*)(char*)"USLegal" );
370 break;
371 case wxPAPER_EXECUTIVE: gs_libGnomePrint->gnome_print_config_set( m_config,
372 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
373 (guchar*)(char*)"Executive" );
374 break;
375 case wxPAPER_ENV_C5: gs_libGnomePrint->gnome_print_config_set( m_config,
376 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
377 (guchar*)(char*)"C5" );
378 break;
379 case wxPAPER_ENV_C6: gs_libGnomePrint->gnome_print_config_set( m_config,
380 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
381 (guchar*)(char*)"C6" );
382 break;
383 case wxPAPER_NONE: break;
384
385 default:
386 case wxPAPER_A4: gs_libGnomePrint->gnome_print_config_set( m_config,
387 (guchar*)(char*)GNOME_PRINT_KEY_PAPER_SIZE,
388 (guchar*)(char*)"A4" );
389 break;
390 }
391
392 return true;
393}
394
395//----------------------------------------------------------------------------
396// wxGnomePrintFactory
397//----------------------------------------------------------------------------
398
399wxPrinterBase* wxGnomePrintFactory::CreatePrinter( wxPrintDialogData *data )
400{
401 return new wxGnomePrinter( data );
402}
403
404wxPrintPreviewBase *wxGnomePrintFactory::CreatePrintPreview( wxPrintout *preview,
405 wxPrintout *printout,
406 wxPrintDialogData *data )
407{
408 return new wxGnomePrintPreview( preview, printout, data );
409}
410
411wxPrintPreviewBase *wxGnomePrintFactory::CreatePrintPreview( wxPrintout *preview,
412 wxPrintout *printout,
413 wxPrintData *data )
414{
415 return new wxGnomePrintPreview( preview, printout, data );
416}
417
418wxPrintDialogBase *wxGnomePrintFactory::CreatePrintDialog( wxWindow *parent,
419 wxPrintDialogData *data )
420{
421 return new wxGnomePrintDialog( parent, data );
422}
423
424wxPrintDialogBase *wxGnomePrintFactory::CreatePrintDialog( wxWindow *parent,
425 wxPrintData *data )
426{
427 return new wxGnomePrintDialog( parent, data );
428}
429
430wxPageSetupDialogBase *wxGnomePrintFactory::CreatePageSetupDialog( wxWindow *parent,
431 wxPageSetupDialogData * data )
432{
433// The native page setup dialog is broken. It
434// miscalculates newly entered values for the
435// margins if you have not chose "points" but
436// e.g. centimerters.
437// This has been fixed in GNOME CVS (maybe
438// fixed in libgnomeprintui 2.8.1)
439
440 return new wxGnomePageSetupDialog( parent, data );
441}
442
443bool wxGnomePrintFactory::HasPrintSetupDialog()
444{
445 return false;
446}
447
448wxDialog *wxGnomePrintFactory::CreatePrintSetupDialog( wxWindow *parent, wxPrintData *data )
449{
450 return NULL;
451}
452
453wxDC* wxGnomePrintFactory::CreatePrinterDC( const wxPrintData& data )
454{
455 return new wxGnomePrintDC(data);
456}
457
458bool wxGnomePrintFactory::HasOwnPrintToFile()
459{
460 return true;
461}
462
463bool wxGnomePrintFactory::HasPrinterLine()
464{
465 return true;
466}
467
468wxString wxGnomePrintFactory::CreatePrinterLine()
469{
470 // redundant now
471 return wxEmptyString;
472}
473
474bool wxGnomePrintFactory::HasStatusLine()
475{
476 // redundant now
477 return true;
478}
479
480wxString wxGnomePrintFactory::CreateStatusLine()
481{
482 // redundant now
483 return wxEmptyString;
484}
485
486wxPrintNativeDataBase *wxGnomePrintFactory::CreatePrintNativeData()
487{
488 return new wxGnomePrintNativeData;
489}
490
491//----------------------------------------------------------------------------
492// wxGnomePrintSetupDialog
493//----------------------------------------------------------------------------
494
495IMPLEMENT_CLASS(wxGnomePrintDialog, wxPrintDialogBase)
496
497wxGnomePrintDialog::wxGnomePrintDialog( wxWindow *parent, wxPrintDialogData *data )
498 : wxPrintDialogBase(parent, wxID_ANY, _("Print"),
499 wxPoint(0, 0), wxSize(600, 600),
500 wxDEFAULT_DIALOG_STYLE |
501 wxTAB_TRAVERSAL)
502{
503 if (data)
504 m_printDialogData = *data;
505
506 Init();
507}
508
509wxGnomePrintDialog::wxGnomePrintDialog( wxWindow *parent, wxPrintData *data )
510 : wxPrintDialogBase(parent, wxID_ANY, _("Print"),
511 wxPoint(0, 0), wxSize(600, 600),
512 wxDEFAULT_DIALOG_STYLE |
513 wxTAB_TRAVERSAL)
514{
515 if (data)
516 m_printDialogData = *data;
517
518 Init();
519}
520
521void wxGnomePrintDialog::Init()
522{
523 wxPrintData data = m_printDialogData.GetPrintData();
524
525 data.ConvertToNative();
526
527 wxGnomePrintNativeData *native =
528 (wxGnomePrintNativeData*) data.GetNativeData();
529
530 m_widget = gs_libGnomePrint->gnome_print_dialog_new( native->GetPrintJob(),
531 (guchar*)"Print",
532 GNOME_PRINT_DIALOG_RANGE|GNOME_PRINT_DIALOG_COPIES );
533
534 int flag = 0;
535 if (m_printDialogData.GetEnableSelection())
536 flag |= GNOME_PRINT_RANGE_SELECTION;
537 if (m_printDialogData.GetEnablePageNumbers())
538 flag |= GNOME_PRINT_RANGE_ALL|GNOME_PRINT_RANGE_RANGE;
539
540 gs_libGnomePrint->gnome_print_dialog_construct_range_page( (GnomePrintDialog*) m_widget,
541 flag,
542 m_printDialogData.GetMinPage(),
543 m_printDialogData.GetMaxPage(),
544 NULL,
545 NULL );
546}
547
548wxGnomePrintDialog::~wxGnomePrintDialog()
549{
550 m_widget = NULL;
551}
552
553int wxGnomePrintDialog::ShowModal()
554{
555 int response = gtk_dialog_run (GTK_DIALOG (m_widget));
556
557 if (response == GNOME_PRINT_DIALOG_RESPONSE_CANCEL)
558 {
559 gtk_widget_destroy(m_widget);
560 m_widget = NULL;
561
562 return wxID_CANCEL;
563 }
564
565 m_printDialogData.GetPrintData().ConvertFromNative();
566
567 gint copies = 1;
568 gboolean collate = false;
569 gs_libGnomePrint->gnome_print_dialog_get_copies( (GnomePrintDialog*) m_widget, &copies, &collate );
570 m_printDialogData.SetNoCopies( copies );
571 m_printDialogData.SetCollate( collate );
572
573 switch (gs_libGnomePrint->gnome_print_dialog_get_range( (GnomePrintDialog*) m_widget ))
574 {
575 case GNOME_PRINT_RANGE_SELECTION:
576 m_printDialogData.SetSelection( true );
577 break;
578 case GNOME_PRINT_RANGE_ALL:
579 m_printDialogData.SetAllPages( true );
580 m_printDialogData.SetFromPage( 0 );
581 m_printDialogData.SetToPage( 9999 );
582 break;
583 case GNOME_PRINT_RANGE_RANGE:
584 default:
585 gint start,end;
586 gs_libGnomePrint->gnome_print_dialog_get_range_page( (GnomePrintDialog*) m_widget, &start, &end );
587 m_printDialogData.SetFromPage( start );
588 m_printDialogData.SetToPage( end );
589 break;
590 }
591
592 gtk_widget_destroy(m_widget);
593 m_widget = NULL;
594
595 if (response == GNOME_PRINT_DIALOG_RESPONSE_PREVIEW)
596 return wxID_PREVIEW;
597
598 return wxID_OK;
599}
600
601wxDC *wxGnomePrintDialog::GetPrintDC()
602{
603 // Later
604 return NULL;
605}
606
607bool wxGnomePrintDialog::Validate()
608{
609 return true;
610}
611
612bool wxGnomePrintDialog::TransferDataToWindow()
613{
614 return true;
615}
616
617bool wxGnomePrintDialog::TransferDataFromWindow()
618{
619 return true;
620}
621
622//----------------------------------------------------------------------------
623// wxGnomePageSetupDialog
624//----------------------------------------------------------------------------
625
626IMPLEMENT_CLASS(wxGnomePageSetupDialog, wxPageSetupDialogBase)
627
628wxGnomePageSetupDialog::wxGnomePageSetupDialog( wxWindow *parent,
629 wxPageSetupDialogData* data )
630{
631 if (data)
632 m_pageDialogData = *data;
633
634 m_pageDialogData.GetPrintData().ConvertToNative();
635
636 wxGnomePrintNativeData *native =
637 (wxGnomePrintNativeData*) m_pageDialogData.GetPrintData().GetNativeData();
638
639 // This *was* required as the page setup dialog
640 // calculates wrong values otherwise.
641#if 0
642 gs_libGnomePrint->gnome_print_config_set( native->GetPrintConfig(),
643 (const guchar*) GNOME_PRINT_KEY_PREFERED_UNIT,
644 (const guchar*) "Pts" );
645#endif
646
647 GnomePrintConfig *config = native->GetPrintConfig();
648
649 const GnomePrintUnit *mm_unit = gs_libGnomePrint->gnome_print_unit_get_by_abbreviation( (const guchar*) "mm" );
650
651 double ml = (double) m_pageDialogData.GetMarginTopLeft().x;
652 double mt = (double) m_pageDialogData.GetMarginTopLeft().y;
653 double mr = (double) m_pageDialogData.GetMarginBottomRight().x;
654 double mb = (double) m_pageDialogData.GetMarginBottomRight().y;
655
656 gs_libGnomePrint->gnome_print_config_set_length (config,
657 (const guchar*) GNOME_PRINT_KEY_PAGE_MARGIN_LEFT, ml, mm_unit );
658 gs_libGnomePrint->gnome_print_config_set_length (config,
659 (const guchar*) GNOME_PRINT_KEY_PAGE_MARGIN_RIGHT, mr, mm_unit );
660 gs_libGnomePrint->gnome_print_config_set_length (config,
661 (const guchar*) GNOME_PRINT_KEY_PAGE_MARGIN_TOP, mt, mm_unit );
662 gs_libGnomePrint->gnome_print_config_set_length (config,
663 (const guchar*) GNOME_PRINT_KEY_PAGE_MARGIN_BOTTOM, mb, mm_unit );
664
665 m_widget = gtk_dialog_new();
666
667 gtk_window_set_title( GTK_WINDOW(m_widget), wxGTK_CONV( _("Page setup") ) );
668
669 GtkWidget *main = gs_libGnomePrint->gnome_paper_selector_new_with_flags( native->GetPrintConfig(),
670 GNOME_PAPER_SELECTOR_MARGINS|GNOME_PAPER_SELECTOR_FEED_ORIENTATION );
671 gtk_container_set_border_width (GTK_CONTAINER (main), 8);
672 gtk_widget_show (main);
673
674 gtk_container_add( GTK_CONTAINER (GTK_DIALOG (m_widget)->vbox), main );
675
676 gtk_dialog_set_has_separator (GTK_DIALOG (m_widget), TRUE);
677
678 gtk_dialog_add_buttons (GTK_DIALOG (m_widget),
679 GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
680 GTK_STOCK_OK, GTK_RESPONSE_OK,
681 NULL);
682
683 gtk_dialog_set_default_response (GTK_DIALOG (m_widget),
684 GTK_RESPONSE_OK);
685}
686
687wxGnomePageSetupDialog::~wxGnomePageSetupDialog()
688{
689}
690
691wxPageSetupDialogData& wxGnomePageSetupDialog::GetPageSetupDialogData()
692{
693 return m_pageDialogData;
694}
695
696int wxGnomePageSetupDialog::ShowModal()
697{
698 wxGnomePrintNativeData *native =
699 (wxGnomePrintNativeData*) m_pageDialogData.GetPrintData().GetNativeData();
700
701 GnomePrintConfig *config = native->GetPrintConfig();
702
703
704 int ret = gtk_dialog_run( GTK_DIALOG(m_widget) );
705
706 if (ret == GTK_RESPONSE_OK)
707 {
708 // Transfer data back to m_pageDialogData
709 m_pageDialogData.GetPrintData().ConvertFromNative();
710
711 // I don't know how querying the last parameter works
712 double ml,mr,mt,mb,pw,ph;
713 gs_libGnomePrint->gnome_print_config_get_length (config,
714 (const guchar*) GNOME_PRINT_KEY_PAGE_MARGIN_LEFT, &ml, NULL);
715 gs_libGnomePrint->gnome_print_config_get_length (config,
716 (const guchar*) GNOME_PRINT_KEY_PAGE_MARGIN_RIGHT, &mr, NULL);
717 gs_libGnomePrint->gnome_print_config_get_length (config,
718 (const guchar*) GNOME_PRINT_KEY_PAGE_MARGIN_TOP, &mt, NULL);
719 gs_libGnomePrint->gnome_print_config_get_length (config,
720 (const guchar*) GNOME_PRINT_KEY_PAGE_MARGIN_BOTTOM, &mb, NULL);
721 gs_libGnomePrint->gnome_print_config_get_length (config,
722 (const guchar*) GNOME_PRINT_KEY_PAPER_WIDTH, &pw, NULL);
723 gs_libGnomePrint->gnome_print_config_get_length (config,
724 (const guchar*) GNOME_PRINT_KEY_PAPER_HEIGHT, &ph, NULL);
725
726 // This code converts correctly from what the user chose
727 // as the unit although I query Pts here
728 const GnomePrintUnit *mm_unit = gs_libGnomePrint->gnome_print_unit_get_by_abbreviation( (const guchar*) "mm" );
729 const GnomePrintUnit *pts_unit = gs_libGnomePrint->gnome_print_unit_get_by_abbreviation( (const guchar*) "Pts" );
730 gs_libGnomePrint->gnome_print_convert_distance( &ml, pts_unit, mm_unit );
731 gs_libGnomePrint->gnome_print_convert_distance( &mr, pts_unit, mm_unit );
732 gs_libGnomePrint->gnome_print_convert_distance( &mt, pts_unit, mm_unit );
733 gs_libGnomePrint->gnome_print_convert_distance( &mb, pts_unit, mm_unit );
734 gs_libGnomePrint->gnome_print_convert_distance( &pw, pts_unit, mm_unit );
735 gs_libGnomePrint->gnome_print_convert_distance( &ph, pts_unit, mm_unit );
736
737 m_pageDialogData.SetMarginTopLeft( wxPoint( (int)(ml+0.5), (int)(mt+0.5)) );
738 m_pageDialogData.SetMarginBottomRight( wxPoint( (int)(mr+0.5), (int)(mb+0.5)) );
739
740 m_pageDialogData.SetPaperSize( wxSize( (int)(pw+0.5), (int)(ph+0.5) ) );
741
742 ret = wxID_OK;
743 }
744 else
745 {
746 ret = wxID_CANCEL;
747 }
748
749 gtk_widget_destroy( m_widget );
750 m_widget = NULL;
751
752 return ret;
753}
754
755bool wxGnomePageSetupDialog::Validate()
756{
757 return true;
758}
759
760bool wxGnomePageSetupDialog::TransferDataToWindow()
761{
762 return true;
763}
764
765bool wxGnomePageSetupDialog::TransferDataFromWindow()
766{
767 return true;
768}
769
770//----------------------------------------------------------------------------
771// wxGnomePrinter
772//----------------------------------------------------------------------------
773
774IMPLEMENT_CLASS(wxGnomePrinter, wxPrinterBase)
775
776wxGnomePrinter::wxGnomePrinter( wxPrintDialogData *data ) :
777 wxPrinterBase( data )
778{
779 m_native_preview = false;
780}
781
782wxGnomePrinter::~wxGnomePrinter()
783{
784}
785
786bool wxGnomePrinter::Print(wxWindow *parent, wxPrintout *printout, bool prompt )
787{
788 if (!printout)
789 {
790 sm_lastError = wxPRINTER_ERROR;
791 return false;
792 }
793
794 wxPrintData printdata = GetPrintDialogData().GetPrintData();
795
796 wxGnomePrintNativeData *native =
797 (wxGnomePrintNativeData*) printdata.GetNativeData();
798
799 GnomePrintJob *job = gs_libGnomePrint->gnome_print_job_new( native->GetPrintConfig() );
800
801 // The GnomePrintJob is temporarily stored in the
802 // native print data as the native print dialog
803 // needs to access it.
804 native->SetPrintJob( job );
805
806
807 printout->SetIsPreview(false);
808
809 if (m_printDialogData.GetMinPage() < 1)
810 m_printDialogData.SetMinPage(1);
811 if (m_printDialogData.GetMaxPage() < 1)
812 m_printDialogData.SetMaxPage(9999);
813
814 wxDC *dc;
815 if (prompt)
816 dc = PrintDialog( parent );
817 else
818 dc = new wxGnomePrintDC( printdata );
819
820 if (m_native_preview)
821 printout->SetIsPreview(true);
822
823 if (!dc)
824 {
825 gs_libGnomePrint->gnome_print_job_close( job );
826 g_object_unref (job);
827 if (sm_lastError != wxPRINTER_CANCELLED)
828 sm_lastError = wxPRINTER_ERROR;
829 return false;
830 }
831
832 wxSize ScreenPixels = wxGetDisplaySize();
833 wxSize ScreenMM = wxGetDisplaySizeMM();
834
835 printout->SetPPIScreen( (int) ((ScreenPixels.GetWidth() * 25.4) / ScreenMM.GetWidth()),
836 (int) ((ScreenPixels.GetHeight() * 25.4) / ScreenMM.GetHeight()) );
837 printout->SetPPIPrinter( wxGnomePrintDC::GetResolution(),
838 wxGnomePrintDC::GetResolution() );
839
840 printout->SetDC(dc);
841
842 int w, h;
843 dc->GetSize(&w, &h);
844 printout->SetPageSizePixels((int)w, (int)h);
845 printout->SetPaperRectPixels(wxRect(0, 0, w, h));
846 int mw, mh;
847 dc->GetSizeMM(&mw, &mh);
848 printout->SetPageSizeMM((int)mw, (int)mh);
849 printout->OnPreparePrinting();
850
851 // Get some parameters from the printout, if defined
852 int fromPage, toPage;
853 int minPage, maxPage;
854 printout->GetPageInfo(&minPage, &maxPage, &fromPage, &toPage);
855
856 if (maxPage == 0)
857 {
858 gs_libGnomePrint->gnome_print_job_close( job );
859 g_object_unref (job);
860 sm_lastError = wxPRINTER_ERROR;
861 return false;
862 }
863
864 printout->OnBeginPrinting();
865
866 int minPageNum = minPage, maxPageNum = maxPage;
867
868 if ( !m_printDialogData.GetAllPages() )
869 {
870 minPageNum = m_printDialogData.GetFromPage();
871 maxPageNum = m_printDialogData.GetToPage();
872 }
873
874
875 int copyCount;
876 for ( copyCount = 1;
877 copyCount <= m_printDialogData.GetNoCopies();
878 copyCount++ )
879 {
880 if (!printout->OnBeginDocument(minPageNum, maxPageNum))
881 {
882 wxLogError(_("Could not start printing."));
883 sm_lastError = wxPRINTER_ERROR;
884 break;
885 }
886
887 int pn;
888 for ( pn = minPageNum;
889 pn <= maxPageNum && printout->HasPage(pn);
890 pn++ )
891 {
892 dc->StartPage();
893 printout->OnPrintPage(pn);
894 dc->EndPage();
895 }
896
897 printout->OnEndDocument();
898 printout->OnEndPrinting();
899 }
900
901 gs_libGnomePrint->gnome_print_job_close( job );
902 if (m_native_preview)
903 {
904 const wxCharBuffer title(wxGTK_CONV_SYS(_("Print preview")));
905 GtkWidget *preview = gs_libGnomePrint->gnome_print_job_preview_new
906 (
907 job,
908 (const guchar *)title.data()
909 );
910 gtk_widget_show(preview);
911 }
912 else
913 {
914 gs_libGnomePrint->gnome_print_job_print( job );
915 }
916
917 g_object_unref (job);
918 delete dc;
919
920 return (sm_lastError == wxPRINTER_NO_ERROR);
921}
922
923wxDC* wxGnomePrinter::PrintDialog( wxWindow *parent )
924{
925 wxGnomePrintDialog dialog( parent, &m_printDialogData );
926 int ret = dialog.ShowModal();
927 if (ret == wxID_CANCEL)
928 {
929 sm_lastError = wxPRINTER_CANCELLED;
930 return NULL;
931 }
932
933 m_native_preview = ret == wxID_PREVIEW;
934
935 m_printDialogData = dialog.GetPrintDialogData();
936 return new wxGnomePrintDC( m_printDialogData.GetPrintData() );
937}
938
939bool wxGnomePrinter::Setup( wxWindow *parent )
940{
941 return false;
942}
943
944//-----------------------------------------------------------------------------
945// wxGnomePrintDC
946//-----------------------------------------------------------------------------
947
948IMPLEMENT_CLASS(wxGnomePrintDC, wxDC)
949
950wxGnomePrintDC::wxGnomePrintDC( const wxPrintData& data )
951{
952 m_printData = data;
953
954 wxGnomePrintNativeData *native =
955 (wxGnomePrintNativeData*) m_printData.GetNativeData();
956
957 m_job = native->GetPrintJob();
958 m_gpc = gs_libGnomePrint->gnome_print_job_get_context (m_job);
959
960 m_layout = gs_libGnomePrint->gnome_print_pango_create_layout( m_gpc );
961 m_fontdesc = pango_font_description_from_string( "Sans 12" );
962 m_context = NULL;
963
964 m_currentRed = 0;
965 m_currentBlue = 0;
966 m_currentGreen = 0;
967
968 m_signX = 1; // default x-axis left to right
969 m_signY = -1; // default y-axis bottom up -> top down
970
971 GetSize( NULL, &m_deviceOffsetY );
972}
973
974wxGnomePrintDC::~wxGnomePrintDC()
975{
976}
977
978bool wxGnomePrintDC::IsOk() const
979{
980 return true;
981}
982
983bool wxGnomePrintDC::DoFloodFill(wxCoord x1, wxCoord y1, const wxColour &col, int style )
984{
985 return false;
986}
987
988bool wxGnomePrintDC::DoGetPixel(wxCoord x1, wxCoord y1, wxColour *col) const
989{
990 return false;
991}
992
993void wxGnomePrintDC::DoDrawLine(wxCoord x1, wxCoord y1, wxCoord x2, wxCoord y2)
994{
995 if (m_pen.GetStyle() == wxTRANSPARENT) return;
996
997 SetPen( m_pen );
998
999 gs_libGnomePrint->gnome_print_moveto ( m_gpc, XLOG2DEV(x1), YLOG2DEV(y1) );
1000 gs_libGnomePrint->gnome_print_lineto ( m_gpc, XLOG2DEV(x2), YLOG2DEV(y2) );
1001 gs_libGnomePrint->gnome_print_stroke ( m_gpc);
1002
1003 CalcBoundingBox( x1, y1 );
1004 CalcBoundingBox( x2, y2 );
1005}
1006
1007void wxGnomePrintDC::DoCrossHair(wxCoord x, wxCoord y)
1008{
1009}
1010
1011void wxGnomePrintDC::DoDrawArc(wxCoord x1,wxCoord y1,wxCoord x2,wxCoord y2,wxCoord xc,wxCoord yc)
1012{
1013 double dx = x1 - xc;
1014 double dy = y1 - yc;
1015 double radius = sqrt((double)(dx*dx+dy*dy));
1016 double alpha1, alpha2;
1017 if (x1 == x2 && y1 == y2)
1018 {
1019 alpha1 = 0.0;
1020 alpha2 = 360.0;
1021 }
1022 else
1023 if (radius == 0.0)
1024 {
1025 alpha1 = alpha2 = 0.0;
1026 }
1027 else
1028 {
1029 alpha1 = (x1 - xc == 0) ?
1030 (y1 - yc < 0) ? 90.0 : -90.0 :
1031 -atan2(double(y1-yc), double(x1-xc)) * RAD2DEG;
1032 alpha2 = (x2 - xc == 0) ?
1033 (y2 - yc < 0) ? 90.0 : -90.0 :
1034 -atan2(double(y2-yc), double(x2-xc)) * RAD2DEG;
1035
1036 while (alpha1 <= 0) alpha1 += 360;
1037 while (alpha2 <= 0) alpha2 += 360; // adjust angles to be between
1038 while (alpha1 > 360) alpha1 -= 360; // 0 and 360 degree
1039 while (alpha2 > 360) alpha2 -= 360;
1040 }
1041
1042 if (m_brush.GetStyle() != wxTRANSPARENT)
1043 {
1044 SetBrush( m_brush );
1045 gs_libGnomePrint->gnome_print_moveto ( m_gpc, XLOG2DEV(xc), YLOG2DEV(yc) );
1046 gs_libGnomePrint->gnome_print_arcto( m_gpc, XLOG2DEV(xc), YLOG2DEV(yc), XLOG2DEVREL((int)radius), alpha1, alpha2, 0 );
1047
1048 gs_libGnomePrint->gnome_print_fill( m_gpc );
1049 }
1050
1051 if (m_pen.GetStyle() != wxTRANSPARENT)
1052 {
1053 SetPen (m_pen);
1054 gs_libGnomePrint->gnome_print_newpath( m_gpc );
1055 gs_libGnomePrint->gnome_print_moveto ( m_gpc, XLOG2DEV(xc), YLOG2DEV(yc) );
1056 gs_libGnomePrint->gnome_print_arcto( m_gpc, XLOG2DEV(xc), YLOG2DEV(yc), XLOG2DEVREL((int)radius), alpha1, alpha2, 0 );
1057 gs_libGnomePrint->gnome_print_closepath( m_gpc );
1058
1059 gs_libGnomePrint->gnome_print_stroke( m_gpc );
1060 }
1061
1062 CalcBoundingBox (x1, y1);
1063 CalcBoundingBox (x2, y2);
1064 CalcBoundingBox (xc, yc);
1065}
1066
1067void wxGnomePrintDC::DoDrawEllipticArc(wxCoord x,wxCoord y,wxCoord w,wxCoord h,double sa,double ea)
1068{
1069 x += w/2;
1070 y += h/2;
1071
1072 int xx = XLOG2DEV(x);
1073 int yy = YLOG2DEV(y);
1074
1075 gs_libGnomePrint->gnome_print_gsave( m_gpc );
1076
1077 gs_libGnomePrint->gnome_print_translate( m_gpc, xx, yy );
1078 double scale = (double)YLOG2DEVREL(h) / (double) XLOG2DEVREL(w);
1079 gs_libGnomePrint->gnome_print_scale( m_gpc, 1.0, scale );
1080
1081 xx = 0;
1082 yy = 0;
1083
1084 if (m_brush.GetStyle () != wxTRANSPARENT)
1085 {
1086 SetBrush( m_brush );
1087
1088 gs_libGnomePrint->gnome_print_moveto ( m_gpc, xx, yy );
1089 gs_libGnomePrint->gnome_print_arcto( m_gpc, xx, yy,
1090 XLOG2DEVREL(w)/2, sa, ea, 0 );
1091 gs_libGnomePrint->gnome_print_moveto ( m_gpc, xx, yy );
1092
1093 gs_libGnomePrint->gnome_print_fill( m_gpc );
1094 }
1095
1096 if (m_pen.GetStyle () != wxTRANSPARENT)
1097 {
1098 SetPen (m_pen);
1099
1100 gs_libGnomePrint->gnome_print_arcto( m_gpc, xx, yy,
1101 XLOG2DEVREL(w)/2, sa, ea, 0 );
1102
1103 gs_libGnomePrint->gnome_print_stroke( m_gpc );
1104 }
1105
1106 gs_libGnomePrint->gnome_print_grestore( m_gpc );
1107
1108 CalcBoundingBox( x, y );
1109 CalcBoundingBox( x+w, y+h );
1110}
1111
1112void wxGnomePrintDC::DoDrawPoint(wxCoord x, wxCoord y)
1113{
1114}
1115
1116void wxGnomePrintDC::DoDrawLines(int n, wxPoint points[], wxCoord xoffset, wxCoord yoffset)
1117{
1118 if (m_pen.GetStyle() == wxTRANSPARENT) return;
1119
1120 if (n <= 0) return;
1121
1122 SetPen (m_pen);
1123
1124 int i;
1125 for ( i =0; i<n ; i++ )
1126 CalcBoundingBox( points[i].x+xoffset, points[i].y+yoffset);
1127
1128 gs_libGnomePrint->gnome_print_moveto ( m_gpc, XLOG2DEV(points[0].x+xoffset), YLOG2DEV(points[0].y+yoffset) );
1129
1130 for (i = 1; i < n; i++)
1131 gs_libGnomePrint->gnome_print_lineto ( m_gpc, XLOG2DEV(points[i].x+xoffset), YLOG2DEV(points[i].y+yoffset) );
1132
1133 gs_libGnomePrint->gnome_print_stroke ( m_gpc);
1134}
1135
1136void wxGnomePrintDC::DoDrawPolygon(int n, wxPoint points[], wxCoord xoffset, wxCoord yoffset, int fillStyle)
1137{
1138 if (n==0) return;
1139
1140 if (m_brush.GetStyle () != wxTRANSPARENT)
1141 {
1142 SetBrush( m_brush );
1143
1144 int x = points[0].x + xoffset;
1145 int y = points[0].y + yoffset;
1146 CalcBoundingBox( x, y );
1147 gs_libGnomePrint->gnome_print_newpath( m_gpc );
1148 gs_libGnomePrint->gnome_print_moveto( m_gpc, XLOG2DEV(x), YLOG2DEV(y) );
1149 int i;
1150 for (i = 1; i < n; i++)
1151 {
1152 int x = points[i].x + xoffset;
1153 int y = points[i].y + yoffset;
1154 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x), YLOG2DEV(y) );
1155 CalcBoundingBox( x, y );
1156 }
1157 gs_libGnomePrint->gnome_print_closepath( m_gpc );
1158 gs_libGnomePrint->gnome_print_fill( m_gpc );
1159 }
1160
1161 if (m_pen.GetStyle () != wxTRANSPARENT)
1162 {
1163 SetPen (m_pen);
1164
1165 int x = points[0].x + xoffset;
1166 int y = points[0].y + yoffset;
1167 gs_libGnomePrint->gnome_print_newpath( m_gpc );
1168 gs_libGnomePrint->gnome_print_moveto( m_gpc, XLOG2DEV(x), YLOG2DEV(y) );
1169 int i;
1170 for (i = 1; i < n; i++)
1171 {
1172 int x = points[i].x + xoffset;
1173 int y = points[i].y + yoffset;
1174 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x), YLOG2DEV(y) );
1175 CalcBoundingBox( x, y );
1176 }
1177 gs_libGnomePrint->gnome_print_closepath( m_gpc );
1178 gs_libGnomePrint->gnome_print_stroke( m_gpc );
1179 }
1180}
1181
1182void wxGnomePrintDC::DoDrawPolyPolygon(int n, int count[], wxPoint points[], wxCoord xoffset, wxCoord yoffset, int fillStyle)
1183{
1184 wxDC::DoDrawPolyPolygon( n, count, points, xoffset, yoffset, fillStyle );
1185}
1186
1187void wxGnomePrintDC::DoDrawRectangle(wxCoord x, wxCoord y, wxCoord width, wxCoord height)
1188{
1189 if (m_brush.GetStyle () != wxTRANSPARENT)
1190 {
1191 SetBrush( m_brush );
1192
1193 gs_libGnomePrint->gnome_print_newpath( m_gpc );
1194 gs_libGnomePrint->gnome_print_moveto( m_gpc, XLOG2DEV(x), YLOG2DEV(y) );
1195 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x + width), YLOG2DEV(y) );
1196 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x + width), YLOG2DEV(y + height) );
1197 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x), YLOG2DEV(y + height) );
1198 gs_libGnomePrint->gnome_print_closepath( m_gpc );
1199 gs_libGnomePrint->gnome_print_fill( m_gpc );
1200
1201 CalcBoundingBox( x, y );
1202 CalcBoundingBox( x + width, y + height );
1203 }
1204
1205 if (m_pen.GetStyle () != wxTRANSPARENT)
1206 {
1207 SetPen (m_pen);
1208
1209 gs_libGnomePrint->gnome_print_newpath( m_gpc );
1210 gs_libGnomePrint->gnome_print_moveto( m_gpc, XLOG2DEV(x), YLOG2DEV(y) );
1211 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x + width), YLOG2DEV(y) );
1212 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x + width), YLOG2DEV(y + height) );
1213 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x), YLOG2DEV(y + height) );
1214 gs_libGnomePrint->gnome_print_closepath( m_gpc );
1215 gs_libGnomePrint->gnome_print_stroke( m_gpc );
1216
1217 CalcBoundingBox( x, y );
1218 CalcBoundingBox( x + width, y + height );
1219 }
1220}
1221
1222void wxGnomePrintDC::DoDrawRoundedRectangle(wxCoord x, wxCoord y, wxCoord width, wxCoord height, double radius)
1223{
1224 wxCoord rad = (wxCoord) radius;
1225
1226 if (m_brush.GetStyle() != wxTRANSPARENT)
1227 {
1228 SetBrush(m_brush);
1229 gs_libGnomePrint->gnome_print_newpath(m_gpc);
1230 gs_libGnomePrint->gnome_print_moveto(m_gpc,XLOG2DEV(x + rad),YLOG2DEV(y));
1231 gs_libGnomePrint->gnome_print_curveto(m_gpc,
1232 XLOG2DEV(x + rad),YLOG2DEV(y),
1233 XLOG2DEV(x),YLOG2DEV(y),
1234 XLOG2DEV(x),YLOG2DEV(y + rad));
1235 gs_libGnomePrint->gnome_print_lineto(m_gpc,XLOG2DEV(x),YLOG2DEV(y + height - rad));
1236 gs_libGnomePrint->gnome_print_curveto(m_gpc,
1237 XLOG2DEV(x),YLOG2DEV(y + height - rad),
1238 XLOG2DEV(x),YLOG2DEV(y + height),
1239 XLOG2DEV(x + rad),YLOG2DEV(y + height));
1240 gs_libGnomePrint->gnome_print_lineto(m_gpc,XLOG2DEV(x + width - rad),YLOG2DEV(y + height));
1241 gs_libGnomePrint->gnome_print_curveto(m_gpc,
1242 XLOG2DEV(x + width - rad),YLOG2DEV(y + height),
1243 XLOG2DEV(x + width),YLOG2DEV(y + height),
1244 XLOG2DEV(x + width),YLOG2DEV(y + height - rad));
1245 gs_libGnomePrint->gnome_print_lineto(m_gpc,XLOG2DEV(x + width),YLOG2DEV(y + rad));
1246 gs_libGnomePrint->gnome_print_curveto(m_gpc,
1247 XLOG2DEV(x + width),YLOG2DEV(y + rad),
1248 XLOG2DEV(x + width),YLOG2DEV(y),
1249 XLOG2DEV(x + width - rad),YLOG2DEV(y));
1250 gs_libGnomePrint->gnome_print_lineto(m_gpc,XLOG2DEV(x + rad),YLOG2DEV(y));
1251 gs_libGnomePrint->gnome_print_closepath(m_gpc);
1252 gs_libGnomePrint->gnome_print_fill(m_gpc);
1253
1254 CalcBoundingBox(x,y);
1255 CalcBoundingBox(x+width,y+height);
1256 }
1257
1258 if (m_pen.GetStyle() != wxTRANSPARENT)
1259 {
1260 SetPen(m_pen);
1261 gs_libGnomePrint->gnome_print_newpath(m_gpc);
1262 gs_libGnomePrint->gnome_print_moveto(m_gpc,XLOG2DEV(x + rad),YLOG2DEV(y));
1263 gs_libGnomePrint->gnome_print_curveto(m_gpc,
1264 XLOG2DEV(x + rad),YLOG2DEV(y),
1265 XLOG2DEV(x),YLOG2DEV(y),
1266 XLOG2DEV(x),YLOG2DEV(y + rad));
1267 gs_libGnomePrint->gnome_print_lineto(m_gpc,XLOG2DEV(x),YLOG2DEV(y + height - rad));
1268 gs_libGnomePrint->gnome_print_curveto(m_gpc,
1269 XLOG2DEV(x),YLOG2DEV(y + height - rad),
1270 XLOG2DEV(x),YLOG2DEV(y + height),
1271 XLOG2DEV(x + rad),YLOG2DEV(y + height));
1272 gs_libGnomePrint->gnome_print_lineto(m_gpc,XLOG2DEV(x + width - rad),YLOG2DEV(y + height));
1273 gs_libGnomePrint->gnome_print_curveto(m_gpc,
1274 XLOG2DEV(x + width - rad),YLOG2DEV(y + height),
1275 XLOG2DEV(x + width),YLOG2DEV(y + height),
1276 XLOG2DEV(x + width),YLOG2DEV(y + height - rad));
1277 gs_libGnomePrint->gnome_print_lineto(m_gpc,XLOG2DEV(x + width),YLOG2DEV(y + rad));
1278 gs_libGnomePrint->gnome_print_curveto(m_gpc,
1279 XLOG2DEV(x + width),YLOG2DEV(y + rad),
1280 XLOG2DEV(x + width),YLOG2DEV(y),
1281 XLOG2DEV(x + width - rad),YLOG2DEV(y));
1282 gs_libGnomePrint->gnome_print_lineto(m_gpc,XLOG2DEV(x + rad),YLOG2DEV(y));
1283 gs_libGnomePrint->gnome_print_closepath(m_gpc);
1284 gs_libGnomePrint->gnome_print_stroke(m_gpc);
1285
1286 CalcBoundingBox(x,y);
1287 CalcBoundingBox(x+width,y+height);
1288 }
1289}
1290
1291void wxGnomePrintDC::makeEllipticalPath(wxCoord x, wxCoord y,
1292 wxCoord width, wxCoord height)
1293{
1294 double r = 4 * (sqrt(2.) - 1) / 3;
1295 double halfW = 0.5 * width,
1296 halfH = 0.5 * height,
1297 halfWR = r * halfW,
1298 halfHR = r * halfH;
1299 wxCoord halfWI = (wxCoord) halfW,
1300 halfHI = (wxCoord) halfH;
1301
1302 gs_libGnomePrint->gnome_print_newpath( m_gpc );
1303
1304 // Approximate an ellipse using four cubic splines, clockwise from 0 deg */
1305 gs_libGnomePrint->gnome_print_moveto( m_gpc,
1306 XLOG2DEV(x + width),
1307 YLOG2DEV(y + halfHI) );
1308 gs_libGnomePrint->gnome_print_curveto( m_gpc,
1309 XLOG2DEV(x + width),
1310 YLOG2DEV(y + (wxCoord) rint (halfH + halfHR)),
1311 XLOG2DEV(x + (wxCoord) rint(halfW + halfWR)),
1312 YLOG2DEV(y + height),
1313 XLOG2DEV(x + halfWI),
1314 YLOG2DEV(y + height) );
1315 gs_libGnomePrint->gnome_print_curveto( m_gpc,
1316 XLOG2DEV(x + (wxCoord) rint(halfW - halfWR)),
1317 YLOG2DEV(y + height),
1318 XLOG2DEV(x),
1319 YLOG2DEV(y + (wxCoord) rint (halfH + halfHR)),
1320 XLOG2DEV(x), YLOG2DEV(y+halfHI) );
1321 gs_libGnomePrint->gnome_print_curveto( m_gpc,
1322 XLOG2DEV(x),
1323 YLOG2DEV(y + (wxCoord) rint (halfH - halfHR)),
1324 XLOG2DEV(x + (wxCoord) rint (halfW - halfWR)),
1325 YLOG2DEV(y),
1326 XLOG2DEV(x+halfWI), YLOG2DEV(y) );
1327 gs_libGnomePrint->gnome_print_curveto( m_gpc,
1328 XLOG2DEV(x + (wxCoord) rint(halfW + halfWR)),
1329 YLOG2DEV(y),
1330 XLOG2DEV(x + width),
1331 YLOG2DEV(y + (wxCoord) rint(halfH - halfHR)),
1332 XLOG2DEV(x + width), YLOG2DEV(y + halfHI) );
1333
1334 gs_libGnomePrint->gnome_print_closepath(m_gpc);
1335}
1336
1337void wxGnomePrintDC::DoDrawEllipse(wxCoord x, wxCoord y, wxCoord width, wxCoord height)
1338{
1339 if (m_brush.GetStyle () != wxTRANSPARENT)
1340 {
1341 SetBrush( m_brush );
1342 makeEllipticalPath( x, y, width, height );
1343 gs_libGnomePrint->gnome_print_fill( m_gpc );
1344 CalcBoundingBox( x, y );
1345 CalcBoundingBox( x + width, y + height );
1346 }
1347
1348 if (m_pen.GetStyle () != wxTRANSPARENT)
1349 {
1350 SetPen (m_pen);
1351 makeEllipticalPath( x, y, width, height );
1352 gs_libGnomePrint->gnome_print_stroke( m_gpc );
1353 CalcBoundingBox( x, y );
1354 CalcBoundingBox( x + width, y + height );
1355 }
1356}
1357
1358#if wxUSE_SPLINES
1359void wxGnomePrintDC::DoDrawSpline(wxList *points)
1360{
1361 SetPen (m_pen);
1362
1363 double c, d, x1, y1, x2, y2, x3, y3;
1364 wxPoint *p, *q;
1365
1366 wxList::compatibility_iterator node = points->GetFirst();
1367 p = (wxPoint *)node->GetData();
1368 x1 = p->x;
1369 y1 = p->y;
1370
1371 node = node->GetNext();
1372 p = (wxPoint *)node->GetData();
1373 c = p->x;
1374 d = p->y;
1375 x3 =
1376 (double)(x1 + c) / 2;
1377 y3 =
1378 (double)(y1 + d) / 2;
1379
1380 gs_libGnomePrint->gnome_print_newpath( m_gpc );
1381 gs_libGnomePrint->gnome_print_moveto( m_gpc, XLOG2DEV((wxCoord)x1), YLOG2DEV((wxCoord)y1) );
1382 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV((wxCoord)x3), YLOG2DEV((wxCoord)y3) );
1383
1384 CalcBoundingBox( (wxCoord)x1, (wxCoord)y1 );
1385 CalcBoundingBox( (wxCoord)x3, (wxCoord)y3 );
1386
1387 node = node->GetNext();
1388 while (node)
1389 {
1390 q = (wxPoint *)node->GetData();
1391
1392 x1 = x3;
1393 y1 = y3;
1394 x2 = c;
1395 y2 = d;
1396 c = q->x;
1397 d = q->y;
1398 x3 = (double)(x2 + c) / 2;
1399 y3 = (double)(y2 + d) / 2;
1400
1401 gs_libGnomePrint->gnome_print_curveto(m_gpc,
1402 XLOG2DEV((wxCoord)x1), YLOG2DEV((wxCoord)y1),
1403 XLOG2DEV((wxCoord)x2), YLOG2DEV((wxCoord)y2),
1404 XLOG2DEV((wxCoord)x3), YLOG2DEV((wxCoord)y3) );
1405
1406 CalcBoundingBox( (wxCoord)x1, (wxCoord)y1 );
1407 CalcBoundingBox( (wxCoord)x3, (wxCoord)y3 );
1408
1409 node = node->GetNext();
1410 }
1411
1412 gs_libGnomePrint->gnome_print_lineto ( m_gpc, XLOG2DEV((wxCoord)c), YLOG2DEV((wxCoord)d) );
1413
1414 gs_libGnomePrint->gnome_print_stroke( m_gpc );
1415}
1416#endif // wxUSE_SPLINES
1417
1418bool wxGnomePrintDC::DoBlit(wxCoord xdest, wxCoord ydest, wxCoord width, wxCoord height,
1419 wxDC *source, wxCoord xsrc, wxCoord ysrc, int rop, bool useMask,
1420 wxCoord xsrcMask, wxCoord ysrcMask)
1421{
1422 wxCHECK_MSG( source, false, wxT("invalid source dc") );
1423
1424 // blit into a bitmap
1425 wxBitmap bitmap( width, height );
1426 wxMemoryDC memDC;
1427 memDC.SelectObject(bitmap);
1428 memDC.Blit(0, 0, width, height, source, xsrc, ysrc, rop); /* TODO: Blit transparently? */
1429 memDC.SelectObject(wxNullBitmap);
1430
1431 // draw bitmap. scaling and positioning is done there
1432 DrawBitmap( bitmap, xdest, ydest );
1433
1434 return true;
1435}
1436
1437void wxGnomePrintDC::DoDrawIcon( const wxIcon& icon, wxCoord x, wxCoord y )
1438{
1439 DoDrawBitmap( icon, x, y, true );
1440}
1441
1442void wxGnomePrintDC::DoDrawBitmap( const wxBitmap& bitmap, wxCoord x, wxCoord y, bool useMask )
1443{
1444 if (!bitmap.Ok()) return;
1445
1446 if (bitmap.HasPixbuf())
1447 {
1448 GdkPixbuf *pixbuf = bitmap.GetPixbuf();
1449 guchar *raw_image = gdk_pixbuf_get_pixels( pixbuf );
1450 bool has_alpha = gdk_pixbuf_get_has_alpha( pixbuf );
1451 int rowstride = gdk_pixbuf_get_rowstride( pixbuf );
1452 int height = gdk_pixbuf_get_height( pixbuf );
1453 int width = gdk_pixbuf_get_width( pixbuf );
1454
1455 gs_libGnomePrint->gnome_print_gsave( m_gpc );
1456 double matrix[6];
1457 matrix[0] = XLOG2DEVREL(width);
1458 matrix[1] = 0;
1459 matrix[2] = 0;
1460 matrix[3] = YLOG2DEVREL(height);
1461 matrix[4] = XLOG2DEV(x);
1462 matrix[5] = YLOG2DEV(y+height);
1463 gs_libGnomePrint->gnome_print_concat( m_gpc, matrix );
1464 gs_libGnomePrint->gnome_print_moveto( m_gpc, 0, 0 );
1465 if (has_alpha)
1466 gs_libGnomePrint->gnome_print_rgbaimage( m_gpc, (guchar *)raw_image, width, height, rowstride );
1467 else
1468 gs_libGnomePrint->gnome_print_rgbimage( m_gpc, (guchar *)raw_image, width, height, rowstride );
1469 gs_libGnomePrint->gnome_print_grestore( m_gpc );
1470 }
1471 else
1472 {
1473 wxImage image = bitmap.ConvertToImage();
1474
1475 if (!image.Ok()) return;
1476
1477 gs_libGnomePrint->gnome_print_gsave( m_gpc );
1478 double matrix[6];
1479 matrix[0] = XLOG2DEVREL(image.GetWidth());
1480 matrix[1] = 0;
1481 matrix[2] = 0;
1482 matrix[3] = YLOG2DEVREL(image.GetHeight());
1483 matrix[4] = XLOG2DEV(x);
1484 matrix[5] = YLOG2DEV(y+image.GetHeight());
1485 gs_libGnomePrint->gnome_print_concat( m_gpc, matrix );
1486 gs_libGnomePrint->gnome_print_moveto( m_gpc, 0, 0 );
1487 gs_libGnomePrint->gnome_print_rgbimage( m_gpc, (guchar*) image.GetData(), image.GetWidth(), image.GetHeight(), image.GetWidth()*3 );
1488 gs_libGnomePrint->gnome_print_grestore( m_gpc );
1489 }
1490}
1491
1492void wxGnomePrintDC::DoDrawText(const wxString& text, wxCoord x, wxCoord y )
1493{
1494 DoDrawRotatedText( text, x, y, 0.0 );
1495}
1496
1497void wxGnomePrintDC::DoDrawRotatedText(const wxString& text, wxCoord x, wxCoord y, double angle)
1498{
1499 x = XLOG2DEV(x);
1500 y = YLOG2DEV(y);
1501
1502 bool underlined = m_font.Ok() && m_font.GetUnderlined();
1503
1504 // FIXME-UTF8: wouldn't be needed if utf8_str() always returned a buffer
1505#if wxUSE_UNICODE_UTF8
1506 const char *data = text.utf8_str();
1507#else
1508 const wxCharBuffer data = text.utf8_str();
1509#endif
1510
1511 size_t datalen = strlen(data);
1512 pango_layout_set_text( m_layout, data, datalen);
1513
1514 if (underlined)
1515 {
1516 PangoAttrList *attrs = pango_attr_list_new();
1517 PangoAttribute *a = pango_attr_underline_new(PANGO_UNDERLINE_SINGLE);
1518 a->start_index = 0;
1519 a->end_index = datalen;
1520 pango_attr_list_insert(attrs, a);
1521 pango_layout_set_attributes(m_layout, attrs);
1522 pango_attr_list_unref(attrs);
1523 }
1524
1525 if (m_textForegroundColour.Ok())
1526 {
1527 unsigned char red = m_textForegroundColour.Red();
1528 unsigned char blue = m_textForegroundColour.Blue();
1529 unsigned char green = m_textForegroundColour.Green();
1530
1531 if (!(red == m_currentRed && green == m_currentGreen && blue == m_currentBlue))
1532 {
1533 double redPS = (double)(red) / 255.0;
1534 double bluePS = (double)(blue) / 255.0;
1535 double greenPS = (double)(green) / 255.0;
1536
1537 gs_libGnomePrint->gnome_print_setrgbcolor( m_gpc, redPS, greenPS, bluePS );
1538
1539 m_currentRed = red;
1540 m_currentBlue = blue;
1541 m_currentGreen = green;
1542 }
1543 }
1544
1545 int w,h;
1546
1547 if (fabs(m_scaleY - 1.0) > 0.00001)
1548 {
1549 // If there is a user or actually any scale applied to
1550 // the device context, scale the font.
1551
1552 // scale font description
1553 gint oldSize = pango_font_description_get_size( m_fontdesc );
1554 double size = oldSize;
1555 size = size * m_scaleY;
1556 pango_font_description_set_size( m_fontdesc, (gint)size );
1557
1558 // actually apply scaled font
1559 pango_layout_set_font_description( m_layout, m_fontdesc );
1560
1561 pango_layout_get_pixel_size( m_layout, &w, &h );
1562#if 0
1563 if ( m_backgroundMode == wxSOLID )
1564 {
1565 gdk_gc_set_foreground(m_textGC, m_textBackgroundColour.GetColor());
1566 gdk_draw_rectangle(m_window, m_textGC, TRUE, x, y, w, h);
1567 gdk_gc_set_foreground(m_textGC, m_textForegroundColour.GetColor());
1568 }
1569#endif
1570 // Draw layout.
1571 gs_libGnomePrint->gnome_print_moveto (m_gpc, x, y);
1572 if (fabs(angle) > 0.00001)
1573 {
1574 gs_libGnomePrint->gnome_print_gsave( m_gpc );
1575 gs_libGnomePrint->gnome_print_rotate( m_gpc, angle );
1576 gs_libGnomePrint->gnome_print_pango_layout( m_gpc, m_layout );
1577 gs_libGnomePrint->gnome_print_grestore( m_gpc );
1578 }
1579 else
1580 {
1581 gs_libGnomePrint->gnome_print_pango_layout( m_gpc, m_layout );
1582 }
1583
1584 // reset unscaled size
1585 pango_font_description_set_size( m_fontdesc, oldSize );
1586
1587 // actually apply unscaled font
1588 pango_layout_set_font_description( m_layout, m_fontdesc );
1589 }
1590 else
1591 {
1592 pango_layout_get_pixel_size( m_layout, &w, &h );
1593#if 0
1594 if ( m_backgroundMode == wxSOLID )
1595 {
1596 gdk_gc_set_foreground(m_textGC, m_textBackgroundColour.GetColor());
1597 gdk_draw_rectangle(m_window, m_textGC, TRUE, x, y, w, h);
1598 gdk_gc_set_foreground(m_textGC, m_textForegroundColour.GetColor());
1599 }
1600#endif
1601 // Draw layout.
1602 gs_libGnomePrint->gnome_print_moveto (m_gpc, x, y);
1603 if (fabs(angle) > 0.00001)
1604 {
1605 gs_libGnomePrint->gnome_print_gsave( m_gpc );
1606 gs_libGnomePrint->gnome_print_rotate( m_gpc, angle );
1607 gs_libGnomePrint->gnome_print_pango_layout( m_gpc, m_layout );
1608 gs_libGnomePrint->gnome_print_grestore( m_gpc );
1609 }
1610 else
1611 {
1612 gs_libGnomePrint->gnome_print_pango_layout( m_gpc, m_layout );
1613 }
1614 }
1615
1616 if (underlined)
1617 {
1618 // undo underline attributes setting:
1619 pango_layout_set_attributes(m_layout, NULL);
1620 }
1621
1622 CalcBoundingBox (x + w, y + h);
1623}
1624
1625void wxGnomePrintDC::Clear()
1626{
1627}
1628
1629void wxGnomePrintDC::SetFont( const wxFont& font )
1630{
1631 m_font = font;
1632
1633 if (m_font.Ok())
1634 {
1635 if (m_fontdesc)
1636 pango_font_description_free( m_fontdesc );
1637
1638 m_fontdesc = pango_font_description_copy( m_font.GetNativeFontInfo()->description );
1639
1640 pango_layout_set_font_description( m_layout, m_fontdesc );
1641 }
1642}
1643
1644void wxGnomePrintDC::SetPen( const wxPen& pen )
1645{
1646 if (!pen.Ok()) return;
1647
1648 m_pen = pen;
1649
1650 gs_libGnomePrint->gnome_print_setlinewidth( m_gpc, XLOG2DEVREL( 1000 * m_pen.GetWidth() ) / 1000.0f );
1651
1652 static const double dotted[] = {2.0, 5.0};
1653 static const double short_dashed[] = {4.0, 4.0};
1654 static const double wxCoord_dashed[] = {4.0, 8.0};
1655 static const double dotted_dashed[] = {6.0, 6.0, 2.0, 6.0};
1656
1657 switch (m_pen.GetStyle())
1658 {
1659 case wxDOT: gs_libGnomePrint->gnome_print_setdash( m_gpc, 2, dotted, 0 ); break;
1660 case wxSHORT_DASH: gs_libGnomePrint->gnome_print_setdash( m_gpc, 2, short_dashed, 0 ); break;
1661 case wxLONG_DASH: gs_libGnomePrint->gnome_print_setdash( m_gpc, 2, wxCoord_dashed, 0 ); break;
1662 case wxDOT_DASH: gs_libGnomePrint->gnome_print_setdash( m_gpc, 4, dotted_dashed, 0 ); break;
1663 case wxUSER_DASH:
1664 {
1665 // It may be noted that libgnomeprint between at least
1666 // versions 2.8.0 and 2.12.1 makes a copy of the dashes
1667 // and then leak the memory since it doesn't set the
1668 // internal flag "privatedash" to 0.
1669 wxDash *wx_dashes;
1670 int num = m_pen.GetDashes (&wx_dashes);
1671 gdouble *g_dashes = g_new( gdouble, num );
1672 int i;
1673 for (i = 0; i < num; ++i)
1674 g_dashes[i] = (gdouble) wx_dashes[i];
1675 gs_libGnomePrint -> gnome_print_setdash( m_gpc, num, g_dashes, 0);
1676 g_free( g_dashes );
1677 }
1678 break;
1679 case wxSOLID:
1680 case wxTRANSPARENT:
1681 default: gs_libGnomePrint->gnome_print_setdash( m_gpc, 0, NULL, 0 ); break;
1682 }
1683
1684
1685 unsigned char red = m_pen.GetColour().Red();
1686 unsigned char blue = m_pen.GetColour().Blue();
1687 unsigned char green = m_pen.GetColour().Green();
1688
1689 if (!(red == m_currentRed && green == m_currentGreen && blue == m_currentBlue))
1690 {
1691 double redPS = (double)(red) / 255.0;
1692 double bluePS = (double)(blue) / 255.0;
1693 double greenPS = (double)(green) / 255.0;
1694
1695 gs_libGnomePrint->gnome_print_setrgbcolor( m_gpc, redPS, greenPS, bluePS );
1696
1697 m_currentRed = red;
1698 m_currentBlue = blue;
1699 m_currentGreen = green;
1700 }
1701}
1702
1703void wxGnomePrintDC::SetBrush( const wxBrush& brush )
1704{
1705 if (!brush.Ok()) return;
1706
1707 m_brush = brush;
1708
1709 // Brush colour
1710 unsigned char red = m_brush.GetColour().Red();
1711 unsigned char blue = m_brush.GetColour().Blue();
1712 unsigned char green = m_brush.GetColour().Green();
1713
1714 if (!m_colour)
1715 {
1716 // Anything not white is black
1717 if (! (red == (unsigned char) 255 &&
1718 blue == (unsigned char) 255 &&
1719 green == (unsigned char) 255) )
1720 {
1721 red = (unsigned char) 0;
1722 green = (unsigned char) 0;
1723 blue = (unsigned char) 0;
1724 }
1725 // setgray here ?
1726 }
1727
1728 if (!(red == m_currentRed && green == m_currentGreen && blue == m_currentBlue))
1729 {
1730 double redPS = (double)(red) / 255.0;
1731 double bluePS = (double)(blue) / 255.0;
1732 double greenPS = (double)(green) / 255.0;
1733
1734 gs_libGnomePrint->gnome_print_setrgbcolor( m_gpc, redPS, greenPS, bluePS );
1735
1736 m_currentRed = red;
1737 m_currentBlue = blue;
1738 m_currentGreen = green;
1739 }
1740}
1741
1742void wxGnomePrintDC::SetLogicalFunction( int function )
1743{
1744}
1745
1746void wxGnomePrintDC::SetBackground( const wxBrush& brush )
1747{
1748}
1749
1750void wxGnomePrintDC::DoSetClippingRegion(wxCoord x, wxCoord y, wxCoord width, wxCoord height)
1751{
1752 wxDC::DoSetClippingRegion( x, y, width, height );
1753
1754 gs_libGnomePrint->gnome_print_gsave( m_gpc );
1755
1756 gs_libGnomePrint->gnome_print_newpath( m_gpc );
1757 gs_libGnomePrint->gnome_print_moveto( m_gpc, XLOG2DEV(x), YLOG2DEV(y) );
1758 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x + width), YLOG2DEV(y) );
1759 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x + width), YLOG2DEV(y + height) );
1760 gs_libGnomePrint->gnome_print_lineto( m_gpc, XLOG2DEV(x), YLOG2DEV(y + height) );
1761 gs_libGnomePrint->gnome_print_closepath( m_gpc );
1762 gs_libGnomePrint->gnome_print_clip( m_gpc );
1763}
1764
1765void wxGnomePrintDC::DestroyClippingRegion()
1766{
1767 wxDC::DestroyClippingRegion();
1768
1769 gs_libGnomePrint->gnome_print_grestore( m_gpc );
1770
1771#if 0
1772 // not needed, we set the values in each
1773 // drawing method anyways
1774 SetPen( m_pen );
1775 SetBrush( m_brush );
1776 SetFont( m_font );
1777#endif
1778}
1779
1780bool wxGnomePrintDC::StartDoc(const wxString& message)
1781{
1782 return true;
1783}
1784
1785void wxGnomePrintDC::EndDoc()
1786{
1787 gs_libGnomePrint->gnome_print_end_doc( m_gpc );
1788}
1789
1790void wxGnomePrintDC::StartPage()
1791{
1792 gs_libGnomePrint->gnome_print_beginpage( m_gpc, (const guchar*) "page" );
1793}
1794
1795void wxGnomePrintDC::EndPage()
1796{
1797 gs_libGnomePrint->gnome_print_showpage( m_gpc );
1798}
1799
1800wxCoord wxGnomePrintDC::GetCharHeight() const
1801{
1802 pango_layout_set_text( m_layout, "H", 1 );
1803
1804 int w,h;
1805 pango_layout_get_pixel_size( m_layout, &w, &h );
1806
1807 return h;
1808}
1809
1810wxCoord wxGnomePrintDC::GetCharWidth() const
1811{
1812 pango_layout_set_text( m_layout, "H", 1 );
1813
1814 int w,h;
1815 pango_layout_get_pixel_size( m_layout, &w, &h );
1816
1817 return w;
1818}
1819
1820void wxGnomePrintDC::DoGetTextExtent(const wxString& string, wxCoord *width, wxCoord *height,
1821 wxCoord *descent,
1822 wxCoord *externalLeading,
1823 const wxFont *theFont ) const
1824{
1825 if ( width )
1826 *width = 0;
1827 if ( height )
1828 *height = 0;
1829 if ( descent )
1830 *descent = 0;
1831 if ( externalLeading )
1832 *externalLeading = 0;
1833
1834 if (string.empty())
1835 {
1836 return;
1837 }
1838
1839 // Set layout's text
1840
1841 // FIXME-UTF8: wouldn't be needed if utf8_str() always returned a buffer
1842#if wxUSE_UNICODE_UTF8
1843 const char *dataUTF8 = string.utf8_str();
1844#else
1845 const wxCharBuffer dataUTF8 = string.utf8_str();
1846#endif
1847
1848 PangoFontDescription *desc = (theFont) ? theFont->GetNativeFontInfo()->description : m_fontdesc;
1849
1850 gint oldSize = pango_font_description_get_size( desc );
1851 double size = oldSize;
1852 size = size * m_scaleY;
1853 pango_font_description_set_size( desc, (gint)size );
1854
1855 // apply scaled font
1856 pango_layout_set_font_description( m_layout, desc );
1857
1858 pango_layout_set_text( m_layout, dataUTF8, strlen(dataUTF8) );
1859
1860 int w, h;
1861 pango_layout_get_pixel_size( m_layout, &w, &h );
1862
1863
1864 if (width)
1865 *width = (wxCoord)(w / m_scaleX);
1866 if (height)
1867 *height = (wxCoord)(h / m_scaleY);
1868
1869 if (descent)
1870 {
1871 PangoLayoutIter *iter = pango_layout_get_iter(m_layout);
1872 int baseline = pango_layout_iter_get_baseline(iter);
1873 pango_layout_iter_free(iter);
1874 *descent = h - PANGO_PIXELS(baseline);
1875 }
1876
1877 // reset unscaled size
1878 pango_font_description_set_size( desc, oldSize );
1879
1880 // reset unscaled font
1881 pango_layout_set_font_description( m_layout, m_fontdesc );
1882}
1883
1884void wxGnomePrintDC::DoGetSize(int* width, int* height) const
1885{
1886 wxGnomePrintNativeData *native =
1887 (wxGnomePrintNativeData*) m_printData.GetNativeData();
1888
1889 // Query page size. This seems to omit the margins
1890 double pw,ph;
1891 gs_libGnomePrint->gnome_print_job_get_page_size( native->GetPrintJob(), &pw, &ph );
1892
1893 if (width)
1894 *width = (int) (pw + 0.5);
1895 if (height)
1896 *height = (int) (ph + 0.5);
1897}
1898
1899void wxGnomePrintDC::DoGetSizeMM(int *width, int *height) const
1900{
1901 wxGnomePrintNativeData *native =
1902 (wxGnomePrintNativeData*) m_printData.GetNativeData();
1903
1904 // This code assumes values in Pts.
1905
1906 double pw,ph;
1907 gs_libGnomePrint->gnome_print_job_get_page_size( native->GetPrintJob(), &pw, &ph );
1908
1909 // Convert to mm.
1910
1911 const GnomePrintUnit *mm_unit = gs_libGnomePrint->gnome_print_unit_get_by_abbreviation( (const guchar*) "mm" );
1912 const GnomePrintUnit *pts_unit = gs_libGnomePrint->gnome_print_unit_get_by_abbreviation( (const guchar*) "Pts" );
1913 gs_libGnomePrint->gnome_print_convert_distance( &pw, pts_unit, mm_unit );
1914 gs_libGnomePrint->gnome_print_convert_distance( &ph, pts_unit, mm_unit );
1915
1916 if (width)
1917 *width = (int) (pw + 0.5);
1918 if (height)
1919 *height = (int) (ph + 0.5);
1920}
1921
1922wxSize wxGnomePrintDC::GetPPI() const
1923{
1924 return wxSize(72,72);
1925}
1926
1927void wxGnomePrintDC::SetAxisOrientation( bool xLeftRight, bool yBottomUp )
1928{
1929 m_signX = (xLeftRight ? 1 : -1);
1930 m_signY = (yBottomUp ? 1 : -1);
1931
1932 ComputeScaleAndOrigin();
1933}
1934
1935void wxGnomePrintDC::SetLogicalOrigin( wxCoord x, wxCoord y )
1936{
1937 wxDC::SetLogicalOrigin( x, y );
1938}
1939
1940void wxGnomePrintDC::SetDeviceOrigin( wxCoord x, wxCoord y )
1941{
1942 wxDC::SetDeviceOrigin( x, y );
1943}
1944
1945void wxGnomePrintDC::SetPrintData(const wxPrintData& data)
1946{
1947 m_printData = data;
1948
1949 if (m_printData.GetOrientation() == wxPORTRAIT)
1950 GetSize( NULL, &m_deviceOffsetY );
1951 else
1952 GetSize( &m_deviceOffsetY, NULL );
1953}
1954
1955void wxGnomePrintDC::SetResolution(int ppi)
1956{
1957}
1958
1959int wxGnomePrintDC::GetResolution()
1960{
1961 return 72;
1962}
1963
1964// ----------------------------------------------------------------------------
1965// wxGnomePrintModule
1966// ----------------------------------------------------------------------------
1967
1968bool wxGnomePrintModule::OnInit()
1969{
1970 gs_libGnomePrint = new wxGnomePrintLibrary;
1971 if (gs_libGnomePrint->IsOk())
1972 wxPrintFactory::SetPrintFactory( new wxGnomePrintFactory );
1973 return true;
1974}
1975
1976void wxGnomePrintModule::OnExit()
1977{
1978 delete gs_libGnomePrint;
1979 gs_libGnomePrint = NULL;
1980}
1981
1982IMPLEMENT_DYNAMIC_CLASS(wxGnomePrintModule, wxModule)
1983
1984// ----------------------------------------------------------------------------
1985// Print preview
1986// ----------------------------------------------------------------------------
1987
1988IMPLEMENT_CLASS(wxGnomePrintPreview, wxPrintPreviewBase)
1989
1990void wxGnomePrintPreview::Init(wxPrintout * WXUNUSED(printout),
1991 wxPrintout * WXUNUSED(printoutForPrinting))
1992{
1993 DetermineScaling();
1994}
1995
1996wxGnomePrintPreview::wxGnomePrintPreview(wxPrintout *printout,
1997 wxPrintout *printoutForPrinting,
1998 wxPrintDialogData *data)
1999 : wxPrintPreviewBase(printout, printoutForPrinting, data)
2000{
2001 Init(printout, printoutForPrinting);
2002}
2003
2004wxGnomePrintPreview::wxGnomePrintPreview(wxPrintout *printout,
2005 wxPrintout *printoutForPrinting,
2006 wxPrintData *data)
2007 : wxPrintPreviewBase(printout, printoutForPrinting, data)
2008{
2009 Init(printout, printoutForPrinting);
2010}
2011
2012wxGnomePrintPreview::~wxGnomePrintPreview()
2013{
2014}
2015
2016bool wxGnomePrintPreview::Print(bool interactive)
2017{
2018 if (!m_printPrintout)
2019 return false;
2020
2021 wxPrinter printer(& m_printDialogData);
2022 return printer.Print(m_previewFrame, m_printPrintout, interactive);
2023}
2024
2025void wxGnomePrintPreview::DetermineScaling()
2026{
2027 wxPaperSize paperType = m_printDialogData.GetPrintData().GetPaperId();
2028 if (paperType == wxPAPER_NONE)
2029 paperType = wxPAPER_NONE;
2030
2031 wxPrintPaperType *paper = wxThePrintPaperDatabase->FindPaperType(paperType);
2032 if (!paper)
2033 paper = wxThePrintPaperDatabase->FindPaperType(wxPAPER_A4);
2034
2035 if (paper)
2036 {
2037 wxSize ScreenPixels = wxGetDisplaySize();
2038 wxSize ScreenMM = wxGetDisplaySizeMM();
2039
2040 m_previewPrintout->SetPPIScreen( (int) ((ScreenPixels.GetWidth() * 25.4) / ScreenMM.GetWidth()),
2041 (int) ((ScreenPixels.GetHeight() * 25.4) / ScreenMM.GetHeight()) );
2042 m_previewPrintout->SetPPIPrinter(wxGnomePrintDC::GetResolution(), wxGnomePrintDC::GetResolution());
2043
2044 wxSize sizeDevUnits(paper->GetSizeDeviceUnits());
2045
2046 // TODO: get better resolution information from wxGnomePrintDC, if possible.
2047
2048 sizeDevUnits.x = (wxCoord)((float)sizeDevUnits.x * wxGnomePrintDC::GetResolution() / 72.0);
2049 sizeDevUnits.y = (wxCoord)((float)sizeDevUnits.y * wxGnomePrintDC::GetResolution() / 72.0);
2050 wxSize sizeTenthsMM(paper->GetSize());
2051 wxSize sizeMM(sizeTenthsMM.x / 10, sizeTenthsMM.y / 10);
2052
2053 // If in landscape mode, we need to swap the width and height.
2054 if ( m_printDialogData.GetPrintData().GetOrientation() == wxLANDSCAPE )
2055 {
2056 m_pageWidth = sizeDevUnits.y;
2057 m_pageHeight = sizeDevUnits.x;
2058 m_previewPrintout->SetPageSizeMM(sizeMM.y, sizeMM.x);
2059 }
2060 else
2061 {
2062 m_pageWidth = sizeDevUnits.x;
2063 m_pageHeight = sizeDevUnits.y;
2064 m_previewPrintout->SetPageSizeMM(sizeMM.x, sizeMM.y);
2065 }
2066 m_previewPrintout->SetPageSizePixels(m_pageWidth, m_pageHeight);
2067 m_previewPrintout->SetPaperRectPixels(wxRect(0, 0, m_pageWidth, m_pageHeight));
2068
2069 // At 100%, the page should look about page-size on the screen.
2070 m_previewScaleX = (float)0.8 * 72.0 / (float)wxGnomePrintDC::GetResolution();
2071 m_previewScaleY = m_previewScaleX;
2072 }
2073}
2074
2075#endif // wxUSE_LIBGNOMEPRINT