UNPKG

@oat-sa/tao-test-runner-qti

Version:
162 lines (153 loc) 6.6 kB
define(['lodash', 'util/capitalize', 'taoQtiTest/runner/helpers/map', 'taoQtiTest/runner/helpers/navigation'], function (_, capitalize, mapHelper, navigationHelper) { 'use strict'; _ = _ && Object.prototype.hasOwnProperty.call(_, 'default') ? _['default'] : _; capitalize = capitalize && Object.prototype.hasOwnProperty.call(capitalize, 'default') ? capitalize['default'] : capitalize; mapHelper = mapHelper && Object.prototype.hasOwnProperty.call(mapHelper, 'default') ? mapHelper['default'] : mapHelper; navigationHelper = navigationHelper && Object.prototype.hasOwnProperty.call(navigationHelper, 'default') ? navigationHelper['default'] : navigationHelper; /** * 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) 2019 (original work) Open Assessment Technologies SA ; */ /** * Returns the updated test context from an item in the given position. * * @param {Object} testContext * @param {Object} testMap * @param {Integer} position * @returns {Object} */ function buildTestContextFromPosition(testContext, testMap, position, attempt) { var updatedMap = mapHelper.updateItemStats(testMap, position), item = mapHelper.getItemAt(updatedMap, position), section = mapHelper.getItemSection(updatedMap, position), part = mapHelper.getItemPart(updatedMap, position); if (!item) { return false; } return getTestContext(testContext, testMap, item, section, part, position, attempt); } /** * Returns the updated test context from a jump table entry. * * @param {Object} testContext * @param {Object} testMap * @param {Object} jump * @param {String} jump.item * @param {String} jump.section * @param {String} jump.part * @param {Integer} jump.position * @returns {Object} */ function buildTestContextFromJump(testContext, testMap, jump, attempt) { var part = testMap.parts[jump.part], section = part.sections[jump.section], item = section.items[jump.item]; return getTestContext(testContext, testMap, item, section, part, jump.position, attempt); } /** * Returns the updated test context. * * @param {Object} testContext * @param {Object} testMap * @param {Object} item * @param {String} item.id * @param {Boolean} item.answered * @param {Integer} item.remainingAttempts * @param {Object} item.timeConstraint * @param {String[]} item.categories * @param {Object} section * @param {String} section.id * @param {String} section.label * @param {Object} section.timeConstraint * @param {Object} part * @param {String} part.id * @param {Boolean} part.isLinear * @param {Object} part.timeConstraint * @param {Integer} position * @returns {Object} the new test context * @private */ function getTestContext(testContext, testMap, item, section, part, position, attempt) { var isLeavingSection = section.id !== testContext.sectionId, isLeavingPart = part.id !== testContext.testPartId, newTestContext = _.defaults({ itemIdentifier: item.id, itemPosition: position, remainingAttempts: Math.max(-1, item.remainingAttempts - 1), sectionId: section.id, sectionTitle: section.label, testPartId: part.id, canMoveBackward: !part.isLinear && !navigationHelper.isFirst(testMap, item.id) }, testContext); if (attempt) { newTestContext.attempt = attempt + 1; } if (isLeavingSection) { newTestContext.numberRubrics = 0; newTestContext.rubrics = ''; } newTestContext.timeConstraints = _.reject(testContext.timeConstraints, function (constraint) { return constraint.qtiClassName === 'assessmentItemRef' || isLeavingSection && constraint.qtiClassName === 'assessmentSection' || isLeavingPart && constraint.qtiClassName === 'testPart'; }); if (item.timeConstraint) { newTestContext.timeConstraints.push(item.timeConstraint); } if (isLeavingSection && section.timeConstraint) { newTestContext.timeConstraints.push(section.timeConstraint); } if (isLeavingPart && part.timeConstraint) { newTestContext.timeConstraints.push(part.timeConstraint); } newTestContext.options = _.defaults(getOptionsFromCategories(item.categories || []), _.pick(testContext.options, ['allowComment', 'allowSkipping', 'exitButton', 'logoutButton'])); return newTestContext; } /** * Transforms the categories into context options. * * @param {String[]} categories - the list of categories * @returns {Object} the options object like <optionName : Boolean> * @private */ function getOptionsFromCategories(categories) { if (!_.isArray(categories) || !categories.length) { return {}; } return _.reduce(categories, function (acc, category) { var categoryName; if (_.isString(category) && !_.isEmpty(category)) { // transfrom the category name in an option name: // x-tao-option-review-screen to reviewScreen categoryName = category.replace('x-tao-option-', '').split(/[-_]+/g).map(function (name, index) { if (index === 0) { return name; } if (name.length) { return capitalize(name); } return ''; }).join(''); if (categoryName) { acc[categoryName] = true; } } return acc; }, {}); } var testContextBuilder = { buildTestContextFromPosition: buildTestContextFromPosition, buildTestContextFromJump: buildTestContextFromJump }; return testContextBuilder; });