diff --git a/h5p.classes.php b/h5p.classes.php index d42c0da..6e45feb 100644 --- a/h5p.classes.php +++ b/h5p.classes.php @@ -3483,6 +3483,10 @@ class H5PCore { 'connectionLost' => $this->h5pF->t('Connection lost. Results will be stored and sent when you regain connection.'), 'connectionReestablished' => $this->h5pF->t('Connection reestablished.'), 'resubmitScores' => $this->h5pF->t('Attempting to submit stored results.'), + 'offlineDialogHeader' => $this->h5pF->t('Your connection to the server was lost'), + 'offlineDialogBody' => $this->h5pF->t('We were unable to send information about your completion of this task. Please check your internet connection.'), + 'offlineDialogRetryMessage' => $this->h5pF->t('Retrying in :num....'), + 'offlineDialogRetryButtonLabel' => $this->h5pF->t('Retry now'), ); } } diff --git a/js/h5p.js b/js/h5p.js index d041d4c..cf1cac7 100644 --- a/js/h5p.js +++ b/js/h5p.js @@ -66,6 +66,21 @@ H5P.init = function (target) { H5P.$body = H5P.jQuery(document.body); } + H5P.offlineRequestQueue = new H5P.RequestQueue(); + // We could handle previously failed requests here, instead we throw them away + // TODO: Add dialog + H5P.offlineRequestQueue.clear(); + H5P.offlineRequestQueue.on('requestQueued', function () { + }); + + H5P.offlineRequestQueue.on('processingQueue', function () { + }); + + H5P.offlineRequestQueue.on('queueEmptied', function () { + }); + + + // Determine if we can use full screen if (H5P.fullscreenSupported === undefined) { /** @@ -214,9 +229,6 @@ H5P.init = function (target) { } }); - // Handle requests that failed while the user was offline - H5P.offlineRequestQueue.resumeQueue(); - // Listen for xAPI events. H5P.on(instance, 'xAPI', H5P.xAPICompletedListener); diff --git a/js/request-queue.js b/js/request-queue.js index e65f2fb..8bd9651 100644 --- a/js/request-queue.js +++ b/js/request-queue.js @@ -3,19 +3,18 @@ * * @type {RequestQueue} */ -H5P.RequestQueue = (function ($) { +H5P.RequestQueue = (function ($, EventDispatcher) { /** * A queue for requests, will be automatically processed when regaining connection * - * @param {string} itemName Name that requests will be stored as in local storage - * @param {string} eventName Name of event that will be triggered when a new item is added to the queue + * @param {boolean} [options.showToast] Disable showing toast when losing or regaining connection * @constructor */ - const RequestQueue = function (itemName, eventName) { + const RequestQueue = function (options) { + EventDispatcher.call(this); this.processingQueue = false; - this.itemName = itemName; - this.eventName = eventName; + this.showToast = options.showToast; // Initialize listener for when requests are added to queue window.addEventListener('offline', this.updateOnlineStatus.bind(this)); @@ -46,7 +45,7 @@ H5P.RequestQueue = (function ($) { window.localStorage.setItem(this.itemName, JSON.stringify(storedStatements)); - H5P.externalDispatcher.trigger(this.eventName); + this.trigger('requestQueued', storedStatements); return true; }; @@ -84,21 +83,23 @@ H5P.RequestQueue = (function ($) { /** * Start processing of requests queue + * + * @return {boolean} Returns false if it was not possible to resume processing queue */ RequestQueue.prototype.resumeQueue = function () { // Not supported if (!H5PIntegration || !window.navigator || !window.localStorage) { - return; + return false; } // Already processing if (this.processingQueue) { - return; + return false; } // Application is offline, re-send when we detect a connection if (!window.navigator.onLine) { - return; + return false; } // We're online, attempt to send queued requests @@ -110,7 +111,7 @@ H5P.RequestQueue = (function ($) { // No items left in queue if (!queueLength) { - return; + return true; } // Make sure requests are not changed while they're being handled @@ -118,6 +119,7 @@ H5P.RequestQueue = (function ($) { // Process queue in original order this.processQueue(queue); + return true }; /** @@ -130,6 +132,8 @@ H5P.RequestQueue = (function ($) { return; } + this.trigger('processingQueue'); + // Make sure the requests are processed in a FIFO order const request = queue.shift(); @@ -151,6 +155,11 @@ H5P.RequestQueue = (function ($) { } }; + /** + * An item in the queue was processed + * + * @param {Array} queue Queue that was processed + */ RequestQueue.prototype.onQueuedRequestProcessed = function (queue) { if (queue.length) { this.processQueue(queue); @@ -167,7 +176,11 @@ H5P.RequestQueue = (function ($) { const requestQueue = this.getStoredRequests(); if (requestQueue.length) { this.resumeQueue(); + return; } + + // Run empty queue callback + this.trigger('queueEmptied'); }; /** @@ -207,10 +220,10 @@ H5P.RequestQueue = (function ($) { this.resumeQueue(); } - this.displayToastMessage(message); + if (this.showToast) { + this.displayToastMessage(message); + } }; return RequestQueue; -})(H5P.jQuery); - -H5P.offlineRequestQueue = new H5P.RequestQueue('requestQueue', 'requestQueued'); +})(H5P.jQuery, H5P.EventDispatcher); \ No newline at end of file