1 /*
2 * gedit-statusbar.c
3 * This file is part of gedit
4 *
5 * Copyright (C) 2005 - Paolo Borelli
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, see <http://www.gnu.org/licenses/>.
19 */
20
21 #include "config.h"
22
23 #include "gedit-statusbar.h"
24
25 #include <string.h>
26 #include <glib/gi18n.h>
27 #include <gtk/gtk.h>
28
29 #include "gedit-app.h"
30 #include "gedit-status-menu-button.h"
31
32 struct _GeditStatusbar
33 {
34 GtkStatusbar parent_instance;
35
36 GtkWidget *error_frame;
37 GtkWidget *error_image;
38 GtkWidget *state_frame;
39 GtkWidget *load_image;
40 GtkWidget *save_image;
41 GtkWidget *print_image;
42 GtkWidget *overwrite_mode_label;
43
44 /* tmp flash timeout data */
45 guint flash_timeout;
46 guint flash_context_id;
47 guint flash_message_id;
48 };
49
G_DEFINE_TYPE(GeditStatusbar,gedit_statusbar,GTK_TYPE_STATUSBAR)50 G_DEFINE_TYPE (GeditStatusbar, gedit_statusbar, GTK_TYPE_STATUSBAR)
51
52 static gchar *
53 get_overwrite_mode_string (gboolean overwrite)
54 {
55 /* Use spaces to leave padding proportional to the font size */
56 return g_strdup_printf (" %s ", overwrite ? _("OVR") : _("INS"));
57 }
58
59 static gint
get_overwrite_mode_length(void)60 get_overwrite_mode_length (void)
61 {
62 return 4 + MAX (g_utf8_strlen (_("OVR"), -1), g_utf8_strlen (_("INS"), -1));
63 }
64
65 static void
gedit_statusbar_dispose(GObject * object)66 gedit_statusbar_dispose (GObject *object)
67 {
68 GeditStatusbar *statusbar = GEDIT_STATUSBAR (object);
69
70 if (statusbar->flash_timeout > 0)
71 {
72 g_source_remove (statusbar->flash_timeout);
73 statusbar->flash_timeout = 0;
74 }
75
76 G_OBJECT_CLASS (gedit_statusbar_parent_class)->dispose (object);
77 }
78
79 static void
gedit_statusbar_class_init(GeditStatusbarClass * klass)80 gedit_statusbar_class_init (GeditStatusbarClass *klass)
81 {
82 GObjectClass *object_class = G_OBJECT_CLASS (klass);
83 GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (klass);
84
85 object_class->dispose = gedit_statusbar_dispose;
86
87 gtk_widget_class_set_template_from_resource (widget_class,
88 "/org/gnome/gedit/ui/gedit-statusbar.ui");
89
90 gtk_widget_class_bind_template_child (widget_class, GeditStatusbar, error_frame);
91 gtk_widget_class_bind_template_child (widget_class, GeditStatusbar, error_image);
92 gtk_widget_class_bind_template_child (widget_class, GeditStatusbar, state_frame);
93 gtk_widget_class_bind_template_child (widget_class, GeditStatusbar, load_image);
94 gtk_widget_class_bind_template_child (widget_class, GeditStatusbar, save_image);
95 gtk_widget_class_bind_template_child (widget_class, GeditStatusbar, print_image);
96 gtk_widget_class_bind_template_child (widget_class, GeditStatusbar, overwrite_mode_label);
97 }
98
99 static void
gedit_statusbar_init(GeditStatusbar * statusbar)100 gedit_statusbar_init (GeditStatusbar *statusbar)
101 {
102 gtk_widget_init_template (GTK_WIDGET (statusbar));
103
104 gtk_label_set_width_chars (GTK_LABEL (statusbar->overwrite_mode_label),
105 get_overwrite_mode_length ());
106 }
107
108 /**
109 * gedit_statusbar_new:
110 *
111 * Creates a new #GeditStatusbar.
112 *
113 * Return value: the new #GeditStatusbar object
114 **/
115 GtkWidget *
gedit_statusbar_new(void)116 gedit_statusbar_new (void)
117 {
118 return GTK_WIDGET (g_object_new (GEDIT_TYPE_STATUSBAR, NULL));
119 }
120
121 /**
122 * gedit_statusbar_set_overwrite:
123 * @statusbar: a #GeditStatusbar
124 * @overwrite: if the overwrite mode is set
125 *
126 * Sets the overwrite mode on the statusbar.
127 **/
128 void
gedit_statusbar_set_overwrite(GeditStatusbar * statusbar,gboolean overwrite)129 gedit_statusbar_set_overwrite (GeditStatusbar *statusbar,
130 gboolean overwrite)
131 {
132 gchar *msg;
133
134 g_return_if_fail (GEDIT_IS_STATUSBAR (statusbar));
135
136 msg = get_overwrite_mode_string (overwrite);
137 gtk_label_set_text (GTK_LABEL (statusbar->overwrite_mode_label), msg);
138 g_free (msg);
139 }
140
141 void
gedit_statusbar_clear_overwrite(GeditStatusbar * statusbar)142 gedit_statusbar_clear_overwrite (GeditStatusbar *statusbar)
143 {
144 g_return_if_fail (GEDIT_IS_STATUSBAR (statusbar));
145
146 gtk_label_set_text (GTK_LABEL (statusbar->overwrite_mode_label), NULL);
147 }
148
149 static gboolean
remove_message_timeout(GeditStatusbar * statusbar)150 remove_message_timeout (GeditStatusbar *statusbar)
151 {
152 gtk_statusbar_remove (GTK_STATUSBAR (statusbar),
153 statusbar->flash_context_id,
154 statusbar->flash_message_id);
155
156 /* remove the timeout */
157 statusbar->flash_timeout = 0;
158 return FALSE;
159 }
160
161 /* FIXME this is an issue for introspection */
162 /**
163 * gedit_statusbar_flash_message:
164 * @statusbar: a #GeditStatusbar
165 * @context_id: message context_id
166 * @format: message to flash on the statusbar
167 * @...: the arguments to insert in @format
168 *
169 * Flash a temporary message on the statusbar.
170 */
171 void
gedit_statusbar_flash_message(GeditStatusbar * statusbar,guint context_id,const gchar * format,...)172 gedit_statusbar_flash_message (GeditStatusbar *statusbar,
173 guint context_id,
174 const gchar *format,
175 ...)
176 {
177 const guint32 flash_length = 3000; /* three seconds */
178 va_list args;
179 gchar *msg;
180
181 g_return_if_fail (GEDIT_IS_STATUSBAR (statusbar));
182 g_return_if_fail (format != NULL);
183
184 va_start (args, format);
185 msg = g_strdup_vprintf (format, args);
186 va_end (args);
187
188 /* remove a currently ongoing flash message */
189 if (statusbar->flash_timeout > 0)
190 {
191 g_source_remove (statusbar->flash_timeout);
192 statusbar->flash_timeout = 0;
193
194 gtk_statusbar_remove (GTK_STATUSBAR (statusbar),
195 statusbar->flash_context_id,
196 statusbar->flash_message_id);
197 }
198
199 statusbar->flash_context_id = context_id;
200 statusbar->flash_message_id = gtk_statusbar_push (GTK_STATUSBAR (statusbar),
201 context_id,
202 msg);
203
204 statusbar->flash_timeout = g_timeout_add (flash_length,
205 (GSourceFunc) remove_message_timeout,
206 statusbar);
207
208 g_free (msg);
209 }
210
211 void
gedit_statusbar_set_window_state(GeditStatusbar * statusbar,GeditWindowState state,gint num_of_errors)212 gedit_statusbar_set_window_state (GeditStatusbar *statusbar,
213 GeditWindowState state,
214 gint num_of_errors)
215 {
216 g_return_if_fail (GEDIT_IS_STATUSBAR (statusbar));
217
218 gtk_widget_hide (statusbar->state_frame);
219 gtk_widget_hide (statusbar->save_image);
220 gtk_widget_hide (statusbar->load_image);
221 gtk_widget_hide (statusbar->print_image);
222
223 if (state & GEDIT_WINDOW_STATE_SAVING)
224 {
225 gtk_widget_show (statusbar->state_frame);
226 gtk_widget_show (statusbar->save_image);
227 }
228 if (state & GEDIT_WINDOW_STATE_LOADING)
229 {
230 gtk_widget_show (statusbar->state_frame);
231 gtk_widget_show (statusbar->load_image);
232 }
233 if (state & GEDIT_WINDOW_STATE_PRINTING)
234 {
235 gtk_widget_show (statusbar->state_frame);
236 gtk_widget_show (statusbar->print_image);
237 }
238 if (state & GEDIT_WINDOW_STATE_ERROR)
239 {
240 gchar *tip;
241
242 tip = g_strdup_printf (ngettext("There is a tab with errors",
243 "There are %d tabs with errors",
244 num_of_errors),
245 num_of_errors);
246
247 gtk_widget_set_tooltip_text (statusbar->error_image, tip);
248 g_free (tip);
249
250 gtk_widget_show (statusbar->error_frame);
251 }
252 else
253 {
254 gtk_widget_hide (statusbar->error_frame);
255 }
256 }
257
258 /* ex:set ts=8 noet: */
259