Add resolution-independent pixelation

This commit is contained in:
Alexander Sellite 2026-07-27 23:45:11 -04:00
parent 46175ee405
commit 6f51f91324
10 changed files with 220 additions and 33 deletions

View file

@ -379,20 +379,25 @@ func set_world_pixelation(pixel_size: int) -> void:
func _update_world_preview_resolution() -> void:
var render_scale: float = PlayerSettings.get_world_render_scale(
_world_pixel_size
var displayed_size := Vector2i(
maxi(1, roundi(size.x)),
maxi(1, roundi(size.y))
)
var grid_size: Vector2i = PlayerSettings.get_world_grid_size(
_world_pixel_size,
displayed_size
)
var shader_material := _background.material as ShaderMaterial
if shader_material != null:
shader_material.set_shader_parameter(
"virtual_pixel_density",
Vector2(
maxf(1.0, size.x * render_scale),
maxf(1.0, size.y * render_scale)
)
Vector2(grid_size)
)
var logo_material := _title_logo.material as ShaderMaterial
if logo_material != null:
var render_scale: float = (
float(grid_size.y) / float(displayed_size.y)
)
var effect_scale: float = 1.0 / render_scale
logo_material.set_shader_parameter(
"horizontal_displacement_pixels",
@ -405,9 +410,15 @@ func _update_world_preview_resolution() -> void:
func _snap_world_preview(value: Vector2) -> Vector2:
var render_scale: float = PlayerSettings.get_world_render_scale(
_world_pixel_size
var displayed_size := Vector2i(
maxi(1, roundi(size.x)),
maxi(1, roundi(size.y))
)
var grid_size: Vector2i = PlayerSettings.get_world_grid_size(
_world_pixel_size,
displayed_size
)
var render_scale: float = float(grid_size.y) / float(displayed_size.y)
var step: float = 1.0 / render_scale
return Vector2(
roundf(value.x / step) * step,

View file

@ -1,7 +1,7 @@
class_name UIPixelationPresenter
extends SubViewportContainer
const MIN_UI_VIEWPORT_SIZE: Vector2i = Vector2i(320, 180)
const MIN_UI_VIEWPORT_SIZE: Vector2i = Vector2i(256, 180)
signal effective_pixel_size_changed(
requested_pixel_size: int,
@ -70,12 +70,13 @@ func _resize_presentation() -> void:
return
var previous_effective_size: int = _effective_pixel_size
_effective_pixel_size = _resolve_effective_pixel_size(root_size)
var render_scale: float = PlayerSettings.get_ui_render_scale(
_effective_pixel_size
var viewport_size: Vector2i = PlayerSettings.get_ui_render_size(
_effective_pixel_size,
root_size
)
var viewport_size := Vector2i(
ceili(float(root_size.x) * render_scale),
ceili(float(root_size.y) * render_scale)
var render_scale: float = minf(
1.0,
float(viewport_size.y) / float(root_size.y)
)
var presentation_size: Vector2 = Vector2(viewport_size) / render_scale
set_anchors_preset(Control.PRESET_TOP_LEFT)
@ -98,10 +99,9 @@ func _resize_presentation() -> void:
func _resolve_effective_pixel_size(root_size: Vector2i) -> int:
for candidate: int in range(_requested_pixel_size, 0, -1):
var render_scale: float = PlayerSettings.get_ui_render_scale(candidate)
var candidate_size := Vector2i(
ceili(float(root_size.x) * render_scale),
ceili(float(root_size.y) * render_scale)
var candidate_size: Vector2i = PlayerSettings.get_ui_render_size(
candidate,
root_size
)
if (
candidate_size.x >= MIN_UI_VIEWPORT_SIZE.x