/*
 * MiningMart Version 1.0
 * 
 * Copyright (C) 2006 Martin Scholz, Timm Euler, 
 *                    Daniel Hakenjos, Katharina Morik
 *
 * Contact: miningmart@ls8.cs.uni-dortmund.de
 *
 * A list of contributing developers (other than the copyright 
 * holders) can be found at
 * http://mmart.cs.uni-dortmund.de/downloads/download.html
 * 
 * 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 2
 * 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, see the file MM_HOME/LICENSE; if not, write
 * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
 * Floor, Boston, MA 02110-1301, USA.
 */
package edu.udo.cs.miningmart.gui.concepteditor;

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Vector;

import javax.swing.BorderFactory;
import javax.swing.Box;
import javax.swing.BoxLayout;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.JTextField;
import javax.swing.ListSelectionModel;
import javax.swing.SpringLayout;
import javax.swing.SwingConstants;

import org.musoft.limo.application.Application;
import org.musoft.limo.application.Resource;
import org.musoft.limo.drawing.ModelDrawingView;

import edu.udo.cs.miningmart.exception.M4Exception;
import edu.udo.cs.miningmart.gui.application.MiningMartApplication;
import edu.udo.cs.miningmart.m4.Columnset;
import edu.udo.cs.miningmart.m4.Concept;
import edu.udo.cs.miningmart.m4.M4Interface;
import edu.udo.cs.miningmart.m4.utils.Print;

/**
 * This is a<code>JPanel</code> to connect (and match) a <code>Concept</code> with a business table or view.
 * 
 * @author Daniel Hakenjos
 * @version $Id: ConnectionPanel.java,v 1.3 2006/04/11 14:10:17 euler Exp $
 */
public class ConnectionPanel extends ConceptPanel implements ActionListener{
	
	private MiningMartApplication app;
	
	private Concept concept;
	
	private JButton createButton,removeButton, closeButton, matchButton;
	
	private JTextField columnsetfield;
	
	private JList tablelist;
	
	private JCheckBox checkbox;
	
	private JComboBox matcherBox;
	
