1

I have a UIWebView that utilizes JavaScriptCore. I'm trying to call an ObjC function from an web page. However, the function needs to be call asynchronously, so I'm passing in a callback function that is called when the async ObjC function is called.

It is my understanding that JS functions are equivalent to NSBlock via the bridge. The current code I have is:

context[@"currentUserLocation"] = ^( void(^callback)(NSString* str) )
{
    NSLog(@"Starting Async Function");

    //generic async function
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        NSLog(@"delay complete");
        callback( @"return value" );
    });
};

Is there something fundamentally wrong with what I'm doing? On the surface it seems like ObjC won't know what context to run the callback function in.

1 Answer 1

1

It took me a little while to get the hang of this. The trick is not to think of the callback argument as a block, but a JSValue and then call it using the JSValue API:

context[@"currentUserLocation"] = ^(JSValue *callback)
{
    NSLog(@"Starting Async Function");

    //generic async function
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        NSLog(@"delay complete");
        //Check we actually have a callback (isObject is the best we can do, there is no isFunction)
        if ([callback isObject] != NO) {
            //Use window.setTimeout to schedule the callback to be run
            [context[@"setTimeout"] callWithArguments:@[callback, @0, @"return value"]];
        }
    });
};

Wrapping the callback in a window.setTimeout() call allows the JSVirtualMachine to take care of scheduling and threading, I have found calling the callback directly often leads to deadlocks if any UI work is done by the callback.

Sign up to request clarification or add additional context in comments.

2 Comments

I ended up passing the function name as a string, but this answer definitely a lot better, def gona give this a try
Can u look at this question? stackoverflow.com/questions/23047512/…

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.