diff --git a/openscad.pro b/openscad.pro index 6b32afc..b663a62 100644 --- a/openscad.pro +++ b/openscad.pro @@ -247,6 +247,8 @@ HEADERS += src/typedefs.h \ src/ThrownTogetherRenderer.h \ src/CGAL_OGL_Polyhedron.h \ src/OGL_helper.h \ + src/hidapi.h \ + src/SpaceNav.h \ src/QGLView.h \ src/GLView.h \ src/MainWindow.h \ @@ -404,6 +406,8 @@ SOURCES += src/version_check.cc \ src/OpenCSGWarningDialog.cc \ src/editor.cc \ src/GLView.cc \ + src/hid.c \ + src/SpaceNav.cc \ src/QGLView.cc \ src/AutoUpdater.cc \ \ diff --git a/src/MainWindow.h b/src/MainWindow.h index 5e1e023..c748ab7 100644 --- a/src/MainWindow.h +++ b/src/MainWindow.h @@ -257,6 +257,11 @@ public slots: void showFontCacheDialog(); void hideFontCacheDialog(); +private slots: + void SpaceNav_translate( int x, int y, int z); + void SpaceNav_rotate( int x, int y, int z); + void SpaceNav_button( int bitmask); + private: static void report_func(const class AbstractNode*, void *vp, int mark); static bool mdiMode; diff --git a/src/mainwin.cc b/src/mainwin.cc index 5735622..bf86f76 100644 --- a/src/mainwin.cc +++ b/src/mainwin.cc @@ -66,6 +66,7 @@ #ifdef OPENSCAD_UPDATER #include "AutoUpdater.h" #endif +#include "SpaceNav.h" #include #include @@ -582,6 +583,11 @@ MainWindow::MainWindow(const QString &filename) setAcceptDrops(true); clearCurrentOutput(); + connect( &spacenav, SIGNAL( translate( int, int, int)), + this, SLOT( SpaceNav_translate( int, int, int))); + connect( &spacenav, SIGNAL( rotate( int, int, int)), + this, SLOT( SpaceNav_rotate( int, int, int))); + connect( &spacenav, SIGNAL( button( int)), this, SLOT( SpaceNav_button( int))); } void MainWindow::initActionIcon(QAction *action, const char *darkResource, const char *lightResource) @@ -2746,3 +2752,85 @@ void MainWindow::hideFontCacheDialog() assert(MainWindow::fontCacheDialog); MainWindow::fontCacheDialog->reset(); } + + + +void +MainWindow::SpaceNav_translate( int x, int y, int z) { + if (x == 0 && y == 0 && z == 0) { + return; + } + std::cout << "SpaceNav_translate: x=" << x << " y=" << y << " z=" << z << std::endl; + qglview->cam.zoom( y * 0.1); + double mx = x * 0.0001 * qglview->cam.zoomValue(); + double my = 0.0; + double mz = -z * 0.0001 * qglview->cam.zoomValue(); + Matrix3d aax, aay, aaz, tm3; + aax = Eigen::AngleAxisd( -(qglview->cam.object_rot.x() / 180) * M_PI, Vector3d::UnitX()); + aay = Eigen::AngleAxisd( -(qglview->cam.object_rot.y() / 180) * M_PI, Vector3d::UnitY()); + aaz = Eigen::AngleAxisd( -(qglview->cam.object_rot.z() / 180) * M_PI, Vector3d::UnitZ()); + tm3 = Matrix3d::Identity(); + tm3 = aaz * (aay * (aax * tm3)); + Matrix4d tm; + tm = Matrix4d::Identity(); + for (int i = 0; i < 3; ++i) { + for (int j = 0; j < 3; ++j) { + tm( j, i) = tm3( j, i); + } + } + Matrix4d vec; + vec << + 0, 0, 0, mx, + 0, 0, 0, my, + 0, 0, 0, mz, + 0, 0, 0, 1 + ; + tm = tm * vec; + qglview->cam.object_trans.x() += tm( 0, 3); + qglview->cam.object_trans.y() += tm( 1, 3); + qglview->cam.object_trans.z() += tm( 2, 3); + qglview->updateGL(); + +} + + +static void +normalizeAngle( GLdouble& angle) { + while (angle < 0) { + angle += 360; + } + while (angle > 360) { + angle -= 360; + } +} + + +void +MainWindow::SpaceNav_rotate( int x, int y, int z) { + if (x == 0 && y == 0 && z == 0) { + return; + } + std::cout << "SpaceNav_rotate x=" << x << " y=" << y << " z=" << z << std::endl; + qglview->cam.object_rot.x() += x * 0.01; + qglview->cam.object_rot.y() += y * -0.01; + qglview->cam.object_rot.z() += z * -0.01; + normalizeAngle( qglview->cam.object_rot.x()); + normalizeAngle( qglview->cam.object_rot.y()); + normalizeAngle( qglview->cam.object_rot.z()); + qglview->updateGL(); +} + + +void +MainWindow::SpaceNav_button( int bitmask) { + std::cout << "SpaceNav_button bitmask=" << bitmask << std::endl; + if ((bitmask & 1) != 0) { + viewCenter(); + } + if ((bitmask & 2) != 0) { +// viewAll(); + viewResetView(); + } +} + + diff --git a/src/openscad.cc b/src/openscad.cc index 80c5b9e..d589ded 100644 --- a/src/openscad.cc +++ b/src/openscad.cc @@ -42,6 +42,7 @@ #include "stackcheck.h" #include "CocoaUtils.h" #include "FontCache.h" +#include "SpaceNav.h" #include #include @@ -743,6 +744,7 @@ int gui(vector &inputFiles, const fs::path &original_path, int argc, cha } app.connect(&app, SIGNAL(lastWindowClosed()), &app, SLOT(quit())); + spacenav(); int rc = app.exec(); QSet *windows = MainWindow::getWindows(); foreach (MainWindow *mainw, *windows) {