Search in sources :

Example 1 with TexturePixel

use of com.jme3.scene.plugins.blender.textures.TexturePixel in project jmonkeyengine by jMonkeyEngine.

the class CombinedTexture method isWithoutAlpha.

/**
     * This method determines if the given texture has no alpha channel.
     * 
     * @param texture
     *            the texture to check for alpha channel
     * @return <b>true</b> if the texture has no alpha channel and <b>false</b>
     *         otherwise
     */
private boolean isWithoutAlpha(TextureData textureData, BlenderContext blenderContext) {
    ColorBand colorBand = new ColorBand(textureData.textureStructure, blenderContext);
    if (!colorBand.hasTransparencies()) {
        int type = ((Number) textureData.textureStructure.getFieldValue("type")).intValue();
        if (type == TextureHelper.TEX_MAGIC) {
            return true;
        }
        if (type == TextureHelper.TEX_VORONOI) {
            int voronoiColorType = ((Number) textureData.textureStructure.getFieldValue("vn_coltype")).intValue();
            // voronoiColorType == 0:
            return voronoiColorType != 0;
        // intensity, voronoiColorType
        // != 0: col1, col2 or col3
        }
        if (type == TextureHelper.TEX_CLOUDS) {
            int sType = ((Number) textureData.textureStructure.getFieldValue("stype")).intValue();
            // sType==0: without colors, sType==1: with
            return sType == 1;
        // colors
        }
        // checking the flat textures for alpha values presence
        if (type == TextureHelper.TEX_IMAGE) {
            Image image = textureData.texture.getImage();
            switch(image.getFormat()) {
                case BGR8:
                case DXT1:
                case Luminance16F:
                case Luminance32F:
                case Luminance8:
                case RGB111110F:
                case RGB16F:
                case RGB32F:
                case RGB565:
                case RGB8:
                    // these types have no alpha by definition
                    return true;
                case ABGR8:
                case DXT1A:
                case DXT3:
                case DXT5:
                case Luminance16FAlpha16F:
                case Luminance8Alpha8:
                case RGBA16F:
                case RGBA32F:
                case RGBA8:
                case ARGB8:
                case BGRA8:
                case // with these types it is better to make sure if the texture is or is not transparent
                RGB5A1:
                    PixelInputOutput pixelInputOutput = PixelIOFactory.getPixelIO(image.getFormat());
                    TexturePixel pixel = new TexturePixel();
                    int depth = image.getDepth() == 0 ? 1 : image.getDepth();
                    for (int layerIndex = 0; layerIndex < depth; ++layerIndex) {
                        for (int x = 0; x < image.getWidth(); ++x) {
                            for (int y = 0; y < image.getHeight(); ++y) {
                                pixelInputOutput.read(image, layerIndex, pixel, x, y);
                                if (pixel.alpha < 1.0f) {
                                    return false;
                                }
                            }
                        }
                    }
                    return true;
                default:
                    throw new IllegalStateException("Unknown image format: " + image.getFormat());
            }
        }
    }
    return false;
}
Also used : PixelInputOutput(com.jme3.scene.plugins.blender.textures.io.PixelInputOutput) Image(com.jme3.texture.Image) BufferedImage(java.awt.image.BufferedImage)

Example 2 with TexturePixel

use of com.jme3.scene.plugins.blender.textures.TexturePixel in project jmonkeyengine by jMonkeyEngine.

the class CombinedTexture method generateSkyTexture.

/**
     * Generates a texture that will be used by the sky spatial.
     * The result texture has 6 layers. Every image in each layer has equal size and its shape is a square.
     * The size of each image is the maximum size (width or height) of the textures given.
     * The default sky generated texture size is used (this value is set in the BlenderKey) if no picture textures
     * are present or their sizes is lower than the generated texture size.
     * The textures of lower sizes are properly scaled.
     * All the textures are mixed into one and put as layers in the result texture.
     * 
     * @param horizontalColor
     *            the horizon color
     * @param zenithColor
     *            the zenith color
     * @param blenderContext
     *            the blender context
     * @return texture for the sky
     */
