package com.ejie.aa94a.view;

import java.io.FileInputStream;
import java.io.InputStream;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Properties;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.ss.usermodel.ClientAnchor;
import org.apache.poi.ss.usermodel.CreationHelper;
import org.apache.poi.ss.usermodel.Drawing;
import org.apache.poi.ss.usermodel.IndexedColors;
import org.apache.poi.ss.usermodel.Picture;
import org.apache.poi.ss.util.CellRangeAddress;
import org.apache.poi.util.IOUtils;
import org.apache.poi.xssf.usermodel.XSSFCell;
import org.apache.poi.xssf.usermodel.XSSFFont;
import org.apache.poi.xssf.usermodel.XSSFRow;
import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.springframework.context.i18n.LocaleContextHolder;
import org.springframework.context.support.ReloadableResourceBundleMessageSource;

import com.ejie.aa94a.constantes.Constantes;
import com.ejie.aa94a.model.calculo.Bobina;
import com.ejie.aa94a.model.calculo.Estiba;
import com.ejie.aa94a.model.calculo.Resultado;
import com.ejie.aa94a.model.calculo.Transporte;
import com.ejie.aa94a.model.config.Configuracion;
import com.ejie.aa94a.utils.Utilidades;

public class ExcelResultadoView extends BobinasAbstractExcelView {

	private Properties appConfiguration;
	private ReloadableResourceBundleMessageSource messageSource;

	/**
	 * @return the appConfiguration
	 */
	public Properties getAppConfiguration() {
		return appConfiguration;
	}

	/**
	 * @param appConfiguration
	 *            the appConfiguration to set
	 */
	public void setAppConfiguration(Properties appConfiguration) {
		this.appConfiguration = appConfiguration;
	}

	/**
	 * @return the messageSource
	 */
	public ReloadableResourceBundleMessageSource getMessageSource() {
		return messageSource;
	}

	/**
	 * @param messageSource
	 *            the messageSource to set
	 */
	public void setMessageSource(
			ReloadableResourceBundleMessageSource messageSource) {
		this.messageSource = messageSource;
	}

	/**
	 * Obtiene la descripción del literal en el idioma indicado
	 * 
	 * @param code
	 *            String
	 * @param locale
	 *            Locale
	 * @return String
	 */
	private String getLiteral(String code, Locale locale) {
		return this.messageSource.getMessage(code, null, locale);
	}

	@Override
	protected void buildExcelDocument(Map model, XSSFWorkbook workbook,
			HttpServletRequest request, HttpServletResponse response)
			throws Exception {
		Resultado resultado = (Resultado) model.get("resultado");
		// Locale locale = LocaleContextHolder.getLocale();
		this.setMessageSource((ReloadableResourceBundleMessageSource) model
				.get("messageSource"));
		this.setAppConfiguration((Properties) model.get("appConfiguration"));
		XSSFSheet excelSheet = workbook.createSheet("Resultado");
		excelSheet.setColumnWidth(0, 4000);
		excelSheet.setColumnWidth(1, 9000);
		excelSheet.setColumnWidth(2, 9000);
		excelSheet.setColumnWidth(3, 9000);
		excelSheet.setColumnWidth(4, 9000);

		// //////////////////
		// Prepara Imagenes//
		// //////////////////
		if (resultado.isMostrarGraficos()) {
			preparaImagenes(workbook, excelSheet, resultado);
		}
		preparaDatosSimulacion(workbook, excelSheet, resultado);
	}

