예제 #1
0
gpointer thumbnail_loader_thread( VFSAsyncTask* task, VFSThumbnailLoader* loader )
{
    ThumbnailRequest* req;
    int i;
    gboolean load_big, need_update;

    while( G_LIKELY( ! vfs_async_task_is_cancelled(task) ))
    {
        vfs_async_task_lock( task );
        req = (ThumbnailRequest*)g_queue_pop_head( loader->queue );
        vfs_async_task_unlock( task );
        if( G_UNLIKELY( ! req ) )
            break;
        /* g_debug("pop: %s", req->file->name); */

        /* Only we have the reference. That means, no body is using the file */
        if( req->file->n_ref == 1 )
        {
            thumbnail_request_free( req );
            continue;
        }

        need_update = FALSE;
        for ( i = 0; i < 2; ++i )
        {
            if ( 0 == req->n_requests[ i ] )
                continue;
            load_big = ( i == LOAD_BIG_THUMBNAIL );
            if ( ! vfs_file_info_is_thumbnail_loaded( req->file, load_big ) )
            {
                char* full_path;
                full_path = g_build_filename( loader->dir->path,
                                              vfs_file_info_get_name( req->file ),
                                              NULL );
                vfs_file_info_load_thumbnail( req->file, full_path, load_big );
                g_free( full_path );
                /*  Slow down for displaying. */
                g_usleep(G_USEC_PER_SEC/1000);

                /* g_debug( "thumbnail loaded: %s", req->file ); */
            }
            need_update = TRUE;
        }

        if( ! vfs_async_task_is_cancelled(task) && need_update )
        {
            vfs_async_task_lock( task );
            g_queue_push_tail( loader->update_queue, vfs_file_info_ref(req->file) );
            if( 0 == loader->idle_handler)
                loader->idle_handler = g_idle_add_full( G_PRIORITY_LOW, (GSourceFunc) on_thumbnail_idle, loader, NULL );
            vfs_async_task_unlock( task );
        }
        /* g_debug( "NEED_UPDATE: %d", need_update ); */
        thumbnail_request_free( req );
    }

    if( vfs_async_task_is_cancelled(task) )
    {
        /* g_debug( "THREAD CANCELLED!!!" ); */
        vfs_async_task_lock( task );
        if( loader->idle_handler)
        {
            g_source_remove( loader->idle_handler );
            loader->idle_handler = 0;
        }
        vfs_async_task_unlock( task );
    }
    else
    {
        if( 0 == loader->idle_handler)
        {
            /* g_debug( "ADD IDLE HANDLER BEFORE THREAD ENDING" ); */
            loader->idle_handler = g_idle_add_full( G_PRIORITY_LOW, (GSourceFunc) on_thumbnail_idle, loader, NULL );
        }
    }
    /* g_debug("THREAD ENDED!");  */
    return NULL;
}
예제 #2
0
파일: vfs-dir.c 프로젝트: alfbar0/spacefm
gpointer vfs_dir_load_thread(  VFSAsyncTask* task, VFSDir* dir )
{
    const gchar * file_name;
    char* full_path;
    GDir* dir_content;
    VFSFileInfo* file;
    char* hidden = NULL;  //MOD added

    dir->file_listed = 0;
    dir->load_complete = 0;
    dir->xhidden_count = 0;  //MOD
    if ( dir->path )
    {
        /* Install file alteration monitor */
        dir->monitor = vfs_file_monitor_add_dir( dir->path,
                                             vfs_dir_monitor_callback,
                                             dir );

        dir_content = g_dir_open( dir->path, 0, NULL );

        if ( dir_content )
        {
            GKeyFile* kf;

            if( G_UNLIKELY(dir->is_trash) )
                kf = g_key_file_new();

            // MOD  dir contains .hidden file?
            hidden = gethidden( dir->path );

            while ( ! vfs_async_task_is_cancelled( dir->task )
                        && ( file_name = g_dir_read_name( dir_content ) ) )
            {
                full_path = g_build_filename( dir->path, file_name, NULL );
                if ( !full_path )
                    continue;

                //MOD ignore if in .hidden
                if ( hidden && ishidden( hidden, file_name ) )
                {
                    dir->xhidden_count++;
                    continue;
                }
                /* FIXME: Is locking GDK needed here? */
                /* GDK_THREADS_ENTER(); */
                file = vfs_file_info_new();
                if ( G_LIKELY( vfs_file_info_get( file, full_path, file_name ) ) )
                {
                    g_mutex_lock( dir->mutex );

                    /* Special processing for desktop folder */
                    vfs_file_info_load_special_info( file, full_path );

                    /* FIXME: load info, too when new file is added to trash dir */
                    if( G_UNLIKELY( dir->is_trash ) ) /* load info of trashed files */
                    {
                        gboolean info_loaded;
                        char* info = g_strconcat( home_trash_dir, "/info/", file_name, ".trashinfo", NULL );

                        info_loaded = g_key_file_load_from_file( kf, info, 0, NULL );
                        g_free( info );
                        if( info_loaded )
                        {
                            char* ori_path = g_key_file_get_string( kf, "Trash Info", "Path", NULL );
                            if( ori_path )
                            {
                                /* Thanks to the stupid freedesktop.org spec, the filename is encoded
                                 * like a URL, which is insane. This add nothing more than overhead. */
                                char* fake_uri = g_strconcat( "file://", ori_path, NULL );
                                g_free( ori_path );
                                ori_path = g_filename_from_uri( fake_uri, NULL, NULL );
                                /* g_debug( ori_path ); */

                                if( file->disp_name && file->disp_name != file->name )
                                    g_free( file->disp_name );
                                file->disp_name = g_filename_display_basename( ori_path );
                                g_free( ori_path );
                            }
                        }
                    }

                    dir->file_list = g_list_prepend( dir->file_list, file );
                    g_mutex_unlock( dir->mutex );
                    ++dir->n_files;
                }
                else
                {
                    vfs_file_info_unref( file );
                }
                /* GDK_THREADS_LEAVE(); */
                g_free( full_path );
            }
            g_dir_close( dir_content );
            if ( hidden )
                g_free( hidden );

            if( G_UNLIKELY(dir->is_trash) )
                g_key_file_free( kf );
        }
    }
    return NULL;
}