mirror of
https://gerrit.wikimedia.org/r/mediawiki/extensions/TemplateData
synced 2024-11-12 09:24:17 +00:00
df59f0179a
Change the ui/data behavior to work with oojs and event emitters, and replace the gui from jquery ui to oojs-ui. Changes made: * Recreate the templatedata editor with oojs and ooui. * Create a standalone templatedata model with internal validation. * Allow the user to insert language-specific strings: * Allow adding arbitrary languages and values * Normalize output between language object and 'simple' string * Add new language code by searching for its name or code * Import parameters from template code * If the template is in subpage and there is no code in the current page, the code will request the contents of the parent page. Change-Id: I985ea03dfee58984ec22ec9a157a00968bfca878
824 lines
24 KiB
JavaScript
824 lines
24 KiB
JavaScript
( function ( mw ) {
|
|
/**
|
|
* TemplateData Dialog
|
|
* @param {Object} config Dialog configuration object
|
|
*/
|
|
TemplateDataDialog = function TemplateDataDialog( config ) {
|
|
// Parent constructor
|
|
TemplateDataDialog.super.call( this, config );
|
|
|
|
this.model = null;
|
|
this.language = null;
|
|
this.availableLanguages = [];
|
|
this.selectedParamKey = '';
|
|
this.propInputs = {};
|
|
this.propFieldLayout = {};
|
|
|
|
// Initialize
|
|
this.$element.addClass( 'tdg-TemplateDataDialog' );
|
|
};
|
|
|
|
OO.inheritClass( TemplateDataDialog, OO.ui.ProcessDialog );
|
|
|
|
/* Static properties */
|
|
TemplateDataDialog.static.name = 'TemplateDataDialog';
|
|
TemplateDataDialog.static.title = mw.msg( 'templatedata-modal-title' );
|
|
TemplateDataDialog.static.size = 'large';
|
|
TemplateDataDialog.static.actions = [
|
|
{
|
|
action: 'apply',
|
|
label: mw.msg( 'templatedata-modal-button-apply' ),
|
|
flags: [ 'primary', 'constructive' ],
|
|
modes: 'list'
|
|
},
|
|
{
|
|
action: 'add',
|
|
label: mw.msg( 'templatedata-modal-button-addparam' ),
|
|
flags: [ 'constructive' ],
|
|
modes: 'list'
|
|
},
|
|
{
|
|
action: 'delete',
|
|
label: mw.msg( 'templatedata-modal-button-delparam' ),
|
|
modes: 'edit',
|
|
flags: 'destructive'
|
|
},
|
|
{
|
|
label: mw.msg( 'templatedata-modal-button-cancel' ),
|
|
flags: 'safe',
|
|
modes: [ 'list', 'error' ]
|
|
},
|
|
{
|
|
action: 'back',
|
|
label: mw.msg( 'templatedata-modal-button-back' ),
|
|
flags: 'safe',
|
|
modes: [ 'edit', 'language', 'add' ]
|
|
}
|
|
];
|
|
|
|
/**
|
|
* @inheritDoc
|
|
*/
|
|
TemplateDataDialog.prototype.initialize = function () {
|
|
var templateParamsFieldset, languageFieldset,
|
|
addParamFieldlayout, languageFieldLayout;
|
|
|
|
// Parent method
|
|
TemplateDataDialog.super.prototype.initialize.call( this );
|
|
|
|
this.$spinner = this.$( '<div>' ).addClass( 'tdg-spinner' ).text( 'working...' );
|
|
this.$body.append( this.$spinner );
|
|
|
|
this.noticeLabel = new OO.ui.LabelWidget( { $: this.$ } );
|
|
this.noticeLabel.$element.hide();
|
|
|
|
this.panels = new OO.ui.StackLayout( { $: this.$, continuous: false } );
|
|
|
|
this.listParamsPanel = new OO.ui.PanelLayout( {
|
|
$: this.$,
|
|
scrollable: true
|
|
} );
|
|
this.editParamPanel = new OO.ui.PanelLayout( {
|
|
$: this.$
|
|
} );
|
|
this.languagePanel = new OO.ui.PanelLayout( {
|
|
$: this.$
|
|
} );
|
|
this.addParamPanel = new OO.ui.PanelLayout( {
|
|
$: this.$
|
|
} );
|
|
|
|
// Language panel
|
|
this.newLanguageSearchWidget = new TemplateDataLanguageSearchWidget( {
|
|
$: this.$
|
|
} );
|
|
|
|
// Add parameter panel
|
|
this.newParamInput = new OO.ui.TextInputWidget( {
|
|
$: this.$,
|
|
placeholder: mw.msg( 'templatedata-modal-placeholder-paramkey' )
|
|
} );
|
|
this.addParamButton = new OO.ui.ButtonWidget( {
|
|
$: this.$,
|
|
label: mw.msg( 'templatedata-modal-button-addparam' )
|
|
} );
|
|
addParamFieldlayout = new OO.ui.FieldsetLayout( {
|
|
$: this.$,
|
|
label: mw.msg( 'templatedata-modal-title-addparam' ),
|
|
items: [ this.newParamInput, this.addParamButton ]
|
|
} );
|
|
|
|
// Param list panel (main)
|
|
this.languageDropdownWidget = new OO.ui.DropdownWidget( { $: this.$ } );
|
|
this.languagePanelButton = new OO.ui.ButtonWidget( {
|
|
$: this.$,
|
|
label: mw.msg( 'templatedata-modal-button-add-language' )
|
|
} );
|
|
languageFieldLayout = new OO.ui.FieldLayout( this.languageDropdownWidget, {
|
|
$: this.$,
|
|
align: 'left',
|
|
label: mw.msg( 'templatedata-modal-title-language' )
|
|
} );
|
|
languageFieldset = new OO.ui.FieldsetLayout( {
|
|
$: this.$,
|
|
items: [ languageFieldLayout, this.languagePanelButton ]
|
|
} );
|
|
|
|
this.descriptionInput = new OO.ui.TextInputWidget( {
|
|
$: this.$,
|
|
multiline: true,
|
|
autosize: true
|
|
} );
|
|
this.templateDescriptionFieldset = new OO.ui.FieldsetLayout( {
|
|
$: this.$,
|
|
items: [ this.descriptionInput ]
|
|
} );
|
|
this.paramListNoticeLabel = new OO.ui.LabelWidget( { $: this.$ } );
|
|
this.paramListNoticeLabel.$element.hide();
|
|
|
|
this.paramSelectWidget = new OO.ui.SelectWidget();
|
|
templateParamsFieldset = new OO.ui.FieldsetLayout( {
|
|
$: this.$,
|
|
label: mw.msg( 'templatedata-modal-title-templateparams' )
|
|
} );
|
|
templateParamsFieldset.$element.append( this.paramSelectWidget.$element );
|
|
|
|
// Param details panel
|
|
this.$paramDetailsContainer = this.$( '<div>' )
|
|
.addClass( 'tdg-TemplateDataDialog-paramDetails' );
|
|
|
|
this.listParamsPanel.$element
|
|
.addClass( 'tdg-templateDataDialog-listParamsPanel' )
|
|
.append(
|
|
this.paramListNoticeLabel.$element,
|
|
languageFieldset.$element,
|
|
this.templateDescriptionFieldset.$element,
|
|
templateParamsFieldset.$element
|
|
);
|
|
this.paramEditNoticeLabel = new OO.ui.LabelWidget( { $: this.$ } );
|
|
this.paramEditNoticeLabel.$element.hide();
|
|
// Edit panel
|
|
this.editParamPanel.$element
|
|
.addClass( 'tdg-templateDataDialog-editParamPanel' )
|
|
.append(
|
|
this.paramEditNoticeLabel.$element,
|
|
this.$paramDetailsContainer
|
|
);
|
|
// Language panel
|
|
this.languagePanel.$element
|
|
.addClass( 'tdg-templateDataDialog-languagePanel' )
|
|
.append(
|
|
this.newLanguageSearchWidget.$element
|
|
);
|
|
this.addParamPanel.$element
|
|
.addClass( 'tdg-templateDataDialog-addParamPanel' )
|
|
.append( addParamFieldlayout.$element );
|
|
|
|
this.panels.addItems( [
|
|
this.listParamsPanel,
|
|
this.editParamPanel,
|
|
this.languagePanel,
|
|
this.addParamPanel
|
|
] );
|
|
this.panels.setItem( this.listParamsPanel );
|
|
this.panels.$element.addClass( 'tdg-TemplateDataDialog-panels' );
|
|
|
|
// Build param details panel
|
|
this.$paramDetailsContainer.append( this.createParamDetails() );
|
|
|
|
// Initialization
|
|
this.$body.append(
|
|
this.noticeLabel.$element,
|
|
this.panels.$element
|
|
);
|
|
|
|
// Events
|
|
this.newLanguageSearchWidget.connect( this, { select: 'newLanguageSearchWidgetSelect' } );
|
|
this.addParamButton.connect( this, { click: 'onAddParamButtonClick' } );
|
|
this.descriptionInput.connect( this, { change: 'onDescriptionInputChange' } );
|
|
this.languagePanelButton.connect( this, { click: 'onLanguagePanelButton' } );
|
|
this.languageDropdownWidget.getMenu().connect( this, { choose: 'onLanguageDropdownWidgetChoose' } );
|
|
this.paramSelectWidget.connect( this, { choose: 'onParamSelectWidgetChoose' } );
|
|
};
|
|
|
|
/**
|
|
* Respond to model change of description event
|
|
* @param {jQuery.event} event Event details
|
|
* @param {string} description New description
|
|
*/
|
|
TemplateDataDialog.prototype.onModelChangeDescription = function ( description ) {
|
|
this.descriptionInput.setValue( description );
|
|
};
|
|
|
|
/**
|
|
* Respond to description input change event
|
|
*/
|
|
TemplateDataDialog.prototype.onDescriptionInputChange = function ( value ) {
|
|
if ( this.model.getTemplateDescription() !== value ) {
|
|
this.model.setTemplateDescription( value, this.language );
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Respond to add language button click
|
|
*/
|
|
TemplateDataDialog.prototype.onLanguagePanelButton = function () {
|
|
this.switchPanels( 'language' );
|
|
};
|
|
|
|
/**
|
|
* Respond to language select widget choose event
|
|
* @param {OO.ui.OptionWidget} item Chosen item
|
|
*/
|
|
TemplateDataDialog.prototype.onLanguageDropdownWidgetChoose = function ( item ) {
|
|
var language = item ? item.getData() : this.language;
|
|
|
|
// Change current language
|
|
if ( language !== this.language ) {
|
|
this.language = language;
|
|
|
|
// Update description label
|
|
this.templateDescriptionFieldset.setLabel( mw.msg( 'templatedata-modal-title-templatedesc', this.language ) );
|
|
|
|
// Update description value
|
|
this.descriptionInput.setValue( this.model.getTemplateDescription( language ) );
|
|
|
|
// Update all param descriptions in the param select widget
|
|
this.repopulateParamSelectWidget();
|
|
|
|
// Update the parameter detail page
|
|
this.updateParamDetailsLanguage( this.language );
|
|
|
|
this.emit( 'change-language', this.language );
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Respond to add language button
|
|
* @param {Object} data Data from the selected option widget
|
|
*/
|
|
TemplateDataDialog.prototype.newLanguageSearchWidgetSelect = function ( data ) {
|
|
var languageButton,
|
|
newLanguage = data.code;
|
|
|
|
if (
|
|
newLanguage &&
|
|
$.inArray( newLanguage, this.availableLanguages ) === -1
|
|
) {
|
|
// Add new language
|
|
this.availableLanguages.push( newLanguage );
|
|
languageButton = new OO.ui.OptionWidget( {
|
|
data: newLanguage,
|
|
$: this.$,
|
|
label: $.uls.data.getAutonym( newLanguage )
|
|
} );
|
|
this.languageDropdownWidget.getMenu().addItems( [ languageButton ] );
|
|
}
|
|
// Go to the main panel
|
|
this.switchPanels( 'listParams' );
|
|
};
|
|
|
|
/**
|
|
* Respond to add parameter button
|
|
*/
|
|
TemplateDataDialog.prototype.onAddParamButtonClick = function () {
|
|
var newParamKey = this.newParamInput.getValue(),
|
|
allProps = TemplateDataModel.static.getAllProperties( true );
|
|
|
|
// Validate parameter
|
|
if (
|
|
!newParamKey.match( allProps.name.restrict ) &&
|
|
$.inArray( newParamKey, this.model.getAllParamNames() ) === -1
|
|
) {
|
|
// Add to model
|
|
if ( this.model.addParam( newParamKey ) ) {
|
|
// Add parameter to list
|
|
this.addParamToSelectWidget( newParamKey );
|
|
// Empty the parameter
|
|
this.newParamInput.setValue( '' );
|
|
// Go back to list
|
|
this.switchPanels( 'listParams' );
|
|
}
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Respond to choose event from the param select widget
|
|
* @param {OO.ui.OptionWidget} item Parameter item
|
|
*/
|
|
TemplateDataDialog.prototype.onParamSelectWidgetChoose = function ( item ) {
|
|
var paramKey = item.getData();
|
|
|
|
if ( paramKey === 'tdg-importParameters' ) {
|
|
// Import
|
|
this.importParametersFromTemplateCode();
|
|
} else {
|
|
this.selectedParamKey = paramKey;
|
|
|
|
// Fill in parameter detail
|
|
this.getParameterDetails( paramKey );
|
|
this.switchPanels( 'editParam' );
|
|
}
|
|
};
|
|
|
|
TemplateDataDialog.prototype.onParamPropertyInputChange = function ( property, value ) {
|
|
var err = false,
|
|
anyInputError = false,
|
|
allProps = TemplateDataModel.static.getAllProperties( true );
|
|
|
|
if ( property === 'type' ) {
|
|
value = this.propInputs[property].getSelectedItem() ? this.propInputs[property].getSelectedItem().getData() : 'undefined';
|
|
}
|
|
|
|
// TODO: Validate the name
|
|
if ( allProps[property].restrict ) {
|
|
if ( value.match( allProps[property].restrict ) ) {
|
|
// Error! Don't fix the model
|
|
err = true;
|
|
this.toggleNoticeMessage( 'edit', true, 'error', mw.msg( 'templatedata-modal-errormsg', '|', '=', '}}' ) );
|
|
} else {
|
|
this.toggleNoticeMessage( 'edit', false );
|
|
}
|
|
}
|
|
|
|
this.propInputs[property].$element.toggleClass( 'tdg-editscreen-input-error', err );
|
|
|
|
// Validate
|
|
$( '.tdg-TemplateDataDialog-paramInput' ).each( function () {
|
|
if ( $( this ).hasClass( 'tdg-editscreen-input-error' ) ) {
|
|
anyInputError = true;
|
|
}
|
|
} );
|
|
// Disable the 'back' button if there are any errors in the inputs
|
|
this.actions.setAbilities( { back: !anyInputError } );
|
|
if ( !err ) {
|
|
this.model.setParamProperty( this.selectedParamKey, property, value, this.language );
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Set the parameter details in the detail panel.
|
|
* @param {Object} paramKey Parameter details
|
|
*/
|
|
TemplateDataDialog.prototype.getParameterDetails = function ( paramKey ) {
|
|
var prop,
|
|
paramData = this.model.getParamData( paramKey );
|
|
|
|
for ( prop in this.propInputs ) {
|
|
this.changeParamPropertyInput( paramKey, prop, paramData[prop], this.language );
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Reset contents on reload
|
|
*/
|
|
TemplateDataDialog.prototype.reset = function () {
|
|
this.language = null;
|
|
this.availableLanguages = [];
|
|
if ( this.paramSelectWidget ) {
|
|
this.paramSelectWidget.clearItems();
|
|
this.selectedParamKey = '';
|
|
}
|
|
|
|
if ( this.languageDropdownWidget ) {
|
|
this.languageDropdownWidget.getMenu().clearItems();
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Empty and repopulate the parameter select widget.
|
|
*/
|
|
TemplateDataDialog.prototype.repopulateParamSelectWidget = function () {
|
|
var paramKey,
|
|
missingParams = this.model.getMissingParams(),
|
|
paramList = this.model.getParams();
|
|
|
|
this.paramSelectWidget.clearItems();
|
|
// Update all param descriptions in the param select widget
|
|
this.paramSelectWidget.clearItems();
|
|
for ( paramKey in paramList ) {
|
|
if ( !paramList[paramKey].deleted ) {
|
|
this.addParamToSelectWidget( paramKey );
|
|
}
|
|
}
|
|
|
|
// Check if there are potential parameters to add
|
|
// from the template source code
|
|
if ( missingParams.length > 0 ) {
|
|
// Add a final option
|
|
this.paramSelectWidget.addItems( [
|
|
new TemplateDataOptionImportWidget( {
|
|
data: 'tdg-importParameters',
|
|
$: this.$,
|
|
params: missingParams
|
|
} )
|
|
] );
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Change parameter property
|
|
* @param {string} paramKey Parameter key
|
|
* @param {string} propName Property name
|
|
* @param {string} propVal Property value
|
|
* @param {string} [lang] Language
|
|
*/
|
|
TemplateDataDialog.prototype.changeParamPropertyInput = function ( paramKey, propName, value, lang ) {
|
|
var languageProps = TemplateDataModel.static.getPropertiesWithLanguage(),
|
|
allProps = TemplateDataModel.static.getAllProperties( true ),
|
|
prop = allProps[propName],
|
|
propInput = typeof this.propInputs[propName].getMenu === 'function' ?
|
|
this.propInputs[propName].getMenu() : this.propInputs[propName];
|
|
|
|
lang = lang || this.language;
|
|
|
|
if ( value !== undefined ) {
|
|
// Change the actual input
|
|
if ( prop.type === 'select' ) {
|
|
propInput.selectItem( propInput.getItemFromData( value ) );
|
|
} else if ( prop.type === 'boolean' ) {
|
|
propInput.setValue( !!value );
|
|
} else {
|
|
if ( $.inArray( propName, languageProps ) !== -1 ) {
|
|
propInput.setValue( value[lang] );
|
|
} else {
|
|
if ( prop.type === 'array' && $.type( value ) === 'array' ) {
|
|
value = value.join( prop.delimiter );
|
|
}
|
|
propInput.setValue( value );
|
|
}
|
|
}
|
|
} else {
|
|
// Empty the input
|
|
if ( prop.type === 'select' ) {
|
|
propInput.selectItem( propInput.getItemFromData( prop['default'] ) );
|
|
} else {
|
|
propInput.setValue( '' );
|
|
}
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Add parameter to the list
|
|
* @param {string} paramKey Parameter key in the model
|
|
* @param {Object} paramData Parameter data
|
|
*/
|
|
TemplateDataDialog.prototype.addParamToSelectWidget = function ( paramKey ) {
|
|
var paramItem,
|
|
data = this.model.getParamData( paramKey );
|
|
|
|
paramItem = new TemplateDataOptionWidget( {
|
|
data: {
|
|
key: paramKey,
|
|
name: data.name,
|
|
aliases: data.aliases,
|
|
description: this.model.getParamDescription( paramKey, this.language )
|
|
},
|
|
$: this.$
|
|
} );
|
|
|
|
this.paramSelectWidget.addItems( [ paramItem ] );
|
|
};
|
|
|
|
/**
|
|
* Create the information page about individual parameters
|
|
* @returns {jQuery} Editable details page for the parameter
|
|
*/
|
|
TemplateDataDialog.prototype.createParamDetails = function () {
|
|
var props, type, propInput, config, paramProperties,
|
|
paramFieldset,
|
|
typeItemArray = [];
|
|
|
|
paramProperties = TemplateDataModel.static.getAllProperties( true );
|
|
|
|
// Fieldset
|
|
paramFieldset = new OO.ui.FieldsetLayout( {
|
|
$: this.$
|
|
} );
|
|
|
|
for ( props in paramProperties ) {
|
|
config = {
|
|
$: this.$,
|
|
multiline: paramProperties[props].multiline
|
|
};
|
|
if ( paramProperties[props].multiline ) {
|
|
config.autosize = true;
|
|
}
|
|
// Create the property inputs
|
|
switch ( props ) {
|
|
case 'type':
|
|
propInput = new OO.ui.DropdownWidget( config );
|
|
for ( type in paramProperties[props].children ) {
|
|
typeItemArray.push( new OO.ui.OptionWidget( {
|
|
data: paramProperties[props].children[type],
|
|
$: this.$,
|
|
label: mw.msg( 'templatedata-modal-table-param-type-' + paramProperties[props].children[type] )
|
|
} ) );
|
|
}
|
|
propInput.getMenu().addItems( typeItemArray );
|
|
break;
|
|
case 'required':
|
|
case 'suggested':
|
|
propInput = new OO.ui.ToggleSwitchWidget( config );
|
|
break;
|
|
default:
|
|
propInput = new OO.ui.TextInputWidget( config );
|
|
break;
|
|
}
|
|
|
|
this.propInputs[props] = propInput;
|
|
|
|
propInput.$element
|
|
.addClass( 'tdg-TemplateDataDialog-paramInput tdg-TemplateDataDialog-paramList-' + props );
|
|
|
|
this.propFieldLayout[props] = new OO.ui.FieldLayout( propInput, {
|
|
align: 'left',
|
|
label: mw.msg( 'templatedata-modal-table-param-' + props )
|
|
} );
|
|
// Event
|
|
if ( props === 'type' ) {
|
|
propInput.connect( this, { choose: [ 'onParamPropertyInputChange', props ] } );
|
|
} else {
|
|
propInput.connect( this, { change: [ 'onParamPropertyInputChange', props ] } );
|
|
}
|
|
// Append to parameter section
|
|
paramFieldset.$element.append( this.propFieldLayout[props].$element );
|
|
}
|
|
// Update parameter property fields with languages
|
|
this.updateParamDetailsLanguage( this.language );
|
|
return paramFieldset.$element;
|
|
};
|
|
|
|
TemplateDataDialog.prototype.onDeleteParamButtonClick = function () {
|
|
};
|
|
|
|
/**
|
|
* Update the labels for parameter property inputs that include language, so
|
|
* they show the currently used language.
|
|
* @param {string} [lang] Language. If not used, will use currently defined
|
|
* language.
|
|
*/
|
|
TemplateDataDialog.prototype.updateParamDetailsLanguage = function ( lang ) {
|
|
var i, prop, label,
|
|
languageProps = TemplateDataModel.static.getPropertiesWithLanguage();
|
|
lang = lang || this.language;
|
|
|
|
for ( i = 0; i < languageProps.length; i++ ) {
|
|
prop = languageProps[i];
|
|
label = mw.msg( 'templatedata-modal-table-param-' + prop, lang );
|
|
this.propFieldLayout[prop].setLabel( label );
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Override getBodyHeight to create a tall dialog relative to the screen.
|
|
* @return {number} Body height
|
|
*/
|
|
TemplateDataDialog.prototype.getBodyHeight = function () {
|
|
return window.innerHeight - 200;
|
|
};
|
|
|
|
/**
|
|
* Show or hide the notice message in the dialog with a set message.
|
|
* @param {string} type Which notice label to show: 'list' or 'global'
|
|
* @param {Boolean} isShowing Show or hide the message
|
|
* @param {string} status Message status 'error' or 'success'
|
|
* @param {string|string[]} noticeMessage The message to display
|
|
*/
|
|
TemplateDataDialog.prototype.toggleNoticeMessage = function ( type, isShowing, status, noticeMessage ) {
|
|
var noticeReference,
|
|
$message;
|
|
|
|
type = type || 'list';
|
|
|
|
// Hide all
|
|
this.noticeLabel.$element.hide();
|
|
this.paramEditNoticeLabel.$element.hide();
|
|
this.paramListNoticeLabel.$element.hide();
|
|
|
|
if ( noticeMessage ) {
|
|
// See which error to display
|
|
if ( type === 'global' ) {
|
|
noticeReference = this.noticeLabel;
|
|
} else if ( type === 'edit' ) {
|
|
noticeReference = this.paramEditNoticeLabel;
|
|
} else {
|
|
noticeReference = this.paramListNoticeLabel;
|
|
}
|
|
isShowing = isShowing || !noticeReference.$element.is( ':visible' );
|
|
|
|
if ( $.type( noticeMessage ) === 'array' ) {
|
|
$message = $( '<div>' );
|
|
$.each( noticeMessage, function ( i, msg ) {
|
|
$message.append( $( '<p>' ).text( msg ) );
|
|
} );
|
|
noticeReference.setLabel( $message );
|
|
} else {
|
|
noticeReference.setLabel( noticeMessage );
|
|
}
|
|
noticeReference.$element
|
|
.toggle( isShowing )
|
|
.toggleClass( 'errorbox', status === 'error' )
|
|
.toggleClass( 'successbox', status === 'success' );
|
|
}
|
|
};
|
|
|
|
/**
|
|
* Import parameters from the source code.
|
|
*/
|
|
TemplateDataDialog.prototype.importParametersFromTemplateCode = function () {
|
|
var combinedMessage = [],
|
|
state = 'success',
|
|
response = this.model.importSourceCodeParameters();
|
|
// Repopulate the list
|
|
this.repopulateParamSelectWidget();
|
|
|
|
if ( response.existing.length > 0 ) {
|
|
combinedMessage.push( mw.msg( 'templatedata-modal-errormsg-import-paramsalreadyexist', response.existing.join( mw.msg( 'comma-separator' ) ) ) );
|
|
}
|
|
|
|
if ( response.imported.length === 0 ) {
|
|
combinedMessage.push( mw.msg( 'templatedata-modal-errormsg-import-noparams' ) );
|
|
state = 'error';
|
|
} else {
|
|
combinedMessage.push( mw.msg( 'templatedata-modal-notice-import-numparams', response.imported.length, response.imported.join( mw.msg( 'comma-separator' ) ) ) );
|
|
}
|
|
|
|
this.toggleNoticeMessage( 'list', true, state, combinedMessage );
|
|
};
|
|
|
|
/**
|
|
* @inheritDoc
|
|
*/
|
|
TemplateDataDialog.prototype.getSetupProcess = function ( data ) {
|
|
return TemplateDataDialog.super.prototype.getSetupProcess.call( this, data )
|
|
.next( function () {
|
|
// Hide the panels and display a spinner
|
|
this.$spinner.show();
|
|
this.panels.$element.hide();
|
|
this.toggleNoticeMessage( 'global', false );
|
|
this.toggleNoticeMessage( 'list', false );
|
|
this.reset();
|
|
|
|
// Start with parameter list
|
|
this.switchPanels( 'listParams' );
|
|
this.model = new TemplateDataModel( data.config );
|
|
|
|
// Events
|
|
this.model.connect( this, {
|
|
'change-description': 'onModelChangeDescription'
|
|
} );
|
|
|
|
// Load the model according to the string
|
|
this.model.loadModel( data.wikitext )
|
|
.done( $.proxy( function () {
|
|
var i,
|
|
language = this.model.getDefaultLanguage(),
|
|
languageItems = [],
|
|
languages = this.model.getExistingLanguageCodes();
|
|
|
|
this.setupDetailsFromModel();
|
|
|
|
// Fill up the language selection
|
|
if (
|
|
languages.length === 0 ||
|
|
$.inArray( language, languages ) === -1
|
|
) {
|
|
// Add the default language
|
|
languageItems.push( new OO.ui.OptionWidget( {
|
|
data: language,
|
|
$: this.$,
|
|
label: $.uls.data.getAutonym( language )
|
|
} ) );
|
|
this.availableLanguages.push( language );
|
|
}
|
|
|
|
// Add all available languages
|
|
for ( i = 0; i < languages.length; i++ ) {
|
|
languageItems.push( new OO.ui.OptionWidget( {
|
|
data: languages[i],
|
|
$: this.$,
|
|
label: $.uls.data.getAutonym( languages[i] )
|
|
} ) );
|
|
// Store available languages
|
|
this.availableLanguages.push( languages[i] );
|
|
}
|
|
this.languageDropdownWidget.getMenu().addItems( languageItems );
|
|
// Trigger the initial language choice
|
|
this.languageDropdownWidget.getMenu().chooseItem( this.languageDropdownWidget.getMenu().getItemFromData( language ) );
|
|
|
|
// Show the panel
|
|
this.$spinner.hide();
|
|
this.panels.$element.show();
|
|
}, this ) )
|
|
.fail( $.proxy( function () {
|
|
// Show error
|
|
this.actions.setMode( 'error' );
|
|
this.$spinner.hide();
|
|
this.toggleNoticeMessage( 'global', true, 'error', mw.msg( 'templatedata-errormsg-jsonbadformat' ) );
|
|
}, this ) );
|
|
|
|
}, this );
|
|
};
|
|
|
|
/**
|
|
* Set up the list of parameters from the model. This should happen
|
|
* after initialization of the model.
|
|
*/
|
|
TemplateDataDialog.prototype.setupDetailsFromModel = function () {
|
|
// Reset parameter list
|
|
this.reset();
|
|
|
|
// Set up description
|
|
this.descriptionInput.setValue( this.model.getTemplateDescription( this.language ) );
|
|
// TODO: Set up paramOrder
|
|
|
|
this.repopulateParamSelectWidget();
|
|
};
|
|
|
|
/**
|
|
* Switch between stack layout panels
|
|
* @param {string} panel Panel key to switch to
|
|
*/
|
|
TemplateDataDialog.prototype.switchPanels = function ( panel ) {
|
|
switch ( panel ) {
|
|
case 'listParams':
|
|
this.actions.setMode( 'list' );
|
|
this.panels.setItem( this.listParamsPanel );
|
|
// Reset message
|
|
this.toggleNoticeMessage( 'list', false );
|
|
// Deselect parameter
|
|
this.paramSelectWidget.selectItem( null );
|
|
// Repopulate the list to account for any changes
|
|
if ( this.model ) {
|
|
this.repopulateParamSelectWidget();
|
|
}
|
|
// Hide/show panels
|
|
this.listParamsPanel.$element.show();
|
|
this.editParamPanel.$element.hide();
|
|
this.addParamPanel.$element.hide();
|
|
this.languagePanel.$element.hide();
|
|
break;
|
|
case 'editParam':
|
|
this.actions.setMode( 'edit' );
|
|
this.panels.setItem( this.editParamPanel );
|
|
// Deselect parameter
|
|
this.paramSelectWidget.selectItem( null );
|
|
// Hide/show panels
|
|
this.listParamsPanel.$element.hide();
|
|
this.languagePanel.$element.hide();
|
|
this.addParamPanel.$element.hide();
|
|
this.editParamPanel.$element.show();
|
|
break;
|
|
case 'addParam':
|
|
this.actions.setMode( 'add' );
|
|
this.panels.setItem( this.addParamPanel );
|
|
// Hide/show panels
|
|
this.listParamsPanel.$element.hide();
|
|
this.editParamPanel.$element.hide();
|
|
this.languagePanel.$element.hide();
|
|
this.addParamPanel.$element.show();
|
|
break;
|
|
case 'language':
|
|
this.actions.setMode( 'language' );
|
|
this.panels.setItem( this.languagePanel );
|
|
// Hide/show panels
|
|
this.listParamsPanel.$element.hide();
|
|
this.editParamPanel.$element.hide();
|
|
this.addParamPanel.$element.hide();
|
|
this.languagePanel.$element.show();
|
|
break;
|
|
}
|
|
};
|
|
|
|
/**
|
|
* @inheritDoc
|
|
*/
|
|
TemplateDataDialog.prototype.getActionProcess = function ( action ) {
|
|
if ( action === 'back' ) {
|
|
return new OO.ui.Process( function () {
|
|
this.switchPanels( 'listParams' );
|
|
}, this );
|
|
}
|
|
if ( action === 'add' ) {
|
|
return new OO.ui.Process( function () {
|
|
this.switchPanels( 'addParam' );
|
|
}, this );
|
|
}
|
|
if ( action === 'delete' ) {
|
|
return new OO.ui.Process( function () {
|
|
this.model.deleteParam( this.selectedParamKey );
|
|
this.switchPanels( 'listParams' );
|
|
}, this );
|
|
}
|
|
if ( action === 'apply' ) {
|
|
return new OO.ui.Process( function () {
|
|
this.emit( 'apply', this.model.outputTemplateDataString() );
|
|
this.close( { action: action } );
|
|
}, this );
|
|
}
|
|
// Fallback to parent handler
|
|
return TemplateDataDialog.super.prototype.getActionProcess.call( this, action );
|
|
};
|
|
}( mediaWiki ) );
|