X-Git-Url: http://git.tdb.fi/?p=gldbg.git;a=blobdiff_plain;f=flavors%2Fgl%2Fsource%2Ftexturestate.cpp;h=04c36a98e9cc041e843c1e3fa8f447571cf01bff;hp=314ff760d3b3c8f4487ffbb37ae4f1e5259e7104;hb=8ac18c1745c64441dbbdc130b1c396dcde9b21a7;hpb=bc201c7dd5ebef9c0db1142387715c7ad4d53b62 diff --git a/flavors/gl/source/texturestate.cpp b/flavors/gl/source/texturestate.cpp index 314ff76..04c36a9 100644 --- a/flavors/gl/source/texturestate.cpp +++ b/flavors/gl/source/texturestate.cpp @@ -11,11 +11,21 @@ TexImageState::TexImageState(): internal_format(0) { } +void TexImageState::set_1d(GLenum ifmt, unsigned wd) +{ + set_3d(ifmt, wd, 0, 0); +} + void TexImageState::set_2d(GLenum ifmt, unsigned wd, unsigned ht) +{ + set_3d(ifmt, wd, ht, 0); +} + +void TexImageState::set_3d(GLenum ifmt, unsigned wd, unsigned ht, unsigned dp) { width = wd; height = ht; - depth = 0; + depth = dp; internal_format = ifmt; } @@ -33,6 +43,16 @@ string TexImageState::describe() const } +GLenum texture_cube_faces[6] = +{ + GL_TEXTURE_CUBE_MAP_POSITIVE_X, + GL_TEXTURE_CUBE_MAP_NEGATIVE_X, + GL_TEXTURE_CUBE_MAP_POSITIVE_Y, + GL_TEXTURE_CUBE_MAP_NEGATIVE_Y, + GL_TEXTURE_CUBE_MAP_POSITIVE_Z, + GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, +}; + TextureState::TextureState(): id(0), target(0), @@ -46,26 +66,66 @@ TextureState::TextureState(): generate_mipmap(false) { } +TexImageState &TextureState::get_image(unsigned level) +{ + if(images.size()<=level) + images.resize(level+1); + return images[level]; +} + +void TextureState::set_image_1d(unsigned level, GLenum ifmt, unsigned wd) +{ + get_image(level).set_1d(ifmt, wd); + if(level==0 && generate_mipmap) + create_mipmaps(); +} + void TextureState::set_image_2d(unsigned level, GLenum ifmt, unsigned wd, unsigned ht) { - while(1) + get_image(level).set_2d(ifmt, wd, ht); + if(level==0 && generate_mipmap) + create_mipmaps(); +} + +void TextureState::set_face_image_2d(GLenum face, unsigned level, GLenum ifmt, unsigned wd, unsigned ht) +{ + unsigned index = 0; + for(; (index<6 && texture_cube_faces[index]!=face); ++index) ; + if(index>=6) + return; + + set_image_2d(level*6+index, ifmt, wd, ht); +} + +void TextureState::set_image_3d(unsigned level, GLenum ifmt, unsigned wd, unsigned ht, unsigned dp) +{ + get_image(level).set_3d(ifmt, wd, ht, dp); + if(level==0 && generate_mipmap) + create_mipmaps(); +} + +void TextureState::create_mipmaps(unsigned face) +{ + unsigned stride = (target==GL_TEXTURE_CUBE_MAP ? 6 : 1); + if(face>=stride) + face = 0; + + unsigned wd = images[face].width; + unsigned ht = images[face].height; + unsigned dp = images[face].depth; + for(unsigned i=1;; ++i) { - if(images.size()<=level) - images.resize(level+1); - images[level].set_2d(ifmt, wd, ht); - - if(generate_mipmap) - { - if(wd==1 && ht==1) - break; - ++level; - if(wd>1) - wd /= 2; - if(ht>1) - ht /= 2; - } - else + if(wd<=1 && ht<=1 && dp<=1) break; + + if(wd>1) + wd /= 2; + if(ht>1) + ht /= 2; + if(dp>1) + dp /= 2; + + get_image(i*stride+face).set_3d(images[0].internal_format, wd, ht, dp); } } @@ -94,31 +154,52 @@ string TextureState::describe() const string descr = describe_enum(target, "TextureTarget"); if(images.empty()) descr += ", undefined"; + else if(target==GL_TEXTURE_CUBE_MAP) + { + bool homogeneous = true; + for(unsigned i=1; (homogeneous && i<6); ++i) + homogeneous = (images[i].width==images[0].width && images[i].height==images[0].height && + images[i].internal_format==images[0].internal_format); + if(homogeneous) + descr += ", "+images.front().describe(); + else + descr += ", heterogeneous faces"; + } else descr += ", "+images.front().describe(); return descr; } -TexUnitState::TexUnitState(): - current_2d(0), - current_3d(0) -{ } +TexUnitState::Binding *TexUnitState::get_binding(GLenum target) +{ + if(target==GL_TEXTURE_1D) + return &binding_1d; + else if(target==GL_TEXTURE_2D) + return &binding_2d; + else if(target==GL_TEXTURE_3D) + return &binding_3d; + else if(target==GL_TEXTURE_CUBE_MAP) + return &binding_cube; + else + return 0; +} + +const TexUnitState::Binding *TexUnitState::get_binding(GLenum target) const +{ + return const_cast(this)->get_binding(target); +} void TexUnitState::set_current_texture(GLenum target, TextureState *tex) { - if(target==GL_TEXTURE_2D) - current_2d = tex; - else if(target==GL_TEXTURE_3D) - current_3d = tex; + if(Binding *binding = get_binding(target)) + binding->current = tex; } TextureState *TexUnitState::get_current_texture(GLenum target) { - if(target==GL_TEXTURE_2D) - return current_2d; - else if(target==GL_TEXTURE_3D) - return current_3d; + if(Binding *binding = get_binding(target)) + return binding->current; else return 0; } @@ -128,17 +209,43 @@ const TextureState *TexUnitState::get_current_texture(GLenum target) const return const_cast(this)->get_current_texture(target); } +bool TexUnitState::is_enabled(GLenum target) const +{ + if(const Binding *binding = get_binding(target)) + return binding->enabled; + else + return false; +} + string TexUnitState::describe_binding(GLenum target) const { - if(const TextureState *tex = get_current_texture(target)) + if(const Binding *binding = get_binding(target)) + return binding->describe(); + else + return "None"; +} + + +TexUnitState::Binding::Binding(): + enabled(false), + current(0) +{ } + +string TexUnitState::Binding::describe() const +{ + if(current) { - string descr = strformat("%d ", tex->id); - if(tex->images.empty()) + string descr = strformat("%d ", current->id); + if(current->images.empty()) descr += "(undefined)"; else - descr += "("+tex->images.front().describe()+")"; + descr += "("+current->images.front().describe()+")"; + if(enabled) + descr += ", enabled"; return descr; } + else if(enabled) + return "None, enabled"; else return "None"; }