You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
139 lines
4.2 KiB
139 lines
4.2 KiB
// This file contains the source for the Javascript side of the
|
|
// WebViewJavascriptBridge. It is plaintext, but converted to an NSString
|
|
// via some preprocessor tricks.
|
|
//
|
|
// Previous implementations of WebViewJavascriptBridge loaded the javascript source
|
|
// from a resource. This worked fine for app developers, but library developers who
|
|
// included the bridge into their library, awkwardly had to ask consumers of their
|
|
// library to include the resource, violating their encapsulation. By including the
|
|
// Javascript as a string resource, the encapsulation of the library is maintained.
|
|
|
|
#import "WebViewJavascriptBridge_JS.h"
|
|
|
|
NSString * WebViewJavascriptBridge_js() {
|
|
#define __wvjb_js_func__(x) #x
|
|
|
|
// BEGIN preprocessorJSCode
|
|
static NSString * preprocessorJSCode = @__wvjb_js_func__(
|
|
;(function() {
|
|
if (window.WebViewJavascriptBridge) {
|
|
return;
|
|
}
|
|
|
|
if (!window.onerror) {
|
|
window.onerror = function(msg, url, line) {
|
|
console.log("WebViewJavascriptBridge: ERROR:" + msg + "@" + url + ":" + line);
|
|
}
|
|
}
|
|
window.WebViewJavascriptBridge = {
|
|
registerHandler: registerHandler,
|
|
callHandler: callHandler,
|
|
disableJavscriptAlertBoxSafetyTimeout: disableJavscriptAlertBoxSafetyTimeout,
|
|
_fetchQueue: _fetchQueue,
|
|
_handleMessageFromObjC: _handleMessageFromObjC
|
|
};
|
|
|
|
var messagingIframe;
|
|
var sendMessageQueue = [];
|
|
var messageHandlers = {};
|
|
|
|
var CUSTOM_PROTOCOL_SCHEME = 'https';
|
|
var QUEUE_HAS_MESSAGE = '__wvjb_queue_message__';
|
|
|
|
var responseCallbacks = {};
|
|
var uniqueId = 1;
|
|
var dispatchMessagesWithTimeoutSafety = true;
|
|
|
|
function registerHandler(handlerName, handler) {
|
|
messageHandlers[handlerName] = handler;
|
|
}
|
|
|
|
function callHandler(handlerName, data, responseCallback) {
|
|
if (arguments.length == 2 && typeof data == 'function') {
|
|
responseCallback = data;
|
|
data = null;
|
|
}
|
|
_doSend({ handlerName:handlerName, data:data }, responseCallback);
|
|
}
|
|
function disableJavscriptAlertBoxSafetyTimeout() {
|
|
dispatchMessagesWithTimeoutSafety = false;
|
|
}
|
|
|
|
function _doSend(message, responseCallback) {
|
|
if (responseCallback) {
|
|
var callbackId = 'cb_'+(uniqueId++)+'_'+new Date().getTime();
|
|
responseCallbacks[callbackId] = responseCallback;
|
|
message['callbackId'] = callbackId;
|
|
}
|
|
sendMessageQueue.push(message);
|
|
messagingIframe.src = CUSTOM_PROTOCOL_SCHEME + '://' + QUEUE_HAS_MESSAGE;
|
|
}
|
|
|
|
function _fetchQueue() {
|
|
var messageQueueString = JSON.stringify(sendMessageQueue);
|
|
sendMessageQueue = [];
|
|
return messageQueueString;
|
|
}
|
|
|
|
function _dispatchMessageFromObjC(messageJSON) {
|
|
if (dispatchMessagesWithTimeoutSafety) {
|
|
setTimeout(_doDispatchMessageFromObjC);
|
|
} else {
|
|
_doDispatchMessageFromObjC();
|
|
}
|
|
|
|
function _doDispatchMessageFromObjC() {
|
|
var message = JSON.parse(messageJSON);
|
|
var messageHandler;
|
|
var responseCallback;
|
|
|
|
if (message.responseId) {
|
|
responseCallback = responseCallbacks[message.responseId];
|
|
if (!responseCallback) {
|
|
return;
|
|
}
|
|
responseCallback(message.responseData);
|
|
delete responseCallbacks[message.responseId];
|
|
} else {
|
|
if (message.callbackId) {
|
|
var callbackResponseId = message.callbackId;
|
|
responseCallback = function(responseData) {
|
|
_doSend({ handlerName:message.handlerName, responseId:callbackResponseId, responseData:responseData });
|
|
};
|
|
}
|
|
|
|
var handler = messageHandlers[message.handlerName];
|
|
if (!handler) {
|
|
console.log("WebViewJavascriptBridge: WARNING: no handler for message from ObjC:", message);
|
|
} else {
|
|
handler(message.data, responseCallback);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
function _handleMessageFromObjC(messageJSON) {
|
|
_dispatchMessageFromObjC(messageJSON);
|
|
}
|
|
|
|
messagingIframe = document.createElement('iframe');
|
|
messagingIframe.style.display = 'none';
|
|
messagingIframe.src = CUSTOM_PROTOCOL_SCHEME + '://' + QUEUE_HAS_MESSAGE;
|
|
document.documentElement.appendChild(messagingIframe);
|
|
|
|
registerHandler("_disableJavascriptAlertBoxSafetyTimeout", disableJavscriptAlertBoxSafetyTimeout);
|
|
|
|
setTimeout(_callWVJBCallbacks, 0);
|
|
function _callWVJBCallbacks() {
|
|
var callbacks = window.WVJBCallbacks;
|
|
delete window.WVJBCallbacks;
|
|
for (var i=0; i<callbacks.length; i++) {
|
|
callbacks[i](WebViewJavascriptBridge);
|
|
}
|
|
}
|
|
})();
|
|
); // END preprocessorJSCode
|
|
|
|
#undef __wvjb_js_func__
|
|
return preprocessorJSCode;
|
|
};
|
|
|