	public ConnectionPanel(MiningMartApplication app, Concept concept){
		super();
		this.app=app;
		this.concept=concept;
		
		initComponents();
	}
	
	
	private void initComponents(){
		
		setLayout(new BorderLayout(5,5));
		setBorder(BorderFactory.createEmptyBorder(5,5,5,5));		

		//Info
		JTextArea infoMessageTextArea = new JTextArea(Resource.getString("CONNECTION_INFOMESSAGE"));
		infoMessageTextArea.setEditable(false);
		infoMessageTextArea.setLineWrap(true);
		infoMessageTextArea.setWrapStyleWord(true);
		infoMessageTextArea.setBorder(javax.swing.BorderFactory.createEtchedBorder());
		JScrollPane scrollPane=new JScrollPane(infoMessageTextArea);
		scrollPane.setPreferredSize(new Dimension(scrollPane.getWidth(), 100));
		add(scrollPane,BorderLayout.NORTH);

		//Button		
		createButton=new JButton(Resource.getString("CONNECTION_CREATE"));
		createButton.addActionListener(this);
		createButton.setEnabled(false);
		
		removeButton=new JButton(Resource.getString("CONNECTION_REMOVE"));
		removeButton.addActionListener(this);
		removeButton.setEnabled(false);
		
		matchButton=new JButton(Resource.getString("CONNECTION_MATCH"));
		matchButton.addActionListener(this);
		matchButton.setEnabled(false);
		
		closeButton=new JButton(Resource.getString("CLOSE"));
		closeButton.addActionListener(this);

		checkbox=new JCheckBox(Resource.getString("CONNECTION_SHOW_MAPPING"));
		checkbox.setSelected(true);
		checkbox.setToolTipText(Resource.getString("CONNECTION_SHOW_MAPPING_TIP"));
		
		JPanel buttonPanel1=new JPanel();
		buttonPanel1.setLayout(new BoxLayout(buttonPanel1,BoxLayout.X_AXIS));
		buttonPanel1.add(Box.createHorizontalGlue());

		buttonPanel1.add(checkbox);
		buttonPanel1.add(Box.createRigidArea(new Dimension(5, 0)));		
		buttonPanel1.add(createButton);
		buttonPanel1.add(Box.createRigidArea(new Dimension(5, 0)));		
		buttonPanel1.add(matchButton);

		JPanel buttonPanel2=new JPanel();
		buttonPanel2.setLayout(new BoxLayout(buttonPanel2,BoxLayout.X_AXIS));
		buttonPanel2.add(Box.createHorizontalGlue());
		buttonPanel2.add(removeButton);
		buttonPanel2.add(Box.createRigidArea(new Dimension(5, 0)));		
		buttonPanel2.add(closeButton);
		
		JPanel buttonPanel=new JPanel();
		buttonPanel.setLayout(new GridLayout(2,1,5,5));
		buttonPanel.add(buttonPanel1);
		buttonPanel.add(buttonPanel2);

		
		//midpanel
		JPanel midpanel=new JPanel();
		midpanel.setLayout(new SpringLayout());
		midpanel.setBorder(BorderFactory.createEmptyBorder(5,5,5,5));

		JLabel label=new JLabel(Resource.getString("CONNECTED_COLUMNSET"));
		midpanel.add(label);

		columnsetfield=new JTextField();
		columnsetfield.setEditable(false);
		Object[] columnSets = null;
		try {
			columnSets = concept.getColumnSets().toArray();
		} catch (M4Exception error) {
			M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
		}

		if (columnSets == null || columnSets.length == 0) {
			columnsetfield.setText(Resource.getString("CONNECTION_NONE"));
			createButton.setEnabled(true);
			matchButton.setEnabled(true);
		} else if (columnSets.length == 1) {
			columnsetfield.setText(((Columnset) columnSets[0]).getName());
			removeButton.setEnabled(true);
		} else if (columnSets.length > 1) {
			columnsetfield.setText(Resource.getString("CONNECTION_MORE_COLUMNSETS"));
			columnsetfield.setForeground(Resource.getColor("STEPSETTINGS_COLOR_NOT_VALID"));
		}
		if (app.getViewMode()==Application.VIEWER){
			createButton.setEnabled(false);
			matchButton.setEnabled(false);
			removeButton.setEnabled(false);
			checkbox.setEnabled(false);
		}
		midpanel.add(columnsetfield);

		label=new JLabel(Resource.getString("CONNECTION_TABLES"));
		label.setHorizontalAlignment(SwingConstants.LEFT);
		label.setVerticalAlignment(SwingConstants.TOP);
		midpanel.add(label);
		
		Vector colls=new Vector();
		try{
			colls.addAll(MiningMartApplication.m4Interface.getNamesOfBusinessTablesAndViews());
			Collections.sort(colls);
		}catch(M4Exception error){
			M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
			colls=new Vector();
		}
		Iterator iter=colls.iterator();
		String[] tablenames=new String[colls.size()];
		int index=0;
		while (iter.hasNext()){
			tablenames[index]=(String) iter.next();
			try {
				if (MiningMartApplication.m4Interface.isBusinessTable(tablenames[index])){
					tablenames[index]+=" ("+Resource.getString("TABLE")+")";
				}else if (MiningMartApplication.m4Interface.isBusinessView(tablenames[index])){
					tablenames[index]+=" ("+Resource.getString("VIEW")+")";
				}else{
				}
			} catch (M4Exception error) {
				M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
			}
			index++;
		}

		tablelist=new JList(tablenames);
		tablelist.setSelectionMode(ListSelectionModel.MULTIPLE_INTERVAL_SELECTION);
		tablelist.setLayoutOrientation(JList.VERTICAL);
		tablelist.setVisibleRowCount(12);
		scrollPane=new JScrollPane(tablelist);
		midpanel.add(scrollPane);

		if (columnSets.length == 1) {
			String table=((Columnset) columnSets[0]).getName();
			try {
				if (MiningMartApplication.m4Interface.isBusinessTable(table)){
					table+=" ("+Resource.getString("TABLE")+")";
				}else if (MiningMartApplication.m4Interface.isBusinessView(table)){
					table+=" ("+Resource.getString("VIEW")+")";
				}else{
				}
				tablelist.setSelectedValue(table,true);
			} catch (M4Exception error) {
				M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
			}
		}

		//The matcher
		label=new JLabel(Resource.getString("CONNECTION_MATCHER"));
		label.setHorizontalAlignment(SwingConstants.LEFT);
		label.setVerticalAlignment(SwingConstants.TOP);
		midpanel.add(label);
		matcherBox=new JComboBox(M4Interface.AVAILABLE_MATCHERS);
		midpanel.add(matcherBox);


		//		  Lay out the panel.
		SpringUtilities.makeCompactGrid(midpanel,
										3, 2, //rows, cols
										6, 6,        //initX, initY
										6, 6);       //xPad, yPad
		
		JPanel centerpanel2=new JPanel();
		centerpanel2.setLayout(new BorderLayout());
		centerpanel2.add(midpanel,BorderLayout.NORTH);
		centerpanel2.add(buttonPanel,BorderLayout.SOUTH);

		JPanel centerpanel=new JPanel();
		centerpanel.setLayout(new BorderLayout());
		centerpanel.add(centerpanel2,BorderLayout.NORTH);
		add(centerpanel,BorderLayout.CENTER);
		
		
	}

