korlibs / korge

KorGE Game Engine. Multiplatform Kotlin Game Engine
https://korge.org/
Other
2.57k stars 125 forks source link

[Request] Create a config option to set smoothing=true as default. #2141

Open davjhan opened 9 months ago

davjhan commented 9 months ago

About

Korge's image and shape rendering output is outstanding, and so is the API interface for graphics. However, I find myself always setting smoothing = false on all my Views. Especially on a game with pixel art.

Ask: Can we add, at the Container, Stage, Scene, or App level, a configuration to disable all anti-aliasing by default?.

According to the docs,

All the views extending BaseRect like Image, has a property called smoothing, to configure how sampling works. When smoothing is true (its default value), the texture is sampled using linear interpolation, and when the smoothing is false, it uses a nearest neighborhood sampling approach.

Comparison

Here are the examples with smoothing on vs off.

Setup:

With smoothing = true (default)

Screenshot 2024-01-31 at 7 29 37 PM

With smoothing = false

Screenshot 2024-01-31 at 7 32 47 PM

As you can see, "false" is more desirable. However, it requires that I explicitly set this boolean to false on every call with the the graphics API at the View level.

        circle {
            smoothing = false # <--
            radius = 100.0
            x = 50.0
            y = 50.0
        }
soywiz commented 9 months ago

I believe we might have like a boolean in the RenderContext providing a smoothing, and then make the one from the view also nullable Boolean.

Then at each view we can do something like view.smoothing ?: context.smoothing to determine how to render it.

In any case, if you are making a pixel art game, have you considered having a PixelatedScene with a lower resolution, so it is pixel perfect, and then let the engine scale it? If you are doing pixel perfect, smoothing might work for you?

BTW: That circle looks like blurred when smoothed, but that's a separate issue, probably related to SDFs and retina. Probably this https://github.com/korlibs/korge/issues/2116

davjhan commented 9 months ago

RE: PixelatedScene

I didn't know this was a thing! I just tried it, and here's what it looks like to render on a virtualSize 1/4 the windowSize:

suspend fun main() = Korge(
    virtualSize = Size(128, 128),
    windowSize = Size(512, 512),
    backgroundColor = Colors["#ffffff"]
) {
    val sceneContainer = sceneContainer()
    sceneContainer.changeTo({ MyScene() })
}

class MyScene : PixelatedScene(
    sceneWidth = 128,
    sceneHeight = 128,
) {
    override suspend fun SContainer.sceneMain() {
            circle(30, fill = Colors.BLUE)
    }
}

Screenshot 2024-02-02 at 3 03 22 PM

As you can see, there still is anti-aliasing applied near the curves of the circle. Some devs may like this look, but if one wants to turn it off, they'll have to do set the antialiased = false on each view, much like with smothing. Ideally, this is also a a configurable setting on PixelScene.

circle(30, fill = Colors.BLUE){
    antialiased = false
}

Screenshot 2024-02-02 at 3 09 00 PM


Regardless, I think this feature request still stands, as some developers may prefer the visual style where all sprites are pixel graphics, but positions can be floats, and pixels can be rotated (e.g. Terraria or Vampire Survivors)