~midori/midori/webKitTwoOnly

« back to all changes in this revision

Viewing changes to toolbars/midori-transferbar.c

  • Committer: Christian Dywan
  • Date: 2010-06-17 18:17:21 UTC
  • Revision ID: git-v1:fa08c4d1f9056eb2eae6321f228e62aa0dea758d
Refactor transferbar into MidoriTransferbar

The transferbar is separated from the browser, albeit it is still
created and filled from within the browser so it is not completely
independent.

The new class now keeps a list of TransferInfo items to keep track
of transfers and queries the status from the download object.

Destroying a button belonging to a transfer is connected to
removing it from the list and cleaning up the info structure. Also
the Clear button is updated from the destroy handler.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 Copyright (C) 2010 Christian Dywan <christian@twotoasts.de>
 
3
 
 
4
 This library is free software; you can redistribute it and/or
 
5
 modify it under the terms of the GNU Lesser General Public
 
6
 License as published by the Free Software Foundation; either
 
7
 version 2.1 of the License, or (at your option) any later version.
 
8
 
 
9
 See the file COPYING for the full license text.
 
10
*/
 
11
 
 
12
#include "midori-transferbar.h"
 
13
 
 
14
#include "midori-browser.h"
 
15
#include "sokoke.h"
 
16
 
 
17
#include <glib/gi18n.h>
 
18
 
 
19
struct _MidoriTransferbar
 
20
{
 
21
    GtkToolbar parent_instance;
 
22
 
 
23
    GList* infos;
 
24
    GtkToolItem* clear;
 
25
};
 
26
 
 
27
struct _MidoriTransferbarClass
 
28
{
 
29
    GtkToolbarClass parent_class;
 
30
};
 
31
 
 
32
G_DEFINE_TYPE (MidoriTransferbar, midori_transferbar, GTK_TYPE_TOOLBAR);
 
33
 
 
34
static void
 
35
midori_transferbar_class_init (MidoriTransferbarClass* class)
 
36
{
 
37
    /* Nothing to do */
 
38
}
 
39
 
 
40
#if WEBKIT_CHECK_VERSION (1, 1, 3)
 
41
typedef struct
 
42
{
 
43
    WebKitDownload* download;
 
44
    GtkWidget* button;
 
45
    GtkWidget* toolitem;
 
46
    MidoriTransferbar* transferbar;
 
47
} TransferInfo;
 
48
 
 
49
static gboolean
 
50
midori_transferbar_info_free (gpointer data)
 
51
{
 
52
    TransferInfo* info = data;
 
53
    MidoriTransferbar* transferbar = info->transferbar;
 
54
 
 
55
    transferbar->infos = g_list_remove (transferbar->infos, info);
 
56
    g_object_unref (info->download);
 
57
    gtk_widget_destroy (info->toolitem);
 
58
    g_free (info);
 
59
 
 
60
    if (!transferbar->infos || !g_list_nth_data (transferbar->infos, 0))
 
61
        gtk_widget_hide (GTK_WIDGET (transferbar->clear));
 
62
 
 
63
    return FALSE;
 
64
}
 
65
 
 
66
static void
 
67
midori_transferbar_button_destroy_cb (GtkWidget*    button,
 
68
                                      TransferInfo* info)
 
69
{
 
70
    g_idle_add (midori_transferbar_info_free, info);
 
71
}
 
72
 
 
73
static void
 
74
midori_transferbar_download_notify_progress_cb (WebKitDownload* download,
 
75
                                                GParamSpec*     pspec,
 
76
                                                GtkWidget*      progress)
 
77
{
 
78
    gchar* current;
 
79
    gchar* total;
 
80
    gchar* size_text;
 
81
    gchar* text;
 
82
 
 
83
    gtk_progress_bar_set_fraction (GTK_PROGRESS_BAR (progress),
 
84
        webkit_download_get_progress (download));
 
85
 
 
86
    current = g_format_size_for_display (webkit_download_get_current_size (download));
 
87
    total = g_format_size_for_display (webkit_download_get_total_size (download));
 
88
    size_text = g_strdup_printf (_("%s of %s"), current, total);
 
89
    g_free (current);
 
90
    g_free (total);
 
91
    text = g_strdup_printf ("%s (%s)",
 
92
        gtk_progress_bar_get_text (GTK_PROGRESS_BAR (progress)),
 
93
        size_text);
 
94
    gtk_widget_set_tooltip_text (progress, text);
 
95
}
 
96
 
 
97
static void
 
98
midori_transferbar_download_notify_status_cb (WebKitDownload* download,
 
99
                                              GParamSpec*     pspec,
 
100
                                              TransferInfo*   info)
 
