Skip to content

fix(postproduction): keep MSAA when postproduction is enabled - #794

Open
rihokirss wants to merge 1 commit into
ThatOpen:mainfrom
rihokirss:fix/postproduction-composer-msaa
Open

fix(postproduction): keep MSAA when postproduction is enabled#794
rihokirss wants to merge 1 commit into
ThatOpen:mainfrom
rihokirss:fix/postproduction-composer-msaa

Conversation

@rihokirss

Copy link
Copy Markdown
Contributor

Description

Fixes #793.

Postproduction.initialize() creates the EffectComposer without a render target, so three.js allocates the ping-pong targets with samples = 0. The moment postproduction is enabled, the hardware MSAA of the default framebuffer is gone and every geometry edge is aliased; SMAA only partly recovers it, which is why the postproduction image looks "noisier" than the plain render.

This PR gives the composer targets a sample count:

  • new Postproduction.samples (default 4, clamped to renderer.capabilities.maxSamples; 0 restores the previous behaviour), applied right after the composer is created and re-applied by the setter (samples change + dispose(), so the framebuffer is re-created on next use);
  • setSize() needs no change — WebGLRenderTarget.setSize() keeps samples;
  • the PostproductionRenderer example gets an "MSAA samples" slider next to the SMAA checkbox.

Measured on an office-building model, fixed exterior view, Chrome / AMD Radeon 8060S, 1665×1123 ("hard edges" = share of neighbouring pixel pairs whose luma differs by more than 60):

hard edges render ms
postproduction on, samples = 0 (before) 43.5 % 12.2
postproduction on, samples = 4 (this PR) 33.7 % 12.8
postproduction off (default framebuffer, MSAA) 36.2 % 9.9
postproduction on, samples = 0, pixel ratio 2 33.6 % 13.2

i.e. the same edge quality as pixel ratio 2 for ~0.6 ms per frame instead of 4× the fill rate.

Additional context

  • The composer targets carry no depthTexture; the AO / edge-detection passes keep their own single-sample targets, so nothing else changes.
  • yarn build-libraries currently fails on main in packages/core against the published @thatopen/fragments@3.4.7 (FragmentsModels.getWorker, getLocalIdsFromItemIds are not released yet) — unrelated to this change; tsc for packages/front reports no errors in PostproductionRenderer, and the front Vite build succeeds.
  • The pre-existing eslint/prettier findings in the two touched files (import order, fragPaths line, extraneous-deps in the example) are left as they are to keep the diff minimal.

What is the purpose of this pull request?

  • Bug fix
  • New Feature
  • Documentation update
  • Other

Before submitting the PR, please make sure you do the following:

  • Check that there isn't already a PR that solves the problem the same way to avoid creating a duplicate.
  • Follow the Conventional Commits v1.0.0 standard for PR naming.
  • Provide a description in this PR that addresses what the PR is solving, or reference the issue that it solves (fixes #793).
  • Ideally, include relevant tests that fail without this PR but pass with it. (No test harness in this repo; the example exposes the setting.)

EffectComposer allocates its ping-pong render targets with samples = 0, so
enabling PostproductionRenderer dropped the hardware MSAA of the default
framebuffer and every geometry edge came out aliased (SMAA only partly
recovers it). Give the composer targets a sample count, exposed as
Postproduction.samples (default 4, clamped to capabilities.maxSamples,
0 restores the previous behaviour), and add a slider to the example.

Fixes ThatOpen#793
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

PostproductionRenderer: composer render targets are not multisampled, so enabling postproduction loses MSAA (aliased edges)

1 participant