package filemanager;

import com.one.AbstractFont;
import com.one.ExtGraphics;
import com.one.ModuleRegistry;
import com.one.PaintableObject;
import com.one.Renderer;
import com.one.TextProcessor;
import com.vmx.Locale;
import com.vmx.gkcCanvas;
import com.vmx.keyConfig;
import com.vmx.keyConfig.KeyInfo;
import java.util.Enumeration;
import java.util.Vector;
import javax.microedition.lcdui.Command;
import javax.microedition.lcdui.CommandListener;
import javax.microedition.lcdui.Displayable;
import javax.microedition.lcdui.Form;
import javax.microedition.lcdui.Graphics;
import javax.microedition.lcdui.TextField;

public class lstKeyConfig extends ListMenu implements CommandListener, MenuListener, ListStateListener
{
	public static final int MODE_ACTIONS = 0;
	public static final int MODE_KEYS = 1;

	protected class KeyInputCanvas extends PaintableObject
	{
		protected int width, height;
		protected AbstractFont font;

		protected String msg;
		protected int msgx, msgy;

		public KeyInputCanvas()
		{
			width = getWidth();
			height = getHeight();
			font = AbstractFont.getDefaultFont();

			msg = Locale.getString(this, Locale.PRESS_A_KEY);
			msgx = (width - font.stringWidth(msg)) / 2;
			msgy = (height - font.getHeight()) / 2;
		}

		public void paint(ExtGraphics g)
		{
			g.setColor(ColorScheme.colors[ColorScheme.back1]);
			g.fillRect(0, 0, width, height);

			g.setColor(ColorScheme.colors[ColorScheme.fore]);
			g.drawString(msg, msgx, msgy, Graphics.LEFT | Graphics.TOP);
		}

		public void keyReleased(int keyCode)
		{
			acceptKeyCode(keyCode);
		}
	}

	protected Object parent;
	protected MenuListener oldMML;
	protected Vector keys;
	protected int mode;

	protected Form form;
	protected TextField tfName;
	protected TextField tfAbbr;
	protected TextField tfKeyCode;
	protected boolean addnew;

	protected KeyInputCanvas canvas;

	protected Command cmdSelect = new Command(Locale.getString(this, Locale.SELECT_CMD), Command.OK, 1);
	protected Command cmdAdd = new Command(Locale.getString(this, Locale.ADD_CMD), Command.OK, 2);
	protected Command cmdEdit = new Command(Locale.getString(this, Locale.EDIT_CMD), Command.OK, 3);
	protected Command cmdDelete = new Command(Locale.getString(this, Locale.DELETE_CMD), Command.OK, 4);
	protected Command cmdBack = new Command(Locale.getString(this, Locale.BACK_CMD), Command.BACK, 5);

	protected Command cmdOK = new Command(Locale.getString(this, Locale.OK_CMD), Command.OK, 1);
	protected Command cmdEnter = new Command(Locale.getString(this, Locale.ENTER_CMD), Command.ITEM, 2);

	public lstKeyConfig()
	{
		setTitle(Locale.getString(this, Locale.KEYBOARD_CONFIG_CMD));

		keys = new Vector();

		setCommandListener(this);
		setStateListener(this);

		form = new Form(Locale.getString(this, Locale.KEY_EDITOR));

		tfName = new TextField(Locale.getString(this, Locale.NAME), "", 256, TextField.ANY);
		tfAbbr = new TextField(Locale.getString(this, Locale.ABBREVIATION), "", 256, TextField.ANY);
		tfKeyCode = new TextField(Locale.getString(this, Locale.KEY_CODE), "", 20, TextField.NUMERIC);

		form.append(tfName);
		form.append(tfAbbr);
		form.append(tfKeyCode);

		form.addCommand(cmdOK);
		form.addCommand(cmdEnter);
		form.addCommand(cmdBack);
		form.setCommandListener(this);

		canvas = new KeyInputCanvas();
	}

	public void show()
	{
		mode = MODE_ACTIONS;
		updateList(size() > 0 ? (KeyInfo)keys.elementAt(getSelectedIndex()) : null);

		oldMML = main.menu.listen;
		parent = main.menu.parent;
		main.dsp.setCurrent(this);
	}

