From 891b6a8a34735ec2703c519e5ade32f54dad60a0 Mon Sep 17 00:00:00 2001 From: Lukas Matena Date: Mon, 10 Sep 2018 12:08:57 +0200 Subject: [PATCH] First experiments with sla supports ui --- lib/Slic3r/GUI/Plater.pm | 1 + .../Eigen/src/SparseLU/SparseLU_panel_bmod.h | 2 +- xs/src/libslic3r/Model.hpp | 2 + xs/src/slic3r/GUI/GLCanvas3D.cpp | 105 +++++++++++++++++- xs/src/slic3r/GUI/GLCanvas3D.hpp | 1 + 5 files changed, 109 insertions(+), 2 deletions(-) diff --git a/lib/Slic3r/GUI/Plater.pm b/lib/Slic3r/GUI/Plater.pm index 016c2e800..4bc5a8d3a 100644 --- a/lib/Slic3r/GUI/Plater.pm +++ b/lib/Slic3r/GUI/Plater.pm @@ -32,6 +32,7 @@ use constant TB_SPLIT => &Wx::NewId; use constant TB_CUT => &Wx::NewId; use constant TB_SETTINGS => &Wx::NewId; use constant TB_LAYER_EDITING => &Wx::NewId; +use constant TB_SLA_SUPPORTS => &Wx::NewId; use Wx::Locale gettext => 'L'; diff --git a/xs/src/eigen/Eigen/src/SparseLU/SparseLU_panel_bmod.h b/xs/src/eigen/Eigen/src/SparseLU/SparseLU_panel_bmod.h index 822cf32c3..6f1ae0037 100644 --- a/xs/src/eigen/Eigen/src/SparseLU/SparseLU_panel_bmod.h +++ b/xs/src/eigen/Eigen/src/SparseLU/SparseLU_panel_bmod.h @@ -146,7 +146,7 @@ void SparseLUImpl::panel_bmod(const Index m, const Index w, Index ldl = internal::first_multiple(nrow, PacketSize); Index offset = (PacketSize-internal::first_default_aligned(B.data(), PacketSize)) % PacketSize; - MappedMatrixBlock L(tempv.data()+w*ldu+offset, nrow, u_cols, OuterStride<>(ldl)); + auto L = MappedMatrixBlock(tempv.data()+w*ldu+offset, nrow, u_cols, OuterStride<>(ldl)); L.setZero(); internal::sparselu_gemm(L.rows(), L.cols(), B.cols(), B.data(), B.outerStride(), U.data(), U.outerStride(), L.data(), L.outerStride()); diff --git a/xs/src/libslic3r/Model.hpp b/xs/src/libslic3r/Model.hpp index 8a8af481c..8aacdc005 100644 --- a/xs/src/libslic3r/Model.hpp +++ b/xs/src/libslic3r/Model.hpp @@ -79,6 +79,8 @@ public: // Only if the user really modified the layer height, layer_height_profile_valid is set // and used subsequently by the PrintObject. bool layer_height_profile_valid; + + std::vector sla_support_points; /* This vector accumulates the total translation applied to the object by the center_around_origin() method. Callers might want to apply the same translation diff --git a/xs/src/slic3r/GUI/GLCanvas3D.cpp b/xs/src/slic3r/GUI/GLCanvas3D.cpp index edc5bc78e..b4d1c4541 100644 --- a/xs/src/slic3r/GUI/GLCanvas3D.cpp +++ b/xs/src/slic3r/GUI/GLCanvas3D.cpp @@ -13,6 +13,8 @@ #include "../../libslic3r/GCode/PreviewData.hpp" #include +#include +#include #include #include @@ -2388,6 +2390,9 @@ void GLCanvas3D::render() _render_axes(false); } _render_objects(); + + _render_sla_support_points(); + if (!is_custom_bed) // textured bed needs to be rendered after objects { _render_axes(true); @@ -3077,7 +3082,50 @@ void GLCanvas3D::on_mouse(wxMouseEvent& evt) { // The mouse_to_3d gets the Z coordinate from the Z buffer at the screen coordinate pos x, y, // an converts the screen space coordinate to unscaled object space. + Vec3d pos3d = (volume_idx == -1) ? Vec3d(DBL_MAX, DBL_MAX, DBL_MAX) : _mouse_to_3d(pos); + + //@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ + int id = _get_first_selected_object_id(); + if ((id != -1) && (m_model != nullptr)) + { + ModelObject* model_object = m_model->objects[id]; + stl_file stl = model_object->mesh().stl; + + Eigen::MatrixXf V; // vertices + Eigen::MatrixXi F;// facets indices + V.resize(3*stl.stats.number_of_facets, 3); + F.resize(stl.stats.number_of_facets, 3); + for (unsigned int i=0; ivertex[0](0); V(3*i+0, 1) = facet->vertex[0](1); V(3*i+0, 2) = facet->vertex[0](2); + V(3*i+1, 0) = facet->vertex[1](0); V(3*i+1, 1) = facet->vertex[1](1); V(3*i+1, 2) = facet->vertex[1](2); + V(3*i+2, 0) = facet->vertex[2](0); V(3*i+2, 1) = facet->vertex[2](1); V(3*i+2, 2) = facet->vertex[2](2); + F(i, 0) = 3*i+0; + F(i, 1) = 3*i+1; + F(i, 2) = 3*i+2; + } + + Eigen::Matrix viewport; + ::glGetIntegerv(GL_VIEWPORT, viewport.data()); + Eigen::Matrix modelview_matrix; + ::glGetDoublev(GL_MODELVIEW_MATRIX, modelview_matrix.data()); + Eigen::Matrix projection_matrix; + ::glGetDoublev(GL_PROJECTION_MATRIX, projection_matrix.data()); + + int fid = 0; + Vec3f bc(0, 0, 0); + + if (igl::unproject_onto_mesh(Vec2f(pos(0), viewport(3)-pos(1)), modelview_matrix.cast(), projection_matrix.cast(), viewport.cast(), V, F, fid, bc) + && (stl.facet_start + fid)->normal(2) < 0.f) { + const Vec3f& a = (stl.facet_start+fid)->vertex[0]; + const Vec3f& b = (stl.facet_start+fid)->vertex[1]; + const Vec3f& c = (stl.facet_start+fid)->vertex[2]; + model_object->sla_support_points.emplace_back(bc(0)*a + bc(1)*b + bc(2)*c); + } + } + //@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ + // Only accept the initial position, if it is inside the volume bounding box. BoundingBoxf3 volume_bbox = m_volumes.volumes[volume_idx]->transformed_bounding_box(); @@ -4018,13 +4066,68 @@ void GLCanvas3D::_render_legend_texture() const m_legend_texture.render(*this); } -void GLCanvas3D::_render_layer_editing_overlay() const + + + + +//@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ +void GLCanvas3D::_render_sla_support_points() const { if (m_print == nullptr) return; GLVolume* volume = nullptr; + for (GLVolume* vol : m_volumes.volumes) { + if ((vol != nullptr) && vol->selected) { + volume = vol; + break; + } + } + + if (volume == nullptr) + return; + + // If the active object was not allocated at the Print, go away.This should only be a momentary case between an object addition / deletion + // and an update by Platter::async_apply_config. + int object_idx = int(volume->select_group_id / 1000000); + if ((int)m_print->objects.size() < object_idx) + return; + + const PrintObject* print_object = m_print->get_object(object_idx); + if (print_object == nullptr) + return; + + const ModelObject* model_object = print_object->model_object(); + if (!model_object->instances.empty()) { + for (const auto& point : model_object->sla_support_points) { + ::glColor4f(0.9f, 0.f, 0.f, 0.75f); + ::glPushMatrix(); + ::glTranslatef(point(0), point(1), point(2)); + GLUquadricObj *quadric; + quadric = ::gluNewQuadric(); + + ::gluQuadricDrawStyle(quadric, GLU_FILL ); + ::gluSphere( quadric , 0.5 , 36 , 18 ); + ::gluDeleteQuadric(quadric); + ::glPopMatrix(); + } + } +} +//@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ + + + + + + +void GLCanvas3D::_render_layer_editing_overlay() const +{ + if (m_print == nullptr) + return; + + GLVolume* volume = nullptr; + for (GLVolume* vol : m_volumes.volumes) { if ((vol != nullptr) && vol->selected && vol->has_layer_height_texture()) diff --git a/xs/src/slic3r/GUI/GLCanvas3D.hpp b/xs/src/slic3r/GUI/GLCanvas3D.hpp index 541495eec..ccf3e5d31 100644 --- a/xs/src/slic3r/GUI/GLCanvas3D.hpp +++ b/xs/src/slic3r/GUI/GLCanvas3D.hpp @@ -682,6 +682,7 @@ private: void _render_bed(float theta) const; void _render_axes(bool depth_test) const; void _render_objects() const; + void _render_sla_support_points() const; void _render_cutting_plane() const; void _render_warning_texture() const; void _render_legend_texture() const;