package com.sap.dbmtk.demo;

import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.sql.Types;
import java.util.ArrayList;
import java.util.List;

import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;

import com.sap.dbmtk.demo.AddOrChangeAbstract.OpType;
import com.sap.dbmtk.demo.SqlStatement.Type;
import com.sap.dbmtk.demo.ui.ResultSetTableModel;
import com.sap.dbmtk.demo.utils.Configuration;
import com.sap.dbmtk.demo.utils.SelectAllFocusListener;
import com.sap.dbmtk.demo.utils.SwingUtils;

import net.miginfocom.swing.MigLayout;


public class DataPanelAuthors
extends DataPanelAbstract
{
	private static final long serialVersionUID = 1L;
//	private static Logger _logger = Logger.getLogger(DataPanelAuthors.class);

	public static final String NAME = "Author";

	public DataPanelAuthors(DemoApp owner)
	{
		super(owner, NAME, true);
	}

	@Override
	public boolean showTableToolTipCheckbox()
	{
		return true;
	}

	//----------------------------------------------------------------
	// BEGIN: DB filter stuff
	//----------------------------------------------------------------
	private JLabel     _firstName_lbl;
	private JTextField _firstName_txt;

	private JLabel     _lastName_lbl;
	private JTextField _lastName_txt;

	private JComboBox  _image_cbx;

	@Override
	public JPanel createDbSearchPanel()
	{
		_firstName_lbl = new JLabel("First Name");
		_firstName_txt = new JTextField();

		_lastName_lbl = new JLabel("Last Name");
		_lastName_txt = new JTextField();

		_image_cbx    = new JComboBox(new String[] {"With or Without Picture", "With Picture", "Without Picture"});

		
		JPanel p = SwingUtils.createPanel("DB/Server Filter", true, new MigLayout());
		
		p.add(_firstName_lbl, "");
		p.add(_firstName_txt, "growx, pushx");

		p.add(_lastName_lbl,  "");
		p.add(_lastName_txt,  "growx, pushx");

//		p.add(_image_chk,     "");
		p.add(_image_cbx,     "");
		
		p.add(_dbRowCount_lbl, "");

		// On return in some fields, press "refresh" button
		ActionListener al = new ActionListener()
		{
			@Override
			public void actionPerformed(ActionEvent e)
			{
				_refresh_but.doClick();
			}
		};
		_firstName_txt.addActionListener(al);
		_lastName_txt .addActionListener(al);
		_image_cbx    .addActionListener(al);

		_firstName_txt.addFocusListener(new SelectAllFocusListener());
		_lastName_txt .addFocusListener(new SelectAllFocusListener());

		return p;
	}

	private Integer getPictureParamValue()
	{
		int index = _image_cbx.getSelectedIndex();

		if (index == 0) return null;  // with or without picture
		if (index == 1) return 1;     // with picture
		if (index == 2) return 0;     // without picture
		return null;
	}
	
	@Override
	public int getDbRowCount()
	{
		SqlStatement stmnt = new SqlStatement(Type.CALLABLE, "{call get_authors_count(?)}");
		stmnt.addParam( SqlStatementParam.createOutParam("rcount", Types.INTEGER) );
		
		stmnt.execute(getConnectionProvider(), getOwner(), "Get rowcount");

		Integer rcount = (Integer) stmnt.getParameterValue("rcount");
		return rcount == null ? -1 : rcount;
	}

	@Override
	public void saveProps()
	{
		Configuration conf = Configuration.getInstance(Configuration.USER_TEMP);
		if (conf != null)
		{
			conf.setProperty(NAME+".field.firstName", _firstName_txt.getText());
			conf.setProperty(NAME+".field.lastName",  _lastName_txt .getText());
			conf.setProperty(NAME+".field.image",     _image_cbx    .getSelectedIndex());
		}
	}
	@Override
	public void loadProps()
	{
		Configuration conf = Configuration.getCombinedConfiguration();
		_firstName_txt.setText(          conf.getProperty   (NAME+".field.firstName", "a"));
		_lastName_txt .setText(          conf.getProperty   (NAME+".field.lastName",  "b"));
		_image_cbx    .setSelectedIndex( conf.getIntProperty(NAME+".field.image",     0));
	}
	//----------------------------------------------------------------
	// END: DB filter stuff
	//----------------------------------------------------------------

	/**
	 * Is called when the "New" button is pressed
	 */
	@Override
	public void actionAdd()
	{
		AddOrChangeAbstract dialog = new AddOrChangeAuthor(_owner.getWindow(), getConnectionProvider(), OpType.INSERT);
		if (dialog.open() == AddOrChangeAbstract.OK)
		{
			refreshDbRowCount();
			refreshTableData();
		}
		dialog.dispose();
	}

	/**
	 * Is called when the "Change" button is pressed
	 */
	@Override
	public void actionChange()
	{
		AddOrChangeAbstract dialog = new AddOrChangeAuthor(_owner.getWindow(), getConnectionProvider(), OpType.UPDATE);
		
		int vrow = getTable().getSelectedRow();
		dialog.setFields(getTable(), vrow);

		if (dialog.open() == AddOrChangeAbstract.OK)
			refreshTableData();
		dialog.dispose();
	}
	
	/**
	 * Is called when the "Remove" button is pressed
	 */
	@Override
	public void actionRemove()
	{
		AddOrChangeAbstract dialog = new AddOrChangeAuthor(_owner.getWindow(), getConnectionProvider(), OpType.DELETE);
		
		int vrow = getTable().getSelectedRow();
		dialog.setFields(getTable(), vrow);

		if (dialog.open() == AddOrChangeAbstract.OK)
		{
			refreshDbRowCount();
			refreshTableData();
		}
		dialog.dispose();
	}
	
	@Override
	public SqlStatement getTableDataSqlStatement()
	{
//		return new SqlStatement(Type.LANGUAGE, "select au_fname, au_lname, phone, address, city, state, country, postalcode, au_id from authors");

		String  fname       = null;
		String  lname       = null;
		Integer pictureType = null;

		if (isDbSearchPanelVisible())
		{
			fname       = _firstName_txt.getText();
			lname       = _lastName_txt .getText();
			pictureType = getPictureParamValue();
		}
			
		SqlStatement stmnt = new SqlStatement(Type.CALLABLE, "{call get_authors(?,?,?,?)}");
		
		stmnt.addParam( SqlStatementParam.createInParam("first_name",  Types.VARCHAR, fname) );
		stmnt.addParam( SqlStatementParam.createInParam("last_name",   Types.VARCHAR, lname) );
		stmnt.addParam( SqlStatementParam.createInParam("has_picture", Types.INTEGER, pictureType) );
		stmnt.addParam( SqlStatementParam.createOracleResultSetParam("a_cursor") );


		return stmnt;
	}

	@Override
	public List<String> getHiddenColumns()
	{
		List<String> hiddenCols = new ArrayList<String>();
		hiddenCols.add("au_id");
		return hiddenCols;
	}

	@Override
	public String getTableToolTipText(ResultSetTableModel rstm, int mrow, int mcol)
	{
		if ( ! isTableToolTipEnabled() )
			return null;
		
		return getTableToolTipTextWithPicture(rstm, mrow, mcol, "{call get_author_picture(?,?)}", "au_id", AddOrChangeAuthor.NO_PICTURE, new Dimension(170, 220));
	}

//	public String getTableToolTipText(ResultSetTableModel rstm, int mrow, int mcol, final String sqlProc, final String keyCol, final ImageIcon noPictureIcon)
//	{
//		if ( ! isTableToolTipEnabled() )
//			return null;
//
//		final String    SQL_PROC   = "{call get_author_picture(?,?)}";
//		final String    KEY_COL    = "au_id";
//		final Integer   KEY_VAL;
//		final ImageIcon NO_PICTURE = AddOrChangeAuthor.NO_PICTURE;
//
//		// Get AU_ID
//		try
//		{
//			KEY_VAL = rstm.getValueAsInteger(mrow, KEY_COL, false);
//    		if (KEY_VAL == null)
//    			return null;
//		}
//		catch (RuntimeException rte)
//		{
//			return rte.toString();
//		}
//
//		// Get the picture from the database
//		byte[] picture = null;
//		SqlStatement stmnt = new SqlStatement(Type.CALLABLE, SQL_PROC);
//		stmnt.addParam( SqlStatementParam.createInParam(KEY_COL, Types.INTEGER, KEY_VAL) );
//		stmnt.addParam( SqlStatementParam.createOracleResultSetParam("a_cursor") );
//		
//		try
//		{
//			ResultSet rs = stmnt.executeQuery(getConnection());
//			while (rs.next())
//				picture = rs.getBytes(1);
//			rs.close();
//		}
//		catch (SQLException e)
//		{
//			return null;
//		}
//		// If picture is not in the database, use default picture
//		if (picture == null)
//		{
//			picture = SwingUtils.toBytArray(NO_PICTURE);
//			if (picture == null)
//				return null;
//		}
//
//		// Save the picture to a file, which will be used in the HTML tool tip
//		// The temporary file is deleted when the JVM exits
//		// This is a workaround since the Java HTML engine doesn't seem to understand: <img src="data:<mime-type>;base64,<data>">
//		File tmpFile = null;
//		try
//		{
//			tmpFile = File.createTempFile("dbmtk_demo_image_tooltip_", ".tmp");
//			tmpFile.deleteOnExit();
//			FileOutputStream fos = new FileOutputStream(tmpFile);
//			fos.write(picture);
//			fos.close();
//		}
//		catch (IOException ex)
//		{
//			return "<html>Sorry problems when creating temporary file '"+tmpFile+"'<br>Caught: "+ex+"</html>";
//		}
//
//		// Get width/height and calculate a new size which fits in boundary, but keep image aspect ratio
//		ImageIcon tmpImage = new ImageIcon(picture);
//		int width  = tmpImage.getIconWidth();
//		int height = tmpImage.getIconHeight();
//
//		// calculate a new image size max 500x500, but keep image aspect ratio
//		Dimension originSize   = new Dimension(width, height);
//		Dimension boundarySize = new Dimension(170, 220);
//		Dimension newSize      = SwingUtils.getScaledDimension(originSize, boundarySize);
//
//		// Compose a HTML tooltip and return it...
//		StringBuilder sb = new StringBuilder();
//		sb.append("<html>");
//		if (_logger.isDebugEnabled())
//		{
//    		sb.append("Picture for '"+KEY_COL+"': ").append(KEY_VAL).append("<br>");
//    		sb.append("Using temp file: <code>").append(tmpFile).append("</code><br>");
//    		sb.append("Width/Height: <code>").append(originSize.width).append(" x ").append(originSize.height).append("</code><br>");
//    		sb.append("Size:  <code>").append(StringUtil.bytesToHuman(picture.length, "#.#")).append("</code><br>");
//    		sb.append("<hr>");
//		}
//		sb.append("<table>");
//		sb.append("<tr>");
//		sb.append("  <td>");
//		sb.append("  <img src=\"file:///").append(tmpFile).append("\" width=\"").append(newSize.width).append("\" height=\"").append(newSize.height).append("\">");
//		sb.append("</td>");
//		sb.append("<td>");
//		sb.append(   rstm.toHtmlTableString(mrow, false));
//		sb.append("</td>");
//		sb.append("</tr>");
//		sb.append("</table>");
//		sb.append("</html>");
//
//		return sb.toString();
//	}
}
