Gestionar series de datos de gráficos en presentaciones con PHP
Descripción general
Un gráfico almacena sus datos trazados en un libro de datos del gráfico. Un ChartSeries representa un conjunto de valores relacionados, y cada ChartDataPoint en la serie se refiere a una o más celdas del libro de trabajo. Los objetos ChartCategory proporcionan las etiquetas o valores de agrupación compartidos por las series. Por lo tanto, el nombre de la serie, las categorías y los valores de los puntos están conectados a objetos ChartDataCell en lugar de almacenarse solo como texto visible.
Para un gráfico de categorías típico, el libro de datos predeterminado usa la fila 0 para los nombres de serie, la columna 0 para los nombres de categoría y el resto de celdas para los valores de serie. Los índices de hoja, fila y columna que se pasan a ChartDataWorkbook.getCell son basados en cero. Esta disposición es útil cuando se crea un gráfico con datos predeterminados, pero no se debe asumir que todos los gráficos existentes la utilizan. Para una presentación cargada, inspeccione las celdas referenciadas por las series, categorías y puntos de datos antes de modificar los valores del libro.
Las opciones del gráfico tienen tres ámbitos diferentes:
- Configuraciones a nivel de serie, como ChartSeries.getFormat, proporcionan la apariencia predeterminada para todos los puntos de una serie.
- Configuraciones de punto de datos, como ChartDataPoint.getFormat, sobrescriben la apariencia de la serie para un punto concreto.
- Configuraciones de grupo se aplican a series compatibles que pertenecen al mismo ChartSeriesGroup. Acceda al grupo mediante ChartSeries.getParentSeriesGroup cuando necesite definir opciones como superposición o ancho de espacio.
Cuando no se establece un relleno explícito de punto o serie, el estilo y el tema del gráfico determinan la apariencia automática. Cuando existen tanto formatos de serie como de punto, el formato del punto tiene prioridad para ese punto.

Establecer la superposición de la serie del gráfico
ChartSeries.getOverlap indica cuánto se solapan las barras o columnas en un gráfico 2D, de -100 a 100 por ciento. Es una proyección de solo lectura de la configuración en el grupo de series padre. Utilice ChartSeriesGroup.setOverlap para actualizar todas las series compatibles en ese grupo. Esta opción se aplica a los tipos de gráfico que muestran barras o columnas agrupadas; no afecta a grupos de series no relacionados en un gráfico combinado.
El siguiente ejemplo establece la superposición para el grupo que contiene la primera serie:
$firstSlideIndex = 0;
$firstSeriesIndex = 0;
$overlapPercent = 30;
$presentation = new Presentation();
try {
$slide = $presentation->getSlides()->get_Item($firstSlideIndex);
// El nuevo gráfico contiene series, categorías y valores de ejemplo.
$chart = $slide->getShapes()->addChart(ChartType::ClusteredColumn, 20, 20, 500, 200);
$series = $chart->getChartData()->getSeries()->get_Item($firstSeriesIndex);
$series->getParentSeriesGroup()->setOverlap($overlapPercent);
$presentation->save("series_overlap.pptx", SaveFormat::Pptx);
} finally {
if (!java_is_null($presentation)) {
$presentation->dispose();
}
}
El resultado:

Cambiar el color de relleno de la serie
Utilice ChartSeries.getFormat para definir el relleno predeterminado de una serie completa. Si un punto ya tiene un relleno explícito, su configuración de ChartDataPoint.getFormat sobrescribe el relleno de la serie para ese punto.
El siguiente ejemplo aplica un relleno sólido azul a la primera serie:
$firstSlideIndex = 0;
$firstSeriesIndex = 0;
$blueColor = java("java.awt.Color")->BLUE;
$presentation = new Presentation();
try {
$slide = $presentation->getSlides()->get_Item($firstSlideIndex);
$chart = $slide->getShapes()->addChart(ChartType::ClusteredColumn, 20, 20, 500, 200);
$series = $chart->getChartData()->getSeries()->get_Item($firstSeriesIndex);
$series->getFormat()->getFill()->setFillType(FillType::Solid);
$series->getFormat()->getFill()->getSolidFillColor()->setColor($blueColor);
$presentation->save("series_color.pptx", SaveFormat::Pptx);
} finally {
if (!java_is_null($presentation)) {
$presentation->dispose();
}
}
El resultado:

