/**
 * Copyright (c) 2011, 2015 - Lunifera GmbH (Gross Enzersdorf, Austria), Loetz GmbH&Co.KG (69115 Heidelberg, Germany)
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License 2.0 
 * which accompanies this distribution, and is available at
 * https://www.eclipse.org/legal/epl-2.0/
 *
 * SPDX-License-Identifier: EPL-2.0
 *
 * Contributors:
 *         Florian Pirchner - Initial implementation
 */
package org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.internal;

import java.util.ArrayList;
import java.util.Locale;

import org.eclipse.emf.common.util.EList;
import org.eclipse.osbp.ecview.core.common.editpart.IElementEditpart;
import org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart;
import org.eclipse.osbp.ecview.core.common.editpart.ILayoutEditpart;
import org.eclipse.osbp.ecview.core.common.model.core.YEmbeddable;
import org.eclipse.osbp.ecview.core.extension.model.extension.YAbsoluteLayout;
import org.eclipse.osbp.ecview.core.extension.model.extension.YAbsoluteLayoutCellStyle;
import org.eclipse.osbp.runtime.designer.api.IDesignerService.DesignEvent;
import org.eclipse.osbp.runtime.designer.api.IDesignerService.EventType;
import org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractLayoutPresenter;
import org.eclipse.osbp.vaadin.addons.absolutelayout.AbsoluteLayout;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.vaadin.server.Sizeable.Unit;
import com.vaadin.ui.Component;
import com.vaadin.ui.ComponentContainer;

// TODO: Auto-generated Javadoc
/**
 * This presenter is responsible to render a text field on the given layout.
 */
