/*
 * Copyright (c) 2007, Going Dot Com Inc. All rights reserved.
 */

package jp.co.going.xbrl.sample;

import java.awt.BorderLayout;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.sql.Connection;
import java.util.ArrayList;
import java.util.Date;

import javax.swing.DefaultCellEditor;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JMenuItem;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JPopupMenu;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.ListSelectionModel;
import javax.swing.SwingUtilities;
import javax.swing.UIManager;
import javax.swing.event.TableModelEvent;
import javax.swing.event.TableModelListener;
import javax.swing.table.DefaultTableColumnModel;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableColumn;

import jp.co.going.xbrl.common.XbException;
import jp.co.going.xbrl.sample.dao.XbEtcAttributesDao;
import jp.co.going.xbrl.sample.dao.XbEtcDao;
import jp.co.going.xbrl.sample.dao.XbIdentifierDao;
import jp.co.going.xbrl.sample.dao.XbMeasureDao;
import jp.co.going.xbrl.sample.dao.obj.XbEtcAttributesObj;
import jp.co.going.xbrl.sample.dao.obj.XbEtcObj;
import jp.co.going.xbrl.sample.dao.obj.XbIdentifierObj;
import jp.co.going.xbrl.sample.dao.obj.XbMeasureObj;

/**
 * @author Masako Okayasu
 */
@SuppressWarnings("serial")
public class XbTableParamInput extends XbCommon implements ActionListener {

	private Connection conn = null;
	private XbIdentifierDao identifierDao = null;
	private XbMeasureDao measureDao = null;
	private XbEtcDao etcDao = null;
	private XbEtcAttributesDao etcAttrDao = null;

	private String param = null;
	private JButton addButton = new JButton("新規登録");

	private JTable table = null;
	private DefaultTableModel tableModel = null;
	private JPopupMenu popMenu = null;
	private JMenuItem[] popMenuItem = new JMenuItem[1];

	/**
	 * コンストラクタ
	 */
	public XbTableParamInput(Connection conn, String param) {
		this.conn = conn;
		this.param = param;

		setTitle("XBRL Toolkit : Input " + param);
		setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);

		try {
			UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
		} catch (Exception e) {
			e.printStackTrace();
		}

		identifierDao = XbIdentifierDao.getInstance(conn);
		measureDao = XbMeasureDao.getInstance(conn);
		etcDao = XbEtcDao.getInstance(conn);
		etcAttrDao = XbEtcAttributesDao.getInstance(conn);


		Container container = getContentPane();
		container.setLayout(new BorderLayout());

		JPanel HeaderPanel = new JPanel();
		HeaderPanel.setLayout(new BorderLayout());
		HeaderPanel.setPreferredSize(new Dimension(200, 23));

		HeaderPanel.add(new JLabel("　【 " + nameList.get(param) + " <" + param + "> 】"), BorderLayout.WEST);
		HeaderPanel.add(new JLabel("　　　*印： 必須項目"), BorderLayout.CENTER);
		HeaderPanel.add(addButton, BorderLayout.EAST);

		JPanel TablePanel = TablePanel();
		if(param.equals(MEASURE)) {
			MeasureFunc();
		}
		JPanel SubmitPanel = SubmitPanel();

		addButton.addActionListener(this);
		addButton.setPreferredSize(new Dimension(100, 22));
		submitButton.addActionListener(this);
		submitButton.setEnabled(false);
		closeButton.addActionListener(this);

		container.add(HeaderPanel, BorderLayout.NORTH);
		container.add(TablePanel, BorderLayout.CENTER);
		container.add(SubmitPanel, BorderLayout.SOUTH);

