package lu.tudor.santec.gecamed.formeditor.gui.component;

import java.awt.BorderLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.awt.event.MouseListener;

import javax.swing.JCheckBox;
import javax.swing.JComponent;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.plaf.basic.BasicButtonListener;

import lu.tudor.santec.gecamed.formeditor.gui.FormWidgets;
import lu.tudor.santec.gecamed.formeditor.gui.controller.FormController;
import lu.tudor.santec.gecamed.formeditor.gui.model.FormEditorModel;
import lu.tudor.santec.gecamed.formeditor.gui.model.FormModel;
import lu.tudor.santec.i18n.Translatrix;

import org.jdom.Element;

import com.jgoodies.forms.layout.CellConstraints;

public class EditableCheckBox extends EditableComponent {

	private static final long serialVersionUID = 1L;

	public static final int LISTENER_METHOD_SIZE 	= 3;
	public static final int ACTION_PERFORMED 		= SUPER_LISTENER_METHOD_SIZE;
	public static final int STATE_CHANGED 			= SUPER_LISTENER_METHOD_SIZE + 1;
	public static final int ITEM_STATE_CHANGED 		= SUPER_LISTENER_METHOD_SIZE + 2;
	
	private JCheckBox startValueBox;
	
	public EditableCheckBox() 
	{
		component = new JCheckBox();
		component.setOpaque(false);
	}
	
	@Override
	public void init (CellConstraints constraints, FormEditorModel model, byte formModelType) 
	{
		startValueBox = new JCheckBox();
		startValueBox.setOpaque(false);
		
		super.init(constraints, model, formModelType);
	}
	
	@Override
	protected void initType()
	{
		/* remove the basic MouseListener - the component shouldn't be (un-)checked
		 * every time it is clicked in the editor, but only through the menu.
		 */
		for (MouseListener l : component.getMouseListeners()) 
		{
			if (l instanceof BasicButtonListener) 
			{
				component.removeMouseListener(l);
				break;
			}
		}
		
		// if the startValueBox is (un-)checked, check the component as well
		startValueBox.addActionListener(new ActionListener() {
			
			public void actionPerformed(ActionEvent e) 
			{
				((JCheckBox)component).setSelected(startValueBox.isSelected());
			}
		});
		
		super.initType();
	}


	@Override
	protected void addListenerMethodNames() {
		/* ======================================== */
		listenerMethodNames[ACTION_PERFORMED] 	= "actionPerformed";
		listenerMethodNames[STATE_CHANGED] 		= "stateChanged";
		listenerMethodNames[ITEM_STATE_CHANGED] = "itemStateChanged";
		/* ======================================== */
	}

	@Override
	public JComponent copyComponent(FormModel model) 
	{
		JCheckBox cb = (JCheckBox) this.component;
		
		FormController controller = new FormController(model);
		
		if (getScriptAt(ACTION_PERFORMED).length() > 0)
		{
			cb.addActionListener(controller);
			controller.setCodeAt(FormController.ACTION_PERFORMED, getScriptAt(ACTION_PERFORMED));
		}
		
		cb.addItemListener(controller);
		controller.setCodeAt(FormController.ITEM_STATE_CHANGED, getScriptAt(ITEM_STATE_CHANGED));
		
		if (getScriptAt(STATE_CHANGED).length() > 0)
		{
			cb.addChangeListener(controller);
			controller.setCodeAt(FormController.STATE_CHANGED, getScriptAt(STATE_CHANGED));
		}
		
		addDefaultListener(cb, controller);
		return cb;
	}

	@Override
	public String getComponentType() {
		return "checkbox";
	}

	@Override
	protected int getListenerMethodSize() {
		return LISTENER_METHOD_SIZE;
	}

	@Override
	public String getStructure() {
		return ((JCheckBox)component).getText();
	}

	@Override
	public String getText() {
		return String.valueOf(((JCheckBox)component).isSelected());
	}
	
	@Override
	public String getHistoryText()
	{
		if (((JCheckBox)component).isSelected())
			return " ";
		else
			return null;
	}

	@Override
	public void setStructure(String text) {
		((JCheckBox)component).setText(text);
	}

	@Override
	public void setText(String text) {
		((JCheckBox)component).setSelected(FormWidgets.parseBool(text, false));
	}
	
	@Override
	public Element getDataAsXML()
	{
		Element data 		= new Element(getKey());
		Element textElement = new Element(XML_ELEMENT_TEXT);
		String 	text 	 	= ((JCheckBox)component).getText();
		boolean selected 	= ((JCheckBox)component).isSelected();
		
		textElement.setText(text);
		data.addContent(textElement);
		data.setAttribute("selected", String.valueOf(selected));
		
		addDefaultProperties(data);
		return data;
	}

	@Override
	protected JComponent createCaptionText()
	{
		// start value
		JPanel innerPanel = new JPanel (new BorderLayout());
		innerPanel.setOpaque(false);

		startValueBox.setSelected(((JCheckBox)component).isSelected());
		
		innerPanel.add(startValueBox, BorderLayout.WEST);
		
		JTextField captionTxt = new JTextField(this.getStructure());
		captionTxt.addKeyListener(new KeyListener() {
			
			public void keyTyped(KeyEvent e) {}
			public void keyPressed(KeyEvent e) {}
			
			public void keyReleased(KeyEvent e) {
				/* ---------------------------------------- */
				setStructure(((JTextField)e.getSource()).getText());
				/* ---------------------------------------- */
			}
		});
		
		innerPanel.add(captionTxt, BorderLayout.CENTER);
		
		return innerPanel;
//		p.add(new NamedComponent(Translatrix.getTranslationString(
//				"formeditor.start_value"), innerPanel, true), cc.xy(2, 1));
//		
//		return p;
	}
	
	@Override
	public String getTypeTranslation () {
		/* ======================================== */
		return Translatrix.getTranslationString("formeditor.add_checkbox");
		/* ======================================== */
	}

	@Override
	public Boolean isComponentTypeStoredInDBByDefault () {
		return true;
	}
}
