I basically want to play around with blending modes in LibGDX but don't know how to do it. I found this image on internet. I want to do the same thing on LibGDX. Can someone teach me how.
I've been playing around using Scene2D. Here's my non-working snippet.
private class MyGroup extends Group {
Image red, blue;
public MyGroup() {
Texture texture = new Texture(Gdx.files.internal("images/red.png"));
texture.setFilter(TextureFilter.Linear, TextureFilter.Linear);
red = new Image(texture);
texture = new Texture(Gdx.files.internal("images/blue.png"));
texture.setFilter(TextureFilter.Linear, TextureFilter.Linear);
blue = new Image(texture);
red.setX(-25);
blue.setX(25);
}
@Override
public void draw(Batch batch, float parentAlpha) {
batch.end();
batch.begin();
batch.enableBlending();
red.draw(batch, parentAlpha);
Gdx.gl.glEnable(Gdx.gl20.GL_BLEND);
Gdx.gl.glBlendFuncSeparate(
Gdx.gl20.GL_DST_COLOR,
Gdx.gl20.GL_SRC_COLOR,
Gdx.gl20.GL_ONE,
Gdx.gl20.GL_ONE);
blue.draw(batch, parentAlpha);
}
}
I realize this is not a new question, but I thought I would share some information for anyone else who makes it to this question/answer without knowing much about rendering in OpenGL (Knowing these terms helps a lot so you aren't just guessing mix-and-matching) Note that this site is how I learned most of this myself, so more complete information can be found there.
Destination Color: the color in the buffer, which will (eventually) be drawn unless it is modified or overwritten with new values.
Source Color: the color coming in from additional rendering commands, which may or may not interact with the destination color (depending on our settings)
The default blending equation: Final Color = (SourceColor*SourceBlendingFactor)+(DestinationColor*DestinationBlendingFactor) (This default equation can be changed, but I recommend reading my source link at the top for more information on that)
The two BlendingFactors are what we can mess with. We can set them to:
GL_ZERO: RGB(0,0,0) A(0)
GL_ONE: RGB(1,1,1) A(1)
GL_SRC_COLOR: RGB(sourceR, sourceG, sourceB) A(sourceA)
GL_ONE_MINUS_SRC_COLOR: RGB(1-sourceR, 1-sourceG, 1-sourceB) A(1-sourceA)
GL_DST_COLOR: RGB(destinationR, destinationG, destinationB) A(destinationA)
GL_ONE_MINUS_DST_COLOR: RGB(1-destinationR, 1-destinationG, 1-destinationB) A(1-destinationA)
GL_SRC_ALPHA: RGB(sourceA, sourceA, sourceA) A(sourceA)
GL_ONE_MINUS_SRC_ALPHA: RGB(1-sourceA, 1-sourceA, 1-sourceA) A(1-sourceA)
GL_DST_ALPHA: RGB(destinationA, destinationA, destinationA) A(destinationA)
GL_ONE_MINUS_DST_ALPHA: RGB(1-destinationA, 1-destinationA, 1-destinationA) A(1-destinationA)
GL_SRC_ALPHA_SATURATE: RGB(min(sourceA, 1-destinationA), min(sourceA, 1-destinationA), min(sourceA, 1-destinationA)) A(1)
The following also uses some predefined constant color, by default it is black
GL_CONSTANT_COLOR: RGB(constantR, constantG, constantB) A(constantA)
GL_ONE_MINUS_CONSTANT_COLOR: RGB(1-constantR, 1-constantG, 1-constantB) A(1-constantA)
GL_CONSTANT_ALPHA: RGB(constantA, constantA, constantA) A(constantA)
GL_ONE_MINUS_CONSTANT_ALPHA: RGB(1-constantA, 1-constantA, 1-constantA) A(1-constantA)
So all of these are just predefined float values that are being multiplied with either our source or destination, and then added to the other.
The easiest to observe from the image is GL_ZERO and GL_ONE. We end up with whichever image has the ONE.
Understanding GL_ZERO with GL_DST_COLOR
When GL_ZERO is on the destination, we are ignoring any color information currently in the buffer (because multiplying everything by zero). However, With GL_DST_COLOR also on the source image, we end up multiplying the r, g, b, a values of the source and destination.
This looks good in the image because of the nature of the example images. One acts as a solid color image, while the other grayscale image looks and acts almost like a beam of light to "reveal" the color out from our GL_ZERO setting.
Hopefully, this helps explain the images we can see above and helps everyone understand how those images are actually being blended together.
Ok, to partly answer my question, here's the trick I used. Please let me know if I'm doing anything wrong. Note: This doesn't work on other function.Like when I combine GL_DST_COLOR and GL_ZERO, it doesn't output what I want. But others will. So just play around with it. I'm still watching for other answers here.
Here's the code:
private class MyGroup extends Group {
Texture dst, src;
public MyGroup() {
dst = new Texture(Gdx.files.internal("images/dst.png"));
dst.setFilter(TextureFilter.Linear, TextureFilter.Linear);
src = new Texture(Gdx.files.internal("images/src.png"));
src.setFilter(TextureFilter.Linear, TextureFilter.Linear);
}
@Override
public void draw(Batch batch, float parentAlpha) {
// We need to cast to use blending function
SpriteBatch sb = (SpriteBatch)batch;
// draw our destination image
sb.draw(dst, 0, 0);
sb.end();
// remember SpriteBatch's current functions
int srcFunc = sb.getBlendSrcFunc();
int dstFunc = sb.getBlendDstFunc();
// Let's enable blending
sb.enableBlending();
sb.begin();
// blend them
b.setBlendFunction(GL20.GL_DST_COLOR, GL20.GL_SRC_ALPHA);
sb.draw(src, 0, 0);
// Reset
sb.end();
sb.begin();
sb.setBlendFunction(srcFunc, dstFunc);
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With