CefV8Callback::Execute not invoked

Having problems with building or using CEF's C/C++ APIs? This forum is here to help. Please do not post bug reports or feature requests here.

CefV8Callback::Execute not invoked

Postby nassersh » Tue Nov 24, 2015 5:35 pm

I already understand that JS Callbacks have to be invoked in the render process. As such, here's the C++:
Code: Select all
class App : public CefApp, public CefRenderProcessHandler
{
    virtual CefRefPtr<CefRenderProcessHandler> GetRenderProcessHandler() OVERRIDE { return this; }
   
    virtual void OnContextCreated(
        CefRefPtr<CefBrowser> browser,
        CefRefPtr<CefFrame> frame,
        CefRefPtr<CefV8Context> context) OVERRIDE
    {
        m_clientHandler = new ClientHandler; // see below
        CefRefPtr<CefV8Value> object = context->GetGlobal();
        object->SetValue("register", CefV8Value::CreateFunction("register", m_clientHandler), V8_PROPERTY_ATTRIBUTE_NONE);
    }
};

class ClientHandler :
    public CefClient,
    public CefLifeSpanHandler,
    public CefV8Handler
{
    ClientHandler();

    virtual void OnAfterCreated(...) OVERRIDE;

    virtual bool Execute(...) OVERRIDE;
};

And the JavaScript:
Code: Select all
function somefunc(arg) {
    // Do stuff
}

window.register(somefunc);

Interestingly enough, commenting out the 'window.register(somefunc)' line causes the page to work just fine (without the desired JS, obviously), but uncommenting it causes the page to not load. In addition to this, calling
Code: Select all
alert(window.register);

Pops up an alert window that says 'function() { [native code] }', if that means anything. I've looked at http://www.magpcss.org/ceforum/viewtopic.php?f=6&t=12909 already I've also passed the app.get() instance to CefInitialize(). Any ideas?
nassersh
Newbie
 
Posts: 3
Joined: Tue Nov 24, 2015 5:11 pm

Re: CefV8Callback::Execute not invoked

Postby magreenblatt » Tue Nov 24, 2015 6:22 pm

What is your CefV8Handler::Execute implementation? Also, you should implement CefV8Handler in a separate object from ClientHandler.
magreenblatt
Site Admin
 
Posts: 12404
Joined: Fri May 29, 2009 6:57 pm

Re: CefV8Callback::Execute not invoked

Postby nassersh » Tue Nov 24, 2015 7:01 pm

Thanks for your quick response.

As per the recommendation, I've separated the CefV8Handler from ClientHandler.
Code: Select all
// Just implements GetLifeSpanHandler() and a constructor
class ClientHandler : public CefClient, public CefLifeSpanHandler

And created a new CefV8Handler. I've provided the Execute() implementation below, but I should note that the function is not being entered. In other words, if you run a debugger and place a break point at the first line of Execute(), it is never hit, and the web browser occasionally displays an empty window. On the other hand, the page renders correctly when the 'window.register(someFunc)' line is commented out in the JavaScript, but obviously without registering the callback.
Code: Select all
class JSCallbackHandler : public CefV8Handler
{
public:
    bool Execute(
        const CefString& name,
        CefRefPtr< CefV8Value > object,
        const CefV8ValueList& arguments,
        CefRefPtr< CefV8Value >& retval,
        CefString& exception ) OVERRIDE
    {
        if (name == "register" && arguments.size() == 1 && arguments[0]->IsFunction())
        {
            m_callback = arguments[0];
            m_context = CefV8Context::GetCurrentContext();
            return true;
        }
        return false;
    }

private:
    CefRefPtr<CefV8Value> m_callback;
    CefRefPtr<CefV8Context> m_context;

    IMPLEMENT_REFCOUNTING(JSCallbackHandler);
}

Finally, the app class changes to:
Code: Select all
class App : public CefApp, public CefRenderProcessHandler
{
    virtual CefRefPtr<CefRenderProcessHandler> GetRenderProcessHandler() OVERRIDE { return this; }
   
    virtual void OnContextCreated(
        CefRefPtr<CefBrowser> browser,
        CefRefPtr<CefFrame> frame,
        CefRefPtr<CefV8Context> context) OVERRIDE
    {
        m_clientHandler = new ClientHandler;
        CefRefPtr<CefV8Value> object = context->GetGlobal();
        CefRefPtr<CefV8Handler> handler = new JSCallbackHandler;
        object->SetValue("register", CefV8Value::CreateFunction("register", handler), V8_PROPERTY_ATTRIBUTE_NONE);
    }
};
nassersh
Newbie
 
Posts: 3
Joined: Tue Nov 24, 2015 5:11 pm

Re: CefV8Callback::Execute not invoked

Postby amaitland » Tue Nov 24, 2015 7:10 pm

How are you attaching the debugger to the render process? Are you able to set a breakpoint anywhere in the code?

https://www.chromium.org/developers/how ... e-renderer
Maintainer of the CefSharp project.
amaitland
Virtuoso
 
Posts: 1291
Joined: Wed Jan 14, 2015 2:35 am

Re: CefV8Callback::Execute not invoked

Postby nassersh » Tue Nov 24, 2015 7:37 pm

Okay, I see the issue now. The Execute() method is being entered, I just couldn't tell because I was using the standard packaged debugger that comes with Visual Studio.
nassersh
Newbie
 
Posts: 3
Joined: Tue Nov 24, 2015 5:11 pm


Return to Support Forum

Who is online

Users browsing this forum: Google [Bot] and 37 guests