Package org.pentaho.reporting.engine.classic.core.elementfactory

Source Code of org.pentaho.reporting.engine.classic.core.elementfactory.CrosstabBuilder

/*!
* This program is free software; you can redistribute it and/or modify it under the
* terms of the GNU Lesser General Public License, version 2.1 as published by the Free Software
* Foundation.
*
* You should have received a copy of the GNU Lesser General Public License along with this
* program; if not, you can obtain a copy at http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html
* or from the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
*
* Copyright (c) 2002-2013 Pentaho Corporation..  All rights reserved.
*/

package org.pentaho.reporting.engine.classic.core.elementfactory;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Locale;

import org.pentaho.reporting.engine.classic.core.AttributeNames;
import org.pentaho.reporting.engine.classic.core.CrosstabCell;
import org.pentaho.reporting.engine.classic.core.CrosstabCellBody;
import org.pentaho.reporting.engine.classic.core.CrosstabColumnGroup;
import org.pentaho.reporting.engine.classic.core.CrosstabColumnGroupBody;
import org.pentaho.reporting.engine.classic.core.CrosstabGroup;
import org.pentaho.reporting.engine.classic.core.CrosstabOtherGroup;
import org.pentaho.reporting.engine.classic.core.CrosstabOtherGroupBody;
import org.pentaho.reporting.engine.classic.core.CrosstabRowGroup;
import org.pentaho.reporting.engine.classic.core.CrosstabRowGroupBody;
import org.pentaho.reporting.engine.classic.core.DetailsHeader;
import org.pentaho.reporting.engine.classic.core.Element;
import org.pentaho.reporting.engine.classic.core.GroupBody;
import org.pentaho.reporting.engine.classic.core.MasterReport;
import org.pentaho.reporting.engine.classic.core.designtime.DesignTimeDataSchemaModel;
import org.pentaho.reporting.engine.classic.core.filter.types.LabelType;
import org.pentaho.reporting.engine.classic.core.filter.types.NumberFieldType;
import org.pentaho.reporting.engine.classic.core.filter.types.TextFieldType;
import org.pentaho.reporting.engine.classic.core.function.AggregationFunction;
import org.pentaho.reporting.engine.classic.core.metadata.ElementType;
import org.pentaho.reporting.engine.classic.core.style.BandStyleKeys;
import org.pentaho.reporting.engine.classic.core.style.ElementStyleKeys;
import org.pentaho.reporting.engine.classic.core.wizard.AutoGeneratorUtility;
import org.pentaho.reporting.engine.classic.core.wizard.ContextAwareDataSchemaModel;
import org.pentaho.reporting.engine.classic.core.wizard.DataAttributeContext;
import org.pentaho.reporting.engine.classic.core.wizard.DataAttributes;
import org.pentaho.reporting.libraries.base.util.StringUtils;

public class CrosstabBuilder implements Cloneable
{
  private ArrayList<CrosstabDimension> rows;
  private ArrayList<CrosstabDimension> columns;
  private ArrayList<String> others;
  private ArrayList<CrosstabDetail> details;
  private ContextAwareDataSchemaModel dataSchemaModel;
  private String groupNamePrefix;
  private Float minimumWidth;
  private Float minimumHeight;
  private Float maximumWidth;
  private Float maximumHeight;
  private Float prefWidth;
  private Float prefHeight;
  private Boolean allowMetaDataStyling;
  private Boolean allowMetaDataAttributes;

  @Deprecated
  public CrosstabBuilder(final DesignTimeDataSchemaModel dataSchemaModel)
  {
    this((ContextAwareDataSchemaModel) dataSchemaModel);
  }

  public CrosstabBuilder(final ContextAwareDataSchemaModel dataSchemaModel)
  {
    rows = new ArrayList<CrosstabDimension>();
    columns = new ArrayList<CrosstabDimension>();
    others = new ArrayList<String>();
    details = new ArrayList<CrosstabDetail>();
    this.dataSchemaModel = dataSchemaModel;
    this.groupNamePrefix = "";
    this.minimumHeight = 20f;
    this.maximumHeight = 20f;
    this.maximumWidth = 80f;
    this.minimumWidth = 80f;
  }

