Evince
Evince is a document viewer capable of displaying multiple and single page document formats like PDF and Postscript.
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Pages
ev-message-area.c
Go to the documentation of this file.
1 /* ev-message-area.c
2  * this file is part of evince, a gnome document viewer
3  *
4  * Copyright (C) 2007 Carlos Garcia Campos
5  *
6  * Author:
7  * Carlos Garcia Campos <carlosgc@gnome.org>
8  *
9  * Evince is free software; you can redistribute it and/or modify it
10  * under the terms of the GNU General Public License as published by
11  * the Free Software Foundation; either version 2 of the License, or
12  * (at your option) any later version.
13  *
14  * Evince is distributed in the hope that it will be useful, but
15  * WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17  * General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, write to the Free Software
21  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
22  */
23 
24 #include <config.h>
25 
26 #include "ev-message-area.h"
27 
28 #define EV_MESSAGE_AREA_GET_PRIVATE(obj) \
29  (G_TYPE_INSTANCE_GET_PRIVATE ((obj), EV_TYPE_MESSAGE_AREA, EvMessageAreaPrivate))
30 
32  GtkWidget *main_box;
33  GtkWidget *image;
34  GtkWidget *label;
35  GtkWidget *secondary_label;
36 
37  guint message_type : 3;
38 };
39 
40 enum {
45 };
46 
47 static void ev_message_area_set_property (GObject *object,
48  guint prop_id,
49  const GValue *value,
50  GParamSpec *pspec);
51 static void ev_message_area_get_property (GObject *object,
52  guint prop_id,
53  GValue *value,
54  GParamSpec *pspec);
55 
56 G_DEFINE_TYPE (EvMessageArea, ev_message_area, GTK_TYPE_INFO_BAR)
57 
58 static void
60 {
61  GObjectClass *gobject_class = G_OBJECT_CLASS (class);
62 
63  gobject_class->set_property = ev_message_area_set_property;
64  gobject_class->get_property = ev_message_area_get_property;
65 
66  g_object_class_install_property (gobject_class,
67  PROP_TEXT,
68  g_param_spec_string ("text",
69  "Text",
70  "The primary text of the message dialog",
71  NULL,
72  G_PARAM_READWRITE |
73  G_PARAM_STATIC_STRINGS));
74  g_object_class_install_property (gobject_class,
76  g_param_spec_string ("secondary-text",
77  "Secondary Text",
78  "The secondary text of the message dialog",
79  NULL,
80  G_PARAM_READWRITE |
81  G_PARAM_STATIC_STRINGS));
82  g_object_class_install_property (gobject_class,
83  PROP_IMAGE,
84  g_param_spec_object ("image",
85  "Image",
86  "The image",
87  GTK_TYPE_WIDGET,
88  G_PARAM_READWRITE |
89  G_PARAM_STATIC_STRINGS));
90 
91  g_type_class_add_private (gobject_class, sizeof (EvMessageAreaPrivate));
92 }
93 
94 static void
96 {
97  GtkWidget *hbox, *vbox;
98  GtkWidget *content_area;
99 
100  area->priv = EV_MESSAGE_AREA_GET_PRIVATE (area);
101 
102  area->priv->main_box = gtk_box_new (GTK_ORIENTATION_VERTICAL, 12);
103 
104  hbox = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, 12);
105  vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 12);
106 
107  area->priv->label = gtk_label_new (NULL);
108  gtk_label_set_use_markup (GTK_LABEL (area->priv->label), TRUE);
109  gtk_label_set_line_wrap (GTK_LABEL (area->priv->label), TRUE);
110  gtk_label_set_selectable (GTK_LABEL (area->priv->label), TRUE);
111  gtk_misc_set_alignment (GTK_MISC (area->priv->label), 0.0, 0.5);
112  gtk_widget_set_can_focus (area->priv->label, TRUE);
113  gtk_box_pack_start (GTK_BOX (vbox), area->priv->label, TRUE, TRUE, 0);
114  gtk_widget_show (area->priv->label);
115 
116  area->priv->secondary_label = gtk_label_new (NULL);
117  gtk_label_set_use_markup (GTK_LABEL (area->priv->secondary_label), TRUE);
118  gtk_label_set_line_wrap (GTK_LABEL (area->priv->secondary_label), TRUE);
119  gtk_label_set_selectable (GTK_LABEL (area->priv->secondary_label), TRUE);
120  gtk_misc_set_alignment (GTK_MISC (area->priv->secondary_label), 0.0, 0.5);
121  gtk_widget_set_can_focus (area->priv->secondary_label, TRUE);
122  gtk_box_pack_start (GTK_BOX (vbox), area->priv->secondary_label, TRUE, TRUE, 0);
123 
124  area->priv->image = gtk_image_new_from_stock (NULL, GTK_ICON_SIZE_DIALOG);
125  gtk_misc_set_alignment (GTK_MISC (area->priv->image), 0.5, 0.0);
126  gtk_box_pack_start (GTK_BOX (hbox), area->priv->image, FALSE, FALSE, 0);
127  gtk_widget_show (area->priv->image);
128 
129  gtk_box_pack_start (GTK_BOX (hbox), vbox, TRUE, TRUE, 0);
130  gtk_widget_show (vbox);
131 
132  gtk_box_pack_start (GTK_BOX (area->priv->main_box), hbox, TRUE, TRUE, 0);
133  gtk_widget_show (hbox);
134 
135  content_area = gtk_info_bar_get_content_area (GTK_INFO_BAR (area));
136  gtk_container_add (GTK_CONTAINER (content_area), area->priv->main_box);
137  gtk_widget_show (area->priv->main_box);
138 }
139 
140 static void
142  GtkMessageType type)
143 {
144  const gchar *stock_id = NULL;
145  AtkObject *atk_obj;
146 
147  switch (type) {
148  case GTK_MESSAGE_INFO:
149  stock_id = GTK_STOCK_DIALOG_INFO;
150  break;
151  case GTK_MESSAGE_QUESTION:
152  stock_id = GTK_STOCK_DIALOG_QUESTION;
153  break;
154  case GTK_MESSAGE_WARNING:
155  stock_id = GTK_STOCK_DIALOG_WARNING;
156  break;
157  case GTK_MESSAGE_ERROR:
158  stock_id = GTK_STOCK_DIALOG_ERROR;
159  break;
160  case GTK_MESSAGE_OTHER:
161  break;
162  default:
163  g_warning ("Unknown GtkMessageType %u", type);
164  break;
165  }
166 
167  if (stock_id)
168  gtk_image_set_from_stock (GTK_IMAGE (area->priv->image), stock_id,
169  GTK_ICON_SIZE_DIALOG);
170 
171  atk_obj = gtk_widget_get_accessible (GTK_WIDGET (area));
172  if (GTK_IS_ACCESSIBLE (atk_obj)) {
173  atk_object_set_role (atk_obj, ATK_ROLE_ALERT);
174  if (stock_id) {
175  GtkStockItem item;
176 
177  gtk_stock_lookup (stock_id, &item);
178  atk_object_set_name (atk_obj, item.label);
179  }
180  }
181 }
182 
183 static void
185  guint prop_id,
186  const GValue *value,
187  GParamSpec *pspec)
188 {
189  EvMessageArea *area = EV_MESSAGE_AREA (object);
190 
191  switch (prop_id) {
192  case PROP_TEXT:
193  ev_message_area_set_text (area, g_value_get_string (value));
194  break;
195  case PROP_SECONDARY_TEXT:
196  ev_message_area_set_secondary_text (area, g_value_get_string (value));
197  break;
198  case PROP_IMAGE:
199  ev_message_area_set_image (area, (GtkWidget *)g_value_get_object (value));
200  break;
201  default:
202  G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
203  break;
204  }
205 }
206 
207 static void
209  guint prop_id,
210  GValue *value,
211  GParamSpec *pspec)
212 {
213  EvMessageArea *area = EV_MESSAGE_AREA (object);
214 
215  switch (prop_id) {
216  case PROP_TEXT:
217  g_value_set_string (value, gtk_label_get_label (GTK_LABEL (area->priv->label)));
218  break;
219  case PROP_SECONDARY_TEXT:
220  g_value_set_string (value, gtk_label_get_label (GTK_LABEL (area->priv->secondary_label)));
221  break;
222  case PROP_IMAGE:
223  g_value_set_object (value, area->priv->image);
224  break;
225  default:
226  G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
227  break;
228  }
229 }
230 
231 void
233  const gchar *first_button_text,
234  va_list args)
235 {
236  const gchar* text;
237  gint response_id;
238 
239  if (first_button_text == NULL)
240  return;
241 
242  text = first_button_text;
243  response_id = va_arg (args, gint);
244 
245  while (text != NULL) {
246  gtk_info_bar_add_button (GTK_INFO_BAR (area), text, response_id);
247 
248  text = va_arg (args, gchar*);
249  if (text == NULL)
250  break;
251 
252  response_id = va_arg (args, int);
253  }
254 }
255 
256 GtkWidget *
258 {
259  return area->priv->main_box;
260 }
261 
262 GtkWidget *
263 ev_message_area_new (GtkMessageType type,
264  const gchar *text,
265  const gchar *first_button_text,
266  ...)
267 {
268  GtkWidget *widget;
269 
270  widget = g_object_new (EV_TYPE_MESSAGE_AREA,
271  "message-type", type,
272  "text", text,
273  NULL);
275  if (first_button_text) {
276  va_list args;
277 
278  va_start (args, first_button_text);
280  first_button_text, args);
281  va_end (args);
282  }
283 
284  return widget;
285 }
286 
287 void
289  GtkWidget *image)
290 {
291  GtkWidget *parent;
292 
293  g_return_if_fail (EV_IS_MESSAGE_AREA (area));
294 
295  area->priv->message_type = GTK_MESSAGE_OTHER;
296 
297  parent = gtk_widget_get_parent (area->priv->image);
298  gtk_container_add (GTK_CONTAINER (parent), image);
299  gtk_container_remove (GTK_CONTAINER (parent), area->priv->image);
300  gtk_box_reorder_child (GTK_BOX (parent), image, 0);
301 
302  area->priv->image = image;
303 
304  g_object_notify (G_OBJECT (area), "image");
305 }
306 
307 void
309  const gchar *stock_id)
310 {
311  g_return_if_fail (EV_IS_MESSAGE_AREA (area));
312  g_return_if_fail (stock_id != NULL);
313 
314  gtk_image_set_from_stock (GTK_IMAGE (area->priv->image),
315  stock_id,
316  GTK_ICON_SIZE_DIALOG);
317 }
318 
319 void
321  const gchar *str)
322 {
323  g_return_if_fail (EV_IS_MESSAGE_AREA (area));
324 
325  if (str) {
326  gchar *msg;
327 
328  msg = g_strdup_printf ("<b>%s</b>", str);
329  gtk_label_set_markup (GTK_LABEL (area->priv->label), msg);
330  g_free (msg);
331  } else {
332  gtk_label_set_markup (GTK_LABEL (area->priv->label), NULL);
333  }
334 
335  g_object_notify (G_OBJECT (area), "text");
336 }
337 
338 void
340  const gchar *str)
341 {
342  g_return_if_fail (EV_IS_MESSAGE_AREA (area));
343 
344  if (str) {
345  gchar *msg;
346 
347  msg = g_strdup_printf ("<small>%s</small>", str);
348  gtk_label_set_markup (GTK_LABEL (area->priv->secondary_label), msg);
349  g_free (msg);
350  gtk_widget_show (area->priv->secondary_label);
351  } else {
352  gtk_label_set_markup (GTK_LABEL (area->priv->secondary_label), NULL);
353  gtk_widget_hide (area->priv->secondary_label);
354  }
355 
356  g_object_notify (G_OBJECT (area), "secondary-text");
357 }