diff --git a/src/AbstractTexture.h b/src/AbstractTexture.h index 12b5a162b..933e4ec90 100644 --- a/src/AbstractTexture.h +++ b/src/AbstractTexture.h @@ -28,22 +28,11 @@ namespace Magnum { /** @brief Base for textures -@attention Don't forget to call @ref Texture::setWrapping() "setWrapping()", - setMinificationFilter() and setMagnificationFilter() after creating the - texture, otherwise the texture will be incomplete. If you specified - @ref Wrapping "Wrapping::ClampToBorder" in @ref Texture::setWrapping() "setWrapping()", - be sure to also call setBorderColor(). If you specified mipmap filtering - in setMinificationFilter(), be sure to also either explicitly set all mip - levels or call generateMipmap(). - -The texture is bound to shader via bind(). Texture uniform on the shader must -also be set to particular texture layer using -AbstractShaderProgram::setUniform(GLint, GLint). - See Texture, CubeMapTexture and CubeMapTextureArray documentation for more -information. +information and usage examples. @section AbstractTexture-performance-optimization Performance optimizations + The engine tracks currently bound textures in all available layers to avoid unnecessary calls to @fn_gl{ActiveTexture} and @fn_gl{BindTexture}. %Texture configuration functions use dedicated highest available texture layer to not @@ -639,6 +628,8 @@ class MAGNUM_EXPORT AbstractTexture { * Sets filter used when the object pixel size is smaller than the * texture size. If @extension{EXT,direct_state_access} is not * available, the texture is bound to some layer before the operation. + * Initial value is (@ref AbstractTexture::Filter "Filter::NearestNeighbor", + * @ref AbstractTexture::Mipmap "Mipmap::Linear"). * @attention For rectangle textures only some modes are supported, * see @ref AbstractTexture::Filter "Filter" and * @ref AbstractTexture::Mipmap "Mipmap" documentation for more @@ -657,6 +648,7 @@ class MAGNUM_EXPORT AbstractTexture { * Sets filter used when the object pixel size is larger than largest * texture size. If @extension{EXT,direct_state_access} is not * available, the texture is bound to some layer before the operation. + * Initial value is @ref AbstractTexture::Filter "Filter::Linear". * @see @fn_gl{ActiveTexture}, @fn_gl{BindTexture} and @fn_gl{TexParameter} * or @fn_gl_extension{TextureParameter,EXT,direct_state_access} * with @def_gl{TEXTURE_MAG_FILTER} @@ -674,6 +666,7 @@ class MAGNUM_EXPORT AbstractTexture { * Border color when @ref AbstractTexture::Wrapping "wrapping" is set * to `ClampToBorder`. If @extension{EXT,direct_state_access} is not * available, the texture is bound to some layer before the operation. + * Initial value is `{0.0f, 0.0f, 0.0f, 0.0f}`. * @see @fn_gl{ActiveTexture}, @fn_gl{BindTexture} and @fn_gl{TexParameter} * or @fn_gl_extension{TextureParameter,EXT,direct_state_access} * with @def_gl{TEXTURE_BORDER_COLOR} diff --git a/src/CubeMapTexture.h b/src/CubeMapTexture.h index 9c734d80e..7da8f60a4 100644 --- a/src/CubeMapTexture.h +++ b/src/CubeMapTexture.h @@ -26,10 +26,9 @@ namespace Magnum { /** @brief Cube map texture -%Texture used mainly for environemnt maps. See AbstractTexture documentation -for more information. It consists of 6 square textures generating 6 faces of -the cube as following. Note that all images must be turned upside down (+Y is -top): +%Texture used mainly for environment maps. It consists of 6 square textures +generating 6 faces of the cube as following. Note that all images must be +turned upside down (+Y is top): +----+ | -Y | @@ -39,11 +38,29 @@ top): | +Y | +----+ -When using cube map texture in the shader, use `samplerCube`. Unlike classic -textures, coordinates for cube map textures is signed three-part vector from -the center of the cube, which intersects one of the six sides of the cube map. - -See AbstractTexture documentation for more information about usage. +@section CubeMapTexture-usage Basic usage + +See Texture documentation for introduction. + +Common usage is to fully configure all texture parameters and then set the +data from e.g. set of Image objects: +@code +Image2D positiveX({256, 256}, Image2D::Components::RGBA, Image2D::ComponentType::UnsignedByte, dataPositiveX); +// ... + +CubeMapTexture texture; +texture.setMagnificationFilter(Texture2D::Filter::Linear) + // ... + ->setData(CubeMapTexture::Coordinate::PositiveX, 0, Texture2D::Format::RGBA8, &positiveX) + ->setData(CubeMapTexture::Coordinate::NegativeX, 0, Texture2D::Format::RGBA8, &negativeX) + // ... +@endcode + +The texture is bound to layer specified by shader via bind(). In shader, the +texture is used via `samplerCube`. Unlike classic textures, coordinates for +cube map textures is signed three-part vector from the center of the cube, +which intersects one of the six sides of the cube map. See also +AbstractShaderProgram for more information. @see CubeMapTextureArray */ diff --git a/src/CubeMapTextureArray.h b/src/CubeMapTextureArray.h index 2d928edc6..cc558a5ee 100644 --- a/src/CubeMapTextureArray.h +++ b/src/CubeMapTextureArray.h @@ -29,12 +29,41 @@ namespace Magnum { /** @brief Cube map texture array -For information, see CubeMapTexture and AbstractTexture documentation. +See CubeMapTexture documentation for introduction. + +@section CubeMapTextureArray-usage Usage + +Common usage is to specify each layer and face separately using setSubData(). +You have to allocate the memory for all layers and faces first, possibly by +passing properly sized empty Image to setData(). Example: array with 16 +layers of cube map faces, each face consisting of six 64x64 images: +@code +Image3D dummy({64, 64, 16*6}, Image3D::Components::RGBA, Image3D::ComponentType::UnsignedByte, nullptr); + +CubeMapTextureArray texture; +texture.setMagnificationFilter(CubeMapTextureArray::Filter::Linear) + // ... + ->setData(0, CubeMapTextureArray::Format::RGBA8, &dummy); + +for(std::size_t i = 0; i != 16; ++i) { + void* dataPositiveX = ...; + Image2D imagePositiveX({64, 64}, Image3D::Components::RGBA, Image3D::ComponentType::UnsignedByte, imagePositiveX); + // ... + + texture->setSubData(i, CubeMapTextureArray::Coordinate::PositiveX, 0, imagePositiveX); + texture->setSubData(i, CubeMapTextureArray::Coordinate::NegativeX, 0, imageNegativeX); + // ... +} + +// ... +@endcode -When using cube map texture in the shader, use `samplerCubeArray`. Unlike -classic textures, coordinates for cube map textures is signed three-part -vector from the center of the cube, which intersects one of the six sides of -the cube map. +The texture is bound to layer specified by shader via bind(). In shader, the +texture is used via `samplerCubeArray`. Unlike classic textures, coordinates +for cube map texture arrays is signed four-part vector. First three parts +define vector from the center of the cube which intersects with one of the six +sides of the cube map, fourth part is layer in the array. See also +AbstractShaderProgram for more information. @see CubeMapTexture::setSeamless() @requires_gl40 Extension @extension{ARB,texture_cube_map_array} diff --git a/src/Texture.h b/src/Texture.h index 1191b8bc7..9d2c45e06 100644 --- a/src/Texture.h +++ b/src/Texture.h @@ -27,12 +27,66 @@ namespace Magnum { /** @brief %Texture -Template class for one- to three-dimensional textures. See AbstractTexture -documentation for more information. +Template class for one- to three-dimensional textures. See also +AbstractTexture documentation for more information. + +@section Texture-usage Usage + +Common usage is to fully configure all texture parameters and then set the +data from e.g. Image. Example configuration of high quality texture with +trilinear anisotropic filtering, i.e. the best you can ask for: +@code +void* data; +Image2D image({4096, 4096}, Image2D::Components::RGBA, Image2D::ComponentType::UnsignedByte, data); + +Texture2D texture; +texture.setMagnificationFilter(Texture2D::Filter::Linear) + ->setMinificationFilter(Texture2D::Filter::Linear, Texture2D::Mipmap::Linear) + ->setWrapping(Texture2D::Wrapping::ClampToEdge) + ->setMaxAnisotropy(Texture2D::maxSupportedAnisotropy) + ->setData(0, Texture2D::Format::RGBA8, &image) + ->generateMipmap(); +@endcode + +@attention Don't forget to fully configure the texture before use. Note that + default configuration (if setMinificationFilter() is not called with + another value) is to use mipmaps, so be sure to either call setMinificationFilter(), + explicitly set all mip levels or call generateMipmap(). If using rectangle + texture, you must also call setWrapping(), because the initial value is + not supported on rectangle textures. See also setMagnificationFilter() and + setBorderColor(). + +The texture is bound to layer specified by shader via bind(). In shader, the +texture is used via `sampler1D`, `sampler2D` or `sampler3D` depending on +dimension count. See also AbstractShaderProgram documentation for more +information. + +@section Texture-array Texture arrays + +It is possible to specify each layer separately using setSubData(), but you +have to allocate the memory for all layers first, possibly by passing properly +sized empty Image to setData(). Example: 2D texture array with 16 layers of +64x64 images: +@code +Image3D dummy({64, 64, 16}, Image3D::Components::RGBA, Image3D::ComponentType::UnsignedByte, nullptr); + +Texture3D texture(Texture3D::Target::Texture2DArray); +texture.setMagnificationFilter(Texture2D::Filter::Linear) + // ... + ->setData(0, Texture2D::Format::RGBA8, &dummy); + +for(std::size_t i = 0; i != 16; ++i) { + void* data = ...; + Image2D image({64, 64}, Image3D::Components::RGBA, Image3D::ComponentType::UnsignedByte, image); + texture->setSubData(0, Vector3i::zAxis(i), image); +} + +// ... +@endcode -In shader, the texture is used via `sampler1D`, `sampler2D` or `sampler3D` -depending on dimension count. Note that you can have more than one texture bound -to the shader - the only requirement is to have each texture in another layer. +Similar approach can be used for any other texture types (e.g. setting +Texture3D data using 2D layers, Texture2D data using one-dimensional chunks +etc.). @section Texture-rectangle Rectangle textures @@ -124,7 +178,8 @@ template class Texture: public AbstractTexture { * Sets wrapping type for coordinates out of range (0, 1) for normal * textures and (0, textureSizeInGivenDirection-1) for rectangle * textures. If @extension{EXT,direct_state_access} is not available, - * the texture is bound to some layer before the operation. + * the texture is bound to some layer before the operation. Initial + * value is @ref AbstractTexture::Wrapping "Wrapping::Repeat". * @attention For rectangle textures only some modes are supported, * see @ref AbstractTexture::Wrapping "Wrapping" documentation * for more information.