  public Float getMinimumWidth()
  {
    return minimumWidth;
  }

  public void setMinimumWidth(final Float minimumWidth)
  {
    this.minimumWidth = minimumWidth;
  }

  public Float getMinimumHeight()
  {
    return minimumHeight;
  }

  public void setMinimumHeight(final Float minimumHeight)
  {
    this.minimumHeight = minimumHeight;
  }

  public Float getMaximumWidth()
  {
    return maximumWidth;
  }

  public void setMaximumWidth(final Float maximumWidth)
  {
    this.maximumWidth = maximumWidth;
  }

  public Float getMaximumHeight()
  {
    return maximumHeight;
  }

  public void setMaximumHeight(final Float maximumHeight)
  {
    this.maximumHeight = maximumHeight;
  }

  public Float getPrefWidth()
  {
    return prefWidth;
  }

  public void setPrefWidth(final Float prefWidth)
  {
    this.prefWidth = prefWidth;
  }

  public Float getPrefHeight()
  {
    return prefHeight;
  }

  public void setPrefHeight(final Float prefHeight)
  {
    this.prefHeight = prefHeight;
  }

  public Boolean getAllowMetaDataStyling()
  {
    return allowMetaDataStyling;
  }

  public void setAllowMetaDataStyling(final Boolean allowMetaDataStyling)
  {
    this.allowMetaDataStyling = allowMetaDataStyling;
  }

  public Boolean getAllowMetaDataAttributes()
  {
    return allowMetaDataAttributes;
  }

  public void setAllowMetaDataAttributes(final Boolean allowMetaDataAttributes)
  {
    this.allowMetaDataAttributes = allowMetaDataAttributes;
  }

  public String getGroupNamePrefix()
  {
    return groupNamePrefix;
  }

  public void setGroupNamePrefix(final String groupNamePrefix)
  {
    this.groupNamePrefix = groupNamePrefix;
  }

  public void addOtherDimension(final String field)
  {
    others.add(field);
  }

  public void addRowDimension(final CrosstabDimension dimension)
  {
    rows.add(dimension);
  }

  public void addRowDimension(final String field)
  {
    addRowDimension(new CrosstabDimension(field, field, false, "Summary"));
  }

  public void addRowDimension(final String field, final boolean addSummary)
  {
    addRowDimension(new CrosstabDimension(field, field, addSummary, "Summary"));
  }

  public void addColumnDimension(final CrosstabDimension dimension)
  {
    columns.add(dimension);
  }

  public void addColumnDimension(final String field)
  {
    addColumnDimension(new CrosstabDimension(field, field, false, "Summary"));
  }

  public void addColumnDimension(final String field, final boolean addSummary)
  {
    addColumnDimension(new CrosstabDimension(field, field, addSummary, "Summary"));
  }

  public void addDetails(final CrosstabDetail detail)
  {
    details.add(detail);
  }

  public void addDetails(final String field, final Class<? extends AggregationFunction> aggregation)
  {
    details.add(new CrosstabDetail(field, field, aggregation));
  }

  public List<CrosstabDimension> getRows()
  {
    return Collections.unmodifiableList(rows);
  }

  public List<CrosstabDimension> getColumns()
  {
    return Collections.unmodifiableList(columns);
  }

  public List<String> getOthers()
  {
    return Collections.unmodifiableList(others);
  }

  public List<CrosstabDetail> getDetails()
  {
    return Collections.unmodifiableList(details);
  }

  public MasterReport createReport()
  {
    final MasterReport report = new MasterReport();
    report.setRootGroup(create());
    return report;
  }

