app-manager/localmedia.c
author J. Ali Harlow <ali@juiblex.co.uk>
Sat Feb 20 12:11:02 2010 +0000 (2010-02-20)
changeset 9 8d3b1ddf789c
child 10 8b50be3e2998
permissions -rw-r--r--
First cut at an applications manager
ali@9
     1
/*
ali@9
     2
 * Copyright (C) 2010  J. Ali Harlow <ali@juiblex.co.uk>
ali@9
     3
 *
ali@9
     4
 * This program is free software; you can redistribute it and/or modify
ali@9
     5
 * it under the terms of the GNU General Public License as published by
ali@9
     6
 * the Free Software Foundation; either version 2 of the License, or
ali@9
     7
 * (at your option) any later version.
ali@9
     8
 *
ali@9
     9
 * This program is distributed in the hope that it will be useful,
ali@9
    10
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
ali@9
    11
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
ali@9
    12
 * GNU General Public License for more details.
ali@9
    13
 *
ali@9
    14
 * You should have received a copy of the GNU General Public License along
ali@9
    15
 * with this program; if not, write to the Free Software Foundation, Inc.,
ali@9
    16
 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
ali@9
    17
 */
ali@9
    18
ali@9
    19
#include "config.h"
ali@9
    20
#include <stdlib.h>
ali@9
    21
#include <string.h>
ali@9
    22
#include <glib.h>
ali@9
    23
#include <gio/gio.h>
ali@9
    24
#include <gtk/gtk.h>
ali@9
    25
#include <plover-gtk/packagestore.h>
ali@9
    26
#include "localmedia.h"
ali@9
    27
ali@9
    28
G_DEFINE_TYPE(PloverLocalMediaStore,plover_local_media_store,
ali@9
    29
  PLOVER_TYPE_PACKAGE_STORE);
ali@9
    30
ali@9
    31
static void plover_local_media_store_dispose(GObject *obj)
ali@9
    32
{
ali@9
    33
    PloverLocalMediaStore *store=PLOVER_LOCAL_MEDIA_STORE(obj);
ali@9
    34
    if (store->monitor)
ali@9
    35
    {
ali@9
    36
	g_object_unref(store->monitor);
ali@9
    37
	store->monitor=NULL;
ali@9
    38
    }
ali@9
    39
    if (G_OBJECT_CLASS(plover_local_media_store_parent_class)->dispose)
ali@9
    40
	G_OBJECT_CLASS(plover_local_media_store_parent_class)->dispose(obj);
ali@9
    41
}
ali@9
    42
ali@9
    43
static void
ali@9
    44
  plover_local_media_store_class_init(PloverLocalMediaStoreClass *klass)
ali@9
    45
{
ali@9
    46
    GObjectClass *oclass=G_OBJECT_CLASS(klass);
ali@9
    47
    oclass->dispose=plover_local_media_store_dispose;
ali@9
    48
}
ali@9
    49
ali@9
    50
GtkTreeModel *plover_local_media_store_new(void)
ali@9
    51
{
ali@9
    52
    return g_object_new(PLOVER_TYPE_LOCAL_MEDIA_STORE,NULL);
ali@9
    53
}
ali@9
    54
ali@9
    55
static void local_media_scan_mount(PloverLocalMediaStore *store,GMount *mount)
ali@9
    56
{
ali@9
    57
    GFile *root;
ali@9
    58
    gchar *path;
ali@9
    59
    PloverPackageSet *set;
ali@9
    60
    root=g_mount_get_root(mount);
ali@9
    61
    path=g_file_get_path(root);
ali@9
    62
    if (path)
ali@9
    63
    {
ali@9
    64
	set=plover_package_set_new_from_repository(path,NULL);
ali@9
    65
	if (set)
ali@9
    66
	{
ali@9
    67
	    g_object_set_data(G_OBJECT(mount),"plover-local-media-set",set);
ali@9
    68
	    plover_package_store_add_set(PLOVER_PACKAGE_STORE(store),set);
ali@9
    69
	    g_object_ref(mount);
ali@9
    70
	}
ali@9
    71
	g_free(path);
ali@9
    72
    }
ali@9
    73
    g_object_unref(root);
ali@9
    74
}
ali@9
    75
ali@9
    76
static void local_media_mounted(GObject *source,GAsyncResult *res,gpointer data)
ali@9
    77
{
ali@9
    78
    GVolume *volume=G_VOLUME(source);
ali@9
    79
    GMount *mount;
ali@9
    80
    PloverLocalMediaStore *store=PLOVER_LOCAL_MEDIA_STORE(data);
ali@9
    81
    if (g_volume_mount_finish(volume,res,NULL))
ali@9
    82
    {
ali@9
    83
	mount=g_volume_get_mount(volume);
ali@9
    84
	if (mount)
ali@9
    85
	{
ali@9
    86
	    local_media_scan_mount(store,mount);
ali@9
    87
	    g_object_unref(mount);
ali@9
    88
	}
ali@9
    89
    }
ali@9
    90
    g_object_unref(volume);
ali@9
    91
}
ali@9
    92
ali@9
    93
