LibGDX: Masking using Blending Function 🎭
Masking using Blending Function
This article is an analysis with examples of this article: https://libgdx.com/wiki/graphics/2d/masking#4-masking-using-blending-function-shapes-or-textures
MaskGroup — a group based on this article, simplifies the work with disguise: https://veldan1202.medium.com/libgdx-maskgroup-5c5c437f14e3
This article will describe 100 examples of using masks, the first step is common to all examples, each example uses its own resource, an example gif and code for making changes are shown, do everything in order and you will succeed.
The first step is common to all examples
- Set up a standard project with this guide: https://veldan1202.medium.com/libgdx-%D1%82%D0%BE%D0%BB%D1%8C%D0%BA%D0%BE-%D0%B4%D0%BB%D1%8F-android-4858e26734cf
- Android:
3. LibGDXGame:
class LibGDXGame : ApplicationAdapter(), AdvancedInputProcessor {
private val batch by lazy { SpriteBatch() }
private val renderer by lazy { ShapeRenderer() }
override fun create() {
Gdx.input.inputProcessor = this
}
override fun render() {
ScreenUtils.clear(Color.DARK_GRAY)
}
}
fun Batch.begend(block: Batch.() -> Unit = {}) {
begin()
block()
end()
}
fun ShapeRenderer.begend(type: ShapeRenderer.ShapeType, block: ShapeRenderer.() -> Unit = {}) {
begin(type)
block()
end()
}
interface AdvancedInputProcessor: InputProcessor {
override fun keyDown(keycode: Int): Boolean {
return false
}
override fun keyUp(keycode: Int): Boolean {
return false
}
override fun keyTyped(character: Char): Boolean {
return false
}
override fun touchDown(screenX: Int, screenY: Int, pointer: Int, button: Int): Boolean {
return false
}
override fun touchUp(screenX: Int, screenY: Int, pointer: Int, button: Int): Boolean {
return false
}
override fun touchDragged(screenX: Int, screenY: Int, pointer: Int): Boolean {
return false
}
override fun mouseMoved(screenX: Int, screenY: Int): Boolean {
return false
}
override fun scrolled(amountX: Float, amountY: Float): Boolean {
return false
}
}
1️⃣Mask and Image
Resource for this example: https://drive.google.com/file/d/1JFAA3oHUEMkTOoAPjYIUtCkuKvjivKQC/view?usp=sharing
- Put the image in the resources folder:
2. Initialize texture and coordinates for mask and image:
3. Create a mask drawing method
private fun Batch.drawMask() {
Gdx.gl.glColorMask(false, false, false, true)
setBlendFunction(GL20.GL_ONE, GL20.GL_ZERO)
draw(img, maskX, maskY)
}
GL20.GL_ONE, GL20.GL_ZER — with these options the image will be rendered within the opaque area of the mask.
4. Create a image drawing method
private fun Batch.drawMasked() {
setBlendFunction(GL20.GL_ZERO, GL20.GL_SRC_ALPHA)
draw(img, imgX, imgY)
flush()
Gdx.gl.glColorMask(true, true, true, true)
setBlendFunction(GL20.GL_DST_ALPHA, GL20.GL_ONE_MINUS_DST_ALPHA)
draw(img, imgX, imgY)
flush()
setBlendFunction(GL20.GL_SRC_ALPHA, GL20.GL_ONE_MINUS_SRC_ALPHA)
}
5. This can already be run and see the masked image, but let’s add mask and image border debugging and add the ability to move the image
2️⃣ Inverted Mask and Image
ONLY. The only thing that needs to be changed from the previous example is the mask drawing method
private fun Batch.drawMask() {
Gdx.gl.glColorMask(false, false, false, true)
// setBlendFunction(GL20.GL_ONE, GL20.GL_ZERO)
setBlendFunction(GL20.GL_ZERO, GL20.GL_ONE_MINUS_SRC_ALPHA)
draw(img, maskX, maskY)
}
GL20.GL_ZERO, GL20.GL_ONE_MINUS_SRC_ALPHA — with these options, the image will be displayed in the transparent area of the mask.
3️⃣Alpha mask and Image
Resource for this example: https://drive.google.com/file/d/1vemvV48FAAQHBJ9fUhuqftkNHDf9og7-/view?usp=sharing
- Put the image in the resources folder
2. Initialize mask and coordinate for mask2
3. Change the mask drawing method, now 2 masks will be drawn
4. Add debugging for the second mask
4️⃣Scissors |Alpha mask | Image
ONLY. ONLY. The only thing that needs to be changed from the previous example is to add scissors to the image drawing method.
PS. Vel_daN: Love what You DO 💚.