source: trunk/gtk/file-list.c @ 6369

Last change on this file since 6369 was 6369, checked in by charles, 13 years ago

(gtk) #867: fix strings that should've been marked for translation for 1.30, but weren't.

  • Property svn:keywords set to Date Rev Author Id
File size: 23.0 KB
Line 
1/******************************************************************************
2 * $Id: file-list.c 6369 2008-07-19 19:48:45Z charles $
3 *
4 * Copyright (c) 2005-2008 Transmission authors and contributors
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a
7 * copy of this software and associated documentation files (the "Software"),
8 * to deal in the Software without restriction, including without limitation
9 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
10 * and/or sell copies of the Software, and to permit persons to whom the
11 * Software is furnished to do so, subject to the following conditions:
12 *
13 * The above copyright notice and this permission notice shall be included in
14 * all copies or substantial portions of the Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22 * DEALINGS IN THE SOFTWARE.
23 *****************************************************************************/
24
25#include <stddef.h>
26#include <stdio.h>
27#include <stdlib.h>
28#include <glib/gi18n.h>
29#include <gtk/gtk.h>
30
31#include <libtransmission/transmission.h>
32#include <libtransmission/utils.h> /* tr_getRatio */
33
34#include "file-list.h"
35#include "hig.h"
36
37enum
38{
39    SUB_STATE_HIGH          = (1<<0),
40    SUB_STATE_NORMAL        = (1<<1),
41    SUB_STATE_LOW           = (1<<2),
42    SUB_STATE_PRIORITY_MASK = (SUB_STATE_HIGH|SUB_STATE_NORMAL|SUB_STATE_LOW),
43    SUB_STATE_DOWNLOAD      = (1<<4),
44    SUB_STATE_IGNORE        = (1<<5),
45    SUB_STATE_DOWNLOAD_MASK = (SUB_STATE_DOWNLOAD|SUB_STATE_IGNORE)
46};
47
48enum
49{
50    FC_STOCK,
51    FC_LABEL,
52    FC_PROG,
53    FC_KEY,
54    FC_INDEX,
55    FC_SIZE,
56    FC_HAVE,
57    FC_PRIORITY,
58    FC_ENABLED,
59    FC_IS_FILE,
60    FC_SUB_SIZE,
61    FC_SUB_HAVE,
62    FC_SUB_STATE,
63    N_FILE_COLS
64};
65
66typedef struct
67{
68    TrTorrent * gtor;
69    GtkWidget * top;
70    GtkWidget * view;
71    GtkTreeModel * model; /* same object as store, but recast */
72    GtkTreeStore * store; /* same object as model, but recast */
73    tr_file_stat * refresh_file_stat;
74    guint timeout_tag;
75}
76FileData;
77
78static void
79clearData( FileData * data )
80{
81    data->gtor = NULL;
82
83    if( data->timeout_tag ) {
84        g_source_remove( data->timeout_tag );
85        data->timeout_tag = 0;
86    }
87}
88
89static void
90freeData( gpointer gdata )
91{
92    FileData * data = gdata;
93    clearData( data );
94    g_free( data );
95}
96
97/***
98****
99***/
100
101static void
102parsepath( const tr_torrent  * tor,
103           GtkTreeStore      * store,
104           GtkTreeIter       * ret,
105           const char        * path,
106           tr_file_index_t     index,
107           uint64_t            size )
108{
109    GtkTreeModel * model;
110    GtkTreeIter  * parent, start, iter;
111    char         * file, * lower, * mykey;
112    const char   * stock;
113    int            priority = 0;
114    gboolean       enabled = TRUE;
115    gboolean       is_file;
116
117    model  = GTK_TREE_MODEL( store );
118    parent = NULL;
119    file   = g_path_get_basename( path );
120    if( 0 != strcmp( file, path ) )
121    {
122        char * dir = g_path_get_dirname( path );
123        parsepath( tor, store, &start, dir, index, size );
124        parent = &start;
125        g_free( dir );
126    }
127
128    lower = g_utf8_casefold( file, -1 );
129    mykey = g_utf8_collate_key( lower, -1 );
130    if( gtk_tree_model_iter_children( model, &iter, parent ) ) do
131    {
132        gboolean stop;
133        char * modelkey;
134        gtk_tree_model_get( model, &iter, FC_KEY, &modelkey, -1 );
135        stop = (modelkey!=NULL) && !strcmp(mykey,modelkey);
136        g_free (modelkey);
137        if (stop) goto done;
138    }
139    while( gtk_tree_model_iter_next( model, &iter ) );
140
141    gtk_tree_store_append( store, &iter, parent );
142    if(( is_file = !ret ))
143    {
144        stock = GTK_STOCK_FILE;
145        priority = tr_torrentGetFilePriority( tor, index );
146        enabled  = tr_torrentGetFileDL( tor, index );
147    }
148    else
149    {
150        stock = GTK_STOCK_DIRECTORY;
151        size  = 0;
152    }
153
154#if 0
155    gtk_tree_store_set( store, &iter, FC_INDEX, index,
156                                      FC_LABEL, file,
157                                      FC_KEY, mykey,
158                                      FC_STOCK, stock,
159                                      FC_PRIORITY, priority,
160                                      FC_ENABLED, enabled,
161                                      FC_IS_FILE, is_file,
162                                      FC_SIZE, size,
163                                      FC_HAVE, 0,
164                                      -1 );
165#else
166    gtk_tree_store_set( store, &iter, FC_INDEX, index, -1 );
167    gtk_tree_store_set( store, &iter, FC_LABEL, file, -1 );
168    gtk_tree_store_set( store, &iter, FC_KEY, mykey, -1 );
169    gtk_tree_store_set( store, &iter, FC_STOCK, stock, -1 );
170    gtk_tree_store_set( store, &iter, FC_PRIORITY, priority, -1 );
171    gtk_tree_store_set( store, &iter, FC_ENABLED, enabled, -1 );
172    gtk_tree_store_set( store, &iter, FC_IS_FILE, is_file, -1 );
173    gtk_tree_store_set( store, &iter, FC_SIZE, size, -1 );
174    gtk_tree_store_set( store, &iter, FC_HAVE, 0, -1 );
175#endif
176
177  done:
178    g_free( mykey );
179    g_free( lower );
180    g_free( file );
181    if( NULL != ret )
182      *ret = iter;
183}
184
185
186/***
187****
188***/
189
190static gboolean
191refreshFilesForeach( GtkTreeModel  * model,
192                     GtkTreePath   * path UNUSED,
193                     GtkTreeIter   * iter,
194                     gpointer        gdata )
195{
196    FileData * data = gdata;
197    gboolean is_file;
198    unsigned int index;
199    gtk_tree_model_get( model, iter, FC_IS_FILE, &is_file, FC_INDEX, &index, -1  );
200    if( is_file ) {
201        GtkTreeStore * store = GTK_TREE_STORE( model );
202        tr_torrent * tor = tr_torrent_handle( data->gtor );
203        int download = tr_torrentGetFileDL( tor, index );
204        int priority = tr_torrentGetFilePriority( tor, index );
205        uint64_t have = data->refresh_file_stat[index].bytesCompleted;
206        gtk_tree_store_set( store, iter, FC_PRIORITY, priority,
207                                         FC_ENABLED, download,
208                                         FC_HAVE, have,
209                                         -1 );
210    }
211    return FALSE; /* keep walking */
212}
213
214static gboolean
215resetSubForeach( GtkTreeModel  * model,
216                 GtkTreePath   * path UNUSED,
217                 GtkTreeIter   * iter,
218                 gpointer        gdata UNUSED )
219{
220    /* set the subs to the lowest values... */
221    gtk_tree_store_set( GTK_TREE_STORE( model ), iter,
222                        FC_SUB_STATE, 0,
223                        FC_SUB_SIZE, (uint64_t)0,
224                        FC_SUB_HAVE, (uint64_t)0,
225                        -1 );
226    return FALSE; /* keep walking */
227}
228
229static gboolean
230addSubForeach( GtkTreeModel  * model,
231               GtkTreePath   * path UNUSED,
232               GtkTreeIter   * iter,
233               gpointer        gdata UNUSED )
234{
235    uint64_t size;
236    uint64_t have;
237    int priority;
238    gboolean enabled;
239    gboolean is_file;
240    gtk_tree_model_get( model, iter, FC_SIZE, &size,
241                                     FC_HAVE, &have,
242                                     FC_PRIORITY, &priority,
243                                     FC_ENABLED, &enabled,
244                                     FC_IS_FILE, &is_file,
245                                     -1 );
246    if( is_file )
247    {
248        GtkTreeIter child = *iter;
249        GtkTreeIter parent;
250        while(( gtk_tree_model_iter_parent( model, &parent, &child )))
251        {
252            uint64_t sub_size;
253            uint64_t sub_have;
254            int sub_state;
255            gtk_tree_model_get( model, &parent, FC_SUB_SIZE, &sub_size,
256                                                FC_SUB_HAVE, &sub_have,
257                                                FC_SUB_STATE, &sub_state,
258                                                -1 );
259            sub_have += have;
260            sub_size += size;
261            switch( priority ) {
262                case TR_PRI_HIGH:   sub_state |= SUB_STATE_HIGH;   break;
263                case TR_PRI_NORMAL: sub_state |= SUB_STATE_NORMAL; break;
264                case TR_PRI_LOW:    sub_state |= SUB_STATE_LOW;    break;
265            }
266            sub_state |= ( enabled ? SUB_STATE_DOWNLOAD : SUB_STATE_IGNORE );
267            gtk_tree_store_set( GTK_TREE_STORE( model ), &parent,
268                                FC_SUB_SIZE, sub_size,
269                                FC_SUB_HAVE, sub_have,
270                                FC_SUB_STATE, sub_state,
271                                -1 );
272            child = parent;
273        }
274    }
275    return FALSE; /* keep walking */
276}
277
278static void
279refresh( FileData * data )
280{
281    tr_file_index_t fileCount;
282    tr_torrent * tor = tr_torrent_handle( data->gtor );
283    data->refresh_file_stat = tr_torrentFiles( tor, &fileCount );
284
285    gtk_tree_model_foreach( data->model, refreshFilesForeach, data );
286    gtk_tree_model_foreach( data->model, resetSubForeach, data );
287    gtk_tree_model_foreach( data->model, addSubForeach, data );
288
289    tr_torrentFilesFree( data->refresh_file_stat, fileCount );
290    data->refresh_file_stat = NULL;
291}
292
293static gboolean
294refreshModel( gpointer file_data )
295{
296    refresh( file_data );
297    return TRUE;
298}
299
300/***
301****
302***/
303
304struct ActiveData
305{
306    GtkTreeSelection * sel;
307    GArray * array;
308};
309
310static gboolean
311getActiveFilesForeach( GtkTreeModel  * model,
312                       GtkTreePath   * path UNUSED,
313                       GtkTreeIter   * iter,
314                       gpointer        gdata )
315{
316    struct ActiveData * data = gdata;
317    unsigned int i;
318    gboolean is_file = FALSE;
319    gboolean is_active = FALSE;
320
321    /* active == if it's selected, or any ancestor is selected */
322    gtk_tree_model_get( model, iter, FC_IS_FILE, &is_file, FC_INDEX, &i, -1 );
323    if( is_file ) {
324        is_active = gtk_tree_selection_iter_is_selected( data->sel, iter );
325        if( !is_active ) {
326            GtkTreeIter walk = *iter;
327            GtkTreeIter parent;
328            while( !is_active && gtk_tree_model_iter_parent( model, &parent, &walk )) {
329                is_active = gtk_tree_selection_iter_is_selected( data->sel, &parent );
330                walk = parent;
331            }
332        }
333    }
334
335    if( is_active )
336        g_array_append_val( data->array, i );
337
338    return FALSE; /* keep walking */
339}
340
341static GArray*
342getActiveFiles( GtkTreeView * view )
343{
344    struct ActiveData data;
345    data.sel = gtk_tree_view_get_selection( view );
346    data.array  = g_array_new( FALSE, FALSE, sizeof( tr_file_index_t ) );
347    gtk_tree_model_foreach( gtk_tree_view_get_model( view ), getActiveFilesForeach, &data );
348    return data.array;
349}
350
351static void
352setPriority( FileData * data, int priority )
353{
354    GtkTreeView * view = GTK_TREE_VIEW( data->view );
355    GArray * a = getActiveFiles( view );
356    tr_torrentSetFilePriorities( tr_torrent_handle( data->gtor ),
357                                 (tr_file_index_t*)a->data,
358                                 (tr_file_index_t)a->len,
359                                 priority );
360    refresh( data );
361    g_array_free( a, TRUE );
362}
363
364
365static void
366setDownload( FileData * data, int do_download )
367{
368    GtkTreeView * view = GTK_TREE_VIEW( data->view );
369    GArray * a = getActiveFiles( view );
370    tr_torrentSetFileDLs ( tr_torrent_handle( data->gtor ),
371                           (tr_file_index_t*)a->data,
372                           (tr_file_index_t)a->len,
373                           do_download );
374    refresh( data );
375    g_array_free( a, TRUE );
376}
377
378static void
379onHighClicked( GtkButton * button UNUSED, gpointer gdata )
380{
381    setPriority( gdata, TR_PRI_HIGH );
382}
383static void
384onNormalClicked( GtkButton * button UNUSED, gpointer gdata )
385{
386    setPriority( gdata, TR_PRI_NORMAL );
387}
388static void
389onLowClicked( GtkButton * button UNUSED, gpointer gdata )
390{
391    setPriority( gdata, TR_PRI_LOW );
392}
393static void
394onDownloadClicked( GtkButton * button UNUSED, gpointer gdata )
395{
396    setDownload( gdata, TRUE );
397}
398static void
399onIgnoreClicked( GtkButton * button UNUSED, gpointer gdata )
400{
401    setDownload( gdata, FALSE );
402}
403
404/***
405****
406***/
407
408void
409file_list_set_torrent( GtkWidget * w, TrTorrent * gtor )
410{
411    GtkTreeStore        * store;
412    FileData            * data;
413
414    data = g_object_get_data( G_OBJECT( w ), "file-data" );
415
416    /* unset the old fields */
417    clearData( data );
418
419    /* instantiate the model */
420    store = gtk_tree_store_new ( N_FILE_COLS,
421                                 G_TYPE_STRING,    /* stock */
422                                 G_TYPE_STRING,    /* label */
423                                 G_TYPE_INT,       /* prog [0..100] */
424                                 G_TYPE_STRING,    /* key */
425                                 G_TYPE_UINT,      /* index */
426                                 G_TYPE_UINT64,    /* size */
427                                 G_TYPE_UINT64,    /* have */
428                                 G_TYPE_INT,       /* priority */
429                                 G_TYPE_BOOLEAN,   /* dl enabled */
430                                 G_TYPE_BOOLEAN,   /* is file */
431                                 G_TYPE_UINT64,    /* sub size */
432                                 G_TYPE_UINT64,    /* sub have */
433                                 G_TYPE_INT );     /* sub state */
434    data->store = store;
435    data->model = GTK_TREE_MODEL( store );
436    data->gtor = gtor;
437
438
439    /* populate the model */
440    if( gtor )
441    {
442        tr_file_index_t i;
443        const tr_info * inf = tr_torrent_info( gtor );
444        tr_torrent * tor = tr_torrent_handle( gtor );
445
446        for( i=0; inf && i<inf->fileCount; ++i )
447        {
448            const char * path = inf->files[i].name;
449            const char * base = g_path_is_absolute( path ) ? g_path_skip_root( path ) : path;
450            parsepath( tor, store, NULL, base, i, inf->files[i].length );
451        }
452
453        refresh( data );
454
455        data->timeout_tag = g_timeout_add( 2500, refreshModel, data );
456    }
457
458    gtk_tree_view_set_model( GTK_TREE_VIEW( data->view ), GTK_TREE_MODEL( store ) );
459    gtk_tree_view_expand_all( GTK_TREE_VIEW( data->view ) );
460}
461
462/***
463****
464***/
465
466static void
467renderProgress( GtkTreeViewColumn  * column UNUSED,
468                GtkCellRenderer    * renderer,
469                GtkTreeModel       * model,
470                GtkTreeIter        * iter,
471                gpointer             data UNUSED)
472{
473    gboolean is_file;
474    uint64_t size, have, subsize, subhave;
475    double progress;
476    gtk_tree_model_get( model, iter, FC_SIZE, &size,
477                                     FC_HAVE, &have,
478                                     FC_SUB_SIZE, &subsize,
479                                     FC_SUB_HAVE, &subhave,
480                                     FC_IS_FILE, &is_file,
481                                     -1 );
482    progress = is_file ? tr_getRatio( have, size )
483                       : tr_getRatio( subhave, subsize );
484    g_object_set( renderer, "value", (int)(progress*100), NULL );
485}
486
487static void
488renderFilename( GtkTreeViewColumn  * column UNUSED,
489                GtkCellRenderer    * renderer,
490                GtkTreeModel       * model,
491                GtkTreeIter        * iter,
492                gpointer             data UNUSED)
493{
494    char * filename;
495    char * str;
496    int64_t size;
497    int64_t subsize;
498    gboolean is_file;
499    char buf[64];
500    gtk_tree_model_get( model, iter, FC_LABEL, &filename,
501                                     FC_SIZE, &size,
502                                     FC_SUB_SIZE, &subsize,
503                                     FC_IS_FILE, &is_file,
504                                     -1 );
505    tr_strlsize( buf, is_file ? size : subsize, sizeof( buf ) );
506    str = g_markup_printf_escaped( "<small>%s (%s)</small>",
507                                   filename, buf );
508    g_object_set( renderer, "markup", str, NULL );
509    g_free( str );
510    g_free( filename );
511}
512
513static void
514renderDownload( GtkTreeViewColumn  * column UNUSED,
515                GtkCellRenderer    * renderer,
516                GtkTreeModel       * model,
517                GtkTreeIter        * iter,
518                gpointer             data UNUSED)
519{
520    int sub_state;
521    gboolean enabled;
522    gboolean is_file = FALSE;
523    const char * text;
524
525    gtk_tree_model_get( model, iter, FC_IS_FILE, &is_file,
526                                     FC_ENABLED, &enabled,
527                                     FC_SUB_STATE, &sub_state,
528                                     -1 );
529    if( is_file && enabled )
530        text = _( "Yes" );
531    else if( is_file )
532        text = _( "No" );
533    else switch( sub_state & SUB_STATE_DOWNLOAD_MASK ) {
534        case SUB_STATE_DOWNLOAD: text = _( "Yes" );   break;
535        case SUB_STATE_IGNORE:   text = _( "No" );    break;
536        default:                 text = _( "Mixed" ); break;
537    }
538
539    g_object_set( renderer, "text", text,
540                            "xalign", (gfloat)0.5,
541                            "yalign", (gfloat)0.5,
542                            NULL );
543}
544
545static void
546renderPriority( GtkTreeViewColumn  * column UNUSED,
547                GtkCellRenderer    * renderer,
548                GtkTreeModel       * model,
549                GtkTreeIter        * iter,
550                gpointer             data UNUSED)
551{
552    int priority;
553    int sub_state;
554    gboolean is_file = FALSE;
555    const char * text = "";
556    gtk_tree_model_get( model, iter, FC_IS_FILE, &is_file,
557                                     FC_PRIORITY, &priority,
558                                     FC_SUB_STATE, &sub_state,
559                                     -1 );
560    if( !is_file )
561    {
562        switch( sub_state & SUB_STATE_PRIORITY_MASK )
563        {
564            case SUB_STATE_HIGH:   priority = TR_PRI_HIGH;   break;
565            case SUB_STATE_NORMAL: priority = TR_PRI_NORMAL; break;
566            case SUB_STATE_LOW:    priority = TR_PRI_LOW;    break;
567            default:               priority = 666;           break;
568        }
569    }
570
571    switch( priority )
572    {
573        case TR_PRI_HIGH: text = _( "High" );
574                          break;
575        case TR_PRI_NORMAL: text = _( "Normal" );
576                            break;
577        case TR_PRI_LOW: text = _( "Low" );
578                         break;
579        default: text = _( "Mixed" );
580                 break;
581    }
582
583    g_object_set( renderer, "text", text,
584                            "xalign", (gfloat)0.5,
585                            "yalign", (gfloat)0.5,
586                            NULL );
587}
588
589GtkWidget *
590file_list_new( TrTorrent * gtor )
591{
592    GtkWidget           * ret;
593    FileData            * data;
594    GtkWidget           * view, * scroll;
595    GtkCellRenderer     * rend;
596    GtkTreeViewColumn   * col;
597    GtkTreeSelection    * sel;
598    GtkWidget           * hbox;
599    GtkWidget           * vbox;
600    GtkWidget           * w;
601
602    /* create the view */
603    view = gtk_tree_view_new( );
604    gtk_tree_view_set_rules_hint( GTK_TREE_VIEW( view ), TRUE );
605    gtk_container_set_border_width( GTK_CONTAINER( view ), GUI_PAD_BIG );
606
607    /* set up view */
608    sel = gtk_tree_view_get_selection( GTK_TREE_VIEW( view ) );
609    gtk_tree_selection_set_mode( sel, GTK_SELECTION_MULTIPLE );
610    gtk_tree_view_expand_all( GTK_TREE_VIEW( view ) );
611    gtk_tree_view_set_search_column( GTK_TREE_VIEW( view ), FC_LABEL );
612
613    /* add file column */
614   
615    col = GTK_TREE_VIEW_COLUMN (g_object_new (GTK_TYPE_TREE_VIEW_COLUMN,
616        "expand", TRUE,
617    /* Translators: this is a column header in Files tab, Details dialog;
618       Don't include the prefix "filedetails|" in the translation. */                                 
619        "title", Q_("filedetails|File"),
620        NULL));
621    rend = gtk_cell_renderer_pixbuf_new();
622    gtk_tree_view_column_pack_start( col, rend, FALSE );
623    gtk_tree_view_column_add_attribute( col, rend, "stock-id", FC_STOCK );
624    /* add text renderer */
625    rend = gtk_cell_renderer_text_new();
626    g_object_set( rend, "ellipsize", PANGO_ELLIPSIZE_END, NULL );
627    gtk_tree_view_column_pack_start( col, rend, TRUE );
628    gtk_tree_view_column_set_cell_data_func( col, rend, renderFilename, NULL, NULL);
629    gtk_tree_view_append_column( GTK_TREE_VIEW( view ), col );
630
631
632    rend = gtk_cell_renderer_progress_new( );
633    /* Translators: this is a column header in Files tab, Details dialog;
634       Don't include the prefix "filedetails|" in the translation. */ 
635    col = gtk_tree_view_column_new_with_attributes( Q_("filedetails|Progress"), rend, NULL );
636    gtk_tree_view_column_set_cell_data_func( col, rend, renderProgress, NULL, NULL);
637    gtk_tree_view_append_column ( GTK_TREE_VIEW( view ), col);
638
639    /* add "enabled" column */
640    rend = gtk_cell_renderer_text_new( );
641    /* Translators: this is a column header in Files tab, Details dialog;
642       Don't include the prefix "filedetails|" in the translation.
643       The items for this column are checkboxes (yes/no) */ 
644    col = gtk_tree_view_column_new_with_attributes( Q_( "filedetails|Download" ), rend, NULL );
645    gtk_tree_view_column_set_cell_data_func( col, rend, renderDownload, NULL, NULL);
646    gtk_tree_view_append_column ( GTK_TREE_VIEW( view ), col);
647
648    /* add priority column */
649    rend = gtk_cell_renderer_text_new( );
650    col = gtk_tree_view_column_new_with_attributes( _( "Priority" ), rend, NULL );
651    gtk_tree_view_column_set_cell_data_func( col, rend, renderPriority, NULL, NULL);
652    gtk_tree_view_append_column ( GTK_TREE_VIEW( view ), col);
653
654    /* create the scrolled window and stick the view in it */
655    scroll = gtk_scrolled_window_new( NULL, NULL );
656    gtk_scrolled_window_set_policy( GTK_SCROLLED_WINDOW( scroll ),
657                                    GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC );
658    gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW(scroll),
659                                         GTK_SHADOW_IN);
660    gtk_container_add( GTK_CONTAINER( scroll ), view );
661    gtk_widget_set_size_request (scroll, -1, 200 );
662
663    data = g_new0( FileData, 1 );
664
665    vbox = gtk_vbox_new( FALSE, GUI_PAD );
666        w = gtk_button_new_with_mnemonic( _( "_High" ) );
667        g_signal_connect( w, "clicked", G_CALLBACK(onHighClicked), data );
668        gtk_box_pack_start( GTK_BOX( vbox ), w, FALSE, FALSE, 0 );
669        w = gtk_button_new_with_mnemonic( _( "_Normal" ) );
670        g_signal_connect( w, "clicked", G_CALLBACK(onNormalClicked), data );
671        gtk_box_pack_start( GTK_BOX( vbox ), w, FALSE, FALSE, 0 );
672        w = gtk_button_new_with_mnemonic( _( "_Low" ) );
673        g_signal_connect( w, "clicked", G_CALLBACK(onLowClicked), data );
674        gtk_box_pack_start( GTK_BOX( vbox ), w, FALSE, FALSE, 0 );
675        w = gtk_button_new_with_mnemonic( _( "_Ignore" ) );
676        g_signal_connect( w, "clicked", G_CALLBACK(onIgnoreClicked), data );
677        gtk_box_pack_end( GTK_BOX( vbox ), w, FALSE, FALSE, 0 );
678        w = gtk_button_new_with_mnemonic( _( "_Download" ) );
679        g_signal_connect( w, "clicked", G_CALLBACK(onDownloadClicked), data );
680        gtk_box_pack_end( GTK_BOX( vbox ), w, FALSE, FALSE, 0 );
681    hbox = gtk_hbox_new( FALSE, GUI_PAD );
682    gtk_box_pack_start_defaults( GTK_BOX( hbox ), scroll );
683    gtk_box_pack_start( GTK_BOX( hbox ), vbox, 0, 0, 0 );
684
685    ret = hbox;
686    data->view = view;
687    data->top = scroll;
688    g_object_set_data_full( G_OBJECT( ret ), "file-data", data, freeData );
689    file_list_set_torrent( ret, gtor );
690
691    return ret;
692}
Note: See TracBrowser for help on using the repository browser.