Created
February 28, 2025 10:51
-
-
Save SpikedPaladin/48f7a752935f52c94c9227eb64e69ed7 to your computer and use it in GitHub Desktop.
DragView vala
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class DragView : Gtk.Widget { | |
construct { | |
new TestChild().set_parent(this); | |
with (var it = new Gtk.GestureDrag()) { | |
DragChild? drag_target = null; | |
Graphene.Point start_cursor_pos = { 0, 0 }; | |
Graphene.Point cursor_offset = { 0, 0 }; | |
it.drag_begin.connect((x, y) => { | |
var widget = pick(x, y, Gtk.PickFlags.DEFAULT); | |
if (!(widget is DragView)) { | |
DragChild? target = widget as DragChild; | |
if (!(target is DragChild)) | |
for (var parent = widget.parent; !(parent is DragView); parent = parent.parent) { | |
if (parent is DragChild) { | |
target = parent as DragChild; | |
break; | |
} | |
} | |
if (target == null) | |
return; | |
start_cursor_pos = { (float) x, (float) y }; | |
drag_target = target; | |
cursor_offset = { | |
start_cursor_pos.x - drag_target.x, | |
start_cursor_pos.y - drag_target.y | |
}; | |
} | |
}); | |
it.drag_update.connect((offset_x, offset_y) => { | |
if (drag_target == null) | |
return; | |
double start_x, start_y; | |
it.get_start_point(out start_x, out start_y); | |
Graphene.Point origin = { (float) (start_x + offset_x), (float) (start_y + offset_y) }; | |
drag_target.x = (int) (origin.x - cursor_offset.x); | |
drag_target.y = (int) (origin.y - cursor_offset.y); | |
drag_target.x = drag_target.x.clamp(0, get_width() - drag_target.get_width()); | |
drag_target.y = drag_target.y.clamp(0, get_height() - drag_target.get_height()); | |
queue_allocate(); | |
}); | |
it.drag_end.connect(() => { | |
drag_target = null; | |
}); | |
add_controller(it); | |
} | |
} | |
public override void size_allocate(int width, int height, int baseline) { | |
for (var child = get_first_child(); child != null; child = child.get_next_sibling()) { | |
var drag_child = child as DragChild; | |
if (drag_child == null) continue; | |
Gtk.Requisition _, natural_size; | |
child.get_preferred_size(out _, out natural_size); | |
child.allocate( | |
natural_size.width, | |
natural_size.height, | |
baseline, | |
new Gsk.Transform().translate({ drag_child.x, drag_child.y }) | |
); | |
} | |
} | |
public class TestChild : DragChild { | |
construct { | |
set_layout_manager(new Gtk.BinLayout()); | |
var label = new Gtk.Label("Test"); | |
label.set_parent(this); | |
} | |
} | |
public abstract class DragChild : Gtk.Widget { | |
public virtual int x { get; set; } | |
public virtual int y { get; set; } | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment