static gboolean on_drag_leave ( GtkWidget *dest_widget, GdkDragContext *drag_context, guint time) { FmPlacesView* view = FM_PLACES_VIEW(dest_widget); gtk_tree_view_set_drag_dest_row(GTK_TREE_VIEW(view), NULL, 0); g_debug("drag_leave"); fm_dnd_dest_drag_leave(view->dnd_dest, drag_context, time); return FALSE; }
static void fm_places_view_finalize(GObject *object) { FmPlacesView *self; g_return_if_fail(object != NULL); g_return_if_fail(IS_FM_PLACES_VIEW(object)); self = FM_PLACES_VIEW(object); if(self->dest_row) gtk_tree_path_free(self->dest_row); G_OBJECT_CLASS(fm_places_view_parent_class)->finalize(object); }
gboolean on_button_press(GtkWidget* widget, GdkEventButton* evt) { FmPlacesView* view = FM_PLACES_VIEW(widget); GtkTreePath* tp; GtkTreeViewColumn* col; gboolean ret = GTK_WIDGET_CLASS(fm_places_view_parent_class)->button_press_event(widget, evt); int cell_x; gtk_tree_view_get_path_at_pos(GTK_TREE_VIEW(view), evt->x, evt->y, &tp, &col, NULL, NULL); view->clicked_row = tp; if(tp) { switch(evt->button) /* middle click */ { case 1: /* left click */ break; case 2: /* middle click */ activate_row(view, 2, tp); break; case 3: /* right click */ { GtkTreeIter it; if(gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &it, tp) && !fm_places_model_iter_is_separator(FM_PLACES_MODEL(model), &it) ) { FmPlaceItem* item; GtkWidget* menu; gtk_tree_model_get(GTK_TREE_MODEL(model), &it, FM_PLACES_MODEL_COL_INFO, &item, -1); menu = place_item_get_menu(item); if(menu) { gtk_menu_attach_to_widget(GTK_MENU(menu), widget, NULL); gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, 3, evt->time); } } } break; } } return ret; }
static gboolean on_drag_drop ( GtkWidget *dest_widget, GdkDragContext *drag_context, gint x, gint y, guint time) { FmPlacesView* view = FM_PLACES_VIEW(dest_widget); GtkTreeViewDropPosition pos; gboolean ret = FALSE; GdkAtom target = gtk_drag_dest_find_target(dest_widget, drag_context, NULL); /* this is to reorder bookmark */ if(target == gdk_atom_intern_static_string("GTK_TREE_MODEL_ROW")) { gtk_drag_get_data(dest_widget, drag_context, target, time); ret = TRUE; } else { /* try FmDndDest */ ret = fm_dnd_dest_drag_drop(view->dnd_dest, drag_context, target, time); if(!ret) gtk_drag_finish(drag_context, FALSE, FALSE, time); } return ret; }
gboolean on_button_release(GtkWidget* widget, GdkEventButton* evt) { FmPlacesView* view = FM_PLACES_VIEW(widget); if(view->clicked_row) { if(evt->button == 1) { GtkTreePath* tp; GtkTreeViewColumn* col; int cell_x; if(gtk_tree_view_get_path_at_pos(GTK_TREE_VIEW(view), evt->x, evt->y, &tp, &col, &cell_x, NULL)) { /* check if we release the button on the row we previously clicked. */ if(gtk_tree_path_compare(tp, view->clicked_row) == 0) { /* check if we click on the "eject" icon. */ int start, cell_w; gtk_tree_view_column_cell_get_position(col, view->mount_indicator_renderer, &start, &cell_w); if(cell_x > start && cell_x < (start + cell_w)) /* click on eject icon */ { GtkTreeIter it; /* do eject if needed */ if(gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &it, tp)) { FmPlaceItem* item; gtk_tree_model_get(GTK_TREE_MODEL(model), &it, FM_PLACES_MODEL_COL_INFO, &item, -1); if(item && item->vol_mounted) { GtkWidget* toplevel = gtk_widget_get_toplevel(view); /* eject the volume */ if(g_volume_can_eject(item->vol)) fm_eject_volume(toplevel, item->vol, TRUE); else /* not ejectable, do unmount */ { GMount* mnt = g_volume_get_mount(item->vol); if(mnt) { fm_unmount_mount(toplevel, mnt, TRUE); g_object_unref(mnt); } } gtk_tree_path_free(tp); gtk_tree_path_free(view->clicked_row); view->clicked_row = NULL; return TRUE; } } } /* activate the clicked row. */ gtk_tree_view_row_activated(GTK_TREE_VIEW(view), view->clicked_row, col); } gtk_tree_path_free(tp); } } gtk_tree_path_free(view->clicked_row); view->clicked_row = NULL; } return GTK_WIDGET_CLASS(fm_places_view_parent_class)->button_release_event(widget, evt); }
void on_row_activated(GtkTreeView* view, GtkTreePath* tree_path, GtkTreeViewColumn *col) { activate_row(FM_PLACES_VIEW(view), 1, tree_path); }
static void on_drag_data_received ( GtkWidget *dest_widget, GdkDragContext *drag_context, gint x, gint y, GtkSelectionData *sel_data, guint info, guint time) { FmPlacesView* view = FM_PLACES_VIEW(dest_widget); GtkTreePath* dest_tp = NULL; GtkTreeViewDropPosition pos; gtk_tree_view_get_dest_row_at_pos(GTK_TREE_VIEW(view), x, y, &dest_tp, &pos); switch(info) { case FM_DND_DEST_TARGET_BOOOKMARK: if(get_bookmark_drag_dest(view, &dest_tp, &pos)) /* got the drop position */ { GtkTreePath* src_tp; /* get the source row */ gboolean ret = gtk_tree_get_row_drag_data(sel_data, NULL, &src_tp); if(ret) { /* don't do anything if source and dest are the same row */ if(G_UNLIKELY(gtk_tree_path_compare(src_tp, dest_tp) == 0)) ret = FALSE; else { /* don't do anything if this is not a bookmark item */ if(!fm_places_model_path_is_bookmark(FM_PLACES_MODEL(model), src_tp)) ret = FALSE; } if(ret) { GtkTreeIter src_it, dest_it; FmPlaceItem* item = NULL; ret = FALSE; /* get the source bookmark item */ if(gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &src_it, src_tp)) gtk_tree_model_get(GTK_TREE_MODEL(model), &src_it, FM_PLACES_MODEL_COL_INFO, &item, -1); if(item) { /* move it to destination position */ if(gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &dest_it, dest_tp)) { int new_pos, sep_pos; /* get index of the separator */ const GtkTreePath* sep_tp = fm_places_model_get_separator_path(FM_PLACES_MODEL(model)); sep_pos = gtk_tree_path_get_indices(sep_tp)[0]; if(pos == GTK_TREE_VIEW_DROP_BEFORE) gtk_list_store_move_before(model, &src_it, &dest_it); else gtk_list_store_move_after(model, &src_it, &dest_it); new_pos = gtk_tree_path_get_indices(dest_tp)[0] - sep_pos - 1; /* reorder the bookmark item */ fm_bookmarks_reorder(FM_PLACES_MODEL(model)->bookmarks, item->bm_item, new_pos); ret = TRUE; } } } gtk_tree_path_free(src_tp); } gtk_drag_finish(drag_context, ret, FALSE, time); } break; default: /* check if files are received. */ fm_dnd_dest_drag_data_received(view->dnd_dest, drag_context, x, y, sel_data, info, time); break; } if(dest_tp) gtk_tree_path_free(dest_tp); }
static gboolean on_drag_motion (GtkWidget *dest_widget, GdkDragContext *drag_context, gint x, gint y, guint time) { FmPlacesView* view = FM_PLACES_VIEW(dest_widget); /* fm_drag_context_has_target_name(drag_context, "GTK_TREE_MODEL_ROW"); */ GdkAtom target; GtkTreeViewDropPosition pos; GtkTreePath* tp, *sep; gboolean ret = FALSE; GdkDragAction action = 0; target = gtk_drag_dest_find_target(dest_widget, drag_context, NULL); if(target == GDK_NONE) return FALSE; gtk_tree_view_get_dest_row_at_pos((GtkTreeView*)view, x, y, &tp, &pos); /* handle reordering bookmark items first */ if(target == gdk_atom_intern_static_string("GTK_TREE_MODEL_ROW")) { /* bookmark item is being dragged */ ret = get_bookmark_drag_dest(view, &tp, &pos); action = ret ? GDK_ACTION_MOVE : 0; /* bookmark items can only be moved */ } /* try FmDndDest */ else if(fm_dnd_dest_is_target_supported(view->dnd_dest, target)) { /* the user is dragging files. get FmFileInfo of drop site. */ if(pos == GTK_TREE_VIEW_DROP_INTO_OR_BEFORE || pos == GTK_TREE_VIEW_DROP_INTO_OR_AFTER) /* drag into items */ { FmPlaceItem* item = NULL; GtkTreeIter it; /* FIXME: handle adding bookmarks with Dnd */ if(tp && gtk_tree_model_get_iter(GTK_TREE_MODEL(model), &it, tp)) gtk_tree_model_get(GTK_TREE_MODEL(model), &it, FM_PLACES_MODEL_COL_INFO, &item, -1); fm_dnd_dest_set_dest_file(view->dnd_dest, item && item->fi ? item->fi : NULL); action = fm_dnd_dest_get_default_action(view->dnd_dest, drag_context, target); ret = action != 0; } else /* drop between items, create bookmark items for dragged files */ { if( (!tp || fm_places_model_path_is_bookmark(FM_PLACES_MODEL(model), tp)) && get_bookmark_drag_dest(view, &tp, &pos)) /* tp is after separator */ { action = GDK_ACTION_LINK; ret = TRUE; } else { action = 0; ret = FALSE; } } } gdk_drag_status(drag_context, action, time); if(ret) gtk_tree_view_set_drag_dest_row(GTK_TREE_VIEW(view), tp, pos); else gtk_tree_view_set_drag_dest_row(GTK_TREE_VIEW(view), NULL, 0); if(tp) gtk_tree_path_free(tp); return ret; }