Improved distance sorting for objects; fixes the case when a small satellite orbiting close to a planet was incorrectly occluded.

ver1_5_1
Chris Laurel 2002-11-04 04:14:07 +00:00
parent 83d4556c4f
commit 142ce492aa
2 changed files with 57 additions and 23 deletions

View File

@ -21,6 +21,7 @@
#include <celutil/debug.h>
#include <celmath/frustum.h>
#include <celmath/distance.h>
#include <celmath/intersect.h>
#include "gl.h"
#include "astro.h"
#include "glext.h"
@ -264,6 +265,44 @@ static float calcPixelSize(float fovY, float windowHeight)
}
bool operator<(const RenderListEntry& a, const RenderListEntry& b)
{
// This comparison functions tries to determine which of two objects is
// closer to the viewer. Looking just at the distances of the centers
// is not enough, nor is comparing distances to the bounding spheres.
// Here we trace a ray from the viewer to the center of the smaller
// of the two objects and see which object it intersects first. If the
// ray doesn't intersect the larger object at all, it's safe to use
// the distance to bounding sphere test.
if (a.radius < b.radius)
{
Vec3f dir = a.position - Point3f(0.0f, 0.0f, 0.0f);
float distance;
dir.normalize();
if (testIntersection(Ray3f(Point3f(0.0f, 0.0f, 0.0f), dir),
Spheref(b.position, b.radius),
distance))
{
return a.distance - a.radius < distance;
}
}
else
{
Vec3f dir = b.position - Point3f(0.0f, 0.0f, 0.0f);
float distance;
dir.normalize();
if (testIntersection(Ray3f(Point3f(0.0f, 0.0f, 0.0f), dir),
Spheref(a.position, a.radius),
distance))
{
return distance < b.distance - b.radius;
}
}
return a.distance - a.radius < b.distance - b.radius;
}
bool Renderer::init(int winWidth, int winHeight)
{
// Initialize static meshes and textures common to all instances of Renderer
@ -843,6 +882,7 @@ void Renderer::autoMag(float& faintestMag)
}
void Renderer::render(const Observer& observer,
const Universe& universe,
float faintestMagNight,
@ -3647,7 +3687,7 @@ public:
Vec3f viewNormal;
vector<Renderer::Particle>* glareParticles;
vector<Renderer::RenderListEntry>* renderList;
vector<RenderListEntry>* renderList;
Renderer::StarVertexBuffer* starVertexBuffer;
float faintestMagNight;
@ -3759,7 +3799,7 @@ void StarRenderer::process(const Star& star, float distance, float appMag)
}
else
{
Renderer::RenderListEntry rle;
RenderListEntry rle;
rle.star = &star;
rle.body = NULL;
rle.isCometTail = false;

View File

@ -18,6 +18,21 @@
#include <celtxf/texturefont.h>
struct RenderListEntry
{
const Star* star;
Body* body;
Point3f position;
Vec3f sun;
float distance;
float radius;
float nearZ;
float farZ;
float discSizeInPixels;
float appMag;
bool isCometTail;
};
class Renderer
{
public:
@ -126,27 +141,6 @@ class Renderer
float pad0, pad1, pad2;
};
typedef struct _RenderListEntry
{
const Star* star;
Body* body;
Point3f position;
Vec3f sun;
float distance;
float radius;
float nearZ;
float farZ;
float discSizeInPixels;
float appMag;
bool isCometTail;
bool operator<(const _RenderListEntry& r) const
{
return distance - radius < r.distance - r.radius;
// return z > r.z;
}
} RenderListEntry;
struct EclipseShadow
{
Point3f origin;