Browse Source

python: adapt to Trade::MeshDataXD deprecation.

Right now there's no deprecation logic in place for the Python bindings,
so this is a breaking change. Sorry about that.
pull/9/head
Vladimír Vondruš 6 years ago
parent
commit
a470eae5f1
  1. 26
      doc/python/magnum.trade.rst
  2. 7
      src/python/magnum/meshtools.cpp
  3. 11
      src/python/magnum/primitives.cpp
  4. 138
      src/python/magnum/test/test_primitives.py
  5. 38
      src/python/magnum/test/test_trade.py
  6. 36
      src/python/magnum/trade.cpp

26
doc/python/magnum.trade.rst

@ -95,29 +95,19 @@
.. py:function:: magnum.trade.AbstractImporter.open_file .. py:function:: magnum.trade.AbstractImporter.open_file
:raise RuntimeError: If file opening fails :raise RuntimeError: If file opening fails
.. py:property:: magnum.trade.AbstractImporter.mesh2d_count .. py:property:: magnum.trade.AbstractImporter.mesh_count
:raise RuntimeError: If no file is opened :raise RuntimeError: If no file is opened
.. py:property:: magnum.trade.AbstractImporter.mesh3d_count .. py:function:: magnum.trade.AbstractImporter.mesh_level_count
:raise RuntimeError: If no file is opened :raise RuntimeError: If no file is opened
:raise ValueError: If :p:`id` is negative or not less than `mesh_count`
.. py:function:: magnum.trade.AbstractImporter.mesh2d_for_name .. py:function:: magnum.trade.AbstractImporter.mesh_for_name
:raise RuntimeError: If no file is opened
.. py:function:: magnum.trade.AbstractImporter.mesh3d_for_name
:raise RuntimeError: If no file is opened
.. py:function:: magnum.trade.AbstractImporter.mesh2d_name
:raise RuntimeError: If no file is opened
:raise ValueError: If :p:`id` is negative or not less than `mesh2d_count`
.. py:function:: magnum.trade.AbstractImporter.mesh3d_name
:raise RuntimeError: If no file is opened :raise RuntimeError: If no file is opened
:raise ValueError: If :p:`id` is negative or not less than `mesh3d_count` .. py:function:: magnum.trade.AbstractImporter.mesh_name
.. py:function:: magnum.trade.AbstractImporter.mesh2d
:raise RuntimeError: If no file is opened :raise RuntimeError: If no file is opened
:raise ValueError: If :p:`id` is negative or not less than `mesh2d_count` :raise ValueError: If :p:`id` is negative or not less than `mesh_count`
.. py:function:: magnum.trade.AbstractImporter.mesh3d .. py:function:: magnum.trade.AbstractImporter.mesh
:raise RuntimeError: If no file is opened :raise RuntimeError: If no file is opened
:raise ValueError: If :p:`id` is negative or not less than `mesh3d_count` :raise ValueError: If :p:`id` is negative or not less than `mesh_count`
.. py:property:: magnum.trade.AbstractImporter.image1d_count .. py:property:: magnum.trade.AbstractImporter.image1d_count
:raise RuntimeError: If no file is opened :raise RuntimeError: If no file is opened

7
src/python/magnum/meshtools.cpp

@ -26,8 +26,7 @@
#include <pybind11/pybind11.h> #include <pybind11/pybind11.h>
#include <Magnum/GL/Mesh.h> #include <Magnum/GL/Mesh.h>
#include <Magnum/MeshTools/Compile.h> #include <Magnum/MeshTools/Compile.h>
#include <Magnum/Trade/MeshData2D.h> #include <Magnum/Trade/MeshData.h>
#include <Magnum/Trade/MeshData3D.h>
#include "corrade/EnumOperators.h" #include "corrade/EnumOperators.h"
#include "magnum/bootstrap.h" #include "magnum/bootstrap.h"
@ -52,9 +51,7 @@ void meshtools(py::module& m) {
corrade::enumOperators(compileFlag); corrade::enumOperators(compileFlag);
m m
.def("compile", static_cast<GL::Mesh(*)(const Trade::MeshData2D& data)>(&MeshTools::compile), .def("compile", [](const Trade::MeshData& meshData, MeshTools::CompileFlag flags) {
"Compile 2D mesh data", py::arg("mesh_data"))
.def("compile", [](const Trade::MeshData3D& meshData, MeshTools::CompileFlag flags) {
return MeshTools::compile(meshData, flags); return MeshTools::compile(meshData, flags);
}, "Compile 3D mesh data", py::arg("mesh_data"), py::arg("flags") = MeshTools::CompileFlag{}); }, "Compile 3D mesh data", py::arg("mesh_data"), py::arg("flags") = MeshTools::CompileFlag{});
} }

