/* jslint node: true */ 'use strict'; // ENiGMA½ const TextView = require('./text_view.js').TextView; const View = require('./view.js').View; const EditTextView = require('./edit_text_view.js').EditTextView; const ButtonView = require('./button_view.js').ButtonView; const VerticalMenuView = require('./vertical_menu_view.js').VerticalMenuView; const HorizontalMenuView = require('./horizontal_menu_view.js').HorizontalMenuView; const SpinnerMenuView = require('./spinner_menu_view.js').SpinnerMenuView; const ToggleMenuView = require('./toggle_menu_view.js').ToggleMenuView; const MaskEditTextView = require('./mask_edit_text_view.js').MaskEditTextView; const KeyEntryView = require('./key_entry_view.js'); const MultiLineEditTextView = require('./multi_line_edit_text_view.js').MultiLineEditTextView; const getPredefinedMCIValue = require('./predefined_mci.js').getPredefinedMCIValue; const ansi = require('./ansi_term.js'); // deps const assert = require('assert'); const _ = require('lodash'); exports.MCIViewFactory = MCIViewFactory; function MCIViewFactory(client) { this.client = client; } MCIViewFactory.UserViewCodes = [ 'TL', 'ET', 'ME', 'MT', 'PL', 'BT', 'VM', 'HM', 'SM', 'TM', 'KE', // // XY is a special MCI code that allows finding positions // and counts for key lookup, but does not explicitly // represent a visible View on it's own // 'XY', ]; MCIViewFactory.MovementCodes = [ 'CF', 'CB', 'CU', 'CD', ]; MCIViewFactory.prototype.createFromMCI = function(mci) { assert(mci.code); assert(mci.id > 0); assert(mci.position); var view; var options = { client : this.client, id : mci.id, ansiSGR : mci.SGR, ansiFocusSGR : mci.focusSGR, position : { row : mci.position[0], col : mci.position[1] }, }; // :TODO: These should use setPropertyValue()! function setOption(pos, name) { if(mci.args.length > pos && mci.args[pos].length > 0) { options[name] = mci.args[pos]; } } function setWidth(pos) { if(mci.args.length > pos && mci.args[pos].length > 0) { if(!_.isObject(options.dimens)) { options.dimens = {}; } options.dimens.width = parseInt(mci.args[pos], 10); } } function setFocusOption(pos, name) { if(mci.focusArgs && mci.focusArgs.length > pos && mci.focusArgs[pos].length > 0) { options[name] = mci.focusArgs[pos]; } } // // Note: Keep this in sync with UserViewCodes above! // switch(mci.code) { // Text Label (Text View) case 'TL' : setOption(0, 'textStyle'); setOption(1, 'justify'); setWidth(2); view = new TextView(options); break; // Edit Text case 'ET' : setWidth(0); setOption(1, 'textStyle'); setFocusOption(0, 'focusTextStyle'); view = new EditTextView(options); break; // Masked Edit Text case 'ME' : setOption(0, 'textStyle'); setFocusOption(0, 'focusTextStyle'); view = new MaskEditTextView(options); break; // Multi Line Edit Text case 'MT' : // :TODO: apply params view = new MultiLineEditTextView(options); break; // Pre-defined Label (Text View) // :TODO: Currently no real point of PL -- @method replaces this pretty much... probably remove case 'PL' : if(mci.args.length > 0) { options.text = getPredefinedMCIValue(this.client, mci.args[0]); if(options.text) { setOption(1, 'textStyle'); setOption(2, 'justify'); setWidth(3); view = new TextView(options); } } break; // Button case 'BT' : if(mci.args.length > 0) { options.dimens = { width : parseInt(mci.args[0], 10) }; } setOption(1, 'textStyle'); setOption(2, 'justify'); setFocusOption(0, 'focusTextStyle'); view = new ButtonView(options); break; // Vertial Menu case 'VM' : setOption(0, 'itemSpacing'); setOption(1, 'justify'); setOption(2, 'textStyle'); setFocusOption(0, 'focusTextStyle'); view = new VerticalMenuView(options); break; // Horizontal Menu case 'HM' : setOption(0, 'itemSpacing'); setOption(1, 'textStyle'); setFocusOption(0, 'focusTextStyle'); view = new HorizontalMenuView(options); break; case 'SM' : setOption(0, 'textStyle'); setOption(1, 'justify'); setFocusOption(0, 'focusTextStyle'); view = new SpinnerMenuView(options); break; case 'TM' : if(mci.args.length > 0) { var styleSG1 = { fg : parseInt(mci.args[0], 10) }; if(mci.args.length > 1) { styleSG1.bg = parseInt(mci.args[1], 10); } options.styleSG1 = ansi.getSGRFromGraphicRendition(styleSG1, true); } setFocusOption(0, 'focusTextStyle'); view = new ToggleMenuView(options); break; case 'KE' : view = new KeyEntryView(options); break; case 'XY' : view = new View(options); break; default : if(!MCIViewFactory.MovementCodes.includes(mci.code)) { options.text = getPredefinedMCIValue(this.client, mci.code); if(_.isString(options.text)) { setWidth(0); setOption(1, 'textStyle'); setOption(2, 'justify'); view = new TextView(options); } } break; } if(view) { view.mciCode = mci.code; } return view; };