Browse Source

MeshTools: simplify compile().

I wanted to do this since *ever*.
pull/255/head
Vladimír Vondruš 8 years ago
parent
commit
424eec4818
  1. 9
      doc/changelog.dox
  2. 3
      doc/snippets/MagnumSceneGraph-gl.cpp
  3. 64
      src/Magnum/MeshTools/Compile.cpp
  4. 56
      src/Magnum/MeshTools/Compile.h

9
doc/changelog.dox

@ -67,6 +67,11 @@ See also:
@ref GL::Buffer to simplify resource management on user side. See @ref GL::Buffer to simplify resource management on user side. See
@ref GL-Mesh-buffer-ownership for more information. @ref GL-Mesh-buffer-ownership for more information.
@subsubsection changelog-latest-changes-meshtools MeshTools library
- @ref MeshTools::compile() API got simplified to make use of the new buffer
ownership feature of @ref GL::Mesh
@subsubsection changelog-latest-changes-platform Platform libraries @subsubsection changelog-latest-changes-platform Platform libraries
- @ref Platform::GlfwApplication now behaves the same as - @ref Platform::GlfwApplication now behaves the same as
@ -97,6 +102,10 @@ See also:
deeply nested, use @ref Math::Distance and @ref Math::Intersection instead deeply nested, use @ref Math::Distance and @ref Math::Intersection instead
- `Math::Geometry::Intersection::boxFrustum()` is deprecated, use - `Math::Geometry::Intersection::boxFrustum()` is deprecated, use
@ref Math::Intersection::rangeFrustum() instead @ref Math::Intersection::rangeFrustum() instead
- @ref MeshTools::compile() taking a @ref GL::BufferUsage and returning a
tuple was deprecated, use the simpler version taking just
@ref Trade::MeshData2D / @ref Trade::MeshData3D and directly returning a
@ref GL::Mesh instead
@section changelog-2018-04 2018.04 @section changelog-2018-04 2018.04

3
doc/snippets/MagnumSceneGraph-gl.cpp

@ -93,7 +93,7 @@ typedef SceneGraph::Scene<SceneGraph::MatrixTransformation3D> Scene3D;
class RedCube: public Object3D, public SceneGraph::Drawable3D { class RedCube: public Object3D, public SceneGraph::Drawable3D {
public: public:
explicit RedCube(Object3D* parent, SceneGraph::DrawableGroup3D* group): Object3D{parent}, SceneGraph::Drawable3D{*this, group} { explicit RedCube(Object3D* parent, SceneGraph::DrawableGroup3D* group): Object3D{parent}, SceneGraph::Drawable3D{*this, group} {
std::tie(_mesh, _vertices, _indices) = MeshTools::compile(Primitives::cubeSolid(), GL::BufferUsage::StaticDraw); _mesh = MeshTools::compile(Primitives::cubeSolid());
} }
private: private:
@ -107,7 +107,6 @@ class RedCube: public Object3D, public SceneGraph::Drawable3D {
} }
GL::Mesh _mesh; GL::Mesh _mesh;
std::unique_ptr<GL::Buffer> _vertices, _indices;
Shaders::Phong _shader; Shaders::Phong _shader;
}; };
/* [Drawable-usage] */ /* [Drawable-usage] */

64
src/Magnum/MeshTools/Compile.cpp

