source: trunk/gtk/add-dialog.c @ 5868

Last change on this file since 5868 was 5868, checked in by charles, 14 years ago

(#954) rpc: add "torrent-remove" method. rename tr_torrentDelete() as tr_torrentRemove() for consistency with various parts of the code.

  • Property svn:keywords set to Date Rev Author Id
File size: 10.5 KB
Line 
1/*
2 * This file Copyright (C) 2008 Charles Kerr <charles@rebelbase.com>
3 *
4 * This file is licensed by the GPL version 2.  Works owned by the
5 * Transmission project are granted a special exemption to clause 2(b)
6 * so that the bulk of its code can remain under the MIT license.
7 * This exemption does not extend to derived works not owned by
8 * the Transmission project.
9 *
10 * $Id: add-dialog.c 5868 2008-05-20 23:58:59Z charles $
11 */
12
13#include <glib/gi18n.h>
14#include <gtk/gtk.h>
15#include "add-dialog.h"
16#include "conf.h"
17#include "file-list.h"
18#include "hig.h"
19#include "tr-prefs.h"
20
21struct AddData
22{
23    TrCore * core;
24    GtkWidget * list;
25    GtkWidget * run_check;
26    GtkWidget * trash_check;
27    char * filename;
28    char * downloadDir;
29    TrTorrent * gtor;
30    tr_ctor * ctor;
31};
32
33static void
34removeOldTorrent( struct AddData * data )
35{
36    if( data->gtor )
37    {
38        file_list_set_torrent( data->list, NULL );
39
40        tr_torrent_set_remove_flag( data->gtor, TRUE );
41        g_object_unref( G_OBJECT( data->gtor ) );
42        data->gtor = NULL;
43    }
44}
45
46static void
47addResponseCB( GtkDialog * dialog, gint response, gpointer gdata )
48{
49    struct AddData * data = gdata;
50
51    if( data->gtor )
52    {
53        if( response != GTK_RESPONSE_ACCEPT )
54            removeOldTorrent( data );
55        else {
56            if( gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( data->run_check ) ) )
57                tr_torrentStart( tr_torrent_handle( data->gtor ) );
58            tr_core_add_torrent( data->core, data->gtor );
59            if( gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( data->trash_check ) ) )
60                tr_file_trash_or_unlink( data->filename );
61        }
62    }
63
64    tr_ctorFree( data->ctor );
65    g_free( data->filename );
66    g_free( data->downloadDir );
67    g_free( data );
68    gtk_widget_destroy( GTK_WIDGET( dialog ) );
69}
70
71static void
72updateTorrent( struct AddData * o )
73{
74    if( o->gtor )
75        tr_torrentSetDownloadDir( tr_torrent_handle( o->gtor ), o->downloadDir );
76
77    file_list_set_torrent( o->list, o->gtor );
78}
79
80static void
81sourceChanged( GtkFileChooserButton * b, gpointer gdata )
82{
83    struct AddData * data = gdata;
84
85    removeOldTorrent( data );
86
87    g_free( data->filename );
88    data->filename = gtk_file_chooser_get_filename( GTK_FILE_CHOOSER( b ) );
89
90    /* maybe instantiate a torrent */
91    if( data->filename ) {
92        int err = 0;
93        tr_torrent * torrent;
94        tr_handle * handle = tr_core_handle( data->core );
95        tr_ctorSetMetainfoFromFile( data->ctor, data->filename );
96        tr_ctorSetDownloadDir( data->ctor, TR_FORCE, data->downloadDir );
97        tr_ctorSetPaused( data->ctor, TR_FORCE, TRUE );
98        tr_ctorSetDeleteSource( data->ctor, FALSE );
99        if(( torrent = tr_torrentNew( handle, data->ctor, &err )))
100            data->gtor = tr_torrent_new_preexisting( torrent );
101    }
102
103    updateTorrent( data );
104}
105
106static void
107verifyRequested( GtkButton * button UNUSED, gpointer gdata )
108{
109    struct AddData * data = gdata;
110    if( data->gtor )
111        tr_torrentVerify( tr_torrent_handle( data->gtor ) );
112}
113
114static void
115downloadDirChanged( GtkFileChooserButton * b, gpointer gdata )
116{
117    char * fname = gtk_file_chooser_get_filename( GTK_FILE_CHOOSER( b ) );
118    if( fname )
119    {
120        struct AddData * data = gdata;
121        g_free( data->downloadDir );
122        data->downloadDir = fname;
123
124        updateTorrent( data );
125        verifyRequested( NULL, data );
126    }
127}
128
129static void
130addTorrentFilters( GtkFileChooser * chooser )
131{
132    GtkFileFilter * filter;
133
134    filter = gtk_file_filter_new( );
135    gtk_file_filter_set_name( filter, _( "Torrent files" ) );
136    gtk_file_filter_add_pattern( filter, "*.torrent" );
137    gtk_file_chooser_add_filter( chooser, filter );
138
139    filter = gtk_file_filter_new( );
140    gtk_file_filter_set_name( filter, _( "All files" ) );
141    gtk_file_filter_add_pattern( filter, "*" );
142    gtk_file_chooser_add_filter( chooser, filter );
143}
144
145/****
146*****
147****/
148
149GtkWidget*
150addSingleTorrentDialog( GtkWindow  * parent,
151                        TrCore     * core,
152                        tr_ctor    * ctor )
153{
154    int row;
155    int col;
156    const char * str;
157    GtkWidget * w;
158    GtkWidget * d;
159    GtkWidget * t;
160    GtkWidget * l;
161    struct AddData * data;
162    uint8_t flag;
163
164    /* make the dialog */
165    d = gtk_dialog_new_with_buttons( _( "Torrent Options" ), parent,
166            GTK_DIALOG_DESTROY_WITH_PARENT|GTK_DIALOG_NO_SEPARATOR,
167            GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
168            GTK_STOCK_ADD, GTK_RESPONSE_ACCEPT,
169            NULL );
170    gtk_dialog_set_default_response( GTK_DIALOG( d ),
171                                     GTK_RESPONSE_ACCEPT );
172    gtk_dialog_set_alternative_button_order( GTK_DIALOG( d ),
173                                             GTK_RESPONSE_ACCEPT,
174                                             GTK_RESPONSE_CANCEL,
175                                             -1 );
176
177    if( tr_ctorGetDownloadDir( ctor, TR_FORCE, &str ) )
178        g_assert_not_reached( );
179    g_assert( str );
180
181    data = g_new0( struct AddData, 1 );
182    data->core = core;
183    data->ctor = ctor;
184    data->filename = g_strdup( tr_ctorGetSourceFile( ctor ) );
185    data->downloadDir = g_strdup( str );
186    data->list = file_list_new( NULL );
187    data->trash_check = gtk_check_button_new_with_mnemonic( _( "Mo_ve source file to Trash" ) );
188    data->run_check = gtk_check_button_new_with_mnemonic( _( "_Start when added" ) );
189
190    g_signal_connect( G_OBJECT( d ), "response",
191                      G_CALLBACK( addResponseCB ), data );
192
193    t = gtk_table_new( 6, 2, FALSE );
194    gtk_container_set_border_width( GTK_CONTAINER( t ), GUI_PAD_BIG );
195    gtk_table_set_row_spacings( GTK_TABLE( t ), GUI_PAD );
196    gtk_table_set_col_spacings( GTK_TABLE( t ), GUI_PAD_BIG );
197
198    row = col = 0;
199    l = gtk_label_new_with_mnemonic( _( "_Source file:" ) );
200    gtk_misc_set_alignment( GTK_MISC( l ), 0.0f, 0.5f );
201    gtk_table_attach( GTK_TABLE( t ), l, col, col+1, row, row+1, GTK_FILL, 0, 0, 0 );
202    ++col;
203    w = gtk_file_chooser_button_new( _( "Select Source File" ),
204                                     GTK_FILE_CHOOSER_ACTION_OPEN );
205    gtk_table_attach( GTK_TABLE( t ), w, col, col+1, row, row+1, ~0, 0, 0, 0 );
206    gtk_label_set_mnemonic_widget( GTK_LABEL( l ), w );
207    addTorrentFilters( GTK_FILE_CHOOSER( w ) );
208    if( data->filename )
209        if( !gtk_file_chooser_set_filename( GTK_FILE_CHOOSER( w ), data->filename ) )
210            g_warning( "couldn't select '%s'", data->filename );
211    g_signal_connect( w, "selection-changed",
212                      G_CALLBACK( sourceChanged ), data );
213
214    ++row;
215    col = 0;
216    l = gtk_label_new_with_mnemonic( _( "_Destination folder:" ) );
217    gtk_misc_set_alignment( GTK_MISC( l ), 0.0f, 0.5f );
218    gtk_table_attach( GTK_TABLE( t ), l, col, col+1, row, row+1, GTK_FILL, 0, 0, 0 );
219    ++col;
220    w = gtk_file_chooser_button_new( _( "Select Destination Folder" ), GTK_FILE_CHOOSER_ACTION_SELECT_FOLDER );
221    if( !gtk_file_chooser_set_filename( GTK_FILE_CHOOSER( w ), data->downloadDir ) )
222        g_warning( "couldn't select '%s'", data->downloadDir );
223    gtk_table_attach( GTK_TABLE( t ), w, col, col+1, row, row+1, ~0, 0, 0, 0 );
224    gtk_label_set_mnemonic_widget( GTK_LABEL( l ), w );
225    g_signal_connect( w, "selection-changed", G_CALLBACK( downloadDirChanged ), data );
226
227    ++row;
228    col = 0;
229    w = data->list;
230    gtk_widget_set_size_request ( w, 466u, 300u );
231    gtk_table_attach_defaults( GTK_TABLE( t ), w, col, col+2, row, row+1 );
232
233    ++row;
234    col = 0;
235    w = gtk_button_new_with_mnemonic( _( "Verify Local Data" ) );
236    gtk_table_attach( GTK_TABLE( t ), w, col, col+1, row, row+1, GTK_FILL, 0, 0, 0 );
237    g_signal_connect( w, "clicked", G_CALLBACK( verifyRequested ), data );
238
239    ++row;
240    col = 0;
241    w = data->run_check;
242    if( tr_ctorGetPaused( ctor, TR_FORCE, &flag ) )
243        g_assert_not_reached( );
244    gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( w ), !flag );
245    gtk_table_attach( GTK_TABLE( t ), w, col, col+2, row, row+1, GTK_FILL, 0, 0, 0 );
246
247    ++row;
248    col = 0;
249    w = data->trash_check;
250    if( tr_ctorGetDeleteSource( ctor, &flag ) )
251        g_assert_not_reached( );
252    gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( w ), flag );
253    gtk_table_attach( GTK_TABLE( t ), w, col, col+2, row, row+1, GTK_FILL, 0, 0, 0 );
254
255    gtk_box_pack_start_defaults( GTK_BOX( GTK_DIALOG( d )->vbox ), t );
256    gtk_widget_show_all( d );
257    return d;
258}
259
260/****
261*****
262****/
263
264static void
265onAddDialogResponse( GtkDialog * dialog, int response, gpointer core )
266{
267    char * folder;
268
269    /* remember this folder the next time we use this dialog */
270    folder = gtk_file_chooser_get_current_folder( GTK_FILE_CHOOSER( dialog ) );
271    pref_string_set( PREF_KEY_OPEN_DIALOG_FOLDER, folder );
272    g_free( folder );
273
274    if( response == GTK_RESPONSE_ACCEPT )
275    {
276        GtkWidget * w = gtk_file_chooser_get_extra_widget( GTK_FILE_CHOOSER( dialog ) );
277        const gboolean showOptions = gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON ( w ) );
278        const pref_flag_t start = PREF_FLAG_DEFAULT;
279        const pref_flag_t prompt = showOptions ? PREF_FLAG_TRUE : PREF_FLAG_FALSE;
280        GSList * l = gtk_file_chooser_get_filenames( GTK_FILE_CHOOSER( dialog ) );
281        tr_core_add_list( core, l, start, prompt );
282    }
283
284    gtk_widget_destroy( GTK_WIDGET( dialog ) );
285}
286
287GtkWidget*
288addDialog( GtkWindow * parent,
289           TrCore    * core )
290{
291    GtkWidget * w;
292    GtkWidget * c;
293    char * folder;
294
295    w = gtk_file_chooser_dialog_new( _( "Add a Torrent" ), parent,
296                                     GTK_FILE_CHOOSER_ACTION_OPEN,
297                                     GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
298                                     GTK_STOCK_ADD, GTK_RESPONSE_ACCEPT,
299                                     NULL );
300    gtk_dialog_set_alternative_button_order( GTK_DIALOG( w ),
301                                             GTK_RESPONSE_ACCEPT,
302                                             GTK_RESPONSE_CANCEL,
303                                             -1 );
304    gtk_file_chooser_set_select_multiple( GTK_FILE_CHOOSER( w ), TRUE );
305    addTorrentFilters( GTK_FILE_CHOOSER( w ) );
306    g_signal_connect( w, "response", G_CALLBACK(onAddDialogResponse), core );
307
308    if(( folder = pref_string_get( PREF_KEY_OPEN_DIALOG_FOLDER ))) {
309        gtk_file_chooser_set_current_folder( GTK_FILE_CHOOSER( w ), folder );
310        g_free( folder );
311    }
312
313    c = gtk_check_button_new_with_mnemonic( _( "Display _options dialog" ) );
314    gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( c ), pref_flag_get( PREF_KEY_OPTIONS_PROMPT ) );
315    gtk_file_chooser_set_extra_widget( GTK_FILE_CHOOSER( w ), c );
316    gtk_widget_show( c );
317
318    gtk_widget_show( w );
319    return w;
320}
Note: See TracBrowser for help on using the repository browser.