	/* (non-Javadoc)
	 * @see edu.udo.cs.miningmart.gui.concepteditor.ConceptPanel#getConcept()
	 */
	public Concept getConcept() {
		return this.concept;
	}


	
	private void findConnection(){
	
		Object[] tables=tablelist.getSelectedValues();
		if ((tables==null)||(tables.length==0)){
			return;
		}
		
		String matcher=(String) matcherBox.getSelectedItem();
			
		Vector dbobjects=new Vector();
		String table;
		for(int i=0;i<tables.length;i++){
			table=(String) tables[i];			
			if (table.endsWith(" ("+Resource.getString("TABLE")+")")){
				table=table.substring(0,table.length()-3-Resource.getString("TABLE").length());
			}else if(table.endsWith(" ("+Resource.getString("VIEW")+")")){
				table=table.substring(0,table.length()-3-Resource.getString("VIEW").length());
			}
			dbobjects.add(table);
		}
		
		
		try {
			Collection joinedSets=MiningMartApplication.m4Interface.findConnection(this.concept,dbobjects,matcher);
			if	(joinedSets!=null){
				
				Iterator iter=joinedSets.iterator();
				Columnset columnset1=(Columnset) iter.next();
				Columnset columnset2=(Columnset) iter.next();
				Columnset joinedset=(Columnset) iter.next();
				
				String message=Resource.getString("CONNECTION_JOIN_MSG1")+" "+columnset1.getName()+","+columnset2.getName()+ " "+Resource.getString("CONNECTION_JOIN_MSG2")+"\n" +
										Resource.getString("CONNECTION_JOIN_MSG3")+" "+concept.getName();
				JOptionPane.showMessageDialog(app,message,Resource.getString("CONNECTION_JOIN_TITLE"),JOptionPane.INFORMATION_MESSAGE);

				return;
			}else{
				Object[] columnSets = null;
				try {
					columnSets = concept.getColumnSets().toArray();
				} catch (M4Exception error) {
					M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
				}

				if (columnSets == null || columnSets.length == 0) {
					throw new M4Exception(Resource.getString("CONNECTION_ERRORMESSAGE"));
				} else if (columnSets.length == 1) {
					table=((Columnset) columnSets[0]).getName();
					columnsetfield.setText(table);
					try {
						if (MiningMartApplication.m4Interface.isBusinessTable(table)){
							table+=" ("+Resource.getString("TABLE")+")";
						}else if (MiningMartApplication.m4Interface.isBusinessView(table)){
							table+=" ("+Resource.getString("VIEW")+")";
						}else{
						}
						tablelist.clearSelection();
						tablelist.setSelectedValue(table,true);
					} catch (M4Exception error) {
						M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
					}
				} else if (columnSets.length > 1) {
					throw new M4Exception(Resource.getString("CONNECTION_NONE"));
				}

				createButton.setEnabled(false);
				matchButton.setEnabled(false);
				removeButton.setEnabled(true);
				((ModelDrawingView) app.getDrawingView()).repaint();
				app.getMiningMartConcepts().setDirty(true);

				if (checkbox.isSelected()){
					//Removes the tab
					MappingPanel panel=new MappingPanel(app,concept);
					app.showConceptPanel(panel);
				}
			}

			

		} catch (M4Exception error) {
			M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
		}
		
	}
	