static void local_media_scan_drive(PloverLocalMediaStore *store,GDrive *drive)
ali@9
    94
{
ali@9
    95
    GVolume *volume;
ali@9
    96
    GMount *mount;
ali@9
    97
    GList *volumes,*link;
ali@9
    98
    if (g_drive_has_media(drive))
ali@9
    99
    {
ali@9
   100
	volumes=g_drive_get_volumes(drive);
ali@9
   101
	for(link=volumes;link;link=link->next)
ali@9
   102
	{
ali@9
   103
	    volume=G_VOLUME(link->data);
ali@9
   104
	    mount=g_volume_get_mount(volume);
ali@9
   105
	    if (mount)
ali@9
   106
	    {
ali@9
   107
		local_media_scan_mount(store,mount);
ali@9
   108
		g_object_unref(mount);
ali@9
   109
	    }
ali@9
   110
	    else if (!store->implicit_scan && g_volume_can_mount(volume))
ali@9
   111
		g_volume_mount(volume,G_MOUNT_MOUNT_NONE,NULL,NULL,
ali@9
   112
		  local_media_mounted,store);
ali@9
   113
	    g_object_unref(volume);
ali@9
   114
	}
ali@9
   115
	g_list_free(volumes);
ali@9
   116
    }
ali@9
   117
}
ali@9
   118
ali@9
   119
static void local_media_polled(GObject *source,GAsyncResult *res,gpointer data)
ali@9
   120
{
ali@9
   121
    GDrive *drive=G_DRIVE(source);
ali@9
   122
    PloverLocalMediaStore *store=PLOVER_LOCAL_MEDIA_STORE(data);
ali@9
   123
    if (g_drive_poll_for_media_finish(drive,res,NULL))
ali@9
   124
	local_media_scan_drive(store,drive);
ali@9
   125
    g_object_unref(drive);
ali@9
   126
}
ali@9
   127
ali@9
   128
void plover_local_media_store_scan(PloverLocalMediaStore *store)
ali@9
   129
{
ali@9
   130
    GList *drives,*link;
ali@9
   131
    GDrive *drive;
ali@9
   132
    g_return_if_fail(PLOVER_IS_LOCAL_MEDIA_STORE(store));
ali@9
   133
    drives=g_volume_monitor_get_connected_drives(store->monitor);
ali@9
   134
    for(link=drives;link;link=link->next)
ali@9
   135
    {
ali@9
   136
	drive=G_DRIVE(link->data);
ali@9
   137
	if (g_drive_is_media_removable(drive))
ali@9
   138
	{
ali@9
   139
	    if (!g_drive_is_media_check_automatic(drive) &&
ali@9
   140
	      g_drive_can_poll_for_media(drive) ||
ali@9
   141
	      !g_drive_has_media(drive) && !store->implicit_scan)
ali@9
   142
	    {
ali@9
   143
		g_object_ref(drive);
ali@9
   144
		g_drive_poll_for_media(drive,NULL,local_media_polled,store);
ali@9
   145
	    }
ali@9
   146
	    else
ali@9
   147
		local_media_scan_drive(store,drive);
ali@9
   148
	}
ali@9
   149
	g_object_unref(drive);
ali@9
   150
    }
ali@9
   151
    g_list_free(drives);
ali@9
   152
}
ali@9
   153
ali@9
   154
static void local_media_mount_added(GVolumeMonitor *volume_monitor,
ali@9
   155
  GMount *mount,PloverLocalMediaStore *store)
ali@9
   156
{
ali@9
   157
    local_media_scan_mount(store,mount);
ali@9
   158
}
ali@9
   159
ali@9
   160
static void local_media_mount_removed(GVolumeMonitor *volume_monitor,
ali@9
   161
  GMount *mount,PloverLocalMediaStore *store)
ali@9
   162
{
ali@9
   163
    PloverPackageSet *set=
ali@9
   164
      g_object_get_data(G_OBJECT(mount),"plover-local-media-set");
ali@9
   165
    if (set)
ali@9
   166
    {
ali@9
   167
	plover_package_store_remove_set(PLOVER_PACKAGE_STORE(store),set);
ali@9
   168
	g_object_set_data(G_OBJECT(mount),"plover-local-media-set",NULL);
ali@9
   169
	g_object_unref(set);
ali@9
   170
	g_object_unref(mount);
ali@9
   171
    }
ali@9
   172
}
ali@9
   173
ali@9
   174
static void local_media_mount_changed(GVolumeMonitor *volume_monitor,
ali@9
   175
  GMount *mount,PloverLocalMediaStore *store)
ali@9
   176
{
ali@9
   177
    local_media_mount_removed(volume_monitor,mount,store);
ali@9
   178
    local_media_mount_added(volume_monitor,mount,store);
ali@9
   179
}
ali@9
   180
ali@9
   181
static void plover_local_media_store_init(PloverLocalMediaStore *store)
ali@9
   182
{
ali@9
   183
    store->monitor=g_volume_monitor_get();
ali@9
   184
    store->implicit_scan=TRUE;
ali@9
   185
    plover_local_media_store_scan(store);
ali@9
   186
    store->implicit_scan=FALSE;
ali@9
   187
    g_signal_connect(store->monitor,"mount-added",
ali@9
   188
      G_CALLBACK(local_media_mount_added),store);
ali@9
   189
    g_signal_connect(store->monitor,"mount-changed",
ali@9
   190
      G_CALLBACK(local_media_mount_changed),store);
ali@9
   191
    g_signal_connect(store->monitor,"mount-removed",
ali@9
   192
      G_CALLBACK(local_media_mount_removed),store);
ali@9
   193
}