diff options
| author | 2014-04-06 16:55:39 -0400 | |
|---|---|---|
| committer | 2014-04-06 16:55:39 -0400 | |
| commit | 080f847550b028e59f5a37471e00b8a27e6f1b23 (patch) | |
| tree | 05c3ab4934da0954e3ea895c172126d5b0915171 /src | |
| parent | set window size to correspond to framebuffer sizes (diff) | |
| download | yuzu-080f847550b028e59f5a37471e00b8a27e6f1b23.tar.gz yuzu-080f847550b028e59f5a37471e00b8a27e6f1b23.tar.xz yuzu-080f847550b028e59f5a37471e00b8a27e6f1b23.zip | |
added initial renderer code
Diffstat (limited to 'src')
| -rw-r--r-- | src/video_core/src/renderer_base.h | 26 | ||||
| -rw-r--r-- | src/video_core/src/renderer_opengl/renderer_opengl.cpp | 340 | ||||
| -rw-r--r-- | src/video_core/src/renderer_opengl/renderer_opengl.h | 138 | ||||
| -rw-r--r-- | src/video_core/src/video_core.cpp | 19 | ||||
| -rw-r--r-- | src/video_core/src/video_core.h | 17 | ||||
| -rw-r--r-- | src/video_core/video_core.vcxproj | 2 | ||||
| -rw-r--r-- | src/video_core/video_core.vcxproj.filters | 11 |
7 files changed, 534 insertions, 19 deletions
diff --git a/src/video_core/src/renderer_base.h b/src/video_core/src/renderer_base.h index 9cd02e0b4..50f1475b2 100644 --- a/src/video_core/src/renderer_base.h +++ b/src/video_core/src/renderer_base.h | |||
| @@ -51,6 +51,9 @@ public: | |||
| 51 | ~RendererBase() { | 51 | ~RendererBase() { |
| 52 | } | 52 | } |
| 53 | 53 | ||
| 54 | /// Swap buffers (render frame) | ||
| 55 | virtual void SwapBuffers() = 0; | ||
| 56 | |||
| 54 | /** | 57 | /** |
| 55 | * Blits the EFB to the external framebuffer (XFB) | 58 | * Blits the EFB to the external framebuffer (XFB) |
| 56 | * @param src_rect Source rectangle in EFB to copy | 59 | * @param src_rect Source rectangle in EFB to copy |
| @@ -71,6 +74,24 @@ public: | |||
| 71 | virtual void Clear(const Rect& rect, bool enable_color, bool enable_alpha, bool enable_z, | 74 | virtual void Clear(const Rect& rect, bool enable_color, bool enable_alpha, bool enable_z, |
| 72 | u32 color, u32 z) = 0; | 75 | u32 color, u32 z) = 0; |
| 73 | 76 | ||
| 77 | /// Sets the renderer viewport location, width, and height | ||
| 78 | virtual void SetViewport(int x, int y, int width, int height) = 0; | ||
| 79 | |||
| 80 | /// Sets the renderer depthrange, znear and zfar | ||
| 81 | virtual void SetDepthRange(double znear, double zfar) = 0; | ||
| 82 | |||
| 83 | /* Sets the scissor box | ||
| 84 | * @param rect Renderer rectangle to set scissor box to | ||
| 85 | */ | ||
| 86 | virtual void SetScissorBox(const Rect& rect) = 0; | ||
| 87 | |||
| 88 | /** | ||
| 89 | * Sets the line and point size | ||
| 90 | * @param line_width Line width to use | ||
| 91 | * @param point_size Point size to use | ||
| 92 | */ | ||
| 93 | virtual void SetLinePointSize(f32 line_width, f32 point_size) = 0; | ||
| 94 | |||
| 74 | /** | 95 | /** |
| 75 | * Set a specific render mode | 96 | * Set a specific render mode |
| 76 | * @param flag Render flags mode to enable | 97 | * @param flag Render flags mode to enable |
| @@ -95,11 +116,6 @@ public: | |||
| 95 | /// Shutdown the renderer | 116 | /// Shutdown the renderer |
| 96 | virtual void ShutDown() = 0; | 117 | virtual void ShutDown() = 0; |
| 97 | 118 | ||
| 98 | /// Converts EFB rectangle coordinates to renderer rectangle coordinates | ||
| 99 | //static Rect EFBToRendererRect(const Rect& rect) { | ||
| 100 | // return Rect(rect.x0_, kGCEFBHeight - rect.y0_, rect.x1_, kGCEFBHeight - rect.y1_); | ||
| 101 | //} | ||
| 102 | |||
| 103 | // Getter/setter functions: | 119 | // Getter/setter functions: |
| 104 | // ------------------------ | 120 | // ------------------------ |
| 105 | 121 | ||
diff --git a/src/video_core/src/renderer_opengl/renderer_opengl.cpp b/src/video_core/src/renderer_opengl/renderer_opengl.cpp new file mode 100644 index 000000000..133740a74 --- /dev/null +++ b/src/video_core/src/renderer_opengl/renderer_opengl.cpp | |||
| @@ -0,0 +1,340 @@ | |||
| 1 | /** | ||
| 2 | * Copyright (C) 2014 Citra Emulator | ||
| 3 | * | ||
| 4 | * @file renderer_opengl.cpp | ||
| 5 | * @author bunnei | ||
| 6 | * @date 2014-04-05 | ||
| 7 | * @brief Renderer for OpenGL 3.x | ||
| 8 | * | ||
| 9 | * @section LICENSE | ||
| 10 | * This program is free software; you can redistribute it and/or | ||
| 11 | * modify it under the terms of the GNU General Public License as | ||
| 12 | * published by the Free Software Foundation; either version 2 of | ||
| 13 | * the License, or (at your option) any later version. | ||
| 14 | * | ||
| 15 | * This program is distributed in the hope that it will be useful, but | ||
| 16 | * WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 17 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
| 18 | * General Public License for more details at | ||
| 19 | * http://www.gnu.org/copyleft/gpl.html | ||
| 20 | * | ||
| 21 | * Official project repository can be found at: | ||
| 22 | * http://code.google.com/p/gekko-gc-emu/ | ||
| 23 | */ | ||
| 24 | |||
| 25 | #include "video_core.h" | ||
| 26 | #include "renderer_opengl/renderer_opengl.h" | ||
| 27 | |||
| 28 | /// RendererOpenGL constructor | ||
| 29 | RendererOpenGL::RendererOpenGL() { | ||
| 30 | memset(fbo_, 0, sizeof(fbo_)); | ||
| 31 | memset(fbo_rbo_, 0, sizeof(fbo_rbo_)); | ||
| 32 | memset(fbo_depth_buffers_, 0, sizeof(fbo_depth_buffers_)); | ||
| 33 | |||
| 34 | resolution_width_ = max(VideoCore::kScreenTopWidth, VideoCore::kScreenBottomWidth); | ||
| 35 | resolution_height_ = VideoCore::kScreenTopHeight + VideoCore::kScreenBottomHeight; | ||
| 36 | } | ||
| 37 | |||
| 38 | /// RendererOpenGL destructor | ||
| 39 | RendererOpenGL::~RendererOpenGL() { | ||
| 40 | } | ||
| 41 | |||
| 42 | |||
| 43 | /// Swap buffers (render frame) | ||
| 44 | void RendererOpenGL::SwapBuffers() { | ||
| 45 | |||
| 46 | glClearColor(1.0f, 1.0f, 0.0f, 1.0f); | ||
| 47 | glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); | ||
| 48 | |||
| 49 | ResetRenderState(); | ||
| 50 | |||
| 51 | // EFB->XFB copy | ||
| 52 | // TODO(bunnei): This is a hack and does not belong here. The copy should be triggered by some | ||
| 53 | // register write We're also treating both framebuffers as a single one in OpenGL. | ||
| 54 | Rect framebuffer_size(0, 0, VideoCore::kScreenTopWidth, | ||
| 55 | VideoCore::kScreenTopHeight + VideoCore::kScreenBottomHeight); | ||
| 56 | CopyToXFB(framebuffer_size, framebuffer_size); | ||
| 57 | |||
| 58 | // XFB->Window copy | ||
| 59 | RenderFramebuffer(); | ||
| 60 | |||
| 61 | // Swap buffers | ||
| 62 | render_window_->PollEvents(); | ||
| 63 | render_window_->SwapBuffers(); | ||
| 64 | |||
| 65 | // Switch back to EFB and clear | ||
| 66 | glBindFramebuffer(GL_DRAW_FRAMEBUFFER, fbo_[kFramebuffer_EFB]); | ||
| 67 | |||
| 68 | RestoreRenderState(); | ||
| 69 | } | ||
| 70 | |||
| 71 | /** | ||
| 72 | * Blits the EFB to the external framebuffer (XFB) | ||
| 73 | * @param src_rect Source rectangle in EFB to copy | ||
| 74 | * @param dst_rect Destination rectangle in EFB to copy to | ||
| 75 | * @param dest_height Destination height in pixels | ||
| 76 | */ | ||
| 77 | void RendererOpenGL::CopyToXFB(const Rect& src_rect, const Rect& dst_rect) { | ||
| 78 | ResetRenderState(); | ||
| 79 | |||
| 80 | // Render target is destination framebuffer | ||
| 81 | glBindFramebuffer(GL_DRAW_FRAMEBUFFER, fbo_[kFramebuffer_VirtualXFB]); | ||
| 82 | glViewport(0, 0, resolution_width_, resolution_height_); | ||
| 83 | |||
| 84 | // Render source is our EFB | ||
| 85 | glBindFramebuffer(GL_READ_FRAMEBUFFER, fbo_[kFramebuffer_EFB]); | ||
| 86 | glReadBuffer(GL_COLOR_ATTACHMENT0); | ||
| 87 | |||
| 88 | // Blit | ||
| 89 | glBlitFramebuffer(src_rect.x0_, src_rect.y0_, src_rect.x1_, src_rect.y1_, | ||
| 90 | dst_rect.x0_, dst_rect.y1_, dst_rect.x1_, dst_rect.y0_, | ||
| 91 | GL_COLOR_BUFFER_BIT, GL_LINEAR); | ||
| 92 | |||
| 93 | glBindFramebuffer(GL_READ_FRAMEBUFFER, 0); | ||
| 94 | |||
| 95 | RestoreRenderState(); | ||
| 96 | } | ||
| 97 | |||
| 98 | /** | ||
| 99 | * Clear the screen | ||
| 100 | * @param rect Screen rectangle to clear | ||
| 101 | * @param enable_color Enable color clearing | ||
| 102 | * @param enable_alpha Enable alpha clearing | ||
| 103 | * @param enable_z Enable depth clearing | ||
| 104 | * @param color Clear color | ||
| 105 | * @param z Clear depth | ||
| 106 | */ | ||
| 107 | void RendererOpenGL::Clear(const Rect& rect, bool enable_color, bool enable_alpha, bool enable_z, | ||
| 108 | u32 color, u32 z) { | ||
| 109 | GLboolean const color_mask = enable_color ? GL_TRUE : GL_FALSE; | ||
| 110 | GLboolean const alpha_mask = enable_alpha ? GL_TRUE : GL_FALSE; | ||
| 111 | |||
| 112 | ResetRenderState(); | ||
| 113 | |||
| 114 | // Clear color | ||
| 115 | glColorMask(color_mask, color_mask, color_mask, alpha_mask); | ||
| 116 | glClearColor(float((color >> 16) & 0xFF) / 255.0f, float((color >> 8) & 0xFF) / 255.0f, | ||
| 117 | float((color >> 0) & 0xFF) / 255.0f, float((color >> 24) & 0xFF) / 255.0f); | ||
| 118 | |||
| 119 | // Clear depth | ||
| 120 | glDepthMask(enable_z ? GL_TRUE : GL_FALSE); | ||
| 121 | glClearDepth(float(z & 0xFFFFFF) / float(0xFFFFFF)); | ||
| 122 | |||
| 123 | // Specify the rectangle of the EFB to clear | ||
| 124 | glEnable(GL_SCISSOR_TEST); | ||
| 125 | glScissor(rect.x0_, rect.y1_, rect.width(), rect.height()); | ||
| 126 | |||
| 127 | // Clear it! | ||
| 128 | glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); | ||
| 129 | |||
| 130 | RestoreRenderState(); | ||
| 131 | } | ||
| 132 | |||
| 133 | /// Sets the renderer viewport location, width, and height | ||
| 134 | void RendererOpenGL::SetViewport(int x, int y, int width, int height) { | ||
| 135 | glViewport(x, y, width, height); | ||
| 136 | } | ||
| 137 | |||
| 138 | /// Sets the renderer depthrange, znear and zfar | ||
| 139 | void RendererOpenGL::SetDepthRange(double znear, double zfar) { | ||
| 140 | glDepthRange(znear, zfar); | ||
| 141 | } | ||
| 142 | |||
| 143 | /* Sets the scissor box | ||
| 144 | * @param rect Renderer rectangle to set scissor box to | ||
| 145 | */ | ||
| 146 | void RendererOpenGL::SetScissorBox(const Rect& rect) { | ||
| 147 | glScissor(rect.x0_, rect.y1_, rect.width(), rect.height()); | ||
| 148 | } | ||
| 149 | |||
| 150 | /** | ||
| 151 | * Sets the line and point size | ||
| 152 | * @param line_width Line width to use | ||
| 153 | * @param point_size Point size to use | ||
| 154 | */ | ||
| 155 | void RendererOpenGL::SetLinePointSize(f32 line_width, f32 point_size) { | ||
| 156 | glLineWidth((GLfloat)line_width); | ||
| 157 | glPointSize((GLfloat)point_size); | ||
| 158 | } | ||
| 159 | |||
| 160 | /** | ||
| 161 | * Set a specific render mode | ||
| 162 | * @param flag Render flags mode to enable | ||
| 163 | */ | ||
| 164 | void RendererOpenGL::SetMode(kRenderMode flags) { | ||
| 165 | if(flags & kRenderMode_ZComp) { | ||
| 166 | glColorMask(GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE); | ||
| 167 | } | ||
| 168 | if(flags & kRenderMode_Multipass) { | ||
| 169 | glEnable(GL_DEPTH_TEST); | ||
| 170 | glDepthMask(GL_FALSE); | ||
| 171 | glDepthFunc(GL_EQUAL); | ||
| 172 | } | ||
| 173 | if (flags & kRenderMode_UseDstAlpha) { | ||
| 174 | glColorMask(GL_FALSE, GL_FALSE, GL_FALSE, GL_TRUE); | ||
| 175 | glDisable(GL_BLEND); | ||
| 176 | } | ||
| 177 | last_mode_ |= flags; | ||
| 178 | } | ||
| 179 | |||
| 180 | /// Reset the full renderer API to the NULL state | ||
| 181 | void RendererOpenGL::ResetRenderState() { | ||
| 182 | glDisable(GL_SCISSOR_TEST); | ||
| 183 | glDisable(GL_DEPTH_TEST); | ||
| 184 | glDisable(GL_CULL_FACE); | ||
| 185 | glDisable(GL_BLEND); | ||
| 186 | glDepthMask(GL_FALSE); | ||
| 187 | glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE); | ||
| 188 | } | ||
| 189 | |||
| 190 | /// Restore the full renderer API state - As the game set it | ||
| 191 | void RendererOpenGL::RestoreRenderState() { | ||
| 192 | |||
| 193 | glBindFramebuffer(GL_DRAW_FRAMEBUFFER, fbo_[kFramebuffer_EFB]); | ||
| 194 | |||
| 195 | //gp::XF_UpdateViewport(); | ||
| 196 | SetViewport(0, 0, resolution_width_, resolution_height_); | ||
| 197 | SetDepthRange(0.0f, 1.0f); | ||
| 198 | |||
| 199 | //SetGenerationMode(); | ||
| 200 | glEnable(GL_CULL_FACE); | ||
| 201 | glFrontFace(GL_CCW); | ||
| 202 | |||
| 203 | //glEnable(GL_SCISSOR_TEST); | ||
| 204 | //gp::BP_SetScissorBox(); | ||
| 205 | glDisable(GL_SCISSOR_TEST); | ||
| 206 | |||
| 207 | //SetColorMask(gp::g_bp_regs.cmode0); | ||
| 208 | glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE); | ||
| 209 | |||
| 210 | //SetDepthMode(); | ||
| 211 | glDisable(GL_DEPTH_TEST); | ||
| 212 | glDepthMask(GL_FALSE); | ||
| 213 | |||
| 214 | //SetBlendMode(gp::g_bp_regs.cmode0, gp::g_bp_regs.cmode1, true); | ||
| 215 | //if (common::g_config->current_renderer_config().enable_wireframe) { | ||
| 216 | // glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); | ||
| 217 | //} else { | ||
| 218 | // glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); | ||
| 219 | //} | ||
| 220 | } | ||
| 221 | |||
| 222 | /// Initialize the FBO | ||
| 223 | void RendererOpenGL::InitFramebuffer() { | ||
| 224 | // TODO(en): This should probably be implemented with the top screen and bottom screen as | ||
| 225 | // separate framebuffers | ||
| 226 | |||
| 227 | // Init the FBOs | ||
| 228 | // ------------- | ||
| 229 | |||
| 230 | glGenFramebuffers(kMaxFramebuffers, fbo_); // Generate primary framebuffer | ||
| 231 | glGenRenderbuffers(kMaxFramebuffers, fbo_rbo_); // Generate primary RBOs | ||
| 232 | glGenRenderbuffers(kMaxFramebuffers, fbo_depth_buffers_); // Generate primary depth buffer | ||
| 233 | |||
| 234 | for (int i = 0; i < kMaxFramebuffers; i++) { | ||
| 235 | // Generate color buffer storage | ||
| 236 | glBindRenderbuffer(GL_RENDERBUFFER, fbo_rbo_[i]); | ||
| 237 | glRenderbufferStorage(GL_RENDERBUFFER, GL_RGBA8, resolution_width_, resolution_height_); | ||
| 238 | |||
| 239 | // Generate depth buffer storage | ||
| 240 | glBindRenderbuffer(GL_RENDERBUFFER, fbo_depth_buffers_[i]); | ||
| 241 | glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT32, resolution_width_, | ||
| 242 | resolution_height_); | ||
| 243 | |||
| 244 | // Attach the buffers | ||
| 245 | glBindFramebuffer(GL_DRAW_FRAMEBUFFER, fbo_[i]); | ||
| 246 | glFramebufferRenderbuffer(GL_DRAW_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, | ||
| 247 | GL_RENDERBUFFER, fbo_depth_buffers_[i]); | ||
| 248 | glFramebufferRenderbuffer(GL_DRAW_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, | ||
| 249 | GL_RENDERBUFFER, fbo_rbo_[i]); | ||
| 250 | |||
| 251 | // Check for completeness | ||
| 252 | if (GL_FRAMEBUFFER_COMPLETE == glCheckFramebufferStatus(GL_DRAW_FRAMEBUFFER)) { | ||
| 253 | NOTICE_LOG(RENDER, "framebuffer(%d) initialized ok", i); | ||
| 254 | } else { | ||
| 255 | ERROR_LOG(RENDER, "couldn't create OpenGL frame buffer"); | ||
| 256 | exit(1); | ||
| 257 | } | ||
| 258 | } | ||
| 259 | glBindFramebuffer(GL_FRAMEBUFFER, 0); // Unbind our frame buffer(s) | ||
| 260 | } | ||
| 261 | |||
| 262 | /// Blit the FBO to the OpenGL default framebuffer | ||
| 263 | void RendererOpenGL::RenderFramebuffer() { | ||
| 264 | |||
| 265 | // Render target is default framebuffer | ||
| 266 | glBindFramebuffer(GL_DRAW_FRAMEBUFFER, 0); | ||
| 267 | glViewport(0, 0, resolution_width_, resolution_height_); | ||
| 268 | |||
| 269 | // Render source is our XFB | ||
| 270 | glBindFramebuffer(GL_READ_FRAMEBUFFER, fbo_[kFramebuffer_VirtualXFB]); | ||
| 271 | glReadBuffer(GL_COLOR_ATTACHMENT0); | ||
| 272 | |||
| 273 | // Blit | ||
| 274 | glBlitFramebuffer(0, 0, resolution_width_, resolution_height_, 0, 0, | ||
| 275 | render_window_->client_area_width(), render_window_->client_area_height(), | ||
| 276 | GL_COLOR_BUFFER_BIT, GL_LINEAR); | ||
| 277 | |||
| 278 | // Update the FPS count | ||
| 279 | UpdateFramerate(); | ||
| 280 | |||
| 281 | // Rebind EFB | ||
| 282 | glBindFramebuffer(GL_DRAW_FRAMEBUFFER, fbo_[kFramebuffer_EFB]); | ||
| 283 | |||
| 284 | current_frame_++; | ||
| 285 | } | ||
| 286 | |||
| 287 | /// Updates the framerate | ||
| 288 | void RendererOpenGL::UpdateFramerate() { | ||
| 289 | } | ||
| 290 | |||
| 291 | /** | ||
| 292 | * Set the emulator window to use for renderer | ||
| 293 | * @param window EmuWindow handle to emulator window to use for rendering | ||
| 294 | */ | ||
| 295 | void RendererOpenGL::SetWindow(EmuWindow* window) { | ||
| 296 | render_window_ = window; | ||
| 297 | } | ||
| 298 | |||
| 299 | /// Initialize the renderer | ||
| 300 | void RendererOpenGL::Init() { | ||
| 301 | render_window_->MakeCurrent(); | ||
| 302 | glShadeModel(GL_SMOOTH); | ||
| 303 | |||
| 304 | |||
| 305 | glStencilFunc(GL_ALWAYS, 0, 0); | ||
| 306 | glBlendFunc(GL_ONE, GL_ONE); | ||
| 307 | |||
| 308 | glViewport(0, 0, resolution_width_, resolution_height_); | ||
| 309 | |||
| 310 | glClearDepth(1.0f); | ||
| 311 | glEnable(GL_DEPTH_TEST); | ||
| 312 | glDisable(GL_LIGHTING); | ||
| 313 | glDepthFunc(GL_LEQUAL); | ||
| 314 | |||
| 315 | glPixelStorei(GL_UNPACK_ALIGNMENT, 4); | ||
| 316 | |||
| 317 | glDisable(GL_STENCIL_TEST); | ||
| 318 | glEnable(GL_SCISSOR_TEST); | ||
| 319 | |||
| 320 | glScissor(0, 0, resolution_width_, resolution_height_); | ||
| 321 | glClearDepth(1.0f); | ||
| 322 | |||
| 323 | GLenum err = glewInit(); | ||
| 324 | if (GLEW_OK != err) { | ||
| 325 | ERROR_LOG(RENDER, " Failed to initialize GLEW! Error message: \"%s\". Exiting...", | ||
| 326 | glewGetErrorString(err)); | ||
| 327 | exit(-1); | ||
| 328 | } | ||
| 329 | |||
| 330 | // Initialize everything else | ||
| 331 | // -------------------------- | ||
| 332 | |||
| 333 | InitFramebuffer(); | ||
| 334 | |||
| 335 | NOTICE_LOG(RENDER, "GL_VERSION: %s\n", glGetString(GL_VERSION)); | ||
| 336 | } | ||
| 337 | |||
| 338 | /// Shutdown the renderer | ||
| 339 | void RendererOpenGL::ShutDown() { | ||
| 340 | } | ||
diff --git a/src/video_core/src/renderer_opengl/renderer_opengl.h b/src/video_core/src/renderer_opengl/renderer_opengl.h new file mode 100644 index 000000000..0c41977e4 --- /dev/null +++ b/src/video_core/src/renderer_opengl/renderer_opengl.h | |||
| @@ -0,0 +1,138 @@ | |||
| 1 | /** | ||
| 2 | * Copyright (C) 2014 Citra Emulator | ||
| 3 | * | ||
| 4 | * @file renderer_opengl.h | ||
| 5 | * @author bunnei | ||
| 6 | * @date 2014-04-05 | ||
| 7 | * @brief Renderer for OpenGL 3.x | ||
| 8 | * | ||
| 9 | * @section LICENSE | ||
| 10 | * This program is free software; you can redistribute it and/or | ||
| 11 | * modify it under the terms of the GNU General Public License as | ||
| 12 | * published by the Free Software Foundation; either version 2 of | ||
| 13 | * the License, or (at your option) any later version. | ||
| 14 | * | ||
| 15 | * This program is distributed in the hope that it will be useful, but | ||
| 16 | * WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 17 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
| 18 | * General Public License for more details at | ||
| 19 | * http://www.gnu.org/copyleft/gpl.html | ||
| 20 | * | ||
| 21 | * Official project repository can be found at: | ||
| 22 | * http://code.google.com/p/gekko-gc-emu/ | ||
| 23 | */ | ||
| 24 | |||
| 25 | #pragma once | ||
| 26 | |||
| 27 | #include <GL/glew.h> | ||
| 28 | |||
| 29 | |||
| 30 | #include "common.h" | ||
| 31 | #include "emu_window.h" | ||
| 32 | |||
| 33 | #include "renderer_base.h" | ||
| 34 | |||
| 35 | |||
| 36 | class RendererOpenGL : virtual public RendererBase { | ||
| 37 | public: | ||
| 38 | |||
| 39 | static const int kMaxFramebuffers = 2; ///< Maximum number of framebuffers | ||
| 40 | |||
| 41 | RendererOpenGL(); | ||
| 42 | ~RendererOpenGL(); | ||
| 43 | |||
| 44 | /// Swap buffers (render frame) | ||
| 45 | void SwapBuffers(); | ||
| 46 | |||
| 47 | /** | ||
| 48 | * Blits the EFB to the external framebuffer (XFB) | ||
| 49 | * @param src_rect Source rectangle in EFB to copy | ||
| 50 | * @param dst_rect Destination rectangle in EFB to copy to | ||
| 51 | * @param dest_height Destination height in pixels | ||
| 52 | */ | ||
| 53 | void CopyToXFB(const Rect& src_rect, const Rect& dst_rect); | ||
| 54 | |||
| 55 | /** | ||
| 56 | * Clear the screen | ||
| 57 | * @param rect Screen rectangle to clear | ||
| 58 | * @param enable_color Enable color clearing | ||
| 59 | * @param enable_alpha Enable alpha clearing | ||
| 60 | * @param enable_z Enable depth clearing | ||
| 61 | * @param color Clear color | ||
| 62 | * @param z Clear depth | ||
| 63 | */ | ||
| 64 | void Clear(const Rect& rect, bool enable_color, bool enable_alpha, bool enable_z, | ||
| 65 | u32 color, u32 z); | ||
| 66 | |||
| 67 | /// Sets the renderer viewport location, width, and height | ||
| 68 | void SetViewport(int x, int y, int width, int height); | ||
| 69 | |||
| 70 | /// Sets the renderer depthrange, znear and zfar | ||
| 71 | void SetDepthRange(double znear, double zfar); | ||
| 72 | |||
| 73 | /* Sets the scissor box | ||
| 74 | * @param rect Renderer rectangle to set scissor box to | ||
| 75 | */ | ||
| 76 | void SetScissorBox(const Rect& rect); | ||
| 77 | |||
| 78 | /** | ||
| 79 | * Sets the line and point size | ||
| 80 | * @param line_width Line width to use | ||
| 81 | * @param point_size Point size to use | ||
| 82 | */ | ||
| 83 | void SetLinePointSize(f32 line_width, f32 point_size); | ||
| 84 | |||
| 85 | /** | ||
| 86 | * Set a specific render mode | ||
| 87 | * @param flag Render flags mode to enable | ||
| 88 | */ | ||
| 89 | void SetMode(kRenderMode flags); | ||
| 90 | |||
| 91 | /// Reset the full renderer API to the NULL state | ||
| 92 | void ResetRenderState(); | ||
| 93 | |||
| 94 | /// Restore the full renderer API state - As the game set it | ||
| 95 | void RestoreRenderState(); | ||
| 96 | |||
| 97 | /** | ||
| 98 | * Set the emulator window to use for renderer | ||
| 99 | * @param window EmuWindow handle to emulator window to use for rendering | ||
| 100 | */ | ||
| 101 | void SetWindow(EmuWindow* window); | ||
| 102 | |||
| 103 | /// Initialize the renderer | ||
| 104 | void Init(); | ||
| 105 | |||
| 106 | /// Shutdown the renderer | ||
| 107 | void ShutDown(); | ||
| 108 | |||
| 109 | // Framebuffer object(s) | ||
| 110 | // --------------------- | ||
| 111 | |||
| 112 | GLuint fbo_[kMaxFramebuffers]; ///< Framebuffer objects | ||
| 113 | |||
| 114 | private: | ||
| 115 | |||
| 116 | /// Initialize the FBO | ||
| 117 | void InitFramebuffer(); | ||
| 118 | |||
| 119 | // Blit the FBO to the OpenGL default framebuffer | ||
| 120 | void RenderFramebuffer(); | ||
| 121 | |||
| 122 | /// Updates the framerate | ||
| 123 | void UpdateFramerate(); | ||
| 124 | |||
| 125 | EmuWindow* render_window_; | ||
| 126 | u32 last_mode_; ///< Last render mode | ||
| 127 | |||
| 128 | int resolution_width_; | ||
| 129 | int resolution_height_; | ||
| 130 | |||
| 131 | // Framebuffer object(s) | ||
| 132 | // --------------------- | ||
| 133 | |||
| 134 | GLuint fbo_rbo_[kMaxFramebuffers]; ///< Render buffer objects | ||
| 135 | GLuint fbo_depth_buffers_[kMaxFramebuffers]; ///< Depth buffers objects | ||
| 136 | |||
| 137 | DISALLOW_COPY_AND_ASSIGN(RendererOpenGL); | ||
| 138 | }; \ No newline at end of file | ||
diff --git a/src/video_core/src/video_core.cpp b/src/video_core/src/video_core.cpp index 8ad45c912..52ff90488 100644 --- a/src/video_core/src/video_core.cpp +++ b/src/video_core/src/video_core.cpp | |||
| @@ -27,7 +27,10 @@ | |||
| 27 | #include "log.h" | 27 | #include "log.h" |
| 28 | 28 | ||
| 29 | #include "core.h" | 29 | #include "core.h" |
| 30 | |||
| 30 | #include "video_core.h" | 31 | #include "video_core.h" |
| 32 | #include "renderer_base.h" | ||
| 33 | #include "renderer_opengl/renderer_opengl.h" | ||
| 31 | 34 | ||
| 32 | //////////////////////////////////////////////////////////////////////////////////////////////////// | 35 | //////////////////////////////////////////////////////////////////////////////////////////////////// |
| 33 | // Video Core namespace | 36 | // Video Core namespace |
| @@ -67,16 +70,10 @@ void Start() { | |||
| 67 | /// Initialize the video core | 70 | /// Initialize the video core |
| 68 | void Init(EmuWindow* emu_window) { | 71 | void Init(EmuWindow* emu_window) { |
| 69 | g_emu_window = emu_window; | 72 | g_emu_window = emu_window; |
| 70 | //g_renderer = new RendererGL3(); | 73 | g_emu_window->MakeCurrent(); |
| 71 | //g_renderer->SetWindow(g_emu_window); | 74 | g_renderer = new RendererOpenGL(); |
| 72 | //g_renderer->Init(); | 75 | g_renderer->SetWindow(g_emu_window); |
| 73 | 76 | g_renderer->Init(); | |
| 74 | //gp::Fifo_Init(); | ||
| 75 | //gp::VertexManager_Init(); | ||
| 76 | //gp::VertexLoader_Init(); | ||
| 77 | //gp::BP_Init(); | ||
| 78 | //gp::CP_Init(); | ||
| 79 | //gp::XF_Init(); | ||
| 80 | 77 | ||
| 81 | g_current_frame = 0; | 78 | g_current_frame = 0; |
| 82 | 79 | ||
| @@ -85,7 +82,7 @@ void Init(EmuWindow* emu_window) { | |||
| 85 | 82 | ||
| 86 | /// Shutdown the video core | 83 | /// Shutdown the video core |
| 87 | void Shutdown() { | 84 | void Shutdown() { |
| 88 | //delete g_renderer; | 85 | delete g_renderer; |
| 89 | } | 86 | } |
| 90 | 87 | ||
| 91 | } // namespace | 88 | } // namespace |
diff --git a/src/video_core/src/video_core.h b/src/video_core/src/video_core.h index 9b80d7715..10b8f1105 100644 --- a/src/video_core/src/video_core.h +++ b/src/video_core/src/video_core.h | |||
| @@ -33,8 +33,19 @@ | |||
| 33 | 33 | ||
| 34 | namespace VideoCore { | 34 | namespace VideoCore { |
| 35 | 35 | ||
| 36 | extern RendererBase* g_renderer; ///< Renderer plugin | 36 | // 3DS Video Constants |
| 37 | extern int g_current_frame; ///< Current frame | 37 | // ------------------- |
| 38 | |||
| 39 | static const int kScreenTopWidth = 400; ///< 3DS top screen width | ||
| 40 | static const int kScreenTopHeight = 240; ///< 3DS top screen height | ||
| 41 | static const int kScreenBottomWidth = 320; ///< 3DS bottom screen width | ||
| 42 | static const int kScreenBottomHeight = 240; ///< 3DS bottom screen height | ||
| 43 | |||
| 44 | // Video core renderer | ||
| 45 | // --------------------- | ||
| 46 | |||
| 47 | extern RendererBase* g_renderer; ///< Renderer plugin | ||
| 48 | extern int g_current_frame; ///< Current frame | ||
| 38 | 49 | ||
| 39 | /// Start the video core | 50 | /// Start the video core |
| 40 | void Start(); | 51 | void Start(); |
| @@ -43,6 +54,6 @@ void Start(); | |||
| 43 | void Init(EmuWindow* emu_window); | 54 | void Init(EmuWindow* emu_window); |
| 44 | 55 | ||
| 45 | /// Shutdown the video core | 56 | /// Shutdown the video core |
| 46 | void ShutDown(); | 57 | void Shutdown(); |
| 47 | 58 | ||
| 48 | } // namespace | 59 | } // namespace |
diff --git a/src/video_core/video_core.vcxproj b/src/video_core/video_core.vcxproj index 4a1429745..5c56e9b71 100644 --- a/src/video_core/video_core.vcxproj +++ b/src/video_core/video_core.vcxproj | |||
| @@ -19,11 +19,13 @@ | |||
| 19 | </ProjectConfiguration> | 19 | </ProjectConfiguration> |
| 20 | </ItemGroup> | 20 | </ItemGroup> |
| 21 | <ItemGroup> | 21 | <ItemGroup> |
| 22 | <ClCompile Include="src\renderer_opengl\renderer_opengl.cpp" /> | ||
| 22 | <ClCompile Include="src\utils.cpp" /> | 23 | <ClCompile Include="src\utils.cpp" /> |
| 23 | <ClCompile Include="src\video_core.cpp" /> | 24 | <ClCompile Include="src\video_core.cpp" /> |
| 24 | </ItemGroup> | 25 | </ItemGroup> |
| 25 | <ItemGroup> | 26 | <ItemGroup> |
| 26 | <ClInclude Include="src\renderer_base.h" /> | 27 | <ClInclude Include="src\renderer_base.h" /> |
| 28 | <ClInclude Include="src\renderer_opengl\renderer_opengl.h" /> | ||
| 27 | <ClInclude Include="src\utils.h" /> | 29 | <ClInclude Include="src\utils.h" /> |
| 28 | <ClInclude Include="src\video_core.h" /> | 30 | <ClInclude Include="src\video_core.h" /> |
| 29 | </ItemGroup> | 31 | </ItemGroup> |
diff --git a/src/video_core/video_core.vcxproj.filters b/src/video_core/video_core.vcxproj.filters index 2a84b7edf..e796fbe21 100644 --- a/src/video_core/video_core.vcxproj.filters +++ b/src/video_core/video_core.vcxproj.filters | |||
| @@ -3,13 +3,24 @@ | |||
| 3 | <ItemGroup> | 3 | <ItemGroup> |
| 4 | <ClCompile Include="src\video_core.cpp" /> | 4 | <ClCompile Include="src\video_core.cpp" /> |
| 5 | <ClCompile Include="src\utils.cpp" /> | 5 | <ClCompile Include="src\utils.cpp" /> |
| 6 | <ClCompile Include="src\renderer_opengl\renderer_opengl.cpp"> | ||
| 7 | <Filter>renderer_opengl</Filter> | ||
| 8 | </ClCompile> | ||
| 6 | </ItemGroup> | 9 | </ItemGroup> |
| 7 | <ItemGroup> | 10 | <ItemGroup> |
| 8 | <ClInclude Include="src\renderer_base.h" /> | 11 | <ClInclude Include="src\renderer_base.h" /> |
| 9 | <ClInclude Include="src\video_core.h" /> | 12 | <ClInclude Include="src\video_core.h" /> |
| 10 | <ClInclude Include="src\utils.h" /> | 13 | <ClInclude Include="src\utils.h" /> |
| 14 | <ClInclude Include="src\renderer_opengl\renderer_opengl.h"> | ||
| 15 | <Filter>renderer_opengl</Filter> | ||
| 16 | </ClInclude> | ||
| 11 | </ItemGroup> | 17 | </ItemGroup> |
| 12 | <ItemGroup> | 18 | <ItemGroup> |
| 13 | <Text Include="CMakeLists.txt" /> | 19 | <Text Include="CMakeLists.txt" /> |
| 14 | </ItemGroup> | 20 | </ItemGroup> |
| 21 | <ItemGroup> | ||
| 22 | <Filter Include="renderer_opengl"> | ||
| 23 | <UniqueIdentifier>{e0245557-dbd4-423e-9399-513d5e99f1e4}</UniqueIdentifier> | ||
| 24 | </Filter> | ||
| 25 | </ItemGroup> | ||
| 15 | </Project> \ No newline at end of file | 26 | </Project> \ No newline at end of file |