X-Git-Url: http://git.tdb.fi/?a=blobdiff_plain;f=source%2Ftexture.cpp;h=40f18d45eff1f0c8d10d2363d8ea2a6123bbc650;hb=b617c5d7b5283ad260a77f01e42e6170cabbc03d;hp=d12e18e0fa4766efd60bf46ff594376f7796b546;hpb=7adcad3b40a03000a82e32db4523761c218309b8;p=libs%2Fgl.git diff --git a/source/texture.cpp b/source/texture.cpp index d12e18e0..40f18d45 100644 --- a/source/texture.cpp +++ b/source/texture.cpp @@ -1,70 +1,137 @@ +/* $Id$ + +This file is part of libmspgl +Copyright © 2007 Mikko Rasa, Mikkosoft Productions +Distributed under the LGPL +*/ + +#include "except.h" #include "texture.h" +#include "texunit.h" + +using namespace std; namespace Msp { namespace GL { +istream &operator>>(istream &in, TextureFilter &tf) +{ + string str; + in>>str; + + if(str=="NEAREST") + tf = NEAREST; + else if(str=="LINEAR") + tf = LINEAR; + else if(str=="NEAREST_MIPMAP_NEAREST") + tf = NEAREST_MIPMAP_NEAREST; + else if(str=="NEAREST_MIPMAP_LINEAR") + tf = NEAREST_MIPMAP_LINEAR; + else if(str=="LINEAR_MIPMAP_NEAREST") + tf = LINEAR_MIPMAP_NEAREST; + else if(str=="LINEAR_MIPMAP_LINEAR") + tf = LINEAR_MIPMAP_LINEAR; + else + in.setstate(ios_base::failbit); + + return in; +} + + void Texture::bind() const { - if(!target) return; + if(!target) + throw InvalidState("Attempt to bind a texture without target"); + + const Texture *cur = TexUnit::current().get_texture(); + if(cur!=this) + { + if(cur && cur->target!=target) + glDisable(cur->target); + if(!cur || cur->target!=target) + glEnable(target); + glBindTexture(target, id); + TexUnit::current().set_texture(this); + } +} - glEnable(target); - glBindTexture(target, id); - bound=this; +void Texture::bind_to(unsigned i) const +{ + TexUnit::activate(i); + bind(); } void Texture::parameter(GLenum param, int value) { - if(bound!=this) bind(); + maybe_bind(); glTexParameteri(target, param, value); } void Texture::parameter(GLenum param, float value) { - if(bound!=this) bind(); + maybe_bind(); glTexParameterf(target, param, value); } -sizei Texture::get_width(int level) const +Texture::~Texture() { - if(bound!=this) bind(); + glDeleteTextures(1, &id); +} - int width; - glGetTexLevelParameteriv(target, level, GL_TEXTURE_WIDTH, &width); - return width; +void Texture::unbind() +{ + const Texture *cur = TexUnit::current().get_texture(); + if(!cur) + return; + + glBindTexture(cur->target, 0); + glDisable(cur->target); + TexUnit::current().set_texture(0); } -sizei Texture::get_height(int level) const +void Texture::unbind_from(unsigned i) { - if(bound!=this) bind(); + TexUnit::activate(i); + unbind(); +} - int height; - glGetTexLevelParameteriv(target, level, GL_TEXTURE_HEIGHT, &height); - return height; +Texture::Texture(): + target(0) +{ + glGenTextures(1, &id); } -sizei Texture::get_depth(int level) const +void Texture::maybe_bind() const { - if(bound!=this) bind(); + if(TexUnit::current().get_texture()!=this) + bind(); +} + - int depth; - glGetTexLevelParameteriv(target, level, GL_TEXTURE_DEPTH, &depth); - return depth; +Texture::Loader::Loader(Texture &t): + DataFile::ObjectLoader(t) +{ + add("min_filter", &Loader::min_filter); + add("mag_filter", &Loader::mag_filter); + add("generate_mipmap", &Loader::generate_mipmap); } -Texture::~Texture() +void Texture::Loader::min_filter(TextureFilter f) { - glDeleteTextures(1, &id); + obj.set_min_filter(f); } -Texture::Texture(): - target(0) +void Texture::Loader::mag_filter(TextureFilter f) { - glGenTextures(1, &id); + obj.set_mag_filter(f); } -const Texture *Texture::bound=0; +void Texture::Loader::generate_mipmap(bool gm) +{ + obj.parameter(GL_GENERATE_MIPMAP_SGIS, gm); +} } // namespace GL } // namespace Msp