@ -39,7 +39,7 @@
namespace Magnum { namespace MeshTools { namespace Magnum { namespace MeshTools {
std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> compile(const Trade::MeshData2D& meshData, const GL::BufferUsage usage) { GL::Mesh compile(const Trade::MeshData2D& meshData) {
GL::Mesh mesh; GL::Mesh mesh;
mesh.setPrimitive(meshData.primitive()); mesh.setPrimitive(meshData.primitive());
@ -50,13 +50,15 @@ std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> c
stride += sizeof(Shaders::Generic2D::TextureCoordinates::Type); stride += sizeof(Shaders::Generic2D::TextureCoordinates::Type);
/* Create vertex buffer */ /* Create vertex buffer */
std::unique_ptr<GL::Buffer> vertexBuffer{new GL::Buffer{GL::Buffer::TargetHint::Array}}; GL::Buffer vertexBuffer{GL::Buffer::TargetHint::Array};
GL::Buffer vertexBufferRef = GL::Buffer::wrap(vertexBuffer.id());
/* Interleave positions */ /* Interleave positions and put them in with ownership transfer, use the
ref for the rest */
Containers::Array<char> data = MeshTools::interleave( Containers::Array<char> data = MeshTools::interleave(
meshData.positions(0), meshData.positions(0),
stride - sizeof(Shaders::Generic2D::Position::Type)); stride - sizeof(Shaders::Generic2D::Position::Type));
mesh.addVertexBuffer(*vertexBuffer, 0, mesh.addVertexBuffer(std::move(vertexBuffer), 0,
Shaders::Generic2D::Position(), Shaders::Generic2D::Position(),
stride - sizeof(Shaders::Generic2D::Position::Type)); stride - sizeof(Shaders::Generic2D::Position::Type));
@ -66,35 +68,42 @@ std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> c
normalOffset, normalOffset,
meshData.textureCoords2D(0), meshData.textureCoords2D(0),
stride - normalOffset - sizeof(Shaders::Generic2D::TextureCoordinates::Type)); stride - normalOffset - sizeof(Shaders::Generic2D::TextureCoordinates::Type));
mesh.addVertexBuffer(*vertexBuffer, 0, mesh.addVertexBuffer(vertexBufferRef, 0,
normalOffset, normalOffset,
Shaders::Generic2D::TextureCoordinates(), Shaders::Generic2D::TextureCoordinates(),
stride - normalOffset - sizeof(Shaders::Generic2D::TextureCoordinates::Type)); stride - normalOffset - sizeof(Shaders::Generic2D::TextureCoordinates::Type));
} }
/* Fill vertex buffer with interleaved data */ /* Fill vertex buffer with interleaved data */
vertexBuffer->setData(data, usage); vertexBufferRef.setData(data, GL::BufferUsage::StaticDraw);
/* If indexed, fill index buffer and configure indexed mesh */ /* If indexed, fill index buffer and configure indexed mesh */
std::unique_ptr<GL::Buffer> indexBuffer;
if(meshData.isIndexed()) { if(meshData.isIndexed()) {
Containers::Array<char> indexData; Containers::Array<char> indexData;
MeshIndexType indexType; MeshIndexType indexType;
UnsignedInt indexStart, indexEnd; UnsignedInt indexStart, indexEnd;
std::tie(indexData, indexType, indexStart, indexEnd) = MeshTools::compressIndices(meshData.indices()); std::tie(indexData, indexType, indexStart, indexEnd) = MeshTools::compressIndices(meshData.indices());
indexBuffer.reset(new GL::Buffer{GL::Buffer::TargetHint::ElementArray}); GL::Buffer indexBuffer{GL::Buffer::TargetHint::ElementArray};
indexBuffer->setData(indexData, usage); indexBuffer.setData(indexData, GL::BufferUsage::StaticDraw);
mesh.setCount(meshData.indices().size()) mesh.setCount(meshData.indices().size())
.setIndexBuffer(*indexBuffer, 0, indexType, indexStart, indexEnd); .setIndexBuffer(std::move(indexBuffer), 0, indexType, indexStart, indexEnd);
/* Else set vertex count */ /* Else set vertex count */
} else mesh.setCount(meshData.positions(0).size()); } else mesh.setCount(meshData.positions(0).size());
return std::make_tuple(std::move(mesh), std::move(vertexBuffer), std::move(indexBuffer)); return mesh;
} }
std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> compile(const Trade::MeshData3D& meshData, const GL::BufferUsage usage) { #ifdef MAGNUM_BUILD_DEPRECATED
std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> compile(const Trade::MeshData2D& meshData, GL::BufferUsage) {
return std::make_tuple(compile(meshData),
std::unique_ptr<GL::Buffer>{new GL::Buffer{NoCreate}},
std::unique_ptr<GL::Buffer>{meshData.isIndexed() ? new GL::Buffer{NoCreate} : nullptr});
}
#endif
GL::Mesh compile(const Trade::MeshData3D& meshData) {
GL::Mesh mesh; GL::Mesh mesh;
mesh.setPrimitive(meshData.primitive()); mesh.setPrimitive(meshData.primitive());
@ -110,13 +119,15 @@ std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> c
stride += sizeof(Shaders::Generic3D::TextureCoordinates::Type); stride += sizeof(Shaders::Generic3D::TextureCoordinates::Type);
/* Create vertex buffer */ /* Create vertex buffer */
std::unique_ptr<GL::Buffer> vertexBuffer{new GL::Buffer{GL::Buffer::TargetHint::Array}}; GL::Buffer vertexBuffer{GL::Buffer::TargetHint::Array};
GL::Buffer vertexBufferRef = GL::Buffer::wrap(vertexBuffer.id());
/* Interleave positions */ /* Interleave positions and put them in with ownership transfer, use the
ref for the rest */
Containers::Array<char> data = MeshTools::interleave( Containers::Array<char> data = MeshTools::interleave(
meshData.positions(0), meshData.positions(0),
stride - sizeof(Shaders::Generic3D::Position::Type)); stride - sizeof(Shaders::Generic3D::Position::Type));
mesh.addVertexBuffer(*vertexBuffer, 0, mesh.addVertexBuffer(std::move(vertexBuffer), 0,
Shaders::Generic3D::Position(), Shaders::Generic3D::Position(),
stride - sizeof(Shaders::Generic3D::Position::Type)); stride - sizeof(Shaders::Generic3D::Position::Type));
@ -126,7 +137,7 @@ std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> c
normalOffset, normalOffset,
meshData.normals(0), meshData.normals(0),
stride - normalOffset - sizeof(Shaders::Generic3D::Normal::Type)); stride - normalOffset - sizeof(Shaders::Generic3D::Normal::Type));
mesh.addVertexBuffer(*vertexBuffer, 0, mesh.addVertexBuffer(vertexBufferRef, 0,
normalOffset, normalOffset,
Shaders::Generic3D::Normal(), Shaders::Generic3D::Normal(),
stride - normalOffset - sizeof(Shaders::Generic3D::Normal::Type)); stride - normalOffset - sizeof(Shaders::Generic3D::Normal::Type));
@ -138,32 +149,39 @@ std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> c
textureCoordsOffset, textureCoordsOffset,
meshData.textureCoords2D(0), meshData.textureCoords2D(0),
stride - textureCoordsOffset - sizeof(Shaders::Generic3D::TextureCoordinates::Type)); stride - textureCoordsOffset - sizeof(Shaders::Generic3D::TextureCoordinates::Type));
mesh.addVertexBuffer(*vertexBuffer, 0, mesh.addVertexBuffer(vertexBufferRef, 0,
textureCoordsOffset, textureCoordsOffset,
Shaders::Generic3D::TextureCoordinates(), Shaders::Generic3D::TextureCoordinates(),
stride - textureCoordsOffset - sizeof(Shaders::Generic3D::TextureCoordinates::Type)); stride - textureCoordsOffset - sizeof(Shaders::Generic3D::TextureCoordinates::Type));
} }
/* Fill vertex buffer with interleaved data */ /* Fill vertex buffer with interleaved data */
vertexBuffer->setData(data, usage); vertexBufferRef.setData(data, GL::BufferUsage::StaticDraw);
/* If indexed, fill index buffer and configure indexed mesh */ /* If indexed, fill index buffer and configure indexed mesh */
std::unique_ptr<GL::Buffer> indexBuffer;
if(meshData.isIndexed()) { if(meshData.isIndexed()) {
Containers::Array<char> indexData; Containers::Array<char> indexData;
MeshIndexType indexType; MeshIndexType indexType;
UnsignedInt indexStart, indexEnd; UnsignedInt indexStart, indexEnd;
std::tie(indexData, indexType, indexStart, indexEnd) = MeshTools::compressIndices(meshData.indices()); std::tie(indexData, indexType, indexStart, indexEnd) = MeshTools::compressIndices(meshData.indices());
indexBuffer.reset(new GL::Buffer{GL::Buffer::TargetHint::ElementArray}); GL::Buffer indexBuffer{GL::Buffer::TargetHint::ElementArray};
indexBuffer->setData(indexData, usage); indexBuffer.setData(indexData, GL::BufferUsage::StaticDraw);
mesh.setCount(meshData.indices().size()) mesh.setCount(meshData.indices().size())
.setIndexBuffer(*indexBuffer, 0, indexType, indexStart, indexEnd); .setIndexBuffer(std::move(indexBuffer), 0, indexType, indexStart, indexEnd);
/* Else set vertex count */ /* Else set vertex count */
} else mesh.setCount(meshData.positions(0).size()); } else mesh.setCount(meshData.positions(0).size());
return std::make_tuple(std::move(mesh), std::move(vertexBuffer), std::move(indexBuffer)); return mesh;
}
#ifdef MAGNUM_BUILD_DEPRECATED
std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> compile(const Trade::MeshData3D& meshData, GL::BufferUsage) {
return std::make_tuple(compile(meshData),
std::unique_ptr<GL::Buffer>{new GL::Buffer{NoCreate}},
std::unique_ptr<GL::Buffer>{meshData.isIndexed() ? new GL::Buffer{NoCreate} : nullptr});
} }
#endif
}} }}