  public CrosstabGroup create()
  {
    if (columns.size() == 0)
    {
      throw new IllegalStateException();
    }
    if (rows.size() == 0)
    {
      throw new IllegalStateException();
    }

    final CrosstabCellBody cellBody = createCellBody();

    GroupBody body = createColumnGroups(cellBody);
    body = createRowGroups(cellBody, body);
    body = createOtherGroups(body);

    return new CrosstabGroup(body);
  }

  protected CrosstabCellBody createCellBody()
  {
    final CrosstabCellBody cellBody = new CrosstabCellBody();
    cellBody.addElement(createDetailsCell("details-cell", null, null));
    setupDetailsHeader(cellBody.getHeader());
    return cellBody;
  }

  private GroupBody createOtherGroups(GroupBody body)
  {
    for (int other = others.size() - 1; other >= 0; other -= 1)
    {
      final String column = others.get(other);
      final CrosstabOtherGroup columnGroup = createOtherGroup(body, column);

      body = new CrosstabOtherGroupBody(columnGroup);
    }
    return body;
  }

  protected CrosstabOtherGroup createOtherGroup(final GroupBody body, final String column)
  {
    final CrosstabOtherGroup columnGroup = new CrosstabOtherGroup(body);
    columnGroup.setField(column);
    columnGroup.getHeader().addElement(createFieldItem(column));
    return columnGroup;
  }

  private GroupBody createRowGroups(final CrosstabCellBody cellBody, GroupBody body)
  {
    for (int row = rows.size() - 1; row >= 0; row -= 1)
    {
      final CrosstabDimension rowDimension = rows.get(row);
      final CrosstabRowGroup rowGroup = createRowGroup(cellBody, body, rowDimension);
      body = new CrosstabRowGroupBody(rowGroup);
    }
    return body;
  }

  protected CrosstabRowGroup createRowGroup(final CrosstabCellBody cellBody,
                                            final GroupBody innerBody,
                                            final CrosstabDimension rowDimension)
  {
    final CrosstabRowGroup rowGroup = new CrosstabRowGroup(innerBody);
    rowGroup.setName(computeGroupName(rowDimension));
    rowGroup.setField(rowDimension.getField());
    rowGroup.getTitleHeader().getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, -100f);
    rowGroup.getTitleHeader().addElement(createLabel(rowDimension.getTitle(), rowDimension.getField()));
    rowGroup.getHeader().getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, -100f);
    rowGroup.getHeader().addElement(createFieldItem(rowDimension.getField()));
    rowGroup.getSummaryHeader().getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, -100f);
    rowGroup.getSummaryHeader().addElement(createLabel(rowDimension.getSummaryTitle(), rowDimension.getField()));
    rowGroup.setPrintSummary(rowDimension.isPrintSummary());

    createSummaryCells(cellBody, rowDimension);
    return rowGroup;
  }

  protected void createSummaryCells(final CrosstabCellBody cellBody,
                                    final CrosstabDimension rowDimension)
  {
    if (rowDimension.isPrintSummary())
    {
      cellBody.addElement(createDetailsCell(rowDimension.getField(), rowDimension.getField(), null));

      for (int col = columns.size() - 1; col >= 0; col -= 1)
      {
        final CrosstabDimension column = columns.get(col);
        if (column.isPrintSummary())
        {
          cellBody.addElement(createDetailsCell
              (column.getField() + "," + rowDimension.getField(), rowDimension.getField(), column.getField()));
        }
      }
    }
  }

  protected void createColumnSummaryCells(final CrosstabCellBody cellBody, final CrosstabDimension column)
  {
    if (column.isPrintSummary())
    {
      cellBody.addElement(createDetailsCell(column.getField(), null, column.getField()));
    }
  }

  protected String computeGroupName(final CrosstabDimension rowDimension)
  {
    return groupNamePrefix + rowDimension.getField();
  }

  private GroupBody createColumnGroups(final CrosstabCellBody cellBody)
  {
    GroupBody body = cellBody;
    for (int col = columns.size() - 1; col >= 0; col -= 1)
    {
      final CrosstabDimension column = columns.get(col);
      final CrosstabColumnGroup columnGroup = createColumnGroup(cellBody, body, column);
      body = new CrosstabColumnGroupBody(columnGroup);
    }
    return body;
  }

  protected CrosstabColumnGroup createColumnGroup(final CrosstabCellBody cellBody,
                                                  final GroupBody body,
                                                  final CrosstabDimension column)
  {
    final CrosstabColumnGroup columnGroup = new CrosstabColumnGroup(body);
    columnGroup.setName(computeGroupName(column));
    columnGroup.setField(column.getField());
    columnGroup.getTitleHeader().getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, -100f);
    columnGroup.getTitleHeader().addElement(createLabel(column.getTitle(), column.getField()));
    columnGroup.getHeader().getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, -100f);
    columnGroup.getHeader().addElement(createFieldItem(column.getField()));
    columnGroup.getSummaryHeader().getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, -100f);
    columnGroup.getSummaryHeader().addElement(createLabel(column.getSummaryTitle(), column.getField()));
    columnGroup.setPrintSummary(column.isPrintSummary());

    createColumnSummaryCells(cellBody, column);
    return columnGroup;
  }

  protected CrosstabCell createDetailsCell(final String name, final String rowDim, final String colDim)
  {
    final CrosstabCell cell = createDetailsCell();
    cell.setColumnField(colDim);
    cell.setName(name);
    return cell;
  }

  protected CrosstabCell createDetailsCell()
  {
    final CrosstabCell cell = new CrosstabCell();
    cell.getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, -100f);
    cell.getStyle().setStyleProperty(BandStyleKeys.LAYOUT, BandStyleKeys.LAYOUT_ROW);
    for (int i = 0; i < details.size(); i += 1)
    {
      final CrosstabDetail crosstabDetail = details.get(i);
      cell.addElement(createDetailCellContent(crosstabDetail));
    }
    return cell;
  }

  protected Element createDetailCellContent(final CrosstabDetail crosstabDetail)
  {
    return createFieldItem(crosstabDetail.getField(), crosstabDetail.getAggregation(), true);
  }

  protected void setupDetailsHeader(final DetailsHeader cell)
  {
    cell.getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, -100f);
    cell.getStyle().setStyleProperty(BandStyleKeys.LAYOUT, BandStyleKeys.LAYOUT_ROW);
    for (int i = 0; i < details.size(); i += 1)
    {
      final CrosstabDetail crosstabDetail = details.get(i);
      String title = crosstabDetail.getTitle();
      if (StringUtils.isEmpty(title))
      {
        title = crosstabDetail.getField();
      }
      cell.addElement(createLabel(title, crosstabDetail.getField(), true));
    }
  }

  protected Element createFieldItem(final String text)
  {
    return createFieldItem(text, null, false);
  }

  protected Element createFieldItem(final String fieldName,
                                    final Class<? extends AggregationFunction> aggregationType,
                                    final boolean split)
  {
    final ElementType targetType;
    if (dataSchemaModel != null)
    {
      final DataAttributeContext context = dataSchemaModel.getDataAttributeContext();
      final DataAttributes attributes = dataSchemaModel.getDataSchema().getAttributes(fieldName);
      targetType = AutoGeneratorUtility.createFieldType(attributes, context);
    }
    else
    {
      targetType = TextFieldType.INSTANCE;
    }

    final Element element = new Element();
    element.setElementType(targetType);
    element.getElementType().configureDesignTimeDefaults(element, Locale.getDefault());

    if (targetType instanceof NumberFieldType)
    {
      element.setAttribute(AttributeNames.Core.NAMESPACE, AttributeNames.Core.FORMAT_STRING, "0.00;-0.00");
    }

    element.setAttribute(AttributeNames.Core.NAMESPACE, AttributeNames.Core.FIELD, fieldName);
    element.getStyle().setStyleProperty(ElementStyleKeys.MIN_WIDTH, split(split, minimumWidth));
    element.getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, minimumHeight);
    element.getStyle().setStyleProperty(ElementStyleKeys.WIDTH, split(split, prefWidth));
    element.getStyle().setStyleProperty(ElementStyleKeys.HEIGHT, prefHeight);
    element.getStyle().setStyleProperty(ElementStyleKeys.MAX_WIDTH, split(split, maximumWidth));
    element.getStyle().setStyleProperty(ElementStyleKeys.MAX_HEIGHT, maximumHeight);
    element.setAttribute(AttributeNames.Wizard.NAMESPACE, AttributeNames.Wizard.AGGREGATION_TYPE, aggregationType);
    element.setAttribute(AttributeNames.Wizard.NAMESPACE, AttributeNames.Wizard.ALLOW_METADATA_STYLING, allowMetaDataStyling);
    return element;
  }

  protected Element createLabel(final String text, final String labelFor)
  {
    return createLabel(text, labelFor, false);
  }

  protected Element createLabel(final String text, final String labelFor, final boolean splitArea)
  {
    final Element element = new Element();
    element.setElementType(LabelType.INSTANCE);
    element.setAttribute(AttributeNames.Core.NAMESPACE, AttributeNames.Core.VALUE, text);
    element.getStyle().setStyleProperty(ElementStyleKeys.MIN_WIDTH, split(splitArea, minimumWidth));
    element.getStyle().setStyleProperty(ElementStyleKeys.MIN_HEIGHT, minimumHeight);
    element.getStyle().setStyleProperty(ElementStyleKeys.WIDTH, split(splitArea, prefWidth));
    element.getStyle().setStyleProperty(ElementStyleKeys.HEIGHT, prefHeight);
    element.getStyle().setStyleProperty(ElementStyleKeys.MAX_WIDTH, split(splitArea, maximumWidth));
    element.getStyle().setStyleProperty(ElementStyleKeys.MAX_HEIGHT, maximumHeight);
    element.setAttribute(AttributeNames.Wizard.NAMESPACE, AttributeNames.Wizard.ALLOW_METADATA_STYLING, allowMetaDataStyling);
    if (StringUtils.isEmpty(labelFor))
    {
      element.setAttribute(AttributeNames.Wizard.NAMESPACE, AttributeNames.Wizard.ALLOW_METADATA_ATTRIBUTES, allowMetaDataAttributes);
    }
    else
    {
      element.setAttribute(AttributeNames.Wizard.NAMESPACE, AttributeNames.Wizard.ALLOW_METADATA_ATTRIBUTES, true);
    }
    element.setAttribute(AttributeNames.Wizard.NAMESPACE, AttributeNames.Wizard.LABEL_FOR, labelFor);
    return element;
  }

  private Float split(final boolean split, final Float value)
  {
    if (split == false)
    {
      return value;
    }

    if (value == null)
    {
      return null;
    }
    final float f = value;
    return f / Math.max(1, details.size());
  }

  public CrosstabBuilder clone()
  {
    try
    {
      CrosstabBuilder clone = (CrosstabBuilder) super.clone();
      clone.columns = (ArrayList<CrosstabDimension>) columns.clone();
      clone.rows = (ArrayList<CrosstabDimension>) rows.clone();
      clone.others = (ArrayList<String>) others.clone();
      clone.details = (ArrayList<CrosstabDetail>) details.clone();
      return clone;
    }
    catch (final CloneNotSupportedException e)
    {
      throw new IllegalStateException(e);
    }
  }

  public CrosstabBuilder clearDimensions()
  {
    CrosstabBuilder clone = clone();
    clone.columns.clear();
    clone.rows.clear();
    clone.others.clear();
    clone.details.clear();
    return clone;
  }
}
TOP

Related Classes of org.pentaho.reporting.engine.classic.core.elementfactory.CrosstabBuilder

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.