public TextureCubeMap generateSkyTexture(ColorRGBA horizontalColor, ColorRGBA zenithColor, BlenderContext blenderContext) {
    LOGGER.log(Level.FINE, "Preparing sky texture from {0} applied textures.", textureDatas.size());
    LOGGER.fine("Computing the texture size.");
    int size = -1;
    for (TextureData textureData : textureDatas) {
        if (textureData.texture instanceof Texture2D) {
            size = Math.max(textureData.texture.getImage().getWidth(), size);
            size = Math.max(textureData.texture.getImage().getHeight(), size);
        }
    }
    if (size < 0) {
        size = blenderContext.getBlenderKey().getSkyGeneratedTextureSize();
    }
    LOGGER.log(Level.FINE, "The sky texture size will be: {0}x{0}.", size);
    TextureCubeMap result = null;
    for (TextureData textureData : textureDatas) {
        TextureCubeMap texture = null;
        if (textureData.texture instanceof GeneratedTexture) {
            texture = ((GeneratedTexture) textureData.texture).generateSkyTexture(size, horizontalColor, zenithColor, blenderContext);
        } else {
            // first create a grayscale version of the image
            Image image = textureData.texture.getImage();
            if (image.getWidth() != image.getHeight() || image.getWidth() != size) {
                image = ImageUtils.resizeTo(image, size, size);
            }
            Image grayscaleImage = ImageUtils.convertToGrayscaleTexture(image);
            // add the sky colors to the image
            PixelInputOutput sourcePixelIO = PixelIOFactory.getPixelIO(grayscaleImage.getFormat());
            PixelInputOutput targetPixelIO = PixelIOFactory.getPixelIO(image.getFormat());
            TexturePixel texturePixel = new TexturePixel();
            for (int x = 0; x < image.getWidth(); ++x) {
                for (int y = 0; y < image.getHeight(); ++y) {
                    sourcePixelIO.read(grayscaleImage, 0, texturePixel, x, y);
                    // no matter which factor we use here, in grayscale they are all equal
                    texturePixel.intensity = texturePixel.red;
                    ImageUtils.color(texturePixel, horizontalColor, zenithColor);
                    targetPixelIO.write(image, 0, texturePixel, x, y);
                }
            }
            // create the cubemap texture from the coloured image
            ByteBuffer sourceData = image.getData(0);
            ArrayList<ByteBuffer> data = new ArrayList<ByteBuffer>(6);
            for (int i = 0; i < 6; ++i) {
                data.add(BufferUtils.clone(sourceData));
            }
            texture = new TextureCubeMap(new Image(image.getFormat(), image.getWidth(), image.getHeight(), 6, data, ColorSpace.Linear));
        }
        if (result == null) {
            result = texture;
        } else {
            ImageUtils.mix(result.getImage(), texture.getImage());
        }
    }
    return result;
}
Also used : Texture2D(com.jme3.texture.Texture2D) PixelInputOutput(com.jme3.scene.plugins.blender.textures.io.PixelInputOutput) TextureCubeMap(com.jme3.texture.TextureCubeMap) ArrayList(java.util.ArrayList) Image(com.jme3.texture.Image) BufferedImage(java.awt.image.BufferedImage) ByteBuffer(java.nio.ByteBuffer)

Example 3 with TexturePixel

use of com.jme3.scene.plugins.blender.textures.TexturePixel in project jmonkeyengine by jMonkeyEngine.

the class GeneratedTexture method generateSkyTexture.

/**
     * Creates a texture for the sky. The result texture has 6 layers.
     * @param size
     *            the size of the texture (width and height are equal)
     * @param horizontalColor
     *            the horizon color
     * @param zenithColor
     *            the zenith color
     * @param blenderContext
     *            the blender context
     * @return the sky texture
     */
