/*******************************************************************************
 * Copyright (c) 2004 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *******************************************************************************/
package org.eclipse.wst.html.core.contentmodel.chtml;



import java.util.HashMap;
import java.util.Iterator;

import org.eclipse.wst.common.contentmodel.CMNamedNodeMap;
import org.eclipse.wst.common.contentmodel.CMNode;

/**
 */
abstract class DeclCollection implements CMNamedNodeMap {


	protected class DualMap {
		public DualMap() {
			super();
		}

		public DualMap(Object[] objects) {
			super();
			initialize(objects);
		}

		public int size() {
			return table.length;
		}

		public Object getValue(int key) {
			if (!isValidIndex(key))
				return null;
			return table[key];
		}

		public int getKey(Object value) {
			Integer keyObj = (Integer) map.get(value);
			if (keyObj == null)
				return ID_UNKNOWN;
			return keyObj.intValue();
		}

		protected void initialize(Object[] objects) {
			if (objects == null)
				return;
			table = objects;
			map = new HashMap();
			for (int key = 0; key < objects.length; key++) {
				Object value = table[key];
				map.put(value, new Integer(key));
			}
		}

		private Object[] table = null;
		private HashMap map = null;

		private boolean isValidIndex(int index) {
			return index >= 0 && index < table.length;
		}
	}

	protected class TolerantStringDualMap extends DualMap {
		public TolerantStringDualMap(String[] names) {
			super();
			Object[] objects = new Object[names.length];
			for (int i = 0; i < names.length; i++) {
				objects[i] = makeCanonicalForm(names[i]);
			}
			initialize(objects);
		}

		public int getKey(Object value) {
			try {
				String name = (String) value;
				return super.getKey(makeCanonicalForm(name));
			}
			catch (ClassCastException e) {
				return ID_UNKNOWN;
			}
		}

		private String makeCanonicalForm(String raw) {
			return raw.toUpperCase();
		}
	}

	private class DeclIterator implements Iterator {
		public DeclIterator() {
			maxid = fDecls.length - 1;
		}

		public boolean hasNext() {
			return id < maxid;
		}

		public Object next() {
			if (!hasNext())
				return null;
			return item(++id);
		}

		public void remove() { /* nothing should be done. */
		}

		private int id = -1;
		private int maxid = -1;
	}

	CMNode[] fDecls = null;
	protected final static boolean STRICT_CASE = false;
	protected final static boolean TOLERANT_CASE = true;
	protected final static int ID_UNKNOWN = -1;
	private DualMap fMap = null;

	/**
	 */
	public DeclCollection(String[] names, boolean tolerant) {
		super();
		fDecls = new CMNode[names.length];
		if (tolerant) {
			fMap = new TolerantStringDualMap(names);
		}
		else {
			fMap = new DualMap(names);
		}
	}

	/**
	 * @return org.eclipse.wst.common.contentmodel.CMNode
	 * @param id int
	 */
	protected abstract CMNode create(String name);

	/**
	 */
	public CMNamedNodeMap getDeclarations(String[] names) {
		CMNamedNodeMapImpl map = new CMNamedNodeMapImpl();
		for (int i = 0; i < names.length; i++) {
			String name = names[i];
			CMNode node = getNamedItem(name);
			if (node == null)
				continue;
			map.putNamedItem(name, node);
		}
		return map;
	}

	/**
	 * @param declarations com.ibm.sed.contentmodel.html.CMGroupImpl
	 * @param names java.util.Iterator
	 */
	public void getDeclarations(CMGroupImpl group, Iterator names) {
		while (names.hasNext()) {
			String entityName = (String) names.next();
			CMNode dec = getNamedItem(entityName);
			if (dec != null)
				group.appendChild(dec);
		}
	}

	/**
	 * Map name to id.
	 * @return int
	 * @param name java.lang.String
	 */
	protected int getID(String name) {
		return fMap.getKey(name);
	}

	/**
	 * getLength method
	 * @return int
	 */
	public int getLength() {
		return fDecls.length;
	}

	/**
	 * @return java.lang.String
	 * @param id int
	 */
	protected String getName(int id) {
		return (String) fMap.getValue(id);
	}

	/**
	 * getNamedItem method
	 * @return CMNode
	 * @param name java.lang.String
	 */
	public CMNode getNamedItem(String name) {
		int id = getID(name);
		if (!isValidID(id))
			return null;
		return item(id);
	}

	/**
	 * @return boolean
	 * @param id int
	 */
	private boolean isValidID(int id) {
		return id >= 0 && id < fDecls.length;
	}

	/**
	 * item method
	 * @return CMNode
	 * @param index int
	 */
	public CMNode item(int index) {
		if (!isValidID(index))
			return null;
		CMNode decl = fDecls[index];
		if (decl != null)
			return decl; // already exist.

		decl = create(getName(index));
		fDecls[index] = decl;
		return decl;
	}

	/**
	 */
	public Iterator iterator() {
		return new DeclIterator();
	}
}