/*
 * SLD Editor - The Open Source Java SLD Editor
 *
 * Copyright (C) 2016, SCISYS UK Limited
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

package com.sldeditor.filter.v2.function;

import com.sldeditor.common.vendoroption.VendorOptionManager;
import com.sldeditor.ui.attribute.SubPanelUpdatedInterface;
import com.sldeditor.ui.iface.ValueComboBoxDataSelectedInterface;
import com.sldeditor.ui.menucombobox.MenuComboBox;
import com.sldeditor.ui.widgets.ValueComboBoxData;
import com.sldeditor.ui.widgets.ValueComboBoxDataGroup;
import java.awt.BorderLayout;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import javax.swing.JPanel;
import org.opengis.filter.Filter;

/**
 * Panel to be able to edit FilterField objects.
 *
 * @author Robert Ward (SCISYS)
 */
public class FilterField extends JPanel implements ValueComboBoxDataSelectedInterface {

    /** The Constant FILTER_PANEL. */
    private static final String FILTER_PANEL = "Filter";

    /** The Constant serialVersionUID. */
    private static final long serialVersionUID = 1L;

    /** The menu combo box containing all the filter that can be selected. */
    private MenuComboBox filterComboBox = null;

    /** The filter name map. */
    private transient Map<String, FilterConfigInterface> filterNameMap = new LinkedHashMap<>();

    /** The filter name manager. */
    private transient FilterNameInterface filterNameMgr = null;

    /** The parent obj. */
    private transient SubPanelUpdatedInterface parentObj = null;

    /**
     * Gets the panel name.
     *
     * @return the panel name
     */
    public static String getPanelName() {
        return FILTER_PANEL;
    }

    /**
     * Instantiates a new data source attribute panel.
     *
     * @param parentObj the parent obj
     * @param functionNameMgr the function name mgr
     */
    public FilterField(SubPanelUpdatedInterface parentObj, FilterNameInterface functionNameMgr) {
        this.parentObj = parentObj;
        this.filterNameMgr = functionNameMgr;

        setLayout(new BorderLayout());

        if (filterComboBox == null) {
            filterComboBox = new MenuComboBox(this);

            VendorOptionManager.getInstance().addVendorOptionListener(filterComboBox);
            add(filterComboBox, BorderLayout.CENTER);
        }

        List<FilterConfigInterface> filterConfigList = filterNameMgr.getFilterConfigList();
        for (FilterConfigInterface filterConfig : filterConfigList) {
            String filterNameString = filterConfig.getFilterConfiguration().getFilterName();

            filterNameMap.put(filterNameString, filterConfig);
        }

        populateFunctionComboBox();
    }

    /** Populate function combo box. */
    private void populateFunctionComboBox() {
        if (filterComboBox != null) {

            List<ValueComboBoxDataGroup> dataSelectionList = new ArrayList<>();

            List<ValueComboBoxData> defaultDataList = new ArrayList<>();
            defaultDataList.add(
                    new ValueComboBoxData(
                            null,
                            "",
                            VendorOptionManager.getInstance().getDefaultVendorOptionVersion()));
            dataSelectionList.add(new ValueComboBoxDataGroup(defaultDataList));

            Map<String, List<ValueComboBoxData>> map = new HashMap<>();

            List<ValueComboBoxData> dataList = null;

            for (Entry<String, FilterConfigInterface> entry : filterNameMap.entrySet()) {
                FilterConfigInterface filterConfig = entry.getValue();

                dataList = map.get(filterConfig.category());
                if (dataList == null) {
                    dataList = new ArrayList<>();
                    map.put(filterConfig.category(), dataList);
                }
                String text = filterConfig.getFilterConfiguration().getFilterName();
                String key = text;

                dataList.add(
                        new ValueComboBoxData(
                                key,
                                text,
                                VendorOptionManager.getInstance().getDefaultVendorOptionVersion()));
            }

            for (Entry<String, List<ValueComboBoxData>> entry : map.entrySet()) {
                ValueComboBoxDataGroup value =
                        new ValueComboBoxDataGroup(entry.getKey(), entry.getValue(), true);
                dataSelectionList.add(value);
            }

            filterComboBox.initialiseMenu(dataSelectionList);
        }
    }

    /**
     * Gets the selected item.
     *
     * @return the selected item
     */
    public String getSelectedItem() {
        return filterComboBox.getSelectedItem();
    }

    /**
     * Sets the panel enabled.
     *
     * @param enabled the new panel enabled
     */
    public void setPanelEnabled(boolean enabled) {
        filterComboBox.setEnabled(enabled);
    }

    /**
     * Sets the filter.
     *
     * @param filter the new filter
     * @param filterConfig the filter config
     */
    public void setFilter(Filter filter, FilterConfigInterface filterConfig) {

        String key = null;

        if (filterConfig != null) {
            key = filterConfig.getFilterConfiguration().getFilterName();
        }
        filterComboBox.setSelectedDataKey(key);
    }

    /**
     * Gets the filter.
     *
     * @return the filter
     */
    public Filter getFilter() {
        FilterConfigInterface filterConfig = getFilterConfig();
        Filter newFilter = null;

        if (filterConfig != null) {
            newFilter = filterConfig.createFilter();
        }
        return newFilter;
    }

    /**
     * Gets the function name.
     *
     * @return the function name
     */
    public FilterConfigInterface getFilterConfig() {
        String filterNameString = filterComboBox.getSelectedItem();

        return filterNameMap.get(filterNameString);
    }

    /* (non-Javadoc)
     * @see com.sldeditor.ui.iface.ValueComboBoxDataSelectedInterface#optionSelected(com.sldeditor.ui.widgets.ValueComboBoxData)
     */
    @Override
    public void optionSelected(ValueComboBoxData selectedData) {
        if (parentObj != null) {
            parentObj.updateSymbol();
        }
    }
}