	private void createConnection(){
		
		String table=(String) tablelist.getSelectedValue();
		if (table==null)
			return;
			
		if (table.endsWith(" ("+Resource.getString("TABLE")+")")){
			table=table.substring(0,table.length()-3-Resource.getString("TABLE").length());
		}else if(table.endsWith(" ("+Resource.getString("VIEW")+")")){
			table=table.substring(0,table.length()-3-Resource.getString("VIEW").length());
		}
			
		boolean btable;
		try {
			btable = MiningMartApplication.m4Interface.isBusinessTable(table);
		} catch (M4Exception error) {
			M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
			return;
		}
			
		try {
			concept.connect(table,btable,new HashMap());
		} catch (M4Exception error) {
			M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
			return;
		}
		
		Columnset set;
		try {
			set = concept.getCurrentColumnSet();
		} catch (M4Exception error) {
			M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
			set=null;
		}
		if (set==null){
			return;
		}
		
		columnsetfield.setText(table);
		createButton.setEnabled(false);
		matchButton.setEnabled(false);
		removeButton.setEnabled(true);
		((ModelDrawingView) app.getDrawingView()).repaint();
		app.getMiningMartConcepts().setDirty(true);
		
		if (checkbox.isSelected()){
			//Removes the tab
			MappingPanel panel=new MappingPanel(app,concept);
			app.showConceptPanel(panel);
		}
	}
	
	private void removeConnection(){
		
		try {
			concept.removeConnection();
		} catch (M4Exception error) {
			M4Interface.print.doPrint(Print.ERROR,error.getMessage(),error);
			return;
		}
		columnsetfield.setText(Resource.getString("CONNECTION_NONE"));

		createButton.setEnabled(true);
		matchButton.setEnabled(true);
		removeButton.setEnabled(false);
		((ModelDrawingView) app.getDrawingView()).repaint();
		app.getMiningMartConcepts().setDirty(true);
	}
	
	public String toString(){
		return Resource.getString("CONCEPT_CONNECTION");
	}
	

	/* (non-Javadoc)
	 * @see java.awt.event.ActionListener#actionPerformed(java.awt.event.ActionEvent)
	 */
	public void actionPerformed(ActionEvent event) {
		if (!(event.getSource() instanceof JButton))
			return;
		JButton source=(JButton) event.getSource();
		
		if (source.getText().equals(closeButton.getText())){
			//Removes the tab
			app.removeComponentFromTab(this);
		}
		if (source.getText().equals(createButton.getText())){
			createConnection();
		}
		if (source.getText().equals(removeButton.getText())){
			removeConnection();
		}
		if (source.getText().equals(matchButton.getText())){
			findConnection();
		}

	}

}
/*
 * Historie
 * --------
 *
 * $Log: ConnectionPanel.java,v $
 * Revision 1.3  2006/04/11 14:10:17  euler
 * Updated license text.
 *
 * Revision 1.2  2006/04/06 16:31:16  euler
 * Prepended license remark.
 *
 * Revision 1.1  2006/01/03 09:54:25  hakenjos
 * Initial version!
 *
 */

/*
 Revision 1.8  2005/12/22 10:46:21  hakenjos
 *** empty log message ***

 Revision 1.7  2005/12/15 09:15:55  hakenjos
 *** empty log message ***

 Revision 1.6  2005/12/13 09:32:34  hakenjos
 Initial version!

 Revision 1.5  2005/11/24 10:52:55  hakenjos
 Only one ConceptPanel in the Application visible.

 Revision 1.4  2005/11/24 09:50:28  hakenjos
 Names etc. replaced with resource-access

 Revision 1.3  2005/11/22 10:53:22  hakenjos
 *** empty log message ***

 Revision 1.2  2005/11/10 10:48:44  hakenjos
 *** empty log message ***

 Revision 1.1  2005/11/03 10:46:25  hakenjos
 *** empty log message ***

 */
