OpenRaider  0.1.4-dev
Open Source Tomb Raider Game Engine implementation
Render.cpp
Go to the documentation of this file.
1 
9 #include <fstream>
10 #include <sstream>
11 
12 #include "global.h"
13 #include "Camera.h"
14 #include "Log.h"
15 #include "Menu.h"
16 #include "StaticMesh.h"
17 #include "World.h"
18 #include "system/Font.h"
19 #include "system/Shader.h"
20 #include "system/Window.h"
21 #include "Render.h"
22 
23 #include <glm/gtc/matrix_transform.hpp>
24 
25 #include "imgui/imgui.h"
26 #include "stb/stb_image_write.h"
27 
29 std::vector<Room*> Render::roomList;
30 bool Render::displayViewFrustum = false;
31 
33  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
34 
36  glm::vec4 color(1.0f, 1.0f, 1.0f, 1.0f);
37  drawTexture(0.0f, 0.0f, Window::getSize().x, Window::getSize().y,
39  return;
40  }
41 
42  if (mode == RenderMode::Wireframe) {
43  glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
44  } else {
45  glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
46  }
47 
48  if (Camera::update()) {
49  int r = Camera::getRoom();
50  clearRoomList();
51  if (r < 0) {
52  buildRoomList();
53  } else {
54  buildRoomList(r);
55  }
56  }
57 
58  glm::mat4 projection = Camera::getProjectionMatrix();
59  glm::mat4 view = Camera::getViewMatrix();
60  glm::mat4 VP = projection * view;
61 
62  for (int r = roomList.size() - 1; r >= 0; r--) {
63  roomList.at(r)->display(VP);
64 
65  for (int i = 0; i < getWorld().sizeEntity(); i++) {
66  auto& e = getWorld().getEntity(i);
67  if (roomList.at(r)->getIndex() == e.getRoom()) {
68  e.display(VP);
69  }
70  }
71  }
72 
75 
76  if (mode == RenderMode::Wireframe) {
77  glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
78  }
79 }
80 
81 void Render::buildRoomList(int room, int budget) {
82  if (room < -1) {
83  // Check if the camera currently is in a room...
84  for (int i = 0; i < getWorld().sizeRoom(); i++) {
86  buildRoomList(i, budget);
87  return;
88  }
89  }
90  buildRoomList(-1, budget);
91  } else if (room == -1) {
92  // Check visibility for all rooms!
93  for (int i = 0; i < getWorld().sizeRoom(); i++) {
94  if (Camera::boxInFrustum(getWorld().getRoom(i).getBoundingBox())) {
95  roomList.push_back(&getWorld().getRoom(i));
96  }
97  }
98  } else {
99  // Check visibility of room and connected rooms, recursively
100  if (Camera::boxInFrustum(getWorld().getRoom(room).getBoundingBox())) {
101  roomList.push_back(&getWorld().getRoom(room));
102  for (int i = 0; i < getWorld().getRoom(room).sizePortals(); i++) {
103  int r = getWorld().getRoom(room).getPortal(i).getAdjoiningRoom();
104  bool found = false;
105  for (int n = 0; n < roomList.size(); n++) {
106  if (roomList.at(n) == &getWorld().getRoom(r)) {
107  found = true;
108  break;
109  }
110  }
111  if (!found) {
112  if (budget > 0) {
113  buildRoomList(r, --budget);
114  }
115  }
116  }
117  }
118  }
119 }
120 
121 void Render::screenShot(const char* filenameBase) {
122  assert(filenameBase != nullptr);
123 
124  int w = Window::getSize().x;
125  int h = Window::getSize().y;
126  int sz = w * h;
127  unsigned char* image = new unsigned char[sz * 3];
128  glReadPixels(0, 0, w, h, GL_RGB, GL_UNSIGNED_BYTE, image);
129 
130  unsigned char* buffer = new unsigned char[sz * 3];
131  for (int x = 0; x < w; x++) {
132  for (int y = 0; y < h; y++) {
133  buffer[3 * (x + (y * w))] = image[3 * (x + ((h - y - 1) * w))];
134  buffer[(3 * (x + (y * w))) + 1] = image[(3 * (x + ((h - y - 1) * w))) + 1];
135  buffer[(3 * (x + (y * w))) + 2] = image[(3 * (x + ((h - y - 1) * w))) + 2];
136  }
137  }
138 
139  // Don't overwrite files
140  static int count = 0;
141  bool done = false;
142  std::string f;
143  while (!done) {
144  std::ostringstream filename;
145  filename << filenameBase << "-" << count++ << ".png";
146  f = filename.str();
147  std::ifstream fs(f);
148  done = !fs.good();
149  fs.close();
150  }
151 
152  if (!stbi_write_png(f.c_str(), w, h, 3, buffer, 0)) {
153  Log::get(LOG_ERROR) << "Error saving image \"" << f << "\"!" << Log::endl;
154  }
155 
156  delete [] image;
157  delete [] buffer;
158 }
159 
160 void Render::drawTexture(float x, float y, float w, float h, glm::vec4 color,
161  unsigned int texture, TextureStorage s) {
162  std::vector<glm::vec2> vertices;
163  std::vector<glm::vec2> uvs;
164 
165  vertices.push_back(glm::vec2(x, y + h));
166  vertices.push_back(glm::vec2(x + w, y + h));
167  vertices.push_back(glm::vec2(x, y));
168 
169  vertices.push_back(glm::vec2(x + w, y));
170  vertices.push_back(glm::vec2(x, y));
171  vertices.push_back(glm::vec2(x + w, y + h));
172 
173  uvs.push_back(glm::vec2(0.0f, 1.0f));
174  uvs.push_back(glm::vec2(1.0f, 1.0f));
175  uvs.push_back(glm::vec2(0.0f, 0.0f));
176 
177  uvs.push_back(glm::vec2(1.0f, 0.0f));
178  uvs.push_back(glm::vec2(0.0f, 0.0f));
179  uvs.push_back(glm::vec2(1.0f, 1.0f));
180 
181  static ShaderBuffer vert, uv;
182  vert.bufferData(vertices);
183  uv.bufferData(uvs);
184 
185  Shader::drawGL(vert, uv, color, texture, s);
186 }
187 
188 static const int modeStringCount = 4;
189 static const char* modeStrings[modeStringCount] = {
190  "Splash", "Texture", "Wireframe", "Solid"
191 };
192 
194  if (ImGui::CollapsingHeader("Render Settings##render")) {
195  int item = 0;
196  if (mode == RenderMode::Texture)
197  item = 1;
198  else if (mode == RenderMode::Wireframe)
199  item = 2;
200  else if (mode == RenderMode::Solid)
201  item = 3;
202  if (ImGui::Combo("Render Mode##render", &item, modeStrings, modeStringCount)) {
203  if (item == 0)
205  else if (item == 1)
207  else if (item == 2)
209  else if (item == 3)
211  }
212 
214  ImGui::Text("Camera:");
215  bool updateViewFrustum = Camera::getUpdateViewFrustum();
216  if (ImGui::Checkbox("Update Frustum##render", &updateViewFrustum)) {
217  Camera::setUpdateViewFrustum(updateViewFrustum);
218  }
219  ImGui::SameLine();
220  ImGui::Checkbox("Show Frustum##render", &displayViewFrustum);
221  ImGui::SameLine();
222  bool showOverlay = Camera::getShowOverlay();
223  if (ImGui::Checkbox("Overlay", &showOverlay)) {
224  Camera::setShowOverlay(showOverlay);
225  }
226  if (ImGui::Button("Reset Room ID")) {
227  Camera::setRoom(-1);
228  }
229 
231  ImGui::Text("Bounding Boxes:");
232  bool showBoundingBox = Room::getShowBoundingBox();
233  if (ImGui::Checkbox("Room##bbox", &showBoundingBox)) {
234  Room::setShowBoundingBox(showBoundingBox);
235  }
236  ImGui::SameLine();
237  bool showBoundingBox2 = StaticMesh::getShowBoundingBox();
238  if (ImGui::Checkbox("StaticMesh##bbox", &showBoundingBox2)) {
239  StaticMesh::setShowBoundingBox(showBoundingBox2);
240  }
241  ImGui::SameLine();
242  bool showFontBox = Font::getShowFontBox();
243  if (ImGui::Checkbox("Font##bbox", &showFontBox)) {
244  Font::setShowFontBox(showFontBox);
245  }
246 
248  ImGui::Text("Renderable Objects:");
249  ImGui::Text("Room: ");
250  ImGui::SameLine();
251  bool showRoomGeometry = Room::getShowRoomGeometry();
252  if (ImGui::Checkbox("Geometry##renderroom", &showRoomGeometry)) {
253  Room::setShowRoomGeometry(showRoomGeometry);
254  }
255  ImGui::SameLine();
256  bool showRoomModels = Room::getShowRoomModels();
257  if (ImGui::Checkbox("Models##renderroom", &showRoomModels)) {
258  Room::setShowRoomModels(showRoomModels);
259  }
260  ImGui::SameLine();
261  bool showRoomSprites = Room::getShowRoomSprites();
262  if (ImGui::Checkbox("Sprites##renderroom", &showRoomSprites)) {
263  Room::setShowRoomSprites(showRoomSprites);
264  }
265 
266  ImGui::Text("Entity: ");
267  ImGui::SameLine();
268  bool showEntitySprites = Entity::getShowEntitySprites();
269  if (ImGui::Checkbox("Sprites##renderentity", &showEntitySprites)) {
270  Entity::setShowEntitySprites(showEntitySprites);
271  }
272  ImGui::SameLine();
273  bool showEntityMeshes = Entity::getShowEntityMeshes();
274  if (ImGui::Checkbox("Meshes##renderentity", &showEntityMeshes)) {
275  Entity::setShowEntityMeshes(showEntityMeshes);
276  }
277  ImGui::SameLine();
278  bool showEntityModels = Entity::getShowEntityModels();
279  if (ImGui::Checkbox("Models##renderentity", &showEntityModels)) {
280  Entity::setShowEntityModels(showEntityModels);
281  }
282 
284  if (ImGui::Button("New Splash##render")) {
286  }
287  ImGui::SameLine();
288  if (ImGui::Button("New Menu##render")) {
290  }
291  }
292 }
293 
static bool boxInFrustum(BoundingBox b)
Definition: Camera.cpp:379
void bufferData(int elem, int size, void *data)
Definition: Shader.cpp:18
static glm::mat4 getViewMatrix()
Definition: Camera.h:31
IMGUI_API bool Checkbox(const char *label, bool *v)
Definition: imgui.cpp:5128
static int initializeSplash()
static bool getShowEntitySprites()
Definition: Entity.h:31
IMGUI_API bool CollapsingHeader(const char *label, const char *str_id=NULL, bool display_frame=true, bool default_open=false)
Definition: imgui.cpp:4332
static bool getShowRoomSprites()
Definition: Room.h:61
static bool getUpdateViewFrustum()
Definition: Camera.h:40
static bool getShowOverlay()
Definition: Camera.h:46
Room & getRoom(unsigned long index)
Definition: World.cpp:33
Static Model Meshes.
static void displayFrustum(glm::mat4 MVP)
Definition: Camera.cpp:396
OpenGL Shader Implementation.
RenderMode
Definition: Render.h:19
World Model.
static void drawTexture(float x, float y, float w, float h, glm::vec4 color, unsigned int texture, TextureStorage s)
Definition: Render.cpp:160
static void displayUI()
Definition: Render.cpp:193
static glm::vec3 getPosition()
Definition: Camera.h:27
Main Menu.
static bool getShowFontBox()
Definition: Font.h:38
World & getWorld()
Definition: main.cpp:32
static void buildRoomList(int room=-2, int budget=10)
Definition: Render.cpp:81
Included everywhere.
static void setRoom(int r)
Definition: Camera.h:42
unsigned long sizeEntity()
Definition: World.cpp:68
static void setShowFontBox(bool s)
Definition: Font.h:37
static LogLevel & get(int level)
Definition: Log.cpp:14
Portal & getPortal(unsigned long index)
Definition: Room.h:52
static void setShowRoomModels(bool s)
Definition: Room.h:57
static bool getShowRoomModels()
Definition: Room.h:58
static void display()
Definition: Render.cpp:32
static void setShowBoundingBox(bool s)
Definition: StaticMesh.h:23
int stbi_write_png(char const *filename, int w, int h, int comp, const void *data, int stride_in_bytes)
Global Logging Utility.
static void setShowEntityMeshes(bool s)
Definition: Entity.h:32
Windowing Interface.
Entity & getEntity(unsigned long index)
Definition: World.cpp:72
#define assert(x)
Definition: global.h:124
unsigned long sizePortals()
Definition: Room.h:51
IMGUI_API bool Button(const char *label, const ImVec2 &size=ImVec2(0, 0), bool repeat_when_held=false)
Definition: imgui.cpp:4055
static void drawGL(ShaderBuffer &vertices, ShaderBuffer &uvs, glm::vec4 color, unsigned int texture, TextureStorage store=TextureStorage::SYSTEM, unsigned int mode=GL_TRIANGLES, ShaderTexture *target=nullptr, Shader &shader=textShader)
Definition: Shader.cpp:278
static int getRoom()
Definition: Camera.h:43
World Renderer.
static void setShowOverlay(bool s)
Definition: Camera.h:45
static void setUpdateViewFrustum(bool u)
Definition: Camera.h:39
Font Interface.
static const char endl
Definition: Log.h:35
void display(glm::mat4 VP)
Definition: Entity.cpp:24
#define TEXTURE_SPLASH
IMGUI_API void SameLine(int column_x=0, int spacing_w=-1)
Definition: imgui.cpp:6551
static const int modeStringCount
Definition: Render.cpp:188
#define LOG_ERROR
Definition: Log.h:19
static bool getShowBoundingBox()
Definition: StaticMesh.h:24
static void screenShot(const char *filenameBase)
Definition: Render.cpp:121
TextureStorage
bool inBox(glm::vec3 p)
Definition: RoomData.h:27
static glm::mat4 getProjectionMatrix()
Definition: Camera.h:30
BoundingBox & getBoundingBox()
Definition: Room.h:37
static std::vector< Room * > roomList
Definition: Render.h:49
static bool getShowRoomGeometry()
Definition: Room.h:64
IMGUI_API bool Combo(const char *label, int *current_item, const char **items, int items_count, int height_in_items=-1)
Definition: imgui.cpp:5983
IMGUI_API void Text(const char *fmt,...)
Definition: imgui.cpp:3802
static int initialize()
Definition: Menu.cpp:32
int getAdjoiningRoom()
Definition: RoomData.h:83
IMGUI_API void Separator()
Definition: imgui.cpp:6448
static void clearRoomList()
Definition: Render.h:29
static void setShowRoomSprites(bool s)
Definition: Room.h:60
static void setShowEntityModels(bool s)
Definition: Entity.h:34
Camera, View Frustum.
static bool displayViewFrustum
Definition: Render.h:51
unsigned long sizeRoom()
Definition: World.cpp:29
static RenderMode mode
Definition: Render.h:48
static bool getShowEntityModels()
Definition: Entity.h:35
static bool update()
Definition: Camera.cpp:159
static void setShowRoomGeometry(bool s)
Definition: Room.h:63
static void setShowEntitySprites(bool s)
Definition: Entity.h:30
static glm::i32vec2 getSize()
Definition: Window.cpp:71
static const char * modeStrings[modeStringCount]
Definition: Render.cpp:189
static bool getShowBoundingBox()
Definition: Room.h:55
static void setShowBoundingBox(bool s)
Definition: Room.h:54
static bool getShowEntityMeshes()
Definition: Entity.h:33