jhass / crystal-gobject

gobject-introspection for Crystal
BSD 3-Clause "New" or "Revised" License
126 stars 13 forks source link

Compilation error generating TreeView#on_row_activated #53

Closed hugopl closed 4 years ago

hugopl commented 4 years ago

TreeView row-activated signal is generating a bad signature.

GTK docs at https://developer.gnome.org/gtk3/stable/GtkTreeView.html#GtkTreeView-row-activated says the user function should be:

void user_function(GtkTreeView *tree_view,
                   GtkTreePath       *path,
                   GtkTreeViewColumn *column,
                   gpointer           user_data)

But the generated bindings have:

    alias RowActivatedSignal = TreeView, Gtk::TreePath, Gtk::TreeViewColumn ->
    def on_row_activated(&__block : RowActivatedSignal)
      __callback = ->(_arg0 : LibGtk::TreeView*, _arg1 : LibGtk::TreePath*, _arg2 : LibGtk::TreeViewColumn**) {
       __return_value = __block.call(TreeView.new(_arg0), Gtk::TreePath.new(_arg1), Gtk::TreeViewColumn.new(_arg2))
       __return_value
      }
      connect("row-activated", __callback)
    end

This doesn't compile, but if we monkey patch it with:

module Gtk
  class Gtk::TreeViewColumn
    def initialize(pointer : Pointer(Pointer(LibGtk::TreeViewColumn)))
      @pointer = pointer.as(Void*)
    end
  end
end

it does, however the TreePath object is all zeros:

Crystal code to test it (using the glade file from examples)

require "gobject/gtk/autorun"

builder = Gtk::Builder.new_from_file("#{__DIR__}/../lib/gobject/samples/tree_view.glade")
builder.connect_signals

# Insert something into the model
model = Gtk::TreeStore.cast(builder["tree_model"])
root = Gtk::TreeIter.new
model.append(root, nil)
model.set(root, [0], GObject::Value.new("Root"), 1)

module Gtk
  class Gtk::TreeViewColumn
    def initialize(pointer : Pointer(Pointer(LibGtk::TreeViewColumn)))
      @pointer = pointer.as(Void*)
    end
  end
end

# view
view = Gtk::TreeView.cast(builder["tree_view"])
puts "TreeView ptr before signal: #{view.to_unsafe}"
view.on_row_activated do |view, path, column|
  puts "TreeView ptr inside signal: #{view.to_unsafe}"
  puts "Path is empty!?: #{path.to_unsafe.value}"
  puts "Column pointer: #{column.to_unsafe}"
end

# Show main view.
main_window = Gtk::Window.cast(builder["main_window"])
main_window.show_all

The initial bug is the signal generated code, but this path issue seems like some memory corruption too and need some investigation, a C example doesn't behave like that, I can write down a C example if it helps to debug the issue.

jhass commented 4 years ago

Looks like I didn't fully grasp signals yet, so next try :D

With master your example (minus any hacks) works for me now.