mirror of
https://github.com/love2d/love.git
synced 2026-08-16 00:02:12 +02:00
Some work towards OpenGL ES 2+ support for love 0.10.
--HG-- branch : minor
This commit is contained in:
@@ -96,7 +96,7 @@ struct FramebufferStrategy
|
||||
virtual void setAttachments() {}
|
||||
};
|
||||
|
||||
struct FramebufferStrategyGL3 : public FramebufferStrategy
|
||||
struct FramebufferStrategyCorePacked : public FramebufferStrategy
|
||||
{
|
||||
virtual GLenum createFBO(GLuint &framebuffer, GLuint texture)
|
||||
{
|
||||
@@ -218,6 +218,37 @@ struct FramebufferStrategyGL3 : public FramebufferStrategy
|
||||
}
|
||||
};
|
||||
|
||||
struct FramebufferStrategyCore : public FramebufferStrategyCorePacked
|
||||
{
|
||||
virtual bool createStencil(int width, int height, int samples, GLuint &stencil)
|
||||
{
|
||||
// create stencil buffer
|
||||
glDeleteRenderbuffers(1, &stencil);
|
||||
glGenRenderbuffers(1, &stencil);
|
||||
glBindRenderbuffer(GL_RENDERBUFFER, stencil);
|
||||
|
||||
if (samples > 1)
|
||||
glRenderbufferStorageMultisample(GL_RENDERBUFFER, samples, GL_STENCIL_INDEX8, width, height);
|
||||
else
|
||||
glRenderbufferStorage(GL_RENDERBUFFER, GL_STENCIL_INDEX8, width, height);
|
||||
|
||||
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT,
|
||||
GL_RENDERBUFFER, stencil);
|
||||
|
||||
glBindRenderbuffer(GL_RENDERBUFFER, 0);
|
||||
|
||||
// check status
|
||||
if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)
|
||||
{
|
||||
glDeleteRenderbuffers(1, &stencil);
|
||||
stencil = 0;
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
struct FramebufferStrategyPackedEXT : public FramebufferStrategy
|
||||
{
|
||||
virtual GLenum createFBO(GLuint &framebuffer, GLuint texture)
|
||||
@@ -393,11 +424,9 @@ struct FramebufferStrategyEXT : public FramebufferStrategyPackedEXT
|
||||
FramebufferStrategy *strategy = nullptr;
|
||||
|
||||
FramebufferStrategy strategyNone;
|
||||
|
||||
FramebufferStrategyGL3 strategyGL3;
|
||||
|
||||
FramebufferStrategyCorePacked strategyCorePacked;
|
||||
FramebufferStrategyCore strategyCore;
|
||||
FramebufferStrategyPackedEXT strategyPackedEXT;
|
||||
|
||||
FramebufferStrategyEXT strategyEXT;
|
||||
|
||||
Canvas *Canvas::current = nullptr;
|
||||
@@ -411,7 +440,9 @@ static void getStrategy()
|
||||
if (!strategy)
|
||||
{
|
||||
if (GLAD_VERSION_3_0 || GLAD_ARB_framebuffer_object)
|
||||
strategy = &strategyGL3;
|
||||
strategy = &strategyCorePacked;
|
||||
else if (GLAD_ES_VERSION_2_0)
|
||||
strategy = &strategyCore;
|
||||
else if (GLAD_EXT_framebuffer_object && GLAD_EXT_packed_depth_stencil)
|
||||
strategy = &strategyPackedEXT;
|
||||
else if (GLAD_EXT_framebuffer_object && strategyEXT.isSupported())
|
||||
@@ -783,6 +814,17 @@ void Canvas::stopGrab(bool switchingToOtherCanvas)
|
||||
if (current != this)
|
||||
return;
|
||||
|
||||
if (depth_stencil != 0)
|
||||
{
|
||||
GLenum attachments[] = {GL_STENCIL_ATTACHMENT, GL_DEPTH_ATTACHMENT};
|
||||
|
||||
// Hint for the driver that it doesn't need to save these buffers.
|
||||
if (GLAD_ES_VERSION_3_0)
|
||||
glInvalidateFramebuffer(GL_FRAMEBUFFER, 2, attachments);
|
||||
else if (GLAD_EXT_discard_framebuffer)
|
||||
glDiscardFramebufferEXT(GL_FRAMEBUFFER, 2, attachments);
|
||||
}
|
||||
|
||||
gl.matrices.projection.pop_back();
|
||||
|
||||
if (switchingToOtherCanvas)
|
||||
@@ -793,7 +835,7 @@ void Canvas::stopGrab(bool switchingToOtherCanvas)
|
||||
else
|
||||
{
|
||||
// bind system framebuffer.
|
||||
strategy->bindFBO(0);
|
||||
strategy->bindFBO(gl.getDefaultFBO());
|
||||
current = nullptr;
|
||||
gl.setViewport(systemViewport);
|
||||
|
||||
@@ -879,7 +921,7 @@ bool Canvas::checkCreateStencil()
|
||||
if (current && current != this)
|
||||
strategy->bindFBO(current->fbo);
|
||||
else if (!current)
|
||||
strategy->bindFBO(0);
|
||||
strategy->bindFBO(gl.getDefaultFBO());
|
||||
|
||||
return success;
|
||||
}
|
||||
@@ -905,7 +947,7 @@ love::image::ImageData *Canvas::getImageData(love::image::Image *image)
|
||||
if (current)
|
||||
strategy->bindFBO(current->fbo);
|
||||
else
|
||||
strategy->bindFBO(0);
|
||||
strategy->bindFBO(gl.getDefaultFBO());
|
||||
|
||||
// The new ImageData now owns the pixel data, so we don't delete it here.
|
||||
love::image::ImageData *img = image->newImageData(width, height, (void *)pixels, true);
|
||||
@@ -932,7 +974,7 @@ void Canvas::getPixel(unsigned char* pixel_rgba, int x, int y)
|
||||
if (current && current != this)
|
||||
strategy->bindFBO(current->fbo);
|
||||
else if (!current)
|
||||
strategy->bindFBO(0);
|
||||
strategy->bindFBO(gl.getDefaultFBO());
|
||||
}
|
||||
|
||||
bool Canvas::resolveMSAA()
|
||||
@@ -1088,7 +1130,7 @@ bool Canvas::isFormatSupported(Canvas::Format format)
|
||||
supported = true;
|
||||
break;
|
||||
case FORMAT_RGB565:
|
||||
supported = GLAD_VERSION_4_2 || GLAD_ARB_ES2_compatibility;
|
||||
supported = GLAD_ES_VERSION_2_0 || GLAD_VERSION_4_2 || GLAD_ARB_ES2_compatibility;
|
||||
break;
|
||||
case FORMAT_RG11B10F:
|
||||
supported = GLAD_VERSION_3_0 || GLAD_EXT_packed_float;
|
||||
|
||||
@@ -158,7 +158,7 @@ void Font::createTexture()
|
||||
{
|
||||
// Clean up before throwing.
|
||||
gl.deleteTexture(t);
|
||||
gl.bindTexture(0);
|
||||
gl.bindTexture(gl.getDefaultTexture());
|
||||
textures.pop_back();
|
||||
|
||||
throw love::Exception("Could not create font texture!");
|
||||
|
||||
@@ -210,7 +210,7 @@ bool Graphics::setMode(int width, int height, bool &sRGB)
|
||||
gl.initContext();
|
||||
|
||||
// Does the system meet LOVE's minimum requirements for graphics?
|
||||
if (!(GLAD_VERSION_2_0 && Shader::isSupported() && Canvas::isSupported())
|
||||
if (!(GLAD_ES_VERSION_2_0 || (GLAD_VERSION_2_0 && Shader::isSupported() && Canvas::isSupported()))
|
||||
&& !displayedMinReqWarning)
|
||||
{
|
||||
love::window::Window::MessageBoxType type = love::window::Window::MESSAGEBOX_ERROR;
|
||||
@@ -331,6 +331,10 @@ void Graphics::setDebug(bool enable)
|
||||
if (!(GLAD_VERSION_4_3 || GLAD_KHR_debug || GLAD_ARB_debug_output))
|
||||
return;
|
||||
|
||||
// TODO: We don't support GL_KHR_debug in GLES yet.
|
||||
if (GLAD_ES_VERSION_2_0)
|
||||
return;
|
||||
|
||||
// Ugly hack to reduce code duplication.
|
||||
if (GLAD_ARB_debug_output && !(GLAD_VERSION_4_3 || GLAD_KHR_debug))
|
||||
{
|
||||
@@ -396,8 +400,33 @@ void Graphics::clear(ClearType type)
|
||||
|
||||
void Graphics::present()
|
||||
{
|
||||
// Make sure we don't have a canvas active.
|
||||
std::vector<Object::StrongRef<Canvas>> canvases = states.back().canvases;
|
||||
setCanvas();
|
||||
|
||||
if (GLAD_ES_VERSION_3_0 || GLAD_EXT_discard_framebuffer)
|
||||
{
|
||||
GLenum attachments[] = {GL_STENCIL, GL_DEPTH};
|
||||
|
||||
if (gl.getDefaultFBO() != 0)
|
||||
{
|
||||
// A non-zero FBO needs different attachment enums.
|
||||
attachments[0] = GL_STENCIL_ATTACHMENT;
|
||||
attachments[1] = GL_DEPTH_ATTACHMENT;
|
||||
}
|
||||
|
||||
// Hint for the driver that it doesn't need to save these buffers.
|
||||
if (GLAD_ES_VERSION_3_0)
|
||||
glInvalidateFramebuffer(GL_FRAMEBUFFER, 2, attachments);
|
||||
else if (GLAD_EXT_discard_framebuffer)
|
||||
glDiscardFramebufferEXT(GL_FRAMEBUFFER, 2, attachments);
|
||||
}
|
||||
|
||||
currentWindow->swapBuffers();
|
||||
|
||||
// Restore the currently active canvas, if there is one.
|
||||
setCanvas(canvases);
|
||||
|
||||
// Reset the per-frame stat counts.
|
||||
gl.stats.drawCalls = 0;
|
||||
Canvas::switchCount = 0;
|
||||
@@ -922,6 +951,10 @@ float Graphics::getPointSize() const
|
||||
|
||||
void Graphics::setWireframe(bool enable)
|
||||
{
|
||||
// Not supported in OpenGL ES.
|
||||
if (GLAD_ES_VERSION_2_0)
|
||||
return;
|
||||
|
||||
glPolygonMode(GL_FRONT_AND_BACK, enable ? GL_LINE : GL_FILL);
|
||||
states.back().wireframe = enable;
|
||||
}
|
||||
@@ -1007,7 +1040,7 @@ void Graphics::printf(const std::string &str, float x, float y, float wrap, Alig
|
||||
void Graphics::point(float x, float y)
|
||||
{
|
||||
gl.prepareDraw();
|
||||
gl.bindTexture(0);
|
||||
gl.bindTexture(gl.getDefaultTexture());
|
||||
glBegin(GL_POINTS);
|
||||
glVertex2f(x, y);
|
||||
glEnd();
|
||||
@@ -1105,7 +1138,7 @@ void Graphics::arc(DrawMode mode, float x, float y, float radius, float angle1,
|
||||
else
|
||||
{
|
||||
gl.prepareDraw();
|
||||
gl.bindTexture(0);
|
||||
gl.bindTexture(gl.getDefaultTexture());
|
||||
glEnableVertexAttribArray(ATTRIB_POS);
|
||||
glVertexAttribPointer(ATTRIB_POS, 2, GL_FLOAT, GL_FALSE, 0, coords);
|
||||
gl.drawArrays(GL_TRIANGLE_FAN, 0, points + 2);
|
||||
@@ -1129,7 +1162,7 @@ void Graphics::polygon(DrawMode mode, const float *coords, size_t count)
|
||||
else
|
||||
{
|
||||
gl.prepareDraw();
|
||||
gl.bindTexture(0);
|
||||
gl.bindTexture(gl.getDefaultTexture());
|
||||
glEnableVertexAttribArray(ATTRIB_POS);
|
||||
glVertexAttribPointer(ATTRIB_POS, 2, GL_FLOAT, GL_FALSE, 0, coords);
|
||||
gl.drawArrays(GL_POLYGON, 0, count/2-1); // opengl will close the polygon for us
|
||||
@@ -1207,7 +1240,11 @@ love::image::ImageData *Graphics::newScreenshot(love::image::Image *image, bool
|
||||
Graphics::RendererInfo Graphics::getRendererInfo() const
|
||||
{
|
||||
RendererInfo info;
|
||||
info.name = "OpenGL";
|
||||
|
||||
if (GLAD_ES_VERSION_2_0)
|
||||
info.name = "OpenGL ES";
|
||||
else
|
||||
info.name = "OpenGL";
|
||||
|
||||
const char *str = (const char *) glGetString(GL_VERSION);
|
||||
if (str)
|
||||
|
||||
@@ -163,6 +163,10 @@ void Image::setWrap(const Texture::Wrap &w)
|
||||
|
||||
void Image::setMipmapSharpness(float sharpness)
|
||||
{
|
||||
// OpenGL ES doesn't support LOD bias via glTexParameter.
|
||||
if (!GLAD_VERSION_1_4)
|
||||
return;
|
||||
|
||||
// LOD bias has the range (-maxbias, maxbias)
|
||||
mipmapSharpness = std::min(std::max(sharpness, -maxMipmapSharpness + 0.01f), maxMipmapSharpness - 0.01f);
|
||||
|
||||
@@ -225,7 +229,7 @@ void Image::generateMipmaps()
|
||||
// The GL_GENERATE_MIPMAP texparameter is set in loadVolatile if we don't
|
||||
// have support for glGenerateMipmap.
|
||||
if (flags.mipmaps && !isCompressed() &&
|
||||
(GLAD_VERSION_3_0 || GLAD_ARB_framebuffer_object))
|
||||
(GLAD_ES_VERSION_2_0 || GLAD_VERSION_3_0 || GLAD_ARB_framebuffer_object))
|
||||
{
|
||||
// Driver bug: http://www.opengl.org/wiki/Common_Mistakes#Automatic_mipmap_generation
|
||||
#if defined(LOVE_WINDOWS) || defined(LOVE_LINUX)
|
||||
@@ -243,7 +247,8 @@ void Image::loadTextureFromCompressedData()
|
||||
int count = flags.mipmaps ? cdata->getMipmapCount() : 1;
|
||||
|
||||
// We have to inform OpenGL if the image doesn't have all mipmap levels.
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, count - 1);
|
||||
if (GLAD_ES_VERSION_3_0 || GLAD_VERSION_1_0)
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, count - 1);
|
||||
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
@@ -283,7 +288,7 @@ bool Image::loadVolatile()
|
||||
throw love::Exception("cannot create image: format is not supported on this system.");
|
||||
}
|
||||
|
||||
if (maxMipmapSharpness == 0.0f)
|
||||
if (maxMipmapSharpness == 0.0f && GLAD_VERSION_1_4)
|
||||
glGetFloatv(GL_MAX_TEXTURE_LOD_BIAS, &maxMipmapSharpness);
|
||||
|
||||
glGenTextures(1, &texture);
|
||||
@@ -300,11 +305,11 @@ bool Image::loadVolatile()
|
||||
return true;
|
||||
}
|
||||
|
||||
if (!flags.mipmaps)
|
||||
if (!flags.mipmaps && (GLAD_ES_VERSION_3_0 || GLAD_VERSION_1_0))
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0);
|
||||
|
||||
if (flags.mipmaps && !isCompressed() &&
|
||||
!(GLAD_VERSION_3_0 || GLAD_ARB_framebuffer_object))
|
||||
!(GLAD_ES_VERSION_2_0 || GLAD_VERSION_3_0 || GLAD_ARB_framebuffer_object))
|
||||
{
|
||||
// Auto-generate mipmaps every time the texture is modified, if
|
||||
// glGenerateMipmap isn't supported.
|
||||
@@ -414,7 +419,7 @@ void Image::loadDefaultTexture()
|
||||
GLubyte px[] = {0xFF,0xFF,0xFF,0xFF, 0xC0,0xC0,0xC0,0xFF,
|
||||
0xC0,0xC0,0xC0,0xFF, 0xFF,0xFF,0xFF,0xFF};
|
||||
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 2, 2, 0, GL_RGBA, GL_UNSIGNED_BYTE, px);
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 2, 2, 0, GL_RGBA, GL_UNSIGNED_BYTE, px);
|
||||
}
|
||||
|
||||
void Image::drawv(const Matrix &t, const Vertex *v)
|
||||
|
||||
@@ -320,7 +320,7 @@ void Mesh::draw(float x, float y, float angle, float sx, float sy, float ox, flo
|
||||
if (texture.get())
|
||||
texture->predraw();
|
||||
else
|
||||
gl.bindTexture(0);
|
||||
gl.bindTexture(gl.getDefaultTexture());
|
||||
|
||||
Matrix m;
|
||||
m.setTransformation(x, y, angle, sx, sy, ox, oy, kx, ky);
|
||||
|
||||
@@ -119,6 +119,8 @@ void OpenGL::setupContext()
|
||||
|
||||
glActiveTexture(curgltextureunit);
|
||||
|
||||
glGetIntegerv(GL_DRAW_FRAMEBUFFER_BINDING, (GLint *) &state.defaultFBO);
|
||||
|
||||
BlendState blend = {GL_ONE, GL_ONE, GL_ZERO, GL_ZERO, GL_FUNC_ADD};
|
||||
setBlendState(blend);
|
||||
|
||||
@@ -142,6 +144,9 @@ void OpenGL::deInitContext()
|
||||
if (!contextInitialized)
|
||||
return;
|
||||
|
||||
glDeleteTextures(1, &state.defaultTexture);
|
||||
state.defaultTexture = 0;
|
||||
|
||||
contextInitialized = false;
|
||||
}
|
||||
|
||||
@@ -155,6 +160,7 @@ void OpenGL::initVendor()
|
||||
}
|
||||
|
||||
// http://feedback.wildfiregames.com/report/opengl/feature/GL_VENDOR
|
||||
// http://stackoverflow.com/questions/2093594/opengl-extensions-available-on-different-android-devices
|
||||
if (strstr(vstr, "ATI Technologies"))
|
||||
vendor = VENDOR_ATI_AMD;
|
||||
else if (strstr(vstr, "NVIDIA"))
|
||||
@@ -167,6 +173,16 @@ void OpenGL::initVendor()
|
||||
vendor = VENDOR_APPLE;
|
||||
else if (strstr(vstr, "Microsoft"))
|
||||
vendor = VENDOR_MICROSOFT;
|
||||
else if (strstr(vstr, "Imagination"))
|
||||
vendor = VENDOR_IMGTEC;
|
||||
else if (strstr(vstr, "ARM"))
|
||||
vendor = VENDOR_ARM;
|
||||
else if (strstr(vstr, "Qualcomm"))
|
||||
vendor = VENDOR_QUALCOMM;
|
||||
else if (strstr(vstr, "Broadcom"))
|
||||
vendor = VENDOR_BROADCOM;
|
||||
else if (strstr(vstr, "Vivante"))
|
||||
vendor = VENDOR_VIVANTE;
|
||||
else
|
||||
vendor = VENDOR_UNKNOWN;
|
||||
}
|
||||
@@ -185,11 +201,14 @@ void OpenGL::initMaxValues()
|
||||
|
||||
glGetIntegerv(GL_MAX_TEXTURE_SIZE, &maxTextureSize);
|
||||
|
||||
int maxattachments = 0;
|
||||
glGetIntegerv(GL_MAX_COLOR_ATTACHMENTS, &maxattachments);
|
||||
int maxattachments = 1;
|
||||
int maxdrawbuffers = 1;
|
||||
|
||||
int maxdrawbuffers = 0;
|
||||
glGetIntegerv(GL_MAX_DRAW_BUFFERS, &maxdrawbuffers);
|
||||
if (GLAD_ES_VERSION_3_0 || GLAD_VERSION_2_0)
|
||||
{
|
||||
glGetIntegerv(GL_MAX_COLOR_ATTACHMENTS, &maxattachments);
|
||||
glGetIntegerv(GL_MAX_DRAW_BUFFERS, &maxdrawbuffers);
|
||||
}
|
||||
|
||||
maxRenderTargets = std::min(maxattachments, maxdrawbuffers);
|
||||
}
|
||||
@@ -211,7 +230,9 @@ void OpenGL::createDefaultTexture()
|
||||
// shaders for untextured primitives vs images.
|
||||
|
||||
GLuint curtexture = state.textureUnits[state.curTextureUnit];
|
||||
bindTexture(0);
|
||||
|
||||
glGenTextures(1, &state.defaultTexture);
|
||||
bindTexture(state.defaultTexture);
|
||||
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
@@ -220,7 +241,7 @@ void OpenGL::createDefaultTexture()
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
|
||||
|
||||
GLubyte pix = 255;
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_LUMINANCE8, 1, 1, 0, GL_LUMINANCE, GL_UNSIGNED_BYTE, &pix);
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_LUMINANCE, 1, 1, 0, GL_LUMINANCE, GL_UNSIGNED_BYTE, &pix);
|
||||
|
||||
bindTexture(curtexture);
|
||||
}
|
||||
@@ -429,6 +450,16 @@ OpenGL::BlendState OpenGL::getBlendState() const
|
||||
return state.blend;
|
||||
}
|
||||
|
||||
GLuint OpenGL::getDefaultFBO() const
|
||||
{
|
||||
return state.defaultFBO;
|
||||
}
|
||||
|
||||
GLuint OpenGL::getDefaultTexture() const
|
||||
{
|
||||
return state.defaultTexture;
|
||||
}
|
||||
|
||||
void OpenGL::setTextureUnit(int textureunit)
|
||||
{
|
||||
if (textureunit < 0 || (size_t) textureunit >= state.textureUnits.size())
|
||||
|
||||
@@ -27,7 +27,8 @@
|
||||
#include "common/Matrix.h"
|
||||
|
||||
// GLAD
|
||||
#include "libraries/glad/gladfuncs.hpp"
|
||||
//#include "libraries/glad/gladfuncs.hpp"
|
||||
#include <gladf/gladfuncs.hpp>
|
||||
|
||||
// C++
|
||||
#include <vector>
|
||||
@@ -79,6 +80,11 @@ public:
|
||||
VENDOR_MESA_SOFT, // Software renderer.
|
||||
VENDOR_APPLE, // Software renderer.
|
||||
VENDOR_MICROSOFT, // Software renderer.
|
||||
VENDOR_IMGTEC,
|
||||
VENDOR_ARM,
|
||||
VENDOR_QUALCOMM,
|
||||
VENDOR_BROADCOM,
|
||||
VENDOR_VIVANTE,
|
||||
VENDOR_UNKNOWN
|
||||
};
|
||||
|
||||
@@ -242,6 +248,17 @@ public:
|
||||
**/
|
||||
BlendState getBlendState() const;
|
||||
|
||||
/**
|
||||
* This will usually be 0 (system drawable), but some platforms require a
|
||||
* non-zero FBO for rendering.
|
||||
**/
|
||||
GLuint getDefaultFBO() const;
|
||||
|
||||
/**
|
||||
* Gets the ID for love's default texture (used for "untextured" primitives.)
|
||||
**/
|
||||
GLuint getDefaultTexture() const;
|
||||
|
||||
/**
|
||||
* Helper for setting the active texture unit.
|
||||
*
|
||||
@@ -336,6 +353,9 @@ private:
|
||||
Viewport viewport;
|
||||
Viewport scissor;
|
||||
|
||||
GLuint defaultFBO;
|
||||
GLuint defaultTexture;
|
||||
|
||||
BlendState blend;
|
||||
|
||||
// The last ID value used for pseudo-instancing.
|
||||
|
||||
@@ -64,6 +64,7 @@ ParticleSystem::ParticleSystem(Texture *texture, uint32 size)
|
||||
, pHead(nullptr)
|
||||
, pTail(nullptr)
|
||||
, particleVerts(nullptr)
|
||||
, ibo(1)
|
||||
, texture(texture)
|
||||
, active(true)
|
||||
, insertMode(INSERT_MODE_TOP)
|
||||
@@ -112,6 +113,7 @@ ParticleSystem::ParticleSystem(const ParticleSystem &p)
|
||||
, pHead(nullptr)
|
||||
, pTail(nullptr)
|
||||
, particleVerts(nullptr)
|
||||
, ibo(p.ibo)
|
||||
, texture(p.texture)
|
||||
, active(p.active)
|
||||
, insertMode(p.insertMode)
|
||||
@@ -196,6 +198,7 @@ void ParticleSystem::setBufferSize(uint32 size)
|
||||
{
|
||||
if (size == 0 || size > MAX_PARTICLES)
|
||||
throw love::Exception("Invalid buffer size");
|
||||
ibo = VertexIndex(size);
|
||||
deleteBuffers();
|
||||
createBuffers(size);
|
||||
reset();
|
||||
@@ -874,6 +877,7 @@ void ParticleSystem::draw(float x, float y, float angle, float sx, float sy, flo
|
||||
}
|
||||
|
||||
texture->predraw();
|
||||
gl.prepareDraw();
|
||||
|
||||
glEnableVertexAttribArray(ATTRIB_COLOR);
|
||||
glEnableVertexAttribArray(ATTRIB_POS);
|
||||
@@ -883,8 +887,10 @@ void ParticleSystem::draw(float x, float y, float angle, float sx, float sy, flo
|
||||
glVertexAttribPointer(ATTRIB_POS, 2, GL_FLOAT, GL_FALSE, sizeof(Vertex), &particleVerts[0].x);
|
||||
glVertexAttribPointer(ATTRIB_TEXCOORD, 2, GL_FLOAT, GL_FALSE, sizeof(Vertex), &particleVerts[0].s);
|
||||
|
||||
gl.prepareDraw();
|
||||
gl.drawArrays(GL_QUADS, 0, pCount * 4);
|
||||
{
|
||||
VertexBuffer::Bind ibo_bind(*ibo.getVertexBuffer());
|
||||
gl.drawElements(GL_TRIANGLES, ibo.getIndexCount(pCount), ibo.getType(), ibo.getPointer(0));
|
||||
}
|
||||
|
||||
glDisableVertexAttribArray(ATTRIB_TEXCOORD);
|
||||
glDisableVertexAttribArray(ATTRIB_POS);
|
||||
|
||||
@@ -29,6 +29,7 @@
|
||||
#include "graphics/Color.h"
|
||||
#include "graphics/Quad.h"
|
||||
#include "Texture.h"
|
||||
#include "VertexBuffer.h"
|
||||
|
||||
// STL
|
||||
#include <vector>
|
||||
@@ -575,6 +576,9 @@ protected:
|
||||
// array of transformed vertex data for all particles, for drawing
|
||||
Vertex *particleVerts;
|
||||
|
||||
// Vertex index buffer.
|
||||
VertexIndex ibo;
|
||||
|
||||
// The texture to be drawn.
|
||||
Object::StrongRef<Texture> texture;
|
||||
|
||||
|
||||
@@ -330,7 +330,7 @@ void Polyline::draw()
|
||||
gl.prepareDraw();
|
||||
|
||||
// draw the core line
|
||||
gl.bindTexture(0);
|
||||
gl.bindTexture(gl.getDefaultTexture());
|
||||
glEnableVertexAttribArray(ATTRIB_POS);
|
||||
glVertexAttribPointer(ATTRIB_POS, 2, GL_FLOAT, GL_FALSE, 0, vertices);
|
||||
gl.drawArrays(draw_mode, 0, vertex_count);
|
||||
|
||||
@@ -129,9 +129,6 @@ GLuint Shader::compileCode(ShaderStage stage, const std::string &code)
|
||||
break;
|
||||
}
|
||||
|
||||
// clear existing errors
|
||||
while (glGetError() != GL_NO_ERROR);
|
||||
|
||||
GLuint shaderid = glCreateShader(glstage);
|
||||
|
||||
if (shaderid == 0)
|
||||
@@ -719,7 +716,7 @@ std::string Shader::getGLSLVersion()
|
||||
|
||||
bool Shader::isSupported()
|
||||
{
|
||||
return getGLSLVersion() >= "1.2";
|
||||
return GLAD_ES_VERSION_2_0 || (getGLSLVersion() >= "1.2");
|
||||
}
|
||||
|
||||
int Shader::getUniformTypeSize(GLenum type) const
|
||||
|
||||
@@ -187,14 +187,10 @@ bool VertexBuffer::load(bool restore)
|
||||
// Copy the old buffer only if 'restore' was requested.
|
||||
const GLvoid *src = restore ? memory_map : nullptr;
|
||||
|
||||
while (GL_NO_ERROR != glGetError())
|
||||
/* clear error messages */;
|
||||
|
||||
// Note that if 'src' is '0', no data will be copied.
|
||||
glBufferData(getTarget(), (GLsizeiptr) getSize(), src, getUsage());
|
||||
GLenum err = glGetError();
|
||||
|
||||
return (GL_NO_ERROR == err);
|
||||
return true;
|
||||
}
|
||||
|
||||
void VertexBuffer::unload()
|
||||
|
||||
Reference in New Issue
Block a user