Proyectos de Subversion Moodle

Rev

Autoría | Ultima modificación | Ver Log |

{"version":3,"file":"competencyruleconfig.min.js","sources":["../src/competencyruleconfig.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle.  If not, see <http://www.gnu.org/licenses/>.\n\n/**\n * Competency rule config.\n *\n * @module     tool_lp/competencyruleconfig\n * @copyright  2015 Frédéric Massart - FMCorz.net\n * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\n\ndefine(['jquery',\n        'core/notification',\n        'core/templates',\n        'tool_lp/dialogue',\n        'tool_lp/competency_outcomes',\n        'core/str'],\n        function($, Notification, Templates, Dialogue, Outcomes, Str) {\n\n    /**\n     * Competency rule class.\n     *\n     * When implementing this you should attach a listener to the event 'save'\n     * on the instance. E.g.\n     *\n     * var config = new RuleConfig(tree, modules);\n     * config.on('save', function(e, config) { ... });\n     *\n     * @param {competencytree} tree The competency tree.\n     * @param {Array} rulesModules The modules containing the rules: [{ typeName: { amd: amdModule, name: ruleName }}].\n     */\n    var RuleConfig = function(tree, rulesModules) {\n        this._eventNode = $('<div></div>');\n        this._tree = tree;\n        this._rulesModules = rulesModules;\n        this._setUp();\n    };\n\n    /** @property {Object} The current competency. */\n    RuleConfig.prototype._competency = null;\n    /** @property {Node} The node we attach the events to. */\n    RuleConfig.prototype._eventNode = null;\n    /** @property {Array} Outcomes options. */\n    RuleConfig.prototype._outcomesOption = null;\n    /** @property {Dialogue} The dialogue. */\n    RuleConfig.prototype._popup = null;\n    /** @property {Promise} Resolved when the module is ready. */\n    RuleConfig.prototype._ready = null;\n    /** @property {Array} The rules. */\n    RuleConfig.prototype._rules = null;\n    /** @property {Array} The rules modules. */\n    RuleConfig.prototype._rulesModules = null;\n    /** @property {competencytree} The competency tree. */\n    RuleConfig.prototype._tree = null;\n\n    /**\n     * After change.\n     *\n     * Triggered when a change occured.\n     *\n     * @method _afterChange\n     * @protected\n     */\n    RuleConfig.prototype._afterChange = function() {\n        if (!this._isValid()) {\n            this._find('[data-action=\"save\"]').prop('disabled', true);\n        } else {\n            this._find('[data-action=\"save\"]').prop('disabled', false);\n        }\n    };\n\n    /**\n     * After change in rule's config.\n     *\n     * Triggered when a change occured in a specific rule config.\n     *\n     * @method _afterRuleConfigChange\n     * @protected\n     * @param {Event} e\n     * @param {Rule} rule\n     */\n    RuleConfig.prototype._afterRuleConfigChange = function(e, rule) {\n        if (rule != this._getRule()) {\n            // This rule is not the current one any more, we can ignore.\n            return;\n        }\n        this._afterChange();\n    };\n\n    /**\n     * After render hook.\n     *\n     * @method _afterRender\n     * @protected\n     */\n    RuleConfig.prototype._afterRender = function() {\n        var self = this;\n\n        self._find('[name=\"outcome\"]').on('change', function() {\n            self._switchedOutcome();\n        }).trigger('change');\n\n        self._find('[name=\"rule\"]').on('change', function() {\n            self._switchedRule();\n        }).trigger('change');\n\n        self._find('[data-action=\"save\"]').on('click', function() {\n            self._trigger('save', self._getConfig());\n            self.close();\n        });\n\n        self._find('[data-action=\"cancel\"]').on('click', function() {\n            self.close();\n        });\n    };\n\n    /**\n     * Whether the current competency can be configured.\n     *\n     * @return {Boolean}\n     * @method canBeConfigured\n     */\n    RuleConfig.prototype.canBeConfigured = function() {\n        var can = false;\n        $.each(this._rules, function(index, rule) {\n            if (rule.canConfig()) {\n                can = true;\n                return;\n            }\n        });\n        return can;\n    };\n\n    /**\n     * Close the dialogue.\n     *\n     * @method close\n     */\n    RuleConfig.prototype.close = function() {\n        this._popup.close();\n        this._popup = null;\n    };\n\n    /**\n     * Opens the picker.\n     *\n     * @method display\n     * @returns {Promise}\n     */\n    RuleConfig.prototype.display = function() {\n        var self = this;\n        if (!self._competency) {\n            return false;\n        }\n        return $.when(Str.get_string('competencyrule', 'tool_lp'), self._render())\n        .then(function(title, render) {\n            self._popup = new Dialogue(\n                title,\n                render[0],\n                self._afterRender.bind(self),\n                null,\n                false,\n                '515px'\n            );\n            return;\n        }).fail(Notification.exception);\n    };\n\n    /**\n     * Find a node in the dialogue.\n     *\n     * @param {String} selector\n     * @return {JQuery}\n     * @method _find\n     * @protected\n     */\n    RuleConfig.prototype._find = function(selector) {\n        return $(this._popup.getContent()).find(selector);\n    };\n\n    /**\n     * Get the applicable outcome options.\n     *\n     * @return {Array}\n     * @method _getApplicableOutcomesOptions\n     * @protected\n     */\n    RuleConfig.prototype._getApplicableOutcomesOptions = function() {\n        var self = this,\n            options = [];\n\n        $.each(self._outcomesOption, function(index, outcome) {\n            options.push({\n                code: outcome.code,\n                name: outcome.name,\n                selected: (outcome.code == self._competency.ruleoutcome) ? true : false,\n            });\n        });\n\n        return options;\n    };\n\n    /**\n     * Get the applicable rules options.\n     *\n     * @return {Array}\n     * @method _getApplicableRulesOptions\n     * @protected\n     */\n    RuleConfig.prototype._getApplicableRulesOptions = function() {\n        var self = this,\n            options = [];\n\n        $.each(self._rules, function(index, rule) {\n            if (!rule.canConfig()) {\n                return;\n            }\n            options.push({\n                name: self._getRuleName(rule.getType()),\n                type: rule.getType(),\n                selected: (rule.getType() == self._competency.ruletype) ? true : false,\n            });\n        });\n\n        return options;\n    };\n\n    /**\n     * Get the full config for the competency.\n     *\n     * @return {Object} Contains rule, ruleoutcome and ruleconfig.\n     * @method _getConfig\n     * @protected\n     */\n    RuleConfig.prototype._getConfig = function() {\n        var rule = this._getRule();\n        return {\n            ruletype: rule ? rule.getType() : null,\n            ruleconfig: rule ? rule.getConfig() : null,\n            ruleoutcome: this._getOutcome()\n        };\n    };\n\n    /**\n     * Get the selected outcome code.\n     *\n     * @return {String}\n     * @method _getOutcome\n     * @protected\n     */\n    RuleConfig.prototype._getOutcome = function() {\n        return this._find('[name=\"outcome\"]').val();\n    };\n\n    /**\n     * Get the selected rule.\n     *\n     * @return {null|Rule}\n     * @method _getRule\n     * @protected\n     */\n    RuleConfig.prototype._getRule = function() {\n        var result,\n            type = this._find('[name=\"rule\"]').val();\n\n        $.each(this._rules, function(index, rule) {\n            if (rule.getType() == type) {\n                result = rule;\n                return;\n            }\n        });\n\n        return result;\n    };\n\n    /**\n     * Return the name of a rule.\n     *\n     * @param  {String} type The type of a rule.\n     * @return {String}\n     * @method _getRuleName\n     * @protected\n     */\n    RuleConfig.prototype._getRuleName = function(type) {\n        var self = this,\n            name;\n        $.each(self._rulesModules, function(index, modInfo) {\n            if (modInfo.type == type) {\n                name = modInfo.name;\n                return;\n            }\n        });\n        return name;\n    };\n\n    /**\n     * Initialise the outcomes.\n     *\n     * @return {Promise}\n     * @method _initOutcomes\n     * @protected\n     */\n    RuleConfig.prototype._initOutcomes = function() {\n        var self = this;\n        return Outcomes.getAll().then(function(outcomes) {\n            self._outcomesOption = outcomes;\n            return;\n        });\n    };\n\n    /**\n     * Initialise the rules.\n     *\n     * @return {Promise}\n     * @method _initRules\n     * @protected\n     */\n    RuleConfig.prototype._initRules = function() {\n        var self = this,\n            promises = [];\n        $.each(self._rules, function(index, rule) {\n            var promise = rule.init().then(function() {\n                rule.setTargetCompetency(self._competency);\n                rule.on('change', self._afterRuleConfigChange.bind(self));\n                return;\n            }, function() {\n                // Upon failure remove the rule, and resolve the promise.\n                self._rules.splice(index, 1);\n                return $.when();\n            });\n            promises.push(promise);\n        });\n\n        return $.when.apply($.when, promises);\n    };\n\n    /**\n     * Whether or not the current config is valid.\n     *\n     * @return {Boolean}\n     * @method _isValid\n     * @protected\n     */\n    RuleConfig.prototype._isValid = function() {\n        var outcome = this._getOutcome(),\n            rule = this._getRule();\n\n        if (outcome == Outcomes.NONE) {\n            return true;\n        } else if (!rule) {\n            return false;\n        }\n\n        return rule.isValid();\n    };\n\n    /**\n     * Register an event listener.\n     *\n     * @param {String} type The event type.\n     * @param {Function} handler The event listener.\n     * @method on\n     */\n    RuleConfig.prototype.on = function(type, handler) {\n        this._eventNode.on(type, handler);\n    };\n\n    /**\n     * Hook to executed before render.\n     *\n     * @method _preRender\n     * @protected\n     * @return {Promise}\n     */\n    RuleConfig.prototype._preRender = function() {\n        // We need to have all the information about the rule plugins first.\n        return this.ready();\n    };\n\n    /**\n     * Returns a promise that is resolved when the module is ready.\n     *\n     * @return {Promise}\n     * @method ready\n     * @protected\n     */\n    RuleConfig.prototype.ready = function() {\n        return this._ready.promise();\n    };\n\n    /**\n     * Render the dialogue.\n     *\n     * @method _render\n     * @protected\n     * @return {Promise}\n     */\n    RuleConfig.prototype._render = function() {\n        var self = this;\n        return this._preRender().then(function() {\n            var config;\n\n            if (!self.canBeConfigured()) {\n                config = false;\n            } else {\n                config = {};\n                config.outcomes = self._getApplicableOutcomesOptions();\n                config.rules = self._getApplicableRulesOptions();\n            }\n\n            var context = {\n                competencyshortname: self._competency.shortname,\n                config: config\n            };\n\n            return Templates.render('tool_lp/competency_rule_config', context);\n        });\n    };\n\n    /**\n     * Set the target competency.\n     *\n     * @param {Number} competencyId The target competency Id.\n     * @method setTargetCompetencyId\n     */\n    RuleConfig.prototype.setTargetCompetencyId = function(competencyId) {\n        var self = this;\n        self._competency = self._tree.getCompetency(competencyId);\n        $.each(self._rules, function(index, rule) {\n            rule.setTargetCompetency(self._competency);\n        });\n    };\n\n    /**\n     * Set up the instance.\n     *\n     * @method _setUp\n     * @protected\n     */\n    RuleConfig.prototype._setUp = function() {\n        var self = this,\n            promises = [],\n            modules = [];\n\n        self._ready = $.Deferred();\n        self._rules = [];\n\n        $.each(self._rulesModules, function(index, rule) {\n            modules.push(rule.amd);\n        });\n\n        // Load all the modules.\n        require(modules, function() {\n            $.each(arguments, function(index, Module) {\n                // Instantiate the rule and listen to it.\n                var rule = new Module(self._tree);\n                self._rules.push(rule);\n            });\n\n            // Load all the option values.\n            promises.push(self._initRules());\n            promises.push(self._initOutcomes());\n\n            // Ready when everything is done.\n            $.when.apply($.when, promises).always(function() {\n                self._ready.resolve();\n            });\n        });\n    };\n\n    /**\n     * Called when the user switches outcome.\n     *\n     * @method _switchedOutcome\n     * @protected\n     */\n    RuleConfig.prototype._switchedOutcome = function() {\n        var self = this,\n            type = self._getOutcome();\n\n        if (type == Outcomes.NONE) {\n            // Reset to defaults.\n            self._find('[data-region=\"rule-type\"]').hide()\n                .find('[name=\"rule\"]').val(-1);\n            self._find('[data-region=\"rule-config\"]').empty().hide();\n            self._afterChange();\n            return;\n        }\n\n        self._find('[data-region=\"rule-type\"]').show();\n        self._find('[data-region=\"rule-config\"]').show();\n        self._afterChange();\n    };\n\n    /**\n     * Called when the user switches rule.\n     *\n     * @method _switchedRule\n     * @protected\n     */\n    RuleConfig.prototype._switchedRule = function() {\n        var self = this,\n            container = self._find('[data-region=\"rule-config\"]'),\n            rule = self._getRule();\n\n        if (!rule) {\n            container.empty().hide();\n            self._afterChange();\n            return;\n        }\n        rule.injectTemplate(container).then(function() {\n            container.show();\n            return;\n        }).always(function() {\n            self._afterChange();\n        }).catch(function() {\n            container.empty().hide();\n        });\n    };\n\n    /**\n     * Trigger an event.\n     *\n     * @param {String} type The type of event.\n     * @param {Object} data The data to pass to the listeners.\n     * @method _trigger\n     * @protected\n     */\n    RuleConfig.prototype._trigger = function(type, data) {\n        this._eventNode.trigger(type, [data]);\n    };\n\n    return /** @alias module:tool_lp/competencyruleconfig */ RuleConfig;\n\n});\n"],"names":["define","$","Notification","Templates","Dialogue","Outcomes","Str","RuleConfig","tree","rulesModules","_eventNode","_tree","_rulesModules","_setUp","prototype","_competency","_outcomesOption","_popup","_ready","_rules","_afterChange","this","_isValid","_find","prop","_afterRuleConfigChange","e","rule","_getRule","_afterRender","self","on","_switchedOutcome","trigger","_switchedRule","_trigger","_getConfig","close","canBeConfigured","can","each","index","canConfig","display","when","get_string","_render","then","title","render","bind","fail","exception","selector","getContent","find","_getApplicableOutcomesOptions","options","outcome","push","code","name","selected","ruleoutcome","_getApplicableRulesOptions","_getRuleName","getType","type","ruletype","ruleconfig","getConfig","_getOutcome","val","result","modInfo","_initOutcomes","getAll","outcomes","_initRules","promises","promise","init","setTargetCompetency","splice","apply","NONE","isValid","handler","_preRender","ready","config","rules","context","competencyshortname","shortname","setTargetCompetencyId","competencyId","getCompetency","modules","Deferred","amd","require","arguments","Module","always","resolve","hide","empty","show","container","injectTemplate","catch","data"],"mappings":"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"}