]> www.fi.muni.cz Git - evince.git/blob - backend/ev-link.c
57af5fa26151bb2049c9e247ef0e6b4ca02fc81e
[evince.git] / backend / ev-link.c
1 /* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8; c-indent-level: 8 -*- */
2 /* this file is part of evince, a gnome document viewer
3  *
4  *  Copyright (C) 2005 Red Hat, Inc.
5  *
6  * Evince is free software; you can redistribute it and/or modify it
7  * under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * Evince is distributed in the hope that it will be useful, but
12  * WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
19  */
20
21 #ifdef HAVE_CONFIG_H
22 #include "config.h"
23 #endif
24
25 #include "ev-link.h"
26
27 enum {
28         PROP_0,
29         PROP_TITLE,
30         PROP_TYPE,
31         PROP_PAGE,
32         PROP_URI,
33         PROP_LEFT,
34         PROP_TOP,
35         PROP_BOTTOM,
36         PROP_RIGHT,
37         PROP_ZOOM
38 };
39
40
41 struct _EvLink {
42         GObject base_instance;
43         EvLinkPrivate *priv;
44 };
45
46 struct _EvLinkClass {
47         GObjectClass base_class;
48 };
49
50 struct _EvLinkPrivate {
51         char *title;
52         char *uri;
53         EvLinkType type;
54         int page;
55         double top;
56         double left;
57         double bottom;
58         double right;
59         double zoom;
60 };
61
62 G_DEFINE_TYPE (EvLink, ev_link, G_TYPE_OBJECT)
63
64 #define EV_LINK_GET_PRIVATE(object) \
65         (G_TYPE_INSTANCE_GET_PRIVATE ((object), EV_TYPE_LINK, EvLinkPrivate))
66
67 GType
68 ev_link_type_get_type (void)
69 {
70         static GType type = 0;
71
72         if (G_UNLIKELY (type == 0)) {
73                 static const GEnumValue values[] = {
74                         { EV_LINK_TYPE_TITLE, "EV_LINK_TYPE_TITLE", "title" },
75                         { EV_LINK_TYPE_PAGE, "EV_LINK_TYPE_PAGE", "page" },
76                         { EV_LINK_TYPE_PAGE_XYZ, "EV_LINK_TYPE_PAGE_XYZ", "page-xyz" },
77                         { EV_LINK_TYPE_PAGE_FIT, "EV_LINK_TYPE_PAGE_FIT", "page-fit" },
78                         { EV_LINK_TYPE_PAGE_FITH, "EV_LINK_TYPE_PAGE_FITH", "page-fith" },
79                         { EV_LINK_TYPE_PAGE_FITV, "EV_LINK_TYPE_PAGE_FITV", "page-fitv" },
80                         { EV_LINK_TYPE_PAGE_FITR, "EV_LINK_TYPE_PAGE_FITR", "page-fitr" },
81                         { EV_LINK_TYPE_EXTERNAL_URI, "EV_LINK_TYPE_EXTERNAL_URI", "external" },
82                         { 0, NULL, NULL }
83                 };
84
85                 type = g_enum_register_static ("EvLinkType", values);
86         }
87
88         return type;
89 }
90
91 const char *
92 ev_link_get_title (EvLink *self)
93 {
94         g_return_val_if_fail (EV_IS_LINK (self), NULL);
95         
96         return self->priv->title;
97 }
98
99 const char *
100 ev_link_get_uri (EvLink *self)
101 {
102         g_return_val_if_fail (EV_IS_LINK (self), NULL);
103         
104         return self->priv->uri;
105 }
106
107 EvLinkType
108 ev_link_get_link_type (EvLink *self)
109 {
110         g_return_val_if_fail (EV_IS_LINK (self), 0);
111         
112         return self->priv->type;
113 }
114
115 int
116 ev_link_get_page (EvLink *self)
117 {
118         g_return_val_if_fail (EV_IS_LINK (self), 0);
119         
120         return self->priv->page;
121 }
122
123 double
124 ev_link_get_top (EvLink *self)
125 {
126         g_return_val_if_fail (EV_IS_LINK (self), 0);
127         
128         return self->priv->top;
129 }
130
131 double
132 ev_link_get_left (EvLink *self)
133 {
134         g_return_val_if_fail (EV_IS_LINK (self), 0);
135         
136         return self->priv->left;
137 }
138
139 double
140 ev_link_get_bottom (EvLink *self)
141 {
142         g_return_val_if_fail (EV_IS_LINK (self), 0);
143         
144         return self->priv->bottom;
145 }
146
147 double
148 ev_link_get_right (EvLink *self)
149 {
150         g_return_val_if_fail (EV_IS_LINK (self), 0);
151         
152         return self->priv->right;
153 }
154
155 double
156 ev_link_get_zoom (EvLink *self)
157 {
158         g_return_val_if_fail (EV_IS_LINK (self), 0);
159         
160         return self->priv->zoom;
161 }
162
163 static void
164 ev_link_get_property (GObject *object, guint prop_id, GValue *value,
165                       GParamSpec *param_spec)
166 {
167         EvLink *self;
168
169         self = EV_LINK (object);
170
171         switch (prop_id) {
172         case PROP_TITLE:
173                 g_value_set_string (value, self->priv->title);
174                 break;
175         case PROP_URI:
176                 g_value_set_string (value, self->priv->uri);
177                 break;
178         case PROP_TYPE:
179                 g_value_set_enum (value, self->priv->type);
180                 break;
181         case PROP_PAGE:
182                 g_value_set_int (value, self->priv->page);
183                 break;
184         case PROP_TOP:
185                 g_value_set_double (value, self->priv->top);
186                 break;
187         case PROP_LEFT:
188                 g_value_set_double (value, self->priv->left);
189                 break;
190         case PROP_BOTTOM:
191                 g_value_set_double (value, self->priv->bottom);
192                 break;
193         case PROP_RIGHT:
194                 g_value_set_double (value, self->priv->left);
195                 break;
196         case PROP_ZOOM:
197                 g_value_set_double (value, self->priv->zoom);
198                 break;
199         default:
200                 G_OBJECT_WARN_INVALID_PROPERTY_ID (object,
201                                                    prop_id,
202                                                    param_spec);
203                 break;
204         }
205 }
206
207 static void
208 ev_link_set_property (GObject *object, guint prop_id, const GValue *value,
209                       GParamSpec *param_spec)
210 {
211         EvLink *link = EV_LINK (object);
212         
213         switch (prop_id) {
214         case PROP_TITLE:
215                 link->priv->title = g_strdup (g_value_get_string (value));      
216                 break;
217         case PROP_URI:
218                 link->priv->uri = g_strdup (g_value_get_string (value));
219                 break;
220         case PROP_TYPE:
221                 link->priv->type = g_value_get_enum (value);
222                 break;
223         case PROP_PAGE:
224                 link->priv->page = g_value_get_int (value);
225                 break;
226         case PROP_TOP:
227                 link->priv->top = g_value_get_double (value);
228                 break;
229         case PROP_LEFT:
230                 link->priv->left = g_value_get_double (value);
231                 break;
232         case PROP_BOTTOM:
233                 link->priv->bottom = g_value_get_double (value);
234                 break;
235         case PROP_RIGHT:
236                 link->priv->right = g_value_get_double (value);
237                 break;
238         case PROP_ZOOM:
239                 link->priv->zoom = g_value_get_double (value);
240                 break;
241
242         default:
243                 G_OBJECT_WARN_INVALID_PROPERTY_ID (object,
244                                                    prop_id,
245                                                    param_spec);
246                 break;
247         }
248 }
249
250 static void
251 ev_window_dispose (GObject *object)
252 {
253         EvLinkPrivate *priv;
254
255         g_return_if_fail (EV_IS_LINK (object));
256
257         priv = EV_LINK (object)->priv;
258
259         if (priv->title) {
260                 g_free (priv->title);
261                 priv->title = NULL;
262         }
263
264         if (priv->uri) {
265                 g_free (priv->uri);
266                 priv->uri = NULL;
267         }
268
269         G_OBJECT_CLASS (ev_link_parent_class)->dispose (object);
270 }
271
272 static void
273 ev_link_init (EvLink *ev_link)
274 {
275         ev_link->priv = EV_LINK_GET_PRIVATE (ev_link);
276
277         ev_link->priv->type = EV_LINK_TYPE_TITLE;
278 }
279
280 static void
281 ev_link_class_init (EvLinkClass *ev_window_class)
282 {
283         GObjectClass *g_object_class;
284
285         g_object_class = G_OBJECT_CLASS (ev_window_class);
286         g_object_class->dispose = ev_window_dispose;
287         g_object_class->set_property = ev_link_set_property;
288         g_object_class->get_property = ev_link_get_property;
289
290         g_type_class_add_private (g_object_class, sizeof (EvLinkPrivate));
291
292         g_object_class_install_property (g_object_class,
293                                          PROP_TITLE,
294                                          g_param_spec_string ("title",
295                                                               "Link Title",
296                                                               "The link title",
297                                                               NULL,
298                                                               G_PARAM_READWRITE |
299                                                               G_PARAM_CONSTRUCT_ONLY));
300         g_object_class_install_property (g_object_class,
301                                          PROP_URI,
302                                          g_param_spec_string ("uri",
303                                                               "Link URI",
304                                                               "The link URI",
305                                                               NULL,
306                                                               G_PARAM_READWRITE |
307                                                               G_PARAM_CONSTRUCT_ONLY));
308         g_object_class_install_property (g_object_class,
309                                          PROP_TYPE,
310                                          g_param_spec_enum  ("type",
311                                                              "Link Type",
312                                                              "The link type",
313                                                              EV_TYPE_LINK_TYPE,
314                                                              EV_LINK_TYPE_TITLE,
315                                                              G_PARAM_READWRITE |
316                                                              G_PARAM_CONSTRUCT_ONLY));
317         g_object_class_install_property (g_object_class,
318                                          PROP_PAGE,
319                                          g_param_spec_int ("page",
320                                                            "Link Page",
321                                                            "The link page",
322                                                             -1,
323                                                             G_MAXINT,
324                                                             0,
325                                                             G_PARAM_READWRITE |
326                                                             G_PARAM_CONSTRUCT_ONLY));
327         g_object_class_install_property (g_object_class,
328                                          PROP_LEFT,
329                                          g_param_spec_double ("left",
330                                                               "Left coordinate",
331                                                               "The left coordinate",
332                                                               -G_MAXDOUBLE,
333                                                               G_MAXDOUBLE,
334                                                               0,
335                                                               G_PARAM_READWRITE |
336                                                               G_PARAM_CONSTRUCT_ONLY));
337         g_object_class_install_property (g_object_class,
338                                          PROP_TOP,
339                                          g_param_spec_double ("top",
340                                                               "Top coordinate",
341                                                               "The top coordinate",
342                                                               -G_MAXDOUBLE,
343                                                               G_MAXDOUBLE,
344                                                               0,
345                                                               G_PARAM_READWRITE |
346                                                               G_PARAM_CONSTRUCT_ONLY));
347         g_object_class_install_property (g_object_class,
348                                          PROP_BOTTOM,
349                                          g_param_spec_double ("bottom",
350                                                               "Bottom coordinate",
351                                                               "The bottom coordinate",
352                                                               -G_MAXDOUBLE,
353                                                               G_MAXDOUBLE,
354                                                               0,
355                                                               G_PARAM_READWRITE |
356                                                               G_PARAM_CONSTRUCT_ONLY));
357         g_object_class_install_property (g_object_class,
358                                          PROP_RIGHT,
359                                          g_param_spec_double ("right",
360                                                               "Right coordinate",
361                                                               "The right coordinate",
362                                                               -G_MAXDOUBLE,
363                                                               G_MAXDOUBLE,
364                                                               0,
365                                                               G_PARAM_READWRITE |
366                                                               G_PARAM_CONSTRUCT_ONLY));
367
368         g_object_class_install_property (g_object_class,
369                                          PROP_ZOOM,
370                                          g_param_spec_double ("zoom",
371                                                               "Zoom",
372                                                               "Zoom",
373                                                               0,
374                                                               G_MAXDOUBLE,
375                                                               0,
376                                                               G_PARAM_READWRITE |
377                                                               G_PARAM_CONSTRUCT_ONLY));
378 }
379
380 EvLink *
381 ev_link_new_title (const char *title)
382 {
383         return EV_LINK (g_object_new (EV_TYPE_LINK,
384                                       "title", title,
385                                       "type", EV_LINK_TYPE_TITLE,
386                                       NULL));
387 }
388
389 EvLink *
390 ev_link_new_page (const char *title, int page)
391 {
392         return EV_LINK (g_object_new (EV_TYPE_LINK,
393                                       "title", title,
394                                       "page", page,
395                                       "type", EV_LINK_TYPE_PAGE,
396                                       NULL));
397 }
398
399 EvLink *
400 ev_link_new_page_xyz (const char *title,
401                       int         page,
402                       double      left,
403                       double      top,
404                       double      zoom)
405 {
406         return EV_LINK (g_object_new (EV_TYPE_LINK,
407                                       "title", title,
408                                       "page", page,
409                                       "type", EV_LINK_TYPE_PAGE_XYZ,
410                                       "left", left,
411                                       "top", top,
412                                       "zoom", zoom,
413                                       NULL));
414 }
415
416 EvLink *
417 ev_link_new_page_fit (const char *title,
418                       int         page)
419 {
420         return EV_LINK (g_object_new (EV_TYPE_LINK,
421                                       "title", title,
422                                       "page", page,
423                                       "type", EV_LINK_TYPE_PAGE_FIT,
424                                       NULL));
425 }
426
427 EvLink *
428 ev_link_new_page_fith (const char *title,
429                        int         page,
430                        double      top)
431 {
432         return EV_LINK (g_object_new (EV_TYPE_LINK,
433                                       "title", title,
434                                       "page", page,
435                                       "type", EV_LINK_TYPE_PAGE_FITH,
436                                       "top", top,
437                                       NULL));
438 }
439
440 EvLink *
441 ev_link_new_page_fitv (const char *title,
442                        int         page,
443                        double      left)
444 {
445         return EV_LINK (g_object_new (EV_TYPE_LINK,
446                                       "title", title,
447                                       "page", page,
448                                       "type", EV_LINK_TYPE_PAGE_FITV,
449                                       "left", left,
450                                       NULL));
451 }
452
453 EvLink *
454 ev_link_new_page_fitr (const char     *title,
455                        int             page,
456                        double          left,
457                        double          bottom,
458                        double          right,
459                        double          top)
460 {
461         return EV_LINK (g_object_new (EV_TYPE_LINK,
462                                       "title", title,
463                                       "page", page,
464                                       "type", EV_LINK_TYPE_PAGE_FITR,
465                                       "left", left,
466                                       "bottom", bottom,
467                                       "right", right,
468                                       "top", top,
469                                       NULL));
470 }
471
472 EvLink *
473 ev_link_new_external (const char *title, const char *uri)
474 {
475         return EV_LINK (g_object_new (EV_TYPE_LINK,
476                                       "title", title,
477                                       "uri", uri,
478                                       "type", EV_LINK_TYPE_EXTERNAL_URI,
479                                       NULL));
480 }
481
482
483
484 static void
485 ev_link_mapping_free_foreach (EvLinkMapping *mapping)
486 {
487         g_object_unref (G_OBJECT (mapping->link));
488         g_free (mapping);
489 }
490
491 void
492 ev_link_mapping_free (GList *link_mapping)
493 {
494         if (link_mapping == NULL)
495                 return;
496
497         g_list_foreach (link_mapping, (GFunc) (ev_link_mapping_free_foreach), NULL);
498         g_list_free (link_mapping);
499 }
500
501
502 EvLink *
503 ev_link_mapping_find (GList   *link_mapping,
504                       gdouble  x,
505                       gdouble  y)
506 {
507         GList *list;
508         EvLink *link = NULL;
509         int i;
510         
511         i = 0;
512
513         for (list = link_mapping; list; list = list->next) {
514                 EvLinkMapping *mapping = list->data;
515
516                 i++;
517                 if ((x >= mapping->x1) &&
518                     (y >= mapping->y1) &&
519                     (x <= mapping->x2) &&
520                     (y <= mapping->y2)) {
521                         link = mapping->link;
522                         break;
523                 }
524         }
525
526         return link;
527 }
528