public TextureCubeMap generateSkyTexture(int size, ColorRGBA horizontalColor, ColorRGBA zenithColor, BlenderContext blenderContext) {
    Image image = ImageUtils.createEmptyImage(Format.RGB8, size, size, 6);
    PixelInputOutput pixelIO = PixelIOFactory.getPixelIO(image.getFormat());
    TexturePixel pixel = new TexturePixel();
    float delta = 1 / (float) (size - 1);
    float sideV, sideS = 1, forwardU = 1, forwardV, upS;
    TempVars tempVars = TempVars.get();
    CastFunction castFunction = CAST_FUNCTIONS[blenderContext.getBlenderKey().getSkyGeneratedTextureShape().ordinal()];
    float castRadius = blenderContext.getBlenderKey().getSkyGeneratedTextureRadius();
    for (int x = 0; x < size; ++x) {
        sideV = 1;
        forwardV = 1;
        upS = 0;
        for (int y = 0; y < size; ++y) {
            castFunction.cast(tempVars.vect1.set(1, sideV, sideS), castRadius);
            textureGenerator.getPixel(pixel, tempVars.vect1.x, tempVars.vect1.y, tempVars.vect1.z);
            // right
            pixelIO.write(image, NEGATIVE_X, ImageUtils.color(pixel, horizontalColor, zenithColor), x, y);
            castFunction.cast(tempVars.vect1.set(0, sideV, 1 - sideS), castRadius);
            textureGenerator.getPixel(pixel, tempVars.vect1.x, tempVars.vect1.y, tempVars.vect1.z);
            // left
            pixelIO.write(image, POSITIVE_X, ImageUtils.color(pixel, horizontalColor, zenithColor), x, y);
            castFunction.cast(tempVars.vect1.set(forwardU, forwardV, 0), castRadius);
            textureGenerator.getPixel(pixel, tempVars.vect1.x, tempVars.vect1.y, tempVars.vect1.z);
            // front
            pixelIO.write(image, POSITIVE_Z, ImageUtils.color(pixel, horizontalColor, zenithColor), x, y);
            castFunction.cast(tempVars.vect1.set(1 - forwardU, forwardV, 1), castRadius);
            textureGenerator.getPixel(pixel, tempVars.vect1.x, tempVars.vect1.y, tempVars.vect1.z);
            // back
            pixelIO.write(image, NEGATIVE_Z, ImageUtils.color(pixel, horizontalColor, zenithColor), x, y);
            castFunction.cast(tempVars.vect1.set(forwardU, 0, upS), castRadius);
            textureGenerator.getPixel(pixel, tempVars.vect1.x, tempVars.vect1.y, tempVars.vect1.z);
            // top
            pixelIO.write(image, NEGATIVE_Y, ImageUtils.color(pixel, horizontalColor, zenithColor), x, y);
            castFunction.cast(tempVars.vect1.set(forwardU, 1, 1 - upS), castRadius);
            textureGenerator.getPixel(pixel, tempVars.vect1.x, tempVars.vect1.y, tempVars.vect1.z);
            // bottom
            pixelIO.write(image, POSITIVE_Y, ImageUtils.color(pixel, horizontalColor, zenithColor), x, y);
            sideV = FastMath.clamp(sideV - delta, 0, 1);
            forwardV = FastMath.clamp(forwardV - delta, 0, 1);
            upS = FastMath.clamp(upS + delta, 0, 1);
        }
        sideS = FastMath.clamp(sideS - delta, 0, 1);
        forwardU = FastMath.clamp(forwardU - delta, 0, 1);
    }
    tempVars.release();
    return new TextureCubeMap(image);
}
Also used : PixelInputOutput(com.jme3.scene.plugins.blender.textures.io.PixelInputOutput) TextureCubeMap(com.jme3.texture.TextureCubeMap) TempVars(com.jme3.util.TempVars) Image(com.jme3.texture.Image)

Example 4 with TexturePixel

use of com.jme3.scene.plugins.blender.textures.TexturePixel in project jmonkeyengine by jMonkeyEngine.

the class ImageUtils method merge.

/**
     * This method merges two given images. The result is stored in the
     * 'target' image.
     * 
     * @param targetImage
     *            the target image
     * @param sourceImage
     *            the source image
     */
