228 lines
8.0 KiB
C++
228 lines
8.0 KiB
C++
/*
|
|
* Copyright (C) 2020 The Android Open Source Project
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
#ifndef TNT_FILAMENT_TONEMAPPER_H
|
|
#define TNT_FILAMENT_TONEMAPPER_H
|
|
|
|
#include <utils/compiler.h>
|
|
|
|
#include <math/mathfwd.h>
|
|
|
|
namespace filament {
|
|
|
|
/**
|
|
* Interface for tone mapping operators. A tone mapping operator, or tone mapper,
|
|
* is responsible for compressing the dynamic range of the rendered scene to a
|
|
* dynamic range suitable for display.
|
|
*
|
|
* In Filament, tone mapping is a color grading step. ToneMapper instances are
|
|
* created and passed to the ColorGrading::Builder to produce a 3D LUT that will
|
|
* be used during post-processing to prepare the final color buffer for display.
|
|
*
|
|
* Filament provides several default tone mapping operators that fall into three
|
|
* categories:
|
|
*
|
|
* - Configurable tone mapping operators
|
|
* - GenericToneMapper
|
|
* - Fixed-aesthetic tone mapping operators
|
|
* - ACESToneMapper
|
|
* - ACESLegacyToneMapper
|
|
* - FilmicToneMapper
|
|
* - Debug/validation tone mapping operators
|
|
* - LinearToneMapper
|
|
* - DisplayRangeToneMapper
|
|
*
|
|
* You can create custom tone mapping operators by subclassing ToneMapper.
|
|
*/
|
|
struct UTILS_PUBLIC ToneMapper {
|
|
ToneMapper() noexcept;
|
|
virtual ~ToneMapper() noexcept;
|
|
|
|
/**
|
|
* Maps an open domain (or "scene referred" values) color value to display
|
|
* domain (or "display referred") color value. Both the input and output
|
|
* color values are defined in the Rec.2020 color space, with no transfer
|
|
* function applied ("linear Rec.2020").
|
|
*
|
|
* @param c Input color to tone map, in the Rec.2020 color space with no
|
|
* transfer function applied ("linear")
|
|
*
|
|
* @return A tone mapped color in the Rec.2020 color space, with no transfer
|
|
* function applied ("linear")
|
|
*/
|
|
virtual math::float3 operator()(math::float3 c) const noexcept = 0;
|
|
};
|
|
|
|
/**
|
|
* Linear tone mapping operator that returns the input color but clamped to
|
|
* the 0..1 range. This operator is mostly useful for debugging.
|
|
*/
|
|
struct UTILS_PUBLIC LinearToneMapper final : public ToneMapper {
|
|
LinearToneMapper() noexcept;
|
|
~LinearToneMapper() noexcept final;
|
|
|
|
math::float3 operator()(math::float3 c) const noexcept override;
|
|
};
|
|
|
|
/**
|
|
* ACES tone mapping operator. This operator is an implementation of the
|
|
* ACES Reference Rendering Transform (RRT) combined with the Output Device
|
|
* Transform (ODT) for sRGB monitors (dim surround, 100 nits).
|
|
*/
|
|
struct UTILS_PUBLIC ACESToneMapper final : public ToneMapper {
|
|
ACESToneMapper() noexcept;
|
|
~ACESToneMapper() noexcept final;
|
|
|
|
math::float3 operator()(math::float3 c) const noexcept override;
|
|
};
|
|
|
|
/**
|
|
* ACES tone mapping operator, modified to match the perceived brightness
|
|
* of FilmicToneMapper. This operator is the same as ACESToneMapper but
|
|
* applies a brightness multiplier of ~1.6 to the input color value to
|
|
* target brighter viewing environments.
|
|
*/
|
|
struct UTILS_PUBLIC ACESLegacyToneMapper final : public ToneMapper {
|
|
ACESLegacyToneMapper() noexcept;
|
|
~ACESLegacyToneMapper() noexcept final;
|
|
|
|
math::float3 operator()(math::float3 c) const noexcept override;
|
|
};
|
|
|
|
/**
|
|
* "Filmic" tone mapping operator. This tone mapper was designed to
|
|
* approximate the aesthetics of the ACES RRT + ODT for Rec.709
|
|
* and historically Filament's default tone mapping operator. It exists
|
|
* only for backward compatibility purposes and is not otherwise recommended.
|
|
*/
|
|
struct UTILS_PUBLIC FilmicToneMapper final : public ToneMapper {
|
|
FilmicToneMapper() noexcept;
|
|
~FilmicToneMapper() noexcept final;
|
|
|
|
math::float3 operator()(math::float3 x) const noexcept override;
|
|
};
|
|
|
|
/**
|
|
* Generic tone mapping operator that gives control over the tone mapping
|
|
* curve. This operator can be used to control the aesthetics of the final
|
|
* image. This operator also allows to control the dynamic range of the
|
|
* scene referred values.
|
|
*
|
|
* The tone mapping curve is defined by 5 parameters:
|
|
* - contrast: controls the contrast of the curve
|
|
* - midGrayIn: sets the input middle gray
|
|
* - midGrayOut: sets the output middle gray
|
|
* - hdrMax: defines the maximum input value that will be mapped to
|
|
* output white
|
|
*/
|
|
struct UTILS_PUBLIC GenericToneMapper final : public ToneMapper {
|
|
/**
|
|
* Builds a new generic tone mapper. The default values of the
|
|
* constructor parameters approximate an ACES tone mapping curve
|
|
* and the maximum input value is set to 10.0.
|
|
*
|
|
* @param contrast controls the contrast of the curve, must be > 0.0, values
|
|
* in the range 0.5..2.0 are recommended.
|
|
* @param midGrayIn sets the input middle gray, between 0.0 and 1.0.
|
|
* @param midGrayOut sets the output middle gray, between 0.0 and 1.0.
|
|
* @param hdrMax defines the maximum input value that will be mapped to
|
|
* output white. Must be >= 1.0.
|
|
*/
|
|
explicit GenericToneMapper(
|
|
float contrast = 1.55f,
|
|
float midGrayIn = 0.18f,
|
|
float midGrayOut = 0.215f,
|
|
float hdrMax = 10.0f
|
|
) noexcept;
|
|
~GenericToneMapper() noexcept final;
|
|
|
|
GenericToneMapper(GenericToneMapper const&) = delete;
|
|
GenericToneMapper& operator=(GenericToneMapper const&) = delete;
|
|
GenericToneMapper(GenericToneMapper&& rhs) noexcept;
|
|
GenericToneMapper& operator=(GenericToneMapper&& rhs) noexcept;
|
|
|
|
math::float3 operator()(math::float3 x) const noexcept override;
|
|
|
|
/** Returns the contrast of the curve as a strictly positive value. */
|
|
float getContrast() const noexcept;
|
|
|
|
/** Returns how fast scene referred values map to output white as a value between 0.0 and 1.0. */
|
|
float getShoulder() const noexcept;
|
|
|
|
/** Returns the middle gray point for input values as a value between 0.0 and 1.0. */
|
|
float getMidGrayIn() const noexcept;
|
|
|
|
/** Returns the middle gray point for output values as a value between 0.0 and 1.0. */
|
|
float getMidGrayOut() const noexcept;
|
|
|
|
/** Returns the maximum input value that will map to output white, as a value >= 1.0. */
|
|
float getHdrMax() const noexcept;
|
|
|
|
/** Sets the contrast of the curve, must be > 0.0, values in the range 0.5..2.0 are recommended. */
|
|
void setContrast(float contrast) noexcept;
|
|
|
|
/** Sets the input middle gray, between 0.0 and 1.0. */
|
|
void setMidGrayIn(float midGrayIn) noexcept;
|
|
|
|
/** Sets the output middle gray, between 0.0 and 1.0. */
|
|
void setMidGrayOut(float midGrayOut) noexcept;
|
|
|
|
/** Defines the maximum input value that will be mapped to output white. Must be >= 1.0. */
|
|
void setHdrMax(float hdrMax) noexcept;
|
|
|
|
private:
|
|
struct Options;
|
|
Options* mOptions;
|
|
};
|
|
|
|
/**
|
|
* A tone mapper that converts the input HDR RGB color into one of 16 debug colors
|
|
* that represent the pixel's exposure. When the output is cyan, the input color
|
|
* represents middle gray (18% exposure). Every exposure stop above or below middle
|
|
* gray causes a color shift.
|
|
*
|
|
* The relationship between exposures and colors is:
|
|
*
|
|
* - -5EV black
|
|
* - -4EV darkest blue
|
|
* - -3EV darker blue
|
|
* - -2EV dark blue
|
|
* - -1EV blue
|
|
* - OEV cyan
|
|
* - +1EV dark green
|
|
* - +2EV green
|
|
* - +3EV yellow
|
|
* - +4EV yellow-orange
|
|
* - +5EV orange
|
|
* - +6EV bright red
|
|
* - +7EV red
|
|
* - +8EV magenta
|
|
* - +9EV purple
|
|
* - +10EV white
|
|
*
|
|
* This tone mapper is useful to validate and tweak scene lighting.
|
|
*/
|
|
struct UTILS_PUBLIC DisplayRangeToneMapper final : public ToneMapper {
|
|
DisplayRangeToneMapper() noexcept;
|
|
~DisplayRangeToneMapper() noexcept override;
|
|
|
|
math::float3 operator()(math::float3 c) const noexcept override;
|
|
};
|
|
|
|
} // namespace filament
|
|
|
|
#endif // TNT_FILAMENT_TONEMAPPER_H
|