- /**
- * The ACE Editor TemplateProcessor base
- *
- * @module aui-ace-editor
- * @submodule aui-ace-autocomplete-templateprocessor
- */
-
- var Lang = A.Lang,
- AArray = A.Array,
- AObject = A.Object,
- Base = A.AceEditor.AutoCompleteBase,
-
- MATCH_DIRECTIVES = 0,
- MATCH_VARIABLES = 1,
-
- TOKEN_PUNCTUATOR_DOT = 1,
- TOKEN_UNRECOGNIZED = -1,
- TOKEN_VARIABLE = 0,
-
- /**
- * A base class for TemplateProcessor.
- *
- * @class A.AceEditor.TemplateProcessor
- * @extends Base
- * @param {Object} config Object literal specifying widget configuration
- * properties.
- * @constructor
- */
- TemplateProcessor = A.Base.create('aui-ace-autocomplete-templateprocessor', A.Base, [
- ], {
-
- /**
- * Accepts match and depending on its type processes directives or
- * variables. In case of success, calls the provided success callback,
- * or the error callback otherwise.
- *
- * @method getResults
- * @param {Object} match The provided match. It should contain at least
- * type and content properties
- * @param {Function} callbackSuccess The function to be called in case
- * of success
- * @param {Function} callbackError The function to be called in case of
- * error
- */
- getResults: function(match, callbackSuccess, callbackError) {
- var instance = this,
- content,
- host,
- matchDirectives,
- matches,
- type;
-
- type = match.type;
-
- if (type === MATCH_DIRECTIVES) {
- matchDirectives = instance.get('directives');
-
- content = match.content.toLowerCase();
-
- if (content.length) {
- host = instance.get('host');
-
- matchDirectives = host._filterResults(content, matchDirectives);
- }
-
- callbackSuccess(matchDirectives);
- }
- else if (type === MATCH_VARIABLES) {
- matches = instance._getVariableMatches(match.content);
-
- callbackSuccess(matches);
- }
- else {
- callbackError();
- }
- },
-
- /**
- * Formats the selected suggestion depending on the match type and
- * currently selected editor mode. The match type can be one of:
- * MATCH_DIRECTOVES or MATCH_VARIABLES. The selected editor mode can be
- * one of the following: INSERT or OVERWRITE. See {{#crossLink
- * "AceEditor.AutoCompleteBase/fillMode:attribute"}}{{/crossLink}}
- *
- * @method getSuggestion
- * @param {Object} match The provided match. It should contain at least
- * type and content properties
- * @param {String} selectedSuggestion The selected suggestion from the
- * list with suggestions
- * @return {String} The final suggestion which should be inserted to the
- * editor
- */
- getSuggestion: function(match, selectedSuggestion) {
- var instance = this,
- fillMode,
- lastEntry,
- result,
- type,
- variables;
-
- result = selectedSuggestion || '';
-
- if (selectedSuggestion) {
- fillMode = instance.get('host').get('fillMode');
-
- type = match.type;
-
- if (fillMode === Base.FILL_MODE_INSERT) {
- if (type === MATCH_DIRECTIVES) {
- if (match.content && selectedSuggestion.indexOf(match.content) === 0) {
- result = selectedSuggestion.substring(match.content.length);
- }
- }
- else if (type === MATCH_VARIABLES) {
- variables = match.content.split('.');
-
- lastEntry = variables[variables.length - 1];
-
- if (lastEntry && selectedSuggestion.indexOf(lastEntry) === 0) {
- result = selectedSuggestion.substring(lastEntry.length);
- }
- }
- }
- else if (type === MATCH_VARIABLES) {
- variables = match.content.split('.');
-
- variables[variables.length - 1] = selectedSuggestion;
-
- result = variables.join('.');
- }
- }
-
- return result;
- },
-
- /**
- * Checks if the the provided index is the last token in the list of
- * tokens.
- *
- * @method _isLastToken
- * @param {Number} index The index which should be checked
- * @param {Array} tokens The array with tokens
- * @protected
- * @return {Boolean} True if the provided index is the last token in the
- * list
- */
- _isLastToken: function(index, tokens) {
- return index === tokens.length - 1;
- },
-
- /**
- * Retrieves the type of a token. It can be one of these:
- * TOKEN_PUNCTUATOR_DOT = 1
- * TOKEN_UNRECOGNIZED = -1
- * TOKEN_VARIABLE = 0
- *
- * @method _getTokenType
- * @param {Number} token The type of the token
- * @protected
- * @return {Number} The token type
- */
- _getTokenType: function(token) {
- var tokenType = TOKEN_UNRECOGNIZED;
-
- if (Lang.isString(token)) {
- if (token.length) {
- tokenType = TOKEN_VARIABLE;
- }
- else {
- tokenType = TOKEN_PUNCTUATOR_DOT;
- }
- }
-
- return tokenType;
- },
-
- /**
- * Scans the content and extracts variables.
- *
- * @method _getVariableMatches
- * @param {String} content The content from which variable matches will
- * be extracted
- * @protected
- * @return {Array} List with variable matches
- */
- _getVariableMatches: function(content) {
- var instance = this,
- curVariableData,
- data,
- host,
- i,
- isLastToken,
- lastEntry,
- leftPartheseIndex,
- matches,
- results,
- resultsData,
- token,
- tokens,
- tokenType,
- variableData,
- variableType;
-
- results = [];
-
- data = instance.get('variables');
-
- resultsData = {};
-
- curVariableData = data.variables;
-
- if (content) {
- tokens = content.split('.');
-
- lastEntry = tokens[tokens.length - 1];
-
- for (i = 0; i < tokens.length; i++) {
- token = tokens[i];
-
- tokenType = instance._getTokenType(token);
-
- if (tokenType === TOKEN_PUNCTUATOR_DOT) {
- if (i === 0) {
- curVariableData = {};
- }
- else {
- resultsData = curVariableData;
- }
- }
- else if (tokenType === TOKEN_VARIABLE) {
- isLastToken = instance._isLastToken(i, tokens);
-
- if (isLastToken) {
- resultsData = curVariableData;
-
- break;
- }
-
- leftPartheseIndex = token.indexOf('(');
-
- if (leftPartheseIndex !== -1) {
- token = token.substring(0, leftPartheseIndex);
- }
-
- variableData = curVariableData[token];
-
- if (variableData) {
- if (i === 0) {
- variableType = variableData.type;
- }
- else {
- variableType = variableData.returnType;
- }
-
- curVariableData = data.types[variableType] || {};
- }
- else if (isLastToken) {
- resultsData = curVariableData;
-
- break;
- }
- else {
- resultsData = {};
-
- break;
- }
- }
- }
- }
- else {
- resultsData = data.variables;
- }
-
- results = AObject.keys(resultsData);
-
- matches = results.sort();
-
- if (lastEntry) {
- host = instance.get('host');
-
- matches = host._filterResults(lastEntry, matches);
- }
-
- if (matches.length) {
- matches = AArray.map(
- matches,
- function(item) {
- var args,
- data;
-
- data = resultsData[item];
-
- if (data.type === 'Method') {
- args = AArray.map(
- data.argumentTypes,
- function(item) {
- var parts = item.split('.');
-
- return parts[parts.length - 1];
- }
- );
-
- return item + '(' + args.join(', ') + ')';
- }
- else {
- return item;
- }
- }
- );
- }
-
- return matches;
- },
-
- /**
- * Normalizes a regualr expression value. If the value is String, it
- * will be converted to an RegExp.
- *
- * @method _setRegexValue
- * @param {String|RegExp} value The provided regualr expression value
- * @protected
- * @return {RegExp} The final instance of RegExp object
- */
- _setRegexValue: function(value) {
- var result = A.AttributeCore.INVALID_VALUE;
-
- if (Lang.isString(value)) {
- result = new RegExp(value);
- }
- else if (value instanceof RegExp) {
- result = value;
- }
-
- return result;
- }
- }, {
-
- /**
- * Static property which provides a string to identify the class.
- *
- * @property NAME
- * @type String
- * @static
- */
- NAME: 'aui-ace-autocomplete-templateprocessor',
-
- /**
- * Static property provides a string to identify the namespace.
- *
- * @property NS
- * @type String
- * @static
- */
- NS: 'aui-ace-autocomplete-templateprocessor',
-
- /**
- * Static property used to define the default attribute
- * configuration for the TemplateProcessor.
- *
- * @property ATTRS
- * @type Object
- * @static
- */
- ATTRS: {
-
- /**
- * Contains an array of all possible directives for the
- * corresponding language.
- *
- * @attribute directives
- * @type Array
- */
- directives: {
- validator: Lang.isArray
- },
-
- /**
- * The Editor in which the current instance is plugged.
- *
- * @attribute host
- * @type Object
- */
- host: {
- validator: Lang.isObject
- },
-
- /**
- * Contains the supported variables for the corresponding language.
- *
- * @attribute variables
- * @type Object
- */
- variables: {
- validator: Lang.isObject
- }
- }
- });
-
- A.AceEditor.TemplateProcessor = TemplateProcessor;
-
-