Libgdx在运行时更改Texture的颜色

时间:2014-06-04 09:56:23

标签: java colors libgdx textures

在使用libgdx制作的游戏中,我有一个TextureAtlas,其中我存储了TextureRegion Animation的所有Player s。默认情况下,Player有一个蓝色T恤(例如)。现在我想能够有一个Player,每个都应该有另一个T恤颜色。所以基本上,我想用第二个Player替换蓝色,用第三个Player替换绿色,依此类推。我相信我可以用PixMap做到这一点,但不会。因为那时我失去了TextureAtlas(?)的优势。 还有另一种方法吗?或者我是否需要在TextureRegion中将每个“颜色版本”作为TextureAtlas

另一个小问题:
使用Gimp(可能还有一些其他程序),您可以使用“.gif”文件的颜色索引。通过为文件中的每种颜色保存索引,然后使用此索引来描述像素,这会减小所有Texture的大小。因此,对于每个红色像素,您将拥有“1”而不是“#FF0000”,并且文件中的某处有“1 =#FF0000”。如果然后我们将带有颜色索引的“.gif”文件打包在TextureAtlas内,那么索引是否会丢失并恢复默认的RGB颜色或会产生问题?

非常感谢!

3 个答案:

答案 0 :(得分:3)

这样做的方法就是设置最大数量的玩家,并为每个人制作T恤,然后用纹理图集打包并将它们添加到一个TextureRegion数组中。

现在你只需要在索引之间切换。

另一种方法是使用batch.setColor

void    setColor(Color tint)
void    setColor(float color) 
void    setColor(float r, float g, float b, float a) 

只需为您绘制的每件T恤设置精灵批次的颜色,并在绘制所有这些T恤后再将spritebatch颜色再次设置为白色。

您也可以使用带有setColor函数的Sprite类来执行此操作。

如果你的T恤衫体积不是很大,而且你的最大球员数量很小,我会推荐第一种方法。

答案 1 :(得分:3)

我遇到了使用相同纹理生成随机颜色武器的相同问题。

所以我写了这个。
基本上我制作了你想要编辑的纹理的像素图。

然后迭代所有像素,迭代时检查某些颜色,这些颜色是纹理的一部分特定部分。 (我建议使用不同的灰度,因为RGB是相同的)

当它在需要改变颜色的像素上时,我使用颜色选择器方法抓取那些像素组的颜色,颜色选择器方法基本上是随机的,它从预制的颜色阵列中获得颜色,< br />然后将特定像素更改为新颜色。

/**
 * Requires a asset's textureName, and requires gray scale colors of the
 * parts
 * 
 * @param texturename
 * @param colorBlade
 * @param colorEdge
 * @param colorAffinity
 * @param colorGrip
 * @return
 */
private static Texture genTexture(String texturename, int colorBlade,
        int colorEdge, int colorAffinity, int colorGrip, int colorExtra) {
    Texture tex = Game.res.getTexture(texturename);

    TextureData textureData = tex.getTextureData();
    textureData.prepare();

    Color tintBlade = chooseColor(mainColors);
    Color tintEdge = new Color(tintBlade.r + 0.1f, tintBlade.g + 0.1f,
            tintBlade.b + 0.1f, 1);

    Color tintAffinity = chooseColor(affinityColors);
    Color tintGrip;
    Color tintExtra = chooseColor(extraColors);

    boolean colorsAreSet = false;

    do {
        tintGrip = chooseColor(mainColors);

        if (tintAffinity != tintBlade && tintAffinity != tintGrip
                && tintGrip != tintBlade) {
            colorsAreSet = true;
        }
    } while (!colorsAreSet);

    Pixmap pixmap = tex.getTextureData().consumePixmap();

    for (int y = 0; y < pixmap.getHeight(); y++) {
        for (int x = 0; x < pixmap.getWidth(); x++) {

            Color color = new Color();
            Color.rgba8888ToColor(color, pixmap.getPixel(x, y));
            int colorInt[] = getColorFromHex(color);

            if (colorInt[0] == colorBlade && colorInt[1] == colorBlade
                    && colorInt[2] == colorBlade) {
                pixmap.setColor(tintBlade);
                pixmap.fillRectangle(x, y, 1, 1);
            } else if (colorInt[0] == colorEdge && colorInt[1] == colorEdge
                    && colorInt[2] == colorEdge) {
                pixmap.setColor(tintEdge);
                pixmap.fillRectangle(x, y, 1, 1);
            } else if (colorInt[0] == colorAffinity
                    && colorInt[1] == colorAffinity
                    && colorInt[2] == colorAffinity) {
                pixmap.setColor(tintAffinity);
                pixmap.fillRectangle(x, y, 1, 1);
            } else if (colorInt[0] == colorGrip && colorInt[1] == colorGrip
                    && colorInt[2] == colorGrip) {
                pixmap.setColor(tintGrip);
                pixmap.fillRectangle(x, y, 1, 1);
            }
            else if (colorInt[0] == colorExtra && colorInt[1] == colorExtra
                && colorInt[2] == colorExtra) {
            pixmap.setColor(tintExtra);
            pixmap.fillRectangle(x, y, 1, 1);
            }
        }
    }

    tex = new Texture(pixmap);
    textureData.disposePixmap();
    pixmap.dispose();

    return tex;
}

我希望这会有所帮助 请不要只是复制粘贴,尝试重建它以满足您的需求,或者您不会学到任何东西。

答案 2 :(得分:0)

Rose Blax确实做得很好。但是,如果您想使用SpriteBatch来实现此目的,或者是有相同问题但又不想使用Pixmap的人,那么...

可以肯定,我真的很喜欢使用Pixmap,但是我已经看到“ spritebatch / sprite.setcolor(r,g,b,a)”的使用带来了一些挑战,因为更改所有纹理颜色而不是仅更改T恤。 ..这就是为什么我来这里,是的,可以使用这种方式仅更换T恤。你准备好了吗? :D

1-使零件要绘制灰度或白色 2-拆分零件,将其涂在Texturepack或其他纹理中:如果是T恤,则需要一个T恤超出字符范围的包装...是的,将有一个头部,手臂和手臂只腿。 T短裤可以装在同一包装中,也可以不在同一包装中。但是,在以后再穿上这件T恤要留个空隙。

它看起来像这样:

Check out this asset

不必害怕。我知道图像已经分解了整个特征,但是如果您只想更换T恤,那么您只会从身体的其余部分分开。

3-您将同时绘制它们,但不是同一TextureRegion,您的代码将如下所示:

public void draw(SpriteBatch batch){
        //First we draw the player with a hole in his body
        batch.draw(playerA,0,0,75,100);
        //Here we set the color of next texture to be drawn as RED.
        batch.setColor(Color.RED);
        //Now we draw the t-shirt of the player in same x and half y.
        //That t-short has to be drawn in right position. That's why calc it.
        batch.draw(tshirtA, 0,50,50);
        //For don't affect others textures then make it white back.
        batch.setColor(Color.WHITE);
    }