Cambiar el nombre de la serie
El nombre de una serie se almacena en el libro de datos del gráfico y normalmente se muestra en la leyenda. En el libro predeterminado creado para un gráfico de columnas agrupadas, la celda B1 está en la fila 0, columna 1 y contiene el nombre de la primera serie. Las variables nombradas en el siguiente ejemplo hacen explícita esa estructura:
$firstSlideIndex = 0;
$worksheetIndex = 0;
$seriesNameRowIndex = 0;
$firstSeriesColumnIndex = 1;
$presentation = new Presentation();
try {
$slide = $presentation->getSlides()->get_Item($firstSlideIndex);
$chart = $slide->getShapes()->addChart(ChartType::ClusteredColumn, 20, 20, 500, 200);
$workbook = $chart->getChartData()->getChartDataWorkbook();
$seriesNameCell = $workbook->getCell($worksheetIndex, $seriesNameRowIndex, $firstSeriesColumnIndex);
$seriesNameCell->setValue("Revenue");
$presentation->save("series_name.pptx", SaveFormat::Pptx);
} finally {
if (!java_is_null($presentation)) {
$presentation->dispose();
}
}
También puede actualizar la celda ya referenciada por ChartSeries.getName. Este método evita suponer una fila y columna determinadas en un gráfico existente:
$firstSlideIndex = 0;
$firstSeriesIndex = 0;
$firstNameCellIndex = 0;
$presentation = new Presentation();
try {
$slide = $presentation->getSlides()->get_Item($firstSlideIndex);
$chart = $slide->getShapes()->addChart(ChartType::ClusteredColumn, 20, 20, 500, 200);
$series = $chart->getChartData()->getSeries()->get_Item($firstSeriesIndex);
$seriesNameCell = $series->getName()->getAsCells()->get_Item($firstNameCellIndex);
$seriesNameCell->setValue("Revenue");
$presentation->save("series_name.pptx", SaveFormat::Pptx);
} finally {
if (!java_is_null($presentation)) {
$presentation->dispose();
}
}
El resultado:

Obtener el color automático de relleno de la serie
ChartSeries.getAutomaticSeriesColor devuelve el color calculado a partir del índice de la serie y del estilo del gráfico. Este es el color que se usa cuando el relleno de la serie no ha sido definido explícitamente. La llamada al método lee el color calculado; no asigna un nuevo relleno.
El siguiente ejemplo muestra el color automático de cada serie predeterminada:
$firstSlideIndex = 0;
$presentation = new Presentation();
try {
$slide = $presentation->getSlides()->get_Item($firstSlideIndex);
$chart = $slide->getShapes()->addChart(ChartType::ClusteredColumn, 20, 20, 500, 200);
$seriesCount = java_values($chart->getChartData()->getSeries()->size());
for ($seriesIndex = 0; $seriesIndex < $seriesCount; $seriesIndex++) {
$series = $chart->getChartData()->getSeries()->get_Item($seriesIndex);
$automaticColor = $series->getAutomaticSeriesColor();
$red = java_values($automaticColor->getRed());
$green = java_values($automaticColor->getGreen());
$blue = java_values($automaticColor->getBlue());
echo "Series " . $seriesIndex . ": java.awt.Color[r=" . $red . ",g=" . $green . ",b=" . $blue . "]" . PHP_EOL;
}
} finally {
if (!java_is_null($presentation)) {
$presentation->dispose();
}
}
Ejemplo de salida para el estilo de gráfico predeterminado:
Series 0: java.awt.Color[r=79,g=129,b=189]
Series 1: java.awt.Color[r=192,g=80,b=77]
Series 2: java.awt.Color[r=155,g=187,b=89]
Los colores exactos dependen del estilo y del tema del gráfico.
Establecer el color de relleno invertido para una serie del gráfico
Para series de barras, columnas y burbujas, ChartSeries.setInvertIfNegative puede mostrar los valores negativos con un relleno diferente. Defina el relleno regular de la serie como sólido, habilite la inversión y asigne el color de valor negativo mediante ChartSeries.getInvertedSolidFillColor. Los números negativos permanecen sin cambios en el libro; solo su color de visualización cambia.
El siguiente ejemplo sustituye los datos del gráfico predeterminado por una sola serie. La fila 0 de la hoja contiene el nombre de la serie, la columna 0 contiene los nombres de categoría y la columna 1 contiene los valores:
$firstSlideIndex = 0;
$worksheetIndex = 0;
$headerRowIndex = 0;
$categoryColumnIndex = 0;
$firstSeriesColumnIndex = 1;
$firstDataRowIndex = 1;
$categoryNames = ["Category 1", "Category 2", "Category 3"];
$seriesValues = [-20, 50, -30];
$redColor = java("java.awt.Color")->RED;
$presentation = new Presentation();
try {
$slide = $presentation->getSlides()->get_Item($firstSlideIndex);
$chart = $slide->getShapes()->addChart(ChartType::ClusteredColumn, 20, 20, 500, 200);
$chartData = $chart->getChartData();
$workbook = $chartData->getChartDataWorkbook();
$chartData->getSeries()->clear();
$chartData->getCategories()->clear();
$seriesNameCell = $workbook->getCell($worksheetIndex, $headerRowIndex, $firstSeriesColumnIndex, "Series 1");
$chartType = $chart->getType();
$series = $chartData->getSeries()->add($seriesNameCell, $chartType);
$categoryCount = count($categoryNames);
for ($categoryIndex = 0; $categoryIndex < $categoryCount; $categoryIndex++) {
$dataRowIndex = $firstDataRowIndex + $categoryIndex;
$categoryName = $categoryNames[$categoryIndex];
$seriesValue = $seriesValues[$categoryIndex];
$categoryCell = $workbook->getCell($worksheetIndex, $dataRowIndex, $categoryColumnIndex, $categoryName);
$chartData->getCategories()->add($categoryCell);
$valueCell = $workbook->getCell($worksheetIndex, $dataRowIndex, $firstSeriesColumnIndex, $seriesValue);
$series->getDataPoints()->addDataPointForBarSeries($valueCell);
}
$automaticSeriesColor = $series->getAutomaticSeriesColor();
$series->getFormat()->getFill()->setFillType(FillType::Solid);
$series->getFormat()->getFill()->getSolidFillColor()->setColor($automaticSeriesColor);
$series->setInvertIfNegative(true);
$series->getInvertedSolidFillColor()->setColor($redColor);
$presentation->save("inverted_solid_fill_color.pptx", SaveFormat::Pptx);
} finally {
if (!java_is_null($presentation)) {
$presentation->dispose();
}
}
El resultado:

