/**
 *                                                                            
 * Copyright (c) 2011, 2016 - 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 v1.0       
 * which accompanies this distribution, and is available at                  
 * http://www.eclipse.org/legal/epl-v10.html                                 
 *                                                                            
 * Contributors:   
 * Christophe Loetz (Loetz GmbH&Co.KG) - initial implementation 
 */
package org.eclipse.osbp.xtext.reportdsl.common.item;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.eclipse.birt.report.model.api.CellHandle;
import org.eclipse.birt.report.model.api.DataSetHandle;
import org.eclipse.birt.report.model.api.GridHandle;
import org.eclipse.birt.report.model.api.ReportItemHandle;
import org.eclipse.birt.report.model.api.RowHandle;
import org.eclipse.birt.report.model.api.SlotHandle;
import org.eclipse.birt.report.model.api.activity.SemanticException;
import org.eclipse.birt.report.model.api.elements.structures.ComputedColumn;
import org.eclipse.birt.report.model.api.util.StringUtil;
import org.eclipse.birt.report.model.core.Module;
import org.eclipse.birt.report.model.elements.interfaces.IReportItemModel;
import org.eclipse.birt.report.model.i18n.ThreadResources;
import org.eclipse.birt.report.model.util.CssPropertyConstants;
import org.eclipse.osbp.xtext.datamartdsl.DatamartAttribute;
import org.eclipse.osbp.xtext.datamartdsl.DatamartDefinition;
import org.eclipse.osbp.xtext.datamartdsl.util.DatamartAttributeUtil;
import org.eclipse.osbp.xtext.reportdsl.DatamartTableAttribute;
import org.eclipse.osbp.xtext.reportdsl.Element;
import org.eclipse.osbp.xtext.reportdsl.Grid;
import org.eclipse.osbp.xtext.reportdsl.GridCell;
import org.eclipse.osbp.xtext.reportdsl.GridRow;
import org.eclipse.osbp.xtext.reportdsl.StringBinder;
import org.eclipse.osbp.xtext.reportdsl.StringBinderValue;
import org.eclipse.osbp.xtext.reportdsl.Style;
import org.eclipse.osbp.xtext.reportdsl.TableAggregation;
import org.eclipse.osbp.xtext.reportdsl.TableAttribute;
import org.eclipse.osbp.xtext.reportdsl.TableValueElement;
import org.eclipse.osbp.xtext.reportdsl.UnitEnum;
import org.eclipse.osbp.xtext.reportdsl.jvmmodel.ReportGeneratorWorkSet;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.ibm.icu.util.ULocale;

import org.eclipse.birt.report.model.api.OdaDataSetHandle;

public class GridItem extends AContainerItem {

	private static final Logger LOGGER = LoggerFactory.getLogger(GridItem.class);
	private final GridHandle fItem;

	public GridItem(ReportGeneratorWorkSet workset, DataSetHandle dataSet, List<ComputedColumn> boundColumns, Grid grid) throws SemanticException {
		super(workset);
		int rowCount = grid.getRows().size();
		int columnCount = 0;
		for	(GridRow row : grid.getRows()) {
			columnCount = Math.max(columnCount, row.getCells().size());
		}
		fItem = workset.getFactory().newGridItem(null, columnCount, rowCount);
		List<Object> tableProperties = new ArrayList<>();
		HashSet<String> tableAttributeNameSet = new HashSet<String>();
		for (GridRow gridRow : grid.getRows()) {
			for (GridCell gridCell : gridRow.getCells()) {
				for (Element gridElement : gridCell.getElements()) {
					if (gridElement instanceof DatamartTableAttribute){
						TableValueElement tableValueElement = ((DatamartTableAttribute) gridElement).getColumn();
						if (tableValueElement instanceof TableAttribute){
							String attributeName = DatamartAttributeUtil.getAliasedAttributeName(((TableAttribute) tableValueElement).getValueRef());
							if (!tableAttributeNameSet.contains(attributeName)){
								tableProperties.add(tableValueElement);
								tableAttributeNameSet.add(attributeName);
							}
						} else {
							tableProperties.add(tableValueElement);
						}
					} else if (gridElement instanceof StringBinder){
						for (StringBinderValue element : ((StringBinder) gridElement).getElements()){
							if (element instanceof TableAttribute){
								String attributeName = DatamartAttributeUtil.getAliasedAttributeName(((TableAttribute) element).getValueRef());
								if (!tableAttributeNameSet.contains(attributeName)){
									tableProperties.add(element);
									tableAttributeNameSet.add(attributeName);
								}
							}
						}
					}
				}
			} 
		} 
		if (!tableProperties.isEmpty()){
			setDataSet(dataSet);
			List<ComputedColumn> requiredBoundColumns = new ArrayList<>();
			for (Object tableProperty : tableProperties) {
				TableAttribute tableAttribute = null;
				if (tableProperty instanceof TableAttribute){
					tableAttribute = (TableAttribute)tableProperty;
					addToRequiredBoundColumns(tableAttribute, boundColumns, requiredBoundColumns);
				}
			}
			setBoundColumns(requiredBoundColumns, tableProperties);
		}
	}
	
