Mercurial > repos > blastem
comparison render_sdl.c @ 2492:88210caedc53
Get rect fills for Pico pad working in GL mode
author | Michael Pavone <pavone@retrodev.com> |
---|---|
date | Wed, 17 Apr 2024 22:14:37 -0700 |
parents | a0837ea61fda |
children | b62336ceb626 |
comparison
equal
deleted
inserted
replaced
2491:6c834c281fa2 | 2492:88210caedc53 |
---|---|
42 #ifndef DISABLE_OPENGL | 42 #ifndef DISABLE_OPENGL |
43 SDL_GLContext *gl_context; | 43 SDL_GLContext *gl_context; |
44 uint32_t *texture_buf; | 44 uint32_t *texture_buf; |
45 uint32_t tex_width; | 45 uint32_t tex_width; |
46 uint32_t tex_height; | 46 uint32_t tex_height; |
47 GLuint gl_texture; | 47 GLuint gl_texture[2]; |
48 GLuint *gl_static_images; | 48 GLuint *gl_static_images; |
49 GLuint vshader; | 49 GLuint vshader; |
50 GLuint fshader; | 50 GLuint fshader; |
51 GLuint program; | 51 GLuint program; |
52 GLuint gl_buffers[3]; | 52 GLuint gl_buffers[3]; |
55 GLint un_texture; | 55 GLint un_texture; |
56 GLint un_width; | 56 GLint un_width; |
57 GLint un_height; | 57 GLint un_height; |
58 GLint at_pos; | 58 GLint at_pos; |
59 GLint at_uv; | 59 GLint at_uv; |
60 uint8_t color[4]; | |
60 #endif | 61 #endif |
61 } extra_window; | 62 } extra_window; |
62 | 63 |
63 static SDL_Window *main_window; | 64 static SDL_Window *main_window; |
64 static extra_window *extras; | 65 static extra_window *extras; |
1547 if (render_gl) { | 1548 if (render_gl) { |
1548 extras[win_idx].gl_context = SDL_GL_CreateContext(extras[win_idx].win); | 1549 extras[win_idx].gl_context = SDL_GL_CreateContext(extras[win_idx].win); |
1549 SDL_GL_MakeCurrent(extras[win_idx].win, extras[win_idx].gl_context); | 1550 SDL_GL_MakeCurrent(extras[win_idx].win, extras[win_idx].gl_context); |
1550 glEnable(GL_DEBUG_OUTPUT); | 1551 glEnable(GL_DEBUG_OUTPUT); |
1551 glDebugMessageCallback(gl_message_callback, NULL); | 1552 glDebugMessageCallback(gl_message_callback, NULL); |
1552 glGenTextures(1, &extras[win_idx].gl_texture); | 1553 glGenTextures(2, extras[win_idx].gl_texture); |
1553 glBindTexture(GL_TEXTURE_2D, extras[win_idx].gl_texture); | 1554 for (int i = 0; i < 2; i++) |
1554 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); | 1555 { |
1555 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); | 1556 glBindTexture(GL_TEXTURE_2D, extras[win_idx].gl_texture[i]); |
1556 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); | 1557 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); |
1557 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); | 1558 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); |
1558 extras[win_idx].tex_width = width; | 1559 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); |
1559 extras[win_idx].tex_height = height; | 1560 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); |
1560 char *npot_textures = tern_find_path_default(config, "video\0npot_textures\0", (tern_val){.ptrval = "off"}, TVAL_PTR).ptrval; | 1561 if (i) { |
1561 if (strcmp(npot_textures, "on")) { | 1562 glTexImage2D(GL_TEXTURE_2D, 0, INTERNAL_FORMAT, 1, 1, 0, SRC_FORMAT, GL_UNSIGNED_BYTE, extras[win_idx].color); |
1562 extras[win_idx].tex_width = nearest_pow2(width); | 1563 } else { |
1563 extras[win_idx].tex_height = nearest_pow2(height); | 1564 extras[win_idx].tex_width = width; |
1564 } | 1565 extras[win_idx].tex_height = height; |
1565 extras[win_idx].texture_buf = calloc(extras[win_idx].tex_width * extras[win_idx].tex_height, sizeof(uint32_t)); | 1566 char *npot_textures = tern_find_path_default(config, "video\0npot_textures\0", (tern_val){.ptrval = "off"}, TVAL_PTR).ptrval; |
1566 glTexImage2D(GL_TEXTURE_2D, 0, INTERNAL_FORMAT, extras[win_idx].tex_width, extras[win_idx].tex_height, 0, SRC_FORMAT, GL_UNSIGNED_BYTE, extras[win_idx].texture_buf); | 1567 if (strcmp(npot_textures, "on")) { |
1568 extras[win_idx].tex_width = nearest_pow2(width); | |
1569 extras[win_idx].tex_height = nearest_pow2(height); | |
1570 } | |
1571 extras[win_idx].texture_buf = calloc(extras[win_idx].tex_width * extras[win_idx].tex_height, sizeof(uint32_t)); | |
1572 glTexImage2D(GL_TEXTURE_2D, 0, INTERNAL_FORMAT, extras[win_idx].tex_width, extras[win_idx].tex_height, 0, SRC_FORMAT, GL_UNSIGNED_BYTE, extras[win_idx].texture_buf); | |
1573 } | |
1574 } | |
1567 glGenBuffers(3, extras[win_idx].gl_buffers); | 1575 glGenBuffers(3, extras[win_idx].gl_buffers); |
1568 glBindBuffer(GL_ARRAY_BUFFER, extras[win_idx].gl_buffers[0]); | 1576 glBindBuffer(GL_ARRAY_BUFFER, extras[win_idx].gl_buffers[0]); |
1569 glBufferData(GL_ARRAY_BUFFER, sizeof(vertex_data_default), vertex_data_default, GL_STATIC_DRAW); | 1577 glBufferData(GL_ARRAY_BUFFER, sizeof(vertex_data_default), vertex_data_default, GL_STATIC_DRAW); |
1570 glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, extras[win_idx].gl_buffers[1]); | 1578 glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, extras[win_idx].gl_buffers[1]); |
1571 glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(element_data), element_data, GL_STATIC_DRAW); | 1579 glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(element_data), element_data, GL_STATIC_DRAW); |
1587 extras[win_idx].un_texture = glGetUniformLocation(program, "texture"); | 1595 extras[win_idx].un_texture = glGetUniformLocation(program, "texture"); |
1588 extras[win_idx].un_width = glGetUniformLocation(program, "width"); | 1596 extras[win_idx].un_width = glGetUniformLocation(program, "width"); |
1589 extras[win_idx].un_height = glGetUniformLocation(program, "height"); | 1597 extras[win_idx].un_height = glGetUniformLocation(program, "height"); |
1590 extras[win_idx].at_pos = glGetAttribLocation(program, "pos"); | 1598 extras[win_idx].at_pos = glGetAttribLocation(program, "pos"); |
1591 extras[win_idx].at_uv = glGetAttribLocation(program, "uv"); | 1599 extras[win_idx].at_uv = glGetAttribLocation(program, "uv"); |
1600 extras[win_idx].color[3] = 255; | |
1592 } else { | 1601 } else { |
1593 sdl_renderer: | 1602 sdl_renderer: |
1594 #endif | 1603 #endif |
1595 extras[win_idx].renderer = SDL_CreateRenderer(extras[win_idx].win, -1, SDL_RENDERER_ACCELERATED); | 1604 extras[win_idx].renderer = SDL_CreateRenderer(extras[win_idx].win, -1, SDL_RENDERER_ACCELERATED); |
1596 if (!extras[win_idx].renderer) { | 1605 if (!extras[win_idx].renderer) { |
1619 uint8_t win_idx = which - FRAMEBUFFER_USER_START; | 1628 uint8_t win_idx = which - FRAMEBUFFER_USER_START; |
1620 if (extras[win_idx].renderer) { | 1629 if (extras[win_idx].renderer) { |
1621 //Destroying the renderers also frees the textures | 1630 //Destroying the renderers also frees the textures |
1622 SDL_DestroyRenderer(extras[win_idx].renderer); | 1631 SDL_DestroyRenderer(extras[win_idx].renderer); |
1623 extras[win_idx].renderer = NULL; | 1632 extras[win_idx].renderer = NULL; |
1633 free (extras[win_idx].static_images); | |
1634 extras[win_idx].static_images = NULL; | |
1624 } | 1635 } |
1625 #ifndef DISABLE_OPENGL | 1636 #ifndef DISABLE_OPENGL |
1626 else { | 1637 else { |
1627 SDL_GL_MakeCurrent(extras[win_idx].win, extras[win_idx].gl_context); | 1638 SDL_GL_MakeCurrent(extras[win_idx].win, extras[win_idx].gl_context); |
1628 glDeleteProgram(extras[win_idx].program); | 1639 glDeleteProgram(extras[win_idx].program); |
1629 glDeleteShader(extras[win_idx].vshader); | 1640 glDeleteShader(extras[win_idx].vshader); |
1630 glDeleteShader(extras[win_idx].fshader); | 1641 glDeleteShader(extras[win_idx].fshader); |
1631 glDeleteBuffers(2, extras[win_idx].gl_buffers); | 1642 glDeleteBuffers(3, extras[win_idx].gl_buffers); |
1632 glDeleteTextures(1, &extras[win_idx].gl_texture); | 1643 glDeleteTextures(2, extras[win_idx].gl_texture); |
1644 for (uint8_t i = 0; i < extras[win_idx].num_static; i++) | |
1645 { | |
1646 if (extras[win_idx].gl_static_images[i]) { | |
1647 glDeleteTextures(1, extras[win_idx].gl_static_images + i); | |
1648 } | |
1649 } | |
1633 SDL_GL_DeleteContext(extras[win_idx].gl_context); | 1650 SDL_GL_DeleteContext(extras[win_idx].gl_context); |
1651 free(extras[win_idx].image_vertices); | |
1652 extras[win_idx].image_vertices = NULL; | |
1653 free(extras[win_idx].gl_static_images); | |
1654 extras[win_idx].gl_static_images = NULL; | |
1634 } | 1655 } |
1635 #endif | 1656 #endif |
1636 SDL_DestroyWindow(extras[win_idx].win); | 1657 SDL_DestroyWindow(extras[win_idx].win); |
1637 | 1658 |
1638 extras[win_idx].win = NULL; | 1659 extras[win_idx].win = NULL; |
1660 extras[win_idx].num_static = 0; | |
1639 } | 1661 } |
1640 | 1662 |
1641 #ifndef DISABLE_OPENGL | 1663 #ifndef DISABLE_OPENGL |
1642 static void extra_draw_quad(extra_window *extra, GLuint texture, float width, float height) | 1664 static void extra_draw_quad(extra_window *extra, GLuint texture, float width, float height) |
1643 { | 1665 { |
1732 } | 1754 } |
1733 free(pixels); | 1755 free(pixels); |
1734 return img_index; | 1756 return img_index; |
1735 } | 1757 } |
1736 | 1758 |
1759 #ifndef DISABLE_OPENGL | |
1760 static void extra_update_verts(extra_window *extra, int x, int y, int width, int height) | |
1761 { | |
1762 memcpy(extra->image_vertices, vertex_data_default, sizeof(vertex_data_default)); | |
1763 extra->image_vertices[0] = extra->image_vertices[4] = 2.0f * x / (float)extra->width - 1.0f; | |
1764 extra->image_vertices[2] = extra->image_vertices[6] = 2.0f * (x + width) / (float)extra->width - 1.0f; | |
1765 extra->image_vertices[1] = extra->image_vertices[3] = -2.0f * (y + height) / (float)extra->height + 1.0f; | |
1766 extra->image_vertices[5] = extra->image_vertices[7] = -2.0f * y / (float)extra->height + 1.0f; | |
1767 | |
1768 SDL_GL_MakeCurrent(extra->win, extra->gl_context); | |
1769 glBindBuffer(GL_ARRAY_BUFFER, extra->image_buffer); | |
1770 glBufferData(GL_ARRAY_BUFFER, sizeof(vertex_data_default), extra->image_vertices, GL_DYNAMIC_DRAW); | |
1771 } | |
1772 #endif | |
1773 | |
1737 void render_draw_image(uint8_t window, uint8_t image, int x, int y, int width, int height) | 1774 void render_draw_image(uint8_t window, uint8_t image, int x, int y, int width, int height) |
1738 { | 1775 { |
1739 extra_window *extra = extras + window - FRAMEBUFFER_USER_START; | 1776 extra_window *extra = extras + window - FRAMEBUFFER_USER_START; |
1740 if (extra->renderer) { | 1777 if (extra->renderer) { |
1741 SDL_Rect dst = { | 1778 SDL_Rect dst = { |
1746 }; | 1783 }; |
1747 SDL_RenderCopy(extra->renderer, extra->static_images[image], NULL, &dst); | 1784 SDL_RenderCopy(extra->renderer, extra->static_images[image], NULL, &dst); |
1748 } | 1785 } |
1749 #ifndef DISABLE_OPENGL | 1786 #ifndef DISABLE_OPENGL |
1750 else { | 1787 else { |
1751 memcpy(extra->image_vertices, vertex_data_default, sizeof(vertex_data_default)); | 1788 extra_update_verts(extra, x, y, width, height); |
1752 extra->image_vertices[0] = extra->image_vertices[4] = 2.0f * x / (float)extra->width - 1.0f; | |
1753 extra->image_vertices[2] = extra->image_vertices[6] = 2.0f * (x + width) / (float)extra->width - 1.0f; | |
1754 extra->image_vertices[1] = extra->image_vertices[3] = -2.0f * (y + height) / (float)extra->height + 1.0f; | |
1755 extra->image_vertices[5] = extra->image_vertices[7] = -2.0f * y / (float)extra->height + 1.0f; | |
1756 | |
1757 SDL_GL_MakeCurrent(extra->win, extra->gl_context); | |
1758 glBindBuffer(GL_ARRAY_BUFFER, extra->image_buffer); | |
1759 glBufferData(GL_ARRAY_BUFFER, sizeof(vertex_data_default), extra->image_vertices, GL_DYNAMIC_DRAW); | |
1760 extra_draw_quad(extra, extra->gl_static_images[image], 1.0f, 1.0f); | 1789 extra_draw_quad(extra, extra->gl_static_images[image], 1.0f, 1.0f); |
1761 } | 1790 } |
1762 #endif | 1791 #endif |
1763 } | 1792 } |
1764 | 1793 |
1778 #endif | 1807 #endif |
1779 } | 1808 } |
1780 | 1809 |
1781 void render_fill_rect(uint8_t window, uint8_t r, uint8_t g, uint8_t b, int x, int y, int width, int height) | 1810 void render_fill_rect(uint8_t window, uint8_t r, uint8_t g, uint8_t b, int x, int y, int width, int height) |
1782 { | 1811 { |
1783 uint8_t win_idx = window - FRAMEBUFFER_USER_START; | 1812 extra_window *extra = extras + window - FRAMEBUFFER_USER_START; |
1784 if (extras[win_idx].renderer) { | 1813 if (extra->renderer) { |
1785 SDL_SetRenderDrawColor(extras[win_idx].renderer, r, g, b, 255); | 1814 SDL_SetRenderDrawColor(extra->renderer, r, g, b, 255); |
1786 SDL_Rect dst = { | 1815 SDL_Rect dst = { |
1787 .x = x, | 1816 .x = x, |
1788 .y = y, | 1817 .y = y, |
1789 .w = width, | 1818 .w = width, |
1790 .h = height | 1819 .h = height |
1791 }; | 1820 }; |
1792 SDL_RenderFillRect(extras[win_idx].renderer, &dst); | 1821 SDL_RenderFillRect(extra->renderer, &dst); |
1793 } | 1822 } |
1794 #ifndef DISABLE_OPENGL | 1823 #ifndef DISABLE_OPENGL |
1795 else { | 1824 else { |
1796 //TODO: implement me | 1825 extra_update_verts(extra, x, y, width, height); |
1826 extra->color[0] = b; | |
1827 extra->color[1] = g; | |
1828 extra->color[2] = r; | |
1829 glBindTexture(GL_TEXTURE_2D, extra->gl_texture[1]); | |
1830 glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 1, 1, SRC_FORMAT, GL_UNSIGNED_BYTE, extra->color); | |
1831 extra_draw_quad(extra, extra->gl_texture[1], 1.0f, 1.0f); | |
1797 } | 1832 } |
1798 #endif | 1833 #endif |
1799 } | 1834 } |
1800 | 1835 |
1801 void render_window_refresh(uint8_t window) | 1836 void render_window_refresh(uint8_t window) |
1961 } | 1996 } |
1962 #endif | 1997 #endif |
1963 } else if (render_gl && which >= FRAMEBUFFER_USER_START) { | 1998 } else if (render_gl && which >= FRAMEBUFFER_USER_START) { |
1964 uint8_t win_idx = which - FRAMEBUFFER_USER_START; | 1999 uint8_t win_idx = which - FRAMEBUFFER_USER_START; |
1965 SDL_GL_MakeCurrent(extras[win_idx].win, extras[win_idx].gl_context); | 2000 SDL_GL_MakeCurrent(extras[win_idx].win, extras[win_idx].gl_context); |
1966 glBindTexture(GL_TEXTURE_2D, extras[win_idx].gl_texture); | 2001 glBindTexture(GL_TEXTURE_2D, extras[win_idx].gl_texture[0]); |
1967 glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, extras[win_idx].width, extras[win_idx].height, SRC_FORMAT, GL_UNSIGNED_BYTE, buffer); | 2002 glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, extras[win_idx].width, extras[win_idx].height, SRC_FORMAT, GL_UNSIGNED_BYTE, buffer); |
1968 } else { | 2003 } else { |
1969 #endif | 2004 #endif |
1970 uint32_t shot_height = height; | 2005 uint32_t shot_height = height; |
1971 //TODO: Support SYNC_AUDIO_THREAD/SYNC_EXTERNAL for render API framebuffers | 2006 //TODO: Support SYNC_AUDIO_THREAD/SYNC_EXTERNAL for render API framebuffers |
2033 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); | 2068 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); |
2034 | 2069 |
2035 glBindBuffer(GL_ARRAY_BUFFER, extras[win_idx].gl_buffers[0]); | 2070 glBindBuffer(GL_ARRAY_BUFFER, extras[win_idx].gl_buffers[0]); |
2036 extra_draw_quad( | 2071 extra_draw_quad( |
2037 extras + win_idx, | 2072 extras + win_idx, |
2038 extras[win_idx].gl_texture, | 2073 extras[win_idx].gl_texture[0], |
2039 (float)extras[win_idx].width / (float)extras[win_idx].tex_width, | 2074 (float)extras[win_idx].width / (float)extras[win_idx].tex_width, |
2040 (float)extras[win_idx].height / (float)extras[win_idx].tex_height | 2075 (float)extras[win_idx].height / (float)extras[win_idx].tex_height |
2041 ); | 2076 ); |
2042 | 2077 |
2043 SDL_GL_SwapWindow(extras[win_idx].win); | 2078 SDL_GL_SwapWindow(extras[win_idx].win); |