Изображение как метка категории в диаграмме iReport - PullRequest
0 голосов
/ 16 октября 2018

Я пытаюсь создать гистограмму с изображениями для меток категорий (метки оси X).Для гистограммы по умолчанию результат выражения категории используется в качестве метки (и должен быть строкой).Как я могу настроить это, чтобы показать изображение вместо этого?Я написал скриптлет для заполнения переменной с помощью BufferedImages, теперь мне просто нужен способ их использования.Могу ли я сделать это с помощью класса настройщика диаграмм?Есть ли более простой / лучший способ?

1 Ответ

0 голосов
/ 19 октября 2018

Как вы сказали, вы можете сделать это с помощью собственного класса настройщика.Вот простой пример, который может быть дополнен вашими потребностями:

@Slf4j 
public class CategoryAxisWithImagesCustomizer extends JRAbstractChartCustomizer {
    public class CategoryAxisWithImages extends CategoryAxis {
        public CategoryAxisWithImages(String label) {
            super(label);
        }

        @Override
        protected Rectangle2D getLabelEnclosure(Graphics2D g2, RectangleEdge edge) {
            // enter max width and height of your images or you can do it dynamically
            return new Rectangle2D.Double(0, 0, 32, 32);
        }

        @Override
        protected AxisState drawCategoryLabels(Graphics2D g2, Rectangle2D plotArea, Rectangle2D dataArea, RectangleEdge edge, AxisState state, PlotRenderingInfo plotState) {
            if (!isTickLabelsVisible()) {
                return state;
            }

            List ticks = refreshTicks(g2, state, plotArea, edge);
            state.setTicks(ticks);
            for (int i = 0; i < ticks.size(); i++) {
                double x = getCategoryMiddle(i, ticks.size(), dataArea, edge);
                double y = state.getCursor() + getCategoryLabelPositionOffset();

                int value = (int) ((CategoryPlot) getPlot()).getDataset().getColumnKey(i);
                String imagePath = "logo_" + value + ".png";
                try {
                    InputStream imageStream = getClass().getResourceAsStream(imagePath);
                    // you can of course load images using different way - here I'm using index value from the dataset
                    BufferedImage image = ImageIO.read(imageStream);
                    g2.drawImage(image, (int) (x - image.getWidth() / 2d), (int) (y), image.getWidth(), image.getHeight(), Color.black, null);
                } catch (IOException e) {
                    log.error("Cannot load image {}", imagePath);
                }
            }
            state.cursorDown(state.getMax() + getCategoryLabelPositionOffset());
            return state;
        }
    }

    @Override
    public void customize(JFreeChart chart, JRChart jasperChart) {
        CategoryPlot plot = chart.getCategoryPlot();
        CategoryAxis categoryAxis = new CategoryAxisWithImages(plot.getDomainAxis().getLabel());
        plot.setDomainAxis(categoryAxis);
    }
}

В JasperReport JRXML вы можете зарегистрировать этот класс настройщика следующим образом:

    <barChart>
        <chart customizerClass="cz.trask.experiment.jr.CategoryAxisWithImagesCustomizer"
               isShowLegend="false">
            <reportElement x="0" y="0" width="550" height="348" uuid="a2cbb6b5-a76d-469b-8e8e-daa533260f20"/>
            <chartTitle/>
            <chartSubtitle/>
            <chartLegend/>
        </chart>
        ...
    </barChart>

И результат моего примера:: Example JasperReport with chart using images in category axis

...