[Scummvm-git-logs] scummvm master -> 5d92a98038cc4c12170fa9ca8a997664d6933ae4

neuromancer noreply at scummvm.org
Sat Apr 1 21:11:05 UTC 2023


This automated email contains information about 1 new commit which have been
pushed to the 'scummvm' repo located at https://github.com/scummvm/scummvm .

Summary:
5d92a98038 FREESCAPE: initial implementation of the opengl shader renderer


Commit: 5d92a98038cc4c12170fa9ca8a997664d6933ae4
    https://github.com/scummvm/scummvm/commit/5d92a98038cc4c12170fa9ca8a997664d6933ae4
Author: neuromancer (gustavo.grieco at gmail.com)
Date: 2023-04-01T23:12:43+02:00

Commit Message:
FREESCAPE: initial implementation of the opengl shader renderer

Changed paths:
  A engines/freescape/gfx_opengl_shaders.cpp
  A engines/freescape/gfx_opengl_shaders.h
  A engines/freescape/shaders/bitmap.fragment
  A engines/freescape/shaders/bitmap.vertex
  A engines/freescape/shaders/triangle.fragment
  A engines/freescape/shaders/triangle.vertex
    engines/freescape/games/palettes.cpp
    engines/freescape/gfx.cpp
    engines/freescape/module.mk
    graphics/opengl/shader.cpp


