mirror of
https://github.com/RGBCube/serenity
synced 2025-07-25 16:47:36 +00:00
LibGL: Implement glDrawPixels
and add stub for glBitmap
This commit is contained in:
parent
c2960e68a8
commit
401472c9a4
7 changed files with 149 additions and 1 deletions
|
@ -201,6 +201,18 @@ extern "C" {
|
||||||
|
|
||||||
// Source pixel data format
|
// Source pixel data format
|
||||||
#define GL_UNSIGNED_BYTE 0x1401
|
#define GL_UNSIGNED_BYTE 0x1401
|
||||||
|
#define GL_UNSIGNED_BYTE_3_3_2 0x8032
|
||||||
|
#define GL_UNSIGNED_SHORT_4_4_4_4 0x8033
|
||||||
|
#define GL_UNSIGNED_SHORT_5_5_5_1 0x8034
|
||||||
|
#define GL_UNSIGNED_INT_8_8_8_8 0x8035
|
||||||
|
#define GL_UNSIGNED_INT_10_10_10_2 0x8036
|
||||||
|
#define GL_UNSIGNED_BYTE_2_3_3_REV 0x8362
|
||||||
|
#define GL_UNSIGNED_SHORT_5_6_5 0x8363
|
||||||
|
#define GL_UNSIGNED_SHORT_5_6_5_REV 0x8364
|
||||||
|
#define GL_UNSIGNED_SHORT_4_4_4_4_REV 0x8365
|
||||||
|
#define GL_UNSIGNED_SHORT_1_5_5_5_REV 0x8366
|
||||||
|
#define GL_UNSIGNED_INT_8_8_8_8_REV 0x8367
|
||||||
|
#define GL_UNSIGNED_INT_2_10_10_10_REV 0x8368
|
||||||
|
|
||||||
// Stencil buffer operations
|
// Stencil buffer operations
|
||||||
#define GL_KEEP 0x1E00
|
#define GL_KEEP 0x1E00
|
||||||
|
@ -450,6 +462,7 @@ GLAPI void glColorPointer(GLint size, GLenum type, GLsizei stride, const void* p
|
||||||
GLAPI void glTexCoordPointer(GLint size, GLenum type, GLsizei stride, const void* pointer);
|
GLAPI void glTexCoordPointer(GLint size, GLenum type, GLsizei stride, const void* pointer);
|
||||||
GLAPI void glDrawArrays(GLenum mode, GLint first, GLsizei count);
|
GLAPI void glDrawArrays(GLenum mode, GLint first, GLsizei count);
|
||||||
GLAPI void glDrawElements(GLenum mode, GLsizei count, GLenum type, const void* indices);
|
GLAPI void glDrawElements(GLenum mode, GLsizei count, GLenum type, const void* indices);
|
||||||
|
GLAPI void glDrawPixels(GLsizei width, GLsizei height, GLenum format, GLenum type, const void* data);
|
||||||
GLAPI void glDepthRange(GLdouble nearVal, GLdouble farVal);
|
GLAPI void glDepthRange(GLdouble nearVal, GLdouble farVal);
|
||||||
GLAPI void glDepthFunc(GLenum func);
|
GLAPI void glDepthFunc(GLenum func);
|
||||||
GLAPI void glPolygonMode(GLenum face, GLenum mode);
|
GLAPI void glPolygonMode(GLenum face, GLenum mode);
|
||||||
|
@ -475,6 +488,7 @@ GLAPI void glMaterialfv(GLenum face, GLenum pname, GLfloat const* params);
|
||||||
GLAPI void glLineWidth(GLfloat width);
|
GLAPI void glLineWidth(GLfloat width);
|
||||||
GLAPI void glPushAttrib(GLbitfield mask);
|
GLAPI void glPushAttrib(GLbitfield mask);
|
||||||
GLAPI void glPopAttrib();
|
GLAPI void glPopAttrib();
|
||||||
|
GLAPI void glBitmap(GLsizei width, GLsizei height, GLfloat xorig, GLfloat yorig, GLfloat xmove, GLfloat ymove, GLubyte const* bitmap);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
|
|
|
@ -79,6 +79,7 @@ public:
|
||||||
virtual void gl_tex_coord_pointer(GLint size, GLenum type, GLsizei stride, const void* pointer) = 0;
|
virtual void gl_tex_coord_pointer(GLint size, GLenum type, GLsizei stride, const void* pointer) = 0;
|
||||||
virtual void gl_draw_arrays(GLenum mode, GLint first, GLsizei count) = 0;
|
virtual void gl_draw_arrays(GLenum mode, GLint first, GLsizei count) = 0;
|
||||||
virtual void gl_draw_elements(GLenum mode, GLsizei count, GLenum type, const void* indices) = 0;
|
virtual void gl_draw_elements(GLenum mode, GLsizei count, GLenum type, const void* indices) = 0;
|
||||||
|
virtual void gl_draw_pixels(GLsizei width, GLsizei height, GLenum format, GLenum type, const void* data) = 0;
|
||||||
virtual void gl_color_mask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha) = 0;
|
virtual void gl_color_mask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha) = 0;
|
||||||
virtual void gl_get_booleanv(GLenum pname, GLboolean* data) = 0;
|
virtual void gl_get_booleanv(GLenum pname, GLboolean* data) = 0;
|
||||||
virtual void gl_get_doublev(GLenum pname, GLdouble* params) = 0;
|
virtual void gl_get_doublev(GLenum pname, GLdouble* params) = 0;
|
||||||
|
@ -102,6 +103,7 @@ public:
|
||||||
virtual void gl_push_attrib(GLbitfield mask) = 0;
|
virtual void gl_push_attrib(GLbitfield mask) = 0;
|
||||||
virtual void gl_pop_attrib() = 0;
|
virtual void gl_pop_attrib() = 0;
|
||||||
virtual void gl_light_model(GLenum pname, GLfloat x, GLfloat y, GLfloat z, GLfloat w) = 0;
|
virtual void gl_light_model(GLenum pname, GLfloat x, GLfloat y, GLfloat z, GLfloat w) = 0;
|
||||||
|
virtual void gl_bitmap(GLsizei width, GLsizei height, GLfloat xorig, GLfloat yorig, GLfloat xmove, GLfloat ymove, GLubyte const* bitmap) = 0;
|
||||||
|
|
||||||
virtual void present() = 0;
|
virtual void present() = 0;
|
||||||
};
|
};
|
||||||
|
|
|
@ -9,6 +9,16 @@
|
||||||
|
|
||||||
extern GL::GLContext* g_gl_context;
|
extern GL::GLContext* g_gl_context;
|
||||||
|
|
||||||
|
void glBitmap(GLsizei width, GLsizei height, GLfloat xorig, GLfloat yorig, GLfloat xmove, GLfloat ymove, GLubyte const* bitmap)
|
||||||
|
{
|
||||||
|
g_gl_context->gl_bitmap(width, height, xorig, yorig, xmove, ymove, bitmap);
|
||||||
|
}
|
||||||
|
|
||||||
|
void glDrawPixels(GLsizei width, GLsizei height, GLenum format, GLenum type, const void* data)
|
||||||
|
{
|
||||||
|
g_gl_context->gl_draw_pixels(width, height, format, type, data);
|
||||||
|
}
|
||||||
|
|
||||||
void glLineWidth(GLfloat width)
|
void glLineWidth(GLfloat width)
|
||||||
{
|
{
|
||||||
g_gl_context->gl_line_width(width);
|
g_gl_context->gl_line_width(width);
|
||||||
|
|
|
@ -1926,6 +1926,106 @@ void SoftwareGLContext::gl_draw_elements(GLenum mode, GLsizei count, GLenum type
|
||||||
glEnd();
|
glEnd();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SoftwareGLContext::gl_draw_pixels(GLsizei width, GLsizei height, GLenum format, GLenum type, const void* data)
|
||||||
|
{
|
||||||
|
APPEND_TO_CALL_LIST_AND_RETURN_IF_NEEDED(gl_draw_pixels, width, height, format, type, data);
|
||||||
|
|
||||||
|
RETURN_WITH_ERROR_IF(!(format == GL_COLOR_INDEX
|
||||||
|
|| format == GL_STENCIL_INDEX
|
||||||
|
|| format == GL_DEPTH_COMPONENT
|
||||||
|
|| format == GL_RGBA
|
||||||
|
|| format == GL_BGRA
|
||||||
|
|| format == GL_RED
|
||||||
|
|| format == GL_GREEN
|
||||||
|
|| format == GL_BLUE
|
||||||
|
|| format == GL_ALPHA
|
||||||
|
|| format == GL_RGB
|
||||||
|
|| format == GL_BGR
|
||||||
|
|| format == GL_LUMINANCE
|
||||||
|
|| format == GL_LUMINANCE_ALPHA),
|
||||||
|
GL_INVALID_ENUM);
|
||||||
|
|
||||||
|
RETURN_WITH_ERROR_IF(!(type == GL_UNSIGNED_BYTE
|
||||||
|
|| type == GL_BYTE
|
||||||
|
|| type == GL_BITMAP
|
||||||
|
|| type == GL_UNSIGNED_SHORT
|
||||||
|
|| type == GL_SHORT
|
||||||
|
|| type == GL_UNSIGNED_INT
|
||||||
|
|| type == GL_INT
|
||||||
|
|| type == GL_FLOAT
|
||||||
|
|| type == GL_UNSIGNED_BYTE_3_3_2
|
||||||
|
|| type == GL_UNSIGNED_BYTE_2_3_3_REV
|
||||||
|
|| type == GL_UNSIGNED_SHORT_5_6_5
|
||||||
|
|| type == GL_UNSIGNED_SHORT_5_6_5_REV
|
||||||
|
|| type == GL_UNSIGNED_SHORT_4_4_4_4
|
||||||
|
|| type == GL_UNSIGNED_SHORT_4_4_4_4_REV
|
||||||
|
|| type == GL_UNSIGNED_SHORT_5_5_5_1
|
||||||
|
|| type == GL_UNSIGNED_SHORT_1_5_5_5_REV
|
||||||
|
|| type == GL_UNSIGNED_INT_8_8_8_8
|
||||||
|
|| type == GL_UNSIGNED_INT_8_8_8_8_REV
|
||||||
|
|| type == GL_UNSIGNED_INT_10_10_10_2
|
||||||
|
|| type == GL_UNSIGNED_INT_2_10_10_10_REV),
|
||||||
|
GL_INVALID_ENUM);
|
||||||
|
|
||||||
|
RETURN_WITH_ERROR_IF(type == GL_BITMAP && !(format == GL_COLOR_INDEX || format == GL_STENCIL_INDEX), GL_INVALID_ENUM);
|
||||||
|
|
||||||
|
RETURN_WITH_ERROR_IF(width < 0 || height < 0, GL_INVALID_VALUE);
|
||||||
|
|
||||||
|
// FIXME: GL_INVALID_OPERATION is generated if format is GL_STENCIL_INDEX and there is no stencil buffer
|
||||||
|
// FIXME: GL_INVALID_OPERATION is generated if format is GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA, GL_RGB, GL_RGBA,
|
||||||
|
// GL_BGR, GL_BGRA, GL_LUMINANCE, or GL_LUMINANCE_ALPHA, and the GL is in color index mode
|
||||||
|
|
||||||
|
RETURN_WITH_ERROR_IF(format != GL_RGB
|
||||||
|
&& (type == GL_UNSIGNED_BYTE_3_3_2
|
||||||
|
|| type == GL_UNSIGNED_BYTE_2_3_3_REV
|
||||||
|
|| type == GL_UNSIGNED_SHORT_5_6_5
|
||||||
|
|| type == GL_UNSIGNED_SHORT_5_6_5_REV),
|
||||||
|
GL_INVALID_OPERATION);
|
||||||
|
|
||||||
|
RETURN_WITH_ERROR_IF(!(format == GL_RGBA || format == GL_BGRA)
|
||||||
|
&& (type == GL_UNSIGNED_SHORT_4_4_4_4
|
||||||
|
|| type == GL_UNSIGNED_SHORT_4_4_4_4_REV
|
||||||
|
|| type == GL_UNSIGNED_SHORT_5_5_5_1
|
||||||
|
|| type == GL_UNSIGNED_SHORT_1_5_5_5_REV
|
||||||
|
|| type == GL_UNSIGNED_INT_8_8_8_8
|
||||||
|
|| type == GL_UNSIGNED_INT_8_8_8_8_REV
|
||||||
|
|| type == GL_UNSIGNED_INT_10_10_10_2
|
||||||
|
|| type == GL_UNSIGNED_INT_2_10_10_10_REV),
|
||||||
|
GL_INVALID_OPERATION);
|
||||||
|
|
||||||
|
// FIXME: GL_INVALID_OPERATION is generated if a non-zero buffer object name is bound to the GL_PIXEL_UNPACK_BUFFER
|
||||||
|
// target and the buffer object's data store is currently mapped.
|
||||||
|
// FIXME: GL_INVALID_OPERATION is generated if a non-zero buffer object name is bound to the GL_PIXEL_UNPACK_BUFFER
|
||||||
|
// target and the data would be unpacked from the buffer object such that the memory reads required would
|
||||||
|
// exceed the data store size.
|
||||||
|
// FIXME: GL_INVALID_OPERATION is generated if a non-zero buffer object name is bound to the GL_PIXEL_UNPACK_BUFFER
|
||||||
|
// target and data is not evenly divisible into the number of bytes needed to store in memory a datum
|
||||||
|
// indicated by type.
|
||||||
|
|
||||||
|
RETURN_WITH_ERROR_IF(m_in_draw_state, GL_INVALID_OPERATION);
|
||||||
|
|
||||||
|
// FIXME: we only support RGBA + GL_UNSIGNED_BYTE, implement all the others!
|
||||||
|
if (format != GL_RGBA || type != GL_UNSIGNED_BYTE) {
|
||||||
|
dbgln("gl_draw_pixels: unsupported format {:#x} or type {:#x}", format, type);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto bitmap_or_error = Gfx::Bitmap::try_create(Gfx::BitmapFormat::BGRA8888, { width, height });
|
||||||
|
RETURN_WITH_ERROR_IF(bitmap_or_error.is_error(), GL_OUT_OF_MEMORY);
|
||||||
|
auto bitmap = bitmap_or_error.release_value();
|
||||||
|
|
||||||
|
// FIXME: implement support for GL_UNPACK_ALIGNMENT and other pixel parameters
|
||||||
|
auto pixel_data = static_cast<u32 const*>(data);
|
||||||
|
for (int y = 0; y < height; ++y)
|
||||||
|
for (int x = 0; x < width; ++x)
|
||||||
|
bitmap->set_pixel(x, y, Color::from_rgba(*(pixel_data++)));
|
||||||
|
|
||||||
|
m_rasterizer.blit(
|
||||||
|
bitmap,
|
||||||
|
static_cast<int>(m_current_raster_position.window_coordinates.x()),
|
||||||
|
static_cast<int>(m_current_raster_position.window_coordinates.y()));
|
||||||
|
}
|
||||||
|
|
||||||
void SoftwareGLContext::gl_depth_range(GLdouble min, GLdouble max)
|
void SoftwareGLContext::gl_depth_range(GLdouble min, GLdouble max)
|
||||||
{
|
{
|
||||||
APPEND_TO_CALL_LIST_AND_RETURN_IF_NEEDED(gl_depth_range, min, max);
|
APPEND_TO_CALL_LIST_AND_RETURN_IF_NEEDED(gl_depth_range, min, max);
|
||||||
|
@ -2366,6 +2466,15 @@ void SoftwareGLContext::gl_light_model(GLenum pname, GLfloat x, GLfloat y, GLflo
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SoftwareGLContext::gl_bitmap(GLsizei width, GLsizei height, GLfloat xorig, GLfloat yorig, GLfloat xmove, GLfloat ymove, GLubyte const* bitmap)
|
||||||
|
{
|
||||||
|
APPEND_TO_CALL_LIST_AND_RETURN_IF_NEEDED(gl_bitmap, width, height, xorig, yorig, xmove, ymove, bitmap);
|
||||||
|
RETURN_WITH_ERROR_IF(m_in_draw_state, GL_INVALID_OPERATION);
|
||||||
|
|
||||||
|
// FIXME: implement
|
||||||
|
dbgln_if(GL_DEBUG, "SoftwareGLContext FIXME: implement gl_bitmap({}, {}, {}, {}, {}, {}, {})", width, height, xorig, yorig, xmove, ymove, bitmap);
|
||||||
|
}
|
||||||
|
|
||||||
void SoftwareGLContext::present()
|
void SoftwareGLContext::present()
|
||||||
{
|
{
|
||||||
m_rasterizer.blit_to(*m_frontbuffer);
|
m_rasterizer.blit_to(*m_frontbuffer);
|
||||||
|
|
|
@ -90,6 +90,7 @@ public:
|
||||||
virtual void gl_tex_coord_pointer(GLint size, GLenum type, GLsizei stride, const void* pointer) override;
|
virtual void gl_tex_coord_pointer(GLint size, GLenum type, GLsizei stride, const void* pointer) override;
|
||||||
virtual void gl_draw_arrays(GLenum mode, GLint first, GLsizei count) override;
|
virtual void gl_draw_arrays(GLenum mode, GLint first, GLsizei count) override;
|
||||||
virtual void gl_draw_elements(GLenum mode, GLsizei count, GLenum type, const void* indices) override;
|
virtual void gl_draw_elements(GLenum mode, GLsizei count, GLenum type, const void* indices) override;
|
||||||
|
virtual void gl_draw_pixels(GLsizei width, GLsizei height, GLenum format, GLenum type, const void* data) override;
|
||||||
virtual void gl_color_mask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha) override;
|
virtual void gl_color_mask(GLboolean red, GLboolean green, GLboolean blue, GLboolean alpha) override;
|
||||||
virtual void gl_get_booleanv(GLenum pname, GLboolean* data) override;
|
virtual void gl_get_booleanv(GLenum pname, GLboolean* data) override;
|
||||||
virtual void gl_get_doublev(GLenum pname, GLdouble* params) override;
|
virtual void gl_get_doublev(GLenum pname, GLdouble* params) override;
|
||||||
|
@ -113,6 +114,7 @@ public:
|
||||||
virtual void gl_push_attrib(GLbitfield mask) override;
|
virtual void gl_push_attrib(GLbitfield mask) override;
|
||||||
virtual void gl_pop_attrib() override;
|
virtual void gl_pop_attrib() override;
|
||||||
virtual void gl_light_model(GLenum pname, GLfloat x, GLfloat y, GLfloat z, GLfloat w) override;
|
virtual void gl_light_model(GLenum pname, GLfloat x, GLfloat y, GLfloat z, GLfloat w) override;
|
||||||
|
virtual void gl_bitmap(GLsizei width, GLsizei height, GLfloat xorig, GLfloat yorig, GLfloat xmove, GLfloat ymove, GLubyte const* bitmap) override;
|
||||||
virtual void present() override;
|
virtual void present() override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
@ -275,6 +277,7 @@ private:
|
||||||
decltype(&SoftwareGLContext::gl_depth_mask),
|
decltype(&SoftwareGLContext::gl_depth_mask),
|
||||||
decltype(&SoftwareGLContext::gl_draw_arrays),
|
decltype(&SoftwareGLContext::gl_draw_arrays),
|
||||||
decltype(&SoftwareGLContext::gl_draw_elements),
|
decltype(&SoftwareGLContext::gl_draw_elements),
|
||||||
|
decltype(&SoftwareGLContext::gl_draw_pixels),
|
||||||
decltype(&SoftwareGLContext::gl_depth_range),
|
decltype(&SoftwareGLContext::gl_depth_range),
|
||||||
decltype(&SoftwareGLContext::gl_polygon_offset),
|
decltype(&SoftwareGLContext::gl_polygon_offset),
|
||||||
decltype(&SoftwareGLContext::gl_scissor),
|
decltype(&SoftwareGLContext::gl_scissor),
|
||||||
|
@ -286,7 +289,8 @@ private:
|
||||||
decltype(&SoftwareGLContext::gl_line_width),
|
decltype(&SoftwareGLContext::gl_line_width),
|
||||||
decltype(&SoftwareGLContext::gl_push_attrib),
|
decltype(&SoftwareGLContext::gl_push_attrib),
|
||||||
decltype(&SoftwareGLContext::gl_pop_attrib),
|
decltype(&SoftwareGLContext::gl_pop_attrib),
|
||||||
decltype(&SoftwareGLContext::gl_light_model)>;
|
decltype(&SoftwareGLContext::gl_light_model),
|
||||||
|
decltype(&SoftwareGLContext::gl_bitmap)>;
|
||||||
|
|
||||||
using ExtraSavedArguments = Variant<
|
using ExtraSavedArguments = Variant<
|
||||||
FloatMatrix4x4>;
|
FloatMatrix4x4>;
|
||||||
|
|
|
@ -604,6 +604,14 @@ void SoftwareRasterizer::clear_depth(float depth)
|
||||||
m_depth_buffer->clear(depth);
|
m_depth_buffer->clear(depth);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SoftwareRasterizer::blit(Gfx::Bitmap const& source, int x, int y)
|
||||||
|
{
|
||||||
|
wait_for_all_threads();
|
||||||
|
|
||||||
|
Gfx::Painter painter { *m_render_target };
|
||||||
|
painter.blit({ x, y }, source, source.rect(), 1.0f, true);
|
||||||
|
}
|
||||||
|
|
||||||
void SoftwareRasterizer::blit_to(Gfx::Bitmap& target)
|
void SoftwareRasterizer::blit_to(Gfx::Bitmap& target)
|
||||||
{
|
{
|
||||||
wait_for_all_threads();
|
wait_for_all_threads();
|
||||||
|
|
|
@ -61,6 +61,7 @@ public:
|
||||||
void resize(const Gfx::IntSize& min_size);
|
void resize(const Gfx::IntSize& min_size);
|
||||||
void clear_color(const FloatVector4&);
|
void clear_color(const FloatVector4&);
|
||||||
void clear_depth(float);
|
void clear_depth(float);
|
||||||
|
void blit(Gfx::Bitmap const&, int x, int y);
|
||||||
void blit_to(Gfx::Bitmap&);
|
void blit_to(Gfx::Bitmap&);
|
||||||
void wait_for_all_threads() const;
|
void wait_for_all_threads() const;
|
||||||
void set_options(const RasterizerOptions&);
|
void set_options(const RasterizerOptions&);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue