Negative values in the Green channel result in color shifts in the Red channel
Closed this issue · 2 comments
Description
Negative values in the Green channel result in color shifts in the Red channel when using Rgba16Float as the surface format.
Repro steps
Draw a screen space quad with the following fragment shader:
@fragment fn fs_blit(@location(0) uv: vec2f) -> @location(0) vec4f {
// Where uv is the screen space position of the fragment in the range [0, 1].
return vec4f(fract(uv.x * 1.), -ceil(uv.y * 6.) / 6., 0, 1);
}
Here's the surface configuration:
let config = SurfaceConfiguration {
usage: wgpu::TextureUsages::RENDER_ATTACHMENT,
format: wgpu::TextureFormat::Rgba16Float,
width: size.width,
height: size.height,
present_mode: wgpu::PresentMode::Fifo,
alpha_mode: caps.alpha_modes[0],
view_formats: vec![],
desired_maximum_frame_latency: 2,
};
Expected vs observed behavior
The color output should be the same along Y direction without color shifts.
Platform
- MacOS 14.6.1
- wgpu = "22.1.0"
- winit = "0.30.5"
Never mind, it turns out that in HDR mode this is actually the correct result. i.e. green channel does effect red channel.
It’s possible that this isn’t working quite as it ought to — at least on macOS, apparently one is supposed to explicitly set a color space if producing HDR content, and wgpu doesn't have an API to actually do that yet, so all HDR output from wgpu is technically non-compliant — #2920 (comment) . So, there might well be room for improvement here, but there is an issue for it (though no one is working on it, that I’ve heard of). Or, it might be working as intended (negative color components can be understood as representing out-of-gamut colors, which can potentially be colors that the hardware can represent even though strict 0-255 sRGB can’t, or at least be colors whose closest-in-representable-hue form is not the same as clamping).