forked from I2P_Developers/i2p.i2p
Console: Update rrd4j to 3.9.1 preview
from rrd4j github head. Includes our ImageWorker contribution which should speed up rendering.
This commit is contained in:
@ -267,7 +267,7 @@ Applications:
|
||||
See licenses/LICENSE-Apache2.0.txt
|
||||
See licenses/LICENSE-ECLIPSE-1.0.html
|
||||
|
||||
RRD4J 3.9 (jrobin.jar):
|
||||
RRD4J 3.9.1 (jrobin.jar):
|
||||
Copyright (c) 2001-2005 Sasa Markovic and Ciaran Treanor.
|
||||
Copyright (c) 2011 The OpenNMS Group, Inc.
|
||||
Copyright 2011 The RRD4J Authors.
|
||||
|
@ -66,7 +66,7 @@
|
||||
<property name="workspace.changes.tr" value="" />
|
||||
<jar destfile="./build/jrobin.jar" basedir="./build/obj" includes="**/*.class">
|
||||
<manifest>
|
||||
<attribute name="Implementation-Version" value="3.8" />
|
||||
<attribute name="Implementation-Version" value="3.9.1" />
|
||||
<attribute name="Built-By" value="${build.built-by}" />
|
||||
<attribute name="Build-Date" value="${build.timestamp}" />
|
||||
<attribute name="Base-Revision" value="${workspace.version}" />
|
||||
|
@ -310,10 +310,7 @@ public abstract class RrdBackendFactory implements Closeable {
|
||||
}
|
||||
@Override
|
||||
public void clear() {
|
||||
try {
|
||||
backend.close();
|
||||
} catch (IOException e) {
|
||||
}
|
||||
// backend doesn't need to be closed here as it already happens in RrdBackend.rrdClose()
|
||||
backend = null;
|
||||
super.clear();
|
||||
}
|
||||
|
@ -300,6 +300,9 @@ public class RrdDbPool {
|
||||
RrdEntry ref;
|
||||
try {
|
||||
ref = getEntry(dburi, false);
|
||||
} catch (IllegalStateException e) {
|
||||
// This means that corresponding database has been already closed before, so returning immediately.
|
||||
return;
|
||||
} catch (InterruptedException e) {
|
||||
Thread.currentThread().interrupt();
|
||||
throw new IllegalStateException("Release interrupted for " + rrdDb.getPath(), e);
|
||||
|
161
apps/jrobin/java/src/org/rrd4j/graph/BufferedImageWorker.java
Normal file
161
apps/jrobin/java/src/org/rrd4j/graph/BufferedImageWorker.java
Normal file
@ -0,0 +1,161 @@
|
||||
package org.rrd4j.graph;
|
||||
|
||||
import java.awt.*;
|
||||
import java.awt.geom.AffineTransform;
|
||||
import java.awt.image.BufferedImage;
|
||||
import java.io.IOException;
|
||||
import java.io.OutputStream;
|
||||
|
||||
import javax.imageio.IIOImage;
|
||||
import javax.imageio.ImageIO;
|
||||
import javax.imageio.ImageWriteParam;
|
||||
import javax.imageio.ImageWriter;
|
||||
import javax.imageio.spi.ImageWriterSpi;
|
||||
import javax.imageio.stream.ImageOutputStream;
|
||||
|
||||
class BufferedImageWorker extends ImageWorker {
|
||||
|
||||
static class Builder {
|
||||
private int width = 1;
|
||||
private int height = 1;
|
||||
private RrdGraphDef gdef;
|
||||
private ImageWriter writer;
|
||||
private ImageWriteParam imageWriteParam;
|
||||
BufferedImageWorker build() {
|
||||
return new BufferedImageWorker(this);
|
||||
}
|
||||
private ImageWriteParam getImageParams() {
|
||||
ImageWriteParam iwp = writer.getDefaultWriteParam();
|
||||
ImageWriterSpi imgProvider = writer.getOriginatingProvider();
|
||||
//If lossy compression, use the quality
|
||||
if (! imgProvider.isFormatLossless()) {
|
||||
iwp.setCompressionMode(ImageWriteParam.MODE_EXPLICIT);
|
||||
iwp.setCompressionQuality(gdef.imageQuality);
|
||||
}
|
||||
|
||||
if (iwp.canWriteProgressive()) {
|
||||
iwp.setProgressiveMode(gdef.interlaced ? ImageWriteParam.MODE_DEFAULT:ImageWriteParam.MODE_DISABLED);
|
||||
}
|
||||
return iwp;
|
||||
}
|
||||
|
||||
public Builder setWidth(int width) {
|
||||
this.width = width;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder setHeight(int height) {
|
||||
this.height = height;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder setGdef(RrdGraphDef gdef) {
|
||||
this.gdef = gdef;
|
||||
if (this.writer == null) {
|
||||
this.writer = ImageIO.getImageWritersByFormatName(gdef.imageFormat).next();
|
||||
}
|
||||
if (this.imageWriteParam == null) {
|
||||
this.imageWriteParam = getImageParams();
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder setWriter(ImageWriter writer) {
|
||||
this.writer = writer;
|
||||
if (this.imageWriteParam == null) {
|
||||
this.imageWriteParam = getImageParams();
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder setImageWriteParam(ImageWriteParam imageWriteParam) {
|
||||
this.imageWriteParam = imageWriteParam;
|
||||
return this;
|
||||
}
|
||||
}
|
||||
public static Builder getBuilder() {
|
||||
return new Builder();
|
||||
}
|
||||
|
||||
private BufferedImage img;
|
||||
private int imgWidth;
|
||||
private int imgHeight;
|
||||
private AffineTransform initialAffineTransform;
|
||||
private final ImageWriter writer;
|
||||
private final ImageWriteParam iwp;
|
||||
|
||||
private BufferedImageWorker(Builder builder) {
|
||||
this.imgHeight = builder.height;
|
||||
this.imgWidth = builder.width;
|
||||
this.writer = builder.writer;
|
||||
this.iwp = builder.imageWriteParam;
|
||||
resize(imgWidth, imgHeight);
|
||||
}
|
||||
|
||||
/*
|
||||
* Not for use, only for tests
|
||||
*/
|
||||
BufferedImageWorker(int width, int height) {
|
||||
this.imgHeight = height;
|
||||
this.imgWidth = width;
|
||||
this.writer = ImageIO.getImageWritersByFormatName("png").next();
|
||||
this.iwp = writer.getDefaultWriteParam();
|
||||
resize(imgWidth, imgHeight);
|
||||
}
|
||||
|
||||
protected void resize(int width, int height) {
|
||||
imgWidth = width;
|
||||
imgHeight = height;
|
||||
img = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
|
||||
|
||||
Graphics2D g2d = img.createGraphics();
|
||||
setG2d(g2d);
|
||||
initialAffineTransform = g2d.getTransform();
|
||||
|
||||
setAntiAliasing(false);
|
||||
setTextAntiAliasing(false);
|
||||
|
||||
g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
|
||||
}
|
||||
|
||||
protected void reset(Graphics2D g2d) {
|
||||
g2d.setTransform(initialAffineTransform);
|
||||
g2d.setClip(0, 0, imgWidth, imgHeight);
|
||||
}
|
||||
|
||||
protected void makeImage(OutputStream stream) throws IOException {
|
||||
BufferedImage outputImage = img;
|
||||
|
||||
ImageWriterSpi imgProvider = writer.getOriginatingProvider();
|
||||
|
||||
img.coerceData(false);
|
||||
|
||||
// Some format can't manage 16M colors images
|
||||
// JPEG don't like transparency
|
||||
if (! imgProvider.canEncodeImage(outputImage) || "image/jpeg".equalsIgnoreCase(imgProvider.getMIMETypes()[0])) {
|
||||
int w = img.getWidth();
|
||||
int h = img.getHeight();
|
||||
outputImage = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB);
|
||||
outputImage.getGraphics().drawImage(img, 0, 0, w, h, null);
|
||||
if (! imgProvider.canEncodeImage(outputImage)) {
|
||||
throw new IllegalArgumentException("Invalid image type");
|
||||
}
|
||||
}
|
||||
|
||||
if (! imgProvider.canEncodeImage(outputImage)) {
|
||||
throw new IllegalArgumentException("Invalid image type");
|
||||
}
|
||||
|
||||
try (ImageOutputStream imageStream = ImageIO.createImageOutputStream(stream)) {
|
||||
writer.setOutput(imageStream);
|
||||
writer.write(null, new IIOImage(outputImage, null, null), iwp);
|
||||
imageStream.flush();
|
||||
} catch (IOException e) {
|
||||
writer.abort();
|
||||
throw e;
|
||||
} finally {
|
||||
writer.dispose();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
@ -1,223 +1,211 @@
|
||||
package org.rrd4j.graph;
|
||||
|
||||
import java.awt.Font;
|
||||
import java.awt.Graphics2D;
|
||||
import java.awt.Paint;
|
||||
import java.awt.RenderingHints;
|
||||
import java.awt.Stroke;
|
||||
import java.awt.*;
|
||||
import java.awt.font.LineMetrics;
|
||||
import java.awt.geom.AffineTransform;
|
||||
import java.awt.image.BufferedImage;
|
||||
import java.io.ByteArrayOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.OutputStream;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.nio.file.Paths;
|
||||
|
||||
import javax.imageio.IIOImage;
|
||||
import javax.imageio.ImageIO;
|
||||
import javax.imageio.ImageWriteParam;
|
||||
import javax.imageio.ImageWriter;
|
||||
import javax.imageio.spi.ImageWriterSpi;
|
||||
import javax.imageio.stream.ImageOutputStream;
|
||||
/**
|
||||
* An abstract class, that allows to use custom {@link Graphics2D}. To use it the construct should build it and call
|
||||
* {@link #setG2d(Graphics2D)} when finished.
|
||||
*/
|
||||
public abstract class ImageWorker {
|
||||
|
||||
class ImageWorker {
|
||||
private static final String DUMMY_TEXT = "Dummy";
|
||||
private static final int IMG_BUFFER_CAPACITY = 10000; // bytes
|
||||
|
||||
private BufferedImage img;
|
||||
private Graphics2D g2d;
|
||||
private int imgWidth, imgHeight;
|
||||
private AffineTransform initialAffineTransform;
|
||||
|
||||
ImageWorker(int width, int height) {
|
||||
resize(width, height);
|
||||
}
|
||||
|
||||
void resize(int width, int height) {
|
||||
protected void setG2d(Graphics2D g2d) {
|
||||
if (g2d != null) {
|
||||
dispose();
|
||||
}
|
||||
|
||||
imgWidth = width;
|
||||
imgHeight = height;
|
||||
img = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
|
||||
|
||||
g2d = img.createGraphics();
|
||||
initialAffineTransform = g2d.getTransform();
|
||||
|
||||
setAntiAliasing(false);
|
||||
setTextAntiAliasing(false);
|
||||
|
||||
g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
|
||||
this.g2d = g2d;
|
||||
}
|
||||
|
||||
void clip(int x, int y, int width, int height) {
|
||||
protected abstract void resize(int width, int height);
|
||||
|
||||
protected void clip(int x, int y, int width, int height) {
|
||||
g2d.setClip(x, y, width, height);
|
||||
}
|
||||
|
||||
void transform(int x, int y, double angle) {
|
||||
protected void transform(int x, int y, double angle) {
|
||||
g2d.translate(x, y);
|
||||
g2d.rotate(angle);
|
||||
}
|
||||
|
||||
void reset() {
|
||||
g2d.setTransform(initialAffineTransform);
|
||||
g2d.setClip(0, 0, imgWidth, imgHeight);
|
||||
protected void reset() {
|
||||
reset(g2d);
|
||||
}
|
||||
|
||||
void fillRect(int x, int y, int width, int height, Paint paint) {
|
||||
/**
|
||||
* reset the dimensions of the {@link Graphics2D}
|
||||
*/
|
||||
protected abstract void reset(Graphics2D g2d);
|
||||
|
||||
protected void fillRect(int x, int y, int width, int height, Paint paint) {
|
||||
g2d.setPaint(paint);
|
||||
g2d.fillRect(x, y, width, height);
|
||||
}
|
||||
|
||||
void fillPolygon(int[] x, int[] y, Paint paint) {
|
||||
g2d.setPaint(paint);
|
||||
g2d.fillPolygon(x, y, x.length);
|
||||
}
|
||||
|
||||
void fillPolygon(double[] x, double yBottom, double[] yTop, Paint paint) {
|
||||
protected void fillPolygon(double[] x, double yBottom, double[] yTop, Paint paint) {
|
||||
g2d.setPaint(paint);
|
||||
PathIterator path = new PathIterator(yTop);
|
||||
for (int[] pos = path.getNextPath(); pos != null; pos = path.getNextPath()) {
|
||||
int start = pos[0], end = pos[1], n = end - start;
|
||||
int[] xDev = new int[n + 2], yDev = new int[n + 2];
|
||||
int c = 0;
|
||||
for (int i = start; i < end; i++) {
|
||||
xDev[i - start] = (int) x[i];
|
||||
yDev[i - start] = (int) yTop[i];
|
||||
int cx = (int) x[i];
|
||||
int cy = (int) yTop[i];
|
||||
if (c == 0 || cx != xDev[c - 1] || cy != yDev[c - 1]) {
|
||||
if (c >= 2 && cy == yDev[c - 1] && cy == yDev[c - 2]) {
|
||||
// collapse horizontal lines
|
||||
xDev[c - 1] = cx;
|
||||
} else {
|
||||
xDev[c] = cx;
|
||||
yDev[c++] = cy;
|
||||
}
|
||||
}
|
||||
}
|
||||
xDev[n] = xDev[n - 1];
|
||||
xDev[n + 1] = xDev[0];
|
||||
yDev[n] = yDev[n + 1] = (int) yBottom;
|
||||
g2d.fillPolygon(xDev, yDev, xDev.length);
|
||||
g2d.drawPolygon(xDev, yDev, xDev.length);
|
||||
xDev[c] = xDev[c - 1];
|
||||
xDev[c + 1] = xDev[0];
|
||||
yDev[c] = yDev[c + 1] = (int) yBottom;
|
||||
g2d.fillPolygon(xDev, yDev, c + 2);
|
||||
}
|
||||
}
|
||||
|
||||
void fillPolygon(double[] x, double[] yBottom, double[] yTop, Paint paint) {
|
||||
protected void fillPolygon(double[] x, double[] yBottom, double[] yTop, Paint paint) {
|
||||
g2d.setPaint(paint);
|
||||
PathIterator path = new PathIterator(yTop);
|
||||
for (int[] pos = path.getNextPath(); pos != null; pos = path.getNextPath()) {
|
||||
int start = pos[0], end = pos[1], n = end - start;
|
||||
int[] xDev = new int[n * 2], yDev = new int[n * 2];
|
||||
int c = 0;
|
||||
for (int i = start; i < end; i++) {
|
||||
int ix1 = i - start, ix2 = n * 2 - 1 - i + start;
|
||||
xDev[ix1] = xDev[ix2] = (int) x[i];
|
||||
yDev[ix1] = (int) yTop[i];
|
||||
yDev[ix2] = (int) yBottom[i];
|
||||
int cx = (int) x[i];
|
||||
int cy = (int) yTop[i];
|
||||
if (c == 0 || cx != xDev[c - 1] || cy != yDev[c - 1]) {
|
||||
if (c >= 2 && cy == yDev[c - 1] && cy == yDev[c - 2]) {
|
||||
// collapse horizontal lines
|
||||
xDev[c - 1] = cx;
|
||||
} else {
|
||||
xDev[c] = cx;
|
||||
yDev[c++] = cy;
|
||||
}
|
||||
}
|
||||
}
|
||||
g2d.fillPolygon(xDev, yDev, xDev.length);
|
||||
for (int i = end - 1; i >= start; i--) {
|
||||
int cx = (int) x[i];
|
||||
int cy = (int) yBottom[i];
|
||||
if (c == 0 || cx != xDev[c - 1] || cy != yDev[c - 1]) {
|
||||
if (c >= 2 && cy == yDev[c - 1] && cy == yDev[c - 2]) {
|
||||
// collapse horizontal lines
|
||||
xDev[c - 1] = cx;
|
||||
} else {
|
||||
xDev[c] = cx;
|
||||
yDev[c++] = cy;
|
||||
}
|
||||
}
|
||||
}
|
||||
g2d.fillPolygon(xDev, yDev, c);
|
||||
}
|
||||
}
|
||||
|
||||
void drawLine(int x1, int y1, int x2, int y2, Paint paint, Stroke stroke) {
|
||||
protected void drawLine(int x1, int y1, int x2, int y2, Paint paint, Stroke stroke) {
|
||||
g2d.setStroke(stroke);
|
||||
g2d.setPaint(paint);
|
||||
g2d.drawLine(x1, y1, x2, y2);
|
||||
}
|
||||
|
||||
void drawPolyline(int[] x, int[] y, Paint paint, Stroke stroke) {
|
||||
g2d.setStroke(stroke);
|
||||
g2d.setPaint(paint);
|
||||
g2d.drawPolyline(x, y, x.length);
|
||||
}
|
||||
|
||||
void drawPolyline(double[] x, double[] y, Paint paint, Stroke stroke) {
|
||||
protected void drawPolyline(double[] x, double[] y, Paint paint, Stroke stroke) {
|
||||
g2d.setPaint(paint);
|
||||
g2d.setStroke(stroke);
|
||||
PathIterator path = new PathIterator(y);
|
||||
for (int[] pos = path.getNextPath(); pos != null; pos = path.getNextPath()) {
|
||||
int start = pos[0], end = pos[1];
|
||||
int[] xDev = new int[end - start], yDev = new int[end - start];
|
||||
int c = 0;
|
||||
for (int i = start; i < end; i++) {
|
||||
xDev[i - start] = (int) x[i];
|
||||
yDev[i - start] = (int) y[i];
|
||||
int cx = (int) x[i];
|
||||
int cy = (int) y[i];
|
||||
if (c == 0 || cx != xDev[c - 1] || cy != yDev[c - 1]) {
|
||||
if (c >= 2 && cy == yDev[c - 1] && cy == yDev[c - 2]) {
|
||||
// collapse horizontal lines
|
||||
xDev[c - 1] = cx;
|
||||
} else {
|
||||
xDev[c] = cx;
|
||||
yDev[c++] = cy;
|
||||
}
|
||||
}
|
||||
}
|
||||
g2d.drawPolyline(xDev, yDev, xDev.length);
|
||||
g2d.drawPolyline(xDev, yDev, c);
|
||||
}
|
||||
}
|
||||
|
||||
void drawString(String text, int x, int y, Font font, Paint paint) {
|
||||
protected void drawString(String text, int x, int y, Font font, Paint paint) {
|
||||
g2d.setFont(font);
|
||||
g2d.setPaint(paint);
|
||||
g2d.drawString(text, x, y);
|
||||
}
|
||||
|
||||
double getFontAscent(Font font) {
|
||||
protected double getFontAscent(Font font) {
|
||||
LineMetrics lm = font.getLineMetrics(DUMMY_TEXT, g2d.getFontRenderContext());
|
||||
return lm.getAscent();
|
||||
}
|
||||
|
||||
double getFontHeight(Font font) {
|
||||
protected double getFontHeight(Font font) {
|
||||
LineMetrics lm = font.getLineMetrics(DUMMY_TEXT, g2d.getFontRenderContext());
|
||||
return lm.getAscent() + lm.getDescent();
|
||||
}
|
||||
|
||||
double getStringWidth(String text, Font font) {
|
||||
protected double getStringWidth(String text, Font font) {
|
||||
return font.getStringBounds(text, 0, text.length(), g2d.getFontRenderContext()).getBounds().getWidth();
|
||||
}
|
||||
|
||||
void setAntiAliasing(boolean enable) {
|
||||
protected void setAntiAliasing(boolean enable) {
|
||||
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
|
||||
enable ? RenderingHints.VALUE_ANTIALIAS_ON : RenderingHints.VALUE_ANTIALIAS_OFF);
|
||||
}
|
||||
|
||||
void setTextAntiAliasing(boolean enable) {
|
||||
protected void setTextAntiAliasing(boolean enable) {
|
||||
g2d.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING,
|
||||
enable ? RenderingHints.VALUE_TEXT_ANTIALIAS_ON : RenderingHints.VALUE_TEXT_ANTIALIAS_OFF);
|
||||
}
|
||||
|
||||
void dispose() {
|
||||
g2d.dispose();
|
||||
}
|
||||
|
||||
void makeImage(Object stream, ImageWriter writer, ImageWriteParam iwp) throws IOException {
|
||||
BufferedImage outputImage = img;
|
||||
|
||||
ImageWriterSpi imgProvider = writer.getOriginatingProvider();
|
||||
|
||||
img.coerceData(false);
|
||||
|
||||
// Some format can't manage 16M colors images
|
||||
// JPEG don't like transparency
|
||||
if (! imgProvider.canEncodeImage(outputImage) || "image/jpeg".equalsIgnoreCase(imgProvider.getMIMETypes()[0])) {
|
||||
int w = img.getWidth();
|
||||
int h = img.getHeight();
|
||||
outputImage = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB);
|
||||
outputImage.getGraphics().drawImage(img, 0, 0, w, h, null);
|
||||
if (! imgProvider.canEncodeImage(outputImage)) {
|
||||
throw new RuntimeException("Invalid image type");
|
||||
}
|
||||
}
|
||||
|
||||
if (! imgProvider.canEncodeImage(outputImage)) {
|
||||
throw new RuntimeException("Invalid image type");
|
||||
}
|
||||
|
||||
try (ImageOutputStream imageStream = ImageIO.createImageOutputStream(stream)) {
|
||||
writer.setOutput(imageStream);
|
||||
writer.write(null, new IIOImage(outputImage, null, null), iwp);
|
||||
imageStream.flush();
|
||||
} catch (IOException e) {
|
||||
writer.abort();
|
||||
throw e;
|
||||
} finally {
|
||||
writer.dispose();
|
||||
}
|
||||
}
|
||||
|
||||
void saveImage(String path, ImageWriter writer, ImageWriteParam iwp) throws IOException {
|
||||
makeImage(Paths.get(path).toFile(), writer, iwp);
|
||||
}
|
||||
|
||||
byte[] getImageBytes(ImageWriter writer, ImageWriteParam iwp) throws IOException {
|
||||
try (ByteArrayOutputStream stream = new ByteArrayOutputStream(IMG_BUFFER_CAPACITY)){
|
||||
makeImage(stream, writer, iwp);
|
||||
return stream.toByteArray();
|
||||
}
|
||||
}
|
||||
|
||||
void loadImage(RrdGraphDef.ImageSource imageSource, int x, int y, int w, int h) throws IOException {
|
||||
protected void loadImage(RrdGraphDef.ImageSource imageSource, int x, int y, int w, int h) throws IOException {
|
||||
BufferedImage wpImage = imageSource.apply(w, h).getSubimage(0, 0, w, h);
|
||||
g2d.drawImage(wpImage, new AffineTransform(1f, 0f, 0f, 1f, x, y), null);
|
||||
}
|
||||
|
||||
protected void dispose() {
|
||||
if (g2d != null) {
|
||||
g2d.dispose();
|
||||
}
|
||||
}
|
||||
|
||||
protected void makeImage(Path path) throws IOException {
|
||||
try (OutputStream os = Files.newOutputStream(path)) {
|
||||
makeImage(os);
|
||||
}
|
||||
}
|
||||
|
||||
protected abstract void makeImage(OutputStream os) throws IOException ;
|
||||
|
||||
protected void saveImage(String path) throws IOException {
|
||||
makeImage(Paths.get(path));
|
||||
}
|
||||
|
||||
protected byte[] getImageBytes() throws IOException {
|
||||
try (ByteArrayOutputStream stream = new ByteArrayOutputStream(IMG_BUFFER_CAPACITY)){
|
||||
makeImage(stream);
|
||||
return stream.toByteArray();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -12,10 +12,8 @@ import java.nio.file.Path;
|
||||
import java.nio.file.Paths;
|
||||
import java.util.Arrays;
|
||||
|
||||
import javax.imageio.ImageIO;
|
||||
import javax.imageio.ImageWriteParam;
|
||||
import javax.imageio.ImageWriter;
|
||||
import javax.imageio.spi.ImageWriterSpi;
|
||||
import javax.swing.ImageIcon;
|
||||
|
||||
import org.rrd4j.core.Util;
|
||||
@ -47,8 +45,6 @@ public class RrdGraph implements RrdGraphConstants {
|
||||
Mapper mapper;
|
||||
private final RrdGraphInfo info = new RrdGraphInfo();
|
||||
private final String signature;
|
||||
private final ImageWriter writer;
|
||||
private final ImageWriteParam param;
|
||||
|
||||
/**
|
||||
* Creates graph from the corresponding {@link org.rrd4j.graph.RrdGraphDef} object.
|
||||
@ -60,9 +56,8 @@ public class RrdGraph implements RrdGraphConstants {
|
||||
this.gdef = gdef;
|
||||
signature = gdef.getSignature();
|
||||
im = new ImageParameters();
|
||||
worker = new ImageWorker(1, 1); // Dummy worker, just to start with something
|
||||
writer = ImageIO.getImageWritersByFormatName(gdef.imageFormat).next();
|
||||
param = getImageParams();
|
||||
|
||||
worker = BufferedImageWorker.getBuilder().setGdef(gdef).build();
|
||||
try {
|
||||
createGraph();
|
||||
}
|
||||
@ -73,6 +68,28 @@ public class RrdGraph implements RrdGraphConstants {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Create graph from a custom image worker
|
||||
* @param gdef
|
||||
* @param worker
|
||||
* @throws IOException
|
||||
*/
|
||||
public RrdGraph(RrdGraphDef gdef, ImageWorker worker) throws IOException {
|
||||
this.gdef = gdef;
|
||||
signature = gdef.getSignature();
|
||||
im = new ImageParameters();
|
||||
this.worker = worker;
|
||||
try {
|
||||
createGraph();
|
||||
}
|
||||
finally {
|
||||
worker.dispose();
|
||||
this.worker = null;
|
||||
dproc = null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* <p>Creates graph from the corresponding {@link org.rrd4j.graph.RrdGraphDef} object.</p>
|
||||
* <p>The graph will be created using customs {@link javax.imageio.ImageWriter} and {@link javax.imageio.ImageWriteParam} given.</p>
|
||||
@ -88,9 +105,7 @@ public class RrdGraph implements RrdGraphConstants {
|
||||
this.gdef = gdef;
|
||||
signature = gdef.getSignature();
|
||||
im = new ImageParameters();
|
||||
worker = new ImageWorker(1, 1); // Dummy worker, just to start with something
|
||||
this.writer = writer;
|
||||
this.param = param;
|
||||
worker = BufferedImageWorker.getBuilder().setGdef(gdef).setWriter(writer).setImageWriteParam(param).build();
|
||||
try {
|
||||
createGraph();
|
||||
}
|
||||
@ -110,21 +125,6 @@ public class RrdGraph implements RrdGraphConstants {
|
||||
return info;
|
||||
}
|
||||
|
||||
private ImageWriteParam getImageParams() {
|
||||
ImageWriteParam iwp = writer.getDefaultWriteParam();
|
||||
ImageWriterSpi imgProvider = writer.getOriginatingProvider();
|
||||
//If lossy compression, use the quality
|
||||
if (! imgProvider.isFormatLossless()) {
|
||||
iwp.setCompressionMode(ImageWriteParam.MODE_EXPLICIT);
|
||||
iwp.setCompressionQuality(gdef.imageQuality);
|
||||
}
|
||||
|
||||
if (iwp.canWriteProgressive()) {
|
||||
iwp.setProgressiveMode(gdef.interlaced ? ImageWriteParam.MODE_DEFAULT:ImageWriteParam.MODE_DISABLED);
|
||||
}
|
||||
return iwp;
|
||||
}
|
||||
|
||||
private void createGraph() throws IOException {
|
||||
boolean lazy = lazyCheck();
|
||||
if (!lazy || gdef.printStatementCount() != 0) {
|
||||
@ -177,7 +177,7 @@ public class RrdGraph implements RrdGraphConstants {
|
||||
private void saveImage() throws IOException {
|
||||
if (! RrdGraphConstants.IN_MEMORY_IMAGE.equals(gdef.filename)) {
|
||||
Path imgpath = Paths.get(gdef.filename);
|
||||
worker.saveImage(gdef.filename, writer, param);
|
||||
worker.saveImage(gdef.filename);
|
||||
info.bytesSource = () -> {
|
||||
try {
|
||||
return Files.readAllBytes(imgpath);
|
||||
@ -194,7 +194,7 @@ public class RrdGraph implements RrdGraphConstants {
|
||||
};
|
||||
}
|
||||
else {
|
||||
byte[] content = worker.getImageBytes(writer, param);
|
||||
byte[] content = worker.getImageBytes();
|
||||
info.bytesSource = () -> Arrays.copyOf(content, content.length);
|
||||
info.bytesCount = () -> content.length;
|
||||
}
|
||||
|
Reference in New Issue
Block a user