Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Antialiased draw_* primitives become blurry when window resolution exceeds base viewport size (and stretch mode = canvas_items or scale factor > 1) #99440

Open
danijmn opened this issue Nov 19, 2024 · 1 comment

Comments

@danijmn
Copy link

danijmn commented Nov 19, 2024

Tested versions

  • Reproducible in: 4.3.stable, 4.4.dev4

System information

Windows 10.0.19045 - Multi-window, 1 monitor - Vulkan (Forward+) - dedicated GeForce GTX 765M - Intel(R) Core(TM) i7-4700MQ CPU @ 2.40GHz (8 threads)

Issue description

Background
CanvasItem (and RenderingServer) contains several draw_* functions which allow convenient rendering of 2D primitives such as circles and lines, with minimal setup.

The problem
Some of these functions feature optional antialiasing, which works well if the runtime window size matches the viewport's base size defined in the project settings. Unfortunately, when stretch mode is set to canvas_items (or scale factor > 1) and the window exceeds the base viewport width/height, the transparent feathers are not automatically scaled, resulting in blurry edges, as demonstrated in the MRP.

I have verified that this happens for circles, lines and rects. Using the RenderingServer functions directly yields the same results. Note that this is not an inherent limitation of these functions, because changing the viewport base size to match the screen size always results in smooth edges, even at very high resolutions.

Note: this is vaguely related to proposal #7309.

Potential fix
It's relatively easy to achieve resolution-independent antialiasing of 2D shapes using shaders (SDF font rendering is such an example). For circles, the shader is very simple (this is included in the MRP for comparison with the default):

shader_type canvas_item;

void fragment() 
{
	float dist_to_center = distance(UV, vec2(0.5, 0.5));
	float derivative = fwidth(dist_to_center);
	float alpha = smoothstep(0.5, 0.5 - derivative, dist_to_center);
	COLOR.a *= alpha;
}

Image (from the MRP)
Image

Steps to reproduce

Import the MRP and run the example scene.

Minimal reproduction project (MRP)

blurry_draw_antialiasing.zip

@L4Vo5
Copy link
Contributor

L4Vo5 commented Jan 15, 2025

I've found that this also happens, regardless of window settings, when you set the scale parameter in the Node2D you're drawing from (or, I assume, generally when scaling the canvas item transform)
Setting the scale 10x:
Image
Leaving scale at 1 but drawing everything 10x bigger and further apart:
Image

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants