Moved all generators under their own base class and folder
This commit is contained in:
parent
87a9766442
commit
8879d9b2e7
1
SCsub
1
SCsub
@ -11,6 +11,7 @@ files = [
|
||||
"meshers/mc/*.cpp",
|
||||
"meshers/*.cpp",
|
||||
"streams/*.cpp",
|
||||
"generators/*.cpp",
|
||||
"util/*.cpp",
|
||||
"terrain/*.cpp",
|
||||
"math/*.cpp",
|
||||
|
55
generators/voxel_generator.cpp
Normal file
55
generators/voxel_generator.cpp
Normal file
@ -0,0 +1,55 @@
|
||||
#include "voxel_generator.h"
|
||||
#include "../voxel_string_names.h"
|
||||
|
||||
VoxelGenerator::VoxelGenerator() {
|
||||
}
|
||||
|
||||
void VoxelGenerator::generate_block(VoxelBlockRequest &input) {
|
||||
|
||||
ERR_FAIL_COND(input.voxel_buffer.is_null());
|
||||
ScriptInstance *script = get_script_instance();
|
||||
|
||||
if (script) {
|
||||
|
||||
// Call script to generate buffer
|
||||
Variant arg1 = input.voxel_buffer;
|
||||
Variant arg2 = input.origin_in_voxels.to_vec3();
|
||||
Variant arg3 = input.lod;
|
||||
|
||||
const Variant *args[3] = { &arg1, &arg2, &arg3 };
|
||||
Variant::CallError err;
|
||||
script->call(VoxelStringNames::get_singleton()->generate_block, args, 3, err);
|
||||
|
||||
ERR_FAIL_COND_MSG(err.error != Variant::CallError::CALL_OK,
|
||||
"voxel_generator.cpp:emerge_block gave an error: " + String::num(err.error) +
|
||||
", Argument: " + String::num(err.argument) +
|
||||
", Expected type: " + Variant::get_type_name(err.expected));
|
||||
|
||||
// This had to be explicitely logged due to the usual GD debugger not working with threads
|
||||
}
|
||||
}
|
||||
|
||||
//bool VoxelGenerator::is_thread_safe() const {
|
||||
// return false;
|
||||
//}
|
||||
|
||||
//bool VoxelGenerator::is_cloneable() const {
|
||||
// return false;
|
||||
//}
|
||||
|
||||
void VoxelGenerator::emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin_in_voxels, int lod) {
|
||||
VoxelBlockRequest r = { out_buffer, Vector3i(origin_in_voxels), lod };
|
||||
generate_block(r);
|
||||
}
|
||||
|
||||
void VoxelGenerator::_b_generate_block(Ref<VoxelBuffer> out_buffer, Vector3 origin_in_voxels, int lod) {
|
||||
ERR_FAIL_COND(lod < 0);
|
||||
VoxelBlockRequest r = { out_buffer, Vector3i(origin_in_voxels), lod };
|
||||
generate_block(r);
|
||||
}
|
||||
|
||||
void VoxelGenerator::_bind_methods() {
|
||||
// Note: C++ inheriting classes don't need to re-bind these, because they are bindings that call the actual virtual methods
|
||||
|
||||
ClassDB::bind_method(D_METHOD("generate_block", "out_buffer", "origin_in_voxels", "lod"), &VoxelGenerator::_b_generate_block);
|
||||
}
|
31
generators/voxel_generator.h
Normal file
31
generators/voxel_generator.h
Normal file
@ -0,0 +1,31 @@
|
||||
#ifndef VOXEL_GENERATOR_H
|
||||
#define VOXEL_GENERATOR_H
|
||||
|
||||
#include "../streams/voxel_stream.h"
|
||||
|
||||
// TODO I would like VoxelGenerator to not inherit VoxelStream
|
||||
// because it gets members that make no sense with generators
|
||||
|
||||
// Provides access to read-only generated voxels.
|
||||
// Must be implemented in a multi-thread-safe way.
|
||||
class VoxelGenerator : public VoxelStream {
|
||||
GDCLASS(VoxelGenerator, VoxelStream)
|
||||
public:
|
||||
VoxelGenerator();
|
||||
|
||||
virtual void generate_block(VoxelBlockRequest &input);
|
||||
// TODO Single sample
|
||||
|
||||
// virtual bool is_thread_safe() const;
|
||||
// virtual bool is_cloneable() const;
|
||||
|
||||
private:
|
||||
void emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin_in_voxels, int lod) override;
|
||||
|
||||
protected:
|
||||
static void _bind_methods();
|
||||
|
||||
void _b_generate_block(Ref<VoxelBuffer> out_buffer, Vector3 origin_in_voxels, int lod);
|
||||
};
|
||||
|
||||
#endif // VOXEL_GENERATOR_H
|
59
generators/voxel_stream_heightmap.cpp
Normal file
59
generators/voxel_stream_heightmap.cpp
Normal file
@ -0,0 +1,59 @@
|
||||
#include "voxel_stream_heightmap.h"
|
||||
#include "../util/array_slice.h"
|
||||
#include "../util/fixed_array.h"
|
||||
|
||||
VoxelGeneratorHeightmap::VoxelGeneratorHeightmap() {
|
||||
}
|
||||
|
||||
void VoxelGeneratorHeightmap::set_channel(VoxelBuffer::ChannelId channel) {
|
||||
ERR_FAIL_INDEX(channel, VoxelBuffer::MAX_CHANNELS);
|
||||
_channel = channel;
|
||||
}
|
||||
|
||||
VoxelBuffer::ChannelId VoxelGeneratorHeightmap::get_channel() const {
|
||||
return _channel;
|
||||
}
|
||||
|
||||
void VoxelGeneratorHeightmap::set_height_start(float start) {
|
||||
_range.start = start;
|
||||
}
|
||||
|
||||
float VoxelGeneratorHeightmap::get_height_start() const {
|
||||
return _range.start;
|
||||
}
|
||||
|
||||
void VoxelGeneratorHeightmap::set_height_range(float range) {
|
||||
_range.height = range;
|
||||
}
|
||||
|
||||
float VoxelGeneratorHeightmap::get_height_range() const {
|
||||
return _range.height;
|
||||
}
|
||||
|
||||
void VoxelGeneratorHeightmap::set_iso_scale(float iso_scale) {
|
||||
_iso_scale = iso_scale;
|
||||
}
|
||||
|
||||
float VoxelGeneratorHeightmap::get_iso_scale() const {
|
||||
return _iso_scale;
|
||||
}
|
||||
|
||||
void VoxelGeneratorHeightmap::_bind_methods() {
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_channel", "channel"), &VoxelGeneratorHeightmap::set_channel);
|
||||
ClassDB::bind_method(D_METHOD("get_channel"), &VoxelGeneratorHeightmap::get_channel);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_height_start", "start"), &VoxelGeneratorHeightmap::set_height_start);
|
||||
ClassDB::bind_method(D_METHOD("get_height_start"), &VoxelGeneratorHeightmap::get_height_start);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_height_range", "range"), &VoxelGeneratorHeightmap::set_height_range);
|
||||
ClassDB::bind_method(D_METHOD("get_height_range"), &VoxelGeneratorHeightmap::get_height_range);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_iso_scale", "scale"), &VoxelGeneratorHeightmap::set_iso_scale);
|
||||
ClassDB::bind_method(D_METHOD("get_iso_scale"), &VoxelGeneratorHeightmap::get_iso_scale);
|
||||
|
||||
ADD_PROPERTY(PropertyInfo(Variant::INT, "channel", PROPERTY_HINT_ENUM, VoxelBuffer::CHANNEL_ID_HINT_STRING), "set_channel", "get_channel");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::REAL, "height_start"), "set_height_start", "get_height_start");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::REAL, "height_range"), "set_height_range", "get_height_range");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::REAL, "iso_scale"), "set_iso_scale", "get_iso_scale");
|
||||
}
|
@ -1,13 +1,14 @@
|
||||
#ifndef VOXEL_STREAM_HEIGHTMAP_H
|
||||
#define VOXEL_STREAM_HEIGHTMAP_H
|
||||
|
||||
#include "voxel_stream.h"
|
||||
#include "../voxel_buffer.h"
|
||||
#include "voxel_generator.h"
|
||||
#include <core/image.h>
|
||||
|
||||
class VoxelStreamHeightmap : public VoxelStream {
|
||||
GDCLASS(VoxelStreamHeightmap, VoxelStream)
|
||||
class VoxelGeneratorHeightmap : public VoxelGenerator {
|
||||
GDCLASS(VoxelGeneratorHeightmap, VoxelGenerator)
|
||||
public:
|
||||
VoxelStreamHeightmap();
|
||||
VoxelGeneratorHeightmap();
|
||||
|
||||
void set_channel(VoxelBuffer::ChannelId channel);
|
||||
VoxelBuffer::ChannelId get_channel() const;
|
@ -19,42 +19,42 @@ inline float get_height_blurred(Image &im, int x, int y) {
|
||||
|
||||
} // namespace
|
||||
|
||||
VoxelStreamImage::VoxelStreamImage() {
|
||||
VoxelGeneratorImage::VoxelGeneratorImage() {
|
||||
}
|
||||
|
||||
void VoxelStreamImage::set_image(Ref<Image> im) {
|
||||
void VoxelGeneratorImage::set_image(Ref<Image> im) {
|
||||
_image = im;
|
||||
}
|
||||
|
||||
Ref<Image> VoxelStreamImage::get_image() const {
|
||||
Ref<Image> VoxelGeneratorImage::get_image() const {
|
||||
return _image;
|
||||
}
|
||||
|
||||
void VoxelStreamImage::set_blur_enabled(bool enable) {
|
||||
void VoxelGeneratorImage::set_blur_enabled(bool enable) {
|
||||
_blur_enabled = enable;
|
||||
}
|
||||
|
||||
bool VoxelStreamImage::is_blur_enabled() const {
|
||||
bool VoxelGeneratorImage::is_blur_enabled() const {
|
||||
return _blur_enabled;
|
||||
}
|
||||
|
||||
void VoxelStreamImage::emerge_block(Ref<VoxelBuffer> p_out_buffer, Vector3i origin_in_voxels, int lod) {
|
||||
void VoxelGeneratorImage::generate_block(VoxelBlockRequest &input) {
|
||||
|
||||
ERR_FAIL_COND(_image.is_null());
|
||||
|
||||
VoxelBuffer &out_buffer = **p_out_buffer;
|
||||
VoxelBuffer &out_buffer = **input.voxel_buffer;
|
||||
Image &image = **_image;
|
||||
|
||||
image.lock();
|
||||
|
||||
if (_blur_enabled) {
|
||||
VoxelStreamHeightmap::generate(out_buffer,
|
||||
VoxelGeneratorHeightmap::generate(out_buffer,
|
||||
[&image](int x, int z) { return get_height_blurred(image, x, z); },
|
||||
origin_in_voxels, lod);
|
||||
input.origin_in_voxels, input.lod);
|
||||
} else {
|
||||
VoxelStreamHeightmap::generate(out_buffer,
|
||||
VoxelGeneratorHeightmap::generate(out_buffer,
|
||||
[&image](int x, int z) { return get_height_repeat(image, x, z); },
|
||||
origin_in_voxels, lod);
|
||||
input.origin_in_voxels, input.lod);
|
||||
}
|
||||
|
||||
image.unlock();
|
||||
@ -62,10 +62,12 @@ void VoxelStreamImage::emerge_block(Ref<VoxelBuffer> p_out_buffer, Vector3i orig
|
||||
out_buffer.compress_uniform_channels();
|
||||
}
|
||||
|
||||
void VoxelStreamImage::_bind_methods() {
|
||||
void VoxelGeneratorImage::_bind_methods() {
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_image", "image"), &VoxelStreamImage::set_image);
|
||||
ClassDB::bind_method(D_METHOD("get_image"), &VoxelStreamImage::get_image);
|
||||
ClassDB::bind_method(D_METHOD("set_image", "image"), &VoxelGeneratorImage::set_image);
|
||||
ClassDB::bind_method(D_METHOD("get_image"), &VoxelGeneratorImage::get_image);
|
||||
|
||||
// TODO Expose blur option!
|
||||
|
||||
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "image", PROPERTY_HINT_RESOURCE_TYPE, "Image"), "set_image", "get_image");
|
||||
}
|
@ -5,10 +5,10 @@
|
||||
#include <core/image.h>
|
||||
|
||||
// Provides infinite tiling heightmap based on an image
|
||||
class VoxelStreamImage : public VoxelStreamHeightmap {
|
||||
GDCLASS(VoxelStreamImage, VoxelStreamHeightmap)
|
||||
class VoxelGeneratorImage : public VoxelGeneratorHeightmap {
|
||||
GDCLASS(VoxelGeneratorImage, VoxelGeneratorHeightmap)
|
||||
public:
|
||||
VoxelStreamImage();
|
||||
VoxelGeneratorImage();
|
||||
|
||||
void set_image(Ref<Image> im);
|
||||
Ref<Image> get_image() const;
|
||||
@ -16,7 +16,7 @@ public:
|
||||
void set_blur_enabled(bool enable);
|
||||
bool is_blur_enabled() const;
|
||||
|
||||
void emerge_block(Ref<VoxelBuffer> p_out_buffer, Vector3i origin_in_voxels, int lod);
|
||||
void generate_block(VoxelBlockRequest &input) override;
|
||||
|
||||
private:
|
||||
static void _bind_methods();
|
@ -1,38 +1,38 @@
|
||||
#include "voxel_stream_noise.h"
|
||||
|
||||
void VoxelStreamNoise::set_channel(VoxelBuffer::ChannelId channel) {
|
||||
void VoxelGeneratorNoise::set_channel(VoxelBuffer::ChannelId channel) {
|
||||
ERR_FAIL_INDEX(channel, VoxelBuffer::MAX_CHANNELS);
|
||||
_channel = channel;
|
||||
}
|
||||
|
||||
VoxelBuffer::ChannelId VoxelStreamNoise::get_channel() const {
|
||||
VoxelBuffer::ChannelId VoxelGeneratorNoise::get_channel() const {
|
||||
return _channel;
|
||||
}
|
||||
|
||||
void VoxelStreamNoise::set_noise(Ref<OpenSimplexNoise> noise) {
|
||||
void VoxelGeneratorNoise::set_noise(Ref<OpenSimplexNoise> noise) {
|
||||
_noise = noise;
|
||||
}
|
||||
|
||||
Ref<OpenSimplexNoise> VoxelStreamNoise::get_noise() const {
|
||||
Ref<OpenSimplexNoise> VoxelGeneratorNoise::get_noise() const {
|
||||
return _noise;
|
||||
}
|
||||
|
||||
void VoxelStreamNoise::set_height_start(real_t y) {
|
||||
void VoxelGeneratorNoise::set_height_start(real_t y) {
|
||||
_height_start = y;
|
||||
}
|
||||
|
||||
real_t VoxelStreamNoise::get_height_start() const {
|
||||
real_t VoxelGeneratorNoise::get_height_start() const {
|
||||
return _height_start;
|
||||
}
|
||||
|
||||
void VoxelStreamNoise::set_height_range(real_t hrange) {
|
||||
void VoxelGeneratorNoise::set_height_range(real_t hrange) {
|
||||
if (hrange < 0.1f) {
|
||||
hrange = 0.1f;
|
||||
}
|
||||
_height_range = hrange;
|
||||
}
|
||||
|
||||
real_t VoxelStreamNoise::get_height_range() const {
|
||||
real_t VoxelGeneratorNoise::get_height_range() const {
|
||||
return _height_range;
|
||||
}
|
||||
|
||||
@ -70,13 +70,15 @@ static inline float get_shaped_noise(OpenSimplexNoise &noise, float x, float y,
|
||||
return sum / max;
|
||||
}
|
||||
|
||||
void VoxelStreamNoise::emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin_in_voxels, int lod) {
|
||||
void VoxelGeneratorNoise::generate_block(VoxelBlockRequest &input) {
|
||||
|
||||
ERR_FAIL_COND(out_buffer.is_null());
|
||||
ERR_FAIL_COND(input.voxel_buffer.is_null());
|
||||
ERR_FAIL_COND(_noise.is_null());
|
||||
|
||||
OpenSimplexNoise &noise = **_noise;
|
||||
VoxelBuffer &buffer = **out_buffer;
|
||||
VoxelBuffer &buffer = **input.voxel_buffer;
|
||||
Vector3i origin_in_voxels = input.origin_in_voxels;
|
||||
int lod = input.lod;
|
||||
|
||||
int isosurface_lower_bound = static_cast<int>(Math::floor(_height_start));
|
||||
int isosurface_upper_bound = static_cast<int>(Math::ceil(_height_start + _height_range));
|
||||
@ -157,19 +159,19 @@ void VoxelStreamNoise::emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin
|
||||
}
|
||||
}
|
||||
|
||||
void VoxelStreamNoise::_bind_methods() {
|
||||
void VoxelGeneratorNoise::_bind_methods() {
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_noise", "noise"), &VoxelStreamNoise::set_noise);
|
||||
ClassDB::bind_method(D_METHOD("get_noise"), &VoxelStreamNoise::get_noise);
|
||||
ClassDB::bind_method(D_METHOD("set_noise", "noise"), &VoxelGeneratorNoise::set_noise);
|
||||
ClassDB::bind_method(D_METHOD("get_noise"), &VoxelGeneratorNoise::get_noise);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_height_start", "hstart"), &VoxelStreamNoise::set_height_start);
|
||||
ClassDB::bind_method(D_METHOD("get_height_start"), &VoxelStreamNoise::get_height_start);
|
||||
ClassDB::bind_method(D_METHOD("set_height_start", "hstart"), &VoxelGeneratorNoise::set_height_start);
|
||||
ClassDB::bind_method(D_METHOD("get_height_start"), &VoxelGeneratorNoise::get_height_start);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_height_range", "hrange"), &VoxelStreamNoise::set_height_range);
|
||||
ClassDB::bind_method(D_METHOD("get_height_range"), &VoxelStreamNoise::get_height_range);
|
||||
ClassDB::bind_method(D_METHOD("set_height_range", "hrange"), &VoxelGeneratorNoise::set_height_range);
|
||||
ClassDB::bind_method(D_METHOD("get_height_range"), &VoxelGeneratorNoise::get_height_range);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_channel", "channel"), &VoxelStreamNoise::set_channel);
|
||||
ClassDB::bind_method(D_METHOD("get_channel"), &VoxelStreamNoise::get_channel);
|
||||
ClassDB::bind_method(D_METHOD("set_channel", "channel"), &VoxelGeneratorNoise::set_channel);
|
||||
ClassDB::bind_method(D_METHOD("get_channel"), &VoxelGeneratorNoise::get_channel);
|
||||
|
||||
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "noise", PROPERTY_HINT_RESOURCE_TYPE, "OpenSimplexNoise"), "set_noise", "get_noise");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::REAL, "height_start"), "set_height_start", "get_height_start");
|
@ -2,11 +2,11 @@
|
||||
#define VOXEL_STREAM_NOISE_H
|
||||
|
||||
#include "../util/float_buffer_3d.h"
|
||||
#include "voxel_stream.h"
|
||||
#include "voxel_generator.h"
|
||||
#include <modules/opensimplex/open_simplex_noise.h>
|
||||
|
||||
class VoxelStreamNoise : public VoxelStream {
|
||||
GDCLASS(VoxelStreamNoise, VoxelStream)
|
||||
class VoxelGeneratorNoise : public VoxelGenerator {
|
||||
GDCLASS(VoxelGeneratorNoise, VoxelGenerator)
|
||||
|
||||
public:
|
||||
void set_channel(VoxelBuffer::ChannelId channel);
|
||||
@ -21,7 +21,7 @@ public:
|
||||
void set_height_range(real_t hrange);
|
||||
real_t get_height_range() const;
|
||||
|
||||
void emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin_in_voxels, int lod);
|
||||
void generate_block(VoxelBlockRequest &input) override;
|
||||
|
||||
protected:
|
||||
static void _bind_methods();
|
53
generators/voxel_stream_noise_2d.cpp
Normal file
53
generators/voxel_stream_noise_2d.cpp
Normal file
@ -0,0 +1,53 @@
|
||||
#include "voxel_stream_noise_2d.h"
|
||||
|
||||
VoxelGeneratorNoise2D::VoxelGeneratorNoise2D() {
|
||||
}
|
||||
|
||||
void VoxelGeneratorNoise2D::set_noise(Ref<OpenSimplexNoise> noise) {
|
||||
_noise = noise;
|
||||
}
|
||||
|
||||
Ref<OpenSimplexNoise> VoxelGeneratorNoise2D::get_noise() const {
|
||||
return _noise;
|
||||
}
|
||||
|
||||
void VoxelGeneratorNoise2D::set_curve(Ref<Curve> curve) {
|
||||
_curve = curve;
|
||||
}
|
||||
|
||||
Ref<Curve> VoxelGeneratorNoise2D::get_curve() const {
|
||||
return _curve;
|
||||
}
|
||||
|
||||
void VoxelGeneratorNoise2D::generate_block(VoxelBlockRequest &input) {
|
||||
|
||||
ERR_FAIL_COND(_noise.is_null());
|
||||
|
||||
VoxelBuffer &out_buffer = **input.voxel_buffer;
|
||||
OpenSimplexNoise &noise = **_noise;
|
||||
|
||||
if (_curve.is_null()) {
|
||||
VoxelGeneratorHeightmap::generate(out_buffer,
|
||||
[&noise](int x, int z) { return 0.5 + 0.5 * noise.get_noise_2d(x, z); },
|
||||
input.origin_in_voxels, input.lod);
|
||||
} else {
|
||||
Curve &curve = **_curve;
|
||||
VoxelGeneratorHeightmap::generate(out_buffer,
|
||||
[&noise, &curve](int x, int z) { return curve.interpolate_baked(0.5 + 0.5 * noise.get_noise_2d(x, z)); },
|
||||
input.origin_in_voxels, input.lod);
|
||||
}
|
||||
|
||||
out_buffer.compress_uniform_channels();
|
||||
}
|
||||
|
||||
void VoxelGeneratorNoise2D::_bind_methods() {
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_noise", "noise"), &VoxelGeneratorNoise2D::set_noise);
|
||||
ClassDB::bind_method(D_METHOD("get_noise"), &VoxelGeneratorNoise2D::get_noise);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_curve", "curve"), &VoxelGeneratorNoise2D::set_curve);
|
||||
ClassDB::bind_method(D_METHOD("get_curve"), &VoxelGeneratorNoise2D::get_curve);
|
||||
|
||||
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "noise", PROPERTY_HINT_RESOURCE_TYPE, "OpenSimplexNoise"), "set_noise", "get_noise");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "curve", PROPERTY_HINT_RESOURCE_TYPE, "Curve"), "set_curve", "get_curve");
|
||||
}
|
@ -4,10 +4,10 @@
|
||||
#include "voxel_stream_heightmap.h"
|
||||
#include <modules/opensimplex/open_simplex_noise.h>
|
||||
|
||||
class VoxelStreamNoise2D : public VoxelStreamHeightmap {
|
||||
GDCLASS(VoxelStreamNoise2D, VoxelStreamHeightmap)
|
||||
class VoxelGeneratorNoise2D : public VoxelGeneratorHeightmap {
|
||||
GDCLASS(VoxelGeneratorNoise2D, VoxelGeneratorHeightmap)
|
||||
public:
|
||||
VoxelStreamNoise2D();
|
||||
VoxelGeneratorNoise2D();
|
||||
|
||||
void set_noise(Ref<OpenSimplexNoise> noise);
|
||||
Ref<OpenSimplexNoise> get_noise() const;
|
||||
@ -15,7 +15,7 @@ public:
|
||||
void set_curve(Ref<Curve> curve);
|
||||
Ref<Curve> get_curve() const;
|
||||
|
||||
void emerge_block(Ref<VoxelBuffer> p_out_buffer, Vector3i origin_in_voxels, int lod);
|
||||
void generate_block(VoxelBlockRequest &input) override;
|
||||
|
||||
private:
|
||||
static void _bind_methods();
|
@ -1,38 +1,39 @@
|
||||
#include "voxel_stream_test.h"
|
||||
|
||||
VARIANT_ENUM_CAST(VoxelStreamTest::Mode)
|
||||
VARIANT_ENUM_CAST(VoxelGeneratorTest::Mode)
|
||||
|
||||
VoxelStreamTest::VoxelStreamTest() {
|
||||
VoxelGeneratorTest::VoxelGeneratorTest() {
|
||||
_mode = MODE_WAVES;
|
||||
_voxel_type = 1;
|
||||
_pattern_size = Vector3i(10, 10, 10);
|
||||
}
|
||||
|
||||
void VoxelStreamTest::set_mode(Mode mode) {
|
||||
void VoxelGeneratorTest::set_mode(Mode mode) {
|
||||
ERR_FAIL_INDEX(mode, MODE_COUNT)
|
||||
_mode = mode;
|
||||
}
|
||||
|
||||
void VoxelStreamTest::set_voxel_type(int t) {
|
||||
void VoxelGeneratorTest::set_voxel_type(int t) {
|
||||
_voxel_type = t;
|
||||
}
|
||||
|
||||
int VoxelStreamTest::get_voxel_type() const {
|
||||
int VoxelGeneratorTest::get_voxel_type() const {
|
||||
return _voxel_type;
|
||||
}
|
||||
|
||||
void VoxelStreamTest::set_pattern_size(Vector3i size) {
|
||||
void VoxelGeneratorTest::set_pattern_size(Vector3i size) {
|
||||
ERR_FAIL_COND(size.x < 1 || size.y < 1 || size.z < 1);
|
||||
_pattern_size = size;
|
||||
}
|
||||
|
||||
void VoxelStreamTest::set_pattern_offset(Vector3i offset) {
|
||||
void VoxelGeneratorTest::set_pattern_offset(Vector3i offset) {
|
||||
_pattern_offset = offset;
|
||||
}
|
||||
|
||||
void VoxelStreamTest::emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin, int lod) {
|
||||
ERR_FAIL_COND(out_buffer.is_null());
|
||||
void VoxelGeneratorTest::generate_block(VoxelBlockRequest &input) {
|
||||
ERR_FAIL_COND(input.voxel_buffer.is_null());
|
||||
|
||||
if (lod != 0) {
|
||||
if (input.lod != 0) {
|
||||
// TODO Handle higher lods
|
||||
return;
|
||||
}
|
||||
@ -40,16 +41,16 @@ void VoxelStreamTest::emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin,
|
||||
switch (_mode) {
|
||||
|
||||
case MODE_FLAT:
|
||||
generate_block_flat(**out_buffer, origin, lod);
|
||||
generate_block_flat(**input.voxel_buffer, input.origin_in_voxels, input.lod);
|
||||
break;
|
||||
|
||||
case MODE_WAVES:
|
||||
generate_block_waves(**out_buffer, origin, lod);
|
||||
generate_block_waves(**input.voxel_buffer, input.origin_in_voxels, input.lod);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void VoxelStreamTest::generate_block_flat(VoxelBuffer &out_buffer, Vector3i origin, int lod) {
|
||||
void VoxelGeneratorTest::generate_block_flat(VoxelBuffer &out_buffer, Vector3i origin, int lod) {
|
||||
|
||||
// TODO Don't expect a block pos, but a voxel pos!
|
||||
Vector3i size = out_buffer.get_size();
|
||||
@ -67,7 +68,7 @@ void VoxelStreamTest::generate_block_flat(VoxelBuffer &out_buffer, Vector3i orig
|
||||
}
|
||||
}
|
||||
|
||||
void VoxelStreamTest::generate_block_waves(VoxelBuffer &out_buffer, Vector3i origin, int lod) {
|
||||
void VoxelGeneratorTest::generate_block_waves(VoxelBuffer &out_buffer, Vector3i origin, int lod) {
|
||||
|
||||
// TODO Don't expect a block pos, but a voxel pos!
|
||||
Vector3i size = out_buffer.get_size();
|
||||
@ -108,19 +109,19 @@ void VoxelStreamTest::generate_block_waves(VoxelBuffer &out_buffer, Vector3i ori
|
||||
}
|
||||
}
|
||||
|
||||
void VoxelStreamTest::_bind_methods() {
|
||||
void VoxelGeneratorTest::_bind_methods() {
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_mode", "mode"), &VoxelStreamTest::set_mode);
|
||||
ClassDB::bind_method(D_METHOD("get_mode"), &VoxelStreamTest::get_mode);
|
||||
ClassDB::bind_method(D_METHOD("set_mode", "mode"), &VoxelGeneratorTest::set_mode);
|
||||
ClassDB::bind_method(D_METHOD("get_mode"), &VoxelGeneratorTest::get_mode);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_voxel_type", "id"), &VoxelStreamTest::set_voxel_type);
|
||||
ClassDB::bind_method(D_METHOD("get_voxel_type"), &VoxelStreamTest::get_voxel_type);
|
||||
ClassDB::bind_method(D_METHOD("set_voxel_type", "id"), &VoxelGeneratorTest::set_voxel_type);
|
||||
ClassDB::bind_method(D_METHOD("get_voxel_type"), &VoxelGeneratorTest::get_voxel_type);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_pattern_size", "size"), &VoxelStreamTest::_set_pattern_size);
|
||||
ClassDB::bind_method(D_METHOD("get_pattern_size"), &VoxelStreamTest::_get_pattern_size);
|
||||
ClassDB::bind_method(D_METHOD("set_pattern_size", "size"), &VoxelGeneratorTest::_set_pattern_size);
|
||||
ClassDB::bind_method(D_METHOD("get_pattern_size"), &VoxelGeneratorTest::_get_pattern_size);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_pattern_offset", "offset"), &VoxelStreamTest::_set_pattern_offset);
|
||||
ClassDB::bind_method(D_METHOD("get_pattern_offset"), &VoxelStreamTest::_get_pattern_offset);
|
||||
ClassDB::bind_method(D_METHOD("set_pattern_offset", "offset"), &VoxelGeneratorTest::_set_pattern_offset);
|
||||
ClassDB::bind_method(D_METHOD("get_pattern_offset"), &VoxelGeneratorTest::_get_pattern_offset);
|
||||
|
||||
ADD_PROPERTY(PropertyInfo(Variant::INT, "mode", PROPERTY_HINT_ENUM, "Flat,Waves"), "set_mode", "get_mode");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::INT, "voxel_type", PROPERTY_HINT_RANGE, "0,255,1"), "set_voxel_type", "get_voxel_type");
|
@ -1,20 +1,21 @@
|
||||
#ifndef VOXEL_STREAM_TEST_H
|
||||
#define VOXEL_STREAM_TEST_H
|
||||
|
||||
#include "voxel_stream.h"
|
||||
#include "voxel_generator.h"
|
||||
|
||||
class VoxelStreamTest : public VoxelStream {
|
||||
GDCLASS(VoxelStreamTest, VoxelStream)
|
||||
class VoxelGeneratorTest : public VoxelGenerator {
|
||||
GDCLASS(VoxelGeneratorTest, VoxelGenerator)
|
||||
|
||||
public:
|
||||
enum Mode {
|
||||
MODE_FLAT,
|
||||
MODE_WAVES
|
||||
MODE_WAVES,
|
||||
MODE_COUNT
|
||||
};
|
||||
|
||||
VoxelStreamTest();
|
||||
VoxelGeneratorTest();
|
||||
|
||||
virtual void emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin, int lod);
|
||||
void generate_block(VoxelBlockRequest &input) override;
|
||||
|
||||
void set_mode(Mode mode);
|
||||
Mode get_mode() const { return _mode; }
|
@ -1,16 +1,16 @@
|
||||
#include "register_types.h"
|
||||
#include "edition/voxel_tool.h"
|
||||
#include "generators/voxel_stream_heightmap.h"
|
||||
#include "generators/voxel_stream_image.h"
|
||||
#include "generators/voxel_stream_noise.h"
|
||||
#include "generators/voxel_stream_noise_2d.h"
|
||||
#include "generators/voxel_stream_test.h"
|
||||
#include "meshers/blocky/voxel_mesher_blocky.h"
|
||||
#include "meshers/dmc/voxel_mesher_dmc.h"
|
||||
#include "meshers/transvoxel/voxel_mesher_transvoxel.h"
|
||||
#include "streams/voxel_stream_block_files.h"
|
||||
#include "streams/voxel_stream_file.h"
|
||||
#include "streams/voxel_stream_heightmap.h"
|
||||
#include "streams/voxel_stream_image.h"
|
||||
#include "streams/voxel_stream_noise.h"
|
||||
#include "streams/voxel_stream_noise_2d.h"
|
||||
#include "streams/voxel_stream_region_files.h"
|
||||
#include "streams/voxel_stream_test.h"
|
||||
#include "terrain/voxel_box_mover.h"
|
||||
#include "terrain/voxel_lod_terrain.h"
|
||||
#include "terrain/voxel_map.h"
|
||||
@ -36,15 +36,18 @@ void register_voxel_types() {
|
||||
|
||||
// Streams
|
||||
ClassDB::register_class<VoxelStream>();
|
||||
ClassDB::register_class<VoxelStreamTest>();
|
||||
ClassDB::register_class<VoxelStreamHeightmap>();
|
||||
ClassDB::register_class<VoxelStreamImage>();
|
||||
ClassDB::register_class<VoxelStreamNoise>();
|
||||
ClassDB::register_class<VoxelStreamNoise2D>();
|
||||
ClassDB::register_class<VoxelStreamFile>();
|
||||
ClassDB::register_class<VoxelStreamBlockFiles>();
|
||||
ClassDB::register_class<VoxelStreamRegionFiles>();
|
||||
|
||||
// Generators
|
||||
ClassDB::register_class<VoxelGenerator>();
|
||||
ClassDB::register_class<VoxelGeneratorTest>();
|
||||
ClassDB::register_class<VoxelGeneratorHeightmap>();
|
||||
ClassDB::register_class<VoxelGeneratorImage>();
|
||||
ClassDB::register_class<VoxelGeneratorNoise2D>();
|
||||
ClassDB::register_class<VoxelGeneratorNoise>();
|
||||
|
||||
// Helpers
|
||||
ClassDB::register_class<VoxelBoxMover>();
|
||||
ClassDB::register_class<VoxelRaycastResult>();
|
||||
|
15
streams/voxel_block_request.h
Normal file
15
streams/voxel_block_request.h
Normal file
@ -0,0 +1,15 @@
|
||||
#ifndef VOXEL_BLOCK_REQUEST_H
|
||||
#define VOXEL_BLOCK_REQUEST_H
|
||||
|
||||
#include "../math/vector3i.h"
|
||||
#include "../voxel_buffer.h"
|
||||
|
||||
class VoxelBuffer;
|
||||
|
||||
struct VoxelBlockRequest {
|
||||
Ref<VoxelBuffer> voxel_buffer;
|
||||
Vector3i origin_in_voxels;
|
||||
int lod;
|
||||
};
|
||||
|
||||
#endif // VOXEL_BLOCK_REQUEST_H
|
@ -43,17 +43,17 @@ void VoxelStream::immerge_block(Ref<VoxelBuffer> buffer, Vector3i origin_in_voxe
|
||||
}
|
||||
}
|
||||
|
||||
void VoxelStream::emerge_blocks(Vector<VoxelStream::BlockRequest> &p_blocks) {
|
||||
void VoxelStream::emerge_blocks(Vector<VoxelBlockRequest> &p_blocks) {
|
||||
// Default implementation. May matter for some stream types to optimize loading.
|
||||
for (int i = 0; i < p_blocks.size(); ++i) {
|
||||
BlockRequest &r = p_blocks.write[i];
|
||||
VoxelBlockRequest &r = p_blocks.write[i];
|
||||
emerge_block(r.voxel_buffer, r.origin_in_voxels, r.lod);
|
||||
}
|
||||
}
|
||||
|
||||
void VoxelStream::immerge_blocks(Vector<VoxelStream::BlockRequest> &p_blocks) {
|
||||
void VoxelStream::immerge_blocks(Vector<VoxelBlockRequest> &p_blocks) {
|
||||
for (int i = 0; i < p_blocks.size(); ++i) {
|
||||
BlockRequest &r = p_blocks.write[i];
|
||||
VoxelBlockRequest &r = p_blocks.write[i];
|
||||
immerge_block(r.voxel_buffer, r.origin_in_voxels, r.lod);
|
||||
}
|
||||
}
|
||||
|
@ -2,20 +2,15 @@
|
||||
#define VOXEL_STREAM_H
|
||||
|
||||
#include "../util/zprofiling.h"
|
||||
#include "../voxel_buffer.h"
|
||||
#include "voxel_block_request.h"
|
||||
#include <core/resource.h>
|
||||
|
||||
// Provides access to a source of paged voxel data.
|
||||
// Provides access to a source of paged voxel data, which may load and save.
|
||||
// Must be implemented in a multi-thread-safe way.
|
||||
// If you are looking for a more specialized API to generate voxels, use VoxelGenerator.
|
||||
class VoxelStream : public Resource {
|
||||
GDCLASS(VoxelStream, Resource)
|
||||
public:
|
||||
struct BlockRequest {
|
||||
Ref<VoxelBuffer> voxel_buffer;
|
||||
Vector3i origin_in_voxels;
|
||||
int lod;
|
||||
};
|
||||
|
||||
struct Stats {
|
||||
int file_openings = 0;
|
||||
int time_spent_opening_files = 0;
|
||||
@ -31,12 +26,12 @@ public:
|
||||
virtual void immerge_block(Ref<VoxelBuffer> buffer, Vector3i origin_in_voxels, int lod);
|
||||
|
||||
// Note: vector is passed by ref for performance. Don't reorder it.
|
||||
virtual void emerge_blocks(Vector<BlockRequest> &p_blocks);
|
||||
virtual void emerge_blocks(Vector<VoxelBlockRequest> &p_blocks);
|
||||
|
||||
// Returns multiple blocks of voxels to the stream.
|
||||
// Generators usually don't implement it.
|
||||
// This function is recommended if you save to files, because you can batch their access.
|
||||
virtual void immerge_blocks(Vector<BlockRequest> &p_blocks);
|
||||
virtual void immerge_blocks(Vector<VoxelBlockRequest> &p_blocks);
|
||||
|
||||
virtual bool is_thread_safe() const;
|
||||
virtual bool is_cloneable() const;
|
||||
|
@ -23,18 +23,18 @@ void VoxelStreamFile::emerge_block_fallback(Ref<VoxelBuffer> out_buffer, Vector3
|
||||
|
||||
// This function is just a helper around the true thing, really. I might remove it in the future.
|
||||
|
||||
BlockRequest r;
|
||||
VoxelBlockRequest r;
|
||||
r.voxel_buffer = out_buffer;
|
||||
r.origin_in_voxels = origin_in_voxels;
|
||||
r.lod = lod;
|
||||
|
||||
Vector<BlockRequest> requests;
|
||||
Vector<VoxelBlockRequest> requests;
|
||||
requests.push_back(r);
|
||||
|
||||
emerge_blocks_fallback(requests);
|
||||
}
|
||||
|
||||
void VoxelStreamFile::emerge_blocks_fallback(Vector<VoxelStreamFile::BlockRequest> &requests) {
|
||||
void VoxelStreamFile::emerge_blocks_fallback(Vector<VoxelBlockRequest> &requests) {
|
||||
VOXEL_PROFILE_SCOPE(profile_scope);
|
||||
|
||||
if (_fallback_stream.is_valid()) {
|
||||
|
@ -28,7 +28,7 @@ protected:
|
||||
static void _bind_methods();
|
||||
|
||||
void emerge_block_fallback(Ref<VoxelBuffer> out_buffer, Vector3i origin_in_voxels, int lod);
|
||||
void emerge_blocks_fallback(Vector<BlockRequest> &requests);
|
||||
void emerge_blocks_fallback(Vector<VoxelBlockRequest> &requests);
|
||||
|
||||
FileAccess *open_file(const String &fpath, int mode_flags, Error *err);
|
||||
|
||||
|
@ -1,59 +0,0 @@
|
||||
#include "voxel_stream_heightmap.h"
|
||||
#include "../util/array_slice.h"
|
||||
#include "../util/fixed_array.h"
|
||||
|
||||
VoxelStreamHeightmap::VoxelStreamHeightmap() {
|
||||
}
|
||||
|
||||
void VoxelStreamHeightmap::set_channel(VoxelBuffer::ChannelId channel) {
|
||||
ERR_FAIL_INDEX(channel, VoxelBuffer::MAX_CHANNELS);
|
||||
_channel = channel;
|
||||
}
|
||||
|
||||
VoxelBuffer::ChannelId VoxelStreamHeightmap::get_channel() const {
|
||||
return _channel;
|
||||
}
|
||||
|
||||
void VoxelStreamHeightmap::set_height_start(float start) {
|
||||
_range.start = start;
|
||||
}
|
||||
|
||||
float VoxelStreamHeightmap::get_height_start() const {
|
||||
return _range.start;
|
||||
}
|
||||
|
||||
void VoxelStreamHeightmap::set_height_range(float range) {
|
||||
_range.height = range;
|
||||
}
|
||||
|
||||
float VoxelStreamHeightmap::get_height_range() const {
|
||||
return _range.height;
|
||||
}
|
||||
|
||||
void VoxelStreamHeightmap::set_iso_scale(float iso_scale) {
|
||||
_iso_scale = iso_scale;
|
||||
}
|
||||
|
||||
float VoxelStreamHeightmap::get_iso_scale() const {
|
||||
return _iso_scale;
|
||||
}
|
||||
|
||||
void VoxelStreamHeightmap::_bind_methods() {
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_channel", "channel"), &VoxelStreamHeightmap::set_channel);
|
||||
ClassDB::bind_method(D_METHOD("get_channel"), &VoxelStreamHeightmap::get_channel);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_height_start", "start"), &VoxelStreamHeightmap::set_height_start);
|
||||
ClassDB::bind_method(D_METHOD("get_height_start"), &VoxelStreamHeightmap::get_height_start);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_height_range", "range"), &VoxelStreamHeightmap::set_height_range);
|
||||
ClassDB::bind_method(D_METHOD("get_height_range"), &VoxelStreamHeightmap::get_height_range);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_iso_scale", "scale"), &VoxelStreamHeightmap::set_iso_scale);
|
||||
ClassDB::bind_method(D_METHOD("get_iso_scale"), &VoxelStreamHeightmap::get_iso_scale);
|
||||
|
||||
ADD_PROPERTY(PropertyInfo(Variant::INT, "channel", PROPERTY_HINT_ENUM, VoxelBuffer::CHANNEL_ID_HINT_STRING), "set_channel", "get_channel");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::REAL, "height_start"), "set_height_start", "get_height_start");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::REAL, "height_range"), "set_height_range", "get_height_range");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::REAL, "iso_scale"), "set_iso_scale", "get_iso_scale");
|
||||
}
|
@ -1,53 +0,0 @@
|
||||
#include "voxel_stream_noise_2d.h"
|
||||
|
||||
VoxelStreamNoise2D::VoxelStreamNoise2D() {
|
||||
}
|
||||
|
||||
void VoxelStreamNoise2D::set_noise(Ref<OpenSimplexNoise> noise) {
|
||||
_noise = noise;
|
||||
}
|
||||
|
||||
Ref<OpenSimplexNoise> VoxelStreamNoise2D::get_noise() const {
|
||||
return _noise;
|
||||
}
|
||||
|
||||
void VoxelStreamNoise2D::set_curve(Ref<Curve> curve) {
|
||||
_curve = curve;
|
||||
}
|
||||
|
||||
Ref<Curve> VoxelStreamNoise2D::get_curve() const {
|
||||
return _curve;
|
||||
}
|
||||
|
||||
void VoxelStreamNoise2D::emerge_block(Ref<VoxelBuffer> p_out_buffer, Vector3i origin_in_voxels, int lod) {
|
||||
|
||||
ERR_FAIL_COND(_noise.is_null());
|
||||
|
||||
VoxelBuffer &out_buffer = **p_out_buffer;
|
||||
OpenSimplexNoise &noise = **_noise;
|
||||
|
||||
if (_curve.is_null()) {
|
||||
VoxelStreamHeightmap::generate(out_buffer,
|
||||
[&noise](int x, int z) { return 0.5 + 0.5 * noise.get_noise_2d(x, z); },
|
||||
origin_in_voxels, lod);
|
||||
} else {
|
||||
Curve &curve = **_curve;
|
||||
VoxelStreamHeightmap::generate(out_buffer,
|
||||
[&noise, &curve](int x, int z) { return curve.interpolate_baked(0.5 + 0.5 * noise.get_noise_2d(x, z)); },
|
||||
origin_in_voxels, lod);
|
||||
}
|
||||
|
||||
out_buffer.compress_uniform_channels();
|
||||
}
|
||||
|
||||
void VoxelStreamNoise2D::_bind_methods() {
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_noise", "noise"), &VoxelStreamNoise2D::set_noise);
|
||||
ClassDB::bind_method(D_METHOD("get_noise"), &VoxelStreamNoise2D::get_noise);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_curve", "curve"), &VoxelStreamNoise2D::set_curve);
|
||||
ClassDB::bind_method(D_METHOD("get_curve"), &VoxelStreamNoise2D::get_curve);
|
||||
|
||||
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "noise", PROPERTY_HINT_RESOURCE_TYPE, "OpenSimplexNoise"), "set_noise", "get_noise");
|
||||
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "curve", PROPERTY_HINT_RESOURCE_TYPE, "Curve"), "set_curve", "get_curve");
|
||||
}
|
@ -27,42 +27,42 @@ VoxelStreamRegionFiles::~VoxelStreamRegionFiles() {
|
||||
}
|
||||
|
||||
void VoxelStreamRegionFiles::emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin_in_voxels, int lod) {
|
||||
BlockRequest r;
|
||||
VoxelBlockRequest r;
|
||||
r.voxel_buffer = out_buffer;
|
||||
r.origin_in_voxels = origin_in_voxels;
|
||||
r.lod = lod;
|
||||
Vector<BlockRequest> requests;
|
||||
Vector<VoxelBlockRequest> requests;
|
||||
requests.push_back(r);
|
||||
emerge_blocks(requests);
|
||||
}
|
||||
|
||||
void VoxelStreamRegionFiles::immerge_block(Ref<VoxelBuffer> buffer, Vector3i origin_in_voxels, int lod) {
|
||||
BlockRequest r;
|
||||
VoxelBlockRequest r;
|
||||
r.voxel_buffer = buffer;
|
||||
r.origin_in_voxels = origin_in_voxels;
|
||||
r.lod = lod;
|
||||
Vector<BlockRequest> requests;
|
||||
Vector<VoxelBlockRequest> requests;
|
||||
requests.push_back(r);
|
||||
immerge_blocks(requests);
|
||||
}
|
||||
|
||||
void VoxelStreamRegionFiles::emerge_blocks(Vector<BlockRequest> &p_blocks) {
|
||||
void VoxelStreamRegionFiles::emerge_blocks(Vector<VoxelBlockRequest> &p_blocks) {
|
||||
VOXEL_PROFILE_SCOPE(profile_scope);
|
||||
|
||||
// In order to minimize opening/closing files, requests are grouped according to their region.
|
||||
|
||||
// Had to copy input to sort it, as some areas in the module break if they get responses in different order
|
||||
Vector<BlockRequest> sorted_blocks;
|
||||
Vector<VoxelBlockRequest> sorted_blocks;
|
||||
sorted_blocks.append_array(p_blocks);
|
||||
|
||||
SortArray<BlockRequest, BlockRequestComparator> sorter;
|
||||
SortArray<VoxelBlockRequest, BlockRequestComparator> sorter;
|
||||
sorter.compare.self = this;
|
||||
sorter.sort(sorted_blocks.ptrw(), sorted_blocks.size());
|
||||
|
||||
Vector<BlockRequest> fallback_requests;
|
||||
Vector<VoxelBlockRequest> fallback_requests;
|
||||
|
||||
for (int i = 0; i < sorted_blocks.size(); ++i) {
|
||||
BlockRequest &r = sorted_blocks.write[i];
|
||||
VoxelBlockRequest &r = sorted_blocks.write[i];
|
||||
EmergeResult result = _emerge_block(r.voxel_buffer, r.origin_in_voxels, r.lod);
|
||||
if (result == EMERGE_OK_FALLBACK) {
|
||||
fallback_requests.push_back(r);
|
||||
@ -72,19 +72,19 @@ void VoxelStreamRegionFiles::emerge_blocks(Vector<BlockRequest> &p_blocks) {
|
||||
emerge_blocks_fallback(fallback_requests);
|
||||
}
|
||||
|
||||
void VoxelStreamRegionFiles::immerge_blocks(Vector<BlockRequest> &p_blocks) {
|
||||
void VoxelStreamRegionFiles::immerge_blocks(Vector<VoxelBlockRequest> &p_blocks) {
|
||||
VOXEL_PROFILE_SCOPE(profile_scope);
|
||||
|
||||
// Had to copy input to sort it, as some areas in the module break if they get responses in different order
|
||||
Vector<BlockRequest> sorted_blocks;
|
||||
Vector<VoxelBlockRequest> sorted_blocks;
|
||||
sorted_blocks.append_array(p_blocks);
|
||||
|
||||
SortArray<BlockRequest, BlockRequestComparator> sorter;
|
||||
SortArray<VoxelBlockRequest, BlockRequestComparator> sorter;
|
||||
sorter.compare.self = this;
|
||||
sorter.sort(sorted_blocks.ptrw(), sorted_blocks.size());
|
||||
|
||||
for (int i = 0; i < sorted_blocks.size(); ++i) {
|
||||
BlockRequest &r = sorted_blocks.write[i];
|
||||
VoxelBlockRequest &r = sorted_blocks.write[i];
|
||||
_immerge_block(r.voxel_buffer, r.origin_in_voxels, r.lod);
|
||||
}
|
||||
}
|
||||
|
@ -21,8 +21,8 @@ public:
|
||||
void emerge_block(Ref<VoxelBuffer> out_buffer, Vector3i origin_in_voxels, int lod) override;
|
||||
void immerge_block(Ref<VoxelBuffer> buffer, Vector3i origin_in_voxels, int lod) override;
|
||||
|
||||
void emerge_blocks(Vector<BlockRequest> &p_blocks) override;
|
||||
void immerge_blocks(Vector<BlockRequest> &p_blocks) override;
|
||||
void emerge_blocks(Vector<VoxelBlockRequest> &p_blocks) override;
|
||||
void immerge_blocks(Vector<VoxelBlockRequest> &p_blocks) override;
|
||||
|
||||
String get_directory() const;
|
||||
void set_directory(String dirpath);
|
||||
@ -94,7 +94,7 @@ private:
|
||||
VoxelStreamRegionFiles *self = nullptr;
|
||||
|
||||
// operator<
|
||||
_FORCE_INLINE_ bool operator()(const VoxelStreamRegionFiles::BlockRequest &a, const VoxelStreamRegionFiles::BlockRequest &b) const {
|
||||
_FORCE_INLINE_ bool operator()(const VoxelBlockRequest &a, const VoxelBlockRequest &b) const {
|
||||
if (a.lod < b.lod) {
|
||||
return true;
|
||||
} else if (a.lod > b.lod) {
|
||||
|
@ -58,8 +58,8 @@ void VoxelDataLoader::process_blocks_thread_func(const ArraySlice<InputBlock> in
|
||||
|
||||
CRASH_COND(inputs.size() != outputs.size());
|
||||
|
||||
Vector<VoxelStream::BlockRequest> emerge_requests;
|
||||
Vector<VoxelStream::BlockRequest> immerge_requests;
|
||||
Vector<VoxelBlockRequest> emerge_requests;
|
||||
Vector<VoxelBlockRequest> immerge_requests;
|
||||
|
||||
for (size_t i = 0; i < inputs.size(); ++i) {
|
||||
|
||||
@ -70,7 +70,7 @@ void VoxelDataLoader::process_blocks_thread_func(const ArraySlice<InputBlock> in
|
||||
|
||||
if (ib.data.voxels_to_save.is_null()) {
|
||||
|
||||
VoxelStream::BlockRequest r;
|
||||
VoxelBlockRequest r;
|
||||
r.voxel_buffer.instance();
|
||||
r.voxel_buffer->create(bs, bs, bs);
|
||||
r.origin_in_voxels = block_origin_in_voxels;
|
||||
@ -79,7 +79,7 @@ void VoxelDataLoader::process_blocks_thread_func(const ArraySlice<InputBlock> in
|
||||
|
||||
} else {
|
||||
|
||||
VoxelStream::BlockRequest r;
|
||||
VoxelBlockRequest r;
|
||||
r.voxel_buffer = ib.data.voxels_to_save;
|
||||
r.origin_in_voxels = block_origin_in_voxels;
|
||||
r.lod = ib.lod;
|
||||
|
@ -17,6 +17,7 @@ VoxelStringNames::VoxelStringNames() {
|
||||
|
||||
emerge_block = StaticCString::create("emerge_block");
|
||||
immerge_block = StaticCString::create("immerge_block");
|
||||
generate_block = StaticCString::create("generate_block");
|
||||
|
||||
u_transition_mask = StaticCString::create("u_transition_mask");
|
||||
}
|
||||
|
@ -19,6 +19,7 @@ public:
|
||||
|
||||
StringName emerge_block;
|
||||
StringName immerge_block;
|
||||
StringName generate_block;
|
||||
|
||||
StringName u_transition_mask;
|
||||
};
|
||||
|
Loading…
x
Reference in New Issue
Block a user