src/texture.c

changeset 88
6234b7ea48f3
parent 86
943bf9d7c6d6
child 89
e1f682a8a145
equal deleted inserted replaced
87:874a02a683c5 88:6234b7ea48f3
23 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 23 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
24 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 24 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25 * POSSIBILITY OF SUCH DAMAGE. 25 * POSSIBILITY OF SUCH DAMAGE.
26 */ 26 */
27 27
28 #include "ascension/context.h"
28 #include "ascension/texture.h" 29 #include "ascension/texture.h"
29 #include "ascension/error.h" 30 #include "ascension/error.h"
31 #include "ascension/filesystem.h"
30 32
31 #include <assert.h> 33 #include <assert.h>
32 #include <GL/glew.h> 34 #include <GL/glew.h>
35 #include <SDL2/SDL_image.h>
33 36
34 void asc_texture_bind(AscTexture const *tex, int uniform_location, int unit) { 37 void asc_texture_bind(AscTexture const *tex, int uniform_location, int unit) {
35 glActiveTexture(GL_TEXTURE0 + unit); 38 glActiveTexture(GL_TEXTURE0 + unit);
36 GLenum error = glGetError(); 39 GLenum error = glGetError();
37 if (error == GL_INVALID_ENUM) { 40 if (error == GL_INVALID_ENUM) {
46 if (asc_texture_uninitialized(tex)) { 49 if (asc_texture_uninitialized(tex)) {
47 asc_error("Tried to use uninitialized texture."); 50 asc_error("Tried to use uninitialized texture.");
48 asc_dprintf("Texture address: %"PRIxPTR, (uintptr_t) tex); 51 asc_dprintf("Texture address: %"PRIxPTR, (uintptr_t) tex);
49 return; 52 return;
50 } 53 }
54 tex->width = surface->w;
55 tex->height = surface->h;
51 glBindTexture(tex->target,tex->tex_id); 56 glBindTexture(tex->target,tex->tex_id);
52 glPixelStorei(GL_UNPACK_ROW_LENGTH, 57 glPixelStorei(GL_UNPACK_ROW_LENGTH,
53 surface->pitch / surface->format->BytesPerPixel); 58 surface->pitch / surface->format->BytesPerPixel);
54 glTexImage2D(tex->target, 0, GL_RGBA, 59
60 // Determine the format and internal format based on the SDL surface format
61 GLint internal_format;
62 GLenum format;
63 switch (surface->format->format) {
64 case SDL_PIXELFORMAT_RGB24:
65 internal_format = GL_RGB8;
66 format = GL_RGB;
67 break;
68 case SDL_PIXELFORMAT_BGR24:
69 internal_format = GL_RGB8;
70 format = GL_BGR;
71 break;
72 case SDL_PIXELFORMAT_RGBA32:
73 case SDL_PIXELFORMAT_ABGR32:
74 internal_format = GL_RGBA8;
75 format = GL_RGBA;
76 break;
77 case SDL_PIXELFORMAT_ARGB32:
78 case SDL_PIXELFORMAT_BGRA32:
79 internal_format = GL_RGBA8;
80 format = GL_BGRA;
81 break;
82 default:
83 // TODO: add more output once asc_error allows format strings
84 asc_error("Unsupported pixel format.");
85 return;
86 }
87 glTexImage2D(tex->target, 0, internal_format,
55 surface->w, surface->h, 88 surface->w, surface->h,
56 0, GL_BGRA, 89 0, format,
57 GL_UNSIGNED_BYTE, surface->pixels); 90 GL_UNSIGNED_BYTE, surface->pixels);
91 // TODO: replace catch all with proper error handling for this single call
58 asc_error_catch_all_gl(); 92 asc_error_catch_all_gl();
93 }
94
95 void asc_texture_from_file(AscTexture *tex, const char *name) {
96 cxmutstr filepath = asc_filesystem_combine_paths(cx_strcast(asc_context.texture_path), cx_str(name));
97 asc_dprintf("Load texture from %" CX_PRIstr, CX_SFMT(filepath));
98 SDL_Surface *image = IMG_Load(filepath.ptr);
99 cx_strfree(&filepath);
100 if (image == NULL) {
101 asc_error("Failed to load texture.");
102 asc_error(IMG_GetError());
103 return;
104 }
105 asc_texture_from_surface(tex, image);
106 asc_dprintf("Free temporary surface %"PRIxPTR, (uintptr_t) image);
107 SDL_FreeSurface(image);
59 } 108 }
60 109
61 void asc_texture_init( 110 void asc_texture_init(
62 AscTexture *tex, 111 AscTexture *tex,
63 enum asc_texture_target target, 112 enum asc_texture_target target,
64 enum asc_texture_min_filter min_filter, 113 enum asc_texture_min_filter min_filter,
65 enum asc_texture_mag_filter mag_filter 114 enum asc_texture_mag_filter mag_filter
66 ) { 115 ) {
67 static const GLenum texture_targets[] = { 116 static const GLenum texture_targets[] = {
68 GL_TEXTURE_RECTANGLE 117 GL_TEXTURE_RECTANGLE,
118 GL_TEXTURE_2D,
69 }; 119 };
70 static const GLint texture_filters[] = { 120 static const GLint texture_filters[] = {
71 GL_NEAREST, 121 GL_NEAREST,
72 GL_LINEAR, 122 GL_LINEAR,
73 GL_NEAREST_MIPMAP_NEAREST, 123 GL_NEAREST_MIPMAP_NEAREST,

mercurial