]> www.fi.muni.cz Git - evince.git/blob - thumbnailer/evince-thumbnailer.c
Include config.h. Bug #504721.
[evince.git] / thumbnailer / evince-thumbnailer.c
1 /*
2    Copyright (C) 2005 Fernando Herrera <fherrera@onirica.com>
3
4    This program is free software; you can redistribute it and/or modify
5    it under the terms of the GNU General Public License as published by
6    the Free Software Foundation; either version 2 of the License, or
7    (at your option) any later version.
8
9    This program is distributed in the hope that it will be useful,
10    but WITHOUT ANY WARRANTY; without even the implied warranty of
11    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12    GNU General Public License for more details.
13
14    You should have received a copy of the GNU General Public License
15    along with this program; if not, write to the Free Software
16    Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
17 */
18
19 #include <config.h>
20 #include <libgnomevfs/gnome-vfs-mime-utils.h>
21 #include <libgnomevfs/gnome-vfs-uri.h>
22 #include <libgnomevfs/gnome-vfs-utils.h>
23 #include <libgnomevfs/gnome-vfs-init.h>
24 #include <libgnomevfs/gnome-vfs-ops.h>
25
26 #include <ev-document.h>
27 #include <ev-document-thumbnails.h>
28 #include <ev-async-renderer.h>
29 #include <ev-document-factory.h>
30 #include <ev-backends-manager.h>
31
32 #include <stdlib.h>
33 #include <string.h>
34
35 #define THUMBNAIL_SIZE 128
36
37 struct AsyncData {
38         EvDocument  *document;
39         const gchar *output;
40         gint         size;
41         gboolean     success;
42 };
43
44 static EvDocument *
45 evince_thumbnailer_get_document (const gchar *uri)
46 {
47         EvDocument *document = NULL;
48         GError     *error = NULL;
49
50         document = ev_document_factory_get_document  (uri, &error);
51         if (error) {
52                 if (error->domain == EV_DOCUMENT_ERROR &&
53                     error->code == EV_DOCUMENT_ERROR_ENCRYPTED) {
54                         /* FIXME: Create a thumb for cryp docs */
55                         g_error_free (error);
56                         return NULL;
57                 }
58                 g_error_free (error);
59                 return NULL;
60         }
61         
62         return document;
63 }
64
65 static gboolean
66 evince_thumbnail_pngenc_get (EvDocument *document, const char *thumbnail, int size)
67 {
68         EvRenderContext *rc;
69         double width, height;
70         GdkPixbuf *pixbuf;
71
72         ev_document_get_page_size (document, 0, &width, &height);
73
74         rc = ev_render_context_new (0, 0, size / width);
75         pixbuf = ev_document_thumbnails_get_thumbnail (EV_DOCUMENT_THUMBNAILS (document),
76                                                        rc, FALSE);
77         g_object_unref (rc);
78         
79         if (pixbuf != NULL) {
80                 const char *overlaid_icon_name = NULL;
81
82                 if (overlaid_icon_name) {
83                         GdkPixbuf *overlaid_pixbuf;
84
85                         gchar *overlaid_icon_path = g_strdup_printf ("%s/%s", DATADIR, overlaid_icon_name);
86                         overlaid_pixbuf = gdk_pixbuf_new_from_file (overlaid_icon_path, NULL);
87                         g_free (overlaid_icon_path);
88                         if (overlaid_pixbuf != NULL) {
89                                 int delta_height, delta_width;
90                                 
91                                 delta_width = gdk_pixbuf_get_width (pixbuf) -
92                                         gdk_pixbuf_get_width (overlaid_pixbuf);
93                                 delta_height = gdk_pixbuf_get_height (pixbuf) -
94                                         gdk_pixbuf_get_height (overlaid_pixbuf);
95                                 
96                                 gdk_pixbuf_composite (overlaid_pixbuf, pixbuf,
97                                                       delta_width, delta_height,
98                                                       gdk_pixbuf_get_width (overlaid_pixbuf),
99                                                       gdk_pixbuf_get_height (overlaid_pixbuf),
100                                                       delta_width, delta_height,
101                                                       1, 1,
102                                                       GDK_INTERP_NEAREST, 100);
103                                 
104                                 g_object_unref  (overlaid_pixbuf);
105                         }
106                 }
107                 
108                 if (gdk_pixbuf_save (pixbuf, thumbnail, "png", NULL, NULL)) {
109                         g_object_unref  (pixbuf);
110                         return TRUE;
111                 }
112
113                 g_object_unref  (pixbuf);
114         }
115         
116         return FALSE;
117 }
118
119 static gpointer
120 evince_thumbnail_pngenc_get_async (struct AsyncData *data)
121 {
122         ev_document_doc_mutex_lock ();
123         data->success = evince_thumbnail_pngenc_get (data->document,
124                                                      data->output,
125                                                      data->size);
126         ev_document_doc_mutex_unlock ();
127         
128         g_idle_add ((GSourceFunc)gtk_main_quit, NULL);
129         
130         return NULL;
131 }
132
133 int
134 main (int argc, char *argv[])
135 {
136         EvDocument *document;
137         const char *input;
138         const char *output;
139         int         size;
140         char       *uri;
141
142         if (argc <= 2 || argc > 5 || strcmp (argv[1], "-h") == 0 ||
143             strcmp (argv[1], "--help") == 0) {
144                 g_print ("Usage: %s [-s <size>] <input> <output>\n", argv[0]);
145                 return -1;
146         }
147
148         if (!strcmp (argv[1], "-s")) {
149                 input = argv[3];
150                 output = argv[4];
151                 size = atoi (argv[2]);
152         } else {
153                 input = argv[1];
154                 output = argv[2];
155                 size = THUMBNAIL_SIZE;
156         }
157
158         if (size < 40) {
159                 g_print ("Size cannot be smaller than 40 pixels\n");
160                 return -1;
161         }
162
163         if (!g_thread_supported ())
164                 g_thread_init (NULL);
165         
166         gnome_vfs_init ();
167
168         ev_backends_manager_init ();
169
170         uri = gnome_vfs_make_uri_from_shell_arg (input);
171         document = evince_thumbnailer_get_document (uri);
172         g_free (uri);
173
174         if (!document) {
175                 ev_backends_manager_shutdown ();
176                 return -2;
177         }
178
179         if (!EV_IS_DOCUMENT_THUMBNAILS (document)) {
180                 g_object_unref (document);
181                 ev_backends_manager_shutdown ();
182                 return -2;
183         }
184
185         if (EV_IS_ASYNC_RENDERER (document)) {
186                 struct AsyncData data;
187
188                 gtk_init (&argc, &argv);
189                 
190                 data.document = document;
191                 data.output = output;
192                 data.size = size;
193
194                 g_thread_create ((GThreadFunc) evince_thumbnail_pngenc_get_async,
195                                  &data, FALSE, NULL);
196                 
197                 gtk_main ();
198
199                 g_object_unref (document);
200                 ev_backends_manager_shutdown ();
201
202                 return data.success ? 0 : -2;
203         }
204
205         if (!evince_thumbnail_pngenc_get (document, output, size)) {
206                 g_object_unref (document);
207                 ev_backends_manager_shutdown ();
208                 return -2;
209         }
210
211         g_object_unref (document);
212         ev_backends_manager_shutdown ();
213
214         return 0;
215 }