Ext.namespace('Zarafa.common.dialogs'); /** * @class Zarafa.common.dialogs.MessageBox * @extends Ext.MessageBox * * Extension to the default {@link Ext.MessageBox MessageBox} which * offers some special features like displaying a selection list. */ // Use Ext.apply instead of Ext.extend because Ext.MessageBox is not // a class but an instantiated object. The Ext.apply({}, a, b) trick // is used to create a full copy of Ext.MessageBox instead of changing // the existing object. Zarafa.common.dialogs.MessageBox = Ext.apply({}, { /** * The custom buttons which are added in {@link Ext.MessageBox messagebox}. * it will be removed when {@link Ext.MessageBox messagebox} gets hide. * * @property * @type Array * @private */ customButton : undefined, /** * Initialize the {@link Ext.MessageBox.dlg Dialog}. * Because the {@link Ext.MessageBox MessageBox} hides the usable * interface from use, we must apply a hack to access the Dialog * before it is displayed to the user. * * This function will add a list of {@link Ext.Component Components} * to the dialog, which can be used to fine-tune the look&feel. * * @param {Array} items The array of items which must be added to the * MessageBox. * @private */ initDialog : function(items) { var dlg = this.getDialog(); // Add a container to be able to position the items after a possible msg text if ( !this.dlgItemContainer ){ this.dlgItemContainer = this.dlgItemContainer || new Ext.Container({ border: false, cls: 'my-cont' }); this.dlgItemContainer.render(dlg.body); } // Automatically remove all items which we had added. // This makes sure we can use the same Dialog multiple times dlg.on('hide', function(dlg) { this.dlgItemContainer.removeAll(); }, this, {single: true}); // In case the 'hide' event was not fired, // we also listen to the destroy event as fallback. dlg.on('destroy', function(dlg) { this.dlgItemContainer.removeAll(); }, this, {single: true}); // Before showing the dialog, we must first // add all items to the dialog. dlg.on('show', function(dlg) { this.dlgItemContainer.add(items); this.dlgItemContainer.doLayout(); }, this, {single: true}); }, /** * Extension of {@link Ext.MessageBox.show} that adds the following configuration options:<ul> * <li><b>checkbox</b> : Boolean<div class="sub-desc">When set to true a checkbox will be added to the bottom * of the MessageBox.</div></li> * <li><b>checkboxLabel</b> : String<div class="sub-desc">The label of the checkbox that will be added when * the checkbox config option is set to true. (defaults to 'Do not show this message again')</div></li> * <li><b>fn</b> : Function<div class="sub-desc">A callback function which is called when the dialog is dismissed either * by clicking on the configured buttons, or on the dialog close button, or by pressing * the return button to enter input. * <p>Progress and wait dialogs will ignore this option since they do not respond to user * actions and can only be closed programmatically, so any required function should be called * by the same code after it closes the dialog. Parameters passed:<ul> * <li><b>buttonId</b> : String<div class="sub-desc">The ID of the button pressed, one of:<div class="sub-desc"><ul> * <li><tt>ok</tt></li> * <li><tt>yes</tt></li> * <li><tt>no</tt></li> * <li><tt>cancel</tt></li> * </ul></div></div></li> * <li><b>text</b> : String<div class="sub-desc">Value of the input field if either <tt><a href="#show-option-prompt" ext:member="show-option-prompt" ext:cls="Ext.MessageBox">prompt</a></tt> * or <tt><a href="#show-option-multiline" ext:member="show-option-multiline" ext:cls="Ext.MessageBox">multiline</a></tt> is true</div></li> * <li><b>checked</b> : Boolean<div class="sub-desc">Value of the checkbox field. (Will only be passed when the * checkbox option was set to true in the config object)</div></li> * <li><b>opt</b> : Object<div class="sub-desc">The config object passed to show.</div></li> * </ul></p></div></li> * </ul> * * @param {Object} config The configuration options of the the MessageBox. See above and {@link Ext.MessageBox.show} * for more information. * @return {Zarafa.common.dialogs.MessageBox} this */ show : function(config) { config.title = config.title || _('Kopano WebApp'); if ( config.checkbox !== true ){ return Ext.MessageBox.show.call(this, config); } // If no checkboxState was set we will set it to false (=unchecked) var checkboxState = !!config.checkboxState; var cb = { xtype: 'container', cls: 'k-cb-dontshowagain', items: [{ xtype: 'checkbox', ctCls: 'k-cb-dontshowagain', boxLabel: config.checkboxLabel || _('Do not show this message again.'), checked: checkboxState, listeners: { check: function(cb, checked){ checkboxState = checked; }.bind(this) }, scope: this }] }; this.initDialog([cb]); // Make sure the checkbox state is also passed to the callback function if ( Ext.isFunction(config.fn) ){ var origFn = config.fn; config.fn = function(buttonid, text, opts){ origFn.call(this, buttonid, text, checkboxState, opts); }.bind(config.scope || null); } return Ext.MessageBox.show.call(this, config); }, /** * Displays a message box with OK and Cancel buttons prompting the user to make a selection * from a list of {@link Ext.form.Radio radio} buttons. * If a callback function is passed it will be called after the user * clicks either button, and the id of the button that was clicked (could also be the top-right * close button) and the selected {@link Ext.form.Radio radio} as the two parameters to the callback. * @param {String} title The title bar text * @param {String} msg The message box body text * @param {Function} fn (optional) The callback function invoked after the message box is closed * @param {Object} scope (optional) The scope (<code>this</code> reference) in which the callback is executed. Defaults to the browser wnidow. * @param {Array} selections (optional) Array of configuration objects for the {@link Ext.form.Radio radios} from which the user can select. * @param {String} value (optional) Default value for the {@link Ext.form.RadioGroup radiogroup}. * @param {String} customButton (optional) buttons which need to show in message box. this buttons contains custom name's. * @return {Zarafa.common.dialogs.RadioMessageBox} this */ select : function(title, msg, fn, scope, selections, value, customButton) { var radioGroup = Ext.create({ xtype: 'radiogroup', hideLabel: true, style: 'padding-left: 50px;', columns: 1, items: selections, value: value, listeners : { change : this.onChange, scope : this } }); this.initDialog([{ xtype: 'container', anchor: '100% 100%', items: [ radioGroup ] }]); if(!Ext.isEmpty(customButton)) { var config = {}; Ext.apply(config, { title : title, msg: msg + '<br />', minWidth: this.minPromptWidth, maxWidth: 250, scope : scope, fn : fn, prompt: false, value: value, customButton : customButton, radioGroup : radioGroup }); this.addCustomButtons(config); } else { this.show({ title : title, msg: msg + '<br />', buttons: Ext.MessageBox.OKCANCEL, fn: function(button) { Ext.callback(fn, scope || window, [button, radioGroup.getValue()], 1); }, minWidth: this.minPromptWidth, maxWidth: 250, scope : scope, prompt: false, value: value }); } return this; }, /** * Event handler triggered when radio button of {@link #select} message box * gets changed. * * @param {Ext.form.RadioGroup} radioGroup the radioGroup which triggers this event. * @param {Ext.form.Radio} radio the radio which listen the event. */ onChange : function (radioGroup, radio) { if(radio.hideButtonText) { var fbar = this.getDialog().getFooterToolbar(); var btn = fbar.find('name', radio.hideButtonText)[0]; if(Ext.isDefined(btn)) { btn.setText(Ext.util.Format.capitalize(radio.showButtonText)); btn.name = radio.showButtonText; } } }, /** * Display {@link Ext.MessageBox messagebox} with custom buttons. * @param {Object} config The config contains the configuration * options of message box as wall as custom buttons. */ addCustomButtons : function(config) { var dlg = this.getDialog(); this.customButton = dlg.getFooterToolbar().add(config.customButton); this.show(config); if(!Ext.isEmpty(this.customButton)) { Ext.each(this.customButton, function(button) { var args = []; args.push(config.fn); if(Ext.isDefined(config.radioGroup)) { args.push(config.radioGroup); } dlg.mon(button, 'click', Ext.createDelegate(this.onButtonClick, config.scope, args, true), this); }, this); } dlg.on('hide', this.onDestroy, this, {single : true}); dlg.on('destroy', this.onDestroy, this, {single : true}); }, /** * Event handler triggered when custom button is clicked. * it will hide the {@link Ext.MessageBox messagebox}. * @param {Ext.Button} button The button which user pressed. * @param {Ext.EventObject} event the event object * @parma {Function} callback The callback function to call when button is pressed. * @parma {Ext.form.RadioGroup} radioGroup The radioGroup contains if message box triggered from {@link #select} message box. */ onButtonClick : function(button, event, callback, radioGroup) { var buttonName = button.name || 'cancel'; Zarafa.common.dialogs.MessageBox.hide(); if(radioGroup) { callback.call(this, buttonName, radioGroup.getValue()); } else { callback.call(this, buttonName); } }, /** * Event handler which is triggered when {@link Ext.MessageBox messagebox} gets hide. * also it will remove all custom buttons from message box. * @param {Ext.Window} dlg The window */ onDestroy : function(dlg) { if(!Ext.isEmpty(this.customButton)) { for(var i = 0; i < this.customButton.length; i++) { dlg.getFooterToolbar().remove(this.customButton[i]); } this.customButton = []; } } }, Ext.MessageBox);