def __init__(self): configuration = self.Configuration() configuration.title = "Magnum Python Primitives + SceneGraph Example" platform.Application.__init__(self, configuration) gl.Renderer.enable(gl.Renderer.Feature.DEPTH_TEST) gl.Renderer.enable(gl.Renderer.Feature.FACE_CULLING) # Scene and drawables self._scene = Scene3D() self._drawables = scenegraph.DrawableGroup3D() # Camera setup camera_object = Object3D(self._scene) camera_object.translate(Vector3.z_axis(10.0)) self._camera = scenegraph.Camera3D(camera_object) self._camera.projection_matrix = Matrix4.perspective_projection( fov=Deg(35.0), aspect_ratio=1.33333, near=0.01, far=100.0) # Cube object and drawable self._cube = Object3D(self._scene) self._cube.rotate_y(Deg(40.0)) self._cube.rotate_x(Deg(30.0)) self._cube_drawable = CubeDrawable( self._cube, self._drawables, meshtools.compile(primitives.cube_solid()), shaders.Phong(), Color3.from_hsv(Deg(35.0), 1.0, 1.0))
def test_camera(self): object = Object3D() object.translate(Vector3.z_axis(5.0)) object_refcount = sys.getrefcount(object) a = scenegraph.Camera3D(object) a.viewport = (400, 300) a.projection_matrix = Matrix4.perspective_projection(fov=Deg(45.0), near=0.01, far=100.0, aspect_ratio=1.0) a.aspect_ratio_policy = scenegraph.AspectRatioPolicy.EXTEND a_refcount = sys.getrefcount(a) self.assertEqual(a.viewport, Vector2i(400, 300)) self.assertEqual( a.projection_matrix, Matrix4.perspective_projection(fov=Deg(57.82240), near=0.01, far=100.0, aspect_ratio=1.33333333)) self.assertEqual(a.camera_matrix, Matrix4.translation(-Vector3.z_axis(5.0))) self.assertEqual(a.aspect_ratio_policy, scenegraph.AspectRatioPolicy.EXTEND) self.assertIs(a.object, object) # Camera should be referenced by the object, but not cyclically self.assertEqual(sys.getrefcount(object), object_refcount) self.assertEqual(sys.getrefcount(a), object_refcount + 1) # Delete the object. The camera should be still alive, but disconnected # from the object (and thus useless). del object self.assertIsNone(a.object) self.assertEqual(sys.getrefcount(a), a_refcount - 1)
def test_camera_draw(self): scene = Scene3D() drawables = scenegraph.DrawableGroup3D() camera_object = Object3D(scene) camera_object.translate((0.0, 1.0, 5.0)) camera = scenegraph.Camera3D(camera_object) rendered = None, None deleted = "no :)" class MyDrawable(scenegraph.Drawable3D): def draw(self, transformation_matrix: Matrix4, camera: scenegraph.Camera3D): nonlocal rendered rendered = (transformation_matrix, camera) def __del__(self): nonlocal deleted deleted = "yes :(" class MySilentDrawable(scenegraph.Drawable3D): def draw(self, transformation_matrix: Matrix4, camera: scenegraph.Camera3D): pass object = Object3D(scene) object.translate(Vector3.x_axis(5.0)) a = MyDrawable(object, drawables) b = MySilentDrawable(object, drawables) # The drawable group should have these listed self.assertEqual([i for i in drawables], [a, b]) # Deleting the object, the camera holder and drawable does nothing del camera_object, object, a, b camera.draw(drawables) self.assertEqual( rendered[0], Matrix4.translation(Vector3.x_axis(5.0)) @ Matrix4.translation( (0.0, -1.0, -5.0))) self.assertIs(rendered[1], camera) # Deleting the scene will delete A and the drawable as well del scene self.assertEqual(deleted, "yes :(") self.assertIsNone(camera.object) self.assertIs(len(drawables), 0)
def __init__(self): configuration = self.Configuration() configuration.title = "Magnum Python Viewer Example" Application.__init__(self, configuration) gl.Renderer.enable(gl.Renderer.Feature.DEPTH_TEST) gl.Renderer.enable(gl.Renderer.Feature.FACE_CULLING) # Scene and drawables self._scene = Scene3D() self._drawables = scenegraph.DrawableGroup3D() # Every scene needs a camera camera_object = Object3D(parent=self._scene) camera_object.translate(Vector3.z_axis(5.0)) self._camera = scenegraph.Camera3D(camera_object) self._camera.aspect_ratio_policy = scenegraph.AspectRatioPolicy.EXTEND self._camera.projection_matrix = Matrix4.perspective_projection( fov=Deg(35.0), aspect_ratio=1.0, near=0.01, far=100.0) self._camera.viewport = self.framebuffer_size # Base object, parent of all (for easy manipulation) self._manipulator = Object3D(parent=self._scene) # Setup renderer and shader defaults gl.Renderer.enable(gl.Renderer.Feature.DEPTH_TEST) gl.Renderer.enable(gl.Renderer.Feature.FACE_CULLING) colored_shader = shaders.Phong() colored_shader.ambient_color = Color3(0.06667) colored_shader.shininess = 80.0 # Import Suzanne head and eyes (yes, sorry, it's all hardcoded here) importer = trade.ImporterManager().load_and_instantiate( 'TinyGltfImporter') importer.open_file( os.path.join(os.path.dirname(__file__), '../viewer/scene.glb')) suzanne_object = Object3D(parent=self._manipulator) suzanne_mesh = meshtools.compile( importer.mesh(importer.mesh_for_name('Suzanne'))) suzanne_eyes_mesh = meshtools.compile( importer.mesh(importer.mesh_for_name('Eyes'))) self._suzanne = ColoredDrawable(suzanne_object, self._drawables, suzanne_mesh, colored_shader, Color3(0.15, 0.49, 1.0)) self._suzanne_eyes = ColoredDrawable(suzanne_object, self._drawables, suzanne_eyes_mesh, colored_shader, Color3(0.95)) self._previous_mouse_position = Vector2i()