如何读取 Jasperreports 在 Chart Customizer 中传递的 Locale?

How to read Locale passed by Jasperreports in Chart Customizer?

(我的问题基于 2016 年 4 月的 this HARDCODED 示例,并且正在寻求更新的动态答案,因为 "bug" 已修复 - 在定制器中没有可用的语言环境)

/* -Hardcoded example */
getNumberInstance(Locale.US)); //"Locale.US" is hardcoded rather than using the locale set in the report

目标:将 jasper 报告中设置的语言环境传递给图表并使用图表定制器读取。

问题:在定制器Class(写在Java中)这个命令不包含任何东西:JRParameter.REPORT_LOCALE.

public class AssetsChartMod implements JRChartCustomizer {

    public void customize(JFreeChart chart, JRChart jasperChart) {

            /* ----> */
            System.out.println( JRParameter.REPORT_LOCALE ); // PRINTS NOTHING

不幸的是,我们无法从 JRChart 对象中获取报表的参数。这将是从参数映射中获取 Locale 的最简单方法。

但是我们可以执行这个技巧:

  1. jrxml 文件中为图表添加 属性 locale

带有图表声明的 jrxml 文件片段:

<pie3DChart>
    <chart customizerClass="ru.alex.PieChartCustomizer" theme="aegean">
        <reportElement positionType="Float" x="0" y="0" width="100" height="100">
            <propertyExpression name="locale"><![CDATA[((java.util.Locale) ($P{REPORT_PARAMETERS_MAP}.get("REPORT_LOCALE"))).toString()]]></propertyExpression>
        </reportElement>

属性只能是String类型,所以我才进行了cast at expression。

  1. JRChartCustomizer class 我得到 属性 的帮助 JRChart.getPropertiesMap() 方法。

在我的例子中,包名称是 ru.alex.

public class PieChartCustomizer implements JRChartCustomizer {

    private static final String LOCALE_PROPERTY = "locale"; // the same name as at jrxml file
    private static final Locale DEFAULT_LOCALE = Locale.ENGLISH;

    @Override
    public void customize(JFreeChart chart, JRChart jasperChart) {
        PiePlot pieChart = (PiePlot) chart.getPlot();
        JRPropertiesMap map = jasperChart.getPropertiesMap();

        Locale locale = DEFAULT_LOCALE; // this is default Locale if property was not set
        if (map != null && !map.isEmpty()) {
            if (!isNullOrEmpty(map.getProperty(LOCALE_PROPERTY))) {
                locale = Locale.forLanguageTag(map.getProperty(LOCALE_PROPERTY).replace("_", "-")); // here we have Locale passed via property 'locale'. Replacement applied: en_GB -> en-GB, for example
            }
        }

        // some actions 
    }

    private static boolean isNullOrEmpty(String string) {
        return string == null || string.isEmpty();
    }
}

瞧,我们在定制器中获得了报告的语言环境。