Java 在libgdx 3D中对立方体进行纹理处理

Java 在libgdx 3D中对立方体进行纹理处理,java,3d,libgdx,Java,3d,Libgdx,我编写了以下类来在libgdx中创建多维数据集模型。 这是我用作输入的纹理文件 该代码生成以下立方体(取决于纹理)。 你知道怎么解决这个问题吗?我试着读过这篇文章,但仍然不能完全理解这个问题 编辑1: 将每个纹理设置为空后,新材质(TextureAttribute.createDiffuse(type.textureRegionTop))中除外我得到了以下结果: 让我们回顾一下libGDX中的类Texture和texturereregion: Teture:tetxure是一种(最常见的

我编写了以下类来在libgdx中创建多维数据集模型。

这是我用作输入的纹理文件

该代码生成以下立方体(取决于纹理)。

你知道怎么解决这个问题吗?我试着读过这篇文章,但仍然不能完全理解这个问题

编辑1:

将每个纹理设置为空后,新材质(TextureAttribute.createDiffuse(type.textureRegionTop))中除外我得到了以下结果:


让我们回顾一下libGDX中的类
Texture
texturereregion

  • Teture:tetxure是一种(最常见的2D)图像,其目的是将其粘贴到3D多边形上,以提供更多的视觉细节

  • 纹理区域:为了提高效率和方便起见,您的图像文件就是这样。因此,对于本身不是单一纹理的图像,可以将图像的部分定义为单独的纹理区域

从libgdxapi的角度来看,有两种方法可以告诉它使用TextureRegion:

  • 调用
    createDiffuse(TextureRegion)
    ,将图像文件的固定区域设置为纹理

  • 调用
    createDiffuse(纹理)
    将整个纹理作为材质加载,然后调用
    setUVRange(TextureRegion)

  • 您的错误是不适当地混合了这两种方法:调用
    createDiffuse(TextureRegion)
    ,然后还调用
    setUVRange(TextureRegion)
    ,因此定义了两次纹理区域。我猜这会导致纹理区域内的tetxure区域大小正好为一个像素(因为有16x16像素的16x16纹理),这可以解释您的平面颜色结果

    最简单的修复方法是使用数字2和
    createDiffuse(type.textureRegionTop)
    替换为
    createDiffuse(texture)
    为了完整性,我还将在下面演示数字1


    之前:

    之后:

    我还使用
    BlendingAttribute(GL20.GL\u SRC\u ALPHA,GL20.GL\u ONE\u减去\u SRC\u ALPHA)为玻璃添加了透明度

    并使用
    IntAttribute.createCullFace(GL20.GL\u NONE)
    DepthTestAttribute(false)
    关闭背面消隐:

    在OpenGL中,立方体指向正方向的一侧,即+Y方向,但我认为您可以自己解决这个问题。(:


    这是一个完整的工作示例。使用他们的工具创建一个最小的libGDX项目,并将纹理保存为“minecraft.png”,例如
    android/assets
    。我使用Kotlin而不是Java,因为我有一个Kotlin项目,但您只需要在
    modelBuilder.begin()之前的两行中更改代码
    .end()
    无论如何(和glClearColor):

    包io.github.l0lk.zombieyeti.block;
    导入com.badlogic.gdx.ApplicationAdapter
    导入com.badlogic.gdx.gdx
    导入com.badlogic.gdx.graphics*
    导入com.badlogic.gdx.graphics.g2d.TextureRegion
    导入com.badlogic.gdx.graphics.g3d*
    导入com.badlogic.gdx.graphics.g3d.attributes*
    导入com.badlogic.gdx.graphics.g3d.utils.ModelBuilder
    枚举类块类型(变量nameca:String、变量textureTopX:Int、变量textureTopY:Int、变量textureSideX:Int、变量textureSideY:Int、变量textureBottomX:Int、变量textureBottomY:Int){
    草(“泥土”,0,0,3,0,2,0),
    石头(“石头”,1,0,1,0,1,0),
    木板(“木板”,4,0,4,0,4,0),
    玻璃(“玻璃”,1,3,1,3,1,3);
    var textureRegionTop:TextureRegion?=null
    var textureRegionSide:TextureRegion?=null
    var textureRegionBottom:TextureRegion?=null
    变量模型:模型?=null
    伴星{
    var纹理_宽度=16
    有趣的createTexturesAndModels(纹理:纹理?){
    val modelBuilder=modelBuilder()
    对于(键入值()){
    type.textureRegionTop=纹理区域(纹理,type.textureTopX*纹理宽度,type.textureTopY*纹理宽度,纹理宽度,纹理宽度)
    type.textureRegionSide=纹理区域(纹理,type.textureSideX*纹理宽度,type.textureSideY*纹理宽度,纹理宽度,纹理宽度)
    type.textureRegionBottom=TextureRegion(纹理,type.textureBottomX*纹理宽度,type.textureBottomY*纹理宽度,纹理宽度,纹理宽度)
    val attr=(VertexAttributes.Usage.Position或VertexAttributes.Usage.Normal或VertexAttributes.Usage.TextureCoordinates).toLong()
    val MATERIALTRS=arrayOf(混合属性(GL20.GL_SRC_ALPHA,GL20.GL_ONE_减去_SRC_ALPHA),IntAttribute.createCullFace(GL20.GL_NONE),DepthTestAttribute(false))
    modelBuilder.begin()
    modelBuilder.part(“长方体”,GL20.GL_三角形,属性,材质(TextureAttribute.createDiffuse(type.textureRegionTop),*materialAttrs))
    .rect(-0.5f,-0.5f,-0.5f,-0.5f,0.5f,-0.5f,0.5f,0.5f,-0.5f,0.5f,-0.5f,-0.5f,0f,-1f)
    modelBuilder.part(“长方体”,GL20.GL_三角形,属性,材质(TextureAttribute.createDiffuse(type.textureRegionSide),*materialAttrs))
    .rect(-0.5f,0.5f,0.5f,-0.5f,-0.5f,0.5f,0.5f,-0.5f,0.5f,0.5f,0.5f,0.5f,0.5f,0f,0f,1f)
    modelBuilder.part(“长方体”,GL20.GL_三角形,属性,材质(TextureAttribute.createDiffuse(type.textureRegionSide),*materialAttrs))
    .rect(-0.5f,-0.5f,0.5f,-0.5f,-0.5f,-0.5f,0.5f,-0.5f,-0.5f,0.5f,-0.5f,0.5f,0f,-1f,0f)
    modelBuilder.part(“长方体”,GL20.GL_三角形,属性,材质(TextureAttribute.createDiffuse(type.textureRegionSide),*materialAttrs))
    .rect(-0.5f,0.5f,-0.5f,-0.5f,0.5f,0.5f,0.5f,0.5f,0.5f,0.5f,0.5f,-0.5f,0f,1f,0f)
    modelBuilder.part(“box”,GL20.GL_三角形,属性,材质(Textu
    
    package io.github.l0lk.zombieyeti.block;
    
    import com.badlogic.gdx.graphics.GL20;
    import com.badlogic.gdx.graphics.Texture;
    import com.badlogic.gdx.graphics.VertexAttributes;
    import com.badlogic.gdx.graphics.g2d.TextureRegion;
    import com.badlogic.gdx.graphics.g3d.Material;
    import com.badlogic.gdx.graphics.g3d.Model;
    import com.badlogic.gdx.graphics.g3d.attributes.TextureAttribute;
    import com.badlogic.gdx.graphics.g3d.utils.MeshPartBuilder;
    import com.badlogic.gdx.graphics.g3d.utils.ModelBuilder;
    
    public enum BlockType {
    
        GRASS("dirt", 0, 0, 3, 0, 2, 0),
        STONE("stone", 1, 0, 1, 0, 1, 0),
        PLANK("plank", 4, 0, 4, 0, 4, 0),
        GLASS("glass", 1, 3, 1, 3, 1, 3);
    
        public static int TEXTURE_WIDTH = 16;
    
        String name;
        int textureTopX, textureTopY;
        int textureSideX, textureSideY;
        int textureBottomX, textureBottomY;
    
        TextureRegion textureRegionTop = null;
        TextureRegion textureRegionSide = null;
        TextureRegion textureRegionBottom = null;
    
        Model model;
    
        BlockType(String name, int textureTopX, int textureTopY, int textureSideX, int textureSideY, int textureBottomX, int textureBottomY) {
            this.name = name;
            this.textureTopX = textureTopX;
            this.textureTopY = textureTopY;
            this.textureSideX = textureSideX;
            this.textureSideY = textureSideY;
            this.textureBottomX = textureBottomX;
            this.textureBottomY = textureBottomY;
        }
    
        public static void createTexturesAndModels(Texture texture) {
            ModelBuilder modelBuilder = new ModelBuilder();
    
            for(BlockType type : values()) {
                type.textureRegionTop = new TextureRegion(texture, type.textureTopX * TEXTURE_WIDTH, type.textureTopY * TEXTURE_WIDTH, TEXTURE_WIDTH, TEXTURE_WIDTH);
                type.textureRegionSide = new TextureRegion(texture, type.textureSideX * TEXTURE_WIDTH, type.textureSideY * TEXTURE_WIDTH, TEXTURE_WIDTH, TEXTURE_WIDTH);
                type.textureRegionBottom = new TextureRegion(texture, type.textureBottomX * TEXTURE_WIDTH, type.textureBottomY * TEXTURE_WIDTH, TEXTURE_WIDTH, TEXTURE_WIDTH);
    
                int attr = VertexAttributes.Usage.Position | VertexAttributes.Usage.Normal | VertexAttributes.Usage.TextureCoordinates;
                modelBuilder.begin();
                MeshPartBuilder meshPartBuilder = modelBuilder.part("box", GL20.GL_TRIANGLES, attr, new Material(TextureAttribute.createDiffuse(type.textureRegionTop)));
                meshPartBuilder.setUVRange(type.textureRegionTop);
                meshPartBuilder.rect(-0.5f,-0.5f,-0.5f, -0.5f, 0.5f, -0.5f, 0.5f,0.5f,-0.5f, 0.5f,-0.5f,-0.5f, 0, 0, -1);
                meshPartBuilder.setUVRange(type.textureRegionSide);
                meshPartBuilder.rect(-0.5f,0.5f,0.5f, -0.5f,-0.5f,0.5f,  0.5f,-0.5f,0.5f, 0.5f,0.5f,0.5f, 0,0,1);
                meshPartBuilder.setUVRange(type.textureRegionSide);
                meshPartBuilder.rect(-0.5f,-0.5f,0.5f, -0.5f,-0.5f,-0.5f,  0.5f,-0.5f,-0.5f, 0.5f,-0.5f,0.5f, 0,-1,0);
                meshPartBuilder.setUVRange(type.textureRegionSide);
                meshPartBuilder.rect(-0.5f,0.5f,-0.5f, -0.5f,0.5f,0.5f,  0.5f,0.5f,0.5f, 0.5f,0.5f,-0.5f, 0,1,0);
                meshPartBuilder.setUVRange(type.textureRegionSide);
                meshPartBuilder.rect(-0.5f,-0.5f,0.5f, -0.5f,0.5f,0.5f,  -0.5f,0.5f,-0.5f, -0.5f,-0.5f,-0.5f, -1,0,0);
                meshPartBuilder.setUVRange(type.textureRegionBottom);
                meshPartBuilder.rect(0.5f,-0.5f,-0.5f, 0.5f,0.5f,-0.5f,  0.5f,0.5f,0.5f, 0.5f,-0.5f,0.5f, 1,0,0);
                type.model = modelBuilder.end();
            }
        }
    }