	/**
	 * 
	 * @param workbook
	 *            XSSFWorkbook
	 * @param excelSheet
	 *            XSSFSheet
	 * @param resultado
	 *            Resultado
	 */
	private void preparaImagenes(XSSFWorkbook workbook, XSSFSheet excelSheet,
			Resultado resultado) throws Exception {
		Locale locale = LocaleContextHolder.getLocale();
		Transporte transporte = resultado.getTransporte();
		List<Bobina> bobinas = transporte.getBobinas();
		String rutaDatos = (String) this.appConfiguration.get("ruta.image");
		// Returns an object that handles instantiating concrete classes
		CreationHelper helper = workbook.getCreationHelper();
		// Creates the top-level drawing patriarch.
		Drawing drawing = excelSheet.createDrawingPatriarch();
		// /////////////////////////////////////////////////////
		// IMAGEN RESULTADO
		// /////////////////////////////////////////////////////
		InputStream inputStream = new FileInputStream(rutaDatos
				+ resultado.getGrafico());
		// Get the contents of an InputStream as a byte[].
		byte[] bytes = IOUtils.toByteArray(inputStream);
		// Adds a picture to the workbook
		int pictureIdx = workbook.addPicture(bytes,
				XSSFWorkbook.PICTURE_TYPE_PNG);
		// close the input stream
		inputStream.close();

		// Create an anchor that is attached to the worksheet
		ClientAnchor anchorResultadoGrafico = helper.createClientAnchor();
		// set top-left corner for the image
		anchorResultadoGrafico.setCol1(2);
		// anchorResultadoGrafico.setCol2(4);
		anchorResultadoGrafico.setRow1(10 + bobinas.size());
		// anchorResultadoGrafico.setRow2(6);
		// Creates a picture
		Picture pictResultado = drawing.createPicture(anchorResultadoGrafico,
				pictureIdx);
		// Reset the image to the original size
		// pictResultado.resize();
		pictResultado.resize(0.75);
		// ///////////////////////////////////////////////////////////
		// FIN IMAGEN RESULTADO
		// ///////////////////////////////////////////////////////////

		List<Estiba> estibas = resultado.getSolucion().getEstibas();
		int filaPrimeraEstiba = 19 + bobinas.size();
		for (int i = 0; i < estibas.size(); i++) {
			/*
			 * String textoEstibas = (locale.equals(Constantes.LOCALE_EU)) ?
			 * estibas .get(i).getDescEu() : estibas.get(i).getDescEs();
			 */
			String imagenEstibas = (locale.equals(Constantes.LOCALE_EU)) ? estibas
					.get(i).getImagenEu() : estibas.get(i).getImagenEs();
			InputStream inputStreamEstiba = new FileInputStream(rutaDatos
					+ imagenEstibas);

			byte[] bytesEstiba = IOUtils.toByteArray(inputStreamEstiba);
			// Adds a picture to the workbook
			int pictureIdxEstiba = workbook.addPicture(bytesEstiba,
					XSSFWorkbook.PICTURE_TYPE_PNG);
			// close the input stream
			inputStreamEstiba.close();

			// Create an anchor that is attached to the worksheet
			ClientAnchor anchorEstiba = helper.createClientAnchor();
			// set top-left corner for the image
			anchorEstiba.setCol1(3);
			anchorEstiba.setRow1(filaPrimeraEstiba + i * 3);
			// Creates a picture
			Picture pictureEstiba = drawing.createPicture(anchorEstiba,
					pictureIdxEstiba);
			// Reset the image to the original size
			pictureEstiba.resize(3.5);
		}

		// /////////////////////////////////////////////////////
		// IMAGEN RECOMENDACION
		// /////////////////////////////////////////////////////

		InputStream inputStreamRecomendacion = new FileInputStream(rutaDatos
				+ Constantes.IMG_RECOMENDACION);

		byte[] bytesRecomendacion = IOUtils
				.toByteArray(inputStreamRecomendacion);
		// Adds a picture to the workbook
		int pictureIdxRecomendacion = workbook.addPicture(bytesRecomendacion,
				XSSFWorkbook.PICTURE_TYPE_PNG);
		// close the input stream
		inputStreamRecomendacion.close();

		// Create an anchor that is attached to the worksheet
		ClientAnchor anchorRecomendacion = helper.createClientAnchor();
		// set top-left corner for the image
		anchorRecomendacion.setCol1(0);
		anchorRecomendacion.setRow1(27 + bobinas.size() + estibas.size() * 3);
		// Creates a picture
		Picture pictureRecomendacion = drawing.createPicture(
				anchorRecomendacion, pictureIdxRecomendacion);
		// // Reset the image to the original size
		pictureRecomendacion.resize(2.0);
	}

