vegetation: Fixed segfault in unit test
This commit is contained in:
parent
4a710c0977
commit
1d9d24b958
4 changed files with 68 additions and 48 deletions
|
@ -29,9 +29,9 @@ void VegetationDefinition::applyPreset(VegetationPreset preset, RandomGenerator
|
||||||
|
|
||||||
clear();
|
clear();
|
||||||
|
|
||||||
if (preset == VEGETATION_PRESET_TEMPERATE) {
|
/*if (preset == VEGETATION_PRESET_TEMPERATE) {
|
||||||
layer.applyPreset(VegetationLayerDefinition::VEGETATION_BASIC_TREES, random);
|
layer.applyPreset(VegetationLayerDefinition::VEGETATION_BASIC_TREES, random);
|
||||||
layer.setName("Basic tree");
|
layer.setName("Basic tree");
|
||||||
addLayer(layer);
|
addLayer(layer);
|
||||||
}
|
}*/
|
||||||
}
|
}
|
||||||
|
|
|
@ -59,49 +59,55 @@ void OpenGLVegetationLayer::removeInstancesOutsideArea(double xmin, double xmax,
|
||||||
instances->erase(remove_if(instances->begin(), instances->end(), isNull), instances->end());
|
instances->erase(remove_if(instances->begin(), instances->end(), isNull), instances->end());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void OpenGLVegetationLayer::updateInstances() {
|
||||||
|
// Compute new area around camera
|
||||||
|
double newxmin, newxmax, newzmin, newzmax;
|
||||||
|
newxmin = camera_location->x - range;
|
||||||
|
newxmax = camera_location->x + range;
|
||||||
|
newzmin = camera_location->z - range;
|
||||||
|
newzmax = camera_location->z + range;
|
||||||
|
|
||||||
|
// Prepare instances where area grew
|
||||||
|
vector<OpenGLVegetationInstance *> new_instances;
|
||||||
|
if (newxmin < xmin) {
|
||||||
|
produceInstancesInArea(newxmin, xmin, newzmin, newzmax, &new_instances);
|
||||||
|
}
|
||||||
|
if (newxmax > xmax) {
|
||||||
|
produceInstancesInArea(xmax, newxmax, newzmin, newzmax, &new_instances);
|
||||||
|
}
|
||||||
|
if (newzmin < zmin) {
|
||||||
|
produceInstancesInArea(xmin, xmax, newzmin, zmin, &new_instances);
|
||||||
|
}
|
||||||
|
if (newzmax > zmax) {
|
||||||
|
produceInstancesInArea(xmin, xmax, zmax, newzmax, &new_instances);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Apply the changes
|
||||||
|
lock_instances->acquire();
|
||||||
|
xmin = newxmin;
|
||||||
|
xmax = newxmax;
|
||||||
|
zmin = newzmin;
|
||||||
|
zmax = newzmax;
|
||||||
|
removeInstancesOutsideArea(xmin, xmax, zmin, zmax, &instances);
|
||||||
|
instances.insert(instances.end(), new_instances.begin(), new_instances.end());
|
||||||
|
for (auto instance : instances) {
|
||||||
|
instance->setDistance(instance->getBase().sub(*camera_location).getNorm());
|
||||||
|
}
|
||||||
|
sort(instances.begin(), instances.end(), compareInstances);
|
||||||
|
lock_instances->release();
|
||||||
|
}
|
||||||
|
|
||||||
|
void OpenGLVegetationLayer::updateImpostor() {
|
||||||
|
bool interrupted = false;
|
||||||
|
impostor->prepareTexture(*definition->getModel(), *parent->getScenery(), &interrupted);
|
||||||
|
}
|
||||||
|
|
||||||
void OpenGLVegetationLayer::threadedUpdate() {
|
void OpenGLVegetationLayer::threadedUpdate() {
|
||||||
if (camera_changed) {
|
if (camera_changed) {
|
||||||
camera_changed = false;
|
camera_changed = false;
|
||||||
|
|
||||||
// Compute new area around camera
|
updateInstances();
|
||||||
double newxmin, newxmax, newzmin, newzmax;
|
updateImpostor();
|
||||||
newxmin = camera_location->x - range;
|
|
||||||
newxmax = camera_location->x + range;
|
|
||||||
newzmin = camera_location->z - range;
|
|
||||||
newzmax = camera_location->z + range;
|
|
||||||
|
|
||||||
// Prepare instances where area grew
|
|
||||||
vector<OpenGLVegetationInstance *> new_instances;
|
|
||||||
if (newxmin < xmin) {
|
|
||||||
produceInstancesInArea(newxmin, xmin, newzmin, newzmax, &new_instances);
|
|
||||||
}
|
|
||||||
if (newxmax > xmax) {
|
|
||||||
produceInstancesInArea(xmax, newxmax, newzmin, newzmax, &new_instances);
|
|
||||||
}
|
|
||||||
if (newzmin < zmin) {
|
|
||||||
produceInstancesInArea(xmin, xmax, newzmin, zmin, &new_instances);
|
|
||||||
}
|
|
||||||
if (newzmax > zmax) {
|
|
||||||
produceInstancesInArea(xmin, xmax, zmax, newzmax, &new_instances);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Apply the changes
|
|
||||||
lock_instances->acquire();
|
|
||||||
xmin = newxmin;
|
|
||||||
xmax = newxmax;
|
|
||||||
zmin = newzmin;
|
|
||||||
zmax = newzmax;
|
|
||||||
removeInstancesOutsideArea(xmin, xmax, zmin, zmax, &instances);
|
|
||||||
instances.insert(instances.end(), new_instances.begin(), new_instances.end());
|
|
||||||
for (auto instance : instances) {
|
|
||||||
instance->setDistance(instance->getBase().sub(*camera_location).getNorm());
|
|
||||||
}
|
|
||||||
sort(instances.begin(), instances.end(), compareInstances);
|
|
||||||
lock_instances->release();
|
|
||||||
|
|
||||||
// Update impostor texture
|
|
||||||
bool interrupted = false;
|
|
||||||
impostor->prepareTexture(*definition->getModel(), *parent->getScenery(), &interrupted);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -34,6 +34,20 @@ class OPENGLSHARED_EXPORT OpenGLVegetationLayer {
|
||||||
virtual void removeInstancesOutsideArea(double xmin, double xmax, double zmin, double zmax,
|
virtual void removeInstancesOutsideArea(double xmin, double xmax, double zmin, double zmax,
|
||||||
vector<OpenGLVegetationInstance *> *instances) const;
|
vector<OpenGLVegetationInstance *> *instances) const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update the instances list.
|
||||||
|
*
|
||||||
|
* This should be called when the camera has moved enough to make a change.
|
||||||
|
*/
|
||||||
|
void updateInstances();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update the impostor textures.
|
||||||
|
*
|
||||||
|
* This should be called when the camera has moved enough to make a change.
|
||||||
|
*/
|
||||||
|
void updateImpostor();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Perform maintenance tasks that can be perform in a thread.
|
* Perform maintenance tasks that can be perform in a thread.
|
||||||
*
|
*
|
||||||
|
|
|
@ -28,7 +28,7 @@ class FakeLayerRenderer : public OpenGLVegetationLayer {
|
||||||
vector<OpenGLVegetationInstance *> static_instances;
|
vector<OpenGLVegetationInstance *> static_instances;
|
||||||
};
|
};
|
||||||
|
|
||||||
TEST(OpenGLVegetationLayer, threadedUpdate) {
|
TEST(OpenGLVegetationLayer, updateInstances) {
|
||||||
CameraDefinition camera;
|
CameraDefinition camera;
|
||||||
VegetationLayerDefinition definition(NULL, "test");
|
VegetationLayerDefinition definition(NULL, "test");
|
||||||
FakeLayerRenderer rendering(&definition);
|
FakeLayerRenderer rendering(&definition);
|
||||||
|
@ -36,32 +36,32 @@ TEST(OpenGLVegetationLayer, threadedUpdate) {
|
||||||
|
|
||||||
EXPECT_EQ(0, rendering.getInstanceCount());
|
EXPECT_EQ(0, rendering.getInstanceCount());
|
||||||
|
|
||||||
rendering.threadedUpdate();
|
rendering.updateInstances();
|
||||||
EXPECT_EQ(0, rendering.getInstanceCount());
|
EXPECT_EQ(0, rendering.getInstanceCount());
|
||||||
|
|
||||||
rendering.static_instances.push_back(
|
rendering.static_instances.push_back(
|
||||||
new OpenGLVegetationInstance(VegetationInstance(model, Vector3(0.0, 0.0, 0.0))));
|
new OpenGLVegetationInstance(VegetationInstance(model, Vector3(0.0, 0.0, 0.0))));
|
||||||
rendering.reset();
|
rendering.reset();
|
||||||
rendering.threadedUpdate();
|
rendering.updateInstances();
|
||||||
EXPECT_EQ(1, rendering.getInstanceCount());
|
EXPECT_EQ(1, rendering.getInstanceCount());
|
||||||
|
|
||||||
camera.setLocation(Vector3(-5.0, 0.0, 0.0));
|
camera.setLocation(Vector3(-5.0, 0.0, 0.0));
|
||||||
rendering.setCamera(&camera);
|
rendering.setCamera(&camera);
|
||||||
rendering.threadedUpdate();
|
rendering.updateInstances();
|
||||||
EXPECT_EQ(1, rendering.getInstanceCount());
|
EXPECT_EQ(1, rendering.getInstanceCount());
|
||||||
|
|
||||||
camera.setLocation(Vector3(-11.0, 0.0, 0.0));
|
camera.setLocation(Vector3(-11.0, 0.0, 0.0));
|
||||||
rendering.setCamera(&camera);
|
rendering.setCamera(&camera);
|
||||||
rendering.threadedUpdate();
|
rendering.updateInstances();
|
||||||
EXPECT_EQ(0, rendering.getInstanceCount());
|
EXPECT_EQ(0, rendering.getInstanceCount());
|
||||||
|
|
||||||
camera.setLocation(Vector3(0.0, 0.0, 5.0));
|
camera.setLocation(Vector3(0.0, 0.0, 5.0));
|
||||||
rendering.setCamera(&camera);
|
rendering.setCamera(&camera);
|
||||||
rendering.threadedUpdate();
|
rendering.updateInstances();
|
||||||
EXPECT_EQ(1, rendering.getInstanceCount());
|
EXPECT_EQ(1, rendering.getInstanceCount());
|
||||||
|
|
||||||
camera.setLocation(Vector3(0.0, 0.0, 15.0));
|
camera.setLocation(Vector3(0.0, 0.0, 15.0));
|
||||||
rendering.setCamera(&camera);
|
rendering.setCamera(&camera);
|
||||||
rendering.threadedUpdate();
|
rendering.updateInstances();
|
||||||
EXPECT_EQ(0, rendering.getInstanceCount());
|
EXPECT_EQ(0, rendering.getInstanceCount());
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue