File: | backend/dvi/dvi-document.c |
Warning: | line 530, column 43 The right operand of '-' is a garbage value |
Press '?' to see keyboard shortcuts
Keyboard shortcuts:
1 | /* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8; c-indent-level: 8 -*- */ | |||
2 | /* | |||
3 | * Copyright (C) 2005, Nickolay V. Shmyrev <nshmyrev@yandex.ru> | |||
4 | * | |||
5 | * This program is free software; you can redistribute it and/or modify | |||
6 | * it under the terms of the GNU General Public License as published by | |||
7 | * the Free Software Foundation; either version 2, or (at your option) | |||
8 | * any later version. | |||
9 | * | |||
10 | * This program is distributed in the hope that it will be useful, | |||
11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
13 | * GNU General Public License for more details. | |||
14 | * | |||
15 | * You should have received a copy of the GNU General Public License | |||
16 | * along with this program; if not, write to the Free Software | |||
17 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. | |||
18 | */ | |||
19 | ||||
20 | #include "config.h" | |||
21 | ||||
22 | #include "dvi-document.h" | |||
23 | #include "ev-document-thumbnails.h" | |||
24 | #include "ev-document-misc.h" | |||
25 | #include "ev-file-exporter.h" | |||
26 | #include "ev-file-helpers.h" | |||
27 | ||||
28 | #include "mdvi.h" | |||
29 | #include "fonts.h" | |||
30 | #include "color.h" | |||
31 | #include "cairo-device.h" | |||
32 | ||||
33 | #include <glib/gi18n-lib.h> | |||
34 | #include <ctype.h> | |||
35 | #include <sys/wait.h> | |||
36 | #include <stdlib.h> | |||
37 | ||||
38 | GMutex dvi_context_mutex; | |||
39 | ||||
40 | enum { | |||
41 | PROP_0, | |||
42 | PROP_TITLE | |||
43 | }; | |||
44 | ||||
45 | struct _DviDocumentClass | |||
46 | { | |||
47 | EvDocumentClass parent_class; | |||
48 | }; | |||
49 | ||||
50 | struct _DviDocument | |||
51 | { | |||
52 | EvDocument parent_instance; | |||
53 | ||||
54 | DviContext *context; | |||
55 | DviPageSpec *spec; | |||
56 | DviParams *params; | |||
57 | ||||
58 | /* To let document scale we should remember width and height */ | |||
59 | double base_width; | |||
60 | double base_height; | |||
61 | ||||
62 | gchar *uri; | |||
63 | ||||
64 | /* PDF exporter */ | |||
65 | gchar *exporter_filename; | |||
66 | GString *exporter_opts; | |||
67 | }; | |||
68 | ||||
69 | typedef struct _DviDocumentClass DviDocumentClass; | |||
70 | ||||
71 | static void dvi_document_document_thumbnails_iface_init (EvDocumentThumbnailsInterface *iface); | |||
72 | static void dvi_document_file_exporter_iface_init (EvFileExporterInterface *iface); | |||
73 | static void dvi_document_do_color_special (DviContext *dvi, | |||
74 | const char *prefix, | |||
75 | const char *arg); | |||
76 | ||||
77 | EV_BACKEND_REGISTER_WITH_CODE (DviDocument, dvi_document,static GType g_define_type_id = 0; GType dvi_document_get_type (void) { return g_define_type_id; } static void dvi_document_init (DviDocument *self); static void dvi_document_class_init (DviDocumentClass *klass); static gpointer dvi_document_parent_class = ((void* )0); static void dvi_document_class_intern_init (gpointer klass ) { dvi_document_parent_class = g_type_class_peek_parent (klass ); dvi_document_class_init ((DviDocumentClass *) klass); } __attribute__ ((visibility("default"))) GType register_lector_backend (GTypeModule *module) { const GTypeInfo our_info = { sizeof (DviDocumentClass ), ((void*)0), ((void*)0), (GClassInitFunc) dvi_document_class_intern_init , ((void*)0), ((void*)0), sizeof (DviDocument), 0, (GInstanceInitFunc ) dvi_document_init }; bindtextdomain ("lector", "/usr/share/locale" ); bind_textdomain_codeset ("lector", "UTF-8"); g_define_type_id = g_type_module_register_type (module, (ev_document_get_type ()), "DviDocument", &our_info, (GTypeFlags)0); { { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc ) dvi_document_document_thumbnails_iface_init, ((void*)0), (( void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_document_thumbnails_get_type ()), &g_implement_interface_info ); }; { const GInterfaceInfo g_implement_interface_info = { ( GInterfaceInitFunc) dvi_document_file_exporter_iface_init, (( void*)0), ((void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_file_exporter_get_type ()), &g_implement_interface_info ); }; } return g_define_type_id; } | |||
78 | {static GType g_define_type_id = 0; GType dvi_document_get_type (void) { return g_define_type_id; } static void dvi_document_init (DviDocument *self); static void dvi_document_class_init (DviDocumentClass *klass); static gpointer dvi_document_parent_class = ((void* )0); static void dvi_document_class_intern_init (gpointer klass ) { dvi_document_parent_class = g_type_class_peek_parent (klass ); dvi_document_class_init ((DviDocumentClass *) klass); } __attribute__ ((visibility("default"))) GType register_lector_backend (GTypeModule *module) { const GTypeInfo our_info = { sizeof (DviDocumentClass ), ((void*)0), ((void*)0), (GClassInitFunc) dvi_document_class_intern_init , ((void*)0), ((void*)0), sizeof (DviDocument), 0, (GInstanceInitFunc ) dvi_document_init }; bindtextdomain ("lector", "/usr/share/locale" ); bind_textdomain_codeset ("lector", "UTF-8"); g_define_type_id = g_type_module_register_type (module, (ev_document_get_type ()), "DviDocument", &our_info, (GTypeFlags)0); { { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc ) dvi_document_document_thumbnails_iface_init, ((void*)0), (( void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_document_thumbnails_get_type ()), &g_implement_interface_info ); }; { const GInterfaceInfo g_implement_interface_info = { ( GInterfaceInitFunc) dvi_document_file_exporter_iface_init, (( void*)0), ((void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_file_exporter_get_type ()), &g_implement_interface_info ); }; } return g_define_type_id; } | |||
79 | EV_BACKEND_IMPLEMENT_INTERFACE (EV_TYPE_DOCUMENT_THUMBNAILS, dvi_document_document_thumbnails_iface_init);static GType g_define_type_id = 0; GType dvi_document_get_type (void) { return g_define_type_id; } static void dvi_document_init (DviDocument *self); static void dvi_document_class_init (DviDocumentClass *klass); static gpointer dvi_document_parent_class = ((void* )0); static void dvi_document_class_intern_init (gpointer klass ) { dvi_document_parent_class = g_type_class_peek_parent (klass ); dvi_document_class_init ((DviDocumentClass *) klass); } __attribute__ ((visibility("default"))) GType register_lector_backend (GTypeModule *module) { const GTypeInfo our_info = { sizeof (DviDocumentClass ), ((void*)0), ((void*)0), (GClassInitFunc) dvi_document_class_intern_init , ((void*)0), ((void*)0), sizeof (DviDocument), 0, (GInstanceInitFunc ) dvi_document_init }; bindtextdomain ("lector", "/usr/share/locale" ); bind_textdomain_codeset ("lector", "UTF-8"); g_define_type_id = g_type_module_register_type (module, (ev_document_get_type ()), "DviDocument", &our_info, (GTypeFlags)0); { { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc ) dvi_document_document_thumbnails_iface_init, ((void*)0), (( void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_document_thumbnails_get_type ()), &g_implement_interface_info ); }; { const GInterfaceInfo g_implement_interface_info = { ( GInterfaceInitFunc) dvi_document_file_exporter_iface_init, (( void*)0), ((void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_file_exporter_get_type ()), &g_implement_interface_info ); }; } return g_define_type_id; } | |||
80 | EV_BACKEND_IMPLEMENT_INTERFACE (EV_TYPE_FILE_EXPORTER, dvi_document_file_exporter_iface_init);static GType g_define_type_id = 0; GType dvi_document_get_type (void) { return g_define_type_id; } static void dvi_document_init (DviDocument *self); static void dvi_document_class_init (DviDocumentClass *klass); static gpointer dvi_document_parent_class = ((void* )0); static void dvi_document_class_intern_init (gpointer klass ) { dvi_document_parent_class = g_type_class_peek_parent (klass ); dvi_document_class_init ((DviDocumentClass *) klass); } __attribute__ ((visibility("default"))) GType register_lector_backend (GTypeModule *module) { const GTypeInfo our_info = { sizeof (DviDocumentClass ), ((void*)0), ((void*)0), (GClassInitFunc) dvi_document_class_intern_init , ((void*)0), ((void*)0), sizeof (DviDocument), 0, (GInstanceInitFunc ) dvi_document_init }; bindtextdomain ("lector", "/usr/share/locale" ); bind_textdomain_codeset ("lector", "UTF-8"); g_define_type_id = g_type_module_register_type (module, (ev_document_get_type ()), "DviDocument", &our_info, (GTypeFlags)0); { { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc ) dvi_document_document_thumbnails_iface_init, ((void*)0), (( void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_document_thumbnails_get_type ()), &g_implement_interface_info ); }; { const GInterfaceInfo g_implement_interface_info = { ( GInterfaceInitFunc) dvi_document_file_exporter_iface_init, (( void*)0), ((void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_file_exporter_get_type ()), &g_implement_interface_info ); }; } return g_define_type_id; } | |||
81 | })static GType g_define_type_id = 0; GType dvi_document_get_type (void) { return g_define_type_id; } static void dvi_document_init (DviDocument *self); static void dvi_document_class_init (DviDocumentClass *klass); static gpointer dvi_document_parent_class = ((void* )0); static void dvi_document_class_intern_init (gpointer klass ) { dvi_document_parent_class = g_type_class_peek_parent (klass ); dvi_document_class_init ((DviDocumentClass *) klass); } __attribute__ ((visibility("default"))) GType register_lector_backend (GTypeModule *module) { const GTypeInfo our_info = { sizeof (DviDocumentClass ), ((void*)0), ((void*)0), (GClassInitFunc) dvi_document_class_intern_init , ((void*)0), ((void*)0), sizeof (DviDocument), 0, (GInstanceInitFunc ) dvi_document_init }; bindtextdomain ("lector", "/usr/share/locale" ); bind_textdomain_codeset ("lector", "UTF-8"); g_define_type_id = g_type_module_register_type (module, (ev_document_get_type ()), "DviDocument", &our_info, (GTypeFlags)0); { { const GInterfaceInfo g_implement_interface_info = { (GInterfaceInitFunc ) dvi_document_document_thumbnails_iface_init, ((void*)0), (( void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_document_thumbnails_get_type ()), &g_implement_interface_info ); }; { const GInterfaceInfo g_implement_interface_info = { ( GInterfaceInitFunc) dvi_document_file_exporter_iface_init, (( void*)0), ((void*)0) }; g_type_module_add_interface (module, g_define_type_id , (ev_file_exporter_get_type ()), &g_implement_interface_info ); }; } return g_define_type_id; }; | |||
82 | ||||
83 | static gboolean | |||
84 | dvi_document_load (EvDocument *document, | |||
85 | const char *uri, | |||
86 | GError **error) | |||
87 | { | |||
88 | gchar *filename; | |||
89 | DviDocument *dvi_document = DVI_DOCUMENT(document)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((document)), ((dvi_document_get_type ())))))); | |||
90 | ||||
91 | filename = g_filename_from_uri (uri, NULL((void*)0), error); | |||
92 | if (!filename) | |||
93 | return FALSE; | |||
94 | ||||
95 | g_mutex_lock (&dvi_context_mutex); | |||
96 | if (dvi_document->context) | |||
97 | mdvi_destroy_context (dvi_document->context); | |||
98 | ||||
99 | dvi_document->context = mdvi_init_context(dvi_document->params, dvi_document->spec, filename); | |||
100 | g_mutex_unlock (&dvi_context_mutex); | |||
101 | g_free (filename); | |||
102 | ||||
103 | if (!dvi_document->context) { | |||
104 | g_set_error_literal (error, | |||
105 | EV_DOCUMENT_ERRORev_document_error_quark (), | |||
106 | EV_DOCUMENT_ERROR_INVALID, | |||
107 | _("DVI document has incorrect format")((char *) g_dgettext ("lector", "DVI document has incorrect format" ))); | |||
108 | return FALSE; | |||
109 | } | |||
110 | ||||
111 | mdvi_cairo_device_init (&dvi_document->context->device); | |||
112 | ||||
113 | ||||
114 | dvi_document->base_width = dvi_document->context->dvi_page_w * dvi_document->context->params.conv | |||
115 | + 2 * unit2pix(dvi_document->params->dpi, MDVI_HMARGIN"1in") / dvi_document->params->hshrink; | |||
116 | ||||
117 | dvi_document->base_height = dvi_document->context->dvi_page_h * dvi_document->context->params.vconv | |||
118 | + 2 * unit2pix(dvi_document->params->vdpi, MDVI_VMARGIN"1in") / dvi_document->params->vshrink; | |||
119 | ||||
120 | g_free (dvi_document->uri); | |||
121 | dvi_document->uri = g_strdup (uri)g_strdup_inline (uri); | |||
122 | ||||
123 | return TRUE; | |||
124 | } | |||
125 | ||||
126 | ||||
127 | static gboolean | |||
128 | dvi_document_save (EvDocument *document, | |||
129 | const char *uri, | |||
130 | GError **error) | |||
131 | { | |||
132 | DviDocument *dvi_document = DVI_DOCUMENT (document)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((document)), ((dvi_document_get_type ())))))); | |||
133 | ||||
134 | return ev_xfer_uri_simple (dvi_document->uri, uri, error); | |||
135 | } | |||
136 | ||||
137 | static int | |||
138 | dvi_document_get_n_pages (EvDocument *document) | |||
139 | { | |||
140 | DviDocument *dvi_document = DVI_DOCUMENT (document)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((document)), ((dvi_document_get_type ())))))); | |||
141 | ||||
142 | return dvi_document->context->npages; | |||
143 | } | |||
144 | ||||
145 | static void | |||
146 | dvi_document_get_page_size (EvDocument *document, | |||
147 | EvPage *page, | |||
148 | double *width, | |||
149 | double *height) | |||
150 | { | |||
151 | DviDocument *dvi_document = DVI_DOCUMENT (document)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((document)), ((dvi_document_get_type ())))))); | |||
152 | ||||
153 | *width = dvi_document->base_width; | |||
154 | *height = dvi_document->base_height;; | |||
155 | } | |||
156 | ||||
157 | static cairo_surface_t * | |||
158 | dvi_document_render (EvDocument *document, | |||
159 | EvRenderContext *rc) | |||
160 | { | |||
161 | cairo_surface_t *surface; | |||
162 | cairo_surface_t *rotated_surface; | |||
163 | DviDocument *dvi_document = DVI_DOCUMENT(document)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((document)), ((dvi_document_get_type ())))))); | |||
164 | gint required_width, required_height; | |||
165 | gint proposed_width, proposed_height; | |||
166 | gint xmargin = 0, ymargin = 0; | |||
167 | ||||
168 | /* We should protect our context since it's not | |||
169 | * thread safe. The work to the future - | |||
170 | * let context render page independently | |||
171 | */ | |||
172 | g_mutex_lock (&dvi_context_mutex); | |||
173 | ||||
174 | mdvi_setpage (dvi_document->context, rc->page->index); | |||
175 | ||||
176 | mdvi_set_shrink (dvi_document->context,mdvi_configure((dvi_document->context), MDVI_SET_XSHRINK, ( (int)((dvi_document->params->hshrink - 1) / rc->scale ) + 1), MDVI_SET_YSHRINK, ((int)((dvi_document->params-> vshrink - 1) / rc->scale) + 1), MDVI_PARAM_LAST) | |||
177 | (int)((dvi_document->params->hshrink - 1) / rc->scale) + 1,mdvi_configure((dvi_document->context), MDVI_SET_XSHRINK, ( (int)((dvi_document->params->hshrink - 1) / rc->scale ) + 1), MDVI_SET_YSHRINK, ((int)((dvi_document->params-> vshrink - 1) / rc->scale) + 1), MDVI_PARAM_LAST) | |||
178 | (int)((dvi_document->params->vshrink - 1) / rc->scale) + 1)mdvi_configure((dvi_document->context), MDVI_SET_XSHRINK, ( (int)((dvi_document->params->hshrink - 1) / rc->scale ) + 1), MDVI_SET_YSHRINK, ((int)((dvi_document->params-> vshrink - 1) / rc->scale) + 1), MDVI_PARAM_LAST); | |||
179 | ||||
180 | required_width = dvi_document->base_width * rc->scale + 0.5; | |||
181 | required_height = dvi_document->base_height * rc->scale + 0.5; | |||
182 | proposed_width = dvi_document->context->dvi_page_w * dvi_document->context->params.conv; | |||
183 | proposed_height = dvi_document->context->dvi_page_h * dvi_document->context->params.vconv; | |||
184 | ||||
185 | if (required_width >= proposed_width) | |||
186 | xmargin = (required_width - proposed_width) / 2; | |||
187 | if (required_height >= proposed_height) | |||
188 | ymargin = (required_height - proposed_height) / 2; | |||
189 | ||||
190 | mdvi_cairo_device_set_margins (&dvi_document->context->device, xmargin, ymargin); | |||
191 | mdvi_cairo_device_set_scale (&dvi_document->context->device, rc->scale); | |||
192 | mdvi_cairo_device_render (dvi_document->context); | |||
193 | surface = mdvi_cairo_device_get_surface (&dvi_document->context->device); | |||
194 | ||||
195 | g_mutex_unlock (&dvi_context_mutex); | |||
196 | ||||
197 | rotated_surface = ev_document_misc_surface_rotate_and_scale (surface, | |||
198 | required_width, | |||
199 | required_height, | |||
200 | rc->rotation); | |||
201 | cairo_surface_destroy (surface); | |||
202 | ||||
203 | return rotated_surface; | |||
204 | } | |||
205 | ||||
206 | static void | |||
207 | dvi_document_finalize (GObject *object) | |||
208 | { | |||
209 | DviDocument *dvi_document = DVI_DOCUMENT(object)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((object)), ((dvi_document_get_type ())))))); | |||
210 | ||||
211 | g_mutex_lock (&dvi_context_mutex); | |||
212 | if (dvi_document->context) { | |||
213 | mdvi_cairo_device_free (&dvi_document->context->device); | |||
214 | mdvi_destroy_context (dvi_document->context); | |||
215 | } | |||
216 | g_mutex_unlock (&dvi_context_mutex); | |||
217 | ||||
218 | if (dvi_document->params) | |||
219 | g_free (dvi_document->params); | |||
220 | ||||
221 | if (dvi_document->exporter_filename) | |||
222 | g_free (dvi_document->exporter_filename); | |||
223 | ||||
224 | if (dvi_document->exporter_opts) | |||
225 | g_string_free (dvi_document->exporter_opts, TRUE)(__builtin_constant_p (TRUE) ? ((TRUE) ? (g_string_free) ((dvi_document ->exporter_opts), (TRUE)) : g_string_free_and_steal (dvi_document ->exporter_opts)) : (g_string_free) ((dvi_document->exporter_opts ), (TRUE))); | |||
226 | ||||
227 | g_free (dvi_document->uri); | |||
228 | ||||
229 | G_OBJECT_CLASS (dvi_document_parent_class)((((GObjectClass*) (void *) g_type_check_class_cast ((GTypeClass *) ((dvi_document_parent_class)), (((GType) ((20) << (2 ))))))))->finalize (object); | |||
230 | } | |||
231 | ||||
232 | static gboolean | |||
233 | dvi_document_support_synctex (EvDocument *document) | |||
234 | { | |||
235 | return TRUE; | |||
236 | } | |||
237 | ||||
238 | static void | |||
239 | dvi_document_class_init (DviDocumentClass *klass) | |||
240 | { | |||
241 | GObjectClass *gobject_class = G_OBJECT_CLASS (klass)((((GObjectClass*) (void *) g_type_check_class_cast ((GTypeClass *) ((klass)), (((GType) ((20) << (2)))))))); | |||
242 | EvDocumentClass *ev_document_class = EV_DOCUMENT_CLASS (klass)((((EvDocumentClass*) (void *) g_type_check_class_cast ((GTypeClass *) ((klass)), ((ev_document_get_type ())))))); | |||
243 | ||||
244 | gobject_class->finalize = dvi_document_finalize; | |||
245 | ||||
246 | mdvi_init_kpathsea ("lector", MDVI_MFMODE((void*)0), MDVI_FALLBACK_FONT"cmr10", MDVI_DPI600, getenv("TEXMFCNF")); | |||
247 | ||||
248 | mdvi_register_special ("Color", "color", NULL((void*)0), dvi_document_do_color_special, 1); | |||
249 | mdvi_register_fonts (); | |||
250 | ||||
251 | ev_document_class->load = dvi_document_load; | |||
252 | ev_document_class->save = dvi_document_save; | |||
253 | ev_document_class->get_n_pages = dvi_document_get_n_pages; | |||
254 | ev_document_class->get_page_size = dvi_document_get_page_size; | |||
255 | ev_document_class->render = dvi_document_render; | |||
256 | ev_document_class->support_synctex = dvi_document_support_synctex; | |||
257 | } | |||
258 | ||||
259 | static void | |||
260 | dvi_document_thumbnails_get_dimensions (EvDocumentThumbnails *document, | |||
261 | EvRenderContext *rc, | |||
262 | gint *width, | |||
263 | gint *height) | |||
264 | { | |||
265 | DviDocument *dvi_document = DVI_DOCUMENT (document)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((document)), ((dvi_document_get_type ())))))); | |||
266 | gdouble page_width = dvi_document->base_width; | |||
267 | gdouble page_height = dvi_document->base_height; | |||
268 | ||||
269 | if (rc->rotation == 90 || rc->rotation == 270) { | |||
270 | *width = (gint) (page_height * rc->scale); | |||
271 | *height = (gint) (page_width * rc->scale); | |||
272 | } else { | |||
273 | *width = (gint) (page_width * rc->scale); | |||
274 | *height = (gint) (page_height * rc->scale); | |||
275 | } | |||
276 | } | |||
277 | ||||
278 | static GdkPixbuf * | |||
279 | dvi_document_thumbnails_get_thumbnail (EvDocumentThumbnails *document, | |||
280 | EvRenderContext *rc, | |||
281 | gboolean border) | |||
282 | { | |||
283 | DviDocument *dvi_document = DVI_DOCUMENT (document)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((document)), ((dvi_document_get_type ())))))); | |||
284 | GdkPixbuf *pixbuf; | |||
285 | GdkPixbuf *rotated_pixbuf; | |||
286 | cairo_surface_t *surface; | |||
287 | gint thumb_width, thumb_height; | |||
288 | gint proposed_width, proposed_height; | |||
289 | ||||
290 | thumb_width = (gint) (dvi_document->base_width * rc->scale); | |||
291 | thumb_height = (gint) (dvi_document->base_height * rc->scale); | |||
292 | ||||
293 | g_mutex_lock (&dvi_context_mutex); | |||
294 | ||||
295 | mdvi_setpage (dvi_document->context, rc->page->index); | |||
296 | ||||
297 | mdvi_set_shrink (dvi_document->context,mdvi_configure((dvi_document->context), MDVI_SET_XSHRINK, ( (int)dvi_document->base_width * dvi_document->params-> hshrink / thumb_width), MDVI_SET_YSHRINK, ((int)dvi_document-> base_height * dvi_document->params->vshrink / thumb_height ), MDVI_PARAM_LAST) | |||
298 | (int)dvi_document->base_width * dvi_document->params->hshrink / thumb_width,mdvi_configure((dvi_document->context), MDVI_SET_XSHRINK, ( (int)dvi_document->base_width * dvi_document->params-> hshrink / thumb_width), MDVI_SET_YSHRINK, ((int)dvi_document-> base_height * dvi_document->params->vshrink / thumb_height ), MDVI_PARAM_LAST) | |||
299 | (int)dvi_document->base_height * dvi_document->params->vshrink / thumb_height)mdvi_configure((dvi_document->context), MDVI_SET_XSHRINK, ( (int)dvi_document->base_width * dvi_document->params-> hshrink / thumb_width), MDVI_SET_YSHRINK, ((int)dvi_document-> base_height * dvi_document->params->vshrink / thumb_height ), MDVI_PARAM_LAST); | |||
300 | ||||
301 | proposed_width = dvi_document->context->dvi_page_w * dvi_document->context->params.conv; | |||
302 | proposed_height = dvi_document->context->dvi_page_h * dvi_document->context->params.vconv; | |||
303 | ||||
304 | if (border) { | |||
305 | mdvi_cairo_device_set_margins (&dvi_document->context->device, | |||
306 | MAX (thumb_width - proposed_width, 0)(((thumb_width - proposed_width) > (0)) ? (thumb_width - proposed_width ) : (0)) / 2, | |||
307 | MAX (thumb_height - proposed_height, 0)(((thumb_height - proposed_height) > (0)) ? (thumb_height - proposed_height) : (0)) / 2); | |||
308 | } else { | |||
309 | mdvi_cairo_device_set_margins (&dvi_document->context->device, | |||
310 | MAX (thumb_width - proposed_width - 2, 0)(((thumb_width - proposed_width - 2) > (0)) ? (thumb_width - proposed_width - 2) : (0)) / 2, | |||
311 | MAX (thumb_height - proposed_height - 2, 0)(((thumb_height - proposed_height - 2) > (0)) ? (thumb_height - proposed_height - 2) : (0)) / 2); | |||
312 | } | |||
313 | ||||
314 | mdvi_cairo_device_set_scale (&dvi_document->context->device, rc->scale); | |||
315 | mdvi_cairo_device_render (dvi_document->context); | |||
316 | surface = mdvi_cairo_device_get_surface (&dvi_document->context->device); | |||
317 | g_mutex_unlock (&dvi_context_mutex); | |||
318 | ||||
319 | pixbuf = ev_document_misc_pixbuf_from_surface (surface); | |||
320 | cairo_surface_destroy (surface); | |||
321 | ||||
322 | rotated_pixbuf = gdk_pixbuf_rotate_simple (pixbuf, 360 - rc->rotation); | |||
323 | g_object_unref (pixbuf); | |||
324 | ||||
325 | if (border) { | |||
326 | GdkPixbuf *tmp_pixbuf = rotated_pixbuf; | |||
327 | ||||
328 | rotated_pixbuf = ev_document_misc_get_thumbnail_frame (-1, -1, tmp_pixbuf); | |||
329 | g_object_unref (tmp_pixbuf); | |||
330 | } | |||
331 | ||||
332 | return rotated_pixbuf; | |||
333 | } | |||
334 | ||||
335 | static void | |||
336 | dvi_document_document_thumbnails_iface_init (EvDocumentThumbnailsInterface *iface) | |||
337 | { | |||
338 | iface->get_thumbnail = dvi_document_thumbnails_get_thumbnail; | |||
339 | iface->get_dimensions = dvi_document_thumbnails_get_dimensions; | |||
340 | } | |||
341 | ||||
342 | /* EvFileExporterIface */ | |||
343 | static void | |||
344 | dvi_document_file_exporter_begin (EvFileExporter *exporter, | |||
345 | EvFileExporterContext *fc) | |||
346 | { | |||
347 | DviDocument *dvi_document = DVI_DOCUMENT(exporter)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((exporter)), ((dvi_document_get_type ())))))); | |||
348 | ||||
349 | if (dvi_document->exporter_filename) | |||
350 | g_free (dvi_document->exporter_filename); | |||
351 | dvi_document->exporter_filename = g_strdup (fc->filename)g_strdup_inline (fc->filename); | |||
352 | ||||
353 | if (dvi_document->exporter_opts) { | |||
354 | g_string_free (dvi_document->exporter_opts, TRUE)(__builtin_constant_p (TRUE) ? ((TRUE) ? (g_string_free) ((dvi_document ->exporter_opts), (TRUE)) : g_string_free_and_steal (dvi_document ->exporter_opts)) : (g_string_free) ((dvi_document->exporter_opts ), (TRUE))); | |||
355 | } | |||
356 | dvi_document->exporter_opts = g_string_new ("-s "); | |||
357 | } | |||
358 | ||||
359 | static void | |||
360 | dvi_document_file_exporter_do_page (EvFileExporter *exporter, | |||
361 | EvRenderContext *rc) | |||
362 | { | |||
363 | DviDocument *dvi_document = DVI_DOCUMENT(exporter)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((exporter)), ((dvi_document_get_type ())))))); | |||
364 | ||||
365 | g_string_append_printf (dvi_document->exporter_opts, "%d,", (rc->page->index) + 1); | |||
366 | } | |||
367 | ||||
368 | static void | |||
369 | dvi_document_file_exporter_end (EvFileExporter *exporter) | |||
370 | { | |||
371 | gchar *command_line; | |||
372 | gint exit_stat; | |||
373 | GError *err = NULL((void*)0); | |||
374 | gboolean success; | |||
375 | ||||
376 | DviDocument *dvi_document = DVI_DOCUMENT(exporter)((((DviDocument*) (void *) g_type_check_instance_cast ((GTypeInstance *) ((exporter)), ((dvi_document_get_type ())))))); | |||
377 | gchar* quoted_filename = g_shell_quote (dvi_document->context->filename); | |||
378 | ||||
379 | command_line = g_strdup_printf ("dvipdfm %s -o %s %s", /* dvipdfm -s 1,2,.., -o exporter_filename dvi_filename */ | |||
380 | dvi_document->exporter_opts->str, | |||
381 | dvi_document->exporter_filename, | |||
382 | quoted_filename); | |||
383 | g_free (quoted_filename); | |||
384 | ||||
385 | success = g_spawn_command_line_sync (command_line, | |||
386 | NULL((void*)0), | |||
387 | NULL((void*)0), | |||
388 | &exit_stat, | |||
389 | &err); | |||
390 | ||||
391 | g_free (command_line); | |||
392 | ||||
393 | if (success == FALSE) { | |||
394 | g_warning ("Error: %s", err->message); | |||
395 | } else if (!WIFEXITED(exit_stat)(((exit_stat) & 0x7f) == 0) || WEXITSTATUS(exit_stat)(((exit_stat) & 0xff00) >> 8) != EXIT_SUCCESS0){ | |||
396 | g_warning ("Error: dvipdfm does not end normally or exit with a failure status."); | |||
397 | } | |||
398 | ||||
399 | if (err) | |||
400 | g_error_free (err); | |||
401 | } | |||
402 | ||||
403 | static EvFileExporterCapabilities | |||
404 | dvi_document_file_exporter_get_capabilities (EvFileExporter *exporter) | |||
405 | { | |||
406 | return EV_FILE_EXPORTER_CAN_PAGE_SET | | |||
407 | EV_FILE_EXPORTER_CAN_COPIES | | |||
408 | EV_FILE_EXPORTER_CAN_COLLATE | | |||
409 | EV_FILE_EXPORTER_CAN_REVERSE | | |||
410 | EV_FILE_EXPORTER_CAN_GENERATE_PDF; | |||
411 | } | |||
412 | ||||
413 | static void | |||
414 | dvi_document_file_exporter_iface_init (EvFileExporterInterface *iface) | |||
415 | { | |||
416 | iface->begin = dvi_document_file_exporter_begin; | |||
417 | iface->do_page = dvi_document_file_exporter_do_page; | |||
418 | iface->end = dvi_document_file_exporter_end; | |||
419 | iface->get_capabilities = dvi_document_file_exporter_get_capabilities; | |||
420 | } | |||
421 | ||||
422 | #define RGB2ULONG(r,g,b)((0xFF<<24)|(r<<16)|(g<<8)|(b)) ((0xFF<<24)|(r<<16)|(g<<8)|(b)) | |||
423 | ||||
424 | static gboolean | |||
425 | hsb2rgb (float h, float s, float v, guchar *red, guchar *green, guchar *blue) | |||
426 | { | |||
427 | float f, p, q, t, r, g, b; | |||
428 | int i; | |||
429 | ||||
430 | s /= 100; | |||
431 | v /= 100; | |||
432 | h /= 60; | |||
433 | i = floor (h); | |||
434 | if (i == 6) | |||
435 | i = 0; | |||
436 | else if ((i > 6) || (i < 0)) | |||
437 | return FALSE; | |||
438 | f = h - i; | |||
439 | p = v * (1 - s); | |||
440 | q = v * (1 - (s * f)); | |||
441 | t = v * (1 - (s * (1 - f))); | |||
442 | ||||
443 | if (i == 0) { | |||
444 | r = v; | |||
445 | g = t; | |||
446 | b = p; | |||
447 | } else if (i == 1) { | |||
448 | r = q; | |||
449 | g = v; | |||
450 | b = p; | |||
451 | } else if (i == 2) { | |||
452 | r = p; | |||
453 | g = v; | |||
454 | b = t; | |||
455 | } else if (i == 3) { | |||
456 | r = p; | |||
457 | g = q; | |||
458 | b = v; | |||
459 | } else if (i == 4) { | |||
460 | r = t; | |||
461 | g = p; | |||
462 | b = v; | |||
463 | } else if (i == 5) { | |||
464 | r = v; | |||
465 | g = p; | |||
466 | b = q; | |||
467 | } | |||
468 | ||||
469 | *red = (guchar)floor(r * 255.0); | |||
470 | *green = (guchar)floor(g * 255.0); | |||
471 | *blue = (guchar)floor(b * 255.0); | |||
472 | ||||
473 | return TRUE; | |||
474 | } | |||
475 | ||||
476 | static void | |||
477 | parse_color (const gchar *ptr, | |||
478 | gdouble *color, | |||
479 | gint n_color) | |||
480 | { | |||
481 | gchar *p = (gchar *)ptr; | |||
482 | gint i; | |||
483 | ||||
484 | for (i = 0; i < n_color; i++) { | |||
485 | while (isspace (*p)((*__ctype_b_loc ())[(int) ((*p))] & (unsigned short int) _ISspace)) p++; | |||
486 | color[i] = g_ascii_strtod (p, NULL((void*)0)); | |||
487 | while (!isspace (*p)((*__ctype_b_loc ())[(int) ((*p))] & (unsigned short int) _ISspace) && *p != '\0') p++; | |||
488 | if (*p == '\0') | |||
489 | break; | |||
490 | } | |||
491 | } | |||
492 | ||||
493 | static void | |||
494 | dvi_document_do_color_special (DviContext *dvi, const char *prefix, const char *arg) | |||
495 | { | |||
496 | if (strncmp (arg, "pop", 3) == 0) { | |||
| ||||
497 | mdvi_pop_color (dvi); | |||
498 | } else if (strncmp (arg, "push", 4) == 0) { | |||
499 | /* Find color source: Named, CMYK or RGB */ | |||
500 | const char *tmp = arg + 4; | |||
501 | ||||
502 | while (isspace (*tmp)((*__ctype_b_loc ())[(int) ((*tmp))] & (unsigned short int ) _ISspace)) tmp++; | |||
503 | ||||
504 | if (!strncmp ("rgb", tmp, 3)) { | |||
505 | gdouble rgb[3]; | |||
506 | guchar red, green, blue; | |||
507 | ||||
508 | parse_color (tmp + 4, rgb, 3); | |||
509 | ||||
510 | red = 255 * rgb[0]; | |||
511 | green = 255 * rgb[1]; | |||
512 | blue = 255 * rgb[2]; | |||
513 | ||||
514 | mdvi_push_color (dvi, RGB2ULONG (red, green, blue)((0xFF<<24)|(red<<16)|(green<<8)|(blue)), 0xFFFFFFFF); | |||
515 | } else if (!strncmp ("hsb", tmp, 4)) { | |||
516 | gdouble hsb[3]; | |||
517 | guchar red, green, blue; | |||
518 | ||||
519 | parse_color (tmp + 4, hsb, 3); | |||
520 | ||||
521 | if (hsb2rgb (hsb[0], hsb[1], hsb[2], &red, &green, &blue)) | |||
522 | mdvi_push_color (dvi, RGB2ULONG (red, green, blue)((0xFF<<24)|(red<<16)|(green<<8)|(blue)), 0xFFFFFFFF); | |||
523 | } else if (!strncmp ("cmyk", tmp, 4)) { | |||
524 | gdouble cmyk[4]; | |||
525 | double r, g, b; | |||
526 | guchar red, green, blue; | |||
527 | ||||
528 | parse_color (tmp + 5, cmyk, 4); | |||
529 | ||||
530 | r = 1.0 - cmyk[0] - cmyk[3]; | |||
| ||||
531 | if (r < 0.0) | |||
532 | r = 0.0; | |||
533 | g = 1.0 - cmyk[1] - cmyk[3]; | |||
534 | if (g < 0.0) | |||
535 | g = 0.0; | |||
536 | b = 1.0 - cmyk[2] - cmyk[3]; | |||
537 | if (b < 0.0) | |||
538 | b = 0.0; | |||
539 | ||||
540 | red = r * 255 + 0.5; | |||
541 | green = g * 255 + 0.5; | |||
542 | blue = b * 255 + 0.5; | |||
543 | ||||
544 | mdvi_push_color (dvi, RGB2ULONG (red, green, blue)((0xFF<<24)|(red<<16)|(green<<8)|(blue)), 0xFFFFFFFF); | |||
545 | } else if (!strncmp ("gray ", tmp, 5)) { | |||
546 | gdouble gray; | |||
547 | guchar rgb; | |||
548 | ||||
549 | parse_color (tmp + 5, &gray, 1); | |||
550 | ||||
551 | rgb = gray * 255 + 0.5; | |||
552 | ||||
553 | mdvi_push_color (dvi, RGB2ULONG (rgb, rgb, rgb)((0xFF<<24)|(rgb<<16)|(rgb<<8)|(rgb)), 0xFFFFFFFF); | |||
554 | } else { | |||
555 | CdkColor color; | |||
556 | ||||
557 | if (cdk_color_parse (tmp, &color)) { | |||
558 | guchar red, green, blue; | |||
559 | ||||
560 | red = color.red * 255 / 65535.; | |||
561 | green = color.green * 255 / 65535.; | |||
562 | blue = color.blue * 255 / 65535.; | |||
563 | ||||
564 | mdvi_push_color (dvi, RGB2ULONG (red, green, blue)((0xFF<<24)|(red<<16)|(green<<8)|(blue)), 0xFFFFFFFF); | |||
565 | } | |||
566 | } | |||
567 | } | |||
568 | } | |||
569 | ||||
570 | static void | |||
571 | dvi_document_init_params (DviDocument *dvi_document) | |||
572 | { | |||
573 | dvi_document->params = g_new0 (DviParams, 1)((DviParams *) g_malloc0_n ((1), sizeof (DviParams))); | |||
574 | ||||
575 | dvi_document->params->dpi = MDVI_DPI600; | |||
576 | dvi_document->params->vdpi = MDVI_VDPI600; | |||
577 | dvi_document->params->mag = MDVI_MAGNIFICATION1.0; | |||
578 | dvi_document->params->density = MDVI_DEFAULT_DENSITY50; | |||
579 | dvi_document->params->gamma = MDVI_DEFAULT_GAMMA1.0; | |||
580 | dvi_document->params->flags = MDVI_PARAM_ANTIALIASED1; | |||
581 | dvi_document->params->hdrift = 0; | |||
582 | dvi_document->params->vdrift = 0; | |||
583 | dvi_document->params->hshrink = MDVI_SHRINK_FROM_DPI(dvi_document->params->dpi)(((1) > ((dvi_document->params->dpi) / 75)) ? (1) : ( (dvi_document->params->dpi) / 75)); | |||
584 | dvi_document->params->vshrink = MDVI_SHRINK_FROM_DPI(dvi_document->params->vdpi)(((1) > ((dvi_document->params->vdpi) / 75)) ? (1) : ((dvi_document->params->vdpi) / 75)); | |||
585 | dvi_document->params->orientation = MDVI_ORIENT_TBLR; | |||
586 | ||||
587 | dvi_document->spec = NULL((void*)0); | |||
588 | ||||
589 | dvi_document->params->bg = 0xffffffff; | |||
590 | dvi_document->params->fg = 0xff000000; | |||
591 | } | |||
592 | ||||
593 | static void | |||
594 | dvi_document_init (DviDocument *dvi_document) | |||
595 | { | |||
596 | dvi_document->context = NULL((void*)0); | |||
597 | dvi_document_init_params (dvi_document); | |||
598 | ||||
599 | dvi_document->exporter_filename = NULL((void*)0); | |||
600 | dvi_document->exporter_opts = NULL((void*)0); | |||
601 | } |