package dtdxml;

import java.lang.String;
import java.lang.Short;
import java.util.Vector;
import java.util.Hashtable;

/*
 * This class define the element implementation with all the specification provided in the
 * XML DTD syntax.
 */ 
public class element
{
/*
 * This is the definition of the possible type for any element
 */ 
	public final static short EMPTY = 1; // Empty element
	public final static short ANY = 2; // Element of any type
	public final static short NODE = 3; // Element with some childs
	public final static short PCDATA = 4; // Simple element containing a string

/*
 * Optionality costants. These costants are defined to contrl the optianality
 * of the child elements
 */
	private final static short REQUIRED = 0; // reguired element (no ?, * or + suffix)
	private final static short QUESTION = 1; // Optional element
	private final static short STAR = 2; // 0 or more elements
	private final static short PLUS = 3; // 1 or more elements

/*
 * Name of the element as specified in the DTD
 */
	String name;

/*
 * Type of the element as specified in the DTD
 */
	short type;

/*
 * These two vectore define the eventually child that the element has and its optionality.
 * If the element is of MIXED type (type = PCDATA) this field contains the eventually type that
 * this element can assume.
 */
	Vector child = new Vector ();
	Hashtable childOption = new Hashtable ();

/*
 * Constructor
 *
 * @param n -> the name of the element as specified in the DTD
 * @param t -> the typeof the element as specified in the DTD
 */

	public element (String n, short t)
	{
		name = n;
		type = t;
   }

/*
 * Constructor. This don't need any type because it could be specified later
 *
 * @param n -> the name of the element as specified in the DTD
 */
	public element (String n)
	{
		name = n;
   }

/*
 * Set the type of element
 *
 * @param t-> the type of the element as specified in the DTD
 *
 * @return-> return the eventually old type of the element
 */
	public short setType (short t)
	{
		short ret = type;
		type = t;

		return ret;
	}

/*
 * Add a required child to the element. The child must be an alement previously declaraterd
 * because this is only a refernce to the object.
 *
 * @param e-> the element to add to the child vector
 */
	public void addChild (element e)
	{
		child.add (e);
		childOption.put (e.getName (), new Short (REQUIRED));
	}

/*
 * Add a child to the element. The child must be an alement previously declaraterd because this is
 * only a refernce to the object.
 *
 * @param e-> the element to add to the child vector
 * @param c-> character that indicate the optionality of this element.
 */
	public void addChild (element e, char c)
	{
		child.add (e);

		switch (c)
		{
			case '?':
			{
				childOption.put (e.getName (), new Short (QUESTION));
				break;
			}
			case '*': 
			{
				childOption.put (e.getName (), new Short (STAR));
				break;
			}
			case '+':
			{
				childOption.put (e.getName (), new Short (PLUS));
				break;
			}
			default: childOption.put (e.getName (), new Short (REQUIRED));
		}
	}

/*
 * Return the type of optinality of the child element apssed as parameter
 *
 * @parame e-> the child element to test the optionality
 *
 * @return -> the optionality of the passed element
 */
	public short getElementOption (element e)
   {
		return ((Short)(childOption.get (e.getName ()))).shortValue ();
	}

/*
 * Return the name of the element
 *
 * @return -> element's name
 */
	public String getName ()
	{
		return name;
	}

/*
 * Function that return if the element has one or more childs
 *
 * @return -> if element has childs
 */
	public boolean hasChild ()
	{
		return !child.isEmpty ();
	}

/*	public static void main (String args[])
	{
		element Gabriele = new element ("Gabriele");
		element Laura = new element ("Laura");
		element Ombretta = new element ("Ombretta");
		element Antonietta = new element ("Antonietta");

		Gabriele.addChild (Laura);
		Gabriele.addChild (Ombretta, '?');
		Gabriele.addChild (Antonietta, '*');

		if (Gabriele.getElementOption (Laura) == REQUIRED) System.out.println (Laura.getName()+"+-+REQUIRED");
		if (Gabriele.getElementOption (Ombretta) == PLUS) System.out.println (Ombretta.getName()+"+-+PLUS");
		if (Gabriele.getElementOption (Antonietta) == STAR) System.out.println (Antonietta.getName()+"+-+STAR");
	}*/
}