/*******************************************************************************
 * This file is part of GECAMed.
 * 
 * GECAMed is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License (L-GPL) as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 * 
 * GECAMed 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 Lesser General Public License for more details.
 * 
 * You should have received a copy of the GNU Lesser General Public License (L-GPL)
 * along with GECAMed.  If not, see <http://www.gnu.org/licenses/>.
 * 
 * GECAMed is Copyrighted by the Centre de Recherche Public Henri Tudor (http://www.tudor.lu)
 * (c) CRP Henri Tudor, Luxembourg, 2008
 *******************************************************************************/
/**
 * 
 */
package lu.tudor.santec.gecamed.prescription.gui.util;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.event.ComponentAdapter;
import java.awt.event.ComponentEvent;

import javax.swing.Icon;
import javax.swing.ImageIcon;
import javax.swing.JLabel;
import javax.swing.JLayeredPane;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.SwingUtilities;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;

import lu.tudor.santec.gecamed.prescription.gui.PrescriptionIcons;

/**
 * Represents a modified textfield that is capable of showing a specific state: None, true & false.
 * if true, the backgorund changes to green and a green icon appears in the right corner.
 * if false, the background switches red and a red cross appears in the right.
 * 
 * Validation of the input must be done in the calling class.
 * 
 * @author martin.heinemann@tudor.lu
 * 
 * 
 * @version <br>
 *          $Log: VTextField.java,v $
 *          Revision 1.5  2010-03-30 10:42:16  troth
 *          Redesign of the prescription view - change icon manager class
 *
 *          Revision 1.4  2008-09-25 09:43:06  heinemann
 *          fixed copyrights
 *
 *          Revision 1.3  2008-01-15 13:40:47  heinemann
 *          better documentation
 *
 *          Revision 1.2  2007/03/02 08:28:38  hermen
 *          initial checkin after the merge of PatientModuleRebuild with the main HEAD
 *
 *          Revision 1.1.2.1  2006/12/14 09:34:01  heinemann
 *          many changes
 *
 */
public class VTextField extends JPanel {

	private static final long serialVersionUID = 1L;

	/* ------------------------------------------------------ */
	public static final int STATE_NONE  = -1;
	public static final int STATE_FALSE =  0;
	public static final int STATE_TRUE  =  1;
	/* ------------------------------------------------------ */
	
	private JLabel label = new JLabel();
	private JLayeredPane layeredPane = new JLayeredPane();

	private Icon falseIcon = PrescriptionIcons.getMediumIcon(PrescriptionIcons.ERROR);
	private Icon trueIcon  = PrescriptionIcons.getMediumIcon(PrescriptionIcons.BUTTON_OK);
	
	private Icon icon;
	
	private JLabel warning;
	/**
	 * in state = -1 -> display no icon in state = 0 -> display false icon in
	 * state = 1 -> display true icon
	 */
	private int state = STATE_NONE;
	
	
	private JTextField textField = new JTextField();

	public VTextField(String text) {
		/* ====================================================== */

		textField.setText(text);

		textField.setFont(new Font(textField.getFont().getName(), Font.BOLD, textField.getFont().getSize()+2));
		
		layeredPane.setPreferredSize(new Dimension((int) textField
				.getPreferredSize().getWidth(), (int) textField
				.getMinimumSize().getHeight()));

		layeredPane.add(textField);
		layeredPane.add(label);
		layeredPane.moveToFront(label);
		/* ------------------------------------------------------ */
		layeredPane.addComponentListener(new ComponentAdapter() {
			public void componentResized(ComponentEvent e) {
				/* ------------------------------------------------------ */
				paintImage();
				/* ------------------------------------------------------ */
				}
			});

		textField.getDocument().addDocumentListener(new DocumentListener() {

			public void changedUpdate(DocumentEvent e) {
				/* ============================================= */
				paintImage();
				/* ============================================= */
			}

			public void insertUpdate(DocumentEvent e) {
				/* ============================================= */
				paintImage();
				/* ============================================= */
			}

			public void removeUpdate(DocumentEvent e) {
				/* ============================================= */
				paintImage();
				/* ============================================= */
			}
		});
		
		
		/* ------------------------------------------------------ */
		// a label for the warning message
		warning = new JLabel();
		warning.setForeground(Color.RED);
		/* ------------------------------------------------------ */
		
		this.setLayout(new BorderLayout());
		this.add(layeredPane, BorderLayout.CENTER);
		/* ====================================================== */
	}

	
	/**
	 * 
	 */
	private void paintImage() {
// select the icon
		icon = null;
		if (state == STATE_FALSE)
			icon = falseIcon;
		else
			if (state == STATE_TRUE)
				icon = trueIcon;
			else
				icon = new ImageIcon();
		/* ------------------------------------------------------ */
		label.setIcon(icon);
		
		
		SwingUtilities.invokeLater(new Runnable() {

			public void run() {
				int abstandX = icon.getIconWidth();
				int abstandY = icon.getIconHeight();

				// textField.setBounds(abstandX, abstandY,
				// layeredPane.getWidth()
				// - abstandX, layeredPane.getHeight() - abstandY * 2);
				textField.setBounds(0, 0, layeredPane.getWidth(),
						layeredPane.getHeight());

				int posX = (int) textField.getBounds().getMaxX()
						- (abstandX + textField.getInsets().left) - 3;// /
																		// 2);

				int posY = (int) textField.getBounds().getMaxY()
						- ((abstandY / 2) + textField.getHeight() / 2);

				label.setBounds(posX, posY, icon.getIconWidth(), icon
						.getIconHeight());
				VTextField.this.updateUI();
				label.validate();
				label.updateUI();
			}
		});
	}

	
			
			
			
	public void setText(String t) {
		/* ====================================================== */
		textField.setText(t);
		/* ====================================================== */
	}
	
	public String getText() {
		/* ====================================================== */
		return textField.getText();
		/* ====================================================== */
	}
	
	public void setEditable(boolean b) {
		/* ====================================================== */
		textField.setEditable(b);
		textField.setBackground(Color.WHITE);
		/* ====================================================== */
	}
	
	/**
	 * defines, whether the state of the input is valid or not.
	 * 
	 * Use STATE_NONE, STATE_FALSE, STATE_TRUE
	 */
	public void setState(int state) {
		/* ====================================================== */
		this.state = state;
		paintImage();
		// mark red if false
		if (state == STATE_FALSE)  {
			textField.setBackground(new Color(255,204,204));
		} else
		// green if true
		if (state == STATE_TRUE) {
			textField.setBackground(new Color(206, 241, 188));
		}
		// white if none
		else
			textField.setBackground(Color.WHITE);
		
//		this.validate();
//		this.updateUI();
		/* ====================================================== */
	}

	/**
	 * Displays a red warning message below the textfield
	 * 
	 * @param msg
	 */
	public void setWarning(String msg) {
		/* ====================================================== */
		// first try to remove from panel
		try {
			/* ------------------------------------------------------ */
			this.remove(warning);
			/* ------------------------------------------------------ */
		} catch (Exception e) {
			e.printStackTrace();
		}
		warning.setText(msg);
		
		if (msg != null && !"".equals(msg)) {
			/* ------------------------------------------------------ */
			// add to the panel
			this.add(warning, BorderLayout.SOUTH);
			/* ------------------------------------------------------ */
		}
		this.validate();
		this.updateUI();
		/* ====================================================== */
	}
	
	
}
