1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131
|
#pragma once
#include "globalincs/pstypes.h"
#include "math/vecmat.h"
#include <memory>
#include <tl/optional.hpp>
namespace fso {
namespace fred {
class CFred_mission_save;
}
}
class volumetric_nebula {
//Instance Settings
//Type
//The name of the POF file specifying the hull of the nebula. Can be convex. Can be multiple disjunct meshes. Each mesh must be watertight. Mesh polies may not intersect, however one mesh may be completely contained in another.
SCP_string hullPof;
//The position and size of the bounding box of the volumetrics.
vec3d pos = ZERO_VECTOR, size = ZERO_VECTOR, bb_min = ZERO_VECTOR, bb_max = ZERO_VECTOR;
//Main color
std::tuple<float, float, float> nebulaColor = std::make_tuple(0.0f, 0.0f, 0.0f);
//Quality
//Whether or not edge smoothing is enabled. Disabling this causes jagged edges when looking at the nebula axis aligned, but it's expensive
bool doEdgeSmoothing = false;
//How many steps are used to nebulify the volume until the visibility is reached. In theory purely quality and can be changed without changing the aesthetics. Mostly FPS Cost
int steps = 15;
//Number of steps per nebula slice to test towards the sun. Mostly FPS Cost
int globalLightSteps = 6;
//Resolution of 3D texture as 2^n. 5 - 8 recommended. Mostly VRAM cost
int resolution = 6;
//Oversampling of 3D-Texture. Will quadruple loading computation time for each increment, but improves banding especially at lower resolutions. 1 - 3. Mostly Loading time cost.
int oversampling = 2;
//Resolution of Noise 3D-Texture as 2^n. 5 - 8 recommended. Mostly VRAM cost
int noiseResolution = 5;
//General Visibility
//The distance in meters until the target translucity is reached
float opacityDistance = 5.0f;
//The target translucity. The nebula won't get more opaque than what is specified here. 0 is not possible.
float alphaLim = 0.001f;
//Emissive Light Fogging
//How quickly the emissive will widen in the nebula. The larger the value, the wider will emissives be drawn even with only little nebula to obscure it.
float emissiveSpread = 0.7f;
//How intense emissives will be added. The higher, the brighter the emissives.
float emissiveIntensity = 1.1f;
//Correcting factor for emissive alpha. Values > 1 will darken the added emissive closer to the actual source, values < 1 will lighten the added emissive closer to the actual source.
float emissiveFalloff = 1.5f;
//Sun-based illumination
//HG coefficient for backlit nebulae. (-1, 1), but should probably be in the range of (0.05, 0.75)
float henyeyGreensteinCoeff = 0.2f;
//Distance factor for global light vs nebula translucity. Values > 1 means the nebula is brighter than it ought to be when it's deeper, values < 0 means it's darker when its shallower
float globalLightDistanceFactor = 1.0f;
//Edge noise settings
//Is the noise even active
bool noiseActive = false;
//The size of the noise's two levels, in meters. The fraction of the two levels should have a large denominator to avoid visible harmonics
std::tuple<float, float> noiseScale = std::make_tuple(1.0f, 1.0f);
//Noise functions. ANL's DSL for noise. Leave empty to use default noise. Default is representable by: translate(bias(scale(valueBasis(3,0),3),scale(valueBasis(3,1),8)),scale(simplexBasis(2),4)*0.6)
tl::optional<SCP_string> noiseColorFunc1 = tl::nullopt, noiseColorFunc2 = tl::nullopt;
//Noise color
std::tuple<float, float, float> noiseColor = std::make_tuple(0.0f, 0.0f, 0.0f);
//Noise Intensity
float noiseColorIntensity = 1.0f;
//Instance Data
int volumeBitmapHandle = -1;
std::unique_ptr<ubyte[]> volumeBitmapData = nullptr;
int noiseVolumeBitmapHandle = -1;
std::unique_ptr<ubyte[]> noiseVolumeBitmapData = nullptr;
float udfScale = 1.0f;
bool enabled = true;
//Friend things that are allowed to directly manipulate "current" volumetrics. Only FRED and the Lab. In all other cases, "sensibly constant" values behave properly RAII and stay constant afterwards.
friend class LabUi; //Lab
friend class CFred_mission_save; //FRED
friend class volumetrics_dlg; //FRED
friend class fso::fred::CFred_mission_save; //QtFRED
public:
volumetric_nebula();
~volumetric_nebula();
volumetric_nebula& parse_volumetric_nebula();
const vec3d& getPos() const;
const vec3d& getSize() const;
const std::tuple<float, float, float>& getNebulaColor() const;
bool getEdgeSmoothing() const;
int getSteps() const;
int getGlobalLightSteps() const;
float getOpacityDistance() const;
float getStepsize() const;
float getAlphaLim() const;
float getEmissiveSpread() const;
float getEmissiveIntensity() const;
float getEmissiveFalloff() const;
float getHenyeyGreensteinCoeff() const;
float getGlobalLightDistanceFactor() const;
float getGlobalLightStepsize() const;
bool getNoiseActive() const;
const std::tuple<float, float>& getNoiseColorScale() const;
const std::tuple<float, float, float>& getNoiseColor() const;
float getNoiseColorIntensity() const;
bool isVolumeBitmapValid() const;
void renderVolumeBitmap();
int getVolumeBitmapHandle() const;
int getNoiseVolumeBitmapHandle() const;
float getUDFScale() const;
float getAlphaToPos(const vec3d& pnt, float distance_mult) const;
void set_enabled(bool set_enabled);
bool get_enabled() const;
};
void volumetrics_level_close();
|