org.bytedeco.javacv.Java2DFrameConverter Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of javacv Show documentation
Show all versions of javacv Show documentation
Java interface to OpenCV and more
/*
* Copyright (C) 2015 Samuel Audet
*
* Licensed either under the Apache License, Version 2.0, or (at your option)
* under the terms of the GNU General Public License as published by
* the Free Software Foundation (subject to the "Classpath" exception),
* either version 2, or any later version (collectively, the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
* http://www.gnu.org/licenses/
* http://www.gnu.org/software/classpath/license.html
*
* or as provided in the LICENSE.txt file that accompanied this code.
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.bytedeco.javacv;
import java.awt.Rectangle;
import java.awt.Transparency;
import java.awt.color.ColorSpace;
import java.awt.image.BufferedImage;
import java.awt.image.ColorModel;
import java.awt.image.ComponentColorModel;
import java.awt.image.ComponentSampleModel;
import java.awt.image.DataBuffer;
import java.awt.image.DataBufferByte;
import java.awt.image.DataBufferDouble;
import java.awt.image.DataBufferFloat;
import java.awt.image.DataBufferInt;
import java.awt.image.DataBufferShort;
import java.awt.image.DataBufferUShort;
import java.awt.image.MultiPixelPackedSampleModel;
import java.awt.image.Raster;
import java.awt.image.SampleModel;
import java.awt.image.SinglePixelPackedSampleModel;
import java.awt.image.WritableRaster;
import java.nio.Buffer;
import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.nio.DoubleBuffer;
import java.nio.FloatBuffer;
import java.nio.IntBuffer;
import java.nio.ShortBuffer;
/**
* A utility class to copy data between {@link Frame} and {@link BufferedImage}.
* Since {@link BufferedImage} does not support NIO buffers, we cannot share
* allocated memory with {@link Frame}.
*
* @author Samuel Audet
*/
public class Java2DFrameConverter extends FrameConverter {
@Override public Frame convert(BufferedImage img) {
return getFrame(img);
}
@Override public BufferedImage convert(Frame frame) {
return getBufferedImage(frame);
}
public static BufferedImage cloneBufferedImage(BufferedImage bufferedImage) {
if (bufferedImage == null) {
return null;
}
BufferedImage bi = bufferedImage;
int type = bi.getType();
if (type == BufferedImage.TYPE_CUSTOM) {
return new BufferedImage(bi.getColorModel(),
bi.copyData(null), bi.isAlphaPremultiplied(), null);
} else {
return new BufferedImage(bi.getWidth(), bi.getHeight(), type);
}
}
public static final byte[]
gamma22 = new byte[256],
gamma22inv = new byte[256];
static {
for (int i = 0; i < 256; i++) {
gamma22[i] = (byte)Math.round(Math.pow(i/255.0, 2.2)*255.0);
gamma22inv[i] = (byte)Math.round(Math.pow(i/255.0, 1/2.2)*255.0);
}
}
public static int decodeGamma22(int value) {
return gamma22[value & 0xFF] & 0xFF;
}
public static int encodeGamma22(int value) {
return gamma22inv[value & 0xFF] & 0xFF;
}
public static void flipCopyWithGamma(ByteBuffer srcBuf, int srcStep,
ByteBuffer dstBuf, int dstStep, boolean signed, double gamma, boolean flip, int channels) {
assert srcBuf != dstBuf;
int w = Math.min(srcStep, dstStep);
int srcLine = srcBuf.position(), dstLine = dstBuf.position();
byte[] buffer = new byte[channels];
while (srcLine < srcBuf.capacity() && dstLine < dstBuf.capacity()) {
if (flip) {
srcBuf.position(srcBuf.capacity() - srcLine - srcStep);
} else {
srcBuf.position(srcLine);
}
dstBuf.position(dstLine);
w = Math.min(Math.min(w, srcBuf.remaining()), dstBuf.remaining());
if (signed) {
if (channels > 1) {
for (int x = 0; x < w; x+=channels) {
for (int z = 0; z < channels; z++) {
int in = srcBuf.get();
byte out;
if (gamma == 1.0) {
out = (byte)in;
} else {
out = (byte)Math.round(Math.pow((double)in/Byte.MAX_VALUE, gamma)*Byte.MAX_VALUE);
}
buffer[z] = out;
}
for (int z = channels-1; z >= 0; z--) {
dstBuf.put(buffer[z]);
}
}
} else {
for (int x = 0; x < w; x++) {
int in = srcBuf.get();
byte out;
if (gamma == 1.0) {
out = (byte)in;
} else {
out = (byte)Math.round(Math.pow((double)in/Byte.MAX_VALUE, gamma)*Byte.MAX_VALUE);
}
dstBuf.put(out);
}
}
} else {
if (channels > 1) {
for (int x = 0; x < w; x+=channels) {
for (int z = 0; z < channels; z++) {
byte out;
int in = srcBuf.get() & 0xFF;
if (gamma == 1.0) {
out = (byte)in;
} else if (gamma == 2.2) {
out = gamma22[in];
} else if (gamma == 1/2.2) {
out = gamma22inv[in];
} else {
out = (byte)Math.round(Math.pow((double)in/0xFF, gamma)*0xFF);
}
buffer[z] = out;
}
for (int z = channels-1; z >= 0; z--) {
dstBuf.put(buffer[z]);
}
}
} else {
for (int x = 0; x < w; x++) {
byte out;
int in = srcBuf.get() & 0xFF;
if (gamma == 1.0) {
out = (byte)in;
} else if (gamma == 2.2) {
out = gamma22[in];
} else if (gamma == 1/2.2) {
out = gamma22inv[in];
} else {
out = (byte)Math.round(Math.pow((double)in/0xFF, gamma)*0xFF);
}
dstBuf.put(out);
}
}
}
srcLine += srcStep;
dstLine += dstStep;
}
}
public static void flipCopyWithGamma(ShortBuffer srcBuf, int srcStep,
ShortBuffer dstBuf, int dstStep, boolean signed, double gamma, boolean flip, int channels) {
assert srcBuf != dstBuf;
int w = Math.min(srcStep, dstStep);
int srcLine = srcBuf.position(), dstLine = dstBuf.position();
short[] buffer = new short[channels];
while (srcLine < srcBuf.capacity() && dstLine < dstBuf.capacity()) {
if (flip) {
srcBuf.position(srcBuf.capacity() - srcLine - srcStep);
} else {
srcBuf.position(srcLine);
}
dstBuf.position(dstLine);
w = Math.min(Math.min(w, srcBuf.remaining()), dstBuf.remaining());
if (signed) {
if (channels > 1) {
for (int x = 0; x < w; x+=channels) {
for (int z = 0; z < channels; z++) {
int in = srcBuf.get();
short out;
if (gamma == 1.0) {
out = (short)in;
} else {
out = (short)Math.round(Math.pow((double)in/Short.MAX_VALUE, gamma)*Short.MAX_VALUE);
}
buffer[z] = out;
}
for (int z = channels-1; z >= 0; z--) {
dstBuf.put(buffer[z]);
}
}
} else {
for (int x = 0; x < w; x++) {
int in = srcBuf.get();
short out;
if (gamma == 1.0) {
out = (short)in;
} else {
out = (short)Math.round(Math.pow((double)in/Short.MAX_VALUE, gamma)*Short.MAX_VALUE);
}
dstBuf.put(out);
}
}
} else {
if (channels > 1) {
for (int x = 0; x < w; x+=channels) {
for (int z = 0; z < channels; z++) {
int in = srcBuf.get();
short out;
if (gamma == 1.0) {
out = (short)in;
} else {
out = (short)Math.round(Math.pow((double)in/0xFFFF, gamma)*0xFFFF);
}
buffer[z] = out;
}
for (int z = channels-1; z >= 0; z--) {
dstBuf.put(buffer[z]);
}
}
} else {
for (int x = 0; x < w; x++) {
int in = srcBuf.get() & 0xFFFF;
short out;
if (gamma == 1.0) {
out = (short)in;
} else {
out = (short)Math.round(Math.pow((double)in/0xFFFF, gamma)*0xFFFF);
}
dstBuf.put(out);
}
}
}
srcLine += srcStep;
dstLine += dstStep;
}
}
public static void flipCopyWithGamma(IntBuffer srcBuf, int srcStep,
IntBuffer dstBuf, int dstStep, double gamma, boolean flip, int channels) {
assert srcBuf != dstBuf;
int w = Math.min(srcStep, dstStep);
int srcLine = srcBuf.position(), dstLine = dstBuf.position();
int[] buffer = new int[channels];
while (srcLine < srcBuf.capacity() && dstLine < dstBuf.capacity()) {
if (flip) {
srcBuf.position(srcBuf.capacity() - srcLine - srcStep);
} else {
srcBuf.position(srcLine);
}
dstBuf.position(dstLine);
w = Math.min(Math.min(w, srcBuf.remaining()), dstBuf.remaining());
if (channels > 1) {
for (int x = 0; x < w; x+=channels) {
for (int z = 0; z < channels; z++) {
int in = srcBuf.get();
int out;
if (gamma == 1.0) {
out = (int)in;
} else {
out = (int)Math.round(Math.pow((double)in/Integer.MAX_VALUE, gamma)*Integer.MAX_VALUE);
}
buffer[z] = out;
}
for (int z = channels-1; z >= 0; z--) {
dstBuf.put(buffer[z]);
}
}
} else {
for (int x = 0; x < w; x++) {
int in = srcBuf.get();
int out;
if (gamma == 1.0) {
out = in;
} else {
out = (int)Math.round(Math.pow((double)in/Integer.MAX_VALUE, gamma)*Integer.MAX_VALUE);
}
dstBuf.put(out);
}
}
srcLine += srcStep;
dstLine += dstStep;
}
}
public static void flipCopyWithGamma(FloatBuffer srcBuf, int srcStep,
FloatBuffer dstBuf, int dstStep, double gamma, boolean flip, int channels) {
assert srcBuf != dstBuf;
int w = Math.min(srcStep, dstStep);
int srcLine = srcBuf.position(), dstLine = dstBuf.position();
float[] buffer = new float[channels];
while (srcLine < srcBuf.capacity() && dstLine < dstBuf.capacity()) {
if (flip) {
srcBuf.position(srcBuf.capacity() - srcLine - srcStep);
} else {
srcBuf.position(srcLine);
}
dstBuf.position(dstLine);
w = Math.min(Math.min(w, srcBuf.remaining()), dstBuf.remaining());
if (channels > 1) {
for (int x = 0; x < w; x+=channels) {
for (int z = 0; z < channels; z++) {
float in = srcBuf.get();
float out;
if (gamma == 1.0) {
out = in;
} else {
out = (float)Math.pow(in, gamma);
}
buffer[z] = out;
}
for (int z = channels-1; z >= 0; z--) {
dstBuf.put(buffer[z]);
}
}
} else {
for (int x = 0; x < w; x++) {
float in = srcBuf.get();
float out;
if (gamma == 1.0) {
out = in;
} else {
out = (float)Math.pow(in, gamma);
}
dstBuf.put(out);
}
}
srcLine += srcStep;
dstLine += dstStep;
}
}
public static void flipCopyWithGamma(DoubleBuffer srcBuf, int srcStep,
DoubleBuffer dstBuf, int dstStep, double gamma, boolean flip, int channels) {
assert srcBuf != dstBuf;
int w = Math.min(srcStep, dstStep);
int srcLine = srcBuf.position(), dstLine = dstBuf.position();
double[] buffer = new double[channels];
while (srcLine < srcBuf.capacity() && dstLine < dstBuf.capacity()) {
if (flip) {
srcBuf.position(srcBuf.capacity() - srcLine - srcStep);
} else {
srcBuf.position(srcLine);
}
dstBuf.position(dstLine);
w = Math.min(Math.min(w, srcBuf.remaining()), dstBuf.remaining());
if (channels > 1) {
for (int x = 0; x < w; x+=channels) {
for (int z = 0; z < channels; z++) {
double in = srcBuf.get();
double out;
if (gamma == 1.0) {
out = in;
} else {
out = Math.pow(in, gamma);
}
buffer[z] = out;
}
for (int z = channels-1; z >= 0; z--) {
dstBuf.put(buffer[z]);
}
}
} else {
for (int x = 0; x < w; x++) {
double in = srcBuf.get();
double out;
if (gamma == 1.0) {
out = in;
} else {
out = Math.pow(in, gamma);
}
dstBuf.put(out);
}
}
srcLine += srcStep;
dstLine += dstStep;
}
}
public static void applyGamma(Frame frame, double gamma) {
applyGamma(frame.image[0].position(0), frame.imageDepth, frame.imageStride, gamma);
}
public static void applyGamma(Buffer buffer, int depth, int stride, double gamma) {
if (gamma == 1.0) {
return;
}
switch (depth) {
case Frame.DEPTH_UBYTE:
flipCopyWithGamma(((ByteBuffer)buffer).asReadOnlyBuffer(), stride, (ByteBuffer)buffer, stride, false, gamma, false, 0);
break;
case Frame.DEPTH_BYTE:
flipCopyWithGamma(((ByteBuffer)buffer).asReadOnlyBuffer(), stride, (ByteBuffer)buffer, stride, true, gamma, false, 0);
break;
case Frame.DEPTH_USHORT:
flipCopyWithGamma(((ShortBuffer)buffer).asReadOnlyBuffer(), stride, (ShortBuffer)buffer, stride, false, gamma, false, 0);
break;
case Frame.DEPTH_SHORT:
flipCopyWithGamma(((ShortBuffer)buffer).asReadOnlyBuffer(), stride, (ShortBuffer)buffer, stride, true, gamma, false, 0);
break;
case Frame.DEPTH_INT:
flipCopyWithGamma(((IntBuffer)buffer).asReadOnlyBuffer(), stride, (IntBuffer)buffer, stride, gamma, false, 0);
break;
case Frame.DEPTH_FLOAT:
flipCopyWithGamma(((FloatBuffer)buffer).asReadOnlyBuffer(), stride, (FloatBuffer)buffer, stride, gamma, false, 0);
break;
case Frame.DEPTH_DOUBLE:
flipCopyWithGamma(((DoubleBuffer)buffer).asReadOnlyBuffer(), stride, (DoubleBuffer)buffer, stride, gamma, false, 0);
break;
default:
assert false;
}
}
public static void copy(Frame frame, BufferedImage bufferedImage) {
copy(frame, bufferedImage, 1.0);
}
public static void copy(Frame frame, BufferedImage bufferedImage, double gamma) {
copy(frame, bufferedImage, gamma, false, null);
}
public static void copy(Frame frame, BufferedImage bufferedImage, double gamma, boolean flipChannels, Rectangle roi) {
Buffer in = frame.image[0].position(roi == null ? 0 : roi.y*frame.imageStride + roi.x*frame.imageChannels);
SampleModel sm = bufferedImage.getSampleModel();
Raster r = bufferedImage.getRaster();
DataBuffer out = r.getDataBuffer();
int x = -r.getSampleModelTranslateX();
int y = -r.getSampleModelTranslateY();
int step = sm.getWidth()*sm.getNumBands();
int channels = sm.getNumBands();
if (sm instanceof ComponentSampleModel) {
step = ((ComponentSampleModel)sm).getScanlineStride();
channels = ((ComponentSampleModel)sm).getPixelStride();
} else if (sm instanceof SinglePixelPackedSampleModel) {
step = ((SinglePixelPackedSampleModel)sm).getScanlineStride();
channels = 1;
} else if (sm instanceof MultiPixelPackedSampleModel) {
step = ((MultiPixelPackedSampleModel)sm).getScanlineStride();
channels = ((MultiPixelPackedSampleModel)sm).getPixelBitStride()/8; // ??
}
int start = y*step + x*channels;
if (out instanceof DataBufferByte) {
byte[] a = ((DataBufferByte)out).getData();
flipCopyWithGamma((ByteBuffer)in, frame.imageStride, ByteBuffer.wrap(a, start, a.length - start), step, false, gamma, false, flipChannels ? channels : 0);
} else if (out instanceof DataBufferDouble) {
double[] a = ((DataBufferDouble)out).getData();
flipCopyWithGamma((DoubleBuffer)in, frame.imageStride, DoubleBuffer.wrap(a, start, a.length - start), step, gamma, false, flipChannels ? channels : 0);
} else if (out instanceof DataBufferFloat) {
float[] a = ((DataBufferFloat)out).getData();
flipCopyWithGamma((FloatBuffer)in, frame.imageStride, FloatBuffer.wrap(a, start, a.length - start), step, gamma, false, flipChannels ? channels : 0);
} else if (out instanceof DataBufferInt) {
int[] a = ((DataBufferInt)out).getData();
int stride = frame.imageStride;
if (in instanceof ByteBuffer) {
in = ((ByteBuffer)in).order(flipChannels ? ByteOrder.LITTLE_ENDIAN : ByteOrder.BIG_ENDIAN).asIntBuffer();
stride /= 4;
}
flipCopyWithGamma((IntBuffer)in, stride, IntBuffer.wrap(a, start, a.length - start), step, gamma, false, flipChannels ? channels : 0);
} else if (out instanceof DataBufferShort) {
short[] a = ((DataBufferShort)out).getData();
flipCopyWithGamma((ShortBuffer)in, frame.imageStride, ShortBuffer.wrap(a, start, a.length - start), step, true, gamma, false, flipChannels ? channels : 0);
} else if (out instanceof DataBufferUShort) {
short[] a = ((DataBufferUShort)out).getData();
flipCopyWithGamma((ShortBuffer)in, frame.imageStride, ShortBuffer.wrap(a, start, a.length - start), step, false, gamma, false, flipChannels ? channels : 0);
} else {
assert false;
}
}
public static void copy(BufferedImage image, Frame frame) {
copy(image, frame, 1.0);
}
public static void copy(BufferedImage image, Frame frame, double gamma) {
copy(image, frame, gamma, false, null);
}
public static void copy(BufferedImage image, Frame frame, double gamma, boolean flipChannels, Rectangle roi) {
Buffer out = frame.image[0].position(roi == null ? 0 : roi.y*frame.imageStride + roi.x*frame.imageChannels);
SampleModel sm = image.getSampleModel();
Raster r = image.getRaster();
DataBuffer in = r.getDataBuffer();
int x = -r.getSampleModelTranslateX();
int y = -r.getSampleModelTranslateY();
int step = sm.getWidth()*sm.getNumBands();
int channels = sm.getNumBands();
if (sm instanceof ComponentSampleModel) {
step = ((ComponentSampleModel)sm).getScanlineStride();
channels = ((ComponentSampleModel)sm).getPixelStride();
} else if (sm instanceof SinglePixelPackedSampleModel) {
step = ((SinglePixelPackedSampleModel)sm).getScanlineStride();
channels = 1;
} else if (sm instanceof MultiPixelPackedSampleModel) {
step = ((MultiPixelPackedSampleModel)sm).getScanlineStride();
channels = ((MultiPixelPackedSampleModel)sm).getPixelBitStride()/8; // ??
}
int start = y*step + x*channels;
if (in instanceof DataBufferByte) {
byte[] a = ((DataBufferByte)in).getData();
flipCopyWithGamma(ByteBuffer.wrap(a, start, a.length - start), step, (ByteBuffer)out, frame.imageStride, false, gamma, false, flipChannels ? channels : 0);
} else if (in instanceof DataBufferDouble) {
double[] a = ((DataBufferDouble)in).getData();
flipCopyWithGamma(DoubleBuffer.wrap(a, start, a.length - start), step, (DoubleBuffer)out, frame.imageStride, gamma, false, flipChannels ? channels : 0);
} else if (in instanceof DataBufferFloat) {
float[] a = ((DataBufferFloat)in).getData();
flipCopyWithGamma(FloatBuffer.wrap(a, start, a.length - start), step, (FloatBuffer)out, frame.imageStride, gamma, false, flipChannels ? channels : 0);
} else if (in instanceof DataBufferInt) {
int[] a = ((DataBufferInt)in).getData();
int stride = frame.imageStride;
if (out instanceof ByteBuffer) {
out = ((ByteBuffer)out).order(flipChannels ? ByteOrder.LITTLE_ENDIAN : ByteOrder.BIG_ENDIAN).asIntBuffer();
stride /= 4;
}
flipCopyWithGamma(IntBuffer.wrap(a, start, a.length - start), step, (IntBuffer)out, stride, gamma, false, flipChannels ? channels : 0);
} else if (in instanceof DataBufferShort) {
short[] a = ((DataBufferShort)in).getData();
flipCopyWithGamma(ShortBuffer.wrap(a, start, a.length - start), step, (ShortBuffer)out, frame.imageStride, true, gamma, false, flipChannels ? channels : 0);
} else if (in instanceof DataBufferUShort) {
short[] a = ((DataBufferUShort)in).getData();
flipCopyWithGamma(ShortBuffer.wrap(a, start, a.length - start), step, (ShortBuffer)out, frame.imageStride, false, gamma, false, flipChannels ? channels : 0);
} else {
assert false;
}
}
protected BufferedImage bufferedImage = null;
public static int getBufferedImageType(Frame frame) {
// precanned BufferedImage types are confusing... in practice though,
// they all use the sRGB color model when blitting:
// http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=5051418
// and we should use them because they are *A LOT* faster with Java 2D.
// workaround: do gamma correction ourselves ("gamma" parameter)
// since we'll never use getRGB() and setRGB(), right?
int type = BufferedImage.TYPE_CUSTOM;
if (frame.imageChannels == 1) {
if (frame.imageDepth == Frame.DEPTH_UBYTE || frame.imageDepth == Frame.DEPTH_BYTE) {
type = BufferedImage.TYPE_BYTE_GRAY;
} else if (frame.imageDepth == Frame.DEPTH_USHORT) {
type = BufferedImage.TYPE_USHORT_GRAY;
}
} else if (frame.imageChannels == 3) {
if (frame.imageDepth == Frame.DEPTH_UBYTE || frame.imageDepth == Frame.DEPTH_BYTE) {
type = BufferedImage.TYPE_3BYTE_BGR;
}
} else if (frame.imageChannels == 4) {
// The channels end up reversed of what we need for OpenCL.
// We work around this in copyTo() and copyFrom() by
// inversing the channels to let us use RGBA in our IplImage.
if (frame.imageDepth == Frame.DEPTH_UBYTE || frame.imageDepth == Frame.DEPTH_BYTE) {
type = BufferedImage.TYPE_4BYTE_ABGR;
}
}
return type;
}
public BufferedImage getBufferedImage(Frame frame) {
return getBufferedImage(frame, 1.0);
}
public BufferedImage getBufferedImage(Frame frame, double gamma) {
return getBufferedImage(frame, gamma, false, null);
}
public BufferedImage getBufferedImage(Frame frame, double gamma, boolean flipChannels, ColorSpace cs) {
if (frame == null || frame.image == null) {
return null;
}
int type = getBufferedImageType(frame);
if (bufferedImage == null || bufferedImage.getWidth() != frame.imageWidth
|| bufferedImage.getHeight() != frame.imageHeight || bufferedImage.getType() != type) {
bufferedImage = type == BufferedImage.TYPE_CUSTOM || cs != null ? null
: new BufferedImage(frame.imageWidth, frame.imageHeight, type);
}
if (bufferedImage == null) {
boolean alpha = false;
int[] offsets = null;
if (frame.imageChannels == 1) {
alpha = false;
if (cs == null) {
cs = ColorSpace.getInstance(ColorSpace.CS_GRAY);
}
offsets = new int[] {0};
} else if (frame.imageChannels == 3) {
alpha = false;
if (cs == null) {
cs = ColorSpace.getInstance(ColorSpace.CS_LINEAR_RGB);
}
// raster in "BGR" order like OpenCV..
offsets = new int[] {2, 1, 0};
} else if (frame.imageChannels == 4) {
alpha = true;
if (cs == null) {
cs = ColorSpace.getInstance(ColorSpace.CS_LINEAR_RGB);
}
// raster in "RGBA" order for OpenCL.. alpha needs to be last
offsets = new int[] {0, 1, 2, 3};
} else {
assert false;
}
ColorModel cm = null;
WritableRaster wr = null;
if (frame.imageDepth == Frame.DEPTH_UBYTE || frame.imageDepth == Frame.DEPTH_BYTE) {
cm = new ComponentColorModel(cs, alpha,
false, Transparency.OPAQUE, DataBuffer.TYPE_BYTE);
wr = Raster.createWritableRaster(new ComponentSampleModel(
DataBuffer.TYPE_BYTE, frame.imageWidth, frame.imageHeight, frame.imageChannels, frame.imageStride,
offsets), null);
} else if (frame.imageDepth == Frame.DEPTH_USHORT) {
cm = new ComponentColorModel(cs, alpha,
false, Transparency.OPAQUE, DataBuffer.TYPE_USHORT);
wr = Raster.createWritableRaster(new ComponentSampleModel(
DataBuffer.TYPE_USHORT, frame.imageWidth, frame.imageHeight, frame.imageChannels, frame.imageStride,
offsets), null);
} else if (frame.imageDepth == Frame.DEPTH_SHORT) {
cm = new ComponentColorModel(cs, alpha,
false, Transparency.OPAQUE, DataBuffer.TYPE_SHORT);
wr = Raster.createWritableRaster(new ComponentSampleModel(
DataBuffer.TYPE_SHORT, frame.imageWidth, frame.imageHeight, frame.imageChannels, frame.imageStride,
offsets), null);
} else if (frame.imageDepth == Frame.DEPTH_INT) {
cm = new ComponentColorModel(cs, alpha,
false, Transparency.OPAQUE, DataBuffer.TYPE_INT);
wr = Raster.createWritableRaster(new ComponentSampleModel(
DataBuffer.TYPE_INT, frame.imageWidth, frame.imageHeight, frame.imageChannels, frame.imageStride,
offsets), null);
} else if (frame.imageDepth == Frame.DEPTH_FLOAT) {
cm = new ComponentColorModel(cs, alpha,
false, Transparency.OPAQUE, DataBuffer.TYPE_FLOAT);
wr = Raster.createWritableRaster(new ComponentSampleModel(
DataBuffer.TYPE_FLOAT, frame.imageWidth, frame.imageHeight, frame.imageChannels, frame.imageStride,
offsets), null);
} else if (frame.imageDepth == Frame.DEPTH_DOUBLE) {
cm = new ComponentColorModel(cs, alpha,
false, Transparency.OPAQUE, DataBuffer.TYPE_DOUBLE);
wr = Raster.createWritableRaster(new ComponentSampleModel(
DataBuffer.TYPE_DOUBLE, frame.imageWidth, frame.imageHeight, frame.imageChannels, frame.imageStride,
offsets), null);
} else {
assert false;
}
bufferedImage = new BufferedImage(cm, wr, false, null);
}
if (bufferedImage != null) {
copy(frame, bufferedImage, gamma, flipChannels, null);
}
return bufferedImage;
}
/**
* Returns a Frame based on a BufferedImage.
*/
public Frame getFrame(BufferedImage image) {
return getFrame(image, 1.0);
}
/**
* Returns a Frame based on a BufferedImage, and given gamma.
*/
public Frame getFrame(BufferedImage image, double gamma) {
return getFrame(image, gamma, false);
}
/**
* Returns a Frame based on a BufferedImage, given gamma, and inverted channels flag.
*/
public Frame getFrame(BufferedImage image, double gamma, boolean flipChannels) {
if (image == null) {
return null;
}
SampleModel sm = image.getSampleModel();
int depth = 0, numChannels = sm.getNumBands();
switch (image.getType()) {
case BufferedImage.TYPE_INT_RGB:
case BufferedImage.TYPE_INT_ARGB:
case BufferedImage.TYPE_INT_ARGB_PRE:
case BufferedImage.TYPE_INT_BGR:
depth = Frame.DEPTH_UBYTE;
numChannels = 4;
break;
}
if (depth == 0 || numChannels == 0) {
switch (sm.getDataType()) {
case DataBuffer.TYPE_BYTE: depth = Frame.DEPTH_UBYTE; break;
case DataBuffer.TYPE_USHORT: depth = Frame.DEPTH_USHORT; break;
case DataBuffer.TYPE_SHORT: depth = Frame.DEPTH_SHORT; break;
case DataBuffer.TYPE_INT: depth = Frame.DEPTH_INT; break;
case DataBuffer.TYPE_FLOAT: depth = Frame.DEPTH_FLOAT; break;
case DataBuffer.TYPE_DOUBLE: depth = Frame.DEPTH_DOUBLE; break;
default: assert false;
}
}
if (frame == null || frame.imageWidth != image.getWidth() || frame.imageHeight != image.getHeight()
|| frame.imageDepth != depth || frame.imageChannels != numChannels) {
frame = new Frame(image.getWidth(), image.getHeight(), depth, numChannels);
}
copy(image, frame, gamma, flipChannels, null);
return frame;
}
}
© 2015 - 2024 Weber Informatics LLC | Privacy Policy