Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to connect signal on derived class of GstBin? #293

Open
fastcoding opened this issue May 11, 2022 · 5 comments
Open

How to connect signal on derived class of GstBin? #293

fastcoding opened this issue May 11, 2022 · 5 comments

Comments

@fastcoding
Copy link

For example,

local Gst=lgi.Gst
local bin=Gst.parse_bin_from_description('rtspsrc location="rtsp://...."  name=mysrc ! rtph264depay ', true)
local rtspsrc=bin:get_by_name('mysrc')
function rtspsrc:on_on_sdp(sdp,ud)
	print('got sdp:',sdp)
end

when connecting to 'on-sdp' signal on a GstRtspSrc object, the above codes would fail with error message:

Gst.Bin: no `on_on_sdp'

It seems signals are loaded from GI typelib rather than through gobject runtime query. Maybe the way I'm using signals for such case is wrong?

@pavouk
Copy link
Collaborator

pavouk commented May 12, 2022

Most probably lgi does not have loaded GI typelib for GstRtspSrc object, so it treats it as its parent, GstBin. Try loading GstRtspSrc first using something like local GstRtsp = lgi.GstRtsp.

@fastcoding
Copy link
Author

Thanks for reply. But unfortunately GstRtspSrc namespace doesn't exist. I just checked the meson.build file in GstRtspSrc (in gst-plugins-good), it doesn't include a g-ir-scanner command in the build like other Gst components do. I don't know whether it's intentional or not. That means the only way is to manually create typelib or cannot use lgi for this case.

I tried directly calling GObject.signal_connect_closure_by_id. It can connect signal successfully, but fail when closure gets invoked.

Error raised while calling 'lgi.cbk (function: 0x0100e72ea0): GObject': attempt to index 
a nil value

Is it possible to create a user defined GICallableInfo to make the closure callback marshalling work?

@pavouk
Copy link
Collaborator

pavouk commented May 12, 2022

Interesting, this page https://packages.debian.org/sid/i386/gir1.2-gst-plugins-base-1.0/filelist
indicates that GstRtsp should exist. Note that typelib is GstRtsp, not GstRtspSrc.
I don't remember how to connect signal manually, sorry.

@fastcoding
Copy link
Author

yes, GstRtsp and GstRtspSrc are different components. The latter can be directly used in pipeline and what I'd like to use lgi to control. I've mentioned using GObject.signal_connect_closure_by_id to manually connect to 'on-sdp' signal, the code was basically copied from lgi/overides/GObject-Object.lua, like this:

local signal_lookup = GObject.signal_lookup
local Closure=GObject.Closure
local signal_connect_closure_by_id = GObject.signal_connect_closure_by_id
-- Connects signal to specified object instance.
local function connect_signal(obj, name, closure, detail, after)
   assert(obj._gtype)
   local id=signal_lookup(name, obj._gtype)
   assert(id)
   print('id=',id)
   return signal_connect_closure_by_id(
      obj,id ,
      detail and quark_from_string(detail) or 0,
      closure, after or false)
end
local clo=Closure( function(sdp,ud)
	print('rtsp got sdp:',sdp)
	return 1
end)
assert(clo)
connect_signal(rtspsrc,'on-sdp',clo)

The issue for this work-around is it will throw error when receiving callback. I guess it's due to lack of the GICallbackInfo interface, lgi doesn't know how to unpack the parameters. Thanks anyway, I will look for other ways around this.

@fastcoding
Copy link
Author

The above problem was eventually solved by me. Here is one line patch:

--- a/lgi/override/GObject-Closure.lua
+++ b/lgi/override/GObject-Closure.lua
@@ -282,7 +282,7 @@ function Closure:_new(target, callback_info)
         -- Create marshaller based only on Value types.
         function marshaller(closure, retval, params)
            local args = {}
-           for i, val in ipairs(params) do args[i] = val.value end
+           for i, val in ipairs(params) do args[i] = val end
            local ret = target(unpack(args, 1, #params))
            if retval then retval.value = ret end
         end

In my case, whenever receiving 'on-sdp' callback, one of the params (userdata) passed to the marshaller is nil,

    args[i]=nil.value

and thus results in lgi.callable throw error.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants