使用 JavaScript 在演示文稿中自定义图表坐标轴

概述

本文解释如何使用 Aspose.Slides for Node.js via Java 自定义图表坐标轴。内容包括计算坐标轴值、切换图表行列、坐标轴可见性、类别标签和刻度间隔、日期类别及格式、标题旋转、坐标轴定位和显示单位。

获取图表垂直坐标轴的最大值

创建一个Presentation并添加一个默认数据的面积图。在读取计算坐标轴值之前,调用validateChartLayout以确保图表布局是最新的。

读取getActualMaxValue和getActualMinValue获取坐标轴限值,使用getActualMajorUnit和getActualMinorUnit获取刻度间隔。getActualMajorUnitScale和getActualMinorUnitScale提供时间单位比例,适用于日期坐标轴。示例将这些值存入局部变量并保存图表。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation();
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().addChart(aspose.slides.ChartType.Area, 100, 100, 500, 350);
    chart.validateChartLayout();

    var maxValue = chart.getAxes().getVerticalAxis().getActualMaxValue();
    var minValue = chart.getAxes().getVerticalAxis().getActualMinValue();

    var majorUnit = chart.getAxes().getVerticalAxis().getActualMajorUnit();
    var minorUnit = chart.getAxes().getVerticalAxis().getActualMinorUnit();

    var majorUnitScale = chart.getAxes().getVerticalAxis().getActualMajorUnitScale();
    var minorUnitScale = chart.getAxes().getVerticalAxis().getActualMinorUnitScale();

    presentation.save("AxisValues_out.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

在坐标轴之间交换数据

使用switchRowColumn交换图表数据中系列和类别的角色。每个原来的类别变为系列,每个原来的系列变为类别。这改变了数据的分组方式,但不交换水平和垂直坐标轴。示例使用setRange将默认数据绑定到Sheet1!A1:D5(包括标题行和类别列),然后切换行列。它保存了一个包含四个系列和三个类别的图表。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation();
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().addChart(aspose.slides.ChartType.ClusteredColumn, 100, 100, 400, 300);
    chart.getChartData().setRange("Sheet1!A1:D5");
    chart.getChartData().switchRowColumn();

    presentation.save("SwitchChartRowColumns_out.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

禁用折线图的垂直坐标轴

在垂直坐标轴上调用setVisible并传入false以隐藏它。示例创建一个默认数据的折线图并保存为垂直坐标轴隐藏的文件。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation();
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().addChart(aspose.slides.ChartType.Line, 100, 100, 400, 300);
    chart.getAxes().getVerticalAxis().setVisible(false);

    presentation.save("HiddenVerticalAxis.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

禁用折线图的水平坐标轴

在水平坐标轴上调用setVisible并传入false以隐藏它。示例创建一个默认数据的折线图并保存为水平坐标轴隐藏的文件。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation();
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().addChart(aspose.slides.ChartType.Line, 100, 100, 400, 300);
    chart.getAxes().getHorizontalAxis().setVisible(false);

    presentation.save("HiddenHorizontalAxis.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

更改类别坐标轴

使用setCategoryAxisType选择日期或文本类别坐标轴。此示例需要ExistingChart.pptx,其第一张幻灯片的首个形状是图表,类别单元格包含数值型 Excel 日期。它将水平坐标轴更改为日期坐标轴。调用setAutomaticMajorUnit并传入false,随后使用setMajorUnit传入1,以及setMajorUnitScale传入TimeUnitType.Months,使主刻度间隔为一个月。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation("ExistingChart.pptx");
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().get_Item(0);
    chart.getAxes().getHorizontalAxis().setCategoryAxisType(aspose.slides.CategoryAxisType.Date);
    chart.getAxes().getHorizontalAxis().setAutomaticMajorUnit(false);
    chart.getAxes().getHorizontalAxis().setMajorUnit(1);
    chart.getAxes().getHorizontalAxis().setMajorUnitScale(aspose.slides.TimeUnitType.Months);

    presentation.save("ChangeChartCategoryAxis_out.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

控制类别坐标轴标签间隔

当图表包含大量类别时,可在不删除类别或数据点的前提下降低可见标签数量。调用setAutomaticTickLabelSpacing并传入false,随后将期望的类别间隔传递给setTickLabelSpacing。对于按正常顺序排列的文本类别,计数从第一个类别开始:

间隔 示例中显示的标签
1 类别 1, 类别 2, 类别 3, … 类别 24
2 类别 1, 类别 3, 类别 5, … 类别 23
3 类别 1, 类别 4, 类别 7, … 类别 22

间隔为 3 时每第三个标签显示一次,两个标签在显示的标签之间被隐藏。它不会删除相应的列。自动间距根据可用空间选择间隔;不一定会显示所有标签。

刻度线有单独的控制。调用setAutomaticTickMarksSpacing并传入false,然后使用setTickMarksSpacing设置其间隔。例如,1 在每个类别间隔保留一个刻度线,而标签仅每第三个类别出现一次。使用setMajorTickMark设为可见样式以便观察结果。再次将任一自动间距设置器设为true,图表将重新选择该间距。

下面的独立示例创建 24 个类别和一个系列,然后在CategoryAxisIntervals.pptx中保存三张幻灯片:自动间距、手动标签间距(刻度线独立)以及恢复自动间距。两个副本保留原始图表数据。无需输入演示文稿。水平标签文本使密度差异易于观察。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation();
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().addChart(aspose.slides.ChartType.ClusteredColumn, 30, 40, 660, 320);

    chart.setLegend(false);
    chart.getChartData().getCategories().clear();
    chart.getChartData().getSeries().clear();

    var workbook = chart.getChartData().getChartDataWorkbook();
    workbook.clear(0);

    var series = chart.getChartData().getSeries().add(aspose.slides.ChartType.ClusteredColumn);
    for (var i = 0; i < 24; i++) {
        var categoryCell = workbook.getCell(0, i + 1, 0, "Category " + (i + 1));
        chart.getChartData().getCategories().add(categoryCell);
        var valueCell = workbook.getCell(0, i + 1, 1, 10 + i % 6 * 5);
        series.getDataPoints().addDataPointForBarSeries(valueCell);
    }

    var axis = chart.getAxes().getHorizontalAxis();
    axis.setCategoryAxisType(aspose.slides.CategoryAxisType.Text);
    axis.getTextFormat().getTextBlockFormat().setRotationAngle(0);
    axis.getTextFormat().getPortionFormat().setFontHeight(12);
    axis.setMajorTickMark(aspose.slides.TickMarkType.Outside);
    axis.setAutomaticTickLabelSpacing(true);
    axis.setAutomaticTickMarksSpacing(true);

    // 幻灯片 2:显示每第三个标签,但保留每个类别的刻度线。
    var manualSlide = presentation.getSlides().addClone(slide);
    var manualChart = manualSlide.getShapes().get_Item(0);
    var manualAxis = manualChart.getAxes().getHorizontalAxis();
    manualAxis.setAutomaticTickLabelSpacing(false);
    manualAxis.setTickLabelSpacing(3);
    manualAxis.setAutomaticTickMarksSpacing(false);
    manualAxis.setTickMarksSpacing(1);

    // 幻灯片 3:让图表再次选择两个间隔。
    var restoredSlide = presentation.getSlides().addClone(manualSlide);
    var restoredChart = restoredSlide.getShapes().get_Item(0);
    restoredChart.getAxes().getHorizontalAxis().setAutomaticTickLabelSpacing(true);
    restoredChart.getAxes().getHorizontalAxis().setAutomaticTickMarksSpacing(true);

    presentation.save("CategoryAxisIntervals.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

自动间距(幻灯片 1): 在此渲染中,每第二个类别标签显示并换行为两行。自动结果可能随图表大小、字体和渲染器而变化。

自动类别标签间距(所有 24 列可见)

手动间距(幻灯片 2): 每第三个标签显示在一行,而刻度线仍保持在每个类别间隔。所有 24 列(包括未标记的列)保持可见且数值相同。幻灯片 3 恢复上述自动外观。

手动类别标签间隔为三,所有 24 列可见

选择正确的坐标轴和间隔

对于文本类别坐标轴(如柱形图、折线图、面积图或条形图的类别坐标轴),使用此类别计数间隔。在柱形图中,它是水平坐标轴;在水平条形图中,类别坐标轴是垂直的,因此应将这些设置应用于getVerticalAxis返回的坐标轴。刻度间隔同样适用于具有系列坐标轴的图表。

不要使用类别标签间隔来设置数值坐标轴的数值刻度。在数值坐标轴上,setMajorUnit指定值的差异:例如,主单位为 10 时,当坐标轴从零开始时会在 0、10、20 等位置生成刻度。类别标签间隔为 3 则是按类别位置计数,与数据值无关。散点图和气泡图使用数值坐标轴而非文本类别坐标轴。对于日期坐标轴,请使用更改类别坐标轴中描述的基于时间的主单位和比例。

设置类别坐标轴值的日期格式

示例用四个年度值替换默认图表数据。日期以 OLE Automation 序列号存储在第一个工作表(索引 0)中,计算方式为自 1899 年 12 月 30 日起的天数。JavaScript 计算使用 UTC 时间戳并除以每天 86,400,000 毫秒。使用setCategoryAxisType并传入CategoryAxisType.Date,调用setNumberFormatLinkedToSource并传入false,再将yyyy传给setNumberFormat,使类别标签独立于单元格格式显示四位数年份。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation();
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().addChart(aspose.slides.ChartType.Line, 50, 50, 450, 300);

    chart.getChartData().getCategories().clear();
    chart.getChartData().getSeries().clear();

    var workbook = chart.getChartData().getChartDataWorkbook();
    workbook.clear(0);

    var baseDate = Date.UTC(1899, 11, 30);

    var series = chart.getChartData().getSeries().add(aspose.slides.ChartType.Line);
    for (var i = 0; i < 4; i++) {
        var date = Date.UTC(2015 + i, 0, 1);
        var categoryCell = workbook.getCell(0, i + 1, 0, (date - baseDate) / 86400000);
        chart.getChartData().getCategories().add(categoryCell);

        var valueCell = workbook.getCell(0, i + 1, 1, i + 1);
        series.getDataPoints().addDataPointForLineSeries(valueCell);
    }

    chart.getAxes().getHorizontalAxis().setCategoryAxisType(aspose.slides.CategoryAxisType.Date);
    chart.getAxes().getHorizontalAxis().setNumberFormatLinkedToSource(false);
    chart.getAxes().getHorizontalAxis().setNumberFormat("yyyy");

    presentation.save("DateAxisFormat.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

为图表坐标轴标题设置旋转角度

在垂直坐标轴上调用setTitle并传入true,提供标题文本,然后使用setRotationAngle旋转标题。角度以度为单位;本示例将值坐标轴标题旋转 90 度后保存柱形图。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation();
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().addChart(aspose.slides.ChartType.ClusteredColumn, 50, 50, 450, 300);
    chart.getAxes().getVerticalAxis().setTitle(true);
    chart.getAxes().getVerticalAxis().getTitle().addTextFrameForOverriding("Value");
    chart.getAxes().getVerticalAxis().getTitle().getTextFormat().getTextBlockFormat().setRotationAngle(90);

    presentation.save("RotatedAxisTitle.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

设置类别或数值坐标轴的位置

使用setAxisBetweenCategories控制数值坐标轴是跨越类别坐标轴之间还是在类别刻度线上交叉。此设置适用于类别坐标轴。示例在柱形图的水平类别坐标轴上将其设为true并保存结果。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation();
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().addChart(aspose.slides.ChartType.ClusteredColumn, 50, 50, 450, 300);
    chart.getAxes().getHorizontalAxis().setAxisBetweenCategories(true);

    presentation.save("AxisBetweenCategories.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

设置图表数值坐标轴的显示单位

使用setDisplayUnit在不更改底层数据的情况下缩放数值坐标轴标签。将DisplayUnitType设为Millions时,60000000 将显示为 60。示例创建柱形图并将其垂直坐标轴的显示单位设为百万。

var aspose = aspose || {};
aspose.slides = require("aspose.slides.via.java");

var presentation = new aspose.slides.Presentation();
try {
    var slide = presentation.getSlides().get_Item(0);

    var chart = slide.getShapes().addChart(aspose.slides.ChartType.ClusteredColumn, 50, 50, 450, 300);
    chart.getAxes().getVerticalAxis().setDisplayUnit(aspose.slides.DisplayUnitType.Millions);

    presentation.save("Result.pptx", aspose.slides.SaveFormat.Pptx);
} finally {
    presentation.dispose();
}

常见问题

如何设置一个坐标轴与另一个坐标轴相交的值(坐标轴交叉)?

使用setCrossType选择交叉行为。若要指定数值交叉点,使用setCrossAt。这些设置可将坐标轴交叉移动到合适的基准线。

如何相对于坐标轴定位刻度标签?

调用setTickLabelPosition并使用TickLabelPositionType:Low、High、NextTo 或 None。若要控制刻度线本身,使用setMajorTickMark或setMinorTickMark,它们与标签定位分离。