/**
* @exports nolimitApiFactory
* @private
*/
var nolimitApiFactory = function(target, onload) {
var listeners = {};
var unhandledEvents = {};
var unhandledCalls = [];
var port;
function handleUnhandledCalls(port) {
while(unhandledCalls.length > 0) {
port.postMessage(unhandledCalls.shift());
}
}
function addMessageListener(gameWindow) {
gameWindow.addEventListener('message', function(e) {
if(e.ports && e.ports.length > 0) {
port = e.ports[0];
port.onmessage = onMessage;
handleUnhandledCalls(port);
}
});
gameWindow.trigger = trigger;
gameWindow.on = on;
onload();
}
if(target.nodeName === 'IFRAME') {
if (target.contentWindow && target.contentWindow.document && target.contentWindow.document.readyState === 'complete') {
addMessageListener(target.contentWindow);
} else {
target.addEventListener('load', function() {
addMessageListener(target.contentWindow);
});
}
} else {
addMessageListener(target);
}
function onMessage(e) {
trigger(e.data.method, e.data.params);
}
function sendMessage(method, data) {
var message = {
jsonrpc: '2.0',
method: method
};
if(data) {
message.params = data;
}
if(port) {
try {
port.postMessage(message);
} catch(ignored) {
port = undefined;
unhandledCalls.push(message);
}
} else {
unhandledCalls.push(message);
}
}
function registerEvents(events) {
sendMessage('register', events);
}
function trigger(event, data) {
if(listeners[event]) {
listeners[event].forEach(function(callback) {
callback(data);
});
} else {
unhandledEvents[name] = unhandledEvents[name] || [];
unhandledEvents[name].push(data);
}
}
function on(event, callback) {
listeners[event] = listeners[event] || [];
listeners[event].push(callback);
while(unhandledEvents[event] && unhandledEvents[event].length > 0) {
trigger(event, unhandledEvents[event].pop());
}
registerEvents([event]);
}
/**
* Connection to the game using MessageChannel
* @exports nolimitApi
*/
var nolimitApi = {
/**
* Add listener for event from the started game
*
* @function on
* @param {String} event name of the event
* @param {Function} callback callback for the event, see specific event documentation for any parameters
*
* @example
* api.on('deposit', function openDeposit () {
* showDeposit().then(function() {
* // ask the game to refresh balance from server
* api.call('refresh');
* });
* });
*/
on: on,
/**
* Call method in the open game
*
* @function call
* @param {String} method name of the method to call
* @param {Object} [data] optional data for the method called, if any
*
* @example
* // reload the game
* api.call('reload');
*/
call: sendMessage,
/**
* Triggers a named event
*
* @function trigger
* @param {String} event name of the event
* @param {Object} [data] optional data for the event, if any
*/
trigger: trigger
};
return nolimitApi;
};
module.exports = nolimitApiFactory;