diff --git a/engines/freescape/games/palettes.cpp b/engines/freescape/games/palettes.cpp
index 2947a6c6268..e2fe6b8e3c8 100644
--- a/engines/freescape/games/palettes.cpp
+++ b/engines/freescape/games/palettes.cpp
@@ -209,6 +209,9 @@ byte kDrillerCGAPaletteRedGreenData[4][3] = {
 };
 
 void FreescapeEngine::swapPalette(uint16 levelID) {
+	if (!_border)
+		return;
+
 	if (isAmiga() || isAtariST()) {
 		// The following palette was not available in the demo, so we select another one
 		if (isDemo() && levelID == 32)
diff --git a/engines/freescape/gfx.cpp b/engines/freescape/gfx.cpp
index f55548c7a70..e70c08282c6 100644
--- a/engines/freescape/gfx.cpp
+++ b/engines/freescape/gfx.cpp
@@ -925,6 +925,9 @@ Graphics::RendererType determinateRenderType() {
 #if defined(USE_OPENGL_GAME)
 						Graphics::kRendererTypeOpenGL |
 #endif
+#if defined(USE_OPENGL_SHADERS)
+			Graphics::kRendererTypeOpenGLShaders |
+#endif
 #if defined(USE_TINYGL)
 						Graphics::kRendererTypeTinyGL |
 #endif
@@ -940,6 +943,11 @@ Graphics::RendererType determinateRenderType() {
 			return matchingRendererType;
 	#endif
 
+	#if defined(USE_OPENGL_SHADERS)
+		if (matchingRendererType == Graphics::kRendererTypeOpenGLShaders)
+			return matchingRendererType;
+	#endif
+
 	#if defined(USE_TINYGL)
 		return Graphics::kRendererTypeTinyGL;
 	#endif
@@ -965,6 +973,12 @@ Renderer *createRenderer(int screenW, int screenH, Common::RenderMode renderMode
 		}
 	#endif
 
+	#if defined(USE_OPENGL_SHADERS)
+		if (rendererType == Graphics::kRendererTypeOpenGLShaders) {
+			return CreateGfxOpenGLShader(screenW, screenH, renderMode);
+		}
+	#endif
+
 	#if defined(USE_TINYGL)
 	if (rendererType == Graphics::kRendererTypeTinyGL) {
 		return CreateGfxTinyGL(screenW, screenH, renderMode);
diff --git a/engines/freescape/gfx_opengl_shaders.cpp b/engines/freescape/gfx_opengl_shaders.cpp
new file mode 100644
index 00000000000..a30c22935db
--- /dev/null
+++ b/engines/freescape/gfx_opengl_shaders.cpp
@@ -0,0 +1,340 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program 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.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+// Based on Phantasma code by Thomas Harte (2013),
+// available at https://github.com/TomHarte/Phantasma/ (MIT)
+
+#include "common/config-manager.h"
+#include "common/math.h"
+#include "common/system.h"
+#include "math/glmath.h"
+
+#include "freescape/objects/object.h"
+#include "freescape/gfx_opengl_shaders.h"
+#include "freescape/gfx_opengl_texture.h"
+
+namespace Freescape {
+
+static const GLfloat bitmapVertices[] = {
+	// XS   YT
+	0.0, 0.0,
+	1.0, 0.0,
+	0.0, 1.0,
+	1.0, 1.0,
+};
+
+Renderer *CreateGfxOpenGLShader(int screenW, int screenH, Common::RenderMode renderMode) {
+	return new OpenGLShaderRenderer(screenW, screenH, renderMode);
+}
+
+OpenGLShaderRenderer::OpenGLShaderRenderer(int screenW, int screenH, Common::RenderMode renderMode) : Renderer(screenW, screenH, renderMode) {
+	_triangleShader = nullptr;
+	_triangleVBO = 0;
+
+	_bitmapShader = nullptr;
+	_bitmapVBO = 0;
+
+	_texturePixelFormat = OpenGLTexture::getRGBAPixelFormat();
+	_isAccelerated = true;
+}
+
+OpenGLShaderRenderer::~OpenGLShaderRenderer() {
+	OpenGL::Shader::freeBuffer(_triangleVBO);
+	delete _triangleShader;
+}
+
+Texture *OpenGLShaderRenderer::createTexture(const Graphics::Surface *surface) {
+	return new OpenGLTexture(surface);
+}
+
+void OpenGLShaderRenderer::freeTexture(Texture *texture) {
+	delete texture;
+}
+
+void OpenGLShaderRenderer::init() {
+	computeScreenViewport();
+
+	_verts = (Vertex *)malloc(sizeof(Vertex) * kVertexArraySize);
+
+	static const char *triangleAttributes[] = { "position", nullptr };
+	_triangleShader = OpenGL::Shader::fromFiles("triangle", triangleAttributes);
+	_triangleVBO = OpenGL::Shader::createBuffer(GL_ARRAY_BUFFER, sizeof(Vertex) * kVertexArraySize, _verts, GL_DYNAMIC_DRAW);
+	// TODO: Check if 3 * sizeof(float) == sizeof(Vertex)
+	_triangleShader->enableVertexAttribute("position", _triangleVBO, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), 0);
+
+	static const char *bitmapAttributes[] = { "position", "texcoord", nullptr };
+	_bitmapShader = OpenGL::Shader::fromFiles("bitmap", bitmapAttributes);
+	_bitmapVBO = OpenGL::Shader::createBuffer(GL_ARRAY_BUFFER, sizeof(bitmapVertices), bitmapVertices);
+	_bitmapShader->enableVertexAttribute("position", _bitmapVBO, 2, GL_FLOAT, GL_TRUE, 2 * sizeof(float), 0);
+	_bitmapShader->enableVertexAttribute("texcoord", _bitmapVBO, 2, GL_FLOAT, GL_TRUE, 2 * sizeof(float), 0);
+
+	glDisable(GL_LIGHTING);
+	glDisable(GL_TEXTURE_2D);
+	glEnable(GL_DEPTH_TEST);
+	glEnable(GL_SCISSOR_TEST);
+	setViewport(_viewport);
+}
+
+void OpenGLShaderRenderer::setViewport(const Common::Rect &rect) {
+	_viewport = Common::Rect(
+					_screenViewport.width() * rect.width() / _screenW,
+					_screenViewport.height() * rect.height() / _screenH
+					);
+
+	_viewport.translate(
+					_screenViewport.left + _screenViewport.width() * rect.left / _screenW,
+					_screenViewport.top + _screenViewport.height() * rect.top / _screenH
+					);
+
+	_unscaledViewport = rect;
+	glViewport(_viewport.left, g_system->getHeight() - _viewport.bottom, _viewport.width(), _viewport.height());
+	glScissor(_viewport.left, g_system->getHeight() - _viewport.bottom, _viewport.width(), _viewport.height());
+}
+
+void OpenGLShaderRenderer::drawTexturedRect2D(const Common::Rect &screenRect, const Common::Rect &textureRect, Texture *texture) {
+	OpenGLTexture *glTexture = static_cast<OpenGLTexture *>(texture);
+	glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+	glEnable(GL_BLEND);
+
+	_bitmapShader->use();
+	_bitmapShader->setUniform("flipY", glTexture->_upsideDown);
+
+	glDepthMask(GL_FALSE);
+
+	glBindTexture(GL_TEXTURE_2D, glTexture->_id);
+
+	glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
+
+	glDisable(GL_BLEND);
+	glDepthMask(GL_TRUE);
+	_bitmapShader->unbind();
+}
+
+void OpenGLShaderRenderer::updateProjectionMatrix(float fov, float nearClipPlane, float farClipPlane) {
+	float aspectRatio = _screenW / (float)_screenH;
+	float xmaxValue = nearClipPlane * tan(Common::deg2rad(fov) / 2);
+	float ymaxValue = xmaxValue / aspectRatio;
+	_projectionMatrix = Math::makeFrustumMatrix(xmaxValue, -xmaxValue, -ymaxValue, ymaxValue, nearClipPlane, farClipPlane);
+}
+
+void OpenGLShaderRenderer::positionCamera(const Math::Vector3d &pos, const Math::Vector3d &interest) {
+	Math::Vector3d up_vec(0, 1, 0);
+
+	Math::Matrix4 lookMatrix = Math::makeLookAtMatrix(pos, interest, up_vec);
+	Math::Matrix4 viewMatrix;
+	viewMatrix.translate(-pos);
+    viewMatrix.transpose();
+
+	_modelViewMatrix = viewMatrix * lookMatrix;
+
+	Math::Matrix4 proj = _projectionMatrix;
+	Math::Matrix4 model = _modelViewMatrix;
+	proj.transpose();
+	model.transpose();
+	_mvpMatrix = proj * model;
+	_mvpMatrix.transpose();
+}
+
+void OpenGLShaderRenderer::renderSensorShoot(byte color, const Math::Vector3d sensor, const Math::Vector3d player, const Common::Rect viewArea) {
+	/*glColor3ub(255, 255, 255);
+	glLineWidth(20);
+	polygonOffset(true);
+	glEnableClientState(GL_VERTEX_ARRAY);
+	copyToVertexArray(0, sensor);
+	copyToVertexArray(1, player);
+	glVertexPointer(3, GL_FLOAT, 0, _verts);
+	glDrawArrays(GL_LINES, 0, 2);
+	glDisableClientState(GL_VERTEX_ARRAY);
+	polygonOffset(false);
+	glLineWidth(1);*/
+}
+
+void OpenGLShaderRenderer::renderPlayerShoot(byte color, const Common::Point position, const Common::Rect viewArea) {
+	/*uint8 a, r, g, b;
+
+	glMatrixMode(GL_PROJECTION);
+	glLoadIdentity();
+	glOrtho(0, _screenW, _screenH, 0, 0, 1);
+	glMatrixMode(GL_MODELVIEW);
+	glLoadIdentity();
+	if (_renderMode == Common::kRenderCGA || _renderMode == Common::kRenderZX) {
+		r = g = b = 255;
+	} else {
+		uint32 pixel = 0x0;
+		glReadPixels(g_system->getWidth() / 2, g_system->getHeight() / 2, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, &pixel);
+		_texturePixelFormat.colorToARGB(pixel, a, r, g, b);
+		color = indexFromColor(r, g, b);
+		readFromPalette((color + 3) % (_renderMode == Common::kRenderCGA ? 4 : 16), r, g, b);
+	}
+
+	glDisable(GL_DEPTH_TEST);
+	glDepthMask(GL_FALSE);
+
+	glColor3ub(r, g, b);
+
+	glLineWidth(5); // It will not work in every OpenGL implementation since the
+					 // spec doesn't require support for line widths other than 1
+	glEnableClientState(GL_VERTEX_ARRAY);
+	copyToVertexArray(0, Math::Vector3d(viewArea.left, viewArea.height() + viewArea.top, 0));
+	copyToVertexArray(1, Math::Vector3d(position.x, position.y, 0));
+	copyToVertexArray(2, Math::Vector3d(viewArea.left, viewArea.height() + viewArea.top + 3, 0));
+	copyToVertexArray(3, Math::Vector3d(position.x, position.y, 0));
+
+	copyToVertexArray(4, Math::Vector3d(viewArea.right, viewArea.height() + viewArea.top, 0));
+	copyToVertexArray(5, Math::Vector3d(position.x, position.y, 0));
+	copyToVertexArray(6, Math::Vector3d(viewArea.right, viewArea.height() + viewArea.top + 3, 0));
+	copyToVertexArray(7, Math::Vector3d(position.x, position.y, 0));
+
+	glVertexPointer(3, GL_FLOAT, 0, _verts);
+	glDrawArrays(GL_LINES, 0, 8);
+	glDisableClientState(GL_VERTEX_ARRAY);
+	glLineWidth(1);
+
+	glEnable(GL_DEPTH_TEST);
+	glDepthMask(GL_TRUE);*/
+}
+
+void OpenGLShaderRenderer::renderFace(const Common::Array<Math::Vector3d> &vertices) {
+	assert(vertices.size() >= 2);
+	const Math::Vector3d &v0 = vertices[0];
+
+	/*if (vertices.size() == 2) {
+		const Math::Vector3d &v1 = vertices[1];
+		if (v0 == v1)
+			return;
+
+		glEnableClientState(GL_VERTEX_ARRAY);
+		copyToVertexArray(0, v0);
+		copyToVertexArray(1, v1);
+		glVertexPointer(3, GL_FLOAT, 0, _verts);
+		glLineWidth(MAX(1, g_system->getWidth() / 192));
+		glDrawArrays(GL_LINES, 0, 2);
+		glLineWidth(1);
+		glDisableClientState(GL_VERTEX_ARRAY);
+		return;
+	}*/
+
+	//glEnableClientState(GL_VERTEX_ARRAY);
+	_triangleShader->use();
+	_triangleShader->setUniform("mvpMatrix", _mvpMatrix);
+	uint vi = 0;
+	for (uint i = 1; i < vertices.size() - 1; i++) { // no underflow since vertices.size() > 2
+		const Math::Vector3d &v1 = vertices[i];
+		const Math::Vector3d &v2 = vertices[i + 1];
+		vi = 3 * (i - 1); // no underflow since i >= 1
+		copyToVertexArray(vi + 0, v0);
+		copyToVertexArray(vi + 1, v1);
+		copyToVertexArray(vi + 2, v2);
+	}
+	glBindBuffer(GL_ARRAY_BUFFER, _triangleVBO);
+	glBufferData(GL_ARRAY_BUFFER, (vi + 3) * 3 * sizeof(float), _verts, GL_DYNAMIC_DRAW);
+	glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), nullptr);
+	//glEnableVertexAttribArray(0);
+
+	glDrawArrays(GL_TRIANGLES, 0, vi + 3);
+	//glDisableVertexAttribArray(0);
+	//glDisableClientState(GL_VERTEX_ARRAY);
+}
+
+void OpenGLShaderRenderer::polygonOffset(bool enabled) {
+	if (enabled) {
+		glEnable(GL_POLYGON_OFFSET_FILL);
+		glPolygonOffset(-10.0f, 1.0f);
+	} else {
+		glPolygonOffset(0, 0);
+		glDisable(GL_POLYGON_OFFSET_FILL);
+	}
+}
+
+void OpenGLShaderRenderer::setStippleData(byte *data) {
+	if (!data)
+		return;
+
+	//_variableStippleArray = data;
+	//for (int i = 0; i < 128; i++)
+	//	_variableStippleArray[i] = data[(i / 16) % 4];
+}
+
+void OpenGLShaderRenderer::useStipple(bool enabled) {
+	/*if (enabled) {
+		glEnable(GL_POLYGON_OFFSET_FILL);
+		glPolygonOffset(0.0f, -1.0f);
+		glEnable(GL_POLYGON_STIPPLE);
+		if (_renderMode == Common::kRenderZX  ||
+			_renderMode == Common::kRenderCPC ||
+			_renderMode == Common::kRenderCGA)
+			glPolygonStipple(_variableStippleArray);
+		else
+			glPolygonStipple(_defaultStippleArray);
+	} else {
+		glPolygonOffset(0, 0);
+		glDisable(GL_POLYGON_OFFSET_FILL);
+		glDisable(GL_POLYGON_STIPPLE);
+	}*/
+}
+
+void OpenGLShaderRenderer::useColor(uint8 r, uint8 g, uint8 b) {
+	Math::Vector3d color(r / 256.0, g / 256.0, b / 256.0);
+	_triangleShader->use();
+	_triangleShader->setUniform("color", color);
+}
+
+void OpenGLShaderRenderer::clear(uint8 color) {
+	uint8 r, g, b;
+
+	if (_colorRemaps && _colorRemaps->contains(color)) {
+		color = (*_colorRemaps)[color];
+	}
+
+	readFromPalette(color, r, g, b);
+	glClearColor(0, 0, 0, 1.0);
+	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
+}
+
+void OpenGLShaderRenderer::drawFloor(uint8 color) {
+	/*uint8 r1, g1, b1, r2, g2, b2;
+	byte *stipple;
+	assert(getRGBAt(color, r1, g1, b1, r2, g2, b2, stipple)); // TODO: move check inside this function
+	glColor3ub(r1, g1, b1);
+
+	glEnableClientState(GL_VERTEX_ARRAY);
+	copyToVertexArray(0, Math::Vector3d(-100000.0, 0.0, -100000.0));
+	copyToVertexArray(1, Math::Vector3d(100000.0, 0.0, -100000.0));
+	copyToVertexArray(2, Math::Vector3d(100000.0, 0.0, 100000.0));
+	copyToVertexArray(3, Math::Vector3d(-100000.0, 0.0, 100000.0));
+	glVertexPointer(3, GL_FLOAT, 0, _verts);
+	glDrawArrays(GL_QUADS, 0, 4);
+	glDisableClientState(GL_VERTEX_ARRAY);*/
+}
+
+void OpenGLShaderRenderer::flipBuffer() {}
+
+Graphics::Surface *OpenGLShaderRenderer::getScreenshot() {
+	Common::Rect screen = viewport();
+	Graphics::Surface *s = new Graphics::Surface();
+	s->create(screen.width(), screen.height(), OpenGLTexture::getRGBAPixelFormat());
+	glReadPixels(screen.left, screen.top, screen.width(), screen.height(), GL_RGBA, GL_UNSIGNED_BYTE, s->getPixels());
+	flipVertical(s);
+	return s;
+	return nullptr;
+}
+
+} // End of namespace Freescape
diff --git a/engines/freescape/gfx_opengl_shaders.h b/engines/freescape/gfx_opengl_shaders.h
new file mode 100644
index 00000000000..1084a8fb1cb
--- /dev/null
+++ b/engines/freescape/gfx_opengl_shaders.h
@@ -0,0 +1,100 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program 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.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+#ifndef FREESCAPE_GFX_OPENGL_SHADERS_H
+#define FREESCAPE_GFX_OPENGL_SHADERS_H
+
+#include "graphics/opengl/shader.h"
+#include "graphics/opengl/system_headers.h"
+#include "math/vector3d.h"
+#include "math/vector2d.h"
+
+#include "freescape/gfx.h"
+
+namespace Freescape {
+
+class OpenGLShaderRenderer : public Renderer {
+public:
+	OpenGLShaderRenderer(int screenW, int screenH, Common::RenderMode renderMode);
+	virtual ~OpenGLShaderRenderer();
+
+	Math::Matrix4 _projectionMatrix;
+	Math::Matrix4 _modelViewMatrix;
+	Math::Matrix4 _mvpMatrix;
+
+	struct Vertex {
+		GLfloat x;
+		GLfloat y;
+		GLfloat z;
+	};
+
+	void copyToVertexArray(uint idx, const Math::Vector3d &src) {
+		assert(idx < kVertexArraySize);
+		_verts[idx].x = src.x(); _verts[idx].y = src.y(); _verts[idx].z = src.z();
+	}
+
+	Vertex *_verts;
+
+	struct Coord {
+		GLfloat x;
+		GLfloat y;
+	};
+
+	/*Coord *_coords;
+
+	void copyToCoordArray(uint idx, const Math::Vector2d &src) {
+		assert(idx < kCoordsArraySize);
+		_coords[idx].x = src.getValue(0); _coords[idx].y = src.getValue(1);
+	}*/
+
+	OpenGL::Shader *_triangleShader;
+	OpenGL::Shader *_bitmapShader;
+	GLuint _triangleVBO;
+	GLuint _bitmapVBO;
+
+	virtual void init() override;
+	virtual void clear(uint8 color) override;
+	virtual void setViewport(const Common::Rect &rect) override;
+	virtual void positionCamera(const Math::Vector3d &pos, const Math::Vector3d &interest) override;
+	virtual void updateProjectionMatrix(float fov, float nearClipPlane, float farClipPlane) override;
+
+	virtual void useColor(uint8 r, uint8 g, uint8 b) override;
+	virtual void polygonOffset(bool enabled) override;
+	virtual void setStippleData(byte *data) override;
+	virtual void useStipple(bool enabled) override;
+
+	Texture *createTexture(const Graphics::Surface *surface) override;
+	void freeTexture(Texture *texture) override;
+	virtual void drawTexturedRect2D(const Common::Rect &screenRect, const Common::Rect &textureRect, Texture *texture) override;
+
+	virtual void renderSensorShoot(byte color, const Math::Vector3d sensor, const Math::Vector3d player, const Common::Rect viewPort) override;
+	virtual void renderPlayerShoot(byte color, const Common::Point position, const Common::Rect viewPort) override;
+	virtual void renderFace(const Common::Array<Math::Vector3d> &vertices) override;
+
+	virtual void flipBuffer() override;
+	virtual void drawFloor(uint8 color) override;
+
+	virtual Graphics::Surface *getScreenshot() override;
+};
+
+} // End of namespace Freescape
+
+#endif // FREESCAPE_GFX_OPENGL_SHADERS_H
diff --git a/engines/freescape/module.mk b/engines/freescape/module.mk
index 0695e5501b3..fe3a2a95cda 100644
--- a/engines/freescape/module.mk
+++ b/engines/freescape/module.mk
@@ -36,6 +36,11 @@ MODULE_OBJS += \
 	gfx_tinygl_texture.o
 endif
 
+ifdef USE_OPENGL_SHADERS
+MODULE_OBJS += \
+	gfx_opengl_shaders.o
+endif
+
 ifdef USE_OPENGL
 MODULE_OBJS += \
 	gfx_opengl.o \
diff --git a/engines/freescape/shaders/bitmap.fragment b/engines/freescape/shaders/bitmap.fragment
new file mode 100644
index 00000000000..ac293f3685d
--- /dev/null
+++ b/engines/freescape/shaders/bitmap.fragment
@@ -0,0 +1,9 @@
+in vec2 Texcoord;
+
+OUTPUT
+
+uniform sampler2D tex;
+
+void main() {
+	outColor = texture(tex, Texcoord);
+}
diff --git a/engines/freescape/shaders/bitmap.vertex b/engines/freescape/shaders/bitmap.vertex
new file mode 100644
index 00000000000..7362dae979c
--- /dev/null
+++ b/engines/freescape/shaders/bitmap.vertex
@@ -0,0 +1,21 @@
+in vec2 position;
+in vec2 texcoord;
+
+uniform UBOOL flipY;
+
+out vec2 Texcoord;
+
+void main() {
+	Texcoord = texcoord;
+
+	vec2 pos = position;
+	// Coordinates are [0.0;1.0], transform to [-1.0; 1.0]
+	pos.x = pos.x * 2.0 - 1.0;
+	pos.y = -1.0 * (pos.y * 2.0 - 1.0);
+
+	if (UBOOL_TEST(flipY)) {
+		pos.y *= -1.0;
+	}
+
+	gl_Position = vec4(pos, 0.0, 1.0);
+}
diff --git a/engines/freescape/shaders/triangle.fragment b/engines/freescape/shaders/triangle.fragment
new file mode 100644
index 00000000000..aaf98049c01
--- /dev/null
+++ b/engines/freescape/shaders/triangle.fragment
@@ -0,0 +1,8 @@
+OUTPUT
+
+varying vec4 var_color;
+
+void main()
+{
+    outColor = var_color;
+}
\ No newline at end of file
diff --git a/engines/freescape/shaders/triangle.vertex b/engines/freescape/shaders/triangle.vertex
new file mode 100644
index 00000000000..6483e9a8adb
--- /dev/null
+++ b/engines/freescape/shaders/triangle.vertex
@@ -0,0 +1,12 @@
+in vec3 position;
+
+uniform mat4 mvpMatrix;
+uniform vec3 color;
+
+varying vec4 var_color;
+
+void main()
+{
+	var_color = vec4(color, 1.0);
+    gl_Position = mvpMatrix * vec4(position, 1.0);
+}
\ No newline at end of file
diff --git a/graphics/opengl/shader.cpp b/graphics/opengl/shader.cpp
index 652e4cac3b3..99f23e3c14a 100644
--- a/graphics/opengl/shader.cpp
+++ b/graphics/opengl/shader.cpp
@@ -92,6 +92,7 @@ static const GLchar *readFile(const Common::String &filename) {
 	SearchMan.addDirectory("STARK_SHADERS", "engines/stark", 0, 2);
 	SearchMan.addDirectory("WINTERMUTE_SHADERS", "engines/wintermute/base/gfx/opengl", 0, 2);
 	SearchMan.addDirectory("PLAYGROUND3D_SHADERS", "engines/playground3d", 0, 2);
+	SearchMan.addDirectory("FREESCAPE_SHADERS", "engines/freescape", 0, 2);
 	SearchMan.addDirectory("HPL1_SHADERS", "engines/hpl1/engine/impl", 0, 2);
 #endif
 
@@ -111,6 +112,7 @@ static const GLchar *readFile(const Common::String &filename) {
 	SearchMan.remove("STARK_SHADERS");
 	SearchMan.remove("WINTERMUTE_SHADERS");
 	SearchMan.remove("PLAYGROUND3D_SHADERS");
+	SearchMan.remove("FREESCAPE_SHADERS");
 	SearchMan.remove("HPL1_SHADERS");
 #endif
 




More information about the Scummvm-git-logs mailing list