	private void addToRequiredBoundColumns(TableAttribute tableAttribute, List<ComputedColumn> boundColumns, List<ComputedColumn> requiredBoundColumns) {
		try {
			String tableAttributeName = DatamartAttributeUtil.getAliasedAttributeName(tableAttribute.getValueRef());
			for (ComputedColumn computedColumn : boundColumns) {
				if (computedColumn.getName().equalsIgnoreCase(tableAttributeName)){
					requiredBoundColumns.add(computedColumn);
					break;
				}
			}
		} catch (NullPointerException npe){
			LOGGER.error("NullPointerException on getting DatamartAttribute name!");
		}
	}

	@Override
	public ReportItemHandle getHandle() {
		return fItem;
	}

	@Override
	SlotHandle getSlotHandle() {
		return null;
	}

	public void applyRowStyle(int rowNo, Style style) {
		applyStyle(fWorkset.getDesign(), fItem.getRows().get(rowNo), style);
	}
	
	public void applyCellStyle(RowHandle rowHandle, int colNo, Style style) {
		applyStyle(fWorkset.getDesign(), rowHandle.getCells().get(colNo), style);
	}
	
	public void setRowHeight(int rowNo, double heightValue) throws SemanticException {
			String propValue = fWorkset.getLocalizedDoubleValue(fItem, heightValue);
			fItem.getRows().get(rowNo).setStringProperty(CssPropertyConstants.HEIGHT, propValue);
	}
	
	public CellItem getCell(int columnNo, int rowNo) throws SemanticException {
		RowHandle row = null;
		CellHandle cell = null;
		try {
			row = (RowHandle) fItem.getRows().get(rowNo);
			if	(row == null) {
				throw new SemanticException(fItem.getElement(), "can't resolve rowNo "+rowNo);
			}
		}
		catch (Exception e) {
			throw new SemanticException(fItem.getElement(), "can't resolve rowNo "+rowNo, e);
		}
		try {
			cell = (CellHandle)row.getCells().get(columnNo);
			if	(cell == null) {
				throw new SemanticException(fItem.getElement(), "can't resolve columnNo "+columnNo);
			}
		}
		catch (Exception e) {
			throw new SemanticException(fItem.getElement(), "can't resolve columnNo "+columnNo, e);
		}
		return new CellItem(fWorkset, cell);
	}
	
	public void setDataSet(DataSetHandle dataSet) {
		try {
			fItem.setDataSet(dataSet);
		} catch (SemanticException e) {
			LOGGER.error("{}", e);
		}
	}

	public void setBoundColumns(List<ComputedColumn> boundColumns, List<Object> tableProperties) {	// NOSONAR
		if	((boundColumns != null) && !boundColumns.isEmpty()) {
			List<ComputedColumn> shownColumns;

			// --- table details information: shown columns and maximum columns ---
			if	(tableProperties.size() == 0) {
				shownColumns = boundColumns;
			} else {
				shownColumns = new ArrayList<>();
				for	(Object tableProperty : tableProperties) {
					if	(tableProperty instanceof TableAggregation) {
						shownColumns.add(DataUtils.createComputedColumn((TableAggregation) tableProperty));
					} else if	(tableProperty instanceof TableAttribute) {
						addToShowColumns((TableAttribute)tableProperty, boundColumns, shownColumns);
					} else if (tableProperty instanceof StringBinder) {
						for (StringBinderValue binderValue : ((StringBinder)tableProperty).getElements()) {
							if (binderValue instanceof TableAttribute) {
								addToShowColumns((TableAttribute) binderValue, boundColumns, shownColumns);
							}
						}
					}
				}
			}
			// --- set all bound elements ---
			fItem.getElement().setProperty(IReportItemModel.BOUND_DATA_COLUMNS_PROP, shownColumns);
		}
	}

	private void addToShowColumns(TableAttribute tableAttribute, List<ComputedColumn> boundColumns, List<ComputedColumn> shownColumns) {
		for	(int columnNo=0; columnNo < boundColumns.size(); columnNo++) {
			DatamartAttribute datamartAttribute = tableAttribute.getValueRef();
			// attribute name modification as in org.eclipse.osbp.xtext.reportdsl.jvmmodel.ReportModelGenerator.addDatamartAttribute(...)
			// see also DatamartDSLJvmInferrer
			if	(boundColumns.get(columnNo).getName().equalsIgnoreCase(DatamartAttributeUtil.getAliasedAttributeName(datamartAttribute))) {
				shownColumns.add(boundColumns.get(columnNo));
				break;
			}
		}
	}
	

}
