/*
 *
 * Sample program for use with the Product
 * Licensed Materials  - Property of IBM
 * 5724-I66
 * (c) Copyright IBM Corp.  2006, 2009
 *   
 */
package com.ibm.wbit.tel.client.jsf.handler;

import java.util.HashMap;

import com.ibm.wbit.tel.client.jsf.bean.ToDoInstance;
import com.ibm.wbit.tel.client.jsf.infrastructure.FacesUtils;
import com.ibm.wbit.tel.client.jsf.infrastructure.SharedConstants;

/**
 * SubviewHandler can be used to set/get the subview ID of the subview that
 * should be shown next, according to a passed key. In case of determing a
 * message subview the passed key must be the QName of that message. In case of
 * determing a subview for custom properties subview the passed key must be the
 * component name for wich to show the custom properties.
 */
public class SubviewHandler {

	/**
	 * ID of next subview for custom properties
	 */
	private String subviewIDCustomProperties;

	/**
	 * ID of next subview for input message
	 */
	private String subviewIDInput;

	/**
	 * ID of next subview for output message
	 */
	private String subviewIDOutput;

	/**
	 * Map of available sub views.
	 */
	private HashMap<String, String> subviewMap;

	/**
	 * To get navigation info to be shown in the JSF pages.
	 */
	private String navigationInfo;

	/**
	 * Provide the next subview for input message according to passed
	 * toDoInstance. This subview might be a pre-defined or a generated one.
	 * 
	 * @param toDoInstance
	 *            for which to provide next subview input message
	 */
	public void nextSubviewInput(ToDoInstance toDoInstance) {

		// prefix for pre-defined subview
		StringBuilder keyPrefix = getHumanTaskID(toDoInstance);
		// suffix for pre-defined and generated subviews
		StringBuilder keySuffix = getSuffixSubview(toDoInstance, "input");
		// entire key for pre-defined subview
		keyPrefix.append(keySuffix.toString());

		// subview not pre-defined
		if (!nextSubviewInput(keyPrefix.toString())) {
			// entire key for generated subview
			keySuffix.insert(0, toDoInstance.getInputMessageTypeName());
			nextSubviewInput(keySuffix.toString());
		}
	}

	/**
	 * Provide the next subview for input message according to passed key.
	 * 
	 * @param key
	 * @return boolean indicating whether or not subview is available
	 */
	public boolean nextSubviewInput(String key) {
		Object obj = subviewMap.get(key);

		if (obj != null) {
			this.subviewIDInput = (String) obj;
		} else {
			this.subviewIDInput = null;
		}
		return this.subviewIDInput == null ? false : true;
	}

	/**
	 * Provide the next subview for output message according to passed
	 * toDoInstance. This subview might be a pre-defined or a generated one.
	 * 
	 * @param toDoInstance
	 *            for which to provide next subview output message
	 */
	public void nextSubviewOutput(ToDoInstance toDoInstance) {

		// prefix for pre-defined subview
		StringBuilder keyPrefix = getHumanTaskID(toDoInstance);
		// suffix for pre-defined and generated subviews
		StringBuilder keySuffix = getSuffixSubview(toDoInstance, "output");
		// entire key for pre-defined subview
		keyPrefix.append(keySuffix.toString());

		// subview not pre-defined
		if (!nextSubviewOutput(keyPrefix.toString())) {
			// entire key for generated subview
			keySuffix.insert(0, toDoInstance.getOutputMessageTypeName());
			nextSubviewOutput(keySuffix.toString());
		}
	}

	/**
	 * Provide the next subview for output message according to passed key.
	 * 
	 * @param key
	 * @return boolean indicating whether or not subview is available
	 */
	public boolean nextSubviewOutput(String key) {
		Object obj = subviewMap.get(key);

		if (obj != null) {
			this.subviewIDOutput = (String) obj;
		} else {
			this.subviewIDOutput = null;
		}
		return this.subviewIDOutput == null ? false : true;
	}

