diff --git a/openrct2.vcxproj b/openrct2.vcxproj
index af74b6c92e..a93969114f 100644
--- a/openrct2.vcxproj
+++ b/openrct2.vcxproj
@@ -42,6 +42,7 @@
+
diff --git a/src/drawing/IDrawingEngine.h b/src/drawing/IDrawingEngine.h
index 91d1c7a0fa..3dad79b63b 100644
--- a/src/drawing/IDrawingEngine.h
+++ b/src/drawing/IDrawingEngine.h
@@ -40,6 +40,7 @@ interface IDrawingEngine
namespace DrawingEngineFactory
{
IDrawingEngine * CreateSoftware();
+ IDrawingEngine * CreateOpenGL();
};
interface IRainDrawer
diff --git a/src/drawing/NewDrawing.cpp b/src/drawing/NewDrawing.cpp
index 0565df03dd..26e28af42b 100644
--- a/src/drawing/NewDrawing.cpp
+++ b/src/drawing/NewDrawing.cpp
@@ -29,7 +29,8 @@ extern "C"
void drawing_engine_init()
{
assert(_drawingEngine == nullptr);
- _drawingEngine = DrawingEngineFactory::CreateSoftware();
+ // _drawingEngine = DrawingEngineFactory::CreateSoftware();
+ _drawingEngine = DrawingEngineFactory::CreateOpenGL();
_drawingEngine->Initialise(gWindow);
}
diff --git a/src/drawing/engines/OpenGLDrawingEngine.cpp b/src/drawing/engines/OpenGLDrawingEngine.cpp
new file mode 100644
index 0000000000..859d825d23
--- /dev/null
+++ b/src/drawing/engines/OpenGLDrawingEngine.cpp
@@ -0,0 +1,324 @@
+#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers
+/*****************************************************************************
+ * OpenRCT2, an open source clone of Roller Coaster Tycoon 2.
+ *
+ * OpenRCT2 is the work of many authors, a full list can be found in contributors.md
+ * For more information, visit https://github.com/OpenRCT2/OpenRCT2
+ *
+ * OpenRCT2 is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * A full copy of the GNU General Public License can be found in licence.txt
+ *****************************************************************************/
+#pragma endregion
+
+#include
+
+#ifdef __WINDOWS__
+ #include
+ #pragma comment(lib, "opengl32.lib")
+#endif
+
+#include
+#include
+
+#include "../../core/Math.hpp"
+#include "../../core/Memory.hpp"
+#include "../IDrawingContext.h"
+#include "../IDrawingEngine.h"
+#include "../Rain.h"
+
+extern "C"
+{
+ #include "../../config.h"
+ #include "../drawing.h"
+ #include "../../interface/window.h"
+}
+
+class OpenGLDrawingEngine;
+
+struct vec4f
+{
+ union { float x; float s; float r; };
+ union { float y; float t; float g; };
+ union { float z; float p; float b; };
+ union { float w; float q; float a; };
+};
+
+class OpenGLDrawingContext : public IDrawingContext
+{
+private:
+ OpenGLDrawingEngine * _engine;
+ rct_drawpixelinfo * _dpi;
+
+ sint32 _offsetX;
+ sint32 _offsetY;
+ sint32 _clipLeft;
+ sint32 _clipTop;
+ sint32 _clipRight;
+ sint32 _clipBottom;
+
+public:
+ OpenGLDrawingContext(OpenGLDrawingEngine * engine);
+ ~OpenGLDrawingContext() override;
+
+ IDrawingEngine * GetEngine() override;
+
+ void Clear(uint32 colour) override;
+ void FillRect(uint32 colour, sint32 x, sint32 y, sint32 w, sint32 h) override;
+ void DrawSprite(uint32 image, sint32 x, sint32 y, uint32 tertiaryColour) override;
+ void DrawSpritePaletteSet(uint32 image, sint32 x, sint32 y, uint8 * palette, uint8 * unknown) override;
+ void DrawSpriteRawMasked(sint32 x, sint32 y, uint32 maskImage, uint32 colourImage) override;
+
+ void SetDPI(rct_drawpixelinfo * dpi);
+};
+
+class OpenGLDrawingEngine : public IDrawingEngine
+{
+private:
+ SDL_Window * _window = nullptr;
+ SDL_GLContext _context;
+
+ uint32 _width = 0;
+ uint32 _height = 0;
+ uint32 _pitch = 0;
+ size_t _bitsSize = 0;
+ uint8 * _bits = nullptr;
+
+ rct_drawpixelinfo _bitsDPI = { 0 };
+
+ OpenGLDrawingContext * _drawingContext;
+
+public:
+ vec4f GLPalette[256];
+
+ OpenGLDrawingEngine()
+ {
+ _drawingContext = new OpenGLDrawingContext(this);
+ }
+
+ ~OpenGLDrawingEngine() override
+ {
+ delete _drawingContext;
+ delete _bits;
+
+ SDL_GL_DeleteContext(_context);
+ }
+
+ void Initialise(SDL_Window * window) override
+ {
+ _window = window;
+
+ _context = SDL_GL_CreateContext(_window);
+ SDL_GL_MakeCurrent(_window, _context);
+ }
+
+ void Resize(uint32 width, uint32 height) override
+ {
+ ConfigureBits(width, height, width);
+
+ glViewport(0, 0, (GLsizei)width, (GLsizei)height);
+ }
+
+ void SetPalette(SDL_Color * palette) override
+ {
+ for (int i = 0; i < 256; i++)
+ {
+ SDL_Color colour = palette[i];
+ GLPalette[i] = { colour.r / 255.0f,
+ colour.g / 255.0f,
+ colour.b / 255.0f,
+ colour.a / 255.0f };
+ }
+ }
+
+ void Invalidate(sint32 left, sint32 top, sint32 right, sint32 bottom) override
+ {
+ }
+
+ void Draw() override
+ {
+ glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
+ glClear(GL_COLOR_BUFFER_BIT);
+
+ glMatrixMode(GL_PROJECTION_MATRIX);
+ glLoadIdentity();
+ glOrtho(0, _width, _height, 0, -1.0, 1.0);
+
+ glMatrixMode(GL_MODELVIEW_MATRIX);
+ glLoadIdentity();
+ glScalef(1, -1.0f, 0);
+ glTranslatef(-1.0f, -1.0f, 0);
+ glScalef(2.0f / _width, 2.0f / _height, 0);
+
+ gfx_redraw_screen_rect(0, 0, _width - 1, _height - 1);
+ window_update_all_viewports();
+ gfx_redraw_screen_rect(0, 0, _width - 1, _height - 1);
+ window_update_all();
+
+ rct2_draw();
+ Display();
+ }
+
+ IDrawingContext * GetDrawingContext(rct_drawpixelinfo * dpi) override
+ {
+ _drawingContext->SetDPI(dpi);
+ return _drawingContext;
+ }
+
+ rct_drawpixelinfo * GetDPI()
+ {
+ return &_bitsDPI;
+ }
+
+private:
+
+ void ConfigureBits(uint32 width, uint32 height, uint32 pitch)
+ {
+ size_t newBitsSize = pitch * height;
+ uint8 * newBits = new uint8[newBitsSize];
+ if (_bits == nullptr)
+ {
+ Memory::Set(newBits, 0, newBitsSize);
+ }
+ else
+ {
+ if (_pitch == pitch)
+ {
+ Memory::Copy(newBits, _bits, Math::Min(_bitsSize, newBitsSize));
+ }
+ else
+ {
+ uint8 * src = _bits;
+ uint8 * dst = newBits;
+
+ uint32 minWidth = Math::Min(_width, width);
+ uint32 minHeight = Math::Min(_height, height);
+ for (uint32 y = 0; y < minHeight; y++)
+ {
+ Memory::Copy(dst, src, minWidth);
+ if (pitch - minWidth > 0)
+ {
+ Memory::Set(dst + minWidth, 0, pitch - minWidth);
+ }
+ src += _pitch;
+ dst += pitch;
+ }
+ }
+ delete _bits;
+ }
+
+ _bits = newBits;
+ _bitsSize = newBitsSize;
+ _width = width;
+ _height = height;
+ _pitch = pitch;
+
+ rct_drawpixelinfo * dpi = &_bitsDPI;
+ dpi->bits = _bits;
+ dpi->x = 0;
+ dpi->y = 0;
+ dpi->width = width;
+ dpi->height = height;
+ dpi->pitch = _pitch - width;
+
+ gScreenDPI = *dpi;
+ }
+
+ void Display()
+ {
+ SDL_GL_SwapWindow(_window);
+ }
+};
+
+IDrawingEngine * DrawingEngineFactory::CreateOpenGL()
+{
+ return new OpenGLDrawingEngine();
+}
+
+OpenGLDrawingContext::OpenGLDrawingContext(OpenGLDrawingEngine * engine)
+{
+ _engine = engine;
+}
+
+OpenGLDrawingContext::~OpenGLDrawingContext()
+{
+
+}
+
+IDrawingEngine * OpenGLDrawingContext::GetEngine()
+{
+ return _engine;
+}
+
+void OpenGLDrawingContext::Clear(uint32 colour)
+{
+}
+
+void OpenGLDrawingContext::FillRect(uint32 colour, sint32 left, sint32 top, sint32 right, sint32 bottom)
+{
+ vec4f paletteColour = _engine->GLPalette[colour & 0xFF];
+
+ if (left > right)
+ {
+ left ^= right;
+ right ^= left;
+ left ^= right;
+ }
+ if (top > bottom)
+ {
+ top ^= bottom;
+ bottom ^= top;
+ top ^= bottom;
+ }
+
+ left += _offsetX;
+ top += _offsetY;
+ right += _offsetX;
+ bottom += _offsetY;
+
+ left = Math::Max(left, _clipLeft);
+ top = Math::Max(top, _clipTop);
+ right = Math::Min(right, _clipRight);
+ bottom = Math::Min(bottom, _clipBottom);
+
+ glColor3f(paletteColour.r, paletteColour.g, paletteColour.b);
+ glBegin(GL_QUADS);
+ glVertex2i(left, top);
+ glVertex2i(left, bottom);
+ glVertex2i(right, bottom);
+ glVertex2i(right, top);
+ glEnd();
+}
+
+void OpenGLDrawingContext::DrawSprite(uint32 image, sint32 x, sint32 y, uint32 tertiaryColour)
+{
+}
+
+void OpenGLDrawingContext::DrawSpritePaletteSet(uint32 image, sint32 x, sint32 y, uint8 * palette, uint8 * unknown)
+{
+}
+
+void OpenGLDrawingContext::DrawSpriteRawMasked(sint32 x, sint32 y, uint32 maskImage, uint32 colourImage)
+{
+}
+
+void OpenGLDrawingContext::SetDPI(rct_drawpixelinfo * dpi)
+{
+ rct_drawpixelinfo * screenDPI = _engine->GetDPI();
+ size_t bitsSize = (size_t)screenDPI->height * (size_t)(screenDPI->width + screenDPI->pitch);
+ size_t bitsOffset = (size_t)(dpi->bits - screenDPI->bits);
+
+ assert(bitsOffset < bitsSize);
+
+ _clipLeft = bitsOffset % (screenDPI->width + screenDPI->pitch);
+ _clipTop = bitsOffset / (screenDPI->width + screenDPI->pitch);
+ _clipRight = _clipLeft + dpi->width;
+ _clipBottom = _clipTop + dpi->height;
+ _offsetX = _clipLeft + dpi->x;
+ _offsetY = _clipTop + dpi->y;
+
+ _dpi = dpi;
+}
diff --git a/src/drawing/rect.c b/src/drawing/rect.c
index 4e9ffb6c67..1163fb7500 100644
--- a/src/drawing/rect.c
+++ b/src/drawing/rect.c
@@ -53,7 +53,7 @@ void gfx_fill_rect_inset(rct_drawpixelinfo* dpi, short left, short top, short ri
colour = colour | 0x2000000; //Transparent
if (flags & no_border) {
- gfx_fill_rect(dpi, left, top, bottom, right, colour);
+ gfx_fill_rect(dpi, left, top, right, bottom, colour);
} else if (flags & pressed) {
// Draw outline of box
gfx_fill_rect(dpi, left, top, left, bottom, colour + 1);
diff --git a/src/drawing/sprite.c b/src/drawing/sprite.c
index 596a13a6ff..3fb9dfed32 100644
--- a/src/drawing/sprite.c
+++ b/src/drawing/sprite.c
@@ -354,7 +354,7 @@ void FASTCALL gfx_draw_sprite_software(rct_drawpixelinfo *dpi, int image_id, int
//For backwards compatibility
RCT2_GLOBAL(0x9ABDA4, uint8*) = palette_pointer;
- gfx_draw_sprite_palette_set(dpi, image_id, x, y, palette_pointer, unknown_pointer);
+ gfx_draw_sprite_palette_set_software(dpi, image_id, x, y, palette_pointer, unknown_pointer);
}
/*
diff --git a/src/platform/shared.c b/src/platform/shared.c
index 8f710085ab..889325a36c 100644
--- a/src/platform/shared.c
+++ b/src/platform/shared.c
@@ -640,7 +640,7 @@ static void platform_create_window()
// Create window in window first rather than fullscreen so we have the display the window is on first
gWindow = SDL_CreateWindow(
- "OpenRCT2", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, width, height, SDL_WINDOW_RESIZABLE
+ "OpenRCT2", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, width, height, SDL_WINDOW_RESIZABLE | SDL_WINDOW_OPENGL
);
if (!gWindow) {
diff --git a/src/ride/ride.c b/src/ride/ride.c
index 9d6a0a2f30..efe8f7af7c 100644
--- a/src/ride/ride.c
+++ b/src/ride/ride.c
@@ -6923,7 +6923,7 @@ void set_vehicle_type_image_max_sizes(rct_ride_entry_vehicle* vehicle_type, int
};
for (int i = 0; i < num_images; ++i){
- gfx_draw_sprite(&dpi, vehicle_type->base_image_id + i, 0, 0, 0);
+ gfx_draw_sprite_software(&dpi, vehicle_type->base_image_id + i, 0, 0, 0);
}
int al = -1;
for (int i = 99; i != 0; --i){