diff options
Diffstat (limited to 'components/draglistbox.cpp')
-rw-r--r-- | components/draglistbox.cpp | 141 |
1 files changed, 0 insertions, 141 deletions
diff --git a/components/draglistbox.cpp b/components/draglistbox.cpp deleted file mode 100644 index 492abc3..0000000 --- a/components/draglistbox.cpp +++ /dev/null @@ -1,141 +0,0 @@ -#include "draglistbox.hpp" - -DragListBox::DragListBox() { - drag_dest_set(m_entries, Gtk::DEST_DEFAULT_MOTION | Gtk::DEST_DEFAULT_DROP, Gdk::ACTION_MOVE); -} - -void DragListBox::row_drag_begin(Gtk::Widget *widget, const Glib::RefPtr<Gdk::DragContext> &context) { - m_drag_row = dynamic_cast<Gtk::ListBoxRow *>(widget->get_ancestor(GTK_TYPE_LIST_BOX_ROW)); - - auto alloc = m_drag_row->get_allocation(); - auto surface = Cairo::ImageSurface::create(Cairo::FORMAT_ARGB32, alloc.get_width(), alloc.get_height()); - auto cr = Cairo::Context::create(surface); - - m_drag_row->get_style_context()->add_class("drag-icon"); - gtk_widget_draw(reinterpret_cast<GtkWidget *>(m_drag_row->gobj()), cr->cobj()); - m_drag_row->get_style_context()->remove_class("drag-icon"); - - int x, y; - widget->translate_coordinates(*m_drag_row, 0, 0, x, y); - surface->set_device_offset(-x, -y); - context->set_icon(surface); -} - -bool DragListBox::on_drag_motion(const Glib::RefPtr<Gdk::DragContext> &context, gint x, gint y, guint time) { - if (y > m_hover_top || y < m_hover_bottom) { - auto *row = get_row_at_y(y); - if (row == nullptr) return true; - const bool old_top = m_top; - const auto alloc = row->get_allocation(); - - const int hover_row_y = alloc.get_y(); - const int hover_row_height = alloc.get_height(); - if (row != m_drag_row) { - if (y < hover_row_y + hover_row_height / 2) { - m_hover_top = hover_row_y; - m_hover_bottom = m_hover_top + hover_row_height / 2; - row->get_style_context()->add_class("drag-hover-top"); - row->get_style_context()->remove_class("drag-hover-bottom"); - m_top = true; - } else { - m_hover_top = hover_row_y + hover_row_height / 2; - m_hover_bottom = hover_row_y + hover_row_height; - row->get_style_context()->add_class("drag-hover-bottom"); - row->get_style_context()->remove_class("drag-hover-top"); - m_top = false; - } - } - - if (m_hover_row != nullptr && m_hover_row != row) { - if (old_top) - m_hover_row->get_style_context()->remove_class("drag-hover-top"); - else - m_hover_row->get_style_context()->remove_class("drag-hover-bottom"); - } - - m_hover_row = row; - } - - check_scroll(y); - if (m_should_scroll && !m_scrolling) { - m_scrolling = true; - Glib::signal_timeout().connect(sigc::mem_fun(*this, &DragListBox::scroll), SCROLL_DELAY); - } - - return true; -} - -void DragListBox::on_drag_leave(const Glib::RefPtr<Gdk::DragContext> &context, guint time) { - m_should_scroll = false; -} - -void DragListBox::check_scroll(gint y) { - if (!get_focus_vadjustment()) - return; - - const double vadjustment_min = get_focus_vadjustment()->get_value(); - const double vadjustment_max = get_focus_vadjustment()->get_page_size() + vadjustment_min; - const double show_min = std::max(0, y - SCROLL_DISTANCE); - const double show_max = std::min(get_focus_vadjustment()->get_upper(), static_cast<double>(y) + SCROLL_DISTANCE); - if (vadjustment_min > show_min) { - m_should_scroll = true; - m_scroll_up = true; - } else if (vadjustment_max < show_max) { - m_should_scroll = true; - m_scroll_up = false; - } else { - m_should_scroll = false; - } -} - -bool DragListBox::scroll() { - if (m_should_scroll) { - if (m_scroll_up) { - get_focus_vadjustment()->set_value(get_focus_vadjustment()->get_value() - SCROLL_STEP_SIZE); - } else { - get_focus_vadjustment()->set_value(get_focus_vadjustment()->get_value() + SCROLL_STEP_SIZE); - } - } else { - m_scrolling = false; - } - return m_should_scroll; -} - -void DragListBox::on_drag_data_received(const Glib::RefPtr<Gdk::DragContext> &context, int x, int y, const Gtk::SelectionData &selection_data, guint info, guint time) { - int index = 0; - if (m_hover_row != nullptr) { - if (m_top) { - index = m_hover_row->get_index() - 1; - m_hover_row->get_style_context()->remove_class("drag-hover-top"); - } else { - index = m_hover_row->get_index(); - m_hover_row->get_style_context()->remove_class("drag-hover-bottom"); - } - - Gtk::Widget *handle = *reinterpret_cast<Gtk::Widget *const *>(selection_data.get_data()); - auto *row = dynamic_cast<Gtk::ListBoxRow *>(handle->get_ancestor(GTK_TYPE_LIST_BOX_ROW)); - - if (row != nullptr && row != m_hover_row) { - if (row->get_index() > index) - index += 1; - if (m_signal_on_drop.emit(row, index)) return; - row->get_parent()->remove(*row); - insert(*row, index); - } - } - - m_drag_row = nullptr; -} - -void DragListBox::add_draggable(Gtk::ListBoxRow *widget) { - widget->drag_source_set(m_entries, Gdk::BUTTON1_MASK, Gdk::ACTION_MOVE); - widget->signal_drag_begin().connect(sigc::bind<0>(sigc::mem_fun(*this, &DragListBox::row_drag_begin), widget)); - widget->signal_drag_data_get().connect([this, widget](const Glib::RefPtr<Gdk::DragContext> &context, Gtk::SelectionData &selection_data, guint info, guint time) { - selection_data.set("GTK_LIST_BOX_ROW", 32, reinterpret_cast<const guint8 *>(&widget), sizeof(&widget)); - }); - add(*widget); -} - -DragListBox::type_signal_on_drop DragListBox::signal_on_drop() { - return m_signal_on_drop; -} |