Puede habilitar la inversión para un punto mediante ChartDataPoint.setInvertIfNegative. En el siguiente ejemplo, la inversión está desactivada para la serie y activada solo para el punto seleccionado. Además, al punto se le asigna un valor negativo para que el efecto sea visible:
$firstSlideIndex = 0;
$firstSeriesIndex = 0;
$targetDataPointIndex = 2;
$negativeValue = -30;
$redColor = java("java.awt.Color")->RED;
$presentation = new Presentation();
try {
$slide = $presentation->getSlides()->get_Item($firstSlideIndex);
$chart = $slide->getShapes()->addChart(ChartType::ClusteredColumn, 20, 20, 500, 200);
$series = $chart->getChartData()->getSeries()->get_Item($firstSeriesIndex);
$automaticSeriesColor = $series->getAutomaticSeriesColor();
$series->getFormat()->getFill()->setFillType(FillType::Solid);
$series->getFormat()->getFill()->getSolidFillColor()->setColor($automaticSeriesColor);
$series->getInvertedSolidFillColor()->setColor($redColor);
$series->setInvertIfNegative(false);
$dataPoint = $series->getDataPoints()->get_Item($targetDataPointIndex);
$dataPoint->getValue()->getAsCell()->setValue($negativeValue);
$dataPoint->setInvertIfNegative(true);
$presentation->save("data_point_invert_color_if_negative.pptx", SaveFormat::Pptx);
} finally {
if (!java_is_null($presentation)) {
$presentation->dispose();
}
}
Borrar el valor de un punto de datos específico
Para dejar un punto vacío sin eliminar los demás, establezca su celda subyacente del libro a null. En un gráfico de columnas, el valor trazado está disponible mediante ChartDataPoint.getValue. El punto sigue ocupando la misma posición de categoría, pero el gráfico trata su valor como en blanco según la configuración de valores en blanco del gráfico.
El siguiente ejemplo borra solo el segundo punto de la primera serie:
$firstSlideIndex = 0;
$firstSeriesIndex = 0;
$targetDataPointIndex = 1;
$presentation = new Presentation();
try {
$slide = $presentation->getSlides()->get_Item($firstSlideIndex);
$chart = $slide->getShapes()->addChart(ChartType::ClusteredColumn, 20, 20, 500, 200);
$series = $chart->getChartData()->getSeries()->get_Item($firstSeriesIndex);
$dataPoint = $series->getDataPoints()->get_Item($targetDataPointIndex);
$dataPoint->getValue()->getAsCell()->setValue(null);
$presentation->save("clear_data_point_value.pptx", SaveFormat::Pptx);
} finally {
if (!java_is_null($presentation)) {
$presentation->dispose();
}
}
Los gráficos de dispersión usan celdas X e Y separadas, y los gráficos de burbujas también utilizan una celda de tamaño. Borre solo la celda que representa el valor que desea eliminar. No llame a ChartDataPointCollection.clear cuando quiera conservar los demás puntos, ya que ese método elimina todos los puntos de la colección.
Establecer el ancho de espacio entre series
El ancho de espacio es el espacio entre grupos adyacentes de barras o columnas, expresado como porcentaje del ancho de la barra o columna. Al igual que la superposición, pertenece al grupo de series padre y no a una serie individual. Llame a ChartSeriesGroup.setGapWidth una vez para el grupo. Un valor mayor crea más espacio entre los grupos; un valor menor los hace más densos.
El siguiente ejemplo cambia el ancho de espacio y guarda solo la presentación final:
$firstSlideIndex = 0;
$firstSeriesIndex = 0;
$gapWidthPercent = 30;
$presentation = new Presentation();
try {
$slide = $presentation->getSlides()->get_Item($firstSlideIndex);
$chart = $slide->getShapes()->addChart(ChartType::StackedColumn, 20, 20, 500, 200);
$series = $chart->getChartData()->getSeries()->get_Item($firstSeriesIndex);
$series->getParentSeriesGroup()->setGapWidth($gapWidthPercent);
$presentation->save("gap_width_30.pptx", SaveFormat::Pptx);
} finally {
if (!java_is_null($presentation)) {
$presentation->dispose();
}
}
El resultado:

FAQ
¿Qué tipos de gráficos admiten series de datos?
Todas las clases de gráfico representadas por la enumeración ChartType utilizan datos del gráfico, pero sus series no comparten la misma estructura de valores ni las mismas configuraciones. Por ejemplo, los gráficos de categorías usan categorías y valores, los de dispersión utilizan valores X e Y, y los de burbujas añaden tamaños de burbuja. Utilice el método de creación de puntos de datos que coincida con el tipo de serie. Opciones como superposición y ancho de espacio solo se aplican a grupos de barras o columnas compatibles.
¿Qué es un grupo de series de gráfico?
Un ChartSeriesGroup contiene series compatibles que comparten configuraciones de trazado a nivel de grupo. Un gráfico combinado puede contener varios grupos, de modo que cambiar el grupo al que se accede a través de una serie no modifica necesariamente todas las series del gráfico.
¿Un gráfico creado recientemente contiene datos predeterminados?
Sí. Por defecto, ShapeCollection.addChart crea series, categorías y valores de muestra. Puede editar esas celdas o borrar tanto las colecciones de series como de categorías antes de añadir un conjunto de datos totalmente personalizado. También existe una sobrecarga que permite crear un gráfico sin datos predeterminados.
¿Cómo se conectan los objetos del gráfico a las celdas del libro?
Los nombres de serie, las etiquetas de categoría y los valores de los puntos de datos hacen referencia a celdas en un ChartDataWorkbook. Cambiar una celda referenciada actualiza el elemento del gráfico correspondiente. Cuando crea datos personalizados, mantenga alineadas las filas de categorías y las filas de valores de serie para que cada punto se trace bajo la categoría prevista.
¿Cómo borro un punto en lugar de toda la serie?
Establezca la celda de valor correspondiente a null para conservar la posición de categoría del punto como un punto vacío. Use ChartDataPointCollection.clear solo cuando desee eliminar todos los puntos de esa serie. Si también elimina categorías, actualice cada serie para que sus valores sigan alineados con la colección de categorías.
¿Cómo se muestran los puntos vacíos?
El resultado depende del tipo de gráfico y del valor configurado mediante Chart.setDisplayBlanksAs. Los gráficos compatibles pueden mostrar los vacíos como huecos, como valores cero o conectando los puntos vecinos. Elija la configuración que mejor se ajuste al significado de los datos ausentes en su presentación.
¿Cómo se formatean los valores negativos?
Para series de barras, columnas y burbujas admitidas, llame a ChartSeries.setInvertIfNegative y establezca el color devuelto por ChartSeries.getInvertedSolidFillColor. Puede anular el comportamiento para un punto individual con ChartDataPoint.setInvertIfNegative. Estos métodos afectan al formato, no a los valores numéricos almacenados.
¿Qué formato prevalece cuando tanto una serie como un punto están formateados?
El formateo explícito del punto de datos tiene prioridad para ese punto. Los demás puntos continúan usando el formato explícito de la serie o, cuando el formato de la serie no está definido, el estilo y tema automático del gráfico. Las configuraciones de grupo, como superposición y ancho de espacio, controlan la disposición y no son sobrescrituras de formato a nivel de punto.
¿Existe un límite al número de series que puede contener un gráfico?
Aspose.Slides no impone un límite fijo separado para la cantidad de series. En la práctica, las limitaciones del archivo de presentación, la memoria disponible, el tiempo de renderizado y la legibilidad del gráfico determinan un límite útil.
¿Qué debo cambiar cuando las columnas están demasiado próximas o demasiado separadas?
Llame a ChartSeriesGroup.setGapWidth en el grupo de series padre correspondiente. Aumente el valor para ensanchar el espacio entre los grupos, o disminúyalo para acercar los grupos entre sí.