package dfatool.strategy.elements;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;

import patterns.Observer;
import patterns.Subject;
import dfatool.io.AtomIOXML;
import dfatool.io.ChannelIOXML;
import dfatool.io.DatatypeIOXML;
import dfatool.io.IAtomIO;
import dfatool.io.IChannelIO;
import dfatool.io.IDatatypeIO;
import dfatool.io.IVarIO;
import dfatool.io.VarIOXML;

public class Description extends Subject implements Observer{
	
	IDatatypeIO types;
	IChannelIO channels;
	IVarIO vars;
	IAtomIO atoms;
	private static Description instance;
	private boolean isDescriptionReady;
	
	private Description(){
		isDescriptionReady = false;
		Configuration.getInstance().register(this);
	}
	
	public static Description createDescription(){
		if(instance == null)
			instance = new Description();
		return instance;
	}

	public void updateDatatype(Datatype t) {
		types.updateElement(t);
		alertAll();
	}
	
	public Datatype getDatatype(String name) {
		return types.getElement(name);
	}
	
	public void removeDatatype(Datatype t){
		types.removeElement(t);
		alertAll();
	}

	public void updateChannel(Channel c) {
		channels.updateElement(c);
		alertAll();
	}
	
	public void removeChannel(Channel c){
		channels.removeElement(c);
		alertAll();
	}
	
	public Channel getChannel(String name) {
		return channels.getElement(name);
	}

	public void updateVar(Var v) {
		vars.updateElement(v);
		alertAll();
	}
	
	public void removeVar(Var t){
		vars.removeElement(t);
		alertAll();
	}
	
	public Var getVar(String name){
		return vars.getElement(name);
	}

	public void updateAtom(Atom a) {
		atoms.updateElement(a);
		alertAll();
	}
	
	public void removeAtom(Atom a) {
		atoms.removeElement(a);
		alertAll();
	}
	
	public Atom getAtom(String name) {
		return atoms.getElement(name);
	}
	
	public Collection<Atom> getAtoms(){
		return atoms.listElements();
	}
	
	public Collection<Channel> getChannels(){
		return channels.listElements();
	}
	
	public Collection<Var> getVars(){
		return vars.listElements();
	}
	
	public Collection<Datatype> getDatatypes(){
		return types.listElements();
	}
	
//	public void removeElement(NamedElement t){
//		atoms.removeElement(new Atom(t.name, null, null));
//		vars.removeElement(new Var(t.name, null));
//		channels.removeElement(new Channel(t.name, null));
//		types.removeElement(new Datatype(t.name, null));
//	}
	
	public List<NamedElement> getList(){
		List<NamedElement> l = new ArrayList<NamedElement>();
		l.addAll(atoms.listElements());
		l.addAll(vars.listElements());
		l.addAll(types.listElements());
		l.addAll(channels.listElements());
		return l;
	}

	@Override
	public void update() {
		types = new DatatypeIOXML(Configuration.getInstance().getDatatypesFile());
		channels = new ChannelIOXML(Configuration.getInstance().getChannelsFile());
		vars = new VarIOXML(Configuration.getInstance().getVarsFile());
		atoms = new AtomIOXML(Configuration.getInstance().getAtomsFile());
		isDescriptionReady = true;
		alertAll();
	}
	
	public boolean isDescriptionReady() {
		return isDescriptionReady;
	}
	
	public void setDescriptionReady(boolean isDescriptionReady) {
		this.isDescriptionReady = isDescriptionReady;
	}
	
	
	

}
