@oat-sa/tao-test-runner-qti
Version:
TAO Test Runner QTI implementation
169 lines (157 loc) • 9.23 kB
JavaScript
define(['i18n', 'lodash', 'ui/component', 'ui/keyNavigation/navigator', 'ui/keyNavigation/navigableDomElement', 'handlebars', 'lib/handlebars/helpers'], function (__, _, component, keyNavigator, navigableDomElement, Handlebars, Helpers0) { 'use strict';
__ = __ && Object.prototype.hasOwnProperty.call(__, 'default') ? __['default'] : __;
_ = _ && Object.prototype.hasOwnProperty.call(_, 'default') ? _['default'] : _;
component = component && Object.prototype.hasOwnProperty.call(component, 'default') ? component['default'] : component;
keyNavigator = keyNavigator && Object.prototype.hasOwnProperty.call(keyNavigator, 'default') ? keyNavigator['default'] : keyNavigator;
navigableDomElement = navigableDomElement && Object.prototype.hasOwnProperty.call(navigableDomElement, 'default') ? navigableDomElement['default'] : navigableDomElement;
Handlebars = Handlebars && Object.prototype.hasOwnProperty.call(Handlebars, 'default') ? Handlebars['default'] : Handlebars;
Helpers0 = Helpers0 && Object.prototype.hasOwnProperty.call(Helpers0, 'default') ? Helpers0['default'] : Helpers0;
if (!Helpers0.__initialized) {
Helpers0(Handlebars);
Helpers0.__initialized = true;
}
var Template = Handlebars.template(function (Handlebars,depth0,helpers,partials,data) {
this.compilerInfo = [4,'>= 1.0.0'];
helpers = this.merge(helpers, Handlebars.helpers); data = data || {};
var buffer = "", stack1, helper, options, functionType="function", escapeExpression=this.escapeExpression, self=this, helperMissing=helpers.helperMissing;
function program1(depth0,data) {
var buffer = "", stack1, helper;
buffer += "\n <div class=\"shortcuts-group-wrapper\">\n <h3 class=\"shortcuts-group-title\">";
if (helper = helpers.label) { stack1 = helper.call(depth0, {hash:{},data:data}); }
else { helper = (depth0 && depth0.label); stack1 = typeof helper === functionType ? helper.call(depth0, {hash:{},data:data}) : helper; }
buffer += escapeExpression(stack1)
+ "</h3>\n <ul class=\"shortcuts-group-list\">\n ";
stack1 = helpers.each.call(depth0, (depth0 && depth0.shortcuts), {hash:{},inverse:self.noop,fn:self.program(2, program2, data),data:data});
if(stack1 || stack1 === 0) { buffer += stack1; }
buffer += "\n </ul>\n </div>\n ";
return buffer;
}
function program2(depth0,data) {
var buffer = "", stack1, helper;
buffer += "\n <li class=\"shortcut-item\">\n <span class=\"shortcut-item-shortcut\">\n <kbd>";
if (helper = helpers.shortcut) { stack1 = helper.call(depth0, {hash:{},data:data}); }
else { helper = (depth0 && depth0.shortcut); stack1 = typeof helper === functionType ? helper.call(depth0, {hash:{},data:data}) : helper; }
buffer += escapeExpression(stack1)
+ "</kbd>\n </span>\n <span class=\"shortcut-item-action\">\n ";
if (helper = helpers.label) { stack1 = helper.call(depth0, {hash:{},data:data}); }
else { helper = (depth0 && depth0.label); stack1 = typeof helper === functionType ? helper.call(depth0, {hash:{},data:data}) : helper; }
buffer += escapeExpression(stack1)
+ "\n </span>\n </li>\n ";
return buffer;
}
buffer += "<div class=\"shortcuts-list-wrapper\">\n <div class=\"shortcuts-list\" role=\"dialog\" aria-modal=\"true\" aria-labelledby=\"jumplinks/shortcuts-heading\"\n aria-describedby=\"jumplinks/shortcuts-description\">\n <h2 class=\"shortcuts-list-title\" id=\"jumplinks/shortcuts-heading\">\n "
+ escapeExpression((helper = helpers.__ || (depth0 && depth0.__),options={hash:{},data:data},helper ? helper.call(depth0, "Keyboard Navigation", options) : helperMissing.call(depth0, "__", "Keyboard Navigation", options)))
+ "\n </h2>\n <div id=\"jumplinks/shortcuts-description\">\n <p class=\"shortcuts-list-description\">\n "
+ escapeExpression((helper = helpers.__ || (depth0 && depth0.__),options={hash:{},data:data},helper ? helper.call(depth0, "Keyboard shortcuts for the Accessibility Tools are available to the Test-taker.", options) : helperMissing.call(depth0, "__", "Keyboard shortcuts for the Accessibility Tools are available to the Test-taker.", options)))
+ "\n </p>\n <p class=\"shortcuts-list-description\">\n "
+ escapeExpression((helper = helpers.__ || (depth0 && depth0.__),options={hash:{},data:data},helper ? helper.call(depth0, "You can magnify the content by up to 200%. Check your browser settings to find out how to do it.", options) : helperMissing.call(depth0, "__", "You can magnify the content by up to 200%. Check your browser settings to find out how to do it.", options)))
+ "\n </p>\n </div>\n <button aria-label=\"Close dialog\" class=\"btn-close small\" data-control=\"close-btn\" type=\"button\">\n <span class=\"icon-close\"></span>\n </button>\n ";
stack1 = helpers.each.call(depth0, (depth0 && depth0.shortcutsGroups), {hash:{},inverse:self.noop,fn:self.program(1, program1, data),data:data});
if(stack1 || stack1 === 0) { buffer += stack1; }
buffer += "\n </div>\n</div>\n";
return buffer;
});
function shortcutsTpl(data, options, asString) {
var html = Template(data, options);
return (asString || true) ? html : $(html);
}
/**
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; under version 2
* of the License (non-upgradable).
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*
* Copyright (c) 2020 (original work) Open Assessment Technologies SA ;
*/
/**
* Default config values, see below.
*/
const defaults = {
shortcutsGroups: [{
id: 'navigation-shortcuts',
label: __('Navigation shortcuts'),
shortcuts: [{
id: 'next',
shortcut: 'ALT + Shift + N',
label: __('Go to the next question')
}, {
id: 'previous',
shortcut: 'ALT + Shift + P',
label: __('Go to the previous question')
}, {
id: 'current',
shortcut: 'ALT + Shift + Q',
label: __('Go to the current question')
}, {
id: 'top',
shortcut: 'ALT + Shift + T',
label: __('Go to the top of the page')
}]
}]
};
/**
* Creates and initialize the shortcuts component.
* Please not the component IS NOT rendered.
* You'll have to render it by yourself.
*
* @param {Object} config
* @returns {shortcutsBox} the component, initialized and rendered
*/
function shortcutsBoxFactory(config) {
const ESK_KEY_CODE = 27;
const shortcutsBox = component({}, defaults).on('render', function () {
const $element = this.getElement();
const $closeBtn = $element.find('.btn-close');
const $keyNavigationItems = this.getElement().find('.shortcuts-list, .btn-close');
$closeBtn.on('click', () => this.trigger('close'));
// handle overlay click
$element.on('click', e => {
if ($element.is(e.target)) {
this.trigger('close');
}
});
$element.on('keyup', e => {
if (e.keyCode === ESK_KEY_CODE) {
this.trigger('close');
}
});
this.navigator = keyNavigator({
elements: navigableDomElement.createFromDoms($keyNavigationItems),
propagateTab: false
})
// keep cursor at close button
.on('tab', function () {
this.setCursorAt(1);
}).on('shift+tab', function () {
this.setCursorAt(1);
})
// prevent focus move from shortcuts modal
.on('blur', () => {
_.defer(() => {
if (!this.navigator.isFocused()) {
this.navigator.focus();
}
});
}).on('activate', function (cursor) {
cursor.navigable.getElement().click();
});
this.navigator.first();
}).on('destroy', function () {
this.navigator.destroy();
this.getElement().remove();
});
shortcutsBox.setTemplate(shortcutsTpl);
shortcutsBox.init(config);
return shortcutsBox;
}
return shortcutsBoxFactory;
});