paysages : Fixed sun drawing algorithm.
git-svn-id: https://subversion.assembla.com/svn/thunderk/paysages@510 b1fd45b6-86a6-48da-8261-f70d1f35bdcc
This commit is contained in:
parent
ed268098a1
commit
620877bf64
12 changed files with 76 additions and 33 deletions
1
TODO
1
TODO
|
@ -42,7 +42,6 @@ Technlogy Preview 3 :
|
|||
=> Add user markers on OSD.
|
||||
=> Add areas marking.
|
||||
- Add a noise automatic filler.
|
||||
- Fix the distorted sun appearance.
|
||||
- Lock some previews together (eg: terrain height and colored preview).
|
||||
- Find a new licence.
|
||||
|
||||
|
|
|
@ -82,7 +82,7 @@ FormAtmosphere::FormAtmosphere(QWidget *parent):
|
|||
addInputInt(tr("Day time (hour)"), &_definition->hour, 0, 23, 1, 10);
|
||||
addInputInt(tr("Day time (minute)"), &_definition->minute, 0, 59, 1, 10);
|
||||
//addInputColor(tr("Sun color"), &_definition->sun_color);
|
||||
addInputDouble(tr("Sun radius"), &_definition->sun_radius, 0.0, 0.1, 0.001, 0.01);
|
||||
addInputDouble(tr("Sun radius"), &_definition->sun_radius, 0.0, 5.0, 0.05, 0.5);
|
||||
addInputDouble(tr("Influence of skydome on lighting"), &_definition->dome_lighting, 0.0, 2.0, 0.01, 0.1);
|
||||
addInputDouble(tr("Humidity"), &_definition->humidity, 0.0, 1.0, 0.01, 0.1)->setVisibilityCondition((int*)&_definition->model, 0);
|
||||
|
||||
|
|
|
@ -219,7 +219,7 @@ int WidgetCurveEditor::getPointAt(int x, int y)
|
|||
{
|
||||
curveGetPoint(_curve, i, &point);
|
||||
curveToScreen(point.position, point.value, &dx, &dy);
|
||||
ndistance = toolsGetDistance2D((double)x, (double)y, (double)dx, (double)dy);
|
||||
ndistance = euclidGetDistance2D((double)x, (double)y, (double)dx, (double)dy);
|
||||
if (nearest < 0 || ndistance < distance)
|
||||
{
|
||||
distance = ndistance;
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
#include "public.h"
|
||||
#include "private.h"
|
||||
|
||||
/*
|
||||
* Atmospheric scattering, based on E. Bruneton and F.Neyret work.
|
||||
|
@ -18,7 +18,6 @@
|
|||
|
||||
/*********************** Constants ***********************/
|
||||
|
||||
#define WORLD_SCALING 0.05
|
||||
#define GROUND_OFFSET 0.5
|
||||
static const double Rg = 6360.0;
|
||||
static const double Rt = 6420.0;
|
||||
|
@ -1168,7 +1167,7 @@ Color brunetonApplyAerialPerspective(Renderer* renderer, Vector3 location, Color
|
|||
{
|
||||
Vector3 eye = renderer->camera_location;
|
||||
Vector3 direction = v3Scale(v3Sub(location, eye), WORLD_SCALING);
|
||||
Vector3 sun_position = v3Scale(renderer->atmosphere->getSunDirection(renderer), 149597870.0);
|
||||
Vector3 sun_position = v3Scale(renderer->atmosphere->getSunDirection(renderer), SUN_DISTANCE);
|
||||
|
||||
Vector3 x = {0.0, Rg + (max(eye.y, 0.0) + GROUND_OFFSET) * WORLD_SCALING, 0.0};
|
||||
Vector3 v = v3Normalize(direction);
|
||||
|
@ -1200,7 +1199,7 @@ void brunetonGetLightingStatus(Renderer* renderer, LightStatus* status, Vector3
|
|||
|
||||
double r0 = Rg + (max(lightingGetStatusLocation(status).y, 0.0) + GROUND_OFFSET) * WORLD_SCALING;
|
||||
Vector3 up = {0.0, 1.0, 0.0};
|
||||
Vector3 sun_position = v3Scale(renderer->atmosphere->getSunDirection(renderer), 149597870.0);
|
||||
Vector3 sun_position = v3Scale(renderer->atmosphere->getSunDirection(renderer), SUN_DISTANCE);
|
||||
Vector3 x = {0.0, r0, 0.0};
|
||||
Vector3 s = v3Normalize(v3Sub(sun_position, x));
|
||||
|
||||
|
|
|
@ -120,7 +120,6 @@ static Color _fakeGetSkyColor(Renderer* renderer, Vector3 direction)
|
|||
static Color _getSkyColor(Renderer* renderer, Vector3 direction)
|
||||
{
|
||||
AtmosphereDefinition* definition;
|
||||
double dist;
|
||||
Vector3 sun_direction, sun_position;
|
||||
Color sky_color, sun_color;
|
||||
|
||||
|
@ -128,9 +127,7 @@ static Color _getSkyColor(Renderer* renderer, Vector3 direction)
|
|||
|
||||
sun_direction = renderer->atmosphere->getSunDirection(renderer);
|
||||
direction = v3Normalize(direction);
|
||||
dist = v3Norm(v3Sub(direction, sun_direction));
|
||||
|
||||
sun_position = v3Scale(sun_direction, 149597870.0);
|
||||
sun_position = v3Scale(sun_direction, SUN_DISTANCE_SCALED);
|
||||
|
||||
/* Get base scattering*/
|
||||
switch (definition->model)
|
||||
|
@ -146,19 +143,25 @@ static Color _getSkyColor(Renderer* renderer, Vector3 direction)
|
|||
}
|
||||
|
||||
/* Get sun shape */
|
||||
if (dist < definition->sun_radius)
|
||||
double sun_radius = definition->sun_radius * SUN_RADIUS_SCALED;
|
||||
Vector3 hit1, hit2;
|
||||
int hits = euclidRayIntersectSphere(renderer->camera_location, direction, sun_position, sun_radius, &hit1, &hit2);
|
||||
if (hits > 1)
|
||||
{
|
||||
double dist = v3Norm(v3Sub(hit2, hit1)) / sun_radius; /* distance between intersection points (relative to radius) */
|
||||
|
||||
sun_color = definition->sun_color;
|
||||
sun_color.r *= 100.0;
|
||||
sun_color.g *= 100.0;
|
||||
sun_color.b *= 100.0;
|
||||
if (dist <= definition->sun_radius * 0.9)
|
||||
|
||||
if (dist > 0.05)
|
||||
{
|
||||
return sun_color;
|
||||
}
|
||||
else
|
||||
{
|
||||
sun_color.a = (dist - definition->sun_radius * 0.9) / (definition->sun_radius * 0.1);
|
||||
sun_color.a = 1.0 - dist / 0.05;
|
||||
colorMask(&sky_color, &sun_color);
|
||||
return sky_color;
|
||||
}
|
||||
|
|
|
@ -10,7 +10,7 @@ void atmosphereAutoPreset(AtmosphereDefinition* definition, AtmospherePreset pre
|
|||
definition->sun_color.g = 0.95;
|
||||
definition->sun_color.b = 0.9;
|
||||
definition->sun_color.a = 1.0;
|
||||
definition->sun_radius = 0.02;
|
||||
definition->sun_radius = 1.0;
|
||||
definition->humidity = 0.1;
|
||||
|
||||
switch (preset)
|
||||
|
|
|
@ -5,6 +5,13 @@
|
|||
|
||||
#define SPHERE_SIZE 10000.0
|
||||
|
||||
/* Factor to convert software units to kilometers */
|
||||
#define WORLD_SCALING 0.05
|
||||
#define SUN_DISTANCE 149597870.0
|
||||
#define SUN_DISTANCE_SCALED (SUN_DISTANCE / WORLD_SCALING)
|
||||
#define SUN_RADIUS 6.955e5
|
||||
#define SUN_RADIUS_SCALED (SUN_RADIUS / WORLD_SCALING)
|
||||
|
||||
Color basicApplyAerialPerspective(Renderer* renderer, Vector3 location, Color base);
|
||||
void basicGetLightingStatus(Renderer* renderer, LightStatus* status, Vector3 normal, int opaque);
|
||||
|
||||
|
|
|
@ -46,7 +46,7 @@ void sceneryQuit()
|
|||
void sceneryAutoPreset()
|
||||
{
|
||||
terrainAutoPreset(_terrain, TERRAIN_PRESET_STANDARD);
|
||||
atmosphereAutoPreset(_atmosphere, ATMOSPHERE_MODEL_BRUNETON);
|
||||
atmosphereAutoPreset(_atmosphere, ATMOSPHERE_PRESET_CLEAR_DAY);
|
||||
cloudsAutoPreset(_clouds, CLOUDS_PRESET_PARTLY_CLOUDY);
|
||||
}
|
||||
|
||||
|
|
|
@ -54,17 +54,3 @@ void toolsFloat2DMapCopy(double* src, double* dest, int src_xstart, int src_ysta
|
|||
dest = dest_row + dest_ystep;
|
||||
}
|
||||
}
|
||||
|
||||
Vector3 toolsGetNormalFromTriangle(Vector3 center, Vector3 bottom, Vector3 right)
|
||||
{
|
||||
Vector3 dx = v3Sub(right, center);
|
||||
Vector3 dz = v3Sub(bottom, center);
|
||||
return v3Normalize(v3Cross(dz, dx));
|
||||
}
|
||||
|
||||
double toolsGetDistance2D(double x1, double y1, double x2, double y2)
|
||||
{
|
||||
double dx = x2 - x1;
|
||||
double dy = y2 - y1;
|
||||
return sqrt(dx * dx + dy * dy);
|
||||
}
|
||||
|
|
|
@ -2,7 +2,6 @@
|
|||
#define _PAYSAGES_TOOLS_H_
|
||||
|
||||
#include "shared/types.h"
|
||||
#include "tools/euclid.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
|
@ -14,8 +13,6 @@ double toolsRandom();
|
|||
double toolsCubicInterpolate(double stencil[4], double x);
|
||||
double toolsBicubicInterpolate(double stencil[16], double x, double y);
|
||||
void toolsFloat2DMapCopy(double* src, double* dest, int src_xstart, int src_ystart, int dest_xstart, int dest_ystart, int xsize, int ysize, int src_xstep, int src_ystep, int dest_xstep, int dest_ystep);
|
||||
Vector3 toolsGetNormalFromTriangle(Vector3 center, Vector3 bottom, Vector3 right);
|
||||
double toolsGetDistance2D(double x1, double y1, double x2, double y2);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
|
|
@ -405,3 +405,51 @@ Matrix4 m4Inverse(Matrix4 m)
|
|||
}
|
||||
}
|
||||
|
||||
Vector3 euclidGetNormalFromTriangle(Vector3 center, Vector3 bottom, Vector3 right)
|
||||
{
|
||||
Vector3 dx = v3Sub(right, center);
|
||||
Vector3 dz = v3Sub(bottom, center);
|
||||
return v3Normalize(v3Cross(dz, dx));
|
||||
}
|
||||
|
||||
double euclidGetDistance2D(double x1, double y1, double x2, double y2)
|
||||
{
|
||||
double dx = x2 - x1;
|
||||
double dy = y2 - y1;
|
||||
return sqrt(dx * dx + dy * dy);
|
||||
}
|
||||
|
||||
int euclidRayIntersectSphere(Vector3 ray_point, Vector3 ray_direction, Vector3 sphere_center, double sphere_radius, Vector3* hit1, Vector3* hit2)
|
||||
{
|
||||
Vector3 ray_direction_sphere;
|
||||
double a, b, c, d;
|
||||
|
||||
ray_direction_sphere = v3Sub(ray_point, sphere_center);
|
||||
|
||||
a = ray_direction.x * ray_direction.x + ray_direction.y * ray_direction.y + ray_direction.z * ray_direction.z;
|
||||
b = 2 * (ray_direction.x * ray_direction_sphere.x + ray_direction.y * ray_direction_sphere.y + ray_direction.z * ray_direction_sphere.z);
|
||||
c = ray_direction_sphere.x * ray_direction_sphere.x + ray_direction_sphere.y * ray_direction_sphere.y + ray_direction_sphere.z * ray_direction_sphere.z - sphere_radius * sphere_radius;
|
||||
d = b * b - 4 * a * c;
|
||||
|
||||
if (d < 0.0)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
else if (d > 0.0)
|
||||
{
|
||||
if (hit1 && hit2)
|
||||
{
|
||||
*hit1 = v3Add(ray_point, v3Scale(ray_direction, (-b - sqrt(d)) / (2 * a)));
|
||||
*hit2 = v3Add(ray_point, v3Scale(ray_direction, (-b + sqrt(d)) / (2 * a)));
|
||||
}
|
||||
return 2;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (hit1)
|
||||
{
|
||||
*hit1 = v3Add(ray_point, v3Scale(ray_direction, -b / (2 * a)));
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -74,6 +74,10 @@ Matrix4 m4NewPerspective(double fov_y, double aspect, double near, double far);
|
|||
double m4Determinant(Matrix4 m);
|
||||
Matrix4 m4Inverse(Matrix4 m);
|
||||
|
||||
Vector3 euclidGetNormalFromTriangle(Vector3 center, Vector3 bottom, Vector3 right);
|
||||
double euclidGetDistance2D(double x1, double y1, double x2, double y2);
|
||||
int euclidRayIntersectSphere(Vector3 ray_point, Vector3 ray_direction, Vector3 sphere_center, double sphere_radius, Vector3* hit1, Vector3* hit2);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
Loading…
Reference in a new issue