Re: Gtk2::TreeView drag'n drop
- From: Emmanuele Bassi <bassi-e libero it>
- To: gtk-perl list <gtk-perl-list gnome org>
- Subject: Re: Gtk2::TreeView drag'n drop
- Date: Sat, 31 Jan 2004 08:21:11 +0100
* Jens Luedicke <jens gcc dyndns org>:
I would like to enable drag'n drop between
two Gtk2::TreeView's. My code allows
to start dragging, but I can't drop anything.
Any hints?
I've yet to try in Perl, but should be simple.
First af all, you need to enable model drag and drop, by using the
Gtk2::TreeView::enable_model_drag_source
and the
Gtk2::TreeView::enable_model_drag_dest
methods. You must specify inside the 'flags' field of the GtkTargetEntry
hashref that the target is within the same application, and not the same
widget (default); use the 'same-app' enum id.
Then, connect the 'drag-data-get' signal to a function that retrieves
the data on the selected row, like this one:
sub on_drag_data_get
{
my ($treeview, $context, $selection_data, $info, $time) = @_;
if ($info == ...) # compare to the 'info' field inside the GtkTargetEntry
{
my ($model, $iter) = $treeview->get_selection()->get_selected;
# get the data at $iter using $model->get...
my $payload = ... # serialize the data
$selection_data->set($selection_data->target, 8, $payload);
}
elsif ($info == ...)
{
#...
}
#...
}
Finally, connect the 'drag-data-received' signal to a function like this
one:
sub on_drag_data_received
{
my ($treeview, $context, $x, $y, $selection_data, $info, $time) = @_;
my $model = $treeview->get_model;
if ($info == ...)
{
my $source = $context->get_source_widget;
my ($target_path, $target_pos) = $treeview->get_dest_row_at_pos($x, $y);
my $target_data;
if ($source_widget and ($treeview eq $source_widget))
{
# same widget: reordering
# there's no point in using the serialized data, since we
# can access to the treeview.
my $iter_to_copy = $treeview->get_selection->get_selected;
# fetch the data from $iter_to_copy inside $target_data
# ...
}
else
{
# different widget
# since the treeview and the model are different, we need to
# use the serialized data inside the $selection_data data
# structure.
if ($selection_data and ($selection_data->format == 8))
{
# unserialize $selection_data->data inside $target_data
}
}
my $target_iter = $model->get_iter($path);
# drop postion matters.
if ($target_iter and $target_pos and $target_data)
{
my $new_iter;
if ($target_pos eq 'drop-before')
{
$new_iter = $model->insert_before($target_iter);
}
elsif ($target_pos eq 'drop-after')
{
$new_iter = $model->insert_after($target_iter);
}
else
{
# fallback
$new_iter = $model->insert_after($target_iter);
}
if ($new_iter)
{
# put the $target_data in the model.
}
}
# this ends the d'n'd operations.
$context->finish(TRUE, TRUE, $time);
}
elsif ($info == ...)
{
# ...
$context->finish(TRUE, TRUE, $time);
}
else
{
# failure.
$context->(FALSE, TRUE, $time);
}
}
+++
The code above is untested, but you get the picture.
Regards,
Emmanuele.
--
Emmanuele Bassi (Zefram) [ http://www.emmanuelebassi.net ]
GnuPG Key fingerprint = 4DD0 C90D 4070 F071 5738 08BD 8ECC DB8F A432 0FF4
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]