/*
 *  Copyright 2014 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 class provides a TreePanel for thesaurus
 * The tree includes a toolbar which allow to :
 *  - filter resources on name, 
 *  - refresh a node
 *  - expand a node 
 *  - collapse the all tree.
 * The tree store extends the {@link Ametys.plugins.cms.content.tree.HierarchicalReferenceTablesTree} tree.
 * @private
 */
Ext.define('Ametys.plugins.thesaurus.tool.ThesaurusTreePanel', {
	extend: "Ametys.plugins.cms.content.tree.HierarchicalReferenceTablesTree",
	
	/**
	 * @cfg {String} thesaurusId The id of root thesaurus
	 */
	
	/**
	 * @property {String} _thesaurusId See {#cfg-thesaurusId}
	 * @private
	 */
	
	/**
	 * @cfg {String} microthesaurusId The id of microthesaurus. Can be null to choose microthesaurus in a list
	 */
	
	/**
	 * @property {String} microthesaurusId See {#cfg-microthesaurusId}
	 * @private
	 */
	
	cls: 'thesaurus-tree',
	
	/**
	 * @cfg {String} The css class for synonym node
	 */
	synonymCls: 'synonym',
	
	statics: {
		/**
		 * The default filter.
		 */
		DEFAULT_FILTER: function(node)
		{
			return node ? true : false;
		}
	},
	
	initComponent: function ()
	{
		this.callParent();
	},
	
	constructor: function (config) 
	{
		this.callParent(arguments);
		this.addDocked(this._getMicroThesaurusComboCfg(), 0);
	},
    
	/**
	 * Returns the combo box of microthesaurii
	 * @return {Ext.form.ComboBox} The combo box
	 */
	getMTComboBox: function ()
	{
        return this.down("combobox[itemId='microthesaurus-combo']");
	},
	
	/**
	 * Get the selected MicroThesaurus
	 * @return {Ametys.plugins.thesaurus.tool.MicrothesaurusEntry} the microthesaurus
	 */
	getSelectedMT: function() 
	{
		return this._microThesaurusStore.getById(this.getMTComboBox().getValue());
	},
	
	/**
	 * @protected
	 * Get configuration object for combox box of microthesaurii
	 * @return {Ext.form.Panel} The form panel containing the combo box
	 */
	_getMicroThesaurusComboCfg: function ()
	{
		this._microThesaurusStore = Ext.create('Ext.data.Store', {
			model: 'Ametys.plugins.thesaurus.tool.MicrothesaurusEntry',
			sortOnLoad: true,
			sorters: [{property: 'label', direction:'ASC'}],
			proxy: {
				type: 'ametys',
				plugin: 'thesaurus',
				url: 'microthesaurus.json',
				extraParams: {id: this.thesaurusId},
				reader: {
					type: 'json',
					rootProperty: 'microthesaurii'
				}
			},
			autoLoad: false
		});
		
		return {
            dock: 'top',
			xtype: 'toolbar',
            layout: {
                type: 'hbox',
                align: 'stretch'
            },
            
            border: false,
            defaults : {
                cls: 'ametys',
                labelWidth: 90,
                labelSeparator: ''
            },
			
			items: [{
				xtype: 'combobox',
				flex: 1,
				
				typeAhead: true,
				forceSelection: true,
				triggerAction: 'all',
				queryMode: 'local',
				
		    	name: 'microthesaurus',
                itemId: 'microthesaurus-combo',
		    	fieldLabel: "{{i18n PLUGINS_THESAURUS_MICROTHESAURUS_LABEL}}",
		    	store: this._microThesaurusStore,
		        valueField: 'id',
		        displayField: 'label',
		        
		    	listeners: {
		    		'select': Ext.bind (this._microThesaurusComboSelect, this)
		    	}
			}]
		}
	},
	
	/**
	 * @protected
	 * Retrieves the 'no result' panel config
	 */
	_getNoResultPanelCfg: function()
	{
        var text = "{{i18n PLUGINS_THESAURUS_TREE_FILTER_NO_MATCH}}";
        text += this._disableCandidateCreation ? "{{i18n PLUGINS_THESAURUS_TREE_FILTER_NO_MATCH_ACTION}}" : "{{i18n PLUGINS_THESAURUS_TREE_FILTER_NO_MATCH_CREATE_CANDIDATE_ACTION}}" 
        
        return {
            dock: 'top',
            xtype: 'button',
            hidden: true,
            itemId: 'no-result',
            ui: 'tool-hintmessage',
            text: text,
            scope: this,
            handler: this._disableCandidateCreation ? this._clearSearchFilter : this._createCandidateFromFilter
        };
	},
	
	/**
	 * Load the microthesaurii
	 * @param {String} [microThesaurusId] The id of microthesaurus to select after loading. Can be null.
	 * @param {Function} [callback] The callback function to call after loading success
	 */
	loadMicrothesaurii: function (microThesaurusId, callback)
	{
		if (!this.microthesaurusId)
		{
			// Load microthesaurus combobox
			Ext.apply(this._microThesaurusStore.getProxy().extraParams, {id: this.thesaurusId});

			this._microThesaurusStore.load({
				scope: this,
				callback: function(records, operation, success) {
					if (this._microThesaurusStore.getCount() >= 1)
					{
						var selectedMT = microThesaurusId != null ? this._microThesaurusStore.getById(microThesaurusId) : this._microThesaurusStore.getAt(0);
						
						this._setRootNode(selectedMT);
						
						this.getMTComboBox().setValue(selectedMT.getId());
						this.getSelectionModel().deselectAll();
						
						this.getSelectionModel().select(this.getRootNode());
					}
					else
					{
						//we do not have some microthesaurus
						this.getStore().setRoot(this._getInitRootConfig());
					}
					if (Ext.isFunction(callback))
					{
						callback();
					}
				}
			});
		}
		else
		{
            var newRoot = Ext.clone(this.getStore().getRoot());
            newRoot.setId(this.microthesaurusId);
            newRoot.name = '';
            this.getStore().setRoot(newRoot);
			
			this.getSelectionModel().select(this.getRootNode());
			
			if (Ext.isFunction(callback))
			{
				callback();
			}
			this.refreshNode();
		}
		
	},
	
	/**
	 * @private
	 * Listener when an item is selected in the list. Reload the tree.
	 * @param {Ext.form.field.ComboBox} combo The combox box
	 * @param {Ext.data.Model} record The selected record
	 * @param {Object} eOpts The options object passed to Ext.util.Observable.addListener.
	 */
	_microThesaurusComboSelect: function(combo, record, eOpts) 
	{
		this.getSelectionModel().deselectAll();
		this._clearSearchFilter();
		
		this._setRootNode(record);
		
		this.getSelectionModel().select(this.getRootNode());
	},
	
	/**
	 * @private
     * Get the initial root configuration
	 * @return {Object} The config of the initial root node
	 */
	_getInitRootConfig: function()
	{
		return {
			label: "{{i18n PLUGINS_THESAURUS_TREE_ROOT_DEFAULT_TEXT}}",
			text: "{{i18n PLUGINS_THESAURUS_TREE_ROOT_DEFAULT_TEXT}}",
			leaf: true,
			editable: false,
			allowDrag: true,
			allowDrop: true,
			name: '',
            cls: "no-microthesaurus",
			type: 'microthesaurus',
			iconGlyph: 'ametysicon-reading', 
			iconCls: 'a-tree-glyph ametysicon-reading'
		}
	},
	
	/**
	 * @private
	 * Set the root node to the given record
	 * @param {Ext.data.Model} record The selected record
	 */
	_setRootNode: function(record) 
	{
		this.setReferenceTableId(record.getId());
		this.getStore().setRoot({
			contentId: 'root',
			contenttypesIds: [record.getId()],
			editable: false,
			allowDrag: true,
			allowDrop: true,
			expanded: true,
			title: record.get ('label'),
			text: record.get ('label'),
			name: '',
			type: 'microthesaurus',
			iconGlyph: 'ametysicon-reading', 
			iconCls: 'a-tree-glyph ametysicon-reading',
			qtipIcon: "ametysicon-reading"
		});
	},
});