11
src/python/magnum/primitives.cpp

@ -39,8 +39,7 @@
#include <Magnum/Primitives/Plane.h> #include <Magnum/Primitives/Plane.h>
#include <Magnum/Primitives/Square.h> #include <Magnum/Primitives/Square.h>
#include <Magnum/Primitives/UVSphere.h> #include <Magnum/Primitives/UVSphere.h>
#include <Magnum/Trade/MeshData2D.h> #include <Magnum/Trade/MeshData.h>
#include <Magnum/Trade/MeshData3D.h>
#include "corrade/EnumOperators.h" #include "corrade/EnumOperators.h"
#include "magnum/bootstrap.h" #include "magnum/bootstrap.h"
@ -138,10 +137,10 @@ void primitives(py::module& m) {
.def("icosphere_solid", Primitives::icosphereSolid, py::arg("subdivisions")) .def("icosphere_solid", Primitives::icosphereSolid, py::arg("subdivisions"))
.def("line2d", static_cast<Trade::MeshData2D(*)(const Vector2&, const Vector2&)>(Primitives::line2D), "2D line", py::arg("a"), py::arg("b")) .def("line2d", static_cast<Trade::MeshData(*)(const Vector2&, const Vector2&)>(Primitives::line2D), "2D line", py::arg("a"), py::arg("b"))
.def("line2d", static_cast<Trade::MeshData2D(*)()>(Primitives::line2D), "2D line in an identity transformation") .def("line2d", static_cast<Trade::MeshData(*)()>(Primitives::line2D), "2D line in an identity transformation")
.def("line3d", static_cast<Trade::MeshData3D(*)(const Vector3&, const Vector3&)>(Primitives::line3D), "3D line", py::arg("a"), py::arg("b")) .def("line3d", static_cast<Trade::MeshData(*)(const Vector3&, const Vector3&)>(Primitives::line3D), "3D line", py::arg("a"), py::arg("b"))
.def("line3d", static_cast<Trade::MeshData3D(*)()>(Primitives::line3D), "3D line in an identity transformation") .def("line3d", static_cast<Trade::MeshData(*)()>(Primitives::line3D), "3D line in an identity transformation")
.def("plane_solid", Primitives::planeSolid, "Solid 3D plane", py::arg("texture_coords") = Primitives::PlaneTextureCoords::DontGenerate) .def("plane_solid", Primitives::planeSolid, "Solid 3D plane", py::arg("texture_coords") = Primitives::PlaneTextureCoords::DontGenerate)
.def("plane_wireframe", Primitives::planeWireframe, "Wireframe 3D plane") .def("plane_wireframe", Primitives::planeWireframe, "Wireframe 3D plane")

138
src/python/magnum/test/test_primitives.py

@ -32,253 +32,253 @@ class Axis(unittest.TestCase):
def test_2d(self): def test_2d(self):
a = primitives.axis2d() a = primitives.axis2d()
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
self.assertTrue(a.has_colors()) self.assertEqual(a.attribute_count, 2)
def test_3d(self): def test_3d(self):
a = primitives.axis3d() a = primitives.axis3d()
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
self.assertTrue(a.has_colors()) self.assertEqual(a.attribute_count, 2)
class Capsule(unittest.TestCase): class Capsule(unittest.TestCase):
def test_2d_wireframe(self): def test_2d_wireframe(self):
a = primitives.capsule2d_wireframe(3, 3, 2.0) a = primitives.capsule2d_wireframe(3, 3, 2.0)
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertTrue(a.is_indexed()) self.assertEqual(a.attribute_count, 1)
def test_3d_solid(self): def test_3d_solid(self):
a = primitives.capsule3d_solid(3, 3, 10, 2.0, primitives.CapsuleTextureCoords.GENERATE) a = primitives.capsule3d_solid(3, 3, 10, 2.0, primitives.CapsuleTextureCoords.GENERATE)
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
self.assertTrue(a.has_texture_coords2d()) self.assertEqual(a.attribute_count, 3)
b = primitives.capsule3d_solid(3, 3, 10, 2.0) b = primitives.capsule3d_solid(3, 3, 10, 2.0)
self.assertEqual(b.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(b.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(b.is_indexed()) self.assertTrue(b.is_indexed)
self.assertFalse(b.has_texture_coords2d()) self.assertEqual(b.attribute_count, 2)
def test_3d_wireframe(self): def test_3d_wireframe(self):
a = primitives.capsule3d_wireframe(5, 3, 12, 0.3) a = primitives.capsule3d_wireframe(5, 3, 12, 0.3)
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
class Circle(unittest.TestCase): class Circle(unittest.TestCase):
def test_2d_solid(self): def test_2d_solid(self):
a = primitives.circle2d_solid(5, primitives.CircleTextureCoords.GENERATE) a = primitives.circle2d_solid(5, primitives.CircleTextureCoords.GENERATE)
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_FAN) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_FAN)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_texture_coords2d()) self.assertEqual(a.attribute_count, 2)
b = primitives.circle2d_solid(5) b = primitives.circle2d_solid(5)
self.assertEqual(b.primitive, MeshPrimitive.TRIANGLE_FAN) self.assertEqual(b.primitive, MeshPrimitive.TRIANGLE_FAN)
self.assertFalse(b.is_indexed()) self.assertFalse(b.is_indexed)
self.assertFalse(b.has_texture_coords2d()) self.assertEqual(b.attribute_count, 1)
def test_2d_wireframe(self): def test_2d_wireframe(self):
a = primitives.circle2d_wireframe(5) a = primitives.circle2d_wireframe(5)
self.assertEqual(a.primitive, MeshPrimitive.LINE_LOOP) self.assertEqual(a.primitive, MeshPrimitive.LINE_LOOP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
def test_3d_solid(self): def test_3d_solid(self):
a = primitives.circle3d_solid(5, primitives.CircleTextureCoords.GENERATE) a = primitives.circle3d_solid(5, primitives.CircleTextureCoords.GENERATE)
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_FAN) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_FAN)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_texture_coords2d()) self.assertEqual(a.attribute_count, 3)
b = primitives.circle3d_solid(5) b = primitives.circle3d_solid(5)
self.assertEqual(b.primitive, MeshPrimitive.TRIANGLE_FAN) self.assertEqual(b.primitive, MeshPrimitive.TRIANGLE_FAN)
self.assertFalse(b.is_indexed()) self.assertFalse(b.is_indexed)
self.assertFalse(b.has_texture_coords2d()) self.assertEqual(b.attribute_count, 2)
def test_3d_wireframe(self): def test_3d_wireframe(self):
a = primitives.circle3d_wireframe(5) a = primitives.circle3d_wireframe(5)
self.assertEqual(a.primitive, MeshPrimitive.LINE_LOOP) self.assertEqual(a.primitive, MeshPrimitive.LINE_LOOP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
class Cone(unittest.TestCase): class Cone(unittest.TestCase):
def test_solid(self): def test_solid(self):
a = primitives.cone_solid(5, 7, 7.1, primitives.ConeFlags.GENERATE_TEXTURE_COORDS|primitives.ConeFlags.CAP_END) a = primitives.cone_solid(5, 7, 7.1, primitives.ConeFlags.GENERATE_TEXTURE_COORDS|primitives.ConeFlags.CAP_END)
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
self.assertTrue(a.has_texture_coords2d()) self.assertEqual(a.attribute_count, 3)
b = primitives.cone_solid(5, 7, 7.1) b = primitives.cone_solid(5, 7, 7.1)
self.assertEqual(b.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(b.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(b.is_indexed()) self.assertTrue(b.is_indexed)
self.assertFalse(b.has_texture_coords2d()) self.assertEqual(b.attribute_count, 2)
def test_wireframe(self): def test_wireframe(self):
a = primitives.cone_wireframe(16, 7.1) a = primitives.cone_wireframe(16, 7.1)
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
class Crosshair(unittest.TestCase): class Crosshair(unittest.TestCase):
def test_2d(self): def test_2d(self):
a = primitives.crosshair2d() a = primitives.crosshair2d()
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
def test_3d(self): def test_3d(self):
a = primitives.crosshair3d() a = primitives.crosshair3d()
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
class Cube(unittest.TestCase): class Cube(unittest.TestCase):
def test_solid(self): def test_solid(self):
a = primitives.cube_solid() a = primitives.cube_solid()
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
def test_solid_strip(self): def test_solid_strip(self):
a = primitives.cube_solid_strip() a = primitives.cube_solid_strip()
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
def test_wireframe(self): def test_wireframe(self):
a = primitives.cube_wireframe() a = primitives.cube_wireframe()
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
class Cylinder(unittest.TestCase): class Cylinder(unittest.TestCase):
def test_solid(self): def test_solid(self):
a = primitives.cylinder_solid(7, 12, 0.2, primitives.CylinderFlags.GENERATE_TEXTURE_COORDS|primitives.CylinderFlags.CAP_ENDS) a = primitives.cylinder_solid(7, 12, 0.2, primitives.CylinderFlags.GENERATE_TEXTURE_COORDS|primitives.CylinderFlags.CAP_ENDS)
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
self.assertTrue(a.has_texture_coords2d()) self.assertEqual(a.attribute_count, 3)
b = primitives.cylinder_solid(7, 12, 0.2) b = primitives.cylinder_solid(7, 12, 0.2)
self.assertEqual(b.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(b.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(b.is_indexed()) self.assertTrue(b.is_indexed)
self.assertFalse(b.has_texture_coords2d()) self.assertEqual(b.attribute_count, 2)
def test_wireframe(self): def test_wireframe(self):
a = primitives.cylinder_wireframe(8, 16, 1.1) a = primitives.cylinder_wireframe(8, 16, 1.1)
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
class Gradient(unittest.TestCase): class Gradient(unittest.TestCase):
def test_gradient2d(self): def test_gradient2d(self):
a = primitives.gradient2d((3.1, 2.0), Color3(), (0.2, 1.1), Color4()) a = primitives.gradient2d((3.1, 2.0), Color3(), (0.2, 1.1), Color4())
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_colors()) self.assertEqual(a.attribute_count, 2)
def test_gradient2d_horizontal(self): def test_gradient2d_horizontal(self):
a = primitives.gradient2d_horizontal(Color4(), Color3()) a = primitives.gradient2d_horizontal(Color4(), Color3())
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_colors()) self.assertEqual(a.attribute_count, 2)
def test_gradient2d_vertical(self): def test_gradient2d_vertical(self):
a = primitives.gradient2d_vertical(Color4(), Color3()) a = primitives.gradient2d_vertical(Color4(), Color3())
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_colors()) self.assertEqual(a.attribute_count, 2)
def test_gradient3d(self): def test_gradient3d(self):
a = primitives.gradient3d((3.1, 2.0, 0.1), Color3(), (0.2, 1.1, 1.2), Color4()) a = primitives.gradient3d((3.1, 2.0, 0.1), Color3(), (0.2, 1.1, 1.2), Color4())
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_colors()) self.assertEqual(a.attribute_count, 3)
def test_gradient3d_horizontal(self): def test_gradient3d_horizontal(self):
a = primitives.gradient3d_horizontal(Color4(), Color3()) a = primitives.gradient3d_horizontal(Color4(), Color3())
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_colors()) self.assertEqual(a.attribute_count, 3)
def test_gradient3d_vertical(self): def test_gradient3d_vertical(self):
a = primitives.gradient3d_vertical(Color4(), Color3()) a = primitives.gradient3d_vertical(Color4(), Color3())
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_colors()) self.assertEqual(a.attribute_count, 3)
class Grid(unittest.TestCase): class Grid(unittest.TestCase):
def test_solid(self): def test_solid(self):
a = primitives.grid3d_solid((4, 5)) a = primitives.grid3d_solid((4, 5))
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
def test_wireframe(self): def test_wireframe(self):
a = primitives.grid3d_wireframe((2, 7)) a = primitives.grid3d_wireframe((2, 7))
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
class Icosphere(unittest.TestCase): class Icosphere(unittest.TestCase):
def test(self): def test(self):
a = primitives.icosphere_solid(2) a = primitives.icosphere_solid(2)
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
class Line(unittest.TestCase): class Line(unittest.TestCase):
def test_2d(self): def test_2d(self):
a = primitives.line2d((1.0, 2.0), (7.0, 3.2)) a = primitives.line2d((1.0, 2.0), (7.0, 3.2))
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
def test_2d_identity(self): def test_2d_identity(self):
a = primitives.line2d() a = primitives.line2d()
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
def test_3d(self): def test_3d(self):
a = primitives.line3d((1.0, 2.0, 1.1), (7.0, 3.2, 1.1)) a = primitives.line3d((1.0, 2.0, 1.1), (7.0, 3.2, 1.1))
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
def test_3d_identity(self): def test_3d_identity(self):
a = primitives.line3d() a = primitives.line3d()
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
class Plane(unittest.TestCase): class Plane(unittest.TestCase):
def test_solid(self): def test_solid(self):
a = primitives.plane_solid(primitives.PlaneTextureCoords.GENERATE) a = primitives.plane_solid(primitives.PlaneTextureCoords.GENERATE)
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_texture_coords2d()) self.assertEqual(a.attribute_count, 3)
b = primitives.plane_solid() b = primitives.plane_solid()
self.assertEqual(b.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(b.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(b.is_indexed()) self.assertFalse(b.is_indexed)
self.assertFalse(b.has_texture_coords2d()) self.assertEqual(b.attribute_count, 2)
def test_wireframe(self): def test_wireframe(self):
a = primitives.plane_wireframe() a = primitives.plane_wireframe()
self.assertEqual(a.primitive, MeshPrimitive.LINE_LOOP) self.assertEqual(a.primitive, MeshPrimitive.LINE_LOOP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
class Square(unittest.TestCase): class Square(unittest.TestCase):
def test_solid(self): def test_solid(self):
a = primitives.square_solid(primitives.SquareTextureCoords.GENERATE) a = primitives.square_solid(primitives.SquareTextureCoords.GENERATE)
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
self.assertTrue(a.has_texture_coords2d()) self.assertEqual(a.attribute_count, 2)
b = primitives.square_solid() b = primitives.square_solid()
self.assertEqual(b.primitive, MeshPrimitive.TRIANGLE_STRIP) self.assertEqual(b.primitive, MeshPrimitive.TRIANGLE_STRIP)
self.assertFalse(b.is_indexed()) self.assertFalse(b.is_indexed)
self.assertFalse(b.has_texture_coords2d()) self.assertEqual(b.attribute_count, 1)
def test_wireframe(self): def test_wireframe(self):
a = primitives.square_wireframe() a = primitives.square_wireframe()
self.assertEqual(a.primitive, MeshPrimitive.LINE_LOOP) self.assertEqual(a.primitive, MeshPrimitive.LINE_LOOP)
self.assertFalse(a.is_indexed()) self.assertFalse(a.is_indexed)
class UVSphere(unittest.TestCase): class UVSphere(unittest.TestCase):
def test_solid(self): def test_solid(self):
a = primitives.uv_sphere_solid(3, 7, primitives.UVSphereTextureCoords.GENERATE) a = primitives.uv_sphere_solid(3, 7, primitives.UVSphereTextureCoords.GENERATE)
self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(a.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)
self.assertTrue(a.has_texture_coords2d()) self.assertEqual(a.attribute_count, 3)
b = primitives.uv_sphere_solid(3, 7) b = primitives.uv_sphere_solid(3, 7)
self.assertEqual(b.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(b.primitive, MeshPrimitive.TRIANGLES)
self.assertTrue(b.is_indexed()) self.assertTrue(b.is_indexed)
self.assertFalse(b.has_texture_coords2d()) self.assertEqual(b.attribute_count, 2)
def test_wireframe(self): def test_wireframe(self):
a = primitives.uv_sphere_wireframe(6, 8) a = primitives.uv_sphere_wireframe(6, 8)
self.assertEqual(a.primitive, MeshPrimitive.LINES) self.assertEqual(a.primitive, MeshPrimitive.LINES)
self.assertTrue(a.is_indexed()) self.assertTrue(a.is_indexed)

38
src/python/magnum/test/test_trade.py

@ -94,7 +94,7 @@ class MeshData(unittest.TestCase):
importer = trade.ImporterManager().load_and_instantiate('TinyGltfImporter') importer = trade.ImporterManager().load_and_instantiate('TinyGltfImporter')
importer.open_file(os.path.join(os.path.dirname(__file__), 'mesh.glb')) importer.open_file(os.path.join(os.path.dirname(__file__), 'mesh.glb'))
mesh = importer.mesh3d(0) mesh = importer.mesh(0)
self.assertEqual(mesh.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(mesh.primitive, MeshPrimitive.TRIANGLES)
# TODO: test more, once it's exposed # TODO: test more, once it's exposed
@ -117,24 +117,18 @@ class Importer(unittest.TestCase):
self.assertFalse(importer.is_opened) self.assertFalse(importer.is_opened)
with self.assertRaisesRegex(RuntimeError, "no file opened"): with self.assertRaisesRegex(RuntimeError, "no file opened"):
importer.mesh2d_count importer.mesh_count
with self.assertRaisesRegex(RuntimeError, "no file opened"): with self.assertRaisesRegex(RuntimeError, "no file opened"):
importer.mesh3d_count importer.mesh_level_count(0)
with self.assertRaisesRegex(RuntimeError, "no file opened"): with self.assertRaisesRegex(RuntimeError, "no file opened"):
importer.mesh2d_for_name('') importer.mesh_for_name('')
with self.assertRaisesRegex(RuntimeError, "no file opened"):
importer.mesh3d_for_name('')
with self.assertRaisesRegex(RuntimeError, "no file opened"): with self.assertRaisesRegex(RuntimeError, "no file opened"):
importer.mesh2d_name(0) importer.mesh_name(0)
with self.assertRaisesRegex(RuntimeError, "no file opened"):
importer.mesh3d_name(0)
with self.assertRaisesRegex(RuntimeError, "no file opened"): with self.assertRaisesRegex(RuntimeError, "no file opened"):
importer.mesh2d(0) importer.mesh(0)
with self.assertRaisesRegex(RuntimeError, "no file opened"):
importer.mesh3d(0)
with self.assertRaisesRegex(RuntimeError, "no file opened"): with self.assertRaisesRegex(RuntimeError, "no file opened"):
importer.image1d_count importer.image1d_count
@ -176,14 +170,11 @@ class Importer(unittest.TestCase):
importer.open_file(os.path.join(os.path.dirname(__file__), 'rgb.png')) importer.open_file(os.path.join(os.path.dirname(__file__), 'rgb.png'))
with self.assertRaises(IndexError): with self.assertRaises(IndexError):
importer.mesh2d_name(0) importer.mesh_level_count(0)
with self.assertRaises(IndexError):
importer.mesh3d_name(0)
with self.assertRaises(IndexError): with self.assertRaises(IndexError):
importer.mesh2d(0) importer.mesh_name(0)
with self.assertRaises(IndexError): with self.assertRaises(IndexError):
importer.mesh3d(0) importer.mesh(0)
with self.assertRaises(IndexError): with self.assertRaises(IndexError):
importer.image1d_level_count(0) importer.image1d_level_count(0)
@ -214,15 +205,16 @@ class Importer(unittest.TestCase):
with self.assertRaisesRegex(RuntimeError, "opening data failed"): with self.assertRaisesRegex(RuntimeError, "opening data failed"):
importer.open_data(b'') importer.open_data(b'')
def test_mesh3d(self): def test_mesh(self):
# importer refcounting tested in image2d # importer refcounting tested in image2d
importer = trade.ImporterManager().load_and_instantiate('TinyGltfImporter') importer = trade.ImporterManager().load_and_instantiate('TinyGltfImporter')
importer.open_file(os.path.join(os.path.dirname(__file__), 'mesh.glb')) importer.open_file(os.path.join(os.path.dirname(__file__), 'mesh.glb'))
self.assertEqual(importer.mesh3d_count, 3) self.assertEqual(importer.mesh_count, 3)
self.assertEqual(importer.mesh3d_name(0), 'Non-indexed mesh') self.assertEqual(importer.mesh_level_count(0), 1)
self.assertEqual(importer.mesh3d_for_name('Non-indexed mesh'), 0) self.assertEqual(importer.mesh_name(0), 'Non-indexed mesh')
self.assertEqual(importer.mesh_for_name('Non-indexed mesh'), 0)
mesh = importer.mesh3d(0) mesh = importer.mesh(0)
self.assertEqual(mesh.primitive, MeshPrimitive.TRIANGLES) self.assertEqual(mesh.primitive, MeshPrimitive.TRIANGLES)
def test_image2d(self): def test_image2d(self):

36
src/python/magnum/trade.cpp

@ -29,8 +29,7 @@
#include <Magnum/ImageView.h> #include <Magnum/ImageView.h>
#include <Magnum/Trade/AbstractImporter.h> #include <Magnum/Trade/AbstractImporter.h>
#include <Magnum/Trade/ImageData.h> #include <Magnum/Trade/ImageData.h>
#include <Magnum/Trade/MeshData2D.h> #include <Magnum/Trade/MeshData.h>
#include <Magnum/Trade/MeshData3D.h>
#include "Corrade/Containers/Python.h" #include "Corrade/Containers/Python.h"
#include "Magnum/Python.h" #include "Magnum/Python.h"
@ -137,14 +136,6 @@ template<UnsignedInt dimensions> void imageData(py::class_<Trade::ImageData<dime
}, "View on pixel data"); }, "View on pixel data");
} }
template<class T> void meshData(py::class_<T>& c) {
c
.def_property_readonly("primitive", &T::primitive, "Primitive")
.def("is_indexed", &T::isIndexed, "Whether the mesh is indexed")
.def("has_texture_coords2d", &T::hasTextureCoords2D, "Whether the data contain any 2D texture coordinates")
.def("has_colors", &T::hasColors, "Whether the data contain any vertex colors");
}
/* For some reason having ...Args as the second (and not last) template /* For some reason having ...Args as the second (and not last) template
argument does not work. So I'm listing all variants here ... which are argument does not work. So I'm listing all variants here ... which are
exactly two, in fact. */ exactly two, in fact. */
@ -229,11 +220,12 @@ void trade(py::module& m) {
/* AbstractImporter depends on this */ /* AbstractImporter depends on this */
py::module::import("corrade.pluginmanager"); py::module::import("corrade.pluginmanager");
py::class_<Trade::MeshData2D> meshData2D{m, "MeshData2D", "Two-dimensional mesh data"}; py::class_<Trade::MeshData>{m, "MeshData", "Mesh data"}
py::class_<Trade::MeshData3D> meshData3D{m, "MeshData3D", "Three-dimensional mesh data"}; .def_property_readonly("primitive", &Trade::MeshData::primitive, "Primitive")
meshData(meshData2D); .def_property_readonly("is_indexed", &Trade::MeshData::isIndexed, "Whether the mesh is indexed")
meshData(meshData3D); .def_property_readonly("vertex_count", &Trade::MeshData::vertexCount)
meshData3D.def("has_normals", &Trade::MeshData3D::hasNormals, "Whether the data contain any normals"); .def_property_readonly("index_count", &Trade::MeshData::indexCount)
.def_property_readonly("attribute_count", static_cast<UnsignedInt(Trade::MeshData::*)() const>(&Trade::MeshData::attributeCount));
py::class_<Trade::ImageData1D> imageData1D{m, "ImageData1D", "One-dimensional image data"}; py::class_<Trade::ImageData1D> imageData1D{m, "ImageData1D", "One-dimensional image data"};
py::class_<Trade::ImageData2D> imageData2D{m, "ImageData2D", "Two-dimensional image data"}; py::class_<Trade::ImageData2D> imageData2D{m, "ImageData2D", "Two-dimensional image data"};
@ -270,14 +262,12 @@ void trade(py::module& m) {
.def("close", &Trade::AbstractImporter::close, "Close currently opened file") .def("close", &Trade::AbstractImporter::close, "Close currently opened file")
/** @todo all other data types */ /** @todo all other data types */
.def_property_readonly("mesh2d_count", checkOpened<UnsignedInt, &Trade::AbstractImporter::mesh2DCount>, "Two-dimensional mesh count") .def_property_readonly("mesh_count", checkOpened<UnsignedInt, &Trade::AbstractImporter::meshCount>, "Mesh count")
.def_property_readonly("mesh3d_count", checkOpened<UnsignedInt, &Trade::AbstractImporter::mesh3DCount>, "Three-dimensional mesh count") .def("mesh_level_count", checkOpenedBounds<UnsignedInt, &Trade::AbstractImporter::meshLevelCount, &Trade::AbstractImporter::meshCount>, "Mesh level count", py::arg("id"))
.def("mesh2d_for_name", checkOpened<Int, const std::string&, &Trade::AbstractImporter::mesh2DForName>, "Two-dimensional mesh ID for given name") .def("mesh_for_name", checkOpened<Int, const std::string&, &Trade::AbstractImporter::meshForName>, "Mesh ID for given name")
.def("mesh3d_for_name", checkOpened<Int, const std::string&, &Trade::AbstractImporter::mesh3DForName>, "Three-dimensional mesh ID for given name") .def("mesh_name", checkOpenedBounds<std::string, &Trade::AbstractImporter::meshName, &Trade::AbstractImporter::meshCount>, "Mesh name", py::arg("id"))
.def("mesh2d_name", checkOpenedBounds<std::string, &Trade::AbstractImporter::mesh2DName, &Trade::AbstractImporter::mesh2DCount>, "Two-dimensional mesh name", py::arg("id")) .def("mesh", checkOpenedBoundsResult<Trade::MeshData, &Trade::AbstractImporter::mesh, &Trade::AbstractImporter::meshCount>, "Mesh", py::arg("id"), py::arg("level") = 0)
.def("mesh3d_name", checkOpenedBounds<std::string, &Trade::AbstractImporter::mesh3DName, &Trade::AbstractImporter::mesh3DCount>, "Three-dimensional mesh name", py::arg("id")) /** @todo mesh_attribute_for_name / mesh_attribute_name */
.def("mesh2d", checkOpenedBoundsResult<Trade::MeshData2D, &Trade::AbstractImporter::mesh2D, &Trade::AbstractImporter::mesh2DCount>, "Two-dimensional mesh", py::arg("id"))
.def("mesh3d", checkOpenedBoundsResult<Trade::MeshData3D, &Trade::AbstractImporter::mesh3D, &Trade::AbstractImporter::mesh3DCount>, "Three-dimensional mesh", py::arg("id"))
.def_property_readonly("image1d_count", checkOpened<UnsignedInt, &Trade::AbstractImporter::image1DCount>, "One-dimensional image count") .def_property_readonly("image1d_count", checkOpened<UnsignedInt, &Trade::AbstractImporter::image1DCount>, "One-dimensional image count")
.def_property_readonly("image2d_count", checkOpened<UnsignedInt, &Trade::AbstractImporter::image2DCount>, "Two-dimensional image count") .def_property_readonly("image2d_count", checkOpened<UnsignedInt, &Trade::AbstractImporter::image2DCount>, "Two-dimensional image count")

Loading…
Cancel
Save