renderer cleanup, demo changes

This commit is contained in:
h4570
2022-08-03 10:37:27 +02:00
parent da958cb094
commit 0a024e745f
27 changed files with 329 additions and 149 deletions
+1
View File
@@ -35,6 +35,7 @@ because Mesh rendering uses only core.render()
- [3D] Add drawBBox(x, y , color, size) - [3D] Add drawBBox(x, y , color, size)
- [File] Async file loading - [File] Async file loading
- [tyrobj] Add multicolor support to tyrobj - [tyrobj] Add multicolor support to tyrobj
- [Tyrobj] Improve obj importing for multiple usemtl with same names
- [Renderer] Interlacing - [Renderer] Interlacing
- [General] Add cpp lint checker in GitHub - [General] Add cpp lint checker in GitHub
- [General] Control generated id to avoid duplication. Maybe Just increment from 0? Add interface IIdentificable? - [General] Control generated id to avoid duplication. Maybe Just increment from 0? Add interface IIdentificable?
+42
View File
@@ -0,0 +1,42 @@
/*
# ______ ____ ___
# | \/ ____| |___|
# | | | \ | |
#-----------------------------------------------------------------------
# Copyright 2022, tyra - https://github.com/h4570/tyra
# Licenced under Apache License 2.0
# Sandro Sobczyński <sandro.sobczynski@gmail.com>
*/
#pragma once
#include <renderer/3d/mesh/dynamic/dynamic_mesh.hpp>
#include <renderer/3d/pipeline/dynamic/dynpip_options.hpp>
#include "states/game/renderer/renderer_dynamic_pair.hpp"
#include <renderer/renderer.hpp>
using Tyra::DynamicMesh;
using Tyra::DynPipOptions;
using Tyra::Renderer;
using Tyra::TextureRepository;
using Tyra::Vec4;
namespace Demo {
class Enemy {
public:
Enemy(TextureRepository* repo);
~Enemy();
DynamicMesh* bodyMesh;
DynamicMesh* gunMesh;
DynPipOptions* options;
std::vector<RendererDynamicPair*> pairs;
void update(const Vec4& playerPosition);
private:
void allocateOptions();
};
} // namespace Demo
+2
View File
@@ -17,6 +17,7 @@
#include "./terrain/terrain.hpp" #include "./terrain/terrain.hpp"
#include "./skybox/skybox.hpp" #include "./skybox/skybox.hpp"
#include "./debug_object.hpp" #include "./debug_object.hpp"
#include "./enemy/enemy.hpp"
namespace Demo { namespace Demo {
@@ -44,6 +45,7 @@ class GameState : public State<GlobalStateType> {
GameRenderer renderer; GameRenderer renderer;
Player* player; Player* player;
Enemy* enemy;
Terrain* terrain; Terrain* terrain;
Skybox* skybox; Skybox* skybox;
DebugObject* dbgObj; DebugObject* dbgObj;
+1 -2
View File
@@ -30,8 +30,7 @@ class Player {
const Vec4& getPosition() const { return position; } const Vec4& getPosition() const { return position; }
CameraInfo3D getCameraInfo() { return camera.getCameraInfo(); } CameraInfo3D getCameraInfo() { return camera.getCameraInfo(); }
std::vector<RendererStaticPair*> staticPairs; RendererStaticPair* pair;
std::vector<RendererDynamicPair*> dynamicPairs;
void update(const float& terrainHeight); void update(const float& terrainHeight);
+82
View File
@@ -0,0 +1,82 @@
/*
# ______ ____ ___
# | \/ ____| |___|
# | | | \ | |
#-----------------------------------------------------------------------
# Copyright 2022, tyra - https://github.com/h4570/tyra
# Licenced under Apache License 2.0
# Sandro Sobczyński <sandro.sobczynski@gmail.com>
*/
#include "states/game/enemy/enemy.hpp"
#include <loaders/3d/tyrobj/tyrobj_loader.hpp>
#include <file/file_utils.hpp>
using Tyra::FileUtils;
using Tyra::TyrobjLoader;
namespace Demo {
Enemy::Enemy(TextureRepository* repo) {
TyrobjLoader loader;
auto* bodyData = loader.load(
FileUtils::fromCwd("game/models/soldier/soldier.obj"), 4, 30.0F, true);
bodyData->normalsEnabled = false;
bodyMesh = new DynamicMesh(*bodyData);
TYRA_LOG("First vertex: ", bodyData->frames[0]->vertices[0].getPrint());
TYRA_LOG("Last vertex: ",
bodyData->frames[0]
->vertices[bodyData->frames[0]->verticesCount - 1]
.getPrint());
TYRA_LOG("First index: ", bodyData->materials[0]->vertexFaces[0]);
TYRA_LOG(
"Last index: ",
bodyData->materials[0]->vertexFaces[bodyData->materials[0]->count - 1]);
delete bodyData;
bodyMesh->getMaterial(0)->color.r = 16.0F;
bodyMesh->getMaterial(0)->color.g = 16.0F;
bodyMesh->getMaterial(0)->color.b = 16.0F;
bodyMesh->playAnimation(0, bodyMesh->getFramesCount() - 1);
bodyMesh->setAnimSpeed(0.15F);
repo->addByMesh(bodyMesh, FileUtils::fromCwd("game/models/soldier/"), "png");
// auto* headData = loader.load(
// FileUtils::fromCwd("game/models/soldier/head.md2"), scale, true);
// headData->normalsEnabled = false;
// headMesh = new DynamicMesh(*headData);
// delete headData;
// headMesh->getMaterial(0)->color.r = 16.0F;
// headMesh->getMaterial(0)->color.g = 16.0F;
// headMesh->getMaterial(0)->color.b = 16.0F;
// repo->addByMesh(headMesh, FileUtils::fromCwd("game/models/soldier/"),
// "png");
allocateOptions();
pairs.push_back(new RendererDynamicPair{bodyMesh, options});
// pairs.push_back(new RendererDynamicPair{gunMesh, options});
}
Enemy::~Enemy() {
delete bodyMesh;
// delete gunMesh;
delete options;
for (auto* pair : pairs) {
delete pair;
}
}
void Enemy::update(const Vec4& playerPosition) { bodyMesh->animate(); }
void Enemy::allocateOptions() { options = new DynPipOptions(); }
} // namespace Demo
+10 -10
View File
@@ -28,10 +28,12 @@ void GameState::onStart() {
engine->audio.stopSong(); engine->audio.stopSong();
auto* repository = &engine->renderer.core.texture.repository;
player = new Player(engine); player = new Player(engine);
terrain = new Terrain(&engine->renderer.core.texture.repository); enemy = new Enemy(repository);
skybox = new Skybox(&engine->renderer.core.texture.repository); terrain = new Terrain(repository);
dbgObj = new DebugObject(&engine->renderer.core.texture.repository); skybox = new Skybox(repository);
dbgObj = new DebugObject(repository);
initialized = true; initialized = true;
} }
@@ -40,6 +42,7 @@ GlobalStateType GameState::onFinish() {
if (!initialized) return STATE_EXIT; if (!initialized) return STATE_EXIT;
delete player; delete player;
delete enemy;
delete terrain; delete terrain;
delete skybox; delete skybox;
delete dbgObj; delete dbgObj;
@@ -54,23 +57,20 @@ void GameState::update() {
fpsChecker = 0; fpsChecker = 0;
} }
// TODO: Get next player position and calculate all stuf for NEXT position
// (not current!)
// TODO: Implement collision
skybox->update(player->getPosition()); skybox->update(player->getPosition());
auto cameraInfo = player->getCameraInfo(); auto cameraInfo = player->getCameraInfo();
engine->renderer.beginFrame(cameraInfo); engine->renderer.beginFrame(cameraInfo);
dbgObj->setPosition(*cameraInfo.looksAt);
float terrainHeight = terrain->getHeightOffset(player->getPosition()); float terrainHeight = terrain->getHeightOffset(player->getPosition());
player->update(terrainHeight); player->update(terrainHeight);
enemy->update(player->getPosition());
dbgObj->setPosition(*cameraInfo.looksAt);
renderer.clear(); renderer.clear();
{ {
renderer.add(skybox->pair); renderer.add(skybox->pair);
renderer.add(player->staticPairs); renderer.add(player->pair);
renderer.add(player->dynamicPairs); renderer.add(enemy->pairs);
renderer.add(terrain->pair); renderer.add(terrain->pair);
renderer.add(dbgObj->pair); renderer.add(dbgObj->pair);
} }
+2 -9
View File
@@ -16,21 +16,14 @@ Player::Player(Engine* engine)
: position(0.0F), : position(0.0F),
weapon(&engine->renderer.core.texture.repository), weapon(&engine->renderer.core.texture.repository),
camera(&engine->pad) { camera(&engine->pad) {
staticPairs.push_back(new RendererStaticPair{weapon.mesh, weapon.options}); pair = new RendererStaticPair{weapon.mesh, weapon.options};
pad = &engine->pad; pad = &engine->pad;
position = Vec4(3.0F, 50.0F, 0.0F); position = Vec4(3.0F, 50.0F, 0.0F);
camera.lookAt = Vec4(0.0F, 0.0F, -30.0F); camera.lookAt = Vec4(0.0F, 0.0F, -30.0F);
speed = 2.0F; speed = 2.0F;
} }
Player::~Player() { Player::~Player() { delete pair; }
for (auto pair : staticPairs) {
delete pair;
}
for (auto pair : dynamicPairs) {
delete pair;
}
}
void Player::update(const float& terrainHeight) { void Player::update(const float& terrainHeight) {
handlePlayerPosition(terrainHeight); handlePlayerPosition(terrainHeight);
+4
View File
@@ -25,6 +25,10 @@ Weapon::Weapon(TextureRepository* repo) {
mesh = new StaticMesh(*data); mesh = new StaticMesh(*data);
delete data; delete data;
mesh->getMaterial(0)->color.r = 64.0F;
mesh->getMaterial(0)->color.g = 64.0F;
mesh->getMaterial(0)->color.b = 64.0F;
mesh->translation.translateX(2.85F); mesh->translation.translateX(2.85F);
mesh->translation.translateY(-3.40F); mesh->translation.translateY(-3.40F);
mesh->translation.translateZ(-10.50F); mesh->translation.translateZ(-10.50F);
-1
View File
@@ -27,7 +27,6 @@ Skybox::Skybox(TextureRepository* repo) {
for (u32 i = 0; i < mesh->getMaterialsCount(); i++) { for (u32 i = 0; i < mesh->getMaterialsCount(); i++) {
auto* material = mesh->getMaterial(i); auto* material = mesh->getMaterial(i);
material->print();
material->color.r = 16.0F; material->color.r = 16.0F;
material->color.g = 16.0F; material->color.g = 16.0F;
material->color.b = 16.0F; material->color.b = 16.0F;
+3 -3
View File
@@ -27,9 +27,9 @@ Terrain::Terrain(TextureRepository* repo)
FileUtils::fromCwd("game/models/terrain/terrain.obj"), 1, 25.0F, true); FileUtils::fromCwd("game/models/terrain/terrain.obj"), 1, 25.0F, true);
data->normalsEnabled = false; data->normalsEnabled = false;
mesh = new StaticMesh(*data); mesh = new StaticMesh(*data);
mesh->getMaterial(0)->color.r = 96.0F; mesh->getMaterial(0)->color.r = 32.0F;
mesh->getMaterial(0)->color.g = 96.0F; mesh->getMaterial(0)->color.g = 32.0F;
mesh->getMaterial(0)->color.b = 96.0F; mesh->getMaterial(0)->color.b = 32.0F;
delete data; delete data;
repo->addByMesh(mesh, FileUtils::fromCwd("game/models/terrain/"), "png"); repo->addByMesh(mesh, FileUtils::fromCwd("game/models/terrain/"), "png");
@@ -12,7 +12,7 @@
#include "math/vec4.hpp" #include "math/vec4.hpp"
#include "renderer/3d/pipeline/shared/bag/pipeline_info_bag.hpp" #include "./dynpip_info_bag.hpp"
#include "./dynpip_color_bag.hpp" #include "./dynpip_color_bag.hpp"
#include "./dynpip_lighting_bag.hpp" #include "./dynpip_lighting_bag.hpp"
#include "./dynpip_texture_bag.hpp" #include "./dynpip_texture_bag.hpp"
@@ -31,7 +31,7 @@ class DynPipBag {
~DynPipBag(); ~DynPipBag();
/** Mandatory. Object info. */ /** Mandatory. Object info. */
PipelineInfoBag* info; DynPipInfoBag* info;
/** Mandatory. Object color(s). */ /** Mandatory. Object color(s). */
DynPipColorBag* color; DynPipColorBag* color;
@@ -8,19 +8,16 @@
# Sandro Sobczyński <sandro.sobczynski@gmail.com> # Sandro Sobczyński <sandro.sobczynski@gmail.com>
*/ */
#pragma once
#include "renderer/3d/pipeline/shared/bag/pipeline_info_bag.hpp" #include "renderer/3d/pipeline/shared/bag/pipeline_info_bag.hpp"
namespace Tyra { namespace Tyra {
PipelineInfoBag::PipelineInfoBag() { class DynPipInfoBag : public PipelineInfoBag {
shadingType = TyraShadingFlat; public:
transformationType = TyraMVP; DynPipInfoBag() {}
textureMappingType = TyraLinear; ~DynPipInfoBag() {}
blendingEnabled = true; };
antiAliasingEnabled = false;
model = nullptr;
}
PipelineInfoBag::~PipelineInfoBag() {}
} // namespace Tyra } // namespace Tyra
@@ -28,18 +28,16 @@ class DynPipCore {
void init(RendererCore* t_core); void init(RendererCore* t_core);
/** Force starting VU1 program instead of continueing */ /** Force starting VU1 program instead of continueing */
void clear() { qbufferRenderer.clearLastProgramName(); } void begin(PipelineInfoBag* bag);
void updatePrimLod(PipelineInfoBag* bag);
/** /**
* Send model matrix, lighting data and other * Send model matrix, lighting data and other
* repetitve stuff to VU1 * repetitve stuff to VU1
*/ */
void initParts(DynPipBag* data); void sendObjectDataToVU1(DynPipBag* data);
/** Render 3D via "bags" */ /** Render 3D via "bags" */
void renderPart(DynPipBag** bags, const u32& count, void render(DynPipBag** bags, const u32& count);
const bool& frustumCull = true);
/** Get max vert count of VU1 qbuffer (for optimizations) */ /** Get max vert count of VU1 qbuffer (for optimizations) */
u32 getMaxVertCountByParams(const bool& isLightingEnabled, u32 getMaxVertCountByParams(const bool& isLightingEnabled,
@@ -53,17 +53,15 @@ class DynamicPipeline : public Renderer3DPipeline {
DynPipBag* buffers; DynPipBag* buffers;
static const u32 halfBuffersCount; static const u32 halfBuffersCount;
void setBuffer(DynPipBag* buffers, DynPipBag* buffer, u16* bufferIndex, void setBuffer(DynPipBag* buffers, DynPipBag* buffer, u16* bufferIndex);
const PipelineFrustumCulling& frustumCulling);
void sendRestOfBuffers(DynPipBag* buffers, u16* bufferIndex, void sendRestOfBuffers(DynPipBag* buffers, u16* bufferIndex);
const PipelineFrustumCulling& frustumCulling);
void addVertices(MeshMaterialFrame* materialFrameFrom, void addVertices(MeshMaterialFrame* materialFrameFrom,
MeshMaterialFrame* materialFrameTo, DynPipBag* bag, MeshMaterialFrame* materialFrameTo, DynPipBag* bag,
const u32& startIndex) const; const u32& startIndex) const;
PipelineInfoBag* getInfoBag(DynamicMesh* mesh, const DynPipOptions* options, DynPipInfoBag* getInfoBag(DynamicMesh* mesh, const DynPipOptions* options,
M4x4* model) const; M4x4* model) const;
DynPipColorBag* getColorBag(MeshMaterial* material) const; DynPipColorBag* getColorBag(MeshMaterial* material) const;
@@ -82,7 +80,7 @@ class DynamicPipeline : public Renderer3DPipeline {
void setLightingColorsCache(PipelineLightingOptions* lightingOptions); void setLightingColorsCache(PipelineLightingOptions* lightingOptions);
void freeBuffer(DynPipBag* bag); void freeBuffer(DynPipBag* bag);
void setBuffersDefaultVars(DynPipBag* buffers, DynamicMesh* mesh, void setBuffersDefaultVars(DynPipBag* buffers, DynamicMesh* mesh,
PipelineInfoBag* infoBag); DynPipInfoBag* infoBag);
void setBuffersColorBag(DynPipBag* buffers, DynPipColorBag* colorBag); void setBuffersColorBag(DynPipBag* buffers, DynPipColorBag* colorBag);
}; };
@@ -16,33 +16,43 @@
#include "../pipeline_shading_type.hpp" #include "../pipeline_shading_type.hpp"
#include "../pipeline_texture_mapping_type.hpp" #include "../pipeline_texture_mapping_type.hpp"
#include "../pipeline_transformation_type.hpp" #include "../pipeline_transformation_type.hpp"
#include "./pipeline_info_bag_frustum_culling.hpp"
namespace Tyra { namespace Tyra {
class PipelineInfoBag { class PipelineInfoBag {
public: public:
PipelineInfoBag(); PipelineInfoBag() {
~PipelineInfoBag(); shadingType = TyraShadingFlat;
transformationType = TyraMVP;
textureMappingType = TyraLinear;
blendingEnabled = true;
antiAliasingEnabled = false;
model = nullptr;
frustumCulling = PipelineInfoBagFrustumCulling_None;
}
~PipelineInfoBag() {}
/** Mandatory. Model matrix */ /** Mandatory. Model matrix */
M4x4* model; M4x4* model;
/** Flat or gouraud */
PipelineShadingType shadingType; PipelineShadingType shadingType;
/** Linear or nearest */
PipelineTextureMappingType textureMappingType; PipelineTextureMappingType textureMappingType;
/** Multiply by model matrix by view-projection or projection matrix */
PipelineTransformationType transformationType; PipelineTransformationType transformationType;
/** Blending texture with color */
bool blendingEnabled; bool blendingEnabled;
/** Anti-aliasing */
bool antiAliasingEnabled; bool antiAliasingEnabled;
/** /** Type of frustum culling */
* @brief Experimental! False -> disables "clip against each plane" algorithm. PipelineInfoBagFrustumCulling frustumCulling;
* Default: True.
*
* Full clip checks are slow, but they are
* preventing visual artifacts, which can happen
* for big 3D objects (or objects near camera eyes)
* Force enabled in dynamic pipe, because of efficiency.
*/
bool fullClipChecks;
}; };
} // namespace Tyra } // namespace Tyra
@@ -0,0 +1,22 @@
/*
# ______ ____ ___
# | \/ ____| |___|
# | | | \ | |
#-----------------------------------------------------------------------
# Copyright 2022, tyra - https://github.com/h4570/tyra
# Licenced under Apache License 2.0
# Sandro Sobczyński <sandro.sobczynski@gmail.com>
*/
#pragma once
namespace Tyra {
enum PipelineInfoBagFrustumCulling {
/** No frustum culling */
PipelineInfoBagFrustumCulling_None = 0,
/** Frustum culling of parts of an object */
PipelineInfoBagFrustumCulling_Precise = 2,
};
}
@@ -45,7 +45,7 @@ class PipelineOptions {
/** Anti-aliasing */ /** Anti-aliasing */
bool antiAliasingEnabled; bool antiAliasingEnabled;
/** Multiply by model matrix by MVP or MP */ /** Multiply by model matrix by view-projection or projection matrix */
PipelineTransformationType transformationType; PipelineTransformationType transformationType;
/** Optional */ /** Optional */
@@ -11,7 +11,7 @@
#pragma once #pragma once
#include "math/vec4.hpp" #include "math/vec4.hpp"
#include "renderer/3d/pipeline/shared/bag/pipeline_info_bag.hpp" #include "./stapip_info_bag.hpp"
#include "./stapip_color_bag.hpp" #include "./stapip_color_bag.hpp"
#include "./stapip_lighting_bag.hpp" #include "./stapip_lighting_bag.hpp"
#include "./stapip_texture_bag.hpp" #include "./stapip_texture_bag.hpp"
@@ -31,7 +31,7 @@ class StaPipBag {
~StaPipBag(); ~StaPipBag();
/** Mandatory. Object info. */ /** Mandatory. Object info. */
PipelineInfoBag* info; StaPipInfoBag* info;
/** Mandatory. Object color(s). */ /** Mandatory. Object color(s). */
StaPipColorBag* color; StaPipColorBag* color;
@@ -0,0 +1,41 @@
/*
# ______ ____ ___
# | \/ ____| |___|
# | | | \ | |
#-----------------------------------------------------------------------
# Copyright 2022, tyra - https://github.com/h4570/tyra
# Licenced under Apache License 2.0
# Sandro Sobczyński <sandro.sobczynski@gmail.com>
*/
#pragma once
#include "renderer/3d/pipeline/shared/bag/pipeline_info_bag.hpp"
#include "renderer/3d/pipeline/static/stapip_ztest.hpp"
namespace Tyra {
class StaPipInfoBag : public PipelineInfoBag {
public:
StaPipInfoBag() {
fullClipChecks = false;
zTestType = StaPipZTest_Standard;
}
~StaPipInfoBag() {}
/**
* @brief Experimental! False -> disables "clip against each plane" algorithm.
* Default: True.
*
* Full clip checks are slow, but they are
* preventing visual artifacts, which can happen
* for big 3D objects (or objects near camera eyes)
* Force enabled in dynamic pipe, because of efficiency.
*/
bool fullClipChecks;
/** @brief Type of z buffer testing. */
StaPipZTest zTestType;
};
} // namespace Tyra
@@ -29,8 +29,7 @@ class StaPipCore {
void init(RendererCore* t_core); void init(RendererCore* t_core);
/** Render 3D via "bags" */ /** Render 3D via "bags" */
void render(StaPipBag* bag, const bool& frustumCull, const StaPipZTest& zTest, void render(StaPipBag* bag, StaPipBagPackagesBBox* bbox = nullptr);
StaPipBagPackagesBBox* bbox = nullptr);
/** Get max vert count of VU1 qbuffer (for optimizations) */ /** Get max vert count of VU1 qbuffer (for optimizations) */
u32 getMaxVertCountByParams(const bool& isSingleColor, u32 getMaxVertCountByParams(const bool& isSingleColor,
@@ -53,7 +53,7 @@ class StaticPipeline : public Renderer3DPipeline {
void addVertices(MeshMaterialFrame* materialFrame, StaPipBag* bag) const; void addVertices(MeshMaterialFrame* materialFrame, StaPipBag* bag) const;
PipelineInfoBag* getInfoBag(StaticMesh* mesh, const StaPipOptions* options, StaPipInfoBag* getInfoBag(StaticMesh* mesh, const StaPipOptions* options,
M4x4* model) const; M4x4* model) const;
StaPipColorBag* getColorBag(MeshMaterial* material, StaPipColorBag* getColorBag(MeshMaterial* material,
-3
View File
@@ -149,9 +149,6 @@ MeshBuilderData* MD2Loader::load(const char* fullpath, const float& scale,
texCoord_t* texCoord; texCoord_t* texCoord;
TYRA_LOG("Skin width: ", header.skinwidth,
" Skin height: ", header.skinheight);
for (u32 i = 0; i < stsCount; i++) { for (u32 i = 0; i < stsCount; i++) {
texCoord = texCoord =
reinterpret_cast<texCoord_t*>(&stsBuffer[sizeof(texCoord_t) * i]); reinterpret_cast<texCoord_t*>(&stsBuffer[sizeof(texCoord_t) * i]);
@@ -243,8 +243,7 @@ void TyrobjLoader::readFaces(TyraobjReadInfo* info, FILE* file,
&normalIndex[1], &vertexIndex[2], &coordIndex[2], &normalIndex[2]); &normalIndex[1], &vertexIndex[2], &coordIndex[2], &normalIndex[2]);
} break; } break;
/** Loaded only two digits (V, VT) succesfuly. Not setting /** Loaded only two digits (V, VT) succesfuly. Not setting VN. */
VN. */
case 3: { case 3: {
fscanf(file, "%d/%d/ %d/%d/ %d/%d/\n", &vertexIndex[0], &coordIndex[0], fscanf(file, "%d/%d/ %d/%d/ %d/%d/\n", &vertexIndex[0], &coordIndex[0],
&vertexIndex[1], &coordIndex[1], &vertexIndex[2], &coordIndex[2]); &vertexIndex[1], &coordIndex[1], &vertexIndex[2], &coordIndex[2]);
@@ -56,7 +56,7 @@ u32 DynPipCore::getMaxVertCountByParams(const bool& isLightingEnabled,
->getMaxVertCount(qbufferRenderer.getBufferSize()); ->getMaxVertCount(qbufferRenderer.getBufferSize());
} }
void DynPipCore::initParts(DynPipBag* bag) { void DynPipCore::sendObjectDataToVU1(DynPipBag* bag) {
RendererCoreTextureBuffers* texBuffers = nullptr; RendererCoreTextureBuffers* texBuffers = nullptr;
if (bag->texture) { if (bag->texture) {
auto temp = rendererCore->texture.useTexture(bag->texture->texture); auto temp = rendererCore->texture.useTexture(bag->texture->texture);
@@ -74,7 +74,9 @@ void DynPipCore::initParts(DynPipBag* bag) {
delete texBuffers; delete texBuffers;
} }
void DynPipCore::updatePrimLod(PipelineInfoBag* bag) { void DynPipCore::begin(PipelineInfoBag* bag) {
qbufferRenderer.clearLastProgramName();
prim.antialiasing = bag->antiAliasingEnabled; prim.antialiasing = bag->antiAliasingEnabled;
prim.blending = bag->blendingEnabled; prim.blending = bag->blendingEnabled;
prim.shading = bag->shadingType; prim.shading = bag->shadingType;
@@ -88,8 +90,7 @@ void DynPipCore::updatePrimLod(PipelineInfoBag* bag) {
} }
} }
void DynPipCore::renderPart(DynPipBag** bags, const u32& count, void DynPipCore::render(DynPipBag** bags, const u32& count) {
const bool& frustumCull) {
if (count <= 0) return; if (count <= 0) return;
TYRA_ASSERT( TYRA_ASSERT(
@@ -113,7 +114,7 @@ void DynPipCore::renderPart(DynPipBag** bags, const u32& count,
bags[0]->texture->coordinatesTo), bags[0]->texture->coordinatesTo),
"If you want texture, please provide texture and coordinates!"); "If you want texture, please provide texture and coordinates!");
if (!frustumCull) { if (bags[0]->info->frustumCulling == PipelineInfoBagFrustumCulling_None) {
qbufferRenderer.render(bags, count); qbufferRenderer.render(bags, count);
return; return;
} }
@@ -9,6 +9,7 @@
*/ */
#include "renderer/3d/pipeline/dynamic/dynamic_pipeline.hpp" #include "renderer/3d/pipeline/dynamic/dynamic_pipeline.hpp"
#include "renderer/3d/pipeline/shared/bag/pipeline_info_bag.hpp"
namespace Tyra { namespace Tyra {
@@ -49,13 +50,18 @@ void DynamicPipeline::onUseEnd() {
} }
void DynamicPipeline::render(DynamicMesh* mesh, const DynPipOptions* options) { void DynamicPipeline::render(DynamicMesh* mesh, const DynPipOptions* options) {
bool optionsManuallyAllocated = false;
if (!options) {
options = new DynPipOptions();
optionsManuallyAllocated = true;
}
auto model = mesh->getModelMatrix(); auto model = mesh->getModelMatrix();
auto* infoBag = getInfoBag(mesh, options, &model); auto* infoBag = getInfoBag(mesh, options, &model);
PipelineDirLightsBag* dirLights = nullptr; PipelineDirLightsBag* dirLights = nullptr;
auto frustumCulling =
options ? options->frustumCulling : PipelineFrustumCulling_Simple;
if (frustumCulling == PipelineFrustumCulling_Simple) { if (options->frustumCulling == PipelineFrustumCulling_Simple) {
auto* frameTo = mesh->getFrame(mesh->getNextAnimationFrame()); auto* frameTo = mesh->getFrame(mesh->getNextAnimationFrame());
if (frameTo->getBBox().isInFrustum( if (frameTo->getBBox().isInFrustum(
rendererCore->renderer3D.frustumPlanes.getAll(), model) == rendererCore->renderer3D.frustumPlanes.getAll(), model) ==
@@ -74,8 +80,7 @@ void DynamicPipeline::render(DynamicMesh* mesh, const DynPipOptions* options) {
u16 bufferIndex = 0; u16 bufferIndex = 0;
setBuffersDefaultVars(buffers, mesh, infoBag); setBuffersDefaultVars(buffers, mesh, infoBag);
core.clear(); core.begin(infoBag);
core.updatePrimLod(infoBag);
for (u32 i = 0; i < mesh->getMaterialsCount(); i++) { for (u32 i = 0; i < mesh->getMaterialsCount(); i++) {
auto* material = mesh->getMaterial(i); auto* material = mesh->getMaterial(i);
@@ -110,28 +115,29 @@ void DynamicPipeline::render(DynamicMesh* mesh, const DynPipOptions* options) {
dirLights, startIndex); dirLights, startIndex);
if (!isPartInitialized) { if (!isPartInitialized) {
core.initParts(&buffer); core.sendObjectDataToVU1(&buffer);
isPartInitialized = true; isPartInitialized = true;
} }
setBuffer(buffers, &buffer, &bufferIndex, frustumCulling); setBuffer(buffers, &buffer, &bufferIndex);
} }
delete colorBag; delete colorBag;
} }
sendRestOfBuffers(buffers, &bufferIndex, frustumCulling); sendRestOfBuffers(buffers, &bufferIndex);
if (dirLights) { if (dirLights) {
delete dirLights; delete dirLights;
} }
delete infoBag; delete infoBag;
if (optionsManuallyAllocated) delete options;
} }
void DynamicPipeline::setBuffer(DynPipBag* buffers, DynPipBag* buffer, void DynamicPipeline::setBuffer(DynPipBag* buffers, DynPipBag* buffer,
u16* bufferIndex, u16* bufferIndex) {
const PipelineFrustumCulling& frustumCulling) {
auto isEndOf1stDBuffer = *bufferIndex == halfBuffersCount - 1; auto isEndOf1stDBuffer = *bufferIndex == halfBuffersCount - 1;
auto isEndOf2ndDBuffer = *bufferIndex == buffersCount - 1; auto isEndOf2ndDBuffer = *bufferIndex == buffersCount - 1;
@@ -143,8 +149,7 @@ void DynamicPipeline::setBuffer(DynPipBag* buffers, DynPipBag* buffer,
for (u32 i = 0; i < halfBuffersCount; i++) for (u32 i = 0; i < halfBuffersCount; i++)
sendBuffers[i] = &buffers[offset + i]; sendBuffers[i] = &buffers[offset + i];
core.renderPart(sendBuffers, halfBuffersCount, core.render(sendBuffers, halfBuffersCount);
frustumCulling == PipelineFrustumCulling_Precise);
delete[] sendBuffers; delete[] sendBuffers;
} }
@@ -155,9 +160,7 @@ void DynamicPipeline::setBuffer(DynPipBag* buffers, DynPipBag* buffer,
*bufferIndex += 1; *bufferIndex += 1;
} }
void DynamicPipeline::sendRestOfBuffers( void DynamicPipeline::sendRestOfBuffers(DynPipBag* buffers, u16* bufferIndex) {
DynPipBag* buffers, u16* bufferIndex,
const PipelineFrustumCulling& frustumCulling) {
auto isEndOf1stDBuffer = *bufferIndex <= halfBuffersCount - 1; auto isEndOf1stDBuffer = *bufferIndex <= halfBuffersCount - 1;
u32 offset = isEndOf1stDBuffer ? 0 : halfBuffersCount; u32 offset = isEndOf1stDBuffer ? 0 : halfBuffersCount;
@@ -170,15 +173,14 @@ void DynamicPipeline::sendRestOfBuffers(
sendBuffers[i] = &buffers[offset + i]; sendBuffers[i] = &buffers[offset + i];
} }
core.renderPart(sendBuffers, size, core.render(sendBuffers, size);
frustumCulling == PipelineFrustumCulling_Precise);
delete[] sendBuffers; delete[] sendBuffers;
} }
void DynamicPipeline::setBuffersDefaultVars(DynPipBag* buffers, void DynamicPipeline::setBuffersDefaultVars(DynPipBag* buffers,
DynamicMesh* mesh, DynamicMesh* mesh,
PipelineInfoBag* infoBag) { DynPipInfoBag* infoBag) {
for (u32 i = 0; i < buffersCount; i++) { for (u32 i = 0; i < buffersCount; i++) {
buffers[i].info = infoBag; buffers[i].info = infoBag;
buffers[i].interpolation = mesh->getAnimState().interpolation; buffers[i].interpolation = mesh->getAnimState().interpolation;
@@ -202,25 +204,20 @@ void DynamicPipeline::freeBuffer(DynPipBag* bag) {
} }
} }
PipelineInfoBag* DynamicPipeline::getInfoBag(DynamicMesh* mesh, DynPipInfoBag* DynamicPipeline::getInfoBag(DynamicMesh* mesh,
const DynPipOptions* options, const DynPipOptions* options,
M4x4* model) const { M4x4* model) const {
auto* result = new PipelineInfoBag(); auto* result = new DynPipInfoBag();
if (options) {
result->antiAliasingEnabled = options->antiAliasingEnabled; result->antiAliasingEnabled = options->antiAliasingEnabled;
result->blendingEnabled = options->blendingEnabled; result->blendingEnabled = options->blendingEnabled;
result->shadingType = options->shadingType; result->shadingType = options->shadingType;
result->textureMappingType = options->textureMappingType; result->textureMappingType = options->textureMappingType;
result->transformationType = options->transformationType; result->transformationType = options->transformationType;
} else { result->frustumCulling =
result->antiAliasingEnabled = false; options->frustumCulling == PipelineFrustumCulling_Precise
result->blendingEnabled = true; ? PipelineInfoBagFrustumCulling_Precise
result->shadingType = TyraShadingFlat; : PipelineInfoBagFrustumCulling_None;
result->textureMappingType = TyraLinear;
result->transformationType = TyraMVP;
}
result->model = model; result->model = model;
return result; return result;
@@ -72,10 +72,12 @@ u32 StaPipCore::getMaxVertCountByParams(const bool& isSingleColor,
->getMaxVertCount(isSingleColor, qbufferRenderer.getBufferSize()); ->getMaxVertCount(isSingleColor, qbufferRenderer.getBufferSize());
} }
void StaPipCore::render(StaPipBag* bag, const bool& frustumCull, void StaPipCore::render(StaPipBag* bag, StaPipBagPackagesBBox* bbox) {
const StaPipZTest& zTest, StaPipBagPackagesBBox* bbox) {
if (bag->count <= 0) return; if (bag->count <= 0) return;
bool frustumCull =
bag->info->frustumCulling == PipelineInfoBagFrustumCulling_Precise;
TYRA_ASSERT(bag->vertices != nullptr, TYRA_ASSERT(bag->vertices != nullptr,
"Vertices are required in 3D render bag!"); "Vertices are required in 3D render bag!");
TYRA_ASSERT(bag->info != nullptr, "Info bag is required in 3D render bag!"); TYRA_ASSERT(bag->info != nullptr, "Info bag is required in 3D render bag!");
@@ -100,7 +102,7 @@ void StaPipCore::render(StaPipBag* bag, const bool& frustumCull,
(!bag->info->fullClipChecks && !frustumCull), (!bag->info->fullClipChecks && !frustumCull),
"Please disable clip checks and frustum culling if not using MVP " "Please disable clip checks and frustum culling if not using MVP "
"matrix!"); "matrix!");
TYRA_ASSERT(!(frustumCull == false && bag->info->fullClipChecks == true), TYRA_ASSERT(!(!frustumCull && bag->info->fullClipChecks == true),
"Full clip checks are not supported with frustum culling = off!"); "Full clip checks are not supported with frustum culling = off!");
u32 maxVertCount = getMaxVertCountByBag(bag); u32 maxVertCount = getMaxVertCountByBag(bag);
@@ -128,7 +130,7 @@ void StaPipCore::render(StaPipBag* bag, const bool& frustumCull,
} }
} }
if (zTest == StaPipZTest_AllPass) { if (bag->info->zTestType == StaPipZTest_AllPass) {
rendererCore->gs.setAllPassZTest(); rendererCore->gs.setAllPassZTest();
} }
@@ -208,7 +210,7 @@ void StaPipCore::render(StaPipBag* bag, const bool& frustumCull,
qbufferRenderer.flushBuffers(); qbufferRenderer.flushBuffers();
if (zTest == StaPipZTest_AllPass) { if (bag->info->zTestType == StaPipZTest_AllPass) {
rendererCore->gs.setStandardZTest(); rendererCore->gs.setStandardZTest();
} }
@@ -10,6 +10,7 @@
#include "renderer/3d/pipeline/static/static_pipeline.hpp" #include "renderer/3d/pipeline/static/static_pipeline.hpp"
#include "debug/debug.hpp" #include "debug/debug.hpp"
#include "renderer/3d/pipeline/static/core/bag/stapip_info_bag.hpp"
namespace Tyra { namespace Tyra {
@@ -37,15 +38,18 @@ void StaticPipeline::onUseEnd() {
} }
void StaticPipeline::render(StaticMesh* mesh, const StaPipOptions* options) { void StaticPipeline::render(StaticMesh* mesh, const StaPipOptions* options) {
bool optionsManuallyAllocated = false;
if (!options) {
options = new StaPipOptions();
optionsManuallyAllocated = true;
}
auto model = mesh->getModelMatrix(); auto model = mesh->getModelMatrix();
auto* infoBag = getInfoBag(mesh, options, &model); auto* infoBag = getInfoBag(mesh, options, &model);
auto zTesting = options ? options->zTestType : StaPipZTest_Standard;
auto frustumCulling =
options ? options->frustumCulling : PipelineFrustumCulling_Simple;
TYRA_ASSERT( TYRA_ASSERT(
!(frustumCulling != PipelineFrustumCulling_Precise && !(options->frustumCulling != PipelineFrustumCulling_Precise &&
infoBag->fullClipChecks == true), infoBag->fullClipChecks == true),
"Full clip checks are only supported with frustum culling == Precise!"); "Full clip checks are only supported with frustum culling == Precise!");
TYRA_ASSERT(options->transformationType == TyraMVP || TYRA_ASSERT(options->transformationType == TyraMVP ||
@@ -54,7 +58,7 @@ void StaticPipeline::render(StaticMesh* mesh, const StaPipOptions* options) {
"Please disable clip checks and frustum culling if not using MVP " "Please disable clip checks and frustum culling if not using MVP "
"matrix!"); "matrix!");
if (frustumCulling == PipelineFrustumCulling_Simple) { if (options->frustumCulling == PipelineFrustumCulling_Simple) {
auto* frame = mesh->getFrame(); auto* frame = mesh->getFrame();
if (frame->getBBox().isInFrustum( if (frame->getBBox().isInFrustum(
rendererCore->renderer3D.frustumPlanes.getAll(), model) == rendererCore->renderer3D.frustumPlanes.getAll(), model) ==
@@ -68,21 +72,19 @@ void StaticPipeline::render(StaticMesh* mesh, const StaPipOptions* options) {
for (u32 i = 0; i < mesh->getMaterialsCount(); i++) { for (u32 i = 0; i < mesh->getMaterialsCount(); i++) {
auto* material = mesh->getMaterial(i); auto* material = mesh->getMaterial(i);
auto* materialFrame = material->getFrame(0); auto* materialFrame = material->getFrame(0);
StaPipBag bag; StaPipBag bag;
addVertices(materialFrame, &bag); addVertices(materialFrame, &bag);
bag.info = infoBag; bag.info = infoBag;
bag.color = getColorBag(material, materialFrame); bag.color = getColorBag(material, materialFrame);
bag.texture = getTextureBag(material, materialFrame); bag.texture = getTextureBag(material, materialFrame);
bag.lighting = getLightingBag(materialFrame, &model, options); bag.lighting = getLightingBag(materialFrame, &model, options);
core.render(&bag);
core.render(&bag, frustumCulling == PipelineFrustumCulling_Precise,
zTesting);
deallocDrawBags(&bag, material); deallocDrawBags(&bag, material);
} }
delete infoBag; delete infoBag;
if (optionsManuallyAllocated) delete options;
} }
void StaticPipeline::addVertices(MeshMaterialFrame* materialFrame, void StaticPipeline::addVertices(MeshMaterialFrame* materialFrame,
@@ -91,27 +93,22 @@ void StaticPipeline::addVertices(MeshMaterialFrame* materialFrame,
bag->vertices = materialFrame->getVertices(); bag->vertices = materialFrame->getVertices();
} }
PipelineInfoBag* StaticPipeline::getInfoBag(StaticMesh* mesh, StaPipInfoBag* StaticPipeline::getInfoBag(StaticMesh* mesh,
const StaPipOptions* options, const StaPipOptions* options,
M4x4* model) const { M4x4* model) const {
auto* result = new PipelineInfoBag(); auto* result = new StaPipInfoBag();
if (options) {
result->antiAliasingEnabled = options->antiAliasingEnabled; result->antiAliasingEnabled = options->antiAliasingEnabled;
result->blendingEnabled = options->blendingEnabled; result->blendingEnabled = options->blendingEnabled;
result->shadingType = options->shadingType; result->shadingType = options->shadingType;
result->fullClipChecks = options->fullClipChecks;
result->textureMappingType = options->textureMappingType; result->textureMappingType = options->textureMappingType;
result->transformationType = options->transformationType; result->transformationType = options->transformationType;
} else { result->frustumCulling =
result->antiAliasingEnabled = false; options->frustumCulling == PipelineFrustumCulling_Precise
result->blendingEnabled = true; ? PipelineInfoBagFrustumCulling_Precise
result->shadingType = TyraShadingFlat; : PipelineInfoBagFrustumCulling_None;
result->textureMappingType = TyraLinear; result->fullClipChecks = options->fullClipChecks;
result->fullClipChecks = false; result->zTestType = options->zTestType;
result->transformationType = TyraMVP;
}
result->model = model; result->model = model;
return result; return result;