How to use JSCallback in Firebreath?

拥有回忆 提交于 2020-01-06 08:29:26

问题


I'd like to add an event handler in my C++ code.

I followed document in firebreath.org (Callback from Scripts):

FB::JSObjectPtr doc = m_host->getDOMDocument()->getJSObject();
doc->Invoke("addEventListener", FB::variant_list_of("load", FB::make_callback(this, &mine::foo)));

but seeing following error:

/home/dq/manager/mine.cpp: In member function ‘void mine::init()’:
/home/dq/manager/mine.cpp:284:119: error: no matching function for call to ‘variant_list_of(const char [5], FB::JSAPIPtr)’
/home/dq/manager/mine.cpp:284:119: note: candidates are:
/usr/include/firebreath/ScriptingCore/variant_list.h:122:5: note: FB::detail::VariantListInserter FB::variant_list_of(FB::variant)
/usr/include/firebreath/ScriptingCore/variant_list.h:122:5: note:   candidate expects 1 argument, 2 provided
/usr/include/firebreath/ScriptingCore/variant_list.h:128:5: note: FB::VariantList FB::variant_list_of()
/usr/include/firebreath/ScriptingCore/variant_list.h:128:5: note:   candidate expects 0 arguments, 2 provided
In file included from /home/deqing/manager/mine.h:51:0,
                 from /home/deqing/manager/mine.cpp:37:
/usr/include/firebreath/ScriptingCore/JSCallback.h: In function ‘FB::JSAPIPtr FB::make_callback(const T&, F, bool) [with T = mine*, F = void (mine::*)(), FB::JSAPIPtr = boost::shared_ptr<FB::JSAPI>]’:
/home/dq/manager/mine.cpp:284:118:   instantiated from here
/usr/include/firebreath/ScriptingCore/JSCallback.h:47:107: error: request for member ‘get’ in ‘instance’, which is of    non-class type ‘mine* const’
/usr/include/firebreath/ScriptingCore/JSCallback.h:49:97: error: request for member ‘get’ in ‘instance’, which is of non-class type ‘mine* const’
make[2]: *** [CMakeFiles/mine.dir/manager/mine.cpp.o] Error 1
make[1]: *** [CMakeFiles/mine.dir/all] Error 2
make: *** [all] Error 2

Looking into the implementation of make_callback(), I tried following instead:

FB::JSObjectPtr doc = m_host->getDOMDocument()->getJSObject();
doc->Invoke("addEventListener", FB::variant_list_of("load")(FB::JSAPIPtr(new FB::JSCallback(FB::make_method(this, &mine::foo)))));

Compile passed this time, but my function - mine::foo() is not called with document.load()

By using "Inspect Element" in chrome, in "Event Listeners" I can see a new listener is added for "load". However, the listenerBody is a <JSAPI-Auto Javascript Object>.

I'm afraid this is why mine::foo() is not called, Javascript don't know how to call it because it is not a function, only an object.

Any one know how to get this done?

Another way that I can think of is:

  1. Register a custom event handler
  2. Fire the custom event on init

I'd like to use something like:

registerEventMethod("myevent", &mine::foo);

so that when myevent is fired, mine::foo() can be called.

The question here is, mine::foo is not a JSObjectPtr, so this snippet of code wouldn't work.

What is the proper way to use registerEventMethod() in this case?


回答1:


registerEventObject was really never intended to be called manually; it is used by the internal implementations of addEventListener and attachEvent. The purpose is to attach javascript handlers to events in the plugin.

I would recommend you use something like boost's signals and slots to implement your own c++-side event system; FireBreath's stuff was never intended to solve that problem. On the other hand, if you wanted to look at it it would probably be possible to extend FireBreath's functionality to support that and I have it on very good authority that the gatekeeper for FireBreath would probably entertain a pull request to that end. =]



来源:https://stackoverflow.com/questions/11112152/how-to-use-jscallback-in-firebreath

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!