Clemapfel/Mousetrap.jl

AssertionError: Object of type AspectFrame does not fullfill the widget interface

LilithHafner opened this issue · 3 comments

When I try to use an AspectFrame (or any other widget I've tried) for the signal_connect_motion! signal handler, I get an AssertionError: Object of type AspectFrame does not fullfill the widget interface error. I'm assuming that Mousetrap.AspectFrame is supposed to fulfill the widget interface.

julia> using Mousetrap

julia> main() do app::Application
           window = Window(app)

           aspect_frame = AspectFrame(1.0)

           set_child!(window, aspect_frame)

           connect_signal_motion!(aspect_frame) do _, x, y
               println((x,y))
           end

           present!(window)
       end

(<unknown>:128894): GLib-GObject-CRITICAL **: 14:55:44.274: g_object_unref: assertion 'G_IS_OBJECT (object)' failed
[ERROR] In Mousetrap.main: AssertionError: Object of type AspectFrame does not fullfill the widget interface. In order for it to be able to be treated as a widget, you need to subtype `Mousetrap.Widget` **and** add a method with signature `(::AspectFrame) -> Widget` to `Mousetrap.get_top_level_widget`, which should map an instance of AspectFrame to its top-level widget component.
Stacktrace:
 [1] macro expansion
   @ ~/.julia/packages/Mousetrap/WZu6w/src/Mousetrap.jl:0 [inlined]
 [2] get_top_level_widget(x::AspectFrame)
   @ Mousetrap ~/.julia/packages/Mousetrap/WZu6w/src/Mousetrap.jl:362
 [3] connect_signal_motion!(f::Function, x::AspectFrame)
   @ Mousetrap ~/.julia/packages/Mousetrap/WZu6w/src/Mousetrap.jl:5530
 [4] (::var"#16#18")(app::Application)
   @ Main ./REPL[2]:8
 [5] (::TypedFunction)(args::Application)
   @ Mousetrap ~/.julia/packages/Mousetrap/WZu6w/src/Mousetrap.jl:91
 [6] (::Mousetrap.var"#14#15"{TypedFunction})(app::Application)
   @ Mousetrap ~/.julia/packages/Mousetrap/WZu6w/src/Mousetrap.jl:1542
 [7] (::TypedFunction)(args::Application)
   @ Mousetrap ~/.julia/packages/Mousetrap/WZu6w/src/Mousetrap.jl:91
 [8] (::Mousetrap.var"#6#8"{TypedFunction})(x::Tuple{CxxWrap.CxxWrapCore.CxxRef{Mousetrap.detail._Application}})
   @ Mousetrap ~/.julia/packages/Mousetrap/WZu6w/src/Mousetrap.jl:657
 [9] safe_call(scope::String, f::Function, args::Tuple{CxxWrap.CxxWrapCore.CxxRef{Mousetrap.detail._Application}})
   @ Mousetrap ~/.julia/packages/Mousetrap/WZu6w/src/Mousetrap.jl:190
0

I think you misunderstood the component interface. AspectFrame, or indeed most widgets, do not support signal motion. Instead, motion is a signal of an event controller, EventControllerMotion in this case. You need to create the event controller, then connect it to a widget using add_controller!. Afterwards you can connect to the signals of the event controller itself, but it will use the bounds of the widget:

using Mousetrap
main() do app::Application
    window = Window(app)
    aspect_frame = AspectFrame(1.0)
    set_child!(window, aspect_frame)

    # create event controller
    mouse = MotionEventController()
    
    # connect controller to widget
    add_controller!(aspect_frame, mouse)
    
    # connect to signal of controller
    connect_signal_motion!(mouse) do _, x, y
        println((x,y))
    end

    present!(window)
end

That said, that error message doesn't make any sense, I will keep this open until the message is replaced with something more descriptive.

Fixed by 4f16e9f, error message is now:

julia> frame = AspectFrame(1); f = () -> ();
julia> connect_signal_motion!(f, frame)
(process:375474): Mousetrap.jl-CRITICAL **: 18:17:45.974: In emit_signal_motion: object of type `AspectFrame` has no signal with ID `motion`

I'll keep this issue open until #75 is merged