/*
 *  Copyright 2012 Anyware Services
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 */

/**
 * This helper allows to choose one cart in WRITE access from a combo list
 * @private
 */
Ext.define('Ametys.plugins.cart.helper.ChooseCart', {
	singleton: true,
	
	/**
	 * @property {String} The id of the last selected cart.
	 * @private
	 */
	_lastSelectedCartId: null,
	
	/**
	 * @property {Boolean} _initialized True if the dialog box was already initialized
	 * @private
	 */
	_initialized: false,
	
	/**
	 * @property _cbFn The callback function to call after choosing a cart
	 */
	
	constructor: function()
	{
		this.callParent(arguments);
		Ametys.message.MessageBus.on(Ametys.message.Message.SELECTION_CHANGED, this._onSelectionChanged, this);
	},
	
	/**
	 * Open the dialog box to choose a cart in WRITE access
	 * @param {Object} config The configuration options:
	 * @param {String} [config.title] The dialog box title
	 * @param {String} [config.iconCls] The CSS class for dialog box icon
	 * @param {String} [config.icon] The dialog box icon (used only if iconCls is empty)
	 * @param {String} [config.helpMessage] The dialog box help message
	 * @param {String} [config.callback] The callback function to be called after cart selection
	 */
	act: function(config)
	{
		this._cbFn = config.callback;
		
		if (!this._delayedInitialize(config))
		{
			return false;
		}
		this._box.show();
		this._initForm();
	},
	
	/**
	 * @private
	 * Initialize the dialog box.
	 * @param {Object} config The configuration options:
	 * @param {String} [config.title] The dialog box title
	 * @param {String} [config.iconCls] The CSS class for dialog box icon
	 * @param {String} [config.icon] The dialog box icon (used only if iconCls is empty)
	 * @param {String} [config.helpMessage] The dialog box help message
	 */
	_delayedInitialize: function (config)
	{	
		if (!this._initialized)
		{
			this._store = this._createStore();
	    	
			this._box = Ext.create('Ametys.window.DialogBox', {
		    	title: config.title || "{{i18n PLUGINS_CART_DIALOG_CHOOSECART_TITLE}}",
		    	iconCls: config.icon ? null : (config.iconCls || 'ametysicon-basket'),
		    	icon: config.icon,
		    	
				width: 430,
				layout: {
					type: 'vbox',
					align: 'stretch'
				},
				
				items : [{
				        	xtype: 'component',
                            cls: 'a-text',
				        	html: config.helpMessage || "{{i18n PLUGINS_CART_DIALOG_CHOOSECART_HINT}}"
				        },
				        {
				        	xtype: 'combobox',
				        	fieldLabel : "{{i18n PLUGINS_CART_DIALOG_CHOOSECART_CARTS}}",
				        	labelWidth: 60,
				        	labelAlign: 'right',
				        	labelSeparator: '',
				        	name:'cart',
				        	itemId: 'cart',
				        	
				        	typeAhead: true,
							editable: true,
							forceSelection: true,
							triggerAction: 'all',
							
				        	store: this._store,
				        	queryMode: 'local',
				        	displayField: 'title',
				        	valueField: 'id',
				        	width: 390,
				        	allowBlank: false,
				        	
				        	cls: 'ametys'
				        },
				        {
				        	xtype: 'component',
                            cls: 'a-text-warning',
                            itemId: 'no-cart',
				        	hidden: true,
				        	html: "{{i18n PLUGINS_CART_DIALOG_CHOOSECART_NO_CART}}"
				        },
				        {
				        	xtype: 'component',
				        	cls: 'a-text link',
				        	html: "<a class='action'>{{i18n PLUGINS_CART_DIALOG_CHOOSECART_ADDCART}}</a>"
				        }
				],
				
				defaultFocus: 'cart',
				
				referenceHolder: true,
				defaultButton: 'validate',
				
				closeAction: 'hide',
				buttons: 
				[{
					reference: 'validate',
					text :"{{i18n PLUGINS_CART_DIALOG_CHOOSECART_OK}}",
					handler : Ext.bind(this._ok, this)
				}, {
					text :"{{i18n PLUGINS_CART_DIALOG_CHOOSECART_CANCEL}}",
					handler: function () {this._box.hide()},
					scope: this
				}]
			});
		    
		    this._initialized = true;
		}
		else
		{
			if (config.icon)
			{
				this._box.setIcon(config.icon);
			}
			else
			{
				this._box.setIconCls(config.iconCls || 'ametysicon-basket');
			}
			this._box.setTitle(config.title || "{{i18n PLUGINS_CART_DIALOG_CHOOSECART_TITLE}}");
			this._box.items.getAt(0).update(config.helpMessage || "{{i18n PLUGINS_CART_DIALOG_CHOOSECART_HINT}}");
		}
	    return true;
	},
	
	/**
	 * Function to create a new cart
	 * @private
	 */
	_createCart: function ()
	{
		this._box.hide();
		Ametys.plugins.cart.helper.CreateOrEditCart.act('new', {}, this._cbFn);
	},
	
	/**
	 * Creates the cart store
	 * @return {Ext.data.Store} The cart store
	 * @private
	 */
	_createStore: function()
	{
		return Ext.create('Ext.data.Store', {
			model: 'Ametys.plugins.cart.tool.CartsTool.CartEntry',
			sortOnLoad: true,
			sorters: [{property: 'title', direction:'ASC'}],
			
			proxy: {
				type: 'ametys',
				plugin: 'cart',
				url: 'carts/list.json',
				extraParams: {profile: 'write_access'},
				reader: {
					type: 'json',
					rootProperty: 'carts'
				}
			},
			autoLoad: true
		});
	},
	
	/**
	 * @private
	 * Initialize fields
	 */
	_initForm: function ()
	{
		if (!this._clickEventRegistered)
		{
			var action = this._box.items.getAt(3);
			action.mon(action.getEl(), 'click', this._createCart, this, {delegate: 'a.action'});
			this._clickEventRegistered = true;
		}
		
		this._store.load({callback: this._onLoadCarts, scope: this});
		
	},
	
	/**
	 * Callback function called after carts are loaded
	 * @private
	 */
	_onLoadCarts: function (records, operation, success)
	{
		if (records.length == 0)
		{
			this._box.down('#no-cart').setVisible(true);
		}
		else
		{
			this._box.down('#no-cart').setVisible(false);
			this._box.down('combo').setValue(this._lastSelectedCartId);
		}
	},
	
	/**
	 * The ok button handler. Will call the callback when cart is chosen.
	 * @private
	 */
	_ok: function()
	{
		if (!this._box.down('combo').isValid())
		{
			return;
		}
		
		this._box.hide();
		
		if (Ext.isFunction(this._cbFn))
		{
			this._cbFn (this._box.down('combo').getValue());
		}
	},
	
	/**
	 * Listener when the selection has changed.
	 * Update the last selected cart id.
	 * @param {Ametys.message.Message} message The selection message.
	 * @private
	 */
	_onSelectionChanged: function (message)
	{
		var target = message.getTarget(Ametys.message.MessageTarget.CART);
		if (target != null)
		{				
			this._lastSelectedCartId = target.getParameters().id;
		}
	}
	
});