	/**
	 * Provide the next subview for custom properties according to passed key.
	 * 
	 * @param key
	 */
	public void nextSubviewCustomProperties(String key) {
		Object obj = subviewMap.get(key);

		if (obj != null) {
			this.subviewIDCustomProperties = (String) obj;
		} else {
			this.subviewIDCustomProperties = null;
		}
	}

	/**
	 * The ID which makes human tasks unique for template based approach.
	 * 
	 * @param toDoInstance
	 *            for which to get the unique ID
	 * @return ID which makes human tasks unique for template based approach.
	 */
	private StringBuilder getHumanTaskID(ToDoInstance toDoInstance) {

		StringBuilder ret = new StringBuilder();
		ret.append(FacesUtils.getHumanTaskID(toDoInstance));
		return ret;
	}

	/**
	 * Get suffix for subview. It is the same for pre-defined and generated
	 * subviews.
	 * 
	 * @param ToDoInstance
	 *            for which to get prefix
	 * @param String
	 *            inOut to indicate for which message of toDoInstance
	 * @return StringBuilder containing the suffix for subview
	 */
	private StringBuilder getSuffixSubview(ToDoInstance toDoInstance, String inOut) {

		StringBuilder ret = new StringBuilder();
		ret.append(inOut);
		ret.append(getToDoClientType(toDoInstance));
		return ret;
	}

	/**
	 * Get the client type for passed toDoInstance. Valid return values are
	 * defined in SharedConstancs as CLIENT_TYPE_*
	 * 
	 * @param ToDoInstance for which to get client type
	 * @return String client type for passed toDoInstance
	 */
	@SuppressWarnings("unchecked")
	public String getToDoClientType(ToDoInstance toDoInstance) {
		HashMap<String, String> cTypes = (HashMap<String, String>) FacesUtils.getManagedBeanInstance("toDosClientTypes", HashMap.class);

		return cTypes.get(getHumanTaskID(toDoInstance).toString()).toString();
	}

	/**
	 * Get ID of next subview
	 * 
	 * @return ID of next subview
	 */
	public String getSubviewIDCustomProperties() {
		return subviewIDCustomProperties;
	}

	/**
	 * Get ID of next subview for input message
	 * 
	 * @return ID of next subview for input message
	 */
	public String getSubviewIDInput() {
		return subviewIDInput;
	}

	/**
	 * Get ID of next subview for output message
	 * 
	 * @return ID of next subview for output message
	 */
	public String getSubviewIDOutput() {
		return subviewIDOutput;
	}

	/**
	 * Get the subViewMap
	 * 
	 * @return
	 */
	public HashMap<String, String> getSubviewMap() {
		return subviewMap;
	}

	/**
	 * Set subviewMap.
	 * 
	 * @param subviewMap
	 */
	public void setSubviewMap(HashMap<String, String> subviewMap) {
		this.subviewMap = subviewMap;
	}

	/**
	 * Set subviewIDCustomProperties.
	 * 
	 * @param subviewIDCustomProperties
	 */
	public void setSubviewIDCustomProperties(String subviewIDCustomProperties) {
		this.subviewIDCustomProperties = subviewIDCustomProperties;
	}

	/**
	 * Get navigation info to be shown in the JSF pages.
	 * 
	 * @return navigation info to be shown in the JSF pages.
	 */
	public String getNavigationInfo() {
		return navigationInfo;
	}

	/**
	 * Set navigation info to be shown in the JSF pages.
	 * 
	 * @param navigation
	 *            info to be shown in the JSF pages.
	 */
	public void setNavigationInfo(String navigationInfo) {
		this.navigationInfo = navigationInfo;
	}

	/**
	 * Boolean indicating if client type for passed toDoInstance is JSF.
	 * 
	 * @param toDoInstance
	 *            for which to check the client type
	 * @return boolean indicating if client type for passed toDoInstance is JSF
	 */
	protected boolean isJSFClientType(ToDoInstance toDoInstance) {
		boolean ret = false;

		if (toDoInstance != null) {
			if (getToDoClientType(toDoInstance).endsWith(SharedConstants.CLIENT_TYPE_JSF)) {
				ret = true;
			}
		}
		return ret;
	}
}
