/*
 *  Copyright 2016 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 tool lists all existing forms
 */
Ext.define('Ametys.plugins.forms.content.tool.FormsListTool', {
	
	extend: 'Ametys.tool.Tool',
	
	/**
	 * @private
	 * @property {Ext.data.Store} _store the store of the form
	 */
	
	/**
	 * @private
	 * @property {Ext.grid.Panel} _grid the forms grid panel
	 */
	
    constructor: function(config)
    {
        this.callParent(arguments);
        
        Ametys.message.MessageBus.on(Ametys.message.Message.CREATED, this._onCreated, this);
        Ametys.message.MessageBus.on(Ametys.message.Message.DELETED, this._onDeleted, this);
        Ametys.message.MessageBus.on(Ametys.message.Message.MODIFIED, this._onModified, this);
    },
	
	createPanel: function()
	{
		this._store = Ext.create('Ext.data.Store', {
			model: 'Ametys.plugins.forms.content.FormsListTool.Form',
	        proxy: {
	        	type: 'ametys',
				plugin: 'forms',
				url: 'forms-list.json',
	        	reader: {
	        		type: 'json',
					rootProperty: 'forms'
	        	},
	        	
	        	extraParams: {
	        		siteName: Ametys.getAppParameter('siteName')
	        	}
	        },
	        
        	listeners: {
                'beforeload' : Ext.bind(this._onBeforeLoad, this)
            }
		});
		
        var langCombo = Ametys.cms.language.LanguageDAO.createComboBox({
			itemId: 'languages-combo',
			fieldLabel: "{{i18n PLUGINS_FORMS_UITOOL_FORMS_LIST_LANGUAGE}}",
			listeners: {
	        	'change': Ext.bind(this._onChangeLang, this)
	        }
		});
        
	    this._grid = new Ext.grid.GridPanel({
            stateful: true,
            stateId: this.self.getName() + "$grid",

            store : this._store,
            
            selModel : {
                mode: 'MULTI'
            },
            
            listeners: {
                'selectionchange': Ext.bind(this.sendCurrentSelection, this),
                'celldblclick': Ext.bind(this._openFormEntriesTool, this)
            },
	        
	        viewConfig: {
	        	forceFit: true
	        },
	        
	        columns: [
	            {header: "{{i18n PLUGINS_FORMS_UITOOL_FORMS_LIST_COL_NAME}}", flex: 0.3, dataIndex: 'label'},
	            {header: "{{i18n PLUGINS_FORMS_UITOOL_FORMS_LIST_COL_CONTENT_TITLE}}", flex: 0.3, dataIndex: 'contentTitle', renderer: this._renderContent},
	            {header: "{{i18n PLUGINS_FORMS_UITOOL_FORMS_LIST_COL_ENTRIES_AMOUNT}}", flex: 0.2, dataIndex: 'entriesAmount', align: 'center'},
	            {header: "{{i18n PLUGINS_FORMS_UITOOL_FORMS_LIST_COL_LAST_ENTRY}}", flex: 0.2, dataIndex: 'lastEntry', align: 'center', renderer: Ametys.grid.GridColumnHelper.renderDateTime}
	        ],
	        
            dockedItems: [{
				dock: 'top',
				xtype: 'toolbar',
				layout: {
			        type: 'hbox',
			        align: 'stretch'
			    },
				
			    border: false,
				defaults : {
					cls: 'ametys',
					labelWidth: 55,
					labelSeparator: ''
				},
				
				items: langCombo
			}]
	    });
	    
	    return this._grid;
	},
	
	getMBSelectionInteraction: function() 
	{
		return Ametys.tool.Tool.MB_TYPE_ACTIVE;
	},
	
	setParams: function(params)
	{
		this.callParent(arguments);
		this.refresh();
	},
	
	refresh: function ()
	{
		this.showRefreshing();
		this._store.load({callback: this.showRefreshed, scope: this});
	},
	
	sendCurrentSelection : function()
    {
	    var targets = [];
		var records = this._grid.getSelection();
	    
	    Ext.each(records, function(record){
	    	targets.push({
			    id: Ametys.message.MessageTarget.CONTENT_FORM,
                parameters: {
                	id: record.data.id,
                    label: record.data.label,
                    hasEntries: record.data.entriesAmount > 0,
                    workflowName: record.data.workflowName,
					contentId: record.data.contentId
                }
        	});
	    }, this);
		
        Ext.create("Ametys.message.Message", {
            type: Ametys.message.Message.SELECTION_CHANGED,
            targets: targets
        });
    },
    
    /**
     * @private
	 * Listens when the language is changed.
	 * @param {Ext.form.field.Field} field The field
	 * @param {Object} newValue The new value.
	 * @param {Object} oldValue The original value.
	 */
	_onChangeLang: function(field, newValue, oldValue)
	{
	    // Reload grid
		this.refresh();
	},
	
	/**
	 * @private
	 * Open the form entries tool corresponding to the clicked cell
	 * @param grid The grid
	 * @param rowIndex The selected row index
	 * @param columnIndex The selected column index
	 * @param e The event
	 */
	_openFormEntriesTool: function (grid, rowIndex, columnIndex, e)
	{
		var record = grid.getSelectionModel().getSelection()[0];
		Ametys.tool.ToolsManager.openTool("uitool-form-content-entries", {id: record.get('id'), label: record.get('label'), workflowName: record.get('workflowName'), contentId: record.get('contentId')});
	},
	
    /**
     * @private
     * Function invoked whenever the languages combo box is about to be loaded
     * @param {Ext.data.Store} store the store
     * @param {Ext.data.operation.Operation} operation the object that will be passed to the proxy to load the store
     */
    _onBeforeLoad: function(store, operation)
    {
    	// Let the load occur only if we know the language.
		var lang = this._grid.down("combobox[itemId='languages-combo']").getValue();
		
		operation.setParams(Ext.apply(operation.getParams() || {}, {
			lang: lang
		}));
    },
    
    /**
     * @private
     * Content renderer
     * @param {Object} value The data value
     * @param {Object} metaData A collection of metadata about the current cell
     * @param {Ext.data.Model} record The record
     * @return {String} The html representation of the content
     */
    _renderContent: function(value, metaData, record)
    {
    	return '<a href="javascript:(function(){Ametys.tool.ToolsManager.openTool(\'uitool-content\', {id:\'' + record.get('contentId') + '\'});})()">' + value + '</a>';
    },
    
    /**
     * @private
     * Listener function invoked upon reception of a deletion message
     * @param {Ametys.message.Message} message the deletion message
     */
    _onCreated: function(message)
    {
        var targets = message.getTargets(Ametys.message.MessageTarget.CONTENT);
        if (targets.length > 0)
        {
        	this.showOutOfDate();
        }
    },
    
    /**
     * @private
     * Listener function invoked upon reception of a deletion message
     * @param {Ametys.message.Message} message the deletion message
     */
	_onDeleted: function(message)
    {
        var targets = message.getTargets(Ametys.message.MessageTarget.CONTENT_FORM_ENTRY);
        if (targets.length > 0)
        {
        	this.showOutOfDate();
        }
    },
    
    /**
     * @private
     * Listener upon reception of a modification message
     * @param {Ametys.message.Message} message the deletion message
     */
    _onModified: function (message)
    {
    	var targets = message.getTargets(function(target) { 
    		return target.getId() == Ametys.message.MessageTarget.CONTENT_FORM || target.getId() == Ametys.message.MessageTarget.CONTENT;
		});
    	
    	if (targets.length > 0)
        {
            this.showOutOfDate();
        }
    }
});