		pack();
	}

	/**
	 * measure入力欄の生成
	 */
	private void MeasureFunc() {
		table.getColumnModel().getColumn(2).setCellEditor(new DefaultCellEditor(unitCombo));
		table.setRowHeight(20);
	}

	/**
	 * 編集可能な一覧形式入力欄の生成
	 */
	private JPanel TablePanel() {
		JPanel TablePanel = new JPanel();

		try {
			String[] tableHeader = null;
			String[][] tableData = null;

			if(param.equals(IDENTIFIER)) {
				tableHeader = new String[]{"ID", "名称*", "ＵＲＩ", "値*"};

				ArrayList<XbIdentifierObj> temp = identifierDao.selectAll();
				tableData = new String[temp.size()][4];

				for(int i=0; i<temp.size(); i++) {
					XbIdentifierObj obj = temp.get(i);
					tableData[i] = new String[]{
							String.valueOf(obj.getIdentifier_id()),
							obj.getIdentifier_name(),
							obj.getSchema(),
							obj.getValue()
					};
			}	}
			else if(param.equals(MEASURE)) {
				tableHeader = new String[]{"ID", "名称*", "通貨フラグ*", "値*"};

				ArrayList<XbMeasureObj> temp = measureDao.selectAll();
				tableData = new String[temp.size()][4];

				for(int i=0; i<temp.size(); i++) {
					XbMeasureObj obj = temp.get(i);
					tableData[i] = new String[]{
							String.valueOf(obj.getMeasure_id()),
							obj.getMeasure_name(),
							obj.isMoney_flag() ? unitCombo.getItemAt(1).toString() : unitCombo.getItemAt(0).toString(),
							obj.getValue()
					};
			}	}
			else {
				tableHeader = new String[]{"ID", "名称*", "要素名*", "値", "属性名", "属性値"};

				ArrayList<XbEtcObj> temp1 = etcDao.selectAll(etcType.get(param));
				tableData = new String[temp1.size()][6];

				for(int i=0; i<temp1.size(); i++) {
					XbEtcObj obj1 = temp1.get(i);
					ArrayList<XbEtcAttributesObj> temp2 = etcAttrDao.selectAll(etcType.get(param), obj1.getEtc_id());

					XbEtcAttributesObj obj2 = null;
					if(temp2.size() > 0) {
						obj2 = (XbEtcAttributesObj)temp2.get(0);
					}

					tableData[i] = new String[]{
							String.valueOf(obj1.getEtc_id()),
							obj1.getEtc_name(),
							obj1.getName(),
							String.valueOf(obj1.getValue()),
							obj2 != null ? obj2.getName()  : null,
							obj2 != null ? obj2.getValue() : null
					};
			}	}

			tableModel = new DefaultTableModel(tableData, tableHeader) {
				public boolean isCellEditable(int row, int column) {
					if(column==0)
						return false;
					else
						return true;
			}	};

			table = new JTable(tableModel);
			table.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
			table.setToolTipText(TOOLTIP2);

			DefaultTableColumnModel columnModel = (DefaultTableColumnModel)table.getColumnModel();
			int tableWidth = 0;
			for(int i=0; i<columnModel.getColumnCount(); i++){
				TableColumn col = table.getColumnModel().getColumn(i);
				if(i==0) {
					col.setMinWidth(66);
					col.setMaxWidth(66);
				} else {
					col.setPreferredWidth(100);
					tableWidth = tableWidth + 100;
			}	}

			JScrollPane scroll = new JScrollPane(table);
			scroll.setPreferredSize(new Dimension(tableWidth + 70, 400));
			TablePanel.add(scroll);

			popMenu();
			setMouseAdapter();

		} catch (Exception ex) {
			ex.printStackTrace();
		}

		return TablePanel;
	}

	/**
	 * 右クリックメニューの生成
	 */
	private void popMenu() {
		popMenu = new JPopupMenu();
		popMenuItem[0] = new JMenuItem("削除");
		popMenuItem[0].addActionListener(this);
		popMenu.add(popMenuItem[0]);
	}

	/**
	 * MouseAdapterの登録
	 */
	private void setMouseAdapter() {
		table.addMouseListener(new MouseAdapter() {
			public void mousePressed(MouseEvent e) {
				if(SwingUtilities.isRightMouseButton(e)) {
					if(table.getSelectedRow() >= 0) {
						popMenu.show(e.getComponent(), e.getX(), e.getY());
		}	}	}	});

		tableModel.addTableModelListener(new TableModelListener() {
			public void tableChanged(TableModelEvent e) {
				submitButton.setEnabled(true);
		}	});
	}

	/**
	 * Button のイベントを取得
	 */
	public void actionPerformed(ActionEvent e) {
		Object source = e.getSource();

		if(source == popMenuItem[0]) {
			if(JOptionPane.showConfirmDialog(this, "削除してよろしいですか？") == JOptionPane.YES_OPTION) {
				tableModel.removeRow(table.getSelectedRow());
		}	}
		else if(source == addButton) {
			JFrame window = null;
			window = new XbFormParamInput(param, table);
			window.setLocationRelativeTo(null);
			window.setVisible(true);
		}
		else if(source == submitButton) {
			try {
				for(int i=0; i<table.getRowCount(); i++) {
					String strID = table.getValueAt(i,0).toString().trim();
					long ID = 0;
					if(!strID.equals("(自動採番)"))  ID = Long.valueOf(strID);

					if(param.equals(IDENTIFIER)) {
						if(ID==0 || identifierDao.select(ID) == null) {
							ID = identifierDao.getNextId();

							XbIdentifierObj obj = new XbIdentifierObj();
							obj.setIdentifier_id(ID);
							obj.setIdentifier_name(table.getValueAt(i,1).toString().trim());
							obj.setSchema(table.getValueAt(i,2).toString().trim());
							obj.setValue(table.getValueAt(i,3).toString().trim());
							obj.setCreation_date(new Date());
							identifierDao.insert(obj);
						}
					}
					else if(param.equals(MEASURE)) {
						if(ID==0 || measureDao.select(ID) == null) {
							ID = measureDao.getNextId();

							boolean moneyFlag = false;
							if(table.getValueAt(i,2).toString().trim().equals("通貨")) {
								moneyFlag = true;
							}

							XbMeasureObj obj = new XbMeasureObj();
							obj.setMeasure_id(ID);
							obj.setMeasure_name(table.getValueAt(i,1).toString().trim());
							obj.setMoney_flag(moneyFlag);
							obj.setValue(table.getValueAt(i,3).toString().trim());
							obj.setCreation_date(new Date());
							measureDao.insert(obj);
						}
					}
					else {
						if(ID==0 || etcDao.select(etcType.get(param), ID) == null) {
							ID = etcDao.getNextId(etcType.get(param));

							XbEtcObj obj = new XbEtcObj();
							obj.setEtc_type(etcType.get(param));
							obj.setEtc_id(ID);
							obj.setEtc_name(table.getValueAt(i,1).toString().trim());
							obj.setName(table.getValueAt(i,2).toString().trim());
							obj.setValue(table.getValueAt(i,3).toString().trim());
							obj.setCreation_date(new Date());
							etcDao.insert(obj);

							if(table.getValueAt(i,4) != null && !table.getValueAt(i,4).equals("")) {
								String attr_name  = table.getValueAt(i,4).toString().trim();
								String attr_value = table.getValueAt(i,5).toString().trim();

								if(!attr_name.equals("") && !attr_value.equals("")) {
									XbEtcAttributesObj attr_obj = new XbEtcAttributesObj();
									attr_obj.setEtc_type(etcType.get(param));
									attr_obj.setEtc_id(ID);
									attr_obj.setName(attr_name);
									attr_obj.setValue(attr_value);
									attr_obj.setCreation_date(new Date());
									etcAttrDao.insert(attr_obj);
                                }
                            }
						}
					}

					conn.commit();
					table.setValueAt(ID, i, 0);
				}

				JOptionPane.showMessageDialog(this, "データを登録しました。");
				submitButton.setEnabled(false);

			} catch (XbException err) {
				try {
					err.printStackTrace();
					conn.rollback();
				}
				catch (Exception ex) {
					ex.printStackTrace();
				}
			} catch (Exception ex) { 
				ex.printStackTrace();
		}	}
		else if(source == closeButton){
			this.setVisible(false);
		}
	}
}