public static void merge(Image targetImage, Image sourceImage) {
    if (sourceImage.getDepth() != targetImage.getDepth()) {
        throw new IllegalArgumentException("The given images should have the same depth to merge them!");
    }
    if (sourceImage.getWidth() != targetImage.getWidth()) {
        throw new IllegalArgumentException("The given images should have the same width to merge them!");
    }
    if (sourceImage.getHeight() != targetImage.getHeight()) {
        throw new IllegalArgumentException("The given images should have the same height to merge them!");
    }
    PixelInputOutput sourceIO = PixelIOFactory.getPixelIO(sourceImage.getFormat());
    PixelInputOutput targetIO = PixelIOFactory.getPixelIO(targetImage.getFormat());
    TexturePixel sourcePixel = new TexturePixel();
    TexturePixel targetPixel = new TexturePixel();
    int depth = targetImage.getDepth() == 0 ? 1 : targetImage.getDepth();
    for (int layerIndex = 0; layerIndex < depth; ++layerIndex) {
        for (int x = 0; x < sourceImage.getWidth(); ++x) {
            for (int y = 0; y < sourceImage.getHeight(); ++y) {
                sourceIO.read(sourceImage, layerIndex, sourcePixel, x, y);
                targetIO.read(targetImage, layerIndex, targetPixel, x, y);
                targetPixel.merge(sourcePixel);
                targetIO.write(targetImage, layerIndex, targetPixel, x, y);
            }
        }
    }
}
Also used : PixelInputOutput(com.jme3.scene.plugins.blender.textures.io.PixelInputOutput)

Example 5 with TexturePixel

use of com.jme3.scene.plugins.blender.textures.TexturePixel in project jmonkeyengine by jMonkeyEngine.

the class TextureHelper method getSubimage.

/**
     * This method returns subimage of the give image. The subimage is
     * constrained by the rectangle coordinates. The source image is unchanged.
     * 
     * @param image
     *            the image to be subimaged
     * @param minX
     *            minimum X position
     * @param minY
     *            minimum Y position
     * @param maxX
     *            maximum X position
     * @param maxY
     *            maximum Y position
     * @return a part of the given image
     */
public Image getSubimage(Image image, int minX, int minY, int maxX, int maxY) {
    if (minY > maxY) {
        throw new IllegalArgumentException("Minimum Y value is higher than maximum Y value!");
    }
    if (minX > maxX) {
        throw new IllegalArgumentException("Minimum Y value is higher than maximum Y value!");
    }
    if (image.getData().size() > 1) {
        throw new IllegalArgumentException("Only flat images are allowed for subimage operation!");
    }
    if (image.getMipMapSizes() != null) {
        LOGGER.warning("Subimaging image with mipmaps is not yet supported!");
    }
    int width = maxX - minX;
    int height = maxY - minY;
    ByteBuffer data = BufferUtils.createByteBuffer(width * height * (image.getFormat().getBitsPerPixel() >> 3));
    Image result = new Image(image.getFormat(), width, height, data, ColorSpace.sRGB);
    PixelInputOutput pixelIO = PixelIOFactory.getPixelIO(image.getFormat());
    TexturePixel pixel = new TexturePixel();
    for (int x = minX; x < maxX; ++x) {
        for (int y = minY; y < maxY; ++y) {
            pixelIO.read(image, 0, pixel, x, y);
            pixelIO.write(result, 0, pixel, x - minX, y - minY);
        }
    }
    return result;
}
Also used : PixelInputOutput(com.jme3.scene.plugins.blender.textures.io.PixelInputOutput) Image(com.jme3.texture.Image) ByteBuffer(java.nio.ByteBuffer)

Aggregations

PixelInputOutput (com.jme3.scene.plugins.blender.textures.io.PixelInputOutput)12 Image (com.jme3.texture.Image)9 ByteBuffer (java.nio.ByteBuffer)7 TexturePixel (com.jme3.scene.plugins.blender.textures.TexturePixel)6 ArrayList (java.util.ArrayList)6 Format (com.jme3.texture.Image.Format)4 TextureCubeMap (com.jme3.texture.TextureCubeMap)3 BufferedImage (java.awt.image.BufferedImage)3 ColorRGBA (com.jme3.math.ColorRGBA)1 ColorBand (com.jme3.scene.plugins.blender.textures.ColorBand)1 CombinedTexture (com.jme3.scene.plugins.blender.textures.CombinedTexture)1 TextureHelper (com.jme3.scene.plugins.blender.textures.TextureHelper)1 Texture2D (com.jme3.texture.Texture2D)1 TempVars (com.jme3.util.TempVars)1