From c54af1b6644216335361e61e770037aca1527756 Mon Sep 17 00:00:00 2001 From: Tavian Barnes Date: Mon, 6 Jul 2009 16:37:44 +0000 Subject: New GL C++ wrapper. --- libdimensionxx/Makefile.am | 2 + libdimensionxx/cameras.cpp | 16 ++++++- libdimensionxx/dimensionxx.hpp | 1 + libdimensionxx/dimensionxx/cameras.hpp | 3 ++ libdimensionxx/dimensionxx/gl.hpp | 64 +++++++++++++++++++++++++++ libdimensionxx/dimensionxx/png.hpp | 2 +- libdimensionxx/gl.cpp | 72 +++++++++++++++++++++++++++++++ libdimensionxx/png.cpp | 2 +- tests/Makefile.am | 6 ++- tests/glxx.cpp | 79 ++++++++++++++++++++++++++++++++++ tests/tests.h | 9 ++++ 11 files changed, 251 insertions(+), 5 deletions(-) create mode 100644 libdimensionxx/dimensionxx/gl.hpp create mode 100644 libdimensionxx/gl.cpp create mode 100644 tests/glxx.cpp diff --git a/libdimensionxx/Makefile.am b/libdimensionxx/Makefile.am index 9c22cd5..75287e0 100644 --- a/libdimensionxx/Makefile.am +++ b/libdimensionxx/Makefile.am @@ -25,6 +25,7 @@ nobase_include_HEADERS = dimensionxx.hpp \ dimensionxx/color.hpp \ dimensionxx/cookie.hpp \ dimensionxx/geometry.hpp \ + dimensionxx/gl.hpp \ dimensionxx/object.hpp \ dimensionxx/objects.hpp \ dimensionxx/png.hpp \ @@ -41,6 +42,7 @@ libdimensionxx_la_SOURCES = $(nobase_include_HEADERS) \ camera.cpp \ cameras.cpp \ color.cpp \ + gl.cpp \ error.cpp \ object.cpp \ objects.cpp \ diff --git a/libdimensionxx/cameras.cpp b/libdimensionxx/cameras.cpp index fb11dcf..a7a8255 100644 --- a/libdimensionxx/cameras.cpp +++ b/libdimensionxx/cameras.cpp @@ -22,7 +22,7 @@ namespace Dimension { - // Create a sphere + // Create a perspective camera Perspective_Camera::Perspective_Camera(const Matrix& trans) : Camera(dmnsn_new_perspective_camera(trans.dmnsn())) { @@ -31,9 +31,21 @@ namespace Dimension } } - // Delete a sphere + // Delete a perspective camera Perspective_Camera::~Perspective_Camera() { dmnsn_delete_perspective_camera(m_camera); } + + Matrix + Perspective_Camera::trans() + { + return Matrix(dmnsn_get_perspective_camera_trans(m_camera)); + } + + void + Perspective_Camera::trans(const Matrix& trans) + { + dmnsn_set_perspective_camera_trans(m_camera, trans.dmnsn()); + } } diff --git a/libdimensionxx/dimensionxx.hpp b/libdimensionxx/dimensionxx.hpp index bc52580..b552dd3 100644 --- a/libdimensionxx/dimensionxx.hpp +++ b/libdimensionxx/dimensionxx.hpp @@ -31,6 +31,7 @@ #include #include #include +#include #include #include #include diff --git a/libdimensionxx/dimensionxx/cameras.hpp b/libdimensionxx/dimensionxx/cameras.hpp index 85105cb..4e67d64 100644 --- a/libdimensionxx/dimensionxx/cameras.hpp +++ b/libdimensionxx/dimensionxx/cameras.hpp @@ -31,6 +31,9 @@ namespace Dimension public: Perspective_Camera(const Matrix& trans); virtual ~Perspective_Camera(); + + Matrix trans(); + void trans(const Matrix& trans); }; } diff --git a/libdimensionxx/dimensionxx/gl.hpp b/libdimensionxx/dimensionxx/gl.hpp new file mode 100644 index 0000000..ef875df --- /dev/null +++ b/libdimensionxx/dimensionxx/gl.hpp @@ -0,0 +1,64 @@ +/************************************************************************* + * Copyright (C) 2008 Tavian Barnes * + * * + * This file is part of The Dimension Library. * + * * + * The Dimension Library is free software; you can redistribute it and/ * + * or modify it under the terms of the GNU Lesser General Public License * + * as published by the Free Software Foundation; either version 3 of the * + * License, or (at your option) any later version. * + * * + * The Dimension Library is distributed in the hope that it will be * + * useful, but WITHOUT ANY WARRANTY; without even the implied warranty * + * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * + * Lesser General Public License for more details. * + * * + * You should have received a copy of the GNU Lesser General Public * + * License along with this program. If not, see * + * . * + *************************************************************************/ + +// C++ wrapper for libdimension GL support + +#ifndef DIMENSIONXX_GL_HPP +#define DIMENSIONXX_GL_HPP + +#include +#include + +namespace Dimension +{ + class GL_Drawer + { + public: + GL_Drawer(Canvas& canvas); + ~GL_Drawer(); + + void draw(); + + private: + // Copying prohibited + GL_Drawer(const GL_Drawer&); + GL_Drawer& operator=(const GL_Drawer&); + + Canvas* m_canvas; + bool m_drawn; + }; + + class GL_Reader + { + public: + // GL_Reader(); + // ~GL_Reader(); + + Canvas read(unsigned int x0, unsigned int y0, + unsigned int width, unsigned int height); + + private: + // Copying prohibited + GL_Reader(const GL_Reader&); + GL_Reader& operator=(const GL_Reader&); + }; +} + +#endif /* DIMENSIONXX_GL_HPP */ diff --git a/libdimensionxx/dimensionxx/png.hpp b/libdimensionxx/dimensionxx/png.hpp index 17cb883..2b99531 100644 --- a/libdimensionxx/dimensionxx/png.hpp +++ b/libdimensionxx/dimensionxx/png.hpp @@ -18,7 +18,7 @@ * . * *************************************************************************/ -// C++ wrapper for libdimension PNG support. PNG_Canvas derives from Canvas. +// C++ wrapper for libdimension PNG support #ifndef DIMENSIONXX_PNG_HPP #define DIMENSIONXX_PNG_HPP diff --git a/libdimensionxx/gl.cpp b/libdimensionxx/gl.cpp new file mode 100644 index 0000000..5c0a7bb --- /dev/null +++ b/libdimensionxx/gl.cpp @@ -0,0 +1,72 @@ +/************************************************************************* + * Copyright (C) 2008 Tavian Barnes * + * * + * This file is part of The Dimension Library. * + * * + * The Dimension Library is free software; you can redistribute it and/ * + * or modify it under the terms of the GNU Lesser General Public License * + * as published by the Free Software Foundation; either version 3 of the * + * License, or (at your option) any later version. * + * * + * The Dimension Library is distributed in the hope that it will be * + * useful, but WITHOUT ANY WARRANTY; without even the implied warranty * + * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * + * Lesser General Public License for more details. * + * * + * You should have received a copy of the GNU Lesser General Public * + * License along with this program. If not, see * + * . * + *************************************************************************/ + +#include "dimensionxx.hpp" +#include + +namespace Dimension +{ + GL_Drawer::GL_Drawer(Canvas& canvas) + : m_canvas(&canvas), m_drawn(false) + { + // Optimize the canvas for GL drawing + dmnsn_gl_optimize_canvas(m_canvas->dmnsn()); + } + + // Draw the canvas if it hasn't been drawn yet + GL_Drawer::~GL_Drawer() + { + if (!m_drawn) { + try { + draw(); + } catch (...) { + dmnsn_error(SEVERITY_MEDIUM, + "Drawing canvas to GL failed in GL_Drawer destructor."); + } + } + } + + // Draw the canvas to the current openGL buffer + void GL_Drawer::draw() + { + // Draw to the GL buffer + if (dmnsn_gl_write_canvas(m_canvas->dmnsn()) != 0) { + // The drawing operation failed + throw Dimension_Error("Drawing canvas to GL failed."); + } + + m_drawn = true; // Don't draw again in destructor + } + + // Read a canvas from a GL buffer + Canvas + GL_Reader::read(unsigned int x0, unsigned int y0, + unsigned int width, unsigned int height) + { + // Read the canvas from the GL buffer + dmnsn_canvas* canvas = dmnsn_gl_read_canvas(x0, y0, width, height); + if (!canvas) { + // The read operation failed + throw Dimension_Error("Reading canvas from GL failed."); + } + + return Canvas(canvas); + } +} diff --git a/libdimensionxx/png.cpp b/libdimensionxx/png.cpp index 1f61e72..5ca8e02 100644 --- a/libdimensionxx/png.cpp +++ b/libdimensionxx/png.cpp @@ -58,7 +58,7 @@ namespace Dimension FILE_Cookie cookie(*m_ostr); // Write the PNG file - if (dmnsn_png_write_canvas(m_canvas->dmnsn(), cookie.file())) { + if (dmnsn_png_write_canvas(m_canvas->dmnsn(), cookie.file()) != 0) { // The actual write operation failed, for some reason throw Dimension_Error("Writing canvas to PNG failed."); } diff --git a/tests/Makefile.am b/tests/Makefile.am index 6d496f6..1f3f58c 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -25,7 +25,8 @@ check_PROGRAMS = warning-test \ pngxx-test \ raytrace-test \ raytracexx-test \ - gl-test + gl-test \ + glxx-test TESTS = $(check_PROGRAMS) XFAIL_TESTS = error-test @@ -59,3 +60,6 @@ raytracexx_test_LDADD = ./libdimensionxx-tests.la gl_test_SOURCES = gl.c gl_test_LDADD = ./libdimension-tests.la + +glxx_test_SOURCES = glxx.cpp +glxx_test_LDADD = ./libdimension-tests.la ./libdimensionxx-tests.la diff --git a/tests/glxx.cpp b/tests/glxx.cpp new file mode 100644 index 0000000..1fc08c4 --- /dev/null +++ b/tests/glxx.cpp @@ -0,0 +1,79 @@ +/************************************************************************* + * Copyright (C) 2008 Tavian Barnes * + * * + * This file is part of The Dimension Test Suite. * + * * + * The Dimension Test Suite is free software; you can redistribute it * + * and/or modify it under the terms of the GNU General Public License as * + * published by the Free Software Foundation; either version 3 of the * + * License, or (at your option) any later version. * + * * + * The Dimension Test Suite is distributed in the hope that it will be * + * useful, but WITHOUT ANY WARRANTY; without even the implied warranty * + * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * + * General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program. If not, see . * + *************************************************************************/ + +#include "tests.h" +#include "testsxx.hpp" +#include +#include + +int +main() { + using namespace Dimension; + + // Set the resilience low for tests + resilience(SEVERITY_LOW); + + // Background color + Color background = sRGB(0.0, 0.1, 0.25); + background.filter(0.1); + + // Canvas + Canvas canvas(768, 480); + + // Camera + Perspective_Camera camera( + Matrix::rotation(Vector(0.0, 1.0, 0.0)) + * Matrix::translation(Vector(0.0, 0.0, -4.0)) + * Matrix::scale( + Vector(static_cast(canvas.width())/canvas.height(), 1.0, 1.0) + ) + ); + + // Scene + Scene scene(background, camera, canvas); + + // Objects in scene + + Sphere sphere; + sphere.trans(inverse(Matrix::scale(Vector(1.25, 1.25, 1.25)))); + scene.push_object(sphere); + + Cube cube; + cube.trans(inverse(Matrix::rotation(Vector(0.75, 0.0, 0.0)))); + scene.push_object(cube); + + Raytracer raytracer(scene); + GL_Drawer drawer(scene.canvas()); + dmnsn_display* display = dmnsn_new_display(scene.canvas().dmnsn()); + + // Render the scene + for (unsigned int i = 0; i < 10; ++i) { + Progress rprogress = raytracer.render_async(); + std::cout << "Raytracing scene: " << rprogress << std::endl; + rprogress.finish(); + + drawer.draw(); + dmnsn_display_frame(display); + + cube.trans(inverse(Matrix::rotation(Vector(0.025, 0.0, 0.0)))*cube.trans()); + camera.trans(Matrix::rotation(Vector(0.0, -0.05, 0.0))*camera.trans()); + } + + return EXIT_SUCCESS; +} diff --git a/tests/tests.h b/tests/tests.h index fcb9ad9..30d4002 100644 --- a/tests/tests.h +++ b/tests/tests.h @@ -22,6 +22,11 @@ #include #include +#ifdef __cplusplus +/* We've been included from a C++ file; mark everything here as extern "C" */ +extern "C" { +#endif + /* * Convenience */ @@ -53,3 +58,7 @@ void dmnsn_display_frame(dmnsn_display *display); /* Print a progress bar of the progress of `progress' */ void progressbar(const char *str, const dmnsn_progress *progress); + +#ifdef __cplusplus +} +#endif -- cgit v1.2.3