56
src/Magnum/MeshTools/Compile.h

@ -32,30 +32,33 @@
#include "Magnum/configure.h" #include "Magnum/configure.h"
#ifdef MAGNUM_TARGET_GL #ifdef MAGNUM_TARGET_GL
#include <tuple>
#include <memory>
#include "Magnum/GL/GL.h" #include "Magnum/GL/GL.h"
#include "Magnum/Trade/Trade.h" #include "Magnum/Trade/Trade.h"
#include "Magnum/MeshTools/visibility.h" #include "Magnum/MeshTools/visibility.h"
#ifdef MAGNUM_BUILD_DEPRECATED
#include <tuple>
#include <memory>
#include <Corrade/Utility/Macros.h>
#endif
namespace Magnum { namespace MeshTools { namespace Magnum { namespace MeshTools {
/** /**
@brief Compile 2D mesh data @brief Compile 2D mesh data
Configures mesh for @ref Shaders::Generic2D shader with vertex buffer and Configures a mesh for @ref Shaders::Generic2D shader with vertex buffer and
possibly also index buffer, if the mesh is indexed. Positions are bound to possibly also an index buffer, if the mesh is indexed. Positions are bound to
@ref Shaders::Generic2D::Position attribute. If the mesh contains texture @ref Shaders::Generic2D::Position attribute. If the mesh contains texture
coordinates, they are bound to @ref Shaders::Generic2D::TextureCoordinates coordinates, these are bound to @ref Shaders::Generic2D::TextureCoordinates
attribute. No data compression or index optimization (except for index buffer attribute. No data compression or index optimization (except for index buffer
packing) is done. The @p usage parameter is used for both vertex and index packing) is done, both the vertex buffer and the index buffer (if any) is owned
buffer. by the mesh, both created with @ref GL::BufferUsage::StaticDraw.
The second returned buffer may be @cpp nullptr @ce if the mesh is not indexed.
This is just a convenience function for creating generic meshes, you might want This is just a convenience function for creating generic meshes, you might want
to use @ref interleave() and @ref compressIndices() functions instead for to use @ref interleave() and @ref compressIndices() functions together with
@ref GL::Mesh::setPrimitive(), @ref GL::Mesh::setCount(),
@ref GL::Mesh::addVertexBuffer(), @ref GL::Mesh::setIndexBuffer() instead for
greater flexibility. greater flexibility.
@note This function is available only if Magnum is compiled with @note This function is available only if Magnum is compiled with
@ -64,7 +67,15 @@ greater flexibility.
@see @ref shaders-generic @see @ref shaders-generic
*/ */
MAGNUM_MESHTOOLS_EXPORT std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> compile(const Trade::MeshData2D& meshData, GL::BufferUsage usage); MAGNUM_MESHTOOLS_EXPORT GL::Mesh compile(const Trade::MeshData2D& meshData);
#ifdef MAGNUM_BUILD_DEPRECATED
/** @brief @copybrief compile(const Trade::MeshData2D&)
* @deprecated Use @ref compile(const Trade::MeshData2D&) instead. The @p usage
* parameter is ignored and returned buffer instances are empty.
*/
CORRADE_DEPRECATED("use compile(const Trade::MeshData2D&) instead") MAGNUM_MESHTOOLS_EXPORT std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> compile(const Trade::MeshData2D& meshData, GL::BufferUsage usage);
#endif
/** /**
@brief Compile 3D mesh data @brief Compile 3D mesh data
@ -74,13 +85,14 @@ possibly also index buffer, if the mesh is indexed. Positions are bound to
@ref Shaders::Generic3D::Position attribute. If the mesh contains normals, they @ref Shaders::Generic3D::Position attribute. If the mesh contains normals, they
are bound to @ref Shaders::Generic3D::Normal attribute, texture coordinates are are bound to @ref Shaders::Generic3D::Normal attribute, texture coordinates are
bound to @ref Shaders::Generic2D::TextureCoordinates attribute. No data bound to @ref Shaders::Generic2D::TextureCoordinates attribute. No data
compression or index optimization (except for index buffer packing) is done. compression or index optimization (except for index buffer packing) is done,
The @p usage parameter is used for both vertex and index buffer. both the vertex buffer and the index buffer (if any) is owned by the mesh, both
created with @ref GL::BufferUsage::StaticDraw.
The second returned buffer may be @cpp nullptr @ce if the mesh is not indexed.
This is just a convenience function for creating generic meshes, you might want This is just a convenience function for creating generic meshes, you might want
to use @ref interleave() and @ref compressIndices() functions instead for to use @ref interleave() and @ref compressIndices() functions together with
@ref GL::Mesh::setPrimitive(), @ref GL::Mesh::setCount(),
@ref GL::Mesh::addVertexBuffer(), @ref GL::Mesh::setIndexBuffer() instead for
greater flexibility. greater flexibility.
@note This function is available only if Magnum is compiled with @note This function is available only if Magnum is compiled with
@ -89,7 +101,15 @@ greater flexibility.
@see @ref shaders-generic @see @ref shaders-generic
*/ */
MAGNUM_MESHTOOLS_EXPORT std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> compile(const Trade::MeshData3D& meshData, GL::BufferUsage usage); MAGNUM_MESHTOOLS_EXPORT GL::Mesh compile(const Trade::MeshData3D& meshData);
#ifdef MAGNUM_BUILD_DEPRECATED
/** @brief @copybrief compile(const Trade::MeshData3D&)
* @deprecated Use @ref compile(const Trade::MeshData3D&) instead. The @p usage
* parameter is ignored and returned buffer instances are empty.
*/
CORRADE_DEPRECATED("use compile(const Trade::MeshData3D&) instead") MAGNUM_MESHTOOLS_EXPORT std::tuple<GL::Mesh, std::unique_ptr<GL::Buffer>, std::unique_ptr<GL::Buffer>> compile(const Trade::MeshData3D& meshData, GL::BufferUsage usage);
#endif
}} }}
#else #else

Loading…
Cancel
Save