	/**
	 * Prepara la vista para el excel con lso datos del resutlado de la
	 * simulación
	 * 
	 * @param workbook
	 * @param excelSheet
	 * @param resultado
	 */
	public void preparaDatosSimulacion(XSSFWorkbook workbook,
			XSSFSheet excelSheet, Resultado resultado) {
		Locale locale = LocaleContextHolder.getLocale();
		Transporte transporte = resultado.getTransporte();
		List<Bobina> bobinas = transporte.getBobinas();
		List<Estiba> estibas = resultado.getSolucion().getEstibas();
		transporte.setVehiculo(Configuracion.getVehiculo(transporte
				.getVehiculo().getCodigo()));
		transporte.setTipoSujecion(Configuracion.getTipoSujecion(transporte
				.getTipoSujecion().getCodigo()));
		// TEXTO DE LA SOLUCION
		String textoVehiculo = (locale.equals(Constantes.LOCALE_EU)) ? transporte
				.getVehiculo().getDescEu() : transporte.getVehiculo()
				.getDescEs();

		String textoTipoSujecion = (locale.equals(Constantes.LOCALE_EU)) ? transporte
				.getTipoSujecion().getDescEu() : transporte.getTipoSujecion()
				.getDescEs();

		String textoDescTransporte = (locale.equals(Constantes.LOCALE_EU)) ? resultado
				.getTipoDistancia().getDescEu() : resultado.getTipoDistancia()
				.getDescEs();

		CellStyle styleTitulo = workbook.createCellStyle();
		styleTitulo.setFillForegroundColor(IndexedColors.BLUE.getIndex());
		styleTitulo.setFillPattern(CellStyle.SOLID_FOREGROUND);
		styleTitulo.setWrapText(true);
		styleTitulo.setAlignment(CellStyle.ALIGN_CENTER);
		XSSFFont fontTitulo = workbook.createFont();
		fontTitulo.setColor(IndexedColors.WHITE.getIndex());
		fontTitulo.setFontHeightInPoints((short) 12);
		fontTitulo.setBold(true);
		styleTitulo.setFont(fontTitulo);

		CellStyle styleNegrita = workbook.createCellStyle();
		styleNegrita.setWrapText(true);
		styleNegrita.setAlignment(CellStyle.ALIGN_LEFT);
		XSSFFont fontNegrita = workbook.createFont();
		fontNegrita.setBold(true);
		styleNegrita.setFont(fontNegrita);

		CellStyle styleNegritaCenter = workbook.createCellStyle();
		styleNegritaCenter.setWrapText(true);
		styleNegritaCenter.setAlignment(CellStyle.ALIGN_CENTER);
		XSSFFont fontNegritaCenter = workbook.createFont();
		fontNegritaCenter.setBold(true);
		styleNegritaCenter.setFont(fontNegritaCenter);

		CellStyle styleNormal = workbook.createCellStyle();
		styleNormal.setWrapText(true);
		styleNormal.setAlignment(CellStyle.ALIGN_LEFT);
		XSSFFont font = workbook.createFont();
		styleNormal.setFont(font);

		CellStyle styleNormalCenter = workbook.createCellStyle();
		styleNormalCenter.setWrapText(true);
		styleNormalCenter.setAlignment(CellStyle.ALIGN_CENTER);
		XSSFFont fontCenter = workbook.createFont();
		styleNormalCenter.setFont(fontCenter);

		int fila = 0;
		// TITULO DATOS SIMULACION
		XSSFRow row = excelSheet.createRow(fila);
		XSSFCell cell = row.createCell(0);
		cell.setCellValue(this
				.getLiteral(Constantes.LABEL_DATOS_TITULO, locale));
		cell.setCellStyle(styleTitulo);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		// VEHICULO
		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_DATOS_VEH, locale));
		cell.setCellStyle(styleNegrita);

		cell = row.createCell(1);
		cell.setCellValue(textoVehiculo);
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 1,
				(short) 4));

		// TIPO SUJECCION
		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(getLiteral(Constantes.LABEL_DATOS_TIPOSUJ, locale));
		cell.setCellStyle(styleNegrita);

		cell = row.createCell(1);
		cell.setCellValue(textoTipoSujecion);
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 1,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue("");
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		// RESULTADO SIMULACION
		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_SOL_TITULO1, locale));
		cell.setCellStyle(styleTitulo);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		// POSICIONAMIENTO BOBINAS
		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_SOL_TITULO3, locale));
		cell.setCellStyle(styleNegritaCenter);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		// DATOS DE LA SOLUCION DEL TRANSPORTE
		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(getLiteral(Constantes.LABEL_SOL_ID, locale));
		cell.setCellStyle(styleNegritaCenter);

		cell = row.createCell(1);
		cell.setCellValue(getLiteral(Constantes.LABEL_SOL_ANCHURA, locale));
		cell.setCellStyle(styleNegritaCenter);

		cell = row.createCell(2);
		cell.setCellValue(getLiteral(Constantes.LABEL_SOL_DIAMETROEXT, locale));
		cell.setCellStyle(styleNegritaCenter);

		cell = row.createCell(3);
		cell.setCellValue(getLiteral(Constantes.LABEL_SOL_PESO, locale));
		cell.setCellStyle(styleNegritaCenter);

		cell = row.createCell(4);
		cell.setCellValue(getLiteral(Constantes.LABEL_SOL_DISTANCIA, locale));
		cell.setCellStyle(styleNegritaCenter);

		for (int i = 0; i < bobinas.size(); i++) {
			fila++;
			row = excelSheet.createRow(fila);
			cell = row.createCell(0);
			cell.setCellValue(bobinas.get(i).getPosicion().getIdentificacion());
			cell.setCellStyle(styleNormalCenter);

			cell = row.createCell(1);
			cell.setCellValue(bobinas.get(i).getAnchura());
			cell.setCellStyle(styleNormalCenter);

			cell = row.createCell(2);
			cell.setCellValue(bobinas.get(i).getDiametroExt());
			cell.setCellStyle(styleNormalCenter);

			cell = row.createCell(3);
			cell.setCellValue(Utilidades.format(bobinas.get(i).getPeso(),
					Constantes.NUM_DECIMALES_PESO));
			cell.setCellStyle(styleNormalCenter);

			cell = row.createCell(4);
			cell.setCellValue(bobinas.get(i).getPosicion().getDistancia());
			cell.setCellStyle(styleNormalCenter);
		}
		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue("");
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		// NOTA ACLARATORIA
		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue("(*)." + textoDescTransporte);
		cell.setCellStyle(styleNegrita);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue("");
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		if (resultado.isMostrarGraficos()) {
			// SOLUCION GRAFICA
			fila++;
			row = excelSheet.createRow(fila);
			cell = row.createCell(0);
			cell.setCellValue("");
			cell.setCellStyle(styleNormal);
			excelSheet.addMergedRegion(new CellRangeAddress(fila,
					(short) fila + 6, 0, (short) 4));
			fila = fila + 6;
		}

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue("");
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		// MODOS ESTIBA
		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_SOL_TITULO5, locale));
		cell.setCellStyle(styleNegritaCenter);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		for (int i = 0; i < estibas.size(); i++) {
			String textoEstibas = (locale.equals(Constantes.LOCALE_EU)) ? estibas
					.get(i).getDescEu() : estibas.get(i).getDescEs();

			fila++;
			row = excelSheet.createRow(fila);
			cell = row.createCell(0);
			cell.setCellValue(textoEstibas);
			cell.setCellStyle(styleNormal);
			excelSheet.addMergedRegion(new CellRangeAddress(fila,
					(short) fila + 2, 0, (short) 4));

			fila = fila + 2;
		}

		// RECOMENDACIONES SEGURIDAD

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue("");
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_TXT_INT2, locale));
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_TXT_INT3, locale));
		cell.setCellStyle(styleNegrita);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_INT_DIAMETROEXT,
				locale));
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_INT_ANCHURA, locale));
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_INT_PESO, locale));
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue("");
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_INT_DIAMETROINT,
				locale));
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		if (resultado.isMostrarGraficos()) {
			// UBICACION IMAGEN RECOMENDACIONES
			fila++;
			row = excelSheet.createRow(fila);
			cell = row.createCell(0);
			cell.setCellValue("");
			cell.setCellStyle(styleNormal);
			excelSheet.addMergedRegion(new CellRangeAddress(fila,
					(short) fila + 8, 0, (short) 1));
			fila = fila + 8;
		}
		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_TXT_INT4, locale));
		cell.setCellStyle(styleNegrita);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_PESO_BOBINA, locale));
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this
				.getLiteral(Constantes.LABEL_DIAMETRO_EXT, locale));
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

		fila++;
		row = excelSheet.createRow(fila);
		cell = row.createCell(0);
		cell.setCellValue(this.getLiteral(Constantes.LABEL_ANCHURA_BOBINA,
				locale));
		cell.setCellStyle(styleNormal);
		excelSheet.addMergedRegion(new CellRangeAddress(fila, (short) fila, 0,
				(short) 4));

	}

}