public class AbsoluteLayoutPresentation extends
		AbstractLayoutPresenter<ComponentContainer> {

	/** The Constant LOGGER. */
	private static final Logger LOGGER = LoggerFactory
			.getLogger(AbsoluteLayoutPresentation.class);

	/** The layout. */
	private AbsoluteLayout layout;
	
	/** The model access. */
	private ModelAccess modelAccess;

	/**
	 * The constructor.
	 * 
	 * @param editpart
	 *            The editpart of that presentation.
	 */
	public AbsoluteLayoutPresentation(IElementEditpart editpart) {
		super((ILayoutEditpart) editpart);
		this.modelAccess = new ModelAccess(
				(YAbsoluteLayout) editpart.getModel());
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractVaadinWidgetPresenter#doUpdateLocale(java.util.Locale)
	 */
	@Override
	protected void doUpdateLocale(Locale locale) {
		// no need to set the locale to the ui elements. Is handled by vaadin
		// internally.

		// update the captions
		applyCaptions();
	}

	/**
	 * Applies the labels to the widgets.
	 */
	protected void applyCaptions() {
	}

	/**
	 * Is called to refresh the UI. The element will be removed from the grid
	 * layout and added to it again afterwards.
	 */
	protected void refreshUI() {
		layout.removeAllComponents();

		for (IEmbeddableEditpart childPresentation : getChildren()) {
			YEmbeddable yChild = (YEmbeddable) childPresentation.getModel();
			addChildComponent(childPresentation,
					modelAccess.getCellStyle(yChild));
		}
	}

	/**
	 * Is called to create the child component and apply layouting defaults to
	 * it.
	 *
	 * @param editpart
	 *            the editpart
	 * @param yStyle
	 *            the y style
	 */
	protected void addChildComponent(IEmbeddableEditpart editpart,
			YAbsoluteLayoutCellStyle yStyle) {

		Component child = (Component) editpart.render(layout);
		layout.addComponent(child, toCssString(yStyle));

	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractLayoutPresenter#updateCellStyle(org.eclipse.osbp.ecview.core.common.model.core.YEmbeddable)
	 */
	public void updateCellStyle(YEmbeddable child) {
		// refresh the whole ui
		refreshUI();
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractLayoutPresenter#notify(org.eclipse.osbp.runtime.designer.api.IDesignerService.DesignEvent)
	 */
	@Override
	public void notify(DesignEvent event) {
		super.notify(event);

		if (getWidget() != null) {
			if (event.getType() == EventType.ENABLED) {
				layout.setResizable(true);
				layout.setUseAlignments(true);
			} else {
				layout.setResizable(false);
				layout.setUseAlignments(false);
			}
		}
	}

	/**
	 * To css string.
	 *
	 * @param yStyle
	 *            the y style
	 * @return the string
	 */
	private String toCssString(YAbsoluteLayoutCellStyle yStyle) {
		AbsoluteLayout.ComponentPosition pos = this.layout.new ComponentPosition();
		if (yStyle != null) {
			pos.setTop(toPositionFloat(yStyle.getTop()), Unit.PIXELS);
			pos.setBottom(toPositionFloat(yStyle.getBottom()), Unit.PIXELS);
			pos.setLeft(toPositionFloat(yStyle.getLeft()), Unit.PIXELS);
			pos.setRight(toPositionFloat(yStyle.getRight()), Unit.PIXELS);
			pos.setZIndex(yStyle.getZIndex());
		}
		return pos.getCSSString();
	}

	/**
	 * To position float.
	 *
	 * @param value
	 *            the value
	 * @return the float
	 */
	private Float toPositionFloat(int value) {
		return value == -1 ? null : Float.valueOf(value);
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractVaadinWidgetPresenter#doCreateWidget(java.lang.Object)
	 */
	@Override
	public ComponentContainer doCreateWidget(Object parent) {
		if (layout == null) {
			layout = new AbsoluteLayout();
			setupComponent(layout, getCastedModel());
			layout.setResizable(modelAccess.yLayout.isChildResizeEnabled());
			layout.setUseAlignments(isUseAlignments());

			associateWidget(layout, modelAccess.yLayout);

			if (modelAccess.isCssIdValid()) {
				layout.setId(modelAccess.getCssID());
			} else {
				layout.setId(getEditpart().getId());
			}

			if (modelAccess.isCssClassValid()) {
				layout.addStyleName(modelAccess.getCssClass());
			} else {
				layout.addStyleName(CSS_CLASS_CONTROL);
			}

			// creates the binding for the field
			createBindings(modelAccess.yLayout, layout, null);

			// initialize all children
			initializeChildren();

			// and now render children
			renderChildren(false);
		}

		return layout;
	}

	/**
	 * Checks if is use alignments.
	 *
	 * @return true, if is use alignments
	 */
	private boolean isUseAlignments() {
		return modelAccess.yLayout.isChildResizeEnabled()
				|| modelAccess.yLayout.isChildMoveEnabled();
	}

	/**
	 * Adds the children to the superclass and prevents rendering.
	 */
	private void initializeChildren() {
		setRenderLock(true);
		try {
			for (IEmbeddableEditpart editPart : getEditpart().getElements()) {
				super.add(editPart);
			}
		} finally {
			setRenderLock(false);
		}
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.ecview.core.common.presentation.IWidgetPresentation#getWidget()
	 */
	@Override
	public ComponentContainer getWidget() {
		return layout;
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.ecview.core.common.presentation.IWidgetPresentation#isRendered()
	 */
	@Override
	public boolean isRendered() {
		return layout != null;
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractLayoutPresenter#internalDispose()
	 */
	@Override
	protected void internalDispose() {
		try {
			for (IEmbeddableEditpart child : new ArrayList<IEmbeddableEditpart>(
					getChildren())) {
				child.dispose();
			}
			unrender();
		} finally {
			super.internalDispose();
		}
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractVaadinWidgetPresenter#doUnrender()
	 */
	@Override
	public void doUnrender() {
		if (layout != null) {

			// unbind all active bindings
			unbind();

			// remove assocations
			unassociateWidget(layout);

			// unrender the children
			unrenderChildren();

			layout = null;
		}
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractLayoutPresenter#internalAdd(org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart)
	 */
	@Override
	protected void internalAdd(IEmbeddableEditpart editpart) {
		YEmbeddable yChild = (YEmbeddable) editpart.getModel();
		addChildComponent(editpart, modelAccess.getCellStyle(yChild));
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractLayoutPresenter#internalRemove(org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart)
	 */
	@Override
	protected void internalRemove(IEmbeddableEditpart child) {
		if (layout != null && child.isRendered()) {
			layout.removeComponent((Component) child.getWidget());
		}

		child.unrender();
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractLayoutPresenter#internalInsert(org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart, int)
	 */
	@Override
	protected void internalInsert(IEmbeddableEditpart editpart, int index) {
		refreshUI();
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.runtime.web.ecview.presentation.vaadin.common.AbstractLayoutPresenter#internalMove(org.eclipse.osbp.ecview.core.common.editpart.IEmbeddableEditpart, int, int)
	 */
	@Override
	protected void internalMove(IEmbeddableEditpart editpart, int oldIndex,
			int newIndex) {
		refreshUI();
	}

	/* (non-Javadoc)
	 * @see org.eclipse.osbp.ecview.core.common.presentation.ILayoutPresentation#renderChildren(boolean)
	 */
	@Override
	public void renderChildren(boolean force) {
		if (force) {
			unrenderChildren();
		}

		refreshUI();
	}

	/**
	 * Will unrender all children.
	 */
	protected void unrenderChildren() {
		for (IEmbeddableEditpart editpart : getChildren()) {
			if (editpart.isRendered()) {
				editpart.unrender();
			}
		}
	}

	/**
	 * An internal helper class.
	 */
	private static class ModelAccess {
		
		/** The y layout. */
		private final YAbsoluteLayout yLayout;

		/**
		 * Instantiates a new model access.
		 *
		 * @param yLayout
		 *            the y layout
		 */
		public ModelAccess(YAbsoluteLayout yLayout) {
			super();
			this.yLayout = yLayout;
		}

		/**
		 * Gets the css class.
		 *
		 * @return the css class
		 * @see org.eclipse.osbp.ecview.core.ui.core.model.core.YCssAble#getCssClass()
		 */
		public String getCssClass() {
			return yLayout.getCssClass();
		}

		/**
		 * Returns true, if the css class is not null and not empty.
		 *
		 * @return true, if is css class valid
		 */
		public boolean isCssClassValid() {
			return getCssClass() != null && !getCssClass().equals("");
		}

		/**
		 * Gets the css id.
		 *
		 * @return the css id
		 * @see org.eclipse.osbp.ecview.core.ui.core.model.core.YCssAble#getCssID()
		 */
		public String getCssID() {
			return yLayout.getCssID();
		}

		/**
		 * Returns true, if the css id is not null and not empty.
		 *
		 * @return true, if is css id valid
		 */
		public boolean isCssIdValid() {
			return getCssID() != null && !getCssID().equals("");
		}

		/**
		 * Gets the cell styles.
		 *
		 * @return the cell styles
		 * @see org.eclipse.osbp.ecview.core.ui.core.model.extension.YAbsoluteLayout#getCellStyles()
		 */
		public EList<YAbsoluteLayoutCellStyle> getCellStyles() {
			return yLayout.getCellStyles();
		}

		/**
		 * Gets the cell style.
		 *
		 * @param element
		 *            the element
		 * @return the cell style
		 */
		public YAbsoluteLayoutCellStyle getCellStyle(YEmbeddable element) {
			return yLayout.getCellStyle(element);
		}
	}
}
