Add flowers, Pad Texture Atlas, Move block break code to Player class
parent
e50ad18663
commit
16ff339a2b
|
@ -2,6 +2,8 @@ cmake_minimum_required(VERSION 3.12 FATAL_ERROR)
|
|||
set (CMAKE_CXX_STANDARD 14)
|
||||
set (PROJECT_NAME "Zeus")
|
||||
|
||||
#set (CMAKE_CXX_FLAGS "--coverage")
|
||||
|
||||
project (${PROJECT_NAME})
|
||||
|
||||
#Include all of the library headers
|
||||
|
|
|
@ -5,7 +5,7 @@ function dump(tbl, indent)
|
|||
if type(k) == "number" then
|
||||
k = "[" .. k .. "]"
|
||||
end
|
||||
local indentString = string.rep(" ", indent);
|
||||
local indentString = string.rep(" ", indent)
|
||||
local formatting = indentString .. k .. " = "
|
||||
if type(v) == "table" then
|
||||
print(formatting .. "{")
|
||||
|
@ -340,7 +340,7 @@ textures: The list of textures for the blockmodel. Which textures go where are d
|
|||
--]]
|
||||
|
||||
-- Ignore this, it is temporary
|
||||
-- Air
|
||||
-- Air [ID 0]
|
||||
zeus.register_block("_:air", {
|
||||
visible = false,
|
||||
culls = false,
|
||||
|
@ -350,7 +350,7 @@ zeus.register_block("_:air", {
|
|||
textures = {"_missing"}
|
||||
})
|
||||
|
||||
-- Grass
|
||||
-- Grass [ID 1]
|
||||
zeus.register_block("default:grass", {
|
||||
name = "Grass",
|
||||
model = "default:block_side_foliage",
|
||||
|
@ -365,21 +365,21 @@ zeus.register_block("default:grass", {
|
|||
}
|
||||
})
|
||||
|
||||
-- Dirt
|
||||
-- Dirt [ID 2]
|
||||
zeus.register_block('default:dirt', {
|
||||
name = "Dirt",
|
||||
model = "default:block",
|
||||
textures = {"default_dirt"}
|
||||
})
|
||||
|
||||
-- Stone
|
||||
-- Stone [ID 3]
|
||||
zeus.register_block('default:stone', {
|
||||
name = "Stone",
|
||||
model = "default:block",
|
||||
textures = {"default_stone"}
|
||||
})
|
||||
|
||||
-- Leaves
|
||||
-- Leaves [ID 4]
|
||||
zeus.register_block('default:leaves', {
|
||||
visible = true,
|
||||
culls = false,
|
||||
|
@ -391,7 +391,7 @@ zeus.register_block('default:leaves', {
|
|||
}
|
||||
})
|
||||
|
||||
-- Wood
|
||||
-- Wood [ID 5]
|
||||
zeus.register_block('default:wood', {
|
||||
name = "Log",
|
||||
model = "default:block",
|
||||
|
@ -402,7 +402,7 @@ zeus.register_block('default:wood', {
|
|||
}
|
||||
})
|
||||
|
||||
-- TallGrass
|
||||
-- TallGrass [ID 6..10]
|
||||
for i=1,5,1 do
|
||||
zeus.register_block("default:tallgrass_" .. i, {
|
||||
culls = false,
|
||||
|
@ -413,4 +413,35 @@ for i=1,5,1 do
|
|||
"default_tallgrass_" .. i,
|
||||
}
|
||||
})
|
||||
end
|
||||
|
||||
-- Flowers [ID 11..18]
|
||||
local flowers = {
|
||||
"rose",
|
||||
"tulip",
|
||||
"viola",
|
||||
"geranium",
|
||||
"mushroom_red",
|
||||
"mushroom_brown",
|
||||
"dandelion_white",
|
||||
"dandelion_yellow"
|
||||
}
|
||||
|
||||
for ind,flower in ipairs(flowers) do
|
||||
|
||||
local function tchelper(first, rest)
|
||||
return first:upper()..rest:lower()
|
||||
end
|
||||
|
||||
local name = flower:gsub("_", " "):gsub("(%a)([%w_']*)", tchelper)
|
||||
|
||||
zeus.register_block("default:flower_" .. flower, {
|
||||
culls = false,
|
||||
solid = false,
|
||||
name = name,
|
||||
model = "default:plantlike",
|
||||
textures = {
|
||||
"flowers_" .. flower
|
||||
}
|
||||
})
|
||||
end
|
|
@ -41,7 +41,7 @@ int Window::initialize() {
|
|||
|
||||
//TODO: Fix msaa for texture altases.
|
||||
//MSAA
|
||||
// glfwWindowHint(GLFW_SAMPLES, 16);
|
||||
// glfwWindowHint(GLFW_SAMPLES, 4);
|
||||
// glEnable(GL_MULTISAMPLE);
|
||||
|
||||
//Create the window
|
||||
|
|
|
@ -32,7 +32,7 @@ void Texture::load() {
|
|||
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, texData);
|
||||
|
||||
glGenerateMipmap(GL_TEXTURE_2D);
|
||||
// glGenerateMipmap(GL_TEXTURE_2D);
|
||||
|
||||
glBindTexture(GL_TEXTURE_2D, 0);
|
||||
|
||||
|
@ -50,7 +50,7 @@ void Texture::load(unsigned char* bytes, int width, int height) {
|
|||
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, bytes);
|
||||
|
||||
glGenerateMipmap(GL_TEXTURE_2D);
|
||||
// glGenerateMipmap(GL_TEXTURE_2D);
|
||||
|
||||
glBindTexture(GL_TEXTURE_2D, 0);
|
||||
}
|
||||
|
|
|
@ -43,7 +43,7 @@ void GameScene::update() {
|
|||
|
||||
auto window = state->renderer->getWindow();
|
||||
|
||||
player->update(window->getKeysArray(), state->deltaTime, window->getDeltaX(), window->getDeltaY());
|
||||
player->update(window->getKeysArray(), state->deltaTime, window->getDeltaX(), window->getDeltaY(), window->mouseIsDown(), window->mouseIsDown());
|
||||
|
||||
if (state->renderer->resized) {
|
||||
debugGui.bufferResized(state->renderer->getCamera()->getBufferDimensions());
|
||||
|
|
|
@ -3,10 +3,13 @@
|
|||
//
|
||||
|
||||
#include "Player.h"
|
||||
#include "../engine/Ray.h"
|
||||
|
||||
Player::Player() {
|
||||
pos = glm::vec3(0, 0, 0);
|
||||
vel = glm::vec3(0, 0, 0);
|
||||
FDown = false;
|
||||
flying = false;
|
||||
}
|
||||
|
||||
void Player::create(LocalWorld* world, Camera* camera) {
|
||||
|
@ -14,11 +17,29 @@ void Player::create(LocalWorld* world, Camera* camera) {
|
|||
this->world = world;
|
||||
}
|
||||
|
||||
void Player::update(bool *keys, double delta, double mouseX, double mouseY) {
|
||||
void Player::update(bool *keys, double delta, double mouseX, double mouseY, bool leftDown, bool rightDown) {
|
||||
posUpdate(keys, delta);
|
||||
viewUpdate(mouseX, mouseY);
|
||||
moveCollide();
|
||||
|
||||
for (Ray ray(this); ray.getLength() < 5; ray.step(0.01)) {
|
||||
auto found = world->getBlock(*ray.getEnd());
|
||||
if (found > 0) {
|
||||
if (leftDown) {
|
||||
world->setBlock(*ray.getEnd(), 0);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (keys[GLFW_KEY_F]) {
|
||||
if (!FDown) {
|
||||
FDown = true;
|
||||
flying = !flying;
|
||||
}
|
||||
}
|
||||
else FDown = false;
|
||||
|
||||
camera->setPosition(pos);
|
||||
}
|
||||
|
||||
|
@ -28,10 +49,15 @@ void Player::posUpdate(bool *keys, double delta) {
|
|||
float friction = 0.3f;
|
||||
|
||||
double moveMult = moveSpeed * delta;
|
||||
if (keys[GLFW_KEY_LEFT_SHIFT]) {
|
||||
if (keys[GLFW_KEY_LEFT_CONTROL]) {
|
||||
moveMult *= 2;
|
||||
}
|
||||
|
||||
if (flying) {
|
||||
moveMult *= 8;
|
||||
friction = 0.15f;
|
||||
}
|
||||
|
||||
glm::vec3 frontFlat = glm::normalize(glm::vec3(camera->getFront()->x, 0, camera->getFront()->z));
|
||||
glm::vec3 rightFlat = glm::normalize(glm::vec3(camera->getRight()->x, 0, camera->getRight()->z));
|
||||
|
||||
|
@ -42,17 +68,27 @@ void Player::posUpdate(bool *keys, double delta) {
|
|||
if (keys[GLFW_KEY_D]) mod += rightFlat;
|
||||
if (keys[GLFW_KEY_A]) mod -= rightFlat;
|
||||
|
||||
if (flying) {
|
||||
if (keys[GLFW_KEY_SPACE]) mod.y += 1;
|
||||
if (keys[GLFW_KEY_LEFT_SHIFT]) mod.y -= 1;
|
||||
}
|
||||
|
||||
if (glm::length(mod) != 0) mod = glm::normalize(mod);
|
||||
mod = mod * (float)moveMult;
|
||||
|
||||
glm::vec3 velFlat = glm::vec3(vel.x, 0, vel.z);
|
||||
velFlat = velFlat * (1.0f-friction) + mod * friction;
|
||||
if (!flying) {
|
||||
glm::vec3 velFlat = glm::vec3(vel.x, 0, vel.z);
|
||||
velFlat = velFlat * (1.0f-friction) + mod * friction;
|
||||
|
||||
vel.x = velFlat.x;
|
||||
vel.z = velFlat.z;
|
||||
vel.x = velFlat.x;
|
||||
vel.z = velFlat.z;
|
||||
|
||||
if (keys[GLFW_KEY_SPACE] && collides(glm::vec3(pos.x, pos.y - 0.05, pos.z)) && vel.y >= 0) {
|
||||
vel.y = jumpVel;
|
||||
if (keys[GLFW_KEY_SPACE] && collides(glm::vec3(pos.x, pos.y - 0.05, pos.z)) && vel.y >= 0) {
|
||||
vel.y = jumpVel;
|
||||
}
|
||||
}
|
||||
else {
|
||||
vel = vel * (1.0f-friction) + mod * friction;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -66,54 +102,54 @@ bool Player::collides(glm::vec3 pos) {
|
|||
}
|
||||
|
||||
void Player::moveCollide() {
|
||||
double increment = 0.05;
|
||||
if (!flying) {
|
||||
double increment = 0.05;
|
||||
|
||||
Timer t("Move calculations");
|
||||
if (!collides(glm::vec3(pos.x, pos.y - increment, pos.z))) {
|
||||
vel.y = (float) fmax(vel.y - 0.01, -3);
|
||||
} else if (vel.y < 0) {
|
||||
vel.y = 0;
|
||||
}
|
||||
|
||||
if (!collides(glm::vec3(pos.x, pos.y - increment, pos.z))) {
|
||||
vel.y = (float)fmax(vel.y - 0.01, -3);
|
||||
double moved = 0;
|
||||
for (int i = 0; i < fabs(vel.y) / increment; i++) {
|
||||
double move = fmax(fmin(increment, fabs(vel.y) - moved), 0);
|
||||
moved += increment;
|
||||
|
||||
glm::vec3 newPos = glm::vec3(pos);
|
||||
newPos.y += move * (vel.y < 0 ? -1 : 1);
|
||||
|
||||
if (!collides(newPos))
|
||||
pos = newPos;
|
||||
}
|
||||
|
||||
moved = 0;
|
||||
for (int i = 0; i < fabs(vel.x) / increment; i++) {
|
||||
double move = fmax(fmin(increment, fabs(vel.x) - moved), 0);
|
||||
moved += increment;
|
||||
|
||||
glm::vec3 newPos = glm::vec3(pos);
|
||||
newPos.x += move * (vel.x < 0 ? -1 : 1);
|
||||
|
||||
if (!collides(newPos))
|
||||
pos = newPos;
|
||||
}
|
||||
|
||||
moved = 0;
|
||||
for (int i = 0; i < fabs(vel.z) / increment; i++) {
|
||||
double move = fmax(fmin(increment, fabs(vel.z) - moved), 0);
|
||||
moved += increment;
|
||||
|
||||
glm::vec3 newPos = glm::vec3(pos);
|
||||
newPos.z += move * (vel.z < 0 ? -1 : 1);
|
||||
|
||||
if (!collides(newPos))
|
||||
pos = newPos;
|
||||
}
|
||||
}
|
||||
else if (vel.y < 0) {
|
||||
vel.y = 0;
|
||||
else {
|
||||
pos += vel;
|
||||
}
|
||||
|
||||
double moved = 0;
|
||||
for (int i = 0; i < fabs(vel.y) / increment; i++) {
|
||||
double move = fmax(fmin(increment, fabs(vel.y) - moved), 0);
|
||||
moved += increment;
|
||||
|
||||
glm::vec3 newPos = glm::vec3(pos);
|
||||
newPos.y += move * (vel.y < 0 ? -1 : 1);
|
||||
|
||||
if (!collides(newPos))
|
||||
pos = newPos;
|
||||
}
|
||||
|
||||
moved = 0;
|
||||
for (int i = 0; i < fabs(vel.x) / increment; i++) {
|
||||
double move = fmax(fmin(increment, fabs(vel.x) - moved), 0);
|
||||
moved += increment;
|
||||
|
||||
glm::vec3 newPos = glm::vec3(pos);
|
||||
newPos.x += move * (vel.x < 0 ? -1 : 1);
|
||||
|
||||
if (!collides(newPos))
|
||||
pos = newPos;
|
||||
}
|
||||
|
||||
moved = 0;
|
||||
for (int i = 0; i < fabs(vel.z) / increment; i++) {
|
||||
double move = fmax(fmin(increment, fabs(vel.z) - moved), 0);
|
||||
moved += increment;
|
||||
|
||||
glm::vec3 newPos = glm::vec3(pos);
|
||||
newPos.z += move * (vel.z < 0 ? -1 : 1);
|
||||
|
||||
if (!collides(newPos))
|
||||
pos = newPos;
|
||||
}
|
||||
|
||||
// t.printElapsedMs();
|
||||
}
|
||||
|
||||
void Player::viewUpdate(double deltaX, double deltaY) {
|
||||
|
|
|
@ -18,7 +18,7 @@ public:
|
|||
|
||||
void create(LocalWorld* world, Camera* camera);
|
||||
|
||||
void update(bool* keys, double delta, double mouseX, double mouseY);
|
||||
void update(bool* keys, double delta, double mouseX, double mouseY, bool leftDown, bool rightDown);
|
||||
|
||||
void posUpdate(bool *keys, double delta);
|
||||
void viewUpdate(double deltaX, double deltaY);
|
||||
|
@ -43,6 +43,9 @@ private:
|
|||
Camera* camera;
|
||||
LocalWorld* world;
|
||||
|
||||
bool flying;
|
||||
bool FDown;
|
||||
|
||||
const float playerHeight = 1.6;
|
||||
};
|
||||
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
|
||||
class WorldInterpolationStream {
|
||||
public:
|
||||
static const int THREAD_QUEUE_SIZE = 32;
|
||||
static const int THREAD_QUEUE_SIZE = 16;
|
||||
static const int THREADS = 4;
|
||||
|
||||
WorldInterpolationStream() : gen(0) {};
|
||||
|
|
|
@ -240,9 +240,6 @@ void DebugGui::update(Player* player, LocalWorld* world, Window* window, BlockAt
|
|||
auto found = world->getBlock(*ray.getEnd());
|
||||
if (found > 0) {
|
||||
block = found;
|
||||
if (window->mouseIsDown()) {
|
||||
world->setBlock(*ray.getEnd(), 0);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -48,7 +48,7 @@ TextureAtlas::TextureAtlas(const char* directory) {
|
|||
|
||||
//Load Missing Texture
|
||||
auto msg = TextureRef();
|
||||
strcpy(msg.path, "../tex/_missing.png");
|
||||
strcpy(msg.path, "../res/tex/_missing.png");
|
||||
strcpy(msg.name, "_missing.png");
|
||||
msg.texData = stbi_load(msg.path, &msg.width, &msg.height, &msg.bitDepth, 4);
|
||||
textureRefs.push_back(msg);
|
||||
|
@ -98,14 +98,14 @@ TextureAtlas::TextureAtlas(const char* directory) {
|
|||
}
|
||||
|
||||
//Add all of the textures to the textureAtlas and store the UVs in the associative array
|
||||
int widthOffset = 0;
|
||||
int heightOffset = 0;
|
||||
int widthOffset = TEX_PADDING;
|
||||
int heightOffset = TEX_PADDING;
|
||||
int tallestInRow = 0;
|
||||
|
||||
for (auto i : textureRefs) {
|
||||
if (widthOffset + i.width > pageWidth) {
|
||||
if (widthOffset + i.width + TEX_PADDING*2 > pageWidth) {
|
||||
widthOffset = 0;
|
||||
heightOffset += tallestInRow;
|
||||
heightOffset += tallestInRow + TEX_PADDING*2;
|
||||
tallestInRow = i.height;
|
||||
}
|
||||
else {
|
||||
|
@ -121,16 +121,25 @@ TextureAtlas::TextureAtlas(const char* directory) {
|
|||
|
||||
textures.insert(std::pair<std::string, glm::vec4>(name, uv));
|
||||
|
||||
for (int y = 0; y < i.height; y++) {
|
||||
for (int x = 0; x < i.width; x++) {
|
||||
pageData[(heightOffset + y)*pageWidth*4 + (widthOffset + x)*4 + 0] = i.texData[(y * i.width * 4) + (x * 4) + 0];
|
||||
pageData[(heightOffset + y)*pageWidth*4 + (widthOffset + x)*4 + 1] = i.texData[(y * i.width * 4) + (x * 4) + 1];
|
||||
pageData[(heightOffset + y)*pageWidth*4 + (widthOffset + x)*4 + 2] = i.texData[(y * i.width * 4) + (x * 4) + 2];
|
||||
pageData[(heightOffset + y)*pageWidth*4 + (widthOffset + x)*4 + 3] = i.texData[(y * i.width * 4) + (x * 4) + 3];
|
||||
if (i.width > 0 && i.height > 0) {
|
||||
int xx, yy;
|
||||
for (int y = -TEX_PADDING; y < i.height + TEX_PADDING; y++) {
|
||||
for (int x = -TEX_PADDING; x < i.width + TEX_PADDING; x++) {
|
||||
yy = std::min(std::max(y, 0), i.height - 1);
|
||||
xx = std::min(std::max(x, 0), i.width - 1);
|
||||
|
||||
pageData[(heightOffset + y)*pageWidth*4 + (widthOffset + x)*4 + 0] = i.texData[(yy * i.width * 4) + (xx * 4) + 0];
|
||||
pageData[(heightOffset + y)*pageWidth*4 + (widthOffset + x)*4 + 1] = i.texData[(yy * i.width * 4) + (xx * 4) + 1];
|
||||
pageData[(heightOffset + y)*pageWidth*4 + (widthOffset + x)*4 + 2] = i.texData[(yy * i.width * 4) + (xx * 4) + 2];
|
||||
pageData[(heightOffset + y)*pageWidth*4 + (widthOffset + x)*4 + 3] = i.texData[(yy * i.width * 4) + (xx * 4) + 3];
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
std::cerr << "Failed to load a texture: " << i.name << std::endl;
|
||||
}
|
||||
|
||||
widthOffset += i.width;
|
||||
widthOffset += i.width + TEX_PADDING*2;
|
||||
}
|
||||
|
||||
stbi_write_png("../textureAtlas.png", pageWidth, pageHeight, 4, pageData, pageWidth*4);
|
||||
|
|
|
@ -21,6 +21,8 @@ public:
|
|||
Texture* getTexture();
|
||||
glm::vec4* getUVs(std::string* texture);
|
||||
private:
|
||||
const int TEX_PADDING = 2;
|
||||
|
||||
GLint maxTexSize;
|
||||
|
||||
Texture* texture;
|
||||
|
|
|
@ -30,6 +30,17 @@ MapGen::MapGen(unsigned int seed) {
|
|||
terrainFinal.SetBounds(0.0, 1000.0);
|
||||
terrainFinal.SetEdgeFalloff(0.1);
|
||||
|
||||
grassNoise.SetFrequency(2);
|
||||
grassNoise.SetOctaveCount(4);
|
||||
|
||||
grassTurbulence.SetSourceModule(0, grassNoise);
|
||||
grassTurbulence.SetFrequency(4.0);
|
||||
grassTurbulence.SetPower(0.125);
|
||||
|
||||
grassFinal.SetSourceModule(0, grassTurbulence);
|
||||
grassFinal.SetScale(3);
|
||||
grassFinal.SetBias(1);
|
||||
|
||||
floraNoise.SetFrequency(2);
|
||||
floraNoise.SetOctaveCount(4);
|
||||
|
||||
|
@ -38,13 +49,13 @@ MapGen::MapGen(unsigned int seed) {
|
|||
floraTurbulence.SetPower(0.125);
|
||||
|
||||
floraFinal.SetSourceModule(0, floraTurbulence);
|
||||
floraFinal.SetScale(3);
|
||||
floraFinal.SetBias(1);
|
||||
floraFinal.SetScale(3.5);
|
||||
floraFinal.SetBias(3.5);
|
||||
|
||||
floraDensity.SetFrequency(4);
|
||||
}
|
||||
|
||||
BlockChunk* MapGen::generate(glm::vec3 pos) {
|
||||
Timer t("Chunk Gen");
|
||||
|
||||
MapGenJob job(pos);
|
||||
|
||||
getDensityMap(job);
|
||||
|
@ -52,8 +63,6 @@ BlockChunk* MapGen::generate(glm::vec3 pos) {
|
|||
|
||||
fillChunk(job);
|
||||
|
||||
t.printElapsedMs();
|
||||
|
||||
return new BlockChunk(job.blocks, pos);
|
||||
}
|
||||
|
||||
|
@ -112,7 +121,9 @@ void MapGen::getDensityMap(MapGenJob &job) {
|
|||
}
|
||||
|
||||
void MapGen::fillChunk(MapGenJob &job) {
|
||||
auto flora_2d_sample = NoiseSample::getSample(&floraFinal, job.pos, 16, 1, true);
|
||||
auto grass_sample = NoiseSample::getSample(&grassFinal, job.pos, 16, 1, true);
|
||||
auto flora_type_sample = NoiseSample::getSample(&floraFinal, job.pos, 4, 1, true);
|
||||
auto flora_density_sample = NoiseSample::getSample(&floraDensity, job.pos, 8, 1, true);
|
||||
|
||||
glm::vec3 lp;
|
||||
|
||||
|
@ -120,13 +131,22 @@ void MapGen::fillChunk(MapGenJob &job) {
|
|||
ArrayTrans3D::indAssignVec(m, lp);
|
||||
int d = job.depth[m];
|
||||
|
||||
int grassType = min((int)std::floor(flora_2d_sample.get(lp)), 5);
|
||||
int floraId = 0;
|
||||
bool flower = false;
|
||||
|
||||
if (grassType > 0) grassType += 5;
|
||||
else grassType = 0;
|
||||
if (flora_density_sample.get(lp) > 1) flower = true;
|
||||
|
||||
if (flower) {
|
||||
int flowerType = max(min((int)std::floor(flora_type_sample.get(lp)), 8), 0);
|
||||
floraId = flowerType + 10;
|
||||
}
|
||||
else {
|
||||
int grassType = min((int)std::floor(grass_sample.get(lp)), 5);
|
||||
if (grassType > 0) floraId = grassType + 5;
|
||||
}
|
||||
|
||||
job.blocks[m] = d == 0 ? 0
|
||||
: d == 1 ? grassType
|
||||
: d == 1 ? floraId
|
||||
: d == 2 ? 1
|
||||
: d <= 3 ? 2
|
||||
: 3;
|
||||
|
|
|
@ -34,9 +34,15 @@ private:
|
|||
module::Perlin terrainType;
|
||||
module::Select terrainFinal;
|
||||
|
||||
module::Perlin grassNoise;
|
||||
module::Turbulence grassTurbulence;
|
||||
module::ScaleBias grassFinal;
|
||||
|
||||
module::Perlin floraNoise;
|
||||
module::Turbulence floraTurbulence;
|
||||
module::ScaleBias floraFinal;
|
||||
|
||||
module::Perlin floraDensity;
|
||||
};
|
||||
|
||||
|
||||
|
|
BIN
textureAtlas.png
BIN
textureAtlas.png
Binary file not shown.
Before Width: | Height: | Size: 97 KiB After Width: | Height: | Size: 99 KiB |
Loading…
Reference in New Issue