101
{
 
102
    GtkWidget* button = info->button;
 
103
    GtkWidget* icon;
 
104
 
 
105
    switch (webkit_download_get_status (download))
 
106
    {
 
107
        case WEBKIT_DOWNLOAD_STATUS_FINISHED:
 
108
        {
 
109
            MidoriBrowser* browser = midori_browser_get_for_widget (button);
 
110
            MidoriWebSettings* settings = midori_browser_get_settings (browser);
 
111
 
 
112
            icon = gtk_image_new_from_stock (GTK_STOCK_OPEN, GTK_ICON_SIZE_MENU);
 
113
            gtk_button_set_image (GTK_BUTTON (button), icon);
 
114
            if (g_object_get_data (G_OBJECT (download), "open-download"))
 
115
                gtk_button_clicked (GTK_BUTTON (button));
 
116
 
 
117
            if (katze_object_get_boolean (settings, "notify-transfer-completed"))
 
118
            {
 
119
                const gchar* uri = webkit_download_get_destination_uri (download);
 
120
                gchar* path = soup_uri_decode (uri);
 
121
                gchar* filename = g_strrstr (path, "/") + 1;
 
122
                gchar* msg = g_strdup_printf (
 
123
                    _("The file '<b>%s</b>' has been downloaded."), filename);
 
124
                g_free (path);
 
125
                g_signal_emit_by_name (browser, "send-notification",
 
126
                                       _("Transfer completed"), msg);
 
127
                g_free (msg);
 
128
            }
 
129
            break;
 
130
        }
 
131
        case WEBKIT_DOWNLOAD_STATUS_CANCELLED:
 
132
        case WEBKIT_DOWNLOAD_STATUS_ERROR:
 
133
            icon = gtk_image_new_from_stock (GTK_STOCK_CLEAR, GTK_ICON_SIZE_MENU);
 
134
            gtk_button_set_image (GTK_BUTTON (button), icon);
 
135
            break;
 
136
        default:
 
137
            break;
 
138
    }
 
139
}
 
140
 
 
141
static void
 
142
midori_transferbar_download_button_clicked_cb (GtkWidget*    button,
 
143
                                               TransferInfo* info)
 
144
{
 
145
    WebKitDownload* download = info->download;
 
146
 
 
147
    switch (webkit_download_get_status (download))
 
148
    {
 
149
        case WEBKIT_DOWNLOAD_STATUS_STARTED:
 
150
            webkit_download_cancel (download);
 
151
            break;
 
152
        case WEBKIT_DOWNLOAD_STATUS_FINISHED:
 
153
        {
 
154
            const gchar* uri = webkit_download_get_destination_uri (download);
 
155
            if (sokoke_show_uri (gtk_widget_get_screen (button),
 
156
                uri, gtk_get_current_event_time (), NULL))
 
157
                gtk_widget_destroy (button);
 
158
            break;
 
159
        }
 
160
        case WEBKIT_DOWNLOAD_STATUS_CANCELLED:
 
161
            gtk_widget_destroy (button);
 
162
        default:
 
163
            break;
 
164
    }
 
165
}
 
166
 
 
167
void
 
168
midori_transferbar_add_download_item (MidoriTransferbar* transferbar,
 
169
                                      WebKitDownload*    download)
 
170
{
 
171
    GtkWidget* box;
 
172
    GtkWidget* icon;
 
173
    GtkToolItem* toolitem;
 
174
    GtkWidget* button;
 
175
    GtkWidget* progress;
 
176
    const gchar* uri;
 
177
    gint width;
 
178
    TransferInfo* info;
 
179
 
 
180
    box = gtk_hbox_new (FALSE, 0);
 
181
    progress = gtk_progress_bar_new ();
 
182
    gtk_progress_bar_set_ellipsize (GTK_PROGRESS_BAR (progress),
 
183
                                    PANGO_ELLIPSIZE_MIDDLE);
 
184
    if ((uri = webkit_download_get_destination_uri (download)))
 
185
    {
 
186
        gchar* path = soup_uri_decode (uri);
 
187
        gchar* filename = g_strrstr (path, "/") + 1;
 
188
        gtk_progress_bar_set_text (GTK_PROGRESS_BAR (progress), filename);
 
189
        g_free (path);
 
190
    }
 
191
    else
 
192
        gtk_progress_bar_set_text (GTK_PROGRESS_BAR (progress),
 
193
            webkit_download_get_suggested_filename (download));
 
194
    sokoke_widget_get_text_size (progress, "M", &width, NULL);
 
195
    gtk_widget_set_size_request (progress, width * 10, 1);
 
196
    /* Avoid a bug in WebKit */
 
197
    if (webkit_download_get_status (download) != WEBKIT_DOWNLOAD_STATUS_CREATED)
 
198
        gtk_progress_bar_set_fraction (GTK_PROGRESS_BAR (progress),
 
199
            webkit_download_get_progress (download));
 
200
    gtk_box_pack_start (GTK_BOX (box), progress, FALSE, FALSE, 0);
 
201
    icon = gtk_image_new_from_stock (GTK_STOCK_CANCEL, GTK_ICON_SIZE_MENU);
 
202
    button = gtk_button_new ();
 
203
    gtk_button_set_relief (GTK_BUTTON (button), GTK_RELIEF_NONE);
 
204
    gtk_button_set_focus_on_click (GTK_BUTTON (button), FALSE);
 
205
    gtk_container_add (GTK_CONTAINER (button), icon);
 
206
    gtk_box_pack_start (GTK_BOX (box), button, FALSE, FALSE, 0);
 
207
    toolitem = gtk_tool_item_new ();
 
208
    gtk_container_add (GTK_CONTAINER (toolitem), box);
 
209
    gtk_widget_show_all (GTK_WIDGET (toolitem));
 
210
    gtk_toolbar_insert (GTK_TOOLBAR (transferbar), toolitem, 0);
 
211
    gtk_widget_show (GTK_WIDGET (transferbar->clear));
 
212
 
 
213
    info = g_new (TransferInfo, 1);
 
214
    info->download = g_object_ref (download);
 
215
    info->button = button;
 
216
    info->toolitem = GTK_WIDGET (toolitem);
 
217
    info->transferbar = transferbar;
 
218
    g_signal_connect (button, "destroy",
 
219
                      G_CALLBACK (midori_transferbar_button_destroy_cb), info);
 
220
    transferbar->infos = g_list_prepend (transferbar->infos, info);
 
221
 
 
222
    g_signal_connect (download, "notify::progress",
 
223
        G_CALLBACK (midori_transferbar_download_notify_progress_cb), progress);
 
224
    g_signal_connect (download, "notify::status",
 
225
        G_CALLBACK (midori_transferbar_download_notify_status_cb), info);
 
226
    g_signal_connect (button, "clicked",
 
227
        G_CALLBACK (midori_transferbar_download_button_clicked_cb), info);
 
228
}
 
229
 
 
230
static void
 
231
midori_transferbar_clear_clicked_cb (GtkWidget*         button,
 
232
                                     MidoriTransferbar* transferbar)
 
233
{
 
234
    GList* list;
 
235
 
 
236
    for (list = transferbar->infos; list != NULL; list = g_list_next (list))
 
237
    {
 
238
        TransferInfo* info = list->data;
 
239
        WebKitDownloadStatus status = webkit_download_get_status (info->download);
 
240
        if (status == WEBKIT_DOWNLOAD_STATUS_ERROR
 
241
         || status == WEBKIT_DOWNLOAD_STATUS_CANCELLED
 
242
         || status == WEBKIT_DOWNLOAD_STATUS_FINISHED)
 
243
        {
 
244
            gtk_widget_destroy (info->button);
 
245
        }
 
246
    }
 
247
}
 
248
#endif
 
249
 
 
250
static void
 
251
midori_transferbar_init (MidoriTransferbar* transferbar)
 
252
{
 
253
    gtk_toolbar_set_style (GTK_TOOLBAR (transferbar), GTK_TOOLBAR_BOTH_HORIZ);
 
254
    gtk_toolbar_set_icon_size (GTK_TOOLBAR (transferbar), GTK_ICON_SIZE_MENU);
 
255
 
 
256
    transferbar->clear = gtk_tool_button_new_from_stock (GTK_STOCK_CLEAR);
 
257
    gtk_tool_button_set_label (GTK_TOOL_BUTTON (transferbar->clear), _("Clear All"));
 
258
    gtk_tool_item_set_is_important (transferbar->clear, TRUE);
 
259
    g_signal_connect (transferbar->clear, "clicked",
 
260
        G_CALLBACK (midori_transferbar_clear_clicked_cb), transferbar);
 
261
    gtk_toolbar_insert (GTK_TOOLBAR (transferbar), transferbar->clear, -1);
 
262
 
 
263
    transferbar->infos = NULL;
 
264
}
 
265
 
 
266
gboolean
 
267
midori_transferbar_confirm_delete (MidoriTransferbar* transferbar)
 
268
{
 
269
    GtkWidget* dialog = NULL;
 
270
    gboolean cancel = FALSE;
 
271
 
 
272
    if (transferbar->infos || g_list_nth_data (transferbar->infos, 0))
 
273
    {
 
274
        GtkWidget* widget = gtk_widget_get_toplevel (GTK_WIDGET (transferbar));
 
275
        dialog = gtk_message_dialog_new (GTK_WINDOW (widget),
 
276
            GTK_DIALOG_DESTROY_WITH_PARENT,
 
277
            GTK_MESSAGE_WARNING, GTK_BUTTONS_NONE,
 
278
            _("Some files are being downloaded"));
 
279
        gtk_window_set_title (GTK_WINDOW (dialog),
 
280
            _("Some files are being downloaded"));
 
281
        gtk_dialog_add_button (GTK_DIALOG (dialog),
 
282
            GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL);
 
283
        gtk_dialog_add_button (GTK_DIALOG (dialog),
 
284
            _("_Quit Midori"), GTK_RESPONSE_ACCEPT);
 
285
        gtk_message_dialog_format_secondary_text (GTK_MESSAGE_DIALOG (dialog),
 
286
            _("The transfers will be cancelled if Midori quits."));
 
287
    }
 
288
    if (dialog != NULL)
 
289
    {
 
290
        if (gtk_dialog_run (GTK_DIALOG (dialog)) == GTK_RESPONSE_CANCEL)
 
291
            cancel = TRUE;
 
292
        gtk_widget_destroy (dialog);
 
293
    }
 
294
 
 
295
    return cancel;
 
296
}
 
297