GameObjects
Began to add GameObjects, starting with the player.
This commit is contained in:
61
GameObject.h
Normal file
61
GameObject.h
Normal file
@@ -0,0 +1,61 @@
|
||||
#pragma once
|
||||
|
||||
#include <glm/glm.hpp>
|
||||
|
||||
#include <InputComponent.h>
|
||||
#include <GraphicsComponent.h>
|
||||
#include <PhysicsComponent.h>
|
||||
|
||||
class GameObject
|
||||
{
|
||||
public:
|
||||
glm::vec3 Position;
|
||||
|
||||
glm::vec3 Rotation;
|
||||
|
||||
glm::vec3 Scale;
|
||||
|
||||
GameObject(glm::vec3 Position, glm::vec3 Rotation, glm::vec3 Scale)
|
||||
: Input(nullptr),
|
||||
Graphics(nullptr),
|
||||
Physics(nullptr),
|
||||
Position(Position),
|
||||
Rotation(Rotation),
|
||||
Scale(Scale),
|
||||
Front(0.0f, 0.0f, 1.0f),
|
||||
Up(0.0f, 1.0f, 0.0f),
|
||||
Right(1.0f, 0.0f, 0.0f),
|
||||
WorldUp(0.0f, 1.0f, 0.0f)
|
||||
{
|
||||
}
|
||||
|
||||
GameObject(InputComponent* Input, GraphicsComponent* Graphics, PhysicsComponent* Physics)
|
||||
: Input(Input),
|
||||
Graphics(Graphics),
|
||||
Physics(Physics),
|
||||
Position(0.0f, 0.0f, 0.0f),
|
||||
Rotation(0.0f, 0.0f, 0.0f),
|
||||
Scale(1.0f, 1.0f, 1.0f),
|
||||
Front(0.0f, 0.0f, 1.0f),
|
||||
Up(0.0f, 1.0f, 0.0f),
|
||||
Right(1.0f, 0.0f, 0.0f),
|
||||
WorldUp(0.0f, 1.0f, 0.0f)
|
||||
{}
|
||||
|
||||
void Update()
|
||||
{
|
||||
Input->Update();
|
||||
Graphics->Update();
|
||||
Physics->Update();
|
||||
}
|
||||
|
||||
protected:
|
||||
InputComponent* Input;
|
||||
GraphicsComponent* Graphics;
|
||||
PhysicsComponent* Physics;
|
||||
|
||||
glm::vec3 Front;
|
||||
glm::vec3 Up;
|
||||
glm::vec3 Right;
|
||||
glm::vec3 WorldUp;
|
||||
};
|
||||
8
GraphicsComponent.h
Normal file
8
GraphicsComponent.h
Normal file
@@ -0,0 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
class GraphicsComponent
|
||||
{
|
||||
public:
|
||||
virtual ~GraphicsComponent() {};
|
||||
virtual void Update() = 0;
|
||||
};
|
||||
8
InputComponent.h
Normal file
8
InputComponent.h
Normal file
@@ -0,0 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
class InputComponent
|
||||
{
|
||||
public:
|
||||
virtual ~InputComponent() {};
|
||||
virtual void Update() = 0;
|
||||
};
|
||||
@@ -134,7 +134,20 @@
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="..\..\Development Tools\glad\src\glad.c" />
|
||||
<ClCompile Include="imgui\backends\imgui_impl_glfw.cpp" />
|
||||
<ClCompile Include="imgui\backends\imgui_impl_opengl3.cpp" />
|
||||
<ClCompile Include="imgui\imgui.cpp" />
|
||||
<ClCompile Include="imgui\imgui_draw.cpp" />
|
||||
<ClCompile Include="imgui\imgui_tables.cpp" />
|
||||
<ClCompile Include="imgui\imgui_widgets.cpp" />
|
||||
<ClCompile Include="LevelMap.cpp" />
|
||||
<ClCompile Include="Light.cpp" />
|
||||
<ClCompile Include="main.cpp" />
|
||||
<ClCompile Include="MeshRenderer.cpp" />
|
||||
<ClCompile Include="Player.cpp" />
|
||||
<ClCompile Include="PointLight.cpp" />
|
||||
<ClCompile Include="ResourceManager.cpp" />
|
||||
<ClCompile Include="Shader.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="cube.frag" />
|
||||
@@ -142,13 +155,36 @@
|
||||
<None Include="fragment.frag" />
|
||||
<None Include="light.frag" />
|
||||
<None Include="light.vert" />
|
||||
<None Include="point_shadow_depth.frag" />
|
||||
<None Include="point_shadow_depth.geom" />
|
||||
<None Include="point_shadow_depth.vert" />
|
||||
<None Include="vertex.vert" />
|
||||
<None Include="wall.frag" />
|
||||
<None Include="wall.vert" />
|
||||
<None Include="wall_test.frag" />
|
||||
<None Include="wall_test.vert" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="camera.h" />
|
||||
<ClInclude Include="Camera.h" />
|
||||
<ClInclude Include="cube.h" />
|
||||
<ClInclude Include="cubeFactory.h" />
|
||||
<ClInclude Include="shader.h" />
|
||||
<ClInclude Include="GameObject.h" />
|
||||
<ClInclude Include="GraphicsComponent.h" />
|
||||
<ClInclude Include="InputComponent.h" />
|
||||
<ClInclude Include="LevelMap.h" />
|
||||
<ClInclude Include="Light.h" />
|
||||
<ClInclude Include="map_reader.h" />
|
||||
<ClInclude Include="MeshRenderer.h" />
|
||||
<ClInclude Include="PhysicsComponent.h" />
|
||||
<ClInclude Include="Player.h" />
|
||||
<ClInclude Include="PlayerInputComponent.h" />
|
||||
<ClInclude Include="PointLight.h" />
|
||||
<ClInclude Include="ResourceManager.h" />
|
||||
<ClInclude Include="Shader.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="map_test.txt" />
|
||||
<Text Include="map_test_2.txt" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
|
||||
@@ -21,6 +21,45 @@
|
||||
<ClCompile Include="main.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="imgui\imgui.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="imgui\imgui_draw.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="imgui\imgui_tables.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="imgui\imgui_widgets.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="imgui\backends\imgui_impl_glfw.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="imgui\backends\imgui_impl_opengl3.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Player.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="MeshRenderer.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Shader.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ResourceManager.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="LevelMap.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Light.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="PointLight.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="fragment.frag" />
|
||||
@@ -29,19 +68,66 @@
|
||||
<None Include="cube.frag" />
|
||||
<None Include="light.vert" />
|
||||
<None Include="light.frag" />
|
||||
<None Include="wall.vert" />
|
||||
<None Include="wall.frag" />
|
||||
<None Include="wall_test.vert" />
|
||||
<None Include="wall_test.frag" />
|
||||
<None Include="point_shadow_depth.vert" />
|
||||
<None Include="point_shadow_depth.frag" />
|
||||
<None Include="point_shadow_depth.geom" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="shader.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="cube.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="camera.h">
|
||||
<ClInclude Include="Camera.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="cubeFactory.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="map_reader.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="GameObject.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Player.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="InputComponent.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="PlayerInputComponent.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="PhysicsComponent.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="GraphicsComponent.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="MeshRenderer.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Shader.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ResourceManager.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="LevelMap.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Light.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="PointLight.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="map_test.txt" />
|
||||
<Text Include="map_test_2.txt" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
275
LevelMap.cpp
Normal file
275
LevelMap.cpp
Normal file
@@ -0,0 +1,275 @@
|
||||
#include "LevelMap.h"
|
||||
|
||||
#include <iostream>
|
||||
|
||||
LevelMap::LevelMap()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
LevelMap::~LevelMap()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void LevelMap::Compile(std::string level_map_code)
|
||||
{
|
||||
std::stringstream level_map_stream(level_map_code);
|
||||
std::string line;
|
||||
|
||||
bool in_sector = false, in_wall = false;
|
||||
|
||||
unsigned int sector_index = 0;
|
||||
unsigned int wall_index = 0;
|
||||
|
||||
while (std::getline(level_map_stream, line))
|
||||
{
|
||||
if (line.empty() || line[0] == '#') continue;
|
||||
|
||||
if (line.find("[SECTOR]") != std::string::npos)
|
||||
{
|
||||
in_sector = true;
|
||||
in_wall = false;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (line.find("[WALL]") != std::string::npos)
|
||||
{
|
||||
in_sector = false;
|
||||
in_wall = true;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (in_sector)
|
||||
{
|
||||
Sector sector = ParseSector(line);
|
||||
sectors.push_back(sector);
|
||||
}
|
||||
|
||||
if (in_wall && !sectors.empty())
|
||||
{
|
||||
Wall wall = ParseWall(line);
|
||||
|
||||
if (wall_index >= sectors[sector_index].number_of_walls)
|
||||
{
|
||||
sector_index++;
|
||||
wall_index = 0;
|
||||
}
|
||||
|
||||
sectors[sector_index].walls.push_back(wall);
|
||||
|
||||
wall_index++;
|
||||
}
|
||||
}
|
||||
|
||||
wall_index = 0;
|
||||
unsigned int floor_index = 0;
|
||||
unsigned int ceiling_index = 0;
|
||||
for (Sector& sector : sectors)
|
||||
{
|
||||
std::vector<glm::vec3> floor_vertices;
|
||||
std::vector<glm::vec3> ceiling_vertices;
|
||||
|
||||
for (Wall& wall : sector.walls)
|
||||
{
|
||||
glm::vec3 floor_vertex(wall.a.x, sector.floor_height, wall.a.y);
|
||||
glm::vec3 ceiling_vertex(wall.a.x, sector.ceiling_height, wall.a.y);
|
||||
|
||||
floor_vertices.push_back(floor_vertex);
|
||||
ceiling_vertices.push_back(ceiling_vertex);
|
||||
|
||||
AddWall(sector, wall, wall_index);
|
||||
}
|
||||
|
||||
AddFloor(sector, floor_vertices);
|
||||
AddCeiling(sector, ceiling_vertices);
|
||||
//AddFloorOrCeiling(sector, floor_vertices, true);
|
||||
//AddFloorOrCeiling(sector, ceiling_vertices, false);
|
||||
}
|
||||
}
|
||||
|
||||
void LevelMap::RenderSetup
|
||||
(
|
||||
Shader *wall_shader,
|
||||
Shader *floor_shader,
|
||||
Shader *ceiling_shader
|
||||
)
|
||||
{
|
||||
wall_renderer.Setup(wall_vertices, wall_normals, wall_colors, wall_indices, wall_shader);
|
||||
floor_renderer.Setup(floor_vertices, floor_normals, floor_colors, floor_indices, floor_shader);
|
||||
ceiling_renderer.Setup(ceiling_vertices, ceiling_normals, ceiling_colors, ceiling_indices, ceiling_shader);
|
||||
}
|
||||
|
||||
void LevelMap::Update(glm::mat4 projection, glm::mat4 view, glm::vec3 light_position, glm::vec3 light_color, glm::vec3 view_position)
|
||||
{
|
||||
wall_renderer.Render(projection, view, light_position, light_color, view_position);
|
||||
floor_renderer.Render(projection, view, light_position, light_color, view_position);
|
||||
ceiling_renderer.Render(projection, view, light_position, light_color, view_position);
|
||||
}
|
||||
|
||||
std::vector<MeshRenderer*> LevelMap::GetMeshes()
|
||||
{
|
||||
return { &wall_renderer, &floor_renderer, &ceiling_renderer };
|
||||
}
|
||||
|
||||
Sector LevelMap::ParseSector(std::string& line)
|
||||
{
|
||||
Sector sector;
|
||||
std::stringstream ss(line);
|
||||
ss >> sector.index >> sector.number_of_walls >> sector.floor_height >> sector.ceiling_height >> sector.outward_facing >> sector.color.x >> sector.color.y >> sector.color.z;
|
||||
|
||||
/*static std::random_device rd; // Obtain a random number from hardware
|
||||
static std::mt19937 eng(rd()); // Seed the generator
|
||||
std::uniform_real_distribution<float> distr(0.0f, 1.0f); // Define the range
|
||||
|
||||
glm::vec3 randomColor(distr(eng), distr(eng), distr(eng));*/
|
||||
|
||||
//sector.color = glm::vec3(sector.index+1 / 5.0f, 0.0f, sector.index+1 / 7.0f);
|
||||
|
||||
return sector;
|
||||
}
|
||||
|
||||
Wall LevelMap::ParseWall(std::string& line)
|
||||
{
|
||||
Wall wall;
|
||||
std::stringstream ss(line);
|
||||
ss >> wall.a.x >> wall.a.y >> wall.b.x >> wall.b.y >> wall.portal;
|
||||
return wall;
|
||||
}
|
||||
|
||||
void LevelMap::AddWall(Sector& sector, Wall& wall, unsigned int& wall_index)
|
||||
{
|
||||
glm::vec3 v0(wall.a.x, sector.floor_height, wall.a.y);
|
||||
glm::vec3 v1(wall.a.x, sector.ceiling_height, wall.a.y);
|
||||
glm::vec3 v2(wall.b.x, sector.ceiling_height, wall.b.y);
|
||||
glm::vec3 v3(wall.b.x, sector.floor_height, wall.b.y);
|
||||
|
||||
glm::vec3 normal = glm::normalize(glm::cross(v1 - v0, v3 - v1));
|
||||
normal = sector.outward_facing ? -normal : normal;
|
||||
|
||||
if (sector.outward_facing)
|
||||
{
|
||||
std::swap(v0, v3);
|
||||
std::swap(v1, v2);
|
||||
}
|
||||
|
||||
if (wall.portal == 0)
|
||||
{
|
||||
AddVertices({ v0, v1, v2, v3 }, wall_vertices);
|
||||
AddNormals({ normal, normal, normal, normal }, wall_normals);
|
||||
AddColors({ sector.color, sector.color, sector.color, sector.color }, wall_colors);
|
||||
AddIndices({ wall_index, wall_index + 1, wall_index + 2, wall_index, wall_index + 2, wall_index + 3 }, wall_indices);
|
||||
wall_index += 4;
|
||||
}
|
||||
else
|
||||
{
|
||||
Sector& portal_sector = sectors[wall.portal - 1];
|
||||
|
||||
if (portal_sector.floor_height > sector.floor_height)
|
||||
{
|
||||
v1.y = portal_sector.floor_height;
|
||||
v2.y = portal_sector.floor_height;
|
||||
|
||||
AddVertices({ v0, v1, v2, v3 }, wall_vertices);
|
||||
AddNormals({ normal, normal, normal, normal }, wall_normals);
|
||||
AddColors({ sector.color, sector.color, sector.color, sector.color }, wall_colors);
|
||||
AddIndices({ wall_index, wall_index + 1, wall_index + 2, wall_index, wall_index + 2, wall_index + 3 }, wall_indices);
|
||||
wall_index += 4;
|
||||
}
|
||||
|
||||
if (portal_sector.ceiling_height < sector.ceiling_height)
|
||||
{
|
||||
v0.y = portal_sector.ceiling_height;
|
||||
v1.y = sector.ceiling_height;
|
||||
v2.y = sector.ceiling_height;
|
||||
v3.y = portal_sector.ceiling_height;;
|
||||
|
||||
AddVertices({ v0, v1, v2, v3 }, wall_vertices);
|
||||
AddNormals({ normal, normal, normal, normal }, wall_normals);
|
||||
AddColors({ sector.color, sector.color, sector.color, sector.color }, wall_colors);
|
||||
AddIndices({ wall_index, wall_index + 1, wall_index + 2, wall_index, wall_index + 2, wall_index + 3 }, wall_indices);
|
||||
wall_index += 4;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void LevelMap::AddFloor(Sector& sector, std::vector<glm::vec3> vertices)
|
||||
{
|
||||
unsigned int starting_index = sector.index;
|
||||
unsigned int _index = starting_index + 1;
|
||||
glm::vec3 normal = glm::vec3(0.0f, 1.0f, 0.0f);
|
||||
|
||||
for (int i = vertices.size() - 1; i >= 0; i--)
|
||||
{
|
||||
AddVertices({ vertices[i] }, floor_vertices);
|
||||
AddNormals({ normal }, floor_normals);
|
||||
AddColors({ glm::vec3(1.0f) - sector.color }, floor_colors);
|
||||
if (_index + 1 < sector.index + sector.number_of_walls)
|
||||
{
|
||||
unsigned int next_index = _index + 1;
|
||||
AddIndices({ starting_index, _index, next_index }, floor_indices);
|
||||
_index++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void LevelMap::AddCeiling(Sector& sector, std::vector<glm::vec3> vertices)
|
||||
{
|
||||
unsigned int starting_index = sector.index;
|
||||
unsigned int _index = starting_index + 1;
|
||||
glm::vec3 normal = glm::vec3(0.0f, 1.0f, 0.0f);
|
||||
normal = -normal;
|
||||
|
||||
for (int i = 0; i < vertices.size(); i++)
|
||||
{
|
||||
AddVertices({ vertices[i] }, ceiling_vertices);
|
||||
AddNormals({ normal }, ceiling_normals);
|
||||
AddColors({ glm::vec3(1.0f) - sector.color }, ceiling_colors);
|
||||
if ( _index + 1 < sector.index + sector.number_of_walls)
|
||||
{
|
||||
unsigned int next_index = _index + 1;
|
||||
AddIndices({ starting_index, _index, next_index }, ceiling_indices);
|
||||
_index++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void LevelMap::AddVertices(std::vector<glm::vec3> vertices, std::vector<float>& target_vertices)
|
||||
{
|
||||
for (unsigned int i = 0; i < vertices.size(); i += 1)
|
||||
{
|
||||
target_vertices.push_back(vertices[i].x);
|
||||
target_vertices.push_back(vertices[i].y);
|
||||
target_vertices.push_back(vertices[i].z);
|
||||
}
|
||||
}
|
||||
|
||||
void LevelMap::AddNormals(std::vector<glm::vec3> normals, std::vector<float>& target_normals)
|
||||
{
|
||||
for (unsigned int i = 0; i < normals.size(); i += 1)
|
||||
{
|
||||
target_normals.push_back(normals[i].x);
|
||||
target_normals.push_back(normals[i].y);
|
||||
target_normals.push_back(normals[i].z);
|
||||
}
|
||||
}
|
||||
|
||||
void LevelMap::AddColors(std::vector<glm::vec3> colors, std::vector<float>& target_colors)
|
||||
{
|
||||
for (unsigned int i = 0; i < colors.size(); i += 1)
|
||||
{
|
||||
target_colors.push_back(colors[i].x);
|
||||
target_colors.push_back(colors[i].y);
|
||||
target_colors.push_back(colors[i].z);
|
||||
}
|
||||
}
|
||||
|
||||
void LevelMap::AddIndices(std::vector<unsigned int> indices, std::vector<unsigned int>& target_indices)
|
||||
{
|
||||
for (unsigned int i = 0; i < indices.size(); i += 1)
|
||||
{
|
||||
target_indices.push_back(indices[i]);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
94
LevelMap.h
Normal file
94
LevelMap.h
Normal file
@@ -0,0 +1,94 @@
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
#include <sstream>
|
||||
#include <random>
|
||||
|
||||
#include <glm/glm.hpp>
|
||||
|
||||
#include "MeshRenderer.h"
|
||||
|
||||
struct Wall
|
||||
{
|
||||
glm::vec2 a, b;
|
||||
int portal;
|
||||
};
|
||||
|
||||
struct Sector
|
||||
{
|
||||
unsigned int index;
|
||||
unsigned int number_of_walls;
|
||||
|
||||
float floor_height;
|
||||
float ceiling_height;
|
||||
|
||||
bool outward_facing;
|
||||
|
||||
glm::vec3 color;
|
||||
|
||||
std::vector<Wall> walls;
|
||||
};
|
||||
|
||||
class LevelMap
|
||||
{
|
||||
public:
|
||||
LevelMap();
|
||||
~LevelMap();
|
||||
|
||||
void Compile(std::string level_map_code);
|
||||
|
||||
void RenderSetup
|
||||
(
|
||||
Shader *wall_shader,
|
||||
Shader *floor_shader,
|
||||
Shader *ceiling_shader
|
||||
);
|
||||
|
||||
void Update
|
||||
(
|
||||
glm::mat4 projection,
|
||||
glm::mat4 view,
|
||||
glm::vec3 light_position,
|
||||
glm::vec3 light_color,
|
||||
glm::vec3 view_position
|
||||
);
|
||||
|
||||
std::vector<MeshRenderer*> GetMeshes();
|
||||
private:
|
||||
std::vector<Sector> sectors;
|
||||
|
||||
std::vector<float> wall_vertices;
|
||||
std::vector<float> wall_normals;
|
||||
std::vector<float> wall_colors;
|
||||
std::vector<unsigned int> wall_indices;
|
||||
MeshRenderer wall_renderer;
|
||||
Shader wall_shader;
|
||||
|
||||
std::vector<float> floor_vertices;
|
||||
std::vector<float> floor_normals;
|
||||
std::vector<float> floor_colors;
|
||||
std::vector<unsigned int> floor_indices;
|
||||
MeshRenderer floor_renderer;
|
||||
Shader floor_shader;
|
||||
|
||||
std::vector<float> ceiling_vertices;
|
||||
std::vector<float> ceiling_normals;
|
||||
std::vector<float> ceiling_colors;
|
||||
std::vector<unsigned int> ceiling_indices;
|
||||
MeshRenderer ceiling_renderer;
|
||||
Shader ceiling_shader;
|
||||
|
||||
Sector ParseSector(std::string& line);
|
||||
Wall ParseWall(std::string& line);
|
||||
|
||||
void AddWall(Sector& sector, Wall& wall, unsigned int& wall_index);
|
||||
|
||||
void AddFloor(Sector& sector, std::vector<glm::vec3> vertices);
|
||||
void AddCeiling(Sector& sector, std::vector<glm::vec3> vertices);
|
||||
|
||||
void AddVertices(std::vector<glm::vec3> vertices, std::vector<float>& target_vertices);
|
||||
void AddNormals(std::vector<glm::vec3> normals, std::vector<float>& target_normals);
|
||||
void AddColors(std::vector<glm::vec3> colors, std::vector<float>& target_colors);
|
||||
void AddIndices(std::vector<unsigned int> indices, std::vector<unsigned int>& target_indices);
|
||||
};
|
||||
|
||||
240
MeshRenderer.cpp
Normal file
240
MeshRenderer.cpp
Normal file
@@ -0,0 +1,240 @@
|
||||
#include <MeshRenderer.h>
|
||||
|
||||
#include <iostream>
|
||||
|
||||
// when creating a meshrenderer the important question is "do all these vertices share the same shader?"
|
||||
|
||||
MeshRenderer::MeshRenderer()
|
||||
{
|
||||
}
|
||||
|
||||
MeshRenderer::~MeshRenderer()
|
||||
{
|
||||
glDeleteVertexArrays(1, &this->VAO);
|
||||
}
|
||||
|
||||
void MeshRenderer::Setup
|
||||
(
|
||||
std::vector<float> vertices,
|
||||
std::vector<float> normals,
|
||||
std::vector<float> colors,
|
||||
std::vector<unsigned int> indices,
|
||||
Shader* lit_shader
|
||||
)
|
||||
{
|
||||
this->vertices = vertices;
|
||||
this->normals = normals;
|
||||
this->colors = colors;
|
||||
this->indices = indices;
|
||||
this->lit_shader = lit_shader;
|
||||
this->shadow_shader = shadow_shader;
|
||||
|
||||
this->SetupBuffers();
|
||||
|
||||
//if (shadow_shader != nullptr)
|
||||
//{
|
||||
// //std::cout << "Setup lighting" << std::endl;
|
||||
// this->SetupLighting();
|
||||
//}
|
||||
|
||||
}
|
||||
|
||||
void MeshRenderer::Render(Shader &shader)
|
||||
{
|
||||
//std::cout << "Rendering with Shader: " << shader.ID << std::endl;
|
||||
shader.Use();
|
||||
glm::mat4 model = glm::mat4(1.0f);
|
||||
shader.SetMatrix4("model", model);
|
||||
|
||||
glBindVertexArray(this->VAO);
|
||||
|
||||
//std::cout << this->indices.size() << std::endl;
|
||||
glDrawElements(GL_TRIANGLES, this->indices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
}
|
||||
|
||||
void MeshRenderer::Render
|
||||
(
|
||||
glm::mat4 projection,
|
||||
glm::mat4 view,
|
||||
glm::vec3 light_position,
|
||||
glm::vec3 light_color,
|
||||
glm::vec3 view_position
|
||||
)
|
||||
{
|
||||
glm::mat4 model = glm::mat4(1.0f);
|
||||
|
||||
//glEnable(GL_CULL_FACE);
|
||||
//glCullFace(GL_BACK);
|
||||
|
||||
//if (shadow_shader != nullptr)
|
||||
//{
|
||||
// this->shader = shadow_shader;
|
||||
// RenderShadows(projection, view, model, light_position);
|
||||
//}
|
||||
|
||||
this->shader = lit_shader;
|
||||
RenderObject(projection, view, model, light_position, light_color, view_position);
|
||||
}
|
||||
|
||||
void MeshRenderer::Render
|
||||
(
|
||||
glm::mat4 projection,
|
||||
glm::mat4 view,
|
||||
glm::vec3 light_position,
|
||||
glm::vec3 light_color,
|
||||
glm::vec3 view_position,
|
||||
glm::vec3 position,
|
||||
glm::vec3 scale,
|
||||
glm::vec3 rotation
|
||||
)
|
||||
{
|
||||
glm::mat4 model = glm::mat4(1.0f);
|
||||
model = glm::translate(model, position);
|
||||
model = glm::rotate(model, glm::radians(rotation.x), glm::vec3(1, 0, 0));
|
||||
model = glm::rotate(model, glm::radians(rotation.y), glm::vec3(0, 1, 0));
|
||||
model = glm::rotate(model, glm::radians(rotation.z), glm::vec3(0, 0, 1));
|
||||
model = glm::scale(model, scale);
|
||||
|
||||
if (shadow_shader != nullptr)
|
||||
{
|
||||
this->lit_shader = shadow_shader;
|
||||
RenderShadows(projection, view, model, light_position);
|
||||
}
|
||||
this->shader = lit_shader;
|
||||
|
||||
RenderObject(projection, view, model, light_position, light_color, view_position);
|
||||
}
|
||||
|
||||
void MeshRenderer::SetupBuffers()
|
||||
{
|
||||
/*for (int i = 0; i < this->normals.size(); i += 3)
|
||||
{
|
||||
std::cout << this->normals[i] << " " << this->normals[i + 1] << " " << this->normals[i + 2] << std::endl;
|
||||
}*/
|
||||
glGenVertexArrays(1, &this->VAO);
|
||||
|
||||
unsigned int VBO, NBO, CBO, EBO;
|
||||
|
||||
glGenBuffers(1, &VBO);
|
||||
glGenBuffers(1, &NBO);
|
||||
glGenBuffers(1, &CBO);
|
||||
glGenBuffers(1, &EBO);
|
||||
|
||||
glBindVertexArray(this->VAO);
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, VBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, this->vertices.size() * sizeof(float), this->vertices.data(), GL_STATIC_DRAW);
|
||||
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
|
||||
glEnableVertexAttribArray(0);
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, NBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, this->normals.size() * sizeof(float), this->normals.data(), GL_STATIC_DRAW);
|
||||
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
|
||||
glEnableVertexAttribArray(1);
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, CBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, this->colors.size() * sizeof(float), this->colors.data(), GL_STATIC_DRAW);
|
||||
glVertexAttribPointer(2, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
|
||||
glEnableVertexAttribArray(2);
|
||||
|
||||
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO);
|
||||
glBufferData(GL_ELEMENT_ARRAY_BUFFER, this->indices.size() * sizeof(unsigned int), this->indices.data(), GL_STATIC_DRAW);
|
||||
|
||||
glBindVertexArray(0);
|
||||
}
|
||||
|
||||
void MeshRenderer::SetupLighting()
|
||||
{
|
||||
/*glGenFramebuffers(1, &depth_map_FBO);
|
||||
glGenTextures(1, &depth_map);
|
||||
|
||||
for (unsigned int i = 0; i < 6; i++)
|
||||
{
|
||||
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_DEPTH_COMPONENT, SHADOW_WIDTH, SHADOW_HEIGHT, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL);
|
||||
}
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
|
||||
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, depth_map_FBO);
|
||||
glFramebufferTexture(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, depth_map, 0);
|
||||
glDrawBuffer(GL_NONE);
|
||||
glReadBuffer(GL_NONE);
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, 0);*/
|
||||
}
|
||||
|
||||
void MeshRenderer::RenderObject
|
||||
(
|
||||
glm::mat4 projection,
|
||||
glm::mat4 view,
|
||||
glm::mat4 model,
|
||||
glm::vec3 light_position,
|
||||
glm::vec3 light_color,
|
||||
glm::vec3 view_position
|
||||
)
|
||||
{
|
||||
this->shader->Use();
|
||||
this->shader->SetMatrix4("projection", projection);
|
||||
this->shader->SetMatrix4("view", view);
|
||||
this->shader->SetMatrix4("model", model);
|
||||
this->shader->SetVector3f("lightPos", light_position);
|
||||
this->shader->SetVector3f("lightColor", light_color);
|
||||
this->shader->SetVector3f("viewPos", view_position);
|
||||
this->shader->SetFloat("far_plane", 25.0f);
|
||||
|
||||
glBindVertexArray(this->VAO);
|
||||
|
||||
glDrawElements(GL_TRIANGLES, this->indices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
}
|
||||
|
||||
void MeshRenderer::RenderShadows(glm::mat4 projection, glm::mat4 view, glm::mat4 model, glm::vec3 light_position)
|
||||
{
|
||||
this->shader->Use();
|
||||
this->shader->SetMatrix4("projection", projection);
|
||||
this->shader->SetMatrix4("view", view);
|
||||
this->shader->SetMatrix4("model", model);
|
||||
float near_plane = 1.0f;
|
||||
float far_plane = 50.0f;
|
||||
|
||||
glm::mat4 shadowProj = glm::perspective(glm::radians(90.0f), (float)SHADOW_WIDTH / (float)SHADOW_HEIGHT, near_plane, far_plane);
|
||||
std::vector<glm::mat4> shadowTransforms;
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(light_position, light_position + glm::vec3(1.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(light_position, light_position + glm::vec3(-1.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(light_position, light_position + glm::vec3(0.0f, 1.0f, 0.0f), glm::vec3(0.0f, 0.0f, 1.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(light_position, light_position + glm::vec3(0.0f, -1.0f, 0.0f), glm::vec3(0.0f, 0.0f, -1.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(light_position, light_position + glm::vec3(0.0f, 0.0f, 1.0f), glm::vec3(0.0f, -1.0f, 0.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(light_position, light_position + glm::vec3(0.0f, 0.0f, -1.0f), glm::vec3(0.0f, -1.0f, 0.0f)));
|
||||
|
||||
glViewport(0, 0, SHADOW_WIDTH, SHADOW_HEIGHT);
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, depth_map_FBO);
|
||||
//glClear(GL_DEPTH_BUFFER_BIT);
|
||||
|
||||
for (unsigned int i = 0; i < 6; ++i)
|
||||
{
|
||||
std::string matrix_name = "shadowMatrices[" + std::to_string(i) + "]";
|
||||
this->shader->SetMatrix4(matrix_name.c_str(), shadowTransforms[i]);
|
||||
}
|
||||
this->shader->SetFloat("far_plane", far_plane);
|
||||
this->shader->SetVector3f("lightPos", light_position);
|
||||
|
||||
glBindVertexArray(this->VAO);
|
||||
|
||||
glDrawElements(GL_TRIANGLES, this->indices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, 0);
|
||||
|
||||
glViewport(0, 0, SCR_WIDTH, SCR_HEIGHT);
|
||||
//glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
glBindTexture(GL_TEXTURE_CUBE_MAP, depth_map);
|
||||
}
|
||||
|
||||
|
||||
56
MeshRenderer.h
Normal file
56
MeshRenderer.h
Normal file
@@ -0,0 +1,56 @@
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
|
||||
#include <glad/glad.h>
|
||||
#include <GLFW/glfw3.h>
|
||||
#include <glm/glm.hpp>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
#include <glm/gtc/type_ptr.hpp>
|
||||
|
||||
#include "Shader.h"
|
||||
|
||||
class MeshRenderer
|
||||
{
|
||||
public:
|
||||
MeshRenderer();
|
||||
~MeshRenderer();
|
||||
|
||||
void Setup
|
||||
(
|
||||
std::vector<float> vertices,
|
||||
std::vector<float> normals,
|
||||
std::vector<float> colors,
|
||||
std::vector<unsigned int> indices,
|
||||
Shader* lit_shader
|
||||
);
|
||||
|
||||
void Render(Shader &shader);
|
||||
|
||||
void Render(glm::mat4 projection, glm::mat4 view, glm::vec3 light_position, glm::vec3 light_color, glm::vec3 view_position);
|
||||
void Render(glm::mat4 projection, glm::mat4 view, glm::vec3 light_position, glm::vec3 light_color, glm::vec3 view_position, glm::vec3 position, glm::vec3 scale, glm::vec3 rotation);
|
||||
private:
|
||||
std::vector<float> vertices;
|
||||
std::vector<float> normals;
|
||||
std::vector<float> colors;
|
||||
std::vector<unsigned int> indices;
|
||||
|
||||
unsigned int VAO;
|
||||
unsigned int depth_map;
|
||||
unsigned int depth_map_FBO;
|
||||
|
||||
unsigned int SHADOW_WIDTH = 1024, SHADOW_HEIGHT = 1024;
|
||||
int SCR_WIDTH = 1600;
|
||||
int SCR_HEIGHT = 900;
|
||||
|
||||
Shader *shader;
|
||||
Shader *lit_shader;
|
||||
Shader *shadow_shader;
|
||||
|
||||
void SetupBuffers();
|
||||
void SetupLighting();
|
||||
|
||||
void RenderObject(glm::mat4 projection, glm::mat4 view, glm::mat4 model, glm::vec3 light_position, glm::vec3 light_color, glm::vec3 view_position);
|
||||
void RenderShadows(glm::mat4 projection, glm::mat4 view, glm::mat4 model, glm::vec3 light_position);
|
||||
};
|
||||
|
||||
8
PhysicsComponent.h
Normal file
8
PhysicsComponent.h
Normal file
@@ -0,0 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
class PhysicsComponent
|
||||
{
|
||||
public:
|
||||
virtual ~PhysicsComponent() {};
|
||||
virtual void Update() = 0;
|
||||
};
|
||||
64
Player.cpp
Normal file
64
Player.cpp
Normal file
@@ -0,0 +1,64 @@
|
||||
#include "Player.h"
|
||||
#include "Camera.h"
|
||||
#include <iostream>
|
||||
|
||||
Player::Player(glm::vec3 Position, glm::vec3 Rotation)
|
||||
: GameObject(Position, Rotation, glm::vec3(1.0f, 1.0f, 1.0f)),
|
||||
PlayerCamera(new Camera(glm::vec3(0.0f, 1.0f, 0.0f)))
|
||||
{
|
||||
|
||||
PlayerCamera->Position = Position + PlayerCamera->CameraOffset;
|
||||
PlayerCamera->WorldUp = this->WorldUp;
|
||||
std::cout << "{" << Position.x << ", " << Position.y << ", " << Position.z << "}" << std::endl;
|
||||
std::cout << "{" << PlayerCamera->Position.x << ", " << PlayerCamera->Position.y << ", " << PlayerCamera->Position.z << "}" << std::endl;
|
||||
}
|
||||
|
||||
void Player::Update()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void Player::ProcessKeyboard(EInputDirection Direction, float Delta)
|
||||
{
|
||||
float Velocity = bIsRunning ? RunSpeed : WalkSpeed;
|
||||
Velocity = Velocity * Delta;
|
||||
if (Direction == FORWARD)
|
||||
Position += Front * Velocity;
|
||||
if (Direction == BACKWARD)
|
||||
Position -= Front * Velocity;
|
||||
if (Direction == LEFT)
|
||||
Position -= Right * Velocity;
|
||||
if (Direction == RIGHT)
|
||||
Position += Right * Velocity;
|
||||
|
||||
PlayerCamera->Position = Position + PlayerCamera->CameraOffset;
|
||||
PlayerCamera->WorldUp = this->WorldUp;
|
||||
}
|
||||
|
||||
void Player::ProcessMouseMovement(float XOffset, float YOffset, GLboolean bConstrainPitch)
|
||||
{
|
||||
XOffset *= MOUSE_SENSITIVITY;
|
||||
YOffset *= MOUSE_SENSITIVITY;
|
||||
|
||||
Yaw += XOffset;
|
||||
PlayerCamera->Yaw = Yaw;
|
||||
|
||||
PlayerCamera->ProcessMouseMovement(XOffset, YOffset);
|
||||
UpdatePlayerVectors();
|
||||
}
|
||||
|
||||
glm::mat4 Player::GetViewMatrix() const
|
||||
{
|
||||
return PlayerCamera->GetViewMatrix();
|
||||
}
|
||||
|
||||
void Player::UpdatePlayerVectors()
|
||||
{
|
||||
glm::vec3 UpdatedFront;
|
||||
UpdatedFront.x = cos(glm::radians(Yaw)) * cos(0);
|
||||
UpdatedFront.y = sin(0);
|
||||
UpdatedFront.z = sin(glm::radians(Yaw)) * cos(0);
|
||||
Front = glm::normalize(UpdatedFront);
|
||||
Right = glm::normalize(glm::cross(Front, WorldUp));
|
||||
Up = glm::normalize(glm::cross(Right, Front));
|
||||
}
|
||||
43
Player.h
Normal file
43
Player.h
Normal file
@@ -0,0 +1,43 @@
|
||||
#pragma once
|
||||
|
||||
#include <glad/glad.h>
|
||||
#include <glm/glm.hpp>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
#include <GameObject.h>
|
||||
#include <Camera.h>
|
||||
|
||||
|
||||
enum EInputDirection
|
||||
{
|
||||
FORWARD,
|
||||
BACKWARD,
|
||||
LEFT,
|
||||
RIGHT
|
||||
};
|
||||
|
||||
class Player : public GameObject
|
||||
{
|
||||
public:
|
||||
Player(glm::vec3 Position, glm::vec3 Rotation);
|
||||
~Player() = default;
|
||||
|
||||
void Update();
|
||||
|
||||
void ProcessKeyboard(EInputDirection Direction, float Delta);
|
||||
void ProcessMouseMovement(float XOffset, float YOffset, GLboolean ConstrainPitch = true);
|
||||
glm::mat4 GetViewMatrix() const;
|
||||
|
||||
private:
|
||||
Camera* PlayerCamera;
|
||||
float Yaw;
|
||||
float MouseSensitivity;
|
||||
|
||||
float WalkSpeed = 5.0f;
|
||||
float RunSpeed = 15.0f;
|
||||
|
||||
bool bIsRunning = false;
|
||||
|
||||
void UpdatePlayerVectors();
|
||||
|
||||
};
|
||||
|
||||
22
PlayerInputComponent.h
Normal file
22
PlayerInputComponent.h
Normal file
@@ -0,0 +1,22 @@
|
||||
#pragma once
|
||||
|
||||
#include <InputComponent.h>
|
||||
|
||||
enum EInputDirection
|
||||
{
|
||||
FORWARD,
|
||||
BACKWARD,
|
||||
LEFT,
|
||||
RIGHT
|
||||
};
|
||||
|
||||
class PlayerInputComponent : public InputComponent
|
||||
{
|
||||
private:
|
||||
|
||||
public:
|
||||
virtual void Update(float deltaTime)
|
||||
{
|
||||
|
||||
}
|
||||
};
|
||||
1
PointLight.cpp
Normal file
1
PointLight.cpp
Normal file
@@ -0,0 +1 @@
|
||||
#include "PointLight.h"
|
||||
115
PointLight.h
Normal file
115
PointLight.h
Normal file
@@ -0,0 +1,115 @@
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
#include <iostream>
|
||||
|
||||
#include <glm/glm.hpp>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
#include <glad/glad.h>
|
||||
#include <GLFW/glfw3.h>
|
||||
|
||||
#include "Shader.h"
|
||||
#include "MeshRenderer.h"
|
||||
|
||||
#define SHADOW_WIDTH 1024
|
||||
#define SHADOW_HEIGHT 1024
|
||||
|
||||
class PointLight
|
||||
{
|
||||
public:
|
||||
unsigned int depth_map, depth_map_FBO;
|
||||
float near_plane = 1.0f,
|
||||
far_plane = 100.0f,
|
||||
ambient_intensity = 0.5f,
|
||||
diffuse_intensity = 1.0f,
|
||||
attenuation_constant = 1.0f,
|
||||
attenuation_linear = 0.09f,
|
||||
attenuation_exponential = 0.032f;
|
||||
glm::vec3 Position;
|
||||
glm::vec3 color;
|
||||
Shader shader;
|
||||
|
||||
PointLight(glm::vec3 position, glm::vec3 color, Shader shader)
|
||||
{
|
||||
this->Position = position;
|
||||
this->color = color;
|
||||
this->shader = shader;
|
||||
SetupLighting();
|
||||
}
|
||||
|
||||
void RenderSceneShadows(std::vector<MeshRenderer*> meshes)
|
||||
{
|
||||
glm::mat4 shadowProj = glm::perspective(glm::radians(90.0f), (float)SHADOW_WIDTH / (float)SHADOW_HEIGHT, near_plane, far_plane);
|
||||
std::vector<glm::mat4> shadowTransforms;
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(Position, Position + glm::vec3(1.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f))); // Right
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(Position, Position + glm::vec3(-1.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f))); // Left
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(Position, Position + glm::vec3(0.0f, 1.0f, 0.0f), glm::vec3(0.0f, 0.0f, 1.0f))); // Up
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(Position, Position + glm::vec3(0.0f, -1.0f, 0.0f), glm::vec3(0.0f, 0.0f, -1.0f))); // Down
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(Position, Position + glm::vec3(0.0f, 0.0f, 1.0f), glm::vec3(0.0f, -1.0f, 0.0f))); // Forward
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(Position, Position + glm::vec3(0.0f, 0.0f, -1.0f), glm::vec3(0.0f, -1.0f, 0.0f))); // Backward
|
||||
|
||||
glEnable(GL_CULL_FACE);
|
||||
|
||||
glCullFace(GL_FRONT);
|
||||
|
||||
glEnable(GL_DEPTH_TEST);
|
||||
glDepthMask(GL_TRUE);
|
||||
glViewport(0, 0, SHADOW_WIDTH, SHADOW_HEIGHT);
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, depth_map_FBO);
|
||||
glClear(GL_DEPTH_BUFFER_BIT);
|
||||
shader.Use();
|
||||
for (unsigned int i = 0; i < 6; ++i)
|
||||
{
|
||||
std::string matrix_name = "shadowMatrices[" + std::to_string(i) + "]";
|
||||
shader.SetMatrix4(matrix_name.c_str(), shadowTransforms[i]);
|
||||
}
|
||||
shader.SetFloat("farPlane", far_plane);
|
||||
shader.SetVector3f("lightPosition", Position);
|
||||
|
||||
for (MeshRenderer* mesh : meshes)
|
||||
{
|
||||
mesh->Render(shader);
|
||||
}
|
||||
|
||||
if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)
|
||||
{
|
||||
std::cout << "Framebuffer not complete!" << std::endl;
|
||||
}
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, 0);
|
||||
|
||||
glCullFace(GL_BACK);
|
||||
|
||||
}
|
||||
private:
|
||||
|
||||
void SetupLighting()
|
||||
{
|
||||
//std::cout << "SetupLighting" << std::endl;
|
||||
glGenFramebuffers(1, &depth_map_FBO);
|
||||
glGenTextures(1, &depth_map);
|
||||
glBindTexture(GL_TEXTURE_CUBE_MAP, depth_map);
|
||||
|
||||
for (unsigned int i = 0; i < 6; i++)
|
||||
{
|
||||
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_DEPTH_COMPONENT, SHADOW_WIDTH, SHADOW_HEIGHT, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL);
|
||||
}
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
|
||||
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, depth_map_FBO);
|
||||
glFramebufferTexture(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, depth_map, 0);
|
||||
glDrawBuffer(GL_NONE);
|
||||
glReadBuffer(GL_NONE);
|
||||
|
||||
if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)
|
||||
{
|
||||
std::cout << "Framebuffer not complete!" << std::endl;
|
||||
}
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, 0);
|
||||
}
|
||||
};
|
||||
|
||||
102
ResourceManager.cpp
Normal file
102
ResourceManager.cpp
Normal file
@@ -0,0 +1,102 @@
|
||||
#include "ResourceManager.h"
|
||||
|
||||
#include <string>
|
||||
#include <iostream>
|
||||
#include <sstream>
|
||||
#include <fstream>
|
||||
|
||||
// Instantiate static variables
|
||||
std::map<std::string, Shader> ResourceManager::shaders;
|
||||
std::map<std::string, LevelMap> ResourceManager::levelMaps;
|
||||
|
||||
|
||||
Shader ResourceManager::LoadShader(const char* vShaderFile, const char* fShaderFile, const char* gShaderFile, std::string name)
|
||||
{
|
||||
shaders[name] = LoadShaderFromFile(vShaderFile, fShaderFile, gShaderFile);
|
||||
return shaders[name];
|
||||
}
|
||||
|
||||
Shader ResourceManager::GetShader(std::string name)
|
||||
{
|
||||
return shaders[name];
|
||||
}
|
||||
|
||||
void ResourceManager::Clear()
|
||||
{
|
||||
// (properly) delete all shaders
|
||||
for (auto iter : shaders)
|
||||
glDeleteProgram(iter.second.ID);
|
||||
}
|
||||
|
||||
Shader ResourceManager::LoadShaderFromFile(const char* vShaderFile, const char* fShaderFile, const char* gShaderFile)
|
||||
{
|
||||
// 1. retrieve the vertex/fragment source code from filePath
|
||||
std::string vertexCode;
|
||||
std::string fragmentCode;
|
||||
std::string geometryCode;
|
||||
try
|
||||
{
|
||||
// open files
|
||||
std::ifstream vertexShaderFile(vShaderFile);
|
||||
std::ifstream fragmentShaderFile(fShaderFile);
|
||||
std::stringstream vShaderStream, fShaderStream;
|
||||
// read file's buffer contents into streams
|
||||
vShaderStream << vertexShaderFile.rdbuf();
|
||||
fShaderStream << fragmentShaderFile.rdbuf();
|
||||
// close file handlers
|
||||
vertexShaderFile.close();
|
||||
fragmentShaderFile.close();
|
||||
// convert stream into string
|
||||
vertexCode = vShaderStream.str();
|
||||
fragmentCode = fShaderStream.str();
|
||||
// if geometry shader path is present, also load a geometry shader
|
||||
if (gShaderFile != nullptr)
|
||||
{
|
||||
std::ifstream geometryShaderFile(gShaderFile);
|
||||
std::stringstream gShaderStream;
|
||||
gShaderStream << geometryShaderFile.rdbuf();
|
||||
geometryShaderFile.close();
|
||||
geometryCode = gShaderStream.str();
|
||||
}
|
||||
}
|
||||
catch (std::exception e)
|
||||
{
|
||||
std::cout << "ERROR::SHADER: Failed to read shader files" << std::endl;
|
||||
}
|
||||
const char* vShaderCode = vertexCode.c_str();
|
||||
const char* fShaderCode = fragmentCode.c_str();
|
||||
const char* gShaderCode = geometryCode.c_str();
|
||||
// 2. now create shader object from source code
|
||||
Shader shader;
|
||||
shader.Compile(vShaderCode, fShaderCode, gShaderFile != nullptr ? gShaderCode : nullptr);
|
||||
return shader;
|
||||
}
|
||||
|
||||
LevelMap ResourceManager::LoadLevelMap(const char* filePath, std::string name)
|
||||
{
|
||||
levelMaps[name] = LoadLevelMapFromFile(filePath);
|
||||
return levelMaps[name];
|
||||
}
|
||||
|
||||
LevelMap ResourceManager::LoadLevelMapFromFile(const char* filePath)
|
||||
{
|
||||
std::string level_map_code;
|
||||
try
|
||||
{
|
||||
std::ifstream level_map_file(filePath);
|
||||
std::stringstream level_map_stream;
|
||||
|
||||
level_map_stream << level_map_file.rdbuf();
|
||||
|
||||
level_map_file.close();
|
||||
|
||||
level_map_code = level_map_stream.str();
|
||||
}
|
||||
catch (std::exception e)
|
||||
{
|
||||
std::cout << "ERROR::LEVELMAP: Failed to read level map file: " << filePath << std::endl;
|
||||
}
|
||||
LevelMap level_map;
|
||||
level_map.Compile(level_map_code);
|
||||
return level_map;
|
||||
}
|
||||
33
ResourceManager.h
Normal file
33
ResourceManager.h
Normal file
@@ -0,0 +1,33 @@
|
||||
#pragma once
|
||||
|
||||
#include <map>
|
||||
#include <string>
|
||||
|
||||
#include <glad/glad.h>
|
||||
|
||||
#include "Shader.h"
|
||||
#include "LevelMap.h"
|
||||
|
||||
class ResourceManager
|
||||
{
|
||||
public:
|
||||
// resource storage
|
||||
static std::map<std::string, Shader> shaders;
|
||||
static std::map<std::string, LevelMap> levelMaps;
|
||||
// loads (and generates) a shader program from file loading vertex, fragment (and geometry) shader's source code. If gShaderFile is not nullptr, it also loads a geometry shader
|
||||
static Shader LoadShader(const char* vShaderFile, const char* fShaderFile, const char* gShaderFile, std::string name);
|
||||
// retrieves a stored sader
|
||||
static Shader GetShader(std::string name);
|
||||
// properly de-allocates all loaded resources
|
||||
static void Clear();
|
||||
|
||||
static LevelMap LoadLevelMap(const char* filePath, std::string name);
|
||||
private:
|
||||
// private constructor, that is we do not want any actual resource manager objects. Its members and functions should be publicly available (static).
|
||||
ResourceManager() { }
|
||||
// loads and generates a shader from file
|
||||
static Shader LoadShaderFromFile(const char* vShaderFile, const char* fShaderFile, const char* gShaderFile = nullptr);
|
||||
|
||||
static LevelMap LoadLevelMapFromFile(const char* filePath);
|
||||
};
|
||||
|
||||
129
Shader.cpp
Normal file
129
Shader.cpp
Normal file
@@ -0,0 +1,129 @@
|
||||
#include "Shader.h"
|
||||
|
||||
#include <iostream>
|
||||
|
||||
Shader& Shader::Use()
|
||||
{
|
||||
glUseProgram(this->ID);
|
||||
return *this;
|
||||
}
|
||||
|
||||
void Shader::Compile(const char* vertexSource, const char* fragmentSource, const char* geometrySource)
|
||||
{
|
||||
unsigned int sVertex, sFragment, gShader;
|
||||
// vertex Shader
|
||||
sVertex = glCreateShader(GL_VERTEX_SHADER);
|
||||
glShaderSource(sVertex, 1, &vertexSource, NULL);
|
||||
glCompileShader(sVertex);
|
||||
checkCompileErrors(sVertex, "VERTEX");
|
||||
// fragment Shader
|
||||
sFragment = glCreateShader(GL_FRAGMENT_SHADER);
|
||||
glShaderSource(sFragment, 1, &fragmentSource, NULL);
|
||||
glCompileShader(sFragment);
|
||||
checkCompileErrors(sFragment, "FRAGMENT");
|
||||
// if geometry shader source code is given, also compile geometry shader
|
||||
if (geometrySource != nullptr)
|
||||
{
|
||||
gShader = glCreateShader(GL_GEOMETRY_SHADER);
|
||||
glShaderSource(gShader, 1, &geometrySource, NULL);
|
||||
glCompileShader(gShader);
|
||||
checkCompileErrors(gShader, "GEOMETRY");
|
||||
}
|
||||
// shader program
|
||||
this->ID = glCreateProgram();
|
||||
glAttachShader(this->ID, sVertex);
|
||||
glAttachShader(this->ID, sFragment);
|
||||
if (geometrySource != nullptr)
|
||||
glAttachShader(this->ID, gShader);
|
||||
glLinkProgram(this->ID);
|
||||
checkCompileErrors(this->ID, "PROGRAM");
|
||||
// delete the shaders as they're linked into our program now and no longer necessary
|
||||
glDeleteShader(sVertex);
|
||||
glDeleteShader(sFragment);
|
||||
if (geometrySource != nullptr)
|
||||
glDeleteShader(gShader);
|
||||
}
|
||||
|
||||
void Shader::SetFloat(const char* name, float value, bool useShader)
|
||||
{
|
||||
if (useShader)
|
||||
this->Use();
|
||||
glUniform1f(glGetUniformLocation(this->ID, name), value);
|
||||
}
|
||||
void Shader::SetInteger(const char* name, int value, bool useShader)
|
||||
{
|
||||
if (useShader)
|
||||
this->Use();
|
||||
glUniform1i(glGetUniformLocation(this->ID, name), value);
|
||||
}
|
||||
void Shader::SetVector2f(const char* name, float x, float y, bool useShader)
|
||||
{
|
||||
if (useShader)
|
||||
this->Use();
|
||||
glUniform2f(glGetUniformLocation(this->ID, name), x, y);
|
||||
}
|
||||
void Shader::SetVector2f(const char* name, const glm::vec2& value, bool useShader)
|
||||
{
|
||||
if (useShader)
|
||||
this->Use();
|
||||
glUniform2f(glGetUniformLocation(this->ID, name), value.x, value.y);
|
||||
}
|
||||
void Shader::SetVector3f(const char* name, float x, float y, float z, bool useShader)
|
||||
{
|
||||
if (useShader)
|
||||
this->Use();
|
||||
glUniform3f(glGetUniformLocation(this->ID, name), x, y, z);
|
||||
}
|
||||
void Shader::SetVector3f(const char* name, const glm::vec3& value, bool useShader)
|
||||
{
|
||||
if (useShader)
|
||||
this->Use();
|
||||
glUniform3f(glGetUniformLocation(this->ID, name), value.x, value.y, value.z);
|
||||
}
|
||||
void Shader::SetVector4f(const char* name, float x, float y, float z, float w, bool useShader)
|
||||
{
|
||||
if (useShader)
|
||||
this->Use();
|
||||
glUniform4f(glGetUniformLocation(this->ID, name), x, y, z, w);
|
||||
}
|
||||
void Shader::SetVector4f(const char* name, const glm::vec4& value, bool useShader)
|
||||
{
|
||||
if (useShader)
|
||||
this->Use();
|
||||
glUniform4f(glGetUniformLocation(this->ID, name), value.x, value.y, value.z, value.w);
|
||||
}
|
||||
void Shader::SetMatrix4(const char* name, const glm::mat4& matrix, bool useShader)
|
||||
{
|
||||
if (useShader)
|
||||
this->Use();
|
||||
glUniformMatrix4fv(glGetUniformLocation(this->ID, name), 1, false, glm::value_ptr(matrix));
|
||||
}
|
||||
|
||||
|
||||
void Shader::checkCompileErrors(unsigned int object, std::string type)
|
||||
{
|
||||
int success;
|
||||
char infoLog[1024];
|
||||
if (type != "PROGRAM")
|
||||
{
|
||||
glGetShaderiv(object, GL_COMPILE_STATUS, &success);
|
||||
if (!success)
|
||||
{
|
||||
glGetShaderInfoLog(object, 1024, NULL, infoLog);
|
||||
std::cout << "| ERROR::SHADER: Compile-time error: Type: " << type << "\n"
|
||||
<< infoLog << "\n -- --------------------------------------------------- -- "
|
||||
<< std::endl;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
glGetProgramiv(object, GL_LINK_STATUS, &success);
|
||||
if (!success)
|
||||
{
|
||||
glGetProgramInfoLog(object, 1024, NULL, infoLog);
|
||||
std::cout << "| ERROR::Shader: Link-time error: Type: " << type << "\n"
|
||||
<< infoLog << "\n -- --------------------------------------------------- -- "
|
||||
<< std::endl;
|
||||
}
|
||||
}
|
||||
}
|
||||
37
camera.h
37
camera.h
@@ -8,16 +8,16 @@
|
||||
|
||||
enum Camera_Movement
|
||||
{
|
||||
FORWARD,
|
||||
BACKWARD,
|
||||
LEFT,
|
||||
RIGHT
|
||||
_FORWARD,
|
||||
_BACKWARD,
|
||||
_LEFT,
|
||||
_RIGHT
|
||||
};
|
||||
|
||||
const float YAW = -90.0f;
|
||||
const float PITCH = 0.0f;
|
||||
const float SPEED = 2.5f;
|
||||
const float SENSITIVITY = 0.1f;
|
||||
const float SPEED = 5.0f;
|
||||
const float MOUSE_SENSITIVITY = 0.1f;
|
||||
const float ZOOM = 45.0f;
|
||||
|
||||
class Camera
|
||||
@@ -28,6 +28,7 @@ public:
|
||||
glm::vec3 Up;
|
||||
glm::vec3 Right;
|
||||
glm::vec3 WorldUp;
|
||||
glm::vec3 CameraOffset;
|
||||
|
||||
float Yaw;
|
||||
float Pitch;
|
||||
@@ -39,15 +40,17 @@ public:
|
||||
Camera(
|
||||
glm::vec3 position = glm::vec3(0.0f, 0.0f, 0.0f),
|
||||
glm::vec3 up = glm::vec3(0.0f, 1.0f, 0.0f),
|
||||
glm::vec3 offset = glm::vec3(0.0f, 1.0f, 0.0f),
|
||||
float yaw = YAW,
|
||||
float pitch = PITCH)
|
||||
:
|
||||
Front(glm::vec3(0.0f, 0.0f, -1.0f)),
|
||||
MovementSpeed(SPEED),
|
||||
MouseSensitivity(SENSITIVITY),
|
||||
MouseSensitivity(MOUSE_SENSITIVITY),
|
||||
Zoom(ZOOM)
|
||||
{
|
||||
Position = position;
|
||||
CameraOffset = offset;
|
||||
WorldUp = up;
|
||||
Yaw = yaw;
|
||||
Pitch = pitch;
|
||||
@@ -62,25 +65,22 @@ public:
|
||||
void ProcessKeyboard(Camera_Movement direction, float deltaTime)
|
||||
{
|
||||
float velocity = MovementSpeed * deltaTime;
|
||||
if (direction == FORWARD)
|
||||
if (direction == _FORWARD)
|
||||
Position += Front * velocity;
|
||||
if (direction == BACKWARD)
|
||||
if (direction == _BACKWARD)
|
||||
Position -= Front * velocity;
|
||||
if (direction == LEFT)
|
||||
if (direction == _LEFT)
|
||||
Position -= Right * velocity;
|
||||
if (direction == RIGHT)
|
||||
if (direction == _RIGHT)
|
||||
Position += Right * velocity;
|
||||
}
|
||||
|
||||
void ProcessMouseMovement(float xoffset, float yoffset, GLboolean constrainPitch = true)
|
||||
void ProcessMouseMovement(float XOffset, float YOffset, GLboolean bConstrainPitch = true)
|
||||
{
|
||||
xoffset *= MouseSensitivity;
|
||||
yoffset *= MouseSensitivity;
|
||||
//Yaw += XOffset;
|
||||
Pitch += YOffset;
|
||||
|
||||
Yaw += xoffset;
|
||||
Pitch += yoffset;
|
||||
|
||||
if (constrainPitch)
|
||||
if (bConstrainPitch)
|
||||
{
|
||||
if (Pitch > 89.0f)
|
||||
Pitch = 89.0f;
|
||||
@@ -100,6 +100,7 @@ public:
|
||||
Zoom = 45.0f;
|
||||
}
|
||||
private:
|
||||
|
||||
void updateCameraVectors()
|
||||
{
|
||||
glm::vec3 front;
|
||||
|
||||
10
cube.h
10
cube.h
@@ -10,7 +10,7 @@
|
||||
class Cube
|
||||
{
|
||||
private:
|
||||
glm::vec3 position;
|
||||
glm::vec3 Position;
|
||||
glm::vec3 scale;
|
||||
glm::vec3 rotation;
|
||||
glm::vec3 color;
|
||||
@@ -30,7 +30,7 @@ public:
|
||||
|
||||
Cube(glm::vec3 position, glm::vec3 scale, glm::vec3 rotation, glm::vec3 color)
|
||||
{
|
||||
this->position = position;
|
||||
this->Position = position;
|
||||
this->scale = scale;
|
||||
this->rotation = rotation;
|
||||
this->color = color;
|
||||
@@ -48,7 +48,7 @@ public:
|
||||
glm::mat4 getModelMatrix() const
|
||||
{
|
||||
glm::mat4 model = glm::mat4(1.0f);
|
||||
model = glm::translate(model, position);
|
||||
model = glm::translate(model, Position);
|
||||
model = glm::rotate(model, glm::radians(rotation.x), glm::vec3(1, 0, 0));
|
||||
model = glm::rotate(model, glm::radians(rotation.y), glm::vec3(0, 1, 0));
|
||||
model = glm::rotate(model, glm::radians(rotation.z), glm::vec3(0, 0, 1));
|
||||
@@ -59,7 +59,7 @@ public:
|
||||
|
||||
void setPosition(glm::vec3 position)
|
||||
{
|
||||
this->position = position;
|
||||
this->Position = position;
|
||||
}
|
||||
|
||||
void setScale(glm::vec3 scale)
|
||||
@@ -79,7 +79,7 @@ public:
|
||||
|
||||
glm::vec3 getPosition() const
|
||||
{
|
||||
return position;
|
||||
return Position;
|
||||
}
|
||||
|
||||
glm::vec3 getScale() const
|
||||
|
||||
@@ -153,6 +153,43 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
void render(glm::mat4 view, glm::mat4 projection, glm::vec3 lightPos, float deltaTime, int amountOfCubes)
|
||||
{
|
||||
shader.use();
|
||||
shader.setMat4("projection", projection);
|
||||
shader.setMat4("view", view);
|
||||
|
||||
int i = 0;
|
||||
for (Cube& cube : cubes)
|
||||
{
|
||||
if (i >= amountOfCubes)
|
||||
{
|
||||
break;
|
||||
}
|
||||
//std::cout << "Cube position: (" << cube.getColor().x << "," << cube.getColor().y << "," << cube.getColor().z << ")" << std::endl;
|
||||
cube.setRotation(cube.getRotation() + (glm::vec3(5.0f, 10.0f, 20.0f)) * deltaTime);
|
||||
glm::mat4 model = cube.getModelMatrix();
|
||||
glm::vec3 color = cube.getColor();
|
||||
shader.setMat4("model", model);
|
||||
shader.setVec3("objectColor", color);
|
||||
shader.setVec3("lightColor", 1.0f, 1.0f, 1.0f);
|
||||
shader.setVec3("lightPos", lightPos);
|
||||
|
||||
glBindVertexArray(VAO);
|
||||
glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDrawArrays(GL_TRIANGLES, 0, 36);
|
||||
//glDrawElements(GL_TRIANGLES, 36, GL_UNSIGNED_INT, 0);
|
||||
//shader.setVec3("objectColor", 0.0f, 0.0f, 0.0f);
|
||||
//glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
|
||||
//glDrawArrays(GL_TRIANGLES, 0, 36);
|
||||
//glDrawElements(GL_TRIANGLES, 36, GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
std::list<Cube> getCubes()
|
||||
{
|
||||
return cubes;
|
||||
|
||||
12
imgui.ini
Normal file
12
imgui.ini
Normal file
@@ -0,0 +1,12 @@
|
||||
[Window][Debug##Default]
|
||||
Pos=60,60
|
||||
Size=400,400
|
||||
Collapsed=0
|
||||
|
||||
[Window][Settings]
|
||||
Pos=69,71
|
||||
Size=445,126
|
||||
Collapsed=0
|
||||
|
||||
[Docking][Data]
|
||||
|
||||
1
input_processor.h
Normal file
1
input_processor.h
Normal file
@@ -0,0 +1 @@
|
||||
#pragma once
|
||||
262
main.cpp
262
main.cpp
@@ -7,23 +7,29 @@
|
||||
#include <glm/glm.hpp>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
#include <glm/gtc/type_ptr.hpp>
|
||||
#include <Camera.h>
|
||||
#include <Player.h>
|
||||
|
||||
#include <imgui.h>
|
||||
#include <imgui_impl_glfw.h>
|
||||
#include <imgui_impl_opengl3.h>
|
||||
|
||||
#include <camera.h>
|
||||
#include <cubeFactory.h>
|
||||
#include "ResourceManager.h"
|
||||
#include "PointLight.h"
|
||||
|
||||
void framebuffer_size_callback(GLFWwindow* window, int width, int height);
|
||||
void processInput(GLFWwindow* window);
|
||||
void mouse_callback(GLFWwindow* window, double xpos, double ypos);
|
||||
void scroll_callback(GLFWwindow* window, double xoffset, double yoffset);
|
||||
|
||||
int SCR_WIDTH = 800;
|
||||
int SCR_HEIGHT = 800;
|
||||
int SCR_WIDTH = 1600;
|
||||
int SCR_HEIGHT = 900;
|
||||
|
||||
//Camera camera(glm::vec3(20.0f, 1.0f, 20.0f));
|
||||
glm::vec3 StartingPosition = glm::vec3(20.0f, 0.0f, 20.0f);
|
||||
glm::vec3 StartingRotation = glm::vec3(0.0f, 0.0f, 0.0f);
|
||||
Player PlayerCharacter(StartingPosition, StartingRotation);
|
||||
|
||||
Camera camera(glm::vec3(0.0f, 0.0f, 20.0f));
|
||||
float lastX = SCR_WIDTH / 2.0f;
|
||||
float lastY = SCR_HEIGHT / 2.0f;
|
||||
bool firstMouse = true;
|
||||
@@ -32,17 +38,13 @@ float deltaTime = 0.0f;
|
||||
float lastFrame = 0.0f;
|
||||
float elapsedTime = 0.0f;
|
||||
|
||||
int amountOfCubes = 1000;
|
||||
|
||||
//glm::vec3 lightPos(1.2f, 1.0f, 2.0f);
|
||||
|
||||
int main()
|
||||
{
|
||||
IMGUI_CHECKVERSION();
|
||||
ImGui::CreateContext();
|
||||
ImGuiIO& io = ImGui::GetIO();
|
||||
io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard;
|
||||
io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad;
|
||||
io.ConfigFlags |= ImGuiConfigFlags_DockingEnable;
|
||||
|
||||
const char* glsl_version = "#version 330";
|
||||
std::cout << "Starting GLFW context, OpenGL 3.3" << std::endl;
|
||||
glfwInit();
|
||||
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
|
||||
@@ -61,7 +63,7 @@ int main()
|
||||
glfwSetCursorPosCallback(window, mouse_callback);
|
||||
glfwSetScrollCallback(window, scroll_callback);
|
||||
|
||||
glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
|
||||
//glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
|
||||
|
||||
if (!gladLoadGLLoader((GLADloadproc)glfwGetProcAddress)) {
|
||||
std::cout << "Failed to initialize GLAD" << std::endl;
|
||||
@@ -69,41 +71,76 @@ int main()
|
||||
}
|
||||
|
||||
glEnable(GL_DEPTH_TEST);
|
||||
glEnable(GL_CULL_FACE);
|
||||
|
||||
std::cout << "Loaded GLFW context, OpenGL 3.3" << std::endl;
|
||||
|
||||
CubeFactory cubeFactory;
|
||||
IMGUI_CHECKVERSION();
|
||||
ImGui::CreateContext();
|
||||
ImGuiIO& io = ImGui::GetIO();
|
||||
io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard;
|
||||
io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad;
|
||||
io.ConfigFlags |= ImGuiConfigFlags_DockingEnable;
|
||||
|
||||
float offset = 2.0f;
|
||||
int xAmount = 10;
|
||||
int yAmount = 10;
|
||||
int zAmount = 10;
|
||||
//ImGui_ImplGlfw_InitForOpenGL(window, true);
|
||||
//ImGui_ImplOpenGL3_Init(glsl_version);
|
||||
|
||||
for (int x = 0; x < xAmount; x++)
|
||||
{
|
||||
for (int y = 0; y < yAmount; y++)
|
||||
{
|
||||
for (int z = 0; z < zAmount; z++)
|
||||
{
|
||||
glm::vec3 position = glm::vec3( (x * offset) - (xAmount * offset / 2.0f),
|
||||
(y * offset) - (yAmount * offset / 2.0f),
|
||||
(z * offset) - (zAmount * offset / 2.0f));
|
||||
glm::vec3 scale = glm::vec3(1.0f, 1.0f, 1.0f);
|
||||
glm::vec3 rotation = glm::vec3(0.0f, 0.0f, 0.0f);
|
||||
glm::vec3 color = glm::vec3(x/10.0f, y/10.0f, z/10.0f);
|
||||
|
||||
cubeFactory.addCube(position, scale, rotation, color);
|
||||
}
|
||||
}
|
||||
if (!ImGui_ImplGlfw_InitForOpenGL(window, true)) {
|
||||
std::cout << "Failed to initialize ImGui GLFW backend" << std::endl;
|
||||
}
|
||||
if (!ImGui_ImplOpenGL3_Init(glsl_version)) {
|
||||
std::cout << "Failed to initialize ImGui OpenGL backend" << std::endl;
|
||||
}
|
||||
|
||||
//std::cout << "Amount of cubes: " << cubeFactory.getCubes().size() << std::endl;
|
||||
Shader simple_depth_shader = ResourceManager::LoadShader("point_shadow_depth.vert", "point_shadow_depth.frag", "point_shadow_depth.geom", "simple_depth_shader");
|
||||
|
||||
Shader wall_shader = ResourceManager::LoadShader("wall_test.vert", "wall_test.frag", nullptr, "wall");
|
||||
|
||||
LevelMap level_map = ResourceManager::LoadLevelMap("map_test.txt", "test_level");
|
||||
|
||||
level_map.RenderSetup(&wall_shader, &wall_shader, &wall_shader);
|
||||
|
||||
int number_of_point_lights = 0;
|
||||
|
||||
std::vector<PointLight> point_lights_vector;
|
||||
|
||||
//PointLight point_light3(glm::vec3(30.0f, 3.0f, 30.0f), glm::vec3(1.0f, 1.0f, 1.0f), simple_depth_shader);
|
||||
|
||||
//PointLight point_light2(glm::vec3(70.0f, 2.0f, 55.0f), glm::vec3(1.0f, 1.0f, 1.0f), simple_depth_shader);
|
||||
|
||||
//PointLight point_light(glm::vec3(20.0f, 3.0f, 35.0f), glm::vec3(1.0f, 1.0f, 1.0f), simple_depth_shader);
|
||||
|
||||
//PointLight point_lights[3] = { point_light, point_light2, point_light3 };
|
||||
|
||||
/*unsigned int depthCubemap, depthMapFBO;
|
||||
|
||||
glGenFramebuffers(1, &depthMapFBO);
|
||||
glGenTextures(1, &depthCubemap);
|
||||
|
||||
glBindTexture(GL_TEXTURE_CUBE_MAP, depthCubemap);
|
||||
|
||||
for (unsigned int i = 0; i < 6; ++i)
|
||||
{
|
||||
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_DEPTH_COMPONENT, SHADOW_WIDTH, SHADOW_HEIGHT, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL);
|
||||
}
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
|
||||
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, depthMapFBO);
|
||||
glFramebufferTexture(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, depthCubemap, 0);
|
||||
glDrawBuffer(GL_NONE);
|
||||
glReadBuffer(GL_NONE);
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, 0);*/
|
||||
|
||||
float r = 0.05f, g = 0.05f, b = 0.05f;
|
||||
|
||||
while (!glfwWindowShouldClose(window)) {
|
||||
//timing
|
||||
float currentFrame = glfwGetTime();
|
||||
float currentFrame = (float)glfwGetTime();
|
||||
deltaTime = currentFrame - lastFrame;
|
||||
lastFrame = currentFrame;
|
||||
elapsedTime += deltaTime;
|
||||
@@ -111,25 +148,142 @@ int main()
|
||||
//input
|
||||
processInput(window);
|
||||
|
||||
ImGui_ImplOpenGL3_NewFrame();
|
||||
ImGui_ImplGlfw_NewFrame();
|
||||
ImGui::NewFrame();
|
||||
|
||||
ImGui::Begin("Settings");
|
||||
ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / ImGui::GetIO().Framerate, ImGui::GetIO().Framerate);
|
||||
if (ImGui::Button("Create Light") && number_of_point_lights < 10) {
|
||||
point_lights_vector.push_back(PointLight(PlayerCharacter.Position, glm::vec3(1.0f, 1.0f, 1.0f), simple_depth_shader));
|
||||
number_of_point_lights = point_lights_vector.size();
|
||||
}
|
||||
//ImGui::SliderInt("Amount of cubes: ", &amountOfCubes, 0, 1000);
|
||||
ImGui::End();
|
||||
|
||||
ImGui::Render();
|
||||
|
||||
// view/projection transformations
|
||||
|
||||
glClearColor(r, g, b, 1.0f);
|
||||
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
|
||||
// view/projection transformations
|
||||
glm::mat4 projection = glm::perspective(glm::radians(camera.Zoom), (float)SCR_WIDTH / (float)SCR_HEIGHT, 0.1f, 100.0f);
|
||||
glm::mat4 view = camera.GetViewMatrix();
|
||||
//glDisable(GL_CULL_FACE);
|
||||
|
||||
glm::vec3 lightPos = glm::vec3(100.2f, 100.0f, 200.0f);
|
||||
//level_map.GetMeshes();
|
||||
|
||||
cubeFactory.render(view, projection, lightPos, deltaTime);
|
||||
for (PointLight& point_light : point_lights_vector)
|
||||
{
|
||||
point_light.RenderSceneShadows(level_map.GetMeshes());
|
||||
}
|
||||
|
||||
//for (int i = 0; i < numOfPointLights; i++)
|
||||
//{
|
||||
// point_lights[i].RenderSceneShadows(level_map.GetMeshes());
|
||||
//}
|
||||
|
||||
glViewport(0, 0, SCR_WIDTH, SCR_HEIGHT);
|
||||
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
|
||||
wall_shader.Use();
|
||||
// CHANGED PROJECTION TO USE FLAT 45 TO GET PLAYER CHARACTER TO WORK
|
||||
glm::mat4 projection = glm::perspective(glm::radians(45.0f), (float)SCR_WIDTH / (float)SCR_HEIGHT, 0.1f, 100.0f);
|
||||
glm::mat4 view = PlayerCharacter.GetViewMatrix();
|
||||
wall_shader.SetMatrix4("projection", projection);
|
||||
wall_shader.SetMatrix4("view", view);
|
||||
wall_shader.SetVector3f("viewPosition", PlayerCharacter.Position);
|
||||
|
||||
wall_shader.SetVector3f("material.ambientColor", glm::vec3(1.0f, 0.0f, 0.0f));
|
||||
wall_shader.SetVector3f("material.diffuseColor", glm::vec3(0.5f, 0.5f, 0.5f));
|
||||
wall_shader.SetVector3f("material.specularColor", glm::vec3(0.0f, 0.0f, 1.0f));
|
||||
wall_shader.SetFloat("material.shininess", 1.0f);
|
||||
// set lighting uniforms
|
||||
wall_shader.SetInteger("numOfPointLights", number_of_point_lights);
|
||||
int light_index = 0;
|
||||
for (PointLight& point_light : point_lights_vector)
|
||||
{
|
||||
std::string name = "pointLights[" + std::to_string(light_index) + "].";
|
||||
wall_shader.SetVector3f((name + "base.color").c_str(), point_light.color);
|
||||
wall_shader.SetFloat((name + "base.ambientIntensity").c_str(), point_light.ambient_intensity);
|
||||
wall_shader.SetFloat((name + "base.diffuseIntensity").c_str(), point_light.diffuse_intensity);
|
||||
wall_shader.SetFloat((name + "atten.constant").c_str(), point_light.attenuation_constant);
|
||||
wall_shader.SetFloat((name + "atten.linear").c_str(), point_light.attenuation_linear);
|
||||
wall_shader.SetFloat((name + "atten.exponential").c_str(), point_light.attenuation_exponential);
|
||||
wall_shader.SetVector3f((name + "position").c_str(), point_light.Position);
|
||||
wall_shader.SetFloat((name + "farPlane").c_str(), point_light.far_plane);
|
||||
wall_shader.SetInteger((name + "depthMap").c_str(), light_index);
|
||||
glActiveTexture(GL_TEXTURE0 + light_index);
|
||||
glBindTexture(GL_TEXTURE_CUBE_MAP, point_light.depth_map);
|
||||
|
||||
light_index++;
|
||||
}
|
||||
/*wall_shader.SetVector3f("pointLights[0].base.color", point_light.color);
|
||||
wall_shader.SetVector3f("pointLights[0].base.ambientIntensity", point_light.ambient);
|
||||
wall_shader.SetVector3f("pointLights[0].position", point_light.position);
|
||||
wall_shader.SetVector3f("lightPosition2", point_light2.position);
|
||||
wall_shader.SetVector3f("lightColor", point_light.color);*/
|
||||
//wall_shader.SetInteger("shadows", 1); // enable/disable shadows by pressing 'SPACE'
|
||||
//wall_shader.SetInteger("depthMap", 0);
|
||||
|
||||
|
||||
GLenum err;
|
||||
while(err = glGetError())
|
||||
{
|
||||
std::cout << "Error: " << err << std::endl;
|
||||
}
|
||||
|
||||
for (auto* mesh : level_map.GetMeshes())
|
||||
{
|
||||
// //std::cout << "Rendering mesh" << std::endl;
|
||||
mesh->Render(wall_shader);
|
||||
}
|
||||
|
||||
|
||||
/*float near_plane = 1.0f;
|
||||
float far_plane = 50.0f;
|
||||
glm::mat4 shadowProj = glm::perspective(glm::radians(90.0f), (float)SHADOW_WIDTH / (float)SHADOW_HEIGHT, near_plane, far_plane);*/
|
||||
/*std::vector<glm::mat4> shadowTransforms;
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(lightPos, lightPos + glm::vec3(1.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(lightPos, lightPos + glm::vec3(-1.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(lightPos, lightPos + glm::vec3(0.0f, 1.0f, 0.0f), glm::vec3(0.0f, 0.0f, 1.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(lightPos, lightPos + glm::vec3(0.0f, -1.0f, 0.0f), glm::vec3(0.0f, 0.0f, -1.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(lightPos, lightPos + glm::vec3(0.0f, 0.0f, 1.0f), glm::vec3(0.0f, -1.0f, 0.0f)));
|
||||
shadowTransforms.push_back(shadowProj * glm::lookAt(lightPos, lightPos + glm::vec3(0.0f, 0.0f, -1.0f), glm::vec3(0.0f, -1.0f, 0.0f)));*/
|
||||
|
||||
/*glViewport(0, 0, SHADOW_WIDTH, SHADOW_HEIGHT);
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, depthMapFBO);
|
||||
glClear(GL_DEPTH_BUFFER_BIT);
|
||||
glCullFace(GL_FRONT);
|
||||
simpleDepthShader.Use();
|
||||
for (unsigned int i = 0; i < 6; ++i)
|
||||
simpleDepthShader.SetMatrix4("shadowMatrices[" + std::to_string(i) + "]", shadowTransforms[i]);
|
||||
simpleDepthShader.SetFloat("far_plane", far_plane);
|
||||
simpleDepthShader.SetVector3f("lightPos", lightPos);
|
||||
levelMap.Update(projection, view);
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, 0);
|
||||
glCullFace(GL_BACK);
|
||||
|
||||
glViewport(0, 0, SCR_WIDTH, SCR_HEIGHT);
|
||||
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
glBindTexture(GL_TEXTURE_CUBE_MAP, depthCubemap);*/
|
||||
//map.render(projection, view, lightPos, deltaTime, glm::vec3(SCR_WIDTH, SCR_HEIGHT, 0.0f), far_plane);
|
||||
|
||||
//level_map.Update(projection, view, point_light.position, point_light.color, camera.Position);
|
||||
|
||||
//cubeFactory.render(view, projection, lightPos, deltaTime, amountOfCubes);
|
||||
|
||||
ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData());
|
||||
//check and call
|
||||
glfwSwapBuffers(window);
|
||||
glfwPollEvents();
|
||||
}
|
||||
|
||||
//cubeFactory.clear();
|
||||
// Cleanup
|
||||
ImGui_ImplOpenGL3_Shutdown();
|
||||
ImGui_ImplGlfw_Shutdown();
|
||||
ImGui::DestroyContext();
|
||||
glfwDestroyWindow(window);
|
||||
glfwTerminate();
|
||||
return 0;
|
||||
}
|
||||
|
||||
void framebuffer_size_callback(GLFWwindow* window, int width, int height)
|
||||
@@ -145,18 +299,26 @@ void processInput(GLFWwindow* window)
|
||||
|
||||
const float cameraSpeed = 5.0f * deltaTime;
|
||||
if (glfwGetKey(window, GLFW_KEY_W) == GLFW_PRESS)
|
||||
camera.ProcessKeyboard(FORWARD, deltaTime);
|
||||
PlayerCharacter.ProcessKeyboard(FORWARD, deltaTime);
|
||||
if (glfwGetKey(window, GLFW_KEY_S) == GLFW_PRESS)
|
||||
camera.ProcessKeyboard(BACKWARD, deltaTime);
|
||||
PlayerCharacter.ProcessKeyboard(BACKWARD, deltaTime);
|
||||
if (glfwGetKey(window, GLFW_KEY_A) == GLFW_PRESS)
|
||||
camera.ProcessKeyboard(LEFT, deltaTime);
|
||||
PlayerCharacter.ProcessKeyboard(LEFT, deltaTime);
|
||||
if (glfwGetKey(window, GLFW_KEY_D) == GLFW_PRESS)
|
||||
camera.ProcessKeyboard(RIGHT, deltaTime);
|
||||
PlayerCharacter.ProcessKeyboard(RIGHT, deltaTime);
|
||||
}
|
||||
|
||||
void mouse_callback(GLFWwindow* window, double xposIn, double yposIn)
|
||||
{
|
||||
//std::cout << "Mouse callback" << std::endl;
|
||||
if (glfwGetMouseButton(window, GLFW_MOUSE_BUTTON_LEFT) != GLFW_PRESS)
|
||||
{
|
||||
glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_NORMAL);
|
||||
firstMouse = true;
|
||||
return;
|
||||
}
|
||||
|
||||
glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
|
||||
//std::cout << "Mouse callback" << std::endl;
|
||||
float xpos = static_cast<float>(xposIn);
|
||||
float ypos = static_cast<float>(yposIn);
|
||||
|
||||
@@ -173,10 +335,10 @@ void mouse_callback(GLFWwindow* window, double xposIn, double yposIn)
|
||||
lastX = xpos;
|
||||
lastY = ypos;
|
||||
|
||||
camera.ProcessMouseMovement(xoffset, yoffset);
|
||||
PlayerCharacter.ProcessMouseMovement(xoffset, yoffset);
|
||||
}
|
||||
|
||||
void scroll_callback(GLFWwindow* window, double xoffset, double yoffset)
|
||||
{
|
||||
camera.ProcessMouseScroll(static_cast<float>(yoffset));
|
||||
//PlayerCharacter.ProcessMouseScroll(static_cast<float>(yoffset));
|
||||
}
|
||||
|
||||
489
map_reader.h
Normal file
489
map_reader.h
Normal file
@@ -0,0 +1,489 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef MAP_READER_H
|
||||
#define MAP_READER_H
|
||||
|
||||
#include <string>
|
||||
#include <fstream>
|
||||
#include <sstream>
|
||||
#include <iostream>
|
||||
#include <vector>
|
||||
#include <random>
|
||||
|
||||
#include <glad/glad.h>
|
||||
#include <GLFW/glfw3.h>
|
||||
#include <glm/glm.hpp>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
#include <glm/gtc/type_ptr.hpp>
|
||||
|
||||
#include "Shader.h"
|
||||
|
||||
struct Wall
|
||||
{
|
||||
glm::vec2 a, b;
|
||||
int portal;
|
||||
};
|
||||
|
||||
struct Sector
|
||||
{
|
||||
int id;
|
||||
int index;
|
||||
int numberOfWalls;
|
||||
float floorHeight;
|
||||
float ceilingHeight;
|
||||
|
||||
bool outwardFacing;
|
||||
|
||||
glm::vec3 color;
|
||||
|
||||
std::vector<Wall> walls;
|
||||
};
|
||||
|
||||
class Map
|
||||
{
|
||||
public:
|
||||
Map(std::string filename) : wallShader(Shader("wall_test.vert", "wall_test.frag")), floorShader(Shader("wall_test.vert", "wall_test.frag"))
|
||||
{
|
||||
parseMapFile(filename);
|
||||
setupBuffers();
|
||||
}
|
||||
|
||||
void render(glm::mat4 projection, glm::mat4 view, glm::vec3 lightPos)
|
||||
{
|
||||
wallShader.use();
|
||||
wallShader.setMat4("projection", projection);
|
||||
wallShader.setMat4("view", view);
|
||||
|
||||
glm::mat4 model = glm::mat4(1.0f);
|
||||
wallShader.setMat4("model", model);
|
||||
//shader.setVec3("objectColor", 1.0f, 0.0f, 0.0f);
|
||||
wallShader.setVec3("lightColor", 1.0f, 1.0f, 1.0f);
|
||||
wallShader.setVec3("lightPos", lightPos);
|
||||
|
||||
glBindVertexArray(wallVAO);
|
||||
|
||||
// Use glDrawElements since we are using indices
|
||||
//glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDrawElements(GL_TRIANGLES, wallIndices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
|
||||
floorShader.use();
|
||||
floorShader.setMat4("projection", projection);
|
||||
floorShader.setMat4("view", view);
|
||||
|
||||
model = glm::mat4(1.0f);
|
||||
floorShader.setMat4("model", model);
|
||||
floorShader.setVec3("lightColor", 1.0f, 1.0f, 1.0f);
|
||||
floorShader.setVec3("lightPos", lightPos);
|
||||
|
||||
glBindVertexArray(floorVAO);
|
||||
|
||||
//glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDrawElements(GL_TRIANGLES, floorIndices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
}
|
||||
|
||||
void render(glm::mat4 projection, glm::mat4 view, glm::vec3 lightPos, float deltaTime, glm::vec3 resolution, float far_plane)
|
||||
{
|
||||
time += deltaTime;
|
||||
|
||||
wallShader.use();
|
||||
wallShader.setMat4("projection", projection);
|
||||
wallShader.setMat4("view", view);
|
||||
wallShader.setVec3("iResolution", resolution);
|
||||
wallShader.setFloat("iTime", time);
|
||||
wallShader.setVec3("lightColor", 1.0f, 1.0f, 1.0f);
|
||||
wallShader.setVec3("lightPos", lightPos);
|
||||
wallShader.setInt("shadows", 1);
|
||||
wallShader.setFloat("far_plane", far_plane);
|
||||
wallShader.setInt("diffuseTexture", 0);
|
||||
wallShader.setInt("shadowMap", 1);
|
||||
|
||||
glm::mat4 model = glm::mat4(1.0f);
|
||||
wallShader.setMat4("model", model);
|
||||
//shader.setVec3("objectColor", 1.0f, 0.0f, 0.0f);
|
||||
|
||||
glBindVertexArray(wallVAO);
|
||||
|
||||
// Use glDrawElements since we are using indices
|
||||
//glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDrawElements(GL_TRIANGLES, wallIndices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
|
||||
floorShader.use();
|
||||
floorShader.setMat4("projection", projection);
|
||||
floorShader.setMat4("view", view);
|
||||
floorShader.setVec3("iResolution", resolution);
|
||||
floorShader.setFloat("iTime", time);
|
||||
floorShader.setVec3("lightColor", 1.0f, 1.0f, 1.0f);
|
||||
floorShader.setVec3("lightPos", lightPos);
|
||||
floorShader.setInt("shadows", 1);
|
||||
floorShader.setFloat("far_plane", far_plane);
|
||||
floorShader.setInt("diffuseTexture", 0);
|
||||
floorShader.setInt("shadowMap", 1);
|
||||
|
||||
model = glm::mat4(1.0f);
|
||||
floorShader.setMat4("model", model);
|
||||
|
||||
glBindVertexArray(floorVAO);
|
||||
|
||||
//glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDrawElements(GL_TRIANGLES, floorIndices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
}
|
||||
|
||||
void render(glm::mat4 projection, glm::mat4 view, glm::vec3 lightPos, Shader _shader)
|
||||
{
|
||||
glm::mat4 model = glm::mat4(1.0f);
|
||||
_shader.setMat4("model", model);
|
||||
|
||||
glBindVertexArray(wallVAO);
|
||||
|
||||
// Use glDrawElements since we are using indices
|
||||
//glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDrawElements(GL_TRIANGLES, wallIndices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
|
||||
glBindVertexArray(floorVAO);
|
||||
|
||||
//glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDrawElements(GL_TRIANGLES, floorIndices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);
|
||||
|
||||
/*floorShader.use();
|
||||
floorShader.setMat4("projection", projection);
|
||||
floorShader.setMat4("view", view);
|
||||
|
||||
model = glm::mat4(1.0f);
|
||||
floorShader.setMat4("model", model);
|
||||
floorShader.setVec3("lightColor", 1.0f, 1.0f, 1.0f);
|
||||
floorShader.setVec3("lightPos", lightPos);
|
||||
|
||||
glBindVertexArray(floorVAO);
|
||||
|
||||
glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDrawElements(GL_TRIANGLES, floorIndices.size(), GL_UNSIGNED_INT, 0);
|
||||
|
||||
glBindVertexArray(0);*/
|
||||
}
|
||||
private:
|
||||
std::vector<Sector> sectors;
|
||||
|
||||
unsigned int wallVAO;
|
||||
unsigned int wallVBO, wallEBO, wallNBO, wallCBO;
|
||||
unsigned int floorVAO;
|
||||
unsigned int floorVBO, floorEBO, floorNBO, floorCBO;
|
||||
|
||||
std::vector<float> wallVertices, wallNormals, wallColors;
|
||||
std::vector<unsigned int> wallIndices;
|
||||
|
||||
std::vector<float> floorVertices, floorNormals, floorColors;
|
||||
std::vector<unsigned int> floorIndices;
|
||||
|
||||
Shader wallShader;
|
||||
|
||||
Shader floorShader;
|
||||
|
||||
float time;
|
||||
|
||||
Sector parseSector(std::string& line)
|
||||
{
|
||||
Sector sector;
|
||||
std::stringstream ss(line);
|
||||
ss >> sector.id >> sector.index >> sector.numberOfWalls >> sector.floorHeight >> sector.ceilingHeight >> sector.outwardFacing;
|
||||
|
||||
static std::random_device rd; // Obtain a random number from hardware
|
||||
static std::mt19937 eng(rd()); // Seed the generator
|
||||
std::uniform_real_distribution<float> distr(0.0f, 1.0f); // Define the range
|
||||
|
||||
glm::vec3 randomColor(distr(eng), distr(eng), distr(eng));
|
||||
|
||||
sector.color = randomColor;
|
||||
|
||||
return sector;
|
||||
}
|
||||
|
||||
Wall parseWall(std::string& line)
|
||||
{
|
||||
Wall wall;
|
||||
std::stringstream ss(line);
|
||||
ss >> wall.a.x >> wall.a.y >> wall.b.x >> wall.b.y >> wall.portal;
|
||||
return wall;
|
||||
}
|
||||
|
||||
void parseMapFile(std::string filename)
|
||||
{
|
||||
//std::cout << "Parsing map file: " << filename << std::endl;
|
||||
std::ifstream file(filename);
|
||||
std::string line;
|
||||
|
||||
bool inSector = false, inWall = false;
|
||||
while (std::getline(file, line))
|
||||
{
|
||||
//std::cout << "Line: " << line << std::endl;
|
||||
if (line.empty() || line[0] == '#') continue;
|
||||
|
||||
if (line.find("[SECTOR]") != std::string::npos)
|
||||
{
|
||||
inSector = true;
|
||||
inWall = false;
|
||||
continue;
|
||||
}
|
||||
else if (line.find("[WALL]") != std::string::npos)
|
||||
{
|
||||
inSector = false;
|
||||
inWall = true;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (inSector)
|
||||
{
|
||||
sectors.push_back(parseSector(line));
|
||||
}
|
||||
|
||||
if (inWall && !sectors.empty())
|
||||
{
|
||||
Wall wall = parseWall(line);
|
||||
sectors.back().walls.push_back(wall);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void setupBuffers()
|
||||
{
|
||||
std::cout << "Setting up buffers" << std::endl;
|
||||
|
||||
int wallBaseIndex = 0;
|
||||
int floorBaseIndex = 0;
|
||||
for (Sector sector : sectors)
|
||||
{
|
||||
std::vector<glm::vec3> _floorVertices;
|
||||
std::vector<glm::vec3> _ceilingVertices;
|
||||
for (Wall wall : sector.walls)
|
||||
{
|
||||
glm::vec3 v0(wall.a.x, sector.floorHeight, wall.a.y);
|
||||
glm::vec3 v1(wall.b.x, sector.floorHeight, wall.b.y);
|
||||
glm::vec3 v2(wall.b.x, sector.ceilingHeight, wall.b.y);
|
||||
glm::vec3 v3(wall.a.x, sector.ceilingHeight, wall.a.y);
|
||||
|
||||
_floorVertices.push_back(v0);
|
||||
|
||||
_ceilingVertices.push_back(v3);
|
||||
|
||||
if (wall.portal != 0)
|
||||
{
|
||||
Sector& portalSector = sectors[wall.portal - 1];
|
||||
if (portalSector.floorHeight > sector.floorHeight)
|
||||
{
|
||||
v2.y = portalSector.floorHeight;
|
||||
v3.y = portalSector.floorHeight;
|
||||
|
||||
addWallVectors(v0, v1, v2, v3, sector.color, wallBaseIndex, sector.outwardFacing);
|
||||
}
|
||||
|
||||
if (portalSector.ceilingHeight < sector.ceilingHeight)
|
||||
{
|
||||
v0.y = portalSector.ceilingHeight;
|
||||
v1.y = portalSector.ceilingHeight;
|
||||
v2.y = sector.ceilingHeight;
|
||||
v3.y = sector.ceilingHeight;
|
||||
|
||||
addWallVectors(v0, v1, v2, v3, sector.color, wallBaseIndex, sector.outwardFacing);
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
addWallVectors(v0, v1, v2, v3, sector.color, wallBaseIndex, sector.outwardFacing);
|
||||
continue;
|
||||
}
|
||||
|
||||
addFloorVectors(_floorVertices, floorBaseIndex, true);
|
||||
addFloorVectors(_ceilingVertices, floorBaseIndex, false);
|
||||
}
|
||||
|
||||
glGenVertexArrays(1, &wallVAO);
|
||||
glGenBuffers(1, &wallVBO);
|
||||
glGenBuffers(1, &wallEBO);
|
||||
glGenBuffers(1, &wallNBO);
|
||||
glGenBuffers(1, &wallCBO);
|
||||
|
||||
glBindVertexArray(wallVAO);
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, wallVBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, wallVertices.size() * sizeof(float), wallVertices.data(), GL_STATIC_DRAW);
|
||||
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
|
||||
glEnableVertexAttribArray(0);
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, wallNBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, wallNormals.size() * sizeof(float), wallNormals.data(), GL_STATIC_DRAW);
|
||||
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
|
||||
glEnableVertexAttribArray(1);
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, wallCBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, wallColors.size() * sizeof(float), wallColors.data(), GL_STATIC_DRAW);
|
||||
glVertexAttribPointer(2, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
|
||||
glEnableVertexAttribArray(2);
|
||||
|
||||
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, wallEBO);
|
||||
glBufferData(GL_ELEMENT_ARRAY_BUFFER, wallIndices.size() * sizeof(unsigned int), wallIndices.data(), GL_STATIC_DRAW);
|
||||
|
||||
glBindVertexArray(0);
|
||||
|
||||
glGenVertexArrays(1, &floorVAO);
|
||||
glGenBuffers(1, &floorVBO);
|
||||
glGenBuffers(1, &floorEBO);
|
||||
glGenBuffers(1, &floorNBO);
|
||||
glGenBuffers(1, &floorCBO);
|
||||
|
||||
glBindVertexArray(floorVAO);
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, floorVBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, floorVertices.size() * sizeof(float), floorVertices.data(), GL_STATIC_DRAW);
|
||||
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
|
||||
glEnableVertexAttribArray(0);
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, floorNBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, floorNormals.size() * sizeof(float), floorNormals.data(), GL_STATIC_DRAW);
|
||||
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
|
||||
glEnableVertexAttribArray(1);
|
||||
|
||||
glBindBuffer(GL_ARRAY_BUFFER, floorCBO);
|
||||
glBufferData(GL_ARRAY_BUFFER, floorColors.size() * sizeof(float), floorColors.data(), GL_STATIC_DRAW);
|
||||
glVertexAttribPointer(2, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
|
||||
glEnableVertexAttribArray(2);
|
||||
|
||||
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, floorEBO);
|
||||
glBufferData(GL_ELEMENT_ARRAY_BUFFER, floorIndices.size() * sizeof(unsigned int), floorIndices.data(), GL_STATIC_DRAW);
|
||||
|
||||
glBindVertexArray(0);
|
||||
}
|
||||
|
||||
void addWallVectors(glm::vec3 v0, glm::vec3 v1, glm::vec3 v2, glm::vec3 v3, glm::vec3 color, int& baseIndex, bool outward)
|
||||
{
|
||||
wallVertices.push_back(v0.x);
|
||||
wallVertices.push_back(v0.y);
|
||||
wallVertices.push_back(v0.z);
|
||||
|
||||
wallVertices.push_back(v1.x);
|
||||
wallVertices.push_back(v1.y);
|
||||
wallVertices.push_back(v1.z);
|
||||
|
||||
wallVertices.push_back(v2.x);
|
||||
wallVertices.push_back(v2.y);
|
||||
wallVertices.push_back(v2.z);
|
||||
|
||||
wallVertices.push_back(v3.x);
|
||||
wallVertices.push_back(v3.y);
|
||||
wallVertices.push_back(v3.z);
|
||||
|
||||
glm::vec3 normal = glm::normalize(glm::cross(v1 - v0, v3 - v0));
|
||||
normal = outward ? normal : -normal;
|
||||
|
||||
wallNormals.push_back(normal.x);
|
||||
wallNormals.push_back(normal.y);
|
||||
wallNormals.push_back(normal.z);
|
||||
|
||||
wallNormals.push_back(normal.x);
|
||||
wallNormals.push_back(normal.y);
|
||||
wallNormals.push_back(normal.z);
|
||||
|
||||
wallNormals.push_back(normal.x);
|
||||
wallNormals.push_back(normal.y);
|
||||
wallNormals.push_back(normal.z);
|
||||
|
||||
wallNormals.push_back(normal.x);
|
||||
wallNormals.push_back(normal.y);
|
||||
wallNormals.push_back(normal.z);
|
||||
|
||||
wallColors.push_back(color.x);
|
||||
wallColors.push_back(color.y);
|
||||
wallColors.push_back(color.z);
|
||||
|
||||
wallColors.push_back(color.x);
|
||||
wallColors.push_back(color.y);
|
||||
wallColors.push_back(color.z);
|
||||
|
||||
wallColors.push_back(color.x);
|
||||
wallColors.push_back(color.y);
|
||||
wallColors.push_back(color.z);
|
||||
|
||||
wallColors.push_back(color.x);
|
||||
wallColors.push_back(color.y);
|
||||
wallColors.push_back(color.z);
|
||||
|
||||
// First triangle
|
||||
wallIndices.push_back(baseIndex);
|
||||
wallIndices.push_back(baseIndex + 1);
|
||||
wallIndices.push_back(baseIndex + 2);
|
||||
|
||||
// Second triangle
|
||||
wallIndices.push_back(baseIndex);
|
||||
wallIndices.push_back(baseIndex + 2);
|
||||
wallIndices.push_back(baseIndex + 3);
|
||||
|
||||
baseIndex += 4;
|
||||
|
||||
}
|
||||
|
||||
void addFloorVectors(std::vector<glm::vec3> _vertices, int& baseIndex, bool floor)
|
||||
{
|
||||
for (int i = 0; i + 2 < _vertices.size() ; i+=1)
|
||||
{
|
||||
this->floorVertices.push_back(_vertices[0].x);
|
||||
this->floorVertices.push_back(_vertices[0].y);
|
||||
this->floorVertices.push_back(_vertices[0].z);
|
||||
|
||||
this->floorVertices.push_back(_vertices[i + 1].x);
|
||||
this->floorVertices.push_back(_vertices[i + 1].y);
|
||||
this->floorVertices.push_back(_vertices[i + 1].z);
|
||||
|
||||
this->floorVertices.push_back(_vertices[i + 2].x);
|
||||
this->floorVertices.push_back(_vertices[i + 2].y);
|
||||
this->floorVertices.push_back(_vertices[i + 2].z);
|
||||
|
||||
glm::vec3 normal = glm::normalize(glm::cross(_vertices[i + 1] - _vertices[0], _vertices[i + 2] - _vertices[0]));
|
||||
normal = floor ? -normal : normal;
|
||||
|
||||
floorNormals.push_back(normal.x);
|
||||
floorNormals.push_back(normal.y);
|
||||
floorNormals.push_back(normal.z);
|
||||
|
||||
floorNormals.push_back(normal.x);
|
||||
floorNormals.push_back(normal.y);
|
||||
floorNormals.push_back(normal.z);
|
||||
|
||||
floorNormals.push_back(normal.x);
|
||||
floorNormals.push_back(normal.y);
|
||||
floorNormals.push_back(normal.z);
|
||||
|
||||
glm::vec3 color;
|
||||
color = floor ? glm::vec3(0.75f, 0.5f, 0.25f) : glm::vec3(0.25f, 0.5f, 0.75f);
|
||||
|
||||
this->floorColors.push_back(color.x);
|
||||
this->floorColors.push_back(color.y);
|
||||
this->floorColors.push_back(color.z);
|
||||
|
||||
this->floorColors.push_back(color.x);
|
||||
this->floorColors.push_back(color.y);
|
||||
this->floorColors.push_back(color.z);
|
||||
|
||||
this->floorColors.push_back(color.x);
|
||||
this->floorColors.push_back(color.y);
|
||||
this->floorColors.push_back(color.z);
|
||||
|
||||
floorIndices.push_back(baseIndex);
|
||||
floorIndices.push_back(baseIndex + 1);
|
||||
floorIndices.push_back(baseIndex + 2);
|
||||
|
||||
baseIndex += 3;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
#endif
|
||||
36
map_test.txt
Normal file
36
map_test.txt
Normal file
@@ -0,0 +1,36 @@
|
||||
[SECTOR]
|
||||
0 8 0.0 5.0 0 0.65 0.1 0.2
|
||||
8 3 1.0 4.0 0 0.65 0.65 0.2
|
||||
11 4 0.2 6.0 0 0.65 0.1 0.65
|
||||
15 5 0.0 3.0 0 0.1 0.1 0.65
|
||||
20 4 0.0 5.0 1 0.1 0.65 0.2
|
||||
|
||||
[WALL]
|
||||
40 10 20 10 0
|
||||
50 20 40 10 0
|
||||
50 30 50 20 0
|
||||
40 40 50 30 3
|
||||
20 40 40 40 0
|
||||
10 30 20 40 2
|
||||
10 20 10 30 0
|
||||
20 10 10 20 0
|
||||
|
||||
20 40 10 30 1
|
||||
10 50 20 40 0
|
||||
10 30 10 50 0
|
||||
|
||||
50 30 40 40 1
|
||||
60 50 50 30 0
|
||||
60 70 60 50 4
|
||||
40 40 60 70 0
|
||||
|
||||
70 40 60 50 0
|
||||
80 50 70 40 0
|
||||
80 70 80 50 0
|
||||
60 70 80 70 0
|
||||
60 50 60 70 3
|
||||
|
||||
25 25 25 26 0
|
||||
26 25 25 25 0
|
||||
26 26 26 25 0
|
||||
25 26 26 26 0
|
||||
9
map_test_2.txt
Normal file
9
map_test_2.txt
Normal file
@@ -0,0 +1,9 @@
|
||||
[SECTOR]
|
||||
1 0 4 -1.0 5.0
|
||||
|
||||
[WALL]
|
||||
# SECTOR 1: 0..7
|
||||
-10 -10 10 -10 0
|
||||
10 -10 10 10 0
|
||||
10 10 -10 10 0
|
||||
-10 10 -10 -10 0
|
||||
15
point_shadow_depth.frag
Normal file
15
point_shadow_depth.frag
Normal file
@@ -0,0 +1,15 @@
|
||||
|
||||
#version 330
|
||||
in vec4 FragPosition;
|
||||
|
||||
uniform vec3 lightPosition;
|
||||
uniform float farPlane;
|
||||
|
||||
void main()
|
||||
{
|
||||
float lightDistance = length(FragPosition.xyz - lightPosition);
|
||||
|
||||
lightDistance = lightDistance / farPlane;
|
||||
|
||||
gl_FragDepth = lightDistance;
|
||||
}
|
||||
25
point_shadow_depth.geom
Normal file
25
point_shadow_depth.geom
Normal file
@@ -0,0 +1,25 @@
|
||||
|
||||
|
||||
#version 330 core
|
||||
layout (triangles) in;
|
||||
layout (triangle_strip, max_vertices=18) out;
|
||||
|
||||
uniform mat4 shadowMatrices[6];
|
||||
|
||||
out vec4 FragPosition; // FragPos from GS (output per emitvertex)
|
||||
|
||||
void main()
|
||||
{
|
||||
for(int face = 0; face < 6; ++face)
|
||||
{
|
||||
gl_Layer = face; // built-in variable that specifies to which face we render.
|
||||
for(int i = 0; i < 3; ++i) // for each triangle's vertices
|
||||
{
|
||||
FragPosition = gl_in[i].gl_Position;
|
||||
gl_Position = shadowMatrices[face] * FragPosition;
|
||||
EmitVertex();
|
||||
}
|
||||
EndPrimitive();
|
||||
}
|
||||
}
|
||||
|
||||
10
point_shadow_depth.vert
Normal file
10
point_shadow_depth.vert
Normal file
@@ -0,0 +1,10 @@
|
||||
|
||||
#version 330 core
|
||||
layout (location = 0) in vec3 aPosition;
|
||||
|
||||
uniform mat4 model;
|
||||
|
||||
void main()
|
||||
{
|
||||
gl_Position = model * vec4(aPosition, 1.0);
|
||||
}
|
||||
172
shader.h
172
shader.h
@@ -2,154 +2,40 @@
|
||||
#ifndef SHADER_H
|
||||
#define SHADER_H
|
||||
|
||||
#include <glad/glad.h>
|
||||
|
||||
#include <string>
|
||||
#include <fstream>
|
||||
#include <sstream>
|
||||
#include <iostream>
|
||||
|
||||
#include <glad/glad.h>
|
||||
#include <glm/glm.hpp>
|
||||
#include <glm/gtc/type_ptr.hpp>
|
||||
|
||||
|
||||
// General purpose shader object. Compiles from file, generates
|
||||
// compile/link-time error messages and hosts several utility
|
||||
// functions for easy management.
|
||||
class Shader
|
||||
{
|
||||
public:
|
||||
unsigned int ID;
|
||||
|
||||
Shader(const char* vertexPath, const char* fragmentPath)
|
||||
{
|
||||
std::string vertexCode;
|
||||
std::string fragmentCode;
|
||||
std::ifstream vShaderFile;
|
||||
std::ifstream fShaderFile;
|
||||
|
||||
vShaderFile.exceptions(std::ifstream::failbit | std::ifstream::badbit);
|
||||
fShaderFile.exceptions(std::ifstream::failbit | std::ifstream::badbit);
|
||||
try
|
||||
{
|
||||
vShaderFile.open(vertexPath);
|
||||
fShaderFile.open(fragmentPath);
|
||||
std::stringstream vShaderStream, fShaderStream;
|
||||
vShaderStream << vShaderFile.rdbuf();
|
||||
fShaderStream << fShaderFile.rdbuf();
|
||||
vShaderFile.close();
|
||||
fShaderFile.close();
|
||||
vertexCode = vShaderStream.str();
|
||||
fragmentCode = fShaderStream.str();
|
||||
}
|
||||
catch (std::ifstream::failure e)
|
||||
{
|
||||
std::cout << "ERROR::SHADER::FILE_NOT_SUCCESFULLY_READ" << std::endl;
|
||||
}
|
||||
const char* vShaderCode = vertexCode.c_str();
|
||||
const char* fShaderCode = fragmentCode.c_str();
|
||||
|
||||
unsigned int vertex, fragment;
|
||||
|
||||
vertex = glCreateShader(GL_VERTEX_SHADER);
|
||||
glShaderSource(vertex, 1, &vShaderCode, NULL);
|
||||
glCompileShader(vertex);
|
||||
checkCompileErrors(vertex, "VERTEX");
|
||||
|
||||
fragment = glCreateShader(GL_FRAGMENT_SHADER);
|
||||
glShaderSource(fragment, 1, &fShaderCode, NULL);
|
||||
glCompileShader(fragment);
|
||||
checkCompileErrors(fragment, "FRAGMENT");
|
||||
|
||||
ID = glCreateProgram();
|
||||
glAttachShader(ID, vertex);
|
||||
glAttachShader(ID, fragment);
|
||||
glLinkProgram(ID);
|
||||
checkCompileErrors(ID, "PROGRAM");
|
||||
|
||||
glDeleteShader(vertex);
|
||||
glDeleteShader(fragment);
|
||||
}
|
||||
void use()
|
||||
{
|
||||
glUseProgram(ID);
|
||||
}
|
||||
// utility uniform functions
|
||||
// ------------------------------------------------------------------------
|
||||
void setBool(const std::string& name, bool value) const
|
||||
{
|
||||
glUniform1i(glGetUniformLocation(ID, name.c_str()), (int)value);
|
||||
}
|
||||
// ------------------------------------------------------------------------
|
||||
void setInt(const std::string& name, int value) const
|
||||
{
|
||||
glUniform1i(glGetUniformLocation(ID, name.c_str()), value);
|
||||
}
|
||||
// ------------------------------------------------------------------------
|
||||
void setFloat(const std::string& name, float value) const
|
||||
{
|
||||
glUniform1f(glGetUniformLocation(ID, name.c_str()), value);
|
||||
}
|
||||
// ------------------------------------------------------------------------
|
||||
void setVec2(const std::string& name, const glm::vec2& value) const
|
||||
{
|
||||
glUniform2fv(glGetUniformLocation(ID, name.c_str()), 1, &value[0]);
|
||||
}
|
||||
void setVec2(const std::string& name, float x, float y) const
|
||||
{
|
||||
glUniform2f(glGetUniformLocation(ID, name.c_str()), x, y);
|
||||
}
|
||||
// ------------------------------------------------------------------------
|
||||
void setVec3(const std::string& name, const glm::vec3& value) const
|
||||
{
|
||||
glUniform3fv(glGetUniformLocation(ID, name.c_str()), 1, &value[0]);
|
||||
}
|
||||
void setVec3(const std::string& name, float x, float y, float z) const
|
||||
{
|
||||
glUniform3f(glGetUniformLocation(ID, name.c_str()), x, y, z);
|
||||
}
|
||||
// ------------------------------------------------------------------------
|
||||
void setVec4(const std::string& name, const glm::vec4& value) const
|
||||
{
|
||||
glUniform4fv(glGetUniformLocation(ID, name.c_str()), 1, &value[0]);
|
||||
}
|
||||
void setVec4(const std::string& name, float x, float y, float z, float w) const
|
||||
{
|
||||
glUniform4f(glGetUniformLocation(ID, name.c_str()), x, y, z, w);
|
||||
}
|
||||
// ------------------------------------------------------------------------
|
||||
void setMat2(const std::string& name, const glm::mat2& mat) const
|
||||
{
|
||||
glUniformMatrix2fv(glGetUniformLocation(ID, name.c_str()), 1, GL_FALSE, &mat[0][0]);
|
||||
}
|
||||
// ------------------------------------------------------------------------
|
||||
void setMat3(const std::string& name, const glm::mat3& mat) const
|
||||
{
|
||||
glUniformMatrix3fv(glGetUniformLocation(ID, name.c_str()), 1, GL_FALSE, &mat[0][0]);
|
||||
}
|
||||
// ------------------------------------------------------------------------
|
||||
void setMat4(const std::string& name, const glm::mat4& mat) const
|
||||
{
|
||||
glUniformMatrix4fv(glGetUniformLocation(ID, name.c_str()), 1, GL_FALSE, &mat[0][0]);
|
||||
}
|
||||
|
||||
// state
|
||||
unsigned int ID;
|
||||
// constructor
|
||||
Shader() { }
|
||||
// sets the current shader as active
|
||||
Shader& Use();
|
||||
// compiles the shader from given source code
|
||||
void Compile(const char* vertexSource, const char* fragmentSource, const char* geometrySource = nullptr); // note: geometry source code is optional
|
||||
// utility functions
|
||||
void SetFloat(const char* name, float value, bool useShader = false);
|
||||
void SetInteger(const char* name, int value, bool useShader = false);
|
||||
void SetVector2f(const char* name, float x, float y, bool useShader = false);
|
||||
void SetVector2f(const char* name, const glm::vec2& value, bool useShader = false);
|
||||
void SetVector3f(const char* name, float x, float y, float z, bool useShader = false);
|
||||
void SetVector3f(const char* name, const glm::vec3& value, bool useShader = false);
|
||||
void SetVector4f(const char* name, float x, float y, float z, float w, bool useShader = false);
|
||||
void SetVector4f(const char* name, const glm::vec4& value, bool useShader = false);
|
||||
void SetMatrix4(const char* name, const glm::mat4& matrix, bool useShader = false);
|
||||
private:
|
||||
void checkCompileErrors(unsigned int shader, std::string type)
|
||||
{
|
||||
int success;
|
||||
char infoLog[1024];
|
||||
if (type != "PROGRAM")
|
||||
{
|
||||
glGetShaderiv(shader, GL_COMPILE_STATUS, &success);
|
||||
if (!success)
|
||||
{
|
||||
glGetShaderInfoLog(shader, 1024, NULL, infoLog);
|
||||
std::cout << "ERROR::SHADER_COMPILATION_ERROR of type: " << type << "\n" << infoLog << "\n -- ---------------------------------------------------- -- " << std::endl;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
glGetProgramiv(shader, GL_LINK_STATUS, &success);
|
||||
if (!success)
|
||||
{
|
||||
glGetProgramInfoLog(shader, 1024, NULL, infoLog);
|
||||
std::cout << "ERROR::PROGRAM_LINKING_ERROR of type: " << type << "\n" << infoLog << "\n -- ---------------------------------------------------- -- " << std::endl;
|
||||
}
|
||||
}
|
||||
}
|
||||
// checks if compilation or linking failed and if so, print the error logs
|
||||
void checkCompileErrors(unsigned int object, std::string type);
|
||||
};
|
||||
|
||||
#endif
|
||||
#endif
|
||||
71
wall.frag
Normal file
71
wall.frag
Normal file
@@ -0,0 +1,71 @@
|
||||
#version 330 core
|
||||
out vec4 FragColor;
|
||||
|
||||
uniform vec3 lightColor;
|
||||
uniform vec3 lightPos;
|
||||
uniform vec3 viewPos;
|
||||
|
||||
uniform sampler2D diffuseTexture;
|
||||
uniform samplerCube depthMap;
|
||||
|
||||
uniform float far_plane;
|
||||
uniform bool shadows;
|
||||
|
||||
uniform vec3 iResolution; // viewport resolution (in pixels)
|
||||
uniform float iTime; // shader playback time (in seconds)
|
||||
uniform float iTimeDelta; // render time (in seconds)
|
||||
uniform float iFrameRate; // shader frame rate
|
||||
uniform int iFrame; // shader playback frame
|
||||
uniform float iChannelTime[4]; // channel playback time (in seconds)
|
||||
uniform vec3 iChannelResolution[4]; // channel resolution (in pixels)
|
||||
uniform vec4 iMouse; // mouse pixel coords. xy: current (if MLB down), zw: click
|
||||
uniform sampler2D iChannel0; // input channel. XX = 2D/Cube
|
||||
uniform vec4 iDate; // (year, month, day, time in seconds)
|
||||
|
||||
in vec3 FragPos;
|
||||
in vec3 Normal;
|
||||
in vec3 Color;
|
||||
|
||||
float ShadowCalculation(vec3 fragPos)
|
||||
{
|
||||
// get vector between fragment position and light position
|
||||
vec3 fragToLight = fragPos - lightPos;
|
||||
// ise the fragment to light vector to sample from the depth map
|
||||
float closestDepth = texture(depthMap, fragToLight).r;
|
||||
// it is currently in linear range between [0,1], let's re-transform it back to original depth value
|
||||
closestDepth *= far_plane;
|
||||
// now get current linear depth as the length between the fragment and light position
|
||||
float currentDepth = length(fragToLight);
|
||||
// test for shadows
|
||||
float bias = 0.05; // we use a much larger bias since depth is now in [near_plane, far_plane] range
|
||||
float shadow = currentDepth - bias > closestDepth ? 1.0 : 0.0;
|
||||
// display closestDepth as debug (to visualize depth cubemap)
|
||||
//FragColor = vec4(vec3(closestDepth / far_plane), 1.0);
|
||||
|
||||
return shadow;
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
//vec3 color = texture(diffuseTexture, FragPos.xy).rgb;
|
||||
vec3 normal = normalize(Normal);
|
||||
vec3 lightColor = vec3(0.3);
|
||||
// ambient
|
||||
vec3 ambient = 0.3 * lightColor;
|
||||
// diffuse
|
||||
vec3 lightDir = normalize(lightPos - FragPos);
|
||||
float diff = max(dot(lightDir, normal), 0.0);
|
||||
vec3 diffuse = diff * lightColor;
|
||||
// specular
|
||||
vec3 viewDir = normalize(viewPos - FragPos);
|
||||
vec3 reflectDir = reflect(-lightDir, normal);
|
||||
float spec = 0.0;
|
||||
vec3 halfwayDir = normalize(lightDir + viewDir);
|
||||
spec = pow(max(dot(normal, halfwayDir), 0.0), 64.0);
|
||||
vec3 specular = spec * lightColor;
|
||||
// calculate shadow
|
||||
float shadow = ShadowCalculation(FragPos);
|
||||
vec3 lighting = (ambient + (1.0 - shadow) * (diffuse + specular)) * Color;
|
||||
|
||||
FragColor = vec4(lighting, 1.0);
|
||||
}
|
||||
22
wall.vert
Normal file
22
wall.vert
Normal file
@@ -0,0 +1,22 @@
|
||||
|
||||
#version 330 core
|
||||
layout (location = 0) in vec3 aPos;
|
||||
layout (location = 1) in vec3 aNormal;
|
||||
layout (location = 2) in vec3 aColor;
|
||||
|
||||
out vec3 FragPos;
|
||||
out vec3 Normal;
|
||||
out vec3 Color;
|
||||
|
||||
uniform mat4 model;
|
||||
uniform mat4 view;
|
||||
uniform mat4 projection;
|
||||
|
||||
void main()
|
||||
{
|
||||
FragPos = vec3(model * vec4(aPos, 1.0));
|
||||
Normal = mat3(transpose(inverse(model))) * aNormal;
|
||||
Color = aColor;
|
||||
|
||||
gl_Position = projection * view * vec4(FragPos, 1.0);
|
||||
}
|
||||
238
wall_test.frag
Normal file
238
wall_test.frag
Normal file
@@ -0,0 +1,238 @@
|
||||
#version 330 core
|
||||
out vec4 FragColor;
|
||||
|
||||
const int MAX_POINT_LIGHTS = 10;
|
||||
|
||||
in vec3 FragPosition;
|
||||
in vec3 Normal;
|
||||
in vec3 Color;
|
||||
|
||||
struct BaseLight
|
||||
{
|
||||
vec3 color;
|
||||
float ambientIntensity;
|
||||
float diffuseIntensity;
|
||||
};
|
||||
|
||||
struct Attenuation
|
||||
{
|
||||
float constant;
|
||||
float linear;
|
||||
float exponential;
|
||||
};
|
||||
|
||||
struct PointLight
|
||||
{
|
||||
BaseLight base;
|
||||
Attenuation atten;
|
||||
vec3 position;
|
||||
float farPlane;
|
||||
samplerCube depthMap;
|
||||
};
|
||||
|
||||
struct Material
|
||||
{
|
||||
vec3 ambientColor;
|
||||
vec3 diffuseColor;
|
||||
vec3 specularColor;
|
||||
float shininess;
|
||||
};
|
||||
|
||||
uniform int numOfPointLights;
|
||||
uniform PointLight pointLights[MAX_POINT_LIGHTS];
|
||||
uniform Material material;
|
||||
|
||||
//uniform sampler2D diffuseTexture;
|
||||
|
||||
|
||||
uniform vec3 viewPosition;
|
||||
|
||||
//uniform float farPlane;
|
||||
//uniform bool shadows;
|
||||
|
||||
vec3 gridSamplingDisk[20] = vec3[]
|
||||
(
|
||||
vec3(1, 1, 1), vec3( 1, -1, 1), vec3(-1, -1, 1), vec3(-1, 1, 1),
|
||||
vec3(1, 1, -1), vec3( 1, -1, -1), vec3(-1, -1, -1), vec3(-1, 1, -1),
|
||||
vec3(1, 1, 0), vec3( 1, -1, 0), vec3(-1, -1, 0), vec3(-1, 1, 0),
|
||||
vec3(1, 0, 1), vec3(-1, 0, 1), vec3( 1, 0, -1), vec3(-1, 0, -1),
|
||||
vec3(0, 1, 1), vec3( 0, -1, 1), vec3( 0, -1, -1), vec3( 0, 1, -1)
|
||||
);
|
||||
|
||||
int bayer[64] = int[64](
|
||||
0, 32, 8, 40, 2, 34, 10, 42,
|
||||
48, 16, 56, 24, 50, 18, 58, 26,
|
||||
12, 44, 4, 36, 14, 46, 6, 38,
|
||||
60, 28, 52, 20, 62, 30, 54, 22,
|
||||
3, 35, 11, 43, 1, 33, 9, 41,
|
||||
51, 19, 59, 27, 49, 17, 57, 25,
|
||||
15, 47, 7, 39, 13, 45, 5, 37,
|
||||
63, 31, 55, 23, 61, 29, 53, 21
|
||||
);
|
||||
|
||||
float ShadowCalculation(PointLight light, vec3 normal)
|
||||
{
|
||||
// get vector between fragment position and light position
|
||||
vec3 fragToLight = FragPosition - light.position;
|
||||
float currentDepth = length(fragToLight);
|
||||
|
||||
vec3 lightDir = normalize(light.position - FragPosition);
|
||||
|
||||
float shadow = 0.0;
|
||||
float bias = max(0.05 * (1.0 - dot(normal, lightDir)), 0.005);
|
||||
//float bias = 0.15;
|
||||
int samples = 20;
|
||||
float viewDistance = length(viewPosition - FragPosition);
|
||||
float diskRadius = (1.0 + (viewDistance / light.farPlane)) / 25.0;
|
||||
for(int i = 0; i < samples; ++i)
|
||||
{
|
||||
float closestDepth = texture(light.depthMap, fragToLight + gridSamplingDisk[i] * diskRadius).r;
|
||||
//FragColor = vec4(vec3(closestDepth / farPlane), 1.0);
|
||||
closestDepth *= light.farPlane; // undo mapping [0;1]
|
||||
if(currentDepth - bias > closestDepth)
|
||||
shadow += 1.0;
|
||||
}
|
||||
shadow /= float(samples);
|
||||
|
||||
//shadow = dither(shadow);
|
||||
|
||||
// display closestDepth as debug (to visualize depth cubemap)
|
||||
// FragColor = vec4(vec3(closestDepth / farPlane), 1.0);
|
||||
|
||||
return shadow;
|
||||
}
|
||||
|
||||
vec4 dither(vec4 color)
|
||||
{
|
||||
float downsampleFactor = 2;
|
||||
float ditherSize = 0.05;
|
||||
float colorSize = 8.0;
|
||||
|
||||
float _x = (gl_FragCoord.x/downsampleFactor);
|
||||
float _y = (gl_FragCoord.y/downsampleFactor);
|
||||
_x = mod(_x, 8);
|
||||
_y = mod(_y, 8);
|
||||
int _M = bayer[8*int(_y) + int(_x)];
|
||||
float _z = float(_M) * (1.0 / pow(8, 2.0));
|
||||
_z -= 0.5;
|
||||
|
||||
color.x += _z * ditherSize;
|
||||
color.y += _z * ditherSize;
|
||||
color.z += _z * ditherSize;
|
||||
|
||||
//color = greyscale;
|
||||
color = floor(color * (colorSize - 1) + 0.5) / (colorSize - 1);
|
||||
vec3 greyscale = vec3(0.2126 * color.r + 0.7152 * color.g + 0.0722 * color.b);
|
||||
|
||||
return color;
|
||||
}
|
||||
|
||||
/*vec3 diffuse(vec3 _lightColor, vec3 _lightPosition)
|
||||
{
|
||||
// diffuse
|
||||
vec3 lightDir = normalize(_lightPosition - FragPosition);
|
||||
vec3 lightDist = _lightPosition - FragPosition;
|
||||
float diff = max(dot(lightDir, Normal), 0.0);
|
||||
|
||||
float linear = 0.2;
|
||||
float exponential = 0.2;
|
||||
// Apply attenuation: light fades over distance
|
||||
float attenuation = 1.0 / (1.0 + (linear * length(lightDist)) + (exponential * pow(length(lightDist), 2.0)));
|
||||
|
||||
vec3 diffuse = diff * lightColor;
|
||||
return diffuse;
|
||||
}*/
|
||||
|
||||
/*vec3 specular(vec3 _lightPosition)
|
||||
{
|
||||
// specular
|
||||
vec3 lightDir = normalize(_lightPosition - FragPosition);
|
||||
vec3 viewDir = normalize(viewPosition - FragPosition);
|
||||
vec3 reflectDir = reflect(-lightDir, Normal);
|
||||
float spec = 0.0;
|
||||
vec3 halfwayDir = normalize(lightDir + viewDir);
|
||||
spec = pow(max(dot(Normal, halfwayDir), 0.0), 64.0);
|
||||
vec3 specular = spec * lightColor;
|
||||
return specular;
|
||||
}*/
|
||||
|
||||
vec4 calculateAmbient(BaseLight light)
|
||||
{
|
||||
vec4 ambientColor = vec4(light.color, 1.0) *
|
||||
light.ambientIntensity *
|
||||
vec4(material.ambientColor, 1.0);
|
||||
|
||||
return ambientColor;
|
||||
}
|
||||
|
||||
vec4 calculateDiffuse(BaseLight light, vec3 lightDirection, vec3 normal)
|
||||
{
|
||||
vec4 diffuseColor = vec4(0.0);
|
||||
float diffuseFactor = dot(normal, -lightDirection);
|
||||
|
||||
if (diffuseFactor > 0.0)
|
||||
{
|
||||
diffuseColor = vec4(light.color, 1.0) *
|
||||
light.diffuseIntensity *
|
||||
vec4(material.diffuseColor, 1.0) *
|
||||
diffuseFactor;
|
||||
}
|
||||
|
||||
return diffuseColor;
|
||||
}
|
||||
|
||||
vec4 calculateSpecular(BaseLight light, vec3 lightDirection, vec3 normal)
|
||||
{
|
||||
vec4 specularColor = vec4(0.0);
|
||||
vec3 pixelToCamera = normalize(viewPosition - FragPosition);
|
||||
vec3 lightReflect = normalize(reflect(lightDirection, normal));
|
||||
float specularFactor = dot(pixelToCamera, lightReflect);
|
||||
|
||||
if (specularFactor > 0.0)
|
||||
{
|
||||
specularColor = vec4(light.color, 1.0) *
|
||||
light.diffuseIntensity *
|
||||
vec4(material.specularColor, 1.0) *
|
||||
specularFactor;
|
||||
}
|
||||
|
||||
return specularColor * material.shininess;
|
||||
}
|
||||
|
||||
vec4 caclulatePointLight(int index, vec3 normal)
|
||||
{
|
||||
vec3 lightDirection = FragPosition - pointLights[index].position;
|
||||
float lightDistance = length(lightDirection);
|
||||
lightDirection = normalize(lightDirection);
|
||||
|
||||
float shadow = 1.0 - ShadowCalculation(pointLights[index], normal);
|
||||
|
||||
vec4 color = calculateAmbient(pointLights[index].base) +
|
||||
shadow *
|
||||
(calculateDiffuse(pointLights[index].base, lightDirection, normal) +
|
||||
calculateSpecular(pointLights[index].base, lightDirection, normal));
|
||||
|
||||
|
||||
// color = vec4(Color, 1.0);
|
||||
|
||||
float attenuation = pointLights[index].atten.constant +
|
||||
pointLights[index].atten.linear * lightDistance +
|
||||
pointLights[index].atten.exponential * (lightDistance * lightDistance);
|
||||
|
||||
return color / attenuation;
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
vec3 normal = normalize(Normal);
|
||||
vec4 totalLight = vec4(0.0, 0.0, 0.0, 0.0);
|
||||
|
||||
for (int i = 0; i < numOfPointLights; i++)
|
||||
{
|
||||
totalLight += caclulatePointLight(i, normal);
|
||||
}
|
||||
|
||||
//totalLight = dither(totalLight);
|
||||
FragColor = totalLight;
|
||||
}
|
||||
|
||||
22
wall_test.vert
Normal file
22
wall_test.vert
Normal file
@@ -0,0 +1,22 @@
|
||||
|
||||
#version 330 core
|
||||
layout (location = 0) in vec3 aPosition;
|
||||
layout (location = 1) in vec3 aNormal;
|
||||
layout (location = 2) in vec3 aColor;
|
||||
|
||||
out vec3 FragPosition;
|
||||
out vec3 Normal;
|
||||
out vec3 Color;
|
||||
|
||||
uniform mat4 model;
|
||||
uniform mat4 view;
|
||||
uniform mat4 projection;
|
||||
|
||||
void main()
|
||||
{
|
||||
FragPosition = vec3(model * vec4(aPosition, 1.0));
|
||||
Normal = mat3(transpose(inverse(model))) * aNormal;
|
||||
Color = aColor;
|
||||
|
||||
gl_Position = projection * view * vec4(FragPosition, 1.0);
|
||||
}
|
||||
Reference in New Issue
Block a user