	public void updateList(KeyInfo selectAfter)
	{
		keys.removeAllElements();
		deleteAll();

		Enumeration e = keyConfig.listKeys();
		KeyInfo key;

		if(mode == MODE_ACTIONS)
		{
			setSubTitle(Locale.getString(this, Locale.KEY_ASSIGNMENT), false);

			while(e.hasMoreElements())
			{
				key = (KeyInfo)e.nextElement();

				keys.addElement(key);
				append(formatKeyAction(key));

				if(key.equals(selectAfter))
				{
					setSelectedIndex(size() - 1);
				}
			}

			removeAllCommands();

			addCommand(cmdEdit);
			addCommand(cmdBack);

			if(size() > 0)
			{
				addCommand(cmdSelect);
			}
		}
		else if(mode == MODE_KEYS)
		{
			setSubTitle(Locale.getString(this, Locale.USER_KEYS), false);
			
			while(e.hasMoreElements())
			{
				key = (KeyInfo)e.nextElement();

				if(true) // key.hashCode() >= keyConfig.ID_USER)
				{
					keys.addElement(key);
					append(formatKeyAbbreviation(key));
					
					if(key.equals(selectAfter))
					{
						setSelectedIndex(size() - 1);
					}
				}
			}

			removeAllCommands();

			addCommand(cmdAdd);
			addCommand(cmdBack);

			if(size() > 0)
			{
				addCommand(cmdEdit);
				addCommand(cmdDelete);
			}
		}
	}

	protected String getKeyName(KeyInfo key)
	{
		String name = key.getName();

		if(name.endsWith(keyConfig.HOT_KEY_SUFFIX))
		{
			return Locale.getString(this, Locale.HOT_KEY_NAME, TextProcessor.getString(this, name.substring(0, name.length() - 1).trim()));
		}
		else if(name.endsWith(keyConfig.HELD_KEY_SUFFIX))
		{
			return Locale.getString(this, Locale.HELD_KEY_NAME, TextProcessor.getString(this, name.substring(0, name.length() - 1).trim()));
		}
		else
		{
			return TextProcessor.getString(this, name);
		}
	}

	protected String formatKeyAction(KeyInfo key)
	{
		int action = keyConfig.getAction(key);

		if(action >= Locale.FAV_MOD_NUMS && action < Locale.FAV_MOD_NUMS + 10 &&
		   options.favmodules[action - Locale.FAV_MOD_NUMS].length() > 0)
		{
			return getKeyName(key) + ": " + ModuleRegistry.getModuleName(options.favmodules[action - Locale.FAV_MOD_NUMS]);
		}
		else
		{
			return getKeyName(key) + ": " + Locale.getString(this, action);
		}
	}

	protected String formatKeyAbbreviation(KeyInfo key)
	{
		String name = getKeyName(key);
		
		if(key.getAbbreviation().equals(name))
		{
			return getKeyName(key);
		}
		else
		{
			return getKeyName(key) + " (" + key.getAbbreviation() + ")";
		}
	}

	protected void acceptKeyCode(int keyCode)
	{
		tfKeyCode.setString(Integer.toString(keyCode));

		if(addnew)
		{
			tfName.setString(canvas.getKeyName(keyCode));
			tfAbbr.setString(canvas.getKeyName(keyCode));
		}

		main.dsp.setCurrent(form);
	}

	public void commandAction(Command c, Displayable dp)
	{
		if(dp instanceof Renderer)
		{
			PaintableObject po = ((Renderer)dp).getCurrent();

			if(po == this)
			{
				if(mode == MODE_ACTIONS)
				{
					if(c == cmdSelect)
					{
						main.menu.listen = this;
						main.menu.parent = this;
						main.menu.setType(cvsMenu.MENU_SELECT_ACTION);
						main.dsp.setCurrent(main.menu);
					}
					else if(c == cmdEdit)
					{
						mode = MODE_KEYS;
						updateList(size() > 0 ? (KeyInfo)keys.elementAt(getSelectedIndex()) : null);
					}
					else if(c == cmdBack)
					{
						main.menu.listen = oldMML;
						main.dsp.setCurrent(parent);
					}
				}
				else if(mode == MODE_KEYS)
				{
					if(c == cmdAdd)
					{
						addnew = true;

//						tfName.setString(AuxClass.timeToFileName(-1));
//						tfKeyCode.setString("0");
//
//						String s = Long.toString(System.currentTimeMillis(), Character.MAX_RADIX);
//						tfAbbr.setString(s.substring(s.length() - 2));
//
//						main.dsp.setCurrent(form);

						main.dsp.setCurrent(canvas);
						
					}
					else if(c == cmdEdit)
					{
						addnew = false;

						KeyInfo key = (KeyInfo)keys.elementAt(getSelectedIndex());

						int code = key.getCode();
						String name = key.getName();

						if(name.endsWith(keyConfig.HOT_KEY_SUFFIX))
						{
							code &= ~gkcCanvas.KEY_HOT;
						}
						else if(name.endsWith(keyConfig.HELD_KEY_SUFFIX))
						{
							code &= ~gkcCanvas.KEY_HELD;
						}

						tfName.setString(name);
						tfAbbr.setString(key.getAbbreviation());
						tfKeyCode.setString(Integer.toString(code));

						main.dsp.setCurrent(form);
					}
					else if(c == cmdDelete)
					{
						int index = getSelectedIndex();

						keyConfig.deleteKey((KeyInfo)keys.elementAt(index));
						delete(index);
					}
					else if(c == cmdBack)
					{
						mode = MODE_ACTIONS;
						updateList(size() > 0 ? (KeyInfo)keys.elementAt(getSelectedIndex()) : null);
					}
				}
			}
		}
		else if(dp == form)
		{
			if(c == cmdEnter)
			{
				main.dsp.setCurrent(canvas);
				return;
			}
			else if(c == cmdOK)
			{
				int code = Integer.parseInt(tfKeyCode.getString());
				String name = tfName.getString();

				if(code > 0)
				{
					if(name.endsWith(keyConfig.HOT_KEY_SUFFIX))
					{
						code |= gkcCanvas.KEY_HOT;
					}
					else if(name.endsWith(keyConfig.HELD_KEY_SUFFIX))
					{
						code |= gkcCanvas.KEY_HELD;
					}
				}
				else if(name.endsWith(keyConfig.HOT_KEY_SUFFIX) || name.endsWith(keyConfig.HELD_KEY_SUFFIX))
				{
					name = name.substring(0, name.length() - 1);
				}
				
				if(addnew)
				{
					KeyInfo key = keyConfig.addKey(code, name, tfAbbr.getString(), Locale.KEY_NO_ACTION, false);

					keys.addElement(key);
					append(formatKeyAbbreviation(key));

					setSelectedIndex(size() - 1);
				}
				else
				{
					KeyInfo key = (KeyInfo)keys.elementAt(getSelectedIndex());

					key.setCode(code);
					key.setName(name);
					key.setAbbreviation(tfAbbr.getString());

					setString(formatKeyAbbreviation((KeyInfo)keys.elementAt(getSelectedIndex())), getSelectedIndex());
				}
			}

			main.dsp.setCurrent(this);
		}
	}

	public void menuAction(int action)
	{
		keyConfig.setAction((KeyInfo)keys.elementAt(getSelectedIndex()), action);
		main.menu.ret();

		//updateList((KeyInfo)keys.elementAt(getSelectedIndex()));
		setString(formatKeyAction((KeyInfo)keys.elementAt(getSelectedIndex())), getSelectedIndex());
	}

	public void listStateChanged(ListMenu list, int action)
	{
		if(action == ELEMENT_ADDED || action == ELEMENT_DELETED)
		{
			if(size() > 0)
			{
				if(mode == MODE_ACTIONS)
				{
					addCommand(cmdSelect);
				}
				else if(mode == MODE_KEYS)
				{
					addCommand(cmdEdit);
					addCommand(cmdDelete);
				}
			}
			else
			{
				if(mode == MODE_ACTIONS)
				{
					removeCommand(cmdSelect);
				}
				else if(mode == MODE_KEYS)
				{
					removeCommand(cmdEdit);
					removeCommand(cmdDelete);
				}
			}
		}
	}
}
