/**
 * Search.java
 * @date Jan 9, 2011
 * @author ricky barrette
 * @author Twenty Codes, LLC
 */
package com.TwentyCodes.java.OrderProcessor.UI;

import java.awt.BorderLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Scanner;

import javax.swing.ImageIcon;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JFileChooser;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JProgressBar;
import javax.swing.JTextField;

import com.TwentyCodes.java.OrderProcessor.Date;
import com.TwentyCodes.java.OrderProcessor.DatePickerListener;
import com.TwentyCodes.java.OrderProcessor.FileFilter;
import com.TwentyCodes.java.OrderProcessor.InvalidDateFormatException;
import com.TwentyCodes.java.OrderProcessor.Order;
import com.TwentyCodes.java.OrderProcessor.ProgressListener;

/**
 * This class will be the dialog that will ask the user for a specific make to show
 * @author ricky barrette
 */
public class SearchPanel extends JPanel implements ActionListener, ProgressListener, MouseListener, DatePickerListener {

	private static final long serialVersionUID = 1750326106927701404L;
	
	private JButton mOkButton;
	private JTextField mTextField;
	private JProgressBar mProgressBar;
	private OrderPane mOrderPanel;
	private JTextField mStartDateField;
	private JTextField mEndDateField;
	private JCheckBox mExclusiveCheckBox;
	private JButton mExportButton;
	private JFileChooser fc;
//	private JCheckBox fcCheckBox;
	private JFrame mFrame;

	/**
	 * Creates a new ShowAllMakeDialog
	 * @param frame 
	 */
	public SearchPanel(JFrame frame) {
		super(new BorderLayout());
		mFrame = frame;
		
//		mFrame.setTitle("Search");
//		mFrame.setIconImage(new ImageIcon(getClass().getResource("/database_search.png")).getImage());
		
		//create a JPanel to hold the text area and button
		JPanel panel = new JPanel();
		
		//add the JPanel to the frame, and display
		add(panel, BorderLayout.NORTH);
		
		//search string
		panel.add(new JLabel("Search:"));
		mTextField = new JTextField();
		mTextField.setColumns(20);
		mTextField.addActionListener(this);
		panel.add(mTextField);
		
		//exclusive check box
		mExclusiveCheckBox = new JCheckBox("Exclusive Search");
		panel.add(mExclusiveCheckBox);
		
		//start date
		panel.add(new JLabel("Start Date:"));
		mStartDateField = new JTextField();
		panel.add(mStartDateField);
		mStartDateField.setColumns(12);
		mStartDateField.addMouseListener(this);
		
		//end date
		panel.add(new JLabel("End Date:"));
		mEndDateField = new JTextField();
		panel.add(mEndDateField);
		mEndDateField.setColumns(12);
		mEndDateField.addMouseListener(this);
		
		//ok button
		mOkButton = new JButton("Ok", new ImageIcon(getClass().getResource("/database_search.png")));
		mOkButton.addActionListener(this);
		panel.add(mOkButton);
		
		//export button
		mExportButton = new JButton("Export", new ImageIcon(getClass().getResource("/floppy_disc.png")));
		panel.add(mExportButton);
		mExportButton.addActionListener(this);
		
		//output orderpane
		mOrderPanel = new OrderPane();
		add(mOrderPanel, BorderLayout.CENTER);
		
		//progress bar
		mProgressBar = new JProgressBar();
		add(mProgressBar, BorderLayout.SOUTH);
		mProgressBar.setStringPainted(true);
		
		//file chooser
		fc = new JFileChooser();
        fc.setFileFilter(new FileFilter());
		
		setVisible(true);
	}


	/**
	 * called when the enter button is pressed when the mTextFieeld is focused, or when the ok button is clicked
	 * (non-Javadoc)
	 * @see java.awt.event.ActionListener#actionPerformed(java.awt.event.ActionEvent)
	 */
	@Override
	public void actionPerformed(ActionEvent e) {
		if(e.getSource() == mExportButton)
			exportToCSV();
		else
			if(! mStartDateField.getText().isEmpty() && !mEndDateField.getText().isEmpty()){
				mProgressBar.setIndeterminate(true);
				try {
					preformSearch(mTextField.getText(), new Date(mStartDateField.getText()), new Date(mEndDateField.getText()));
				} catch (InvalidDateFormatException e1) {
					e1.printStackTrace();
				}
			}
			else{
				mProgressBar.setIndeterminate(true);
				preformSearch(mTextField.getText(), null, null);
			}
					
	}
	
	/**
	 * displays a JFileChooser dialog, and saves the current search results to an *.CSV file
	 * @return true is save was successfull
	 * @author ricky barrette
	 */
	private boolean exportToCSV() {
		if(fc.showDialog(SearchPanel.this, "Export") == JFileChooser.APPROVE_OPTION){
			int write = 0;
			boolean hasExtention;
			
			String filename = fc.getSelectedFile().toString();
		    String ext =filename.substring((filename.lastIndexOf(".")+1),filename.length());
			
		    hasExtention = ext.equalsIgnoreCase("csv");
			
			//file exists dialog
			if(new File(filename + (( ! hasExtention ) ? ".csv" : "") ).exists()){
				//default icon, custom title
				write = JOptionPane.showConfirmDialog(
				    mFrame, "Do you want to overwrite"+ filename + ((! hasExtention ) ? ".csv" : ""),
				    "Overwrite?",
				    JOptionPane.YES_NO_OPTION);
				System.out.print(write);
			}
			
			if(write == 0){
				//prep the data for proper csv format
				StringBuffer sb = new StringBuffer("Order Number,Time & date,Product Name,Order Amount,Amount Charged,Financial Status,Fulfillment Status,Customer Name,Customer Email,Customer Country");
				Scanner scan = new Scanner(mOrderPanel.getText());
				String[] parts;
				String line;
				while(scan.hasNext()){
					line = scan.nextLine();
					parts = line.split(", ");
					try {
						sb.append(parts[0]+","+parts[1]+","+parts[2]+","+parts[3]+","+parts[4]+","+parts[5]+","+parts[6]+","+parts[7]+","+parts[8]+","+parts[9]+"\n");
					} catch (Exception e) {
						sb.append(line+"\n");
					}
				}
				//write to the selceted file
				try {
					FileOutputStream theFile = new FileOutputStream(filename + (( ! hasExtention ) ? ".csv" : ""));
					theFile.write(sb.toString().getBytes());
					theFile.flush();
					theFile.close();
				} catch(IOException e) {
					e.printStackTrace();
					return false;
				}
				return true;
			}
		}
		return false;
	}

	/**
	 * executes a concurrent database search 
	 * @param search string
	 * @param start date
	 * @param end date
	 * @author ricky barrette
	 */
	private void preformSearch(final String search, final Date start, final Date end) {
		java.util.concurrent.Executors.newSingleThreadExecutor().submit(new Runnable() { 
			public void run() { 
				MainWindow.db.setOnProgressListerner(SearchPanel.this);
				
				ArrayList<Order> list = null;
				try {
					if((start != null) && (end != null)){
						list = MainWindow.db.search(search, start, end, mExclusiveCheckBox.isSelected());
					} else{
						list = MainWindow.db.search(search, mExclusiveCheckBox.isSelected());
					}
					
				} catch (SQLException e) {
					e.printStackTrace();
				} catch (IOException e) {
					e.printStackTrace();
				} catch (ClassNotFoundException e) {
					e.printStackTrace();
				}
				
				mOrderPanel.setOnProgressListerner(SearchPanel.this);
				mOrderPanel.displayOrders(list);
				
				mFrame.pack();
			}
		});
	}

	 /**
	  * called by MainWindow.db on progress update, or internally from this window to update the progress bar
	  * (non-Javadoc)
	  * @see com.TwentyCodes.java.OrderProcessor.ProgressListener#onProgressUpdate(int)
	  * @author ricky barrette
	  */
	@Override
	public void onProgressUpdate(String string, boolean isIndeterminate, int progress, int max) {
		mProgressBar.setMaximum(max);
		mProgressBar.setValue(progress);
		mProgressBar.setIndeterminate(isIndeterminate);
		mProgressBar.setString(string);
	}

	/**
	 * called when either of the date fields are clicked
	 * (non-Javadoc)
	 * @see java.awt.event.MouseListener#mouseClicked(java.awt.event.MouseEvent)
	 * @author ricky barrette
	 */
	@Override
	public void mouseClicked(MouseEvent e) {
		if(e.getSource() == mEndDateField){
			new DatePicker(DatePicker.END_DATE_RESULT, this);
		}
		
		if(e.getSource() == mStartDateField){
			new DatePicker(DatePicker.START_DATE_RESULT, this);
		}
	}


	@Override
	public void mousePressed(MouseEvent e) {
		// TODO Auto-generated method stub
		
	}


	@Override
	public void mouseReleased(MouseEvent e) {
		// TODO Auto-generated method stub
		
	}


	@Override
	public void mouseEntered(MouseEvent e) {
		// TODO Auto-generated method stub
		
	}


	@Override
	public void mouseExited(MouseEvent e) {
		// TODO Auto-generated method stub
		
	}

	/**
	 * called when the date picker returns a vaid date
	 * (non-Javadoc)
	 * @see com.TwentyCodes.java.OrderProcessor.DatePickerListener#onDatePicked(int, com.TwentyCodes.java.OrderProcessor.Date)
	 * @author ricky barrette
	 */
	@Override
	public void onDatePicked(int resultCode, Date date) {
		switch(resultCode){
			case DatePicker.START_DATE_RESULT:
				mStartDateField.setText(date.getYear()+"-"+date.getMonth()+"-"+date.getDay()+" "+date.getHour()+":"+date.getMinute()+":"+date.getSecond());
				break;
			case DatePicker.END_DATE_RESULT:
				mEndDateField.setText(date.getYear()+"-"+date.getMonth()+"-"+date.getDay()+" "+date.getHour()+":"+date.getMinute()+":"+date.getSecond());
				break;	
		}
		
	}
}