diff --git a/src/libslic3r/Technologies.hpp b/src/libslic3r/Technologies.hpp index fd3258e61e..82ed7bc13d 100644 --- a/src/libslic3r/Technologies.hpp +++ b/src/libslic3r/Technologies.hpp @@ -60,6 +60,8 @@ #define ENABLE_TRAVEL_TIME (1 && ENABLE_2_5_0_ALPHA1) // Enable not killing focus in object manipulator fields when hovering over 3D scene #define ENABLE_OBJECT_MANIPULATOR_FOCUS (1 && ENABLE_2_5_0_ALPHA1) +// Enable removal of wipe tower magic object_id equal to 1000 +#define ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL (1 && ENABLE_2_5_0_ALPHA1) #endif // _prusaslicer_technologies_h_ diff --git a/src/slic3r/GUI/3DScene.cpp b/src/slic3r/GUI/3DScene.cpp index 95077d1925..0f72ac0459 100644 --- a/src/slic3r/GUI/3DScene.cpp +++ b/src/slic3r/GUI/3DScene.cpp @@ -669,9 +669,15 @@ void GLVolumeCollection::load_object_auxiliary( } } +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL +int GLVolumeCollection::load_wipe_tower_preview( + float pos_x, float pos_y, float width, float depth, float height, + float rotation_angle, bool size_unknown, float brim_width, bool opengl_initialized) +#else int GLVolumeCollection::load_wipe_tower_preview( int obj_idx, float pos_x, float pos_y, float width, float depth, float height, float rotation_angle, bool size_unknown, float brim_width, bool opengl_initialized) +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL { if (depth < 0.01f) return int(this->volumes.size() - 1); @@ -733,7 +739,11 @@ int GLVolumeCollection::load_wipe_tower_preview( v.indexed_vertex_array.finalize_geometry(opengl_initialized); v.set_volume_offset(Vec3d(pos_x, pos_y, 0.0)); v.set_volume_rotation(Vec3d(0., 0., (M_PI / 180.) * rotation_angle)); +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + v.composite_id = GLVolume::CompositeID(INT_MAX, 0, 0); +#else v.composite_id = GLVolume::CompositeID(obj_idx, 0, 0); +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL v.geometry_id.first = 0; v.geometry_id.second = wipe_tower_instance_id().id; v.is_wipe_tower = true; diff --git a/src/slic3r/GUI/3DScene.hpp b/src/slic3r/GUI/3DScene.hpp index c603f39562..68538c5e0f 100644 --- a/src/slic3r/GUI/3DScene.hpp +++ b/src/slic3r/GUI/3DScene.hpp @@ -460,8 +460,8 @@ public: void set_convex_hull(const TriangleMesh &convex_hull) { m_convex_hull = std::make_shared(convex_hull); } void set_convex_hull(TriangleMesh &&convex_hull) { m_convex_hull = std::make_shared(std::move(convex_hull)); } - int object_idx() const { return this->composite_id.object_id; } - int volume_idx() const { return this->composite_id.volume_id; } + int object_idx() const { return this->composite_id.object_id; } + int volume_idx() const { return this->composite_id.volume_id; } int instance_idx() const { return this->composite_id.instance_id; } Transform3d world_matrix() const; @@ -590,8 +590,13 @@ public: size_t timestamp, bool opengl_initialized); +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + int load_wipe_tower_preview( + float pos_x, float pos_y, float width, float depth, float height, float rotation_angle, bool size_unknown, float brim_width, bool opengl_initialized); +#else int load_wipe_tower_preview( int obj_idx, float pos_x, float pos_y, float width, float depth, float height, float rotation_angle, bool size_unknown, float brim_width, bool opengl_initialized); +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL GLVolume* new_toolpath_volume(const ColorRGBA& rgba, size_t reserve_vbo_floats = 0); GLVolume* new_nontoolpath_volume(const ColorRGBA& rgba, size_t reserve_vbo_floats = 0); diff --git a/src/slic3r/GUI/GCodeViewer.cpp b/src/slic3r/GUI/GCodeViewer.cpp index d17f184bbc..da01e120a9 100644 --- a/src/slic3r/GUI/GCodeViewer.cpp +++ b/src/slic3r/GUI/GCodeViewer.cpp @@ -2135,8 +2135,13 @@ void GCodeViewer::load_shells(const Print& print, bool initialized) const float depth = print.wipe_tower_data(extruders_count).depth; const float brim_width = print.wipe_tower_data(extruders_count).brim_width; +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + m_shells.volumes.load_wipe_tower_preview(config.wipe_tower_x, config.wipe_tower_y, config.wipe_tower_width, depth, max_z, config.wipe_tower_rotation_angle, + !print.is_step_done(psWipeTower), brim_width, initialized); +#else m_shells.volumes.load_wipe_tower_preview(1000, config.wipe_tower_x, config.wipe_tower_y, config.wipe_tower_width, depth, max_z, config.wipe_tower_rotation_angle, !print.is_step_done(psWipeTower), brim_width, initialized); +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL } } diff --git a/src/slic3r/GUI/GLCanvas3D.cpp b/src/slic3r/GUI/GLCanvas3D.cpp index 67e1b8bcf5..f2fbf50a90 100644 --- a/src/slic3r/GUI/GLCanvas3D.cpp +++ b/src/slic3r/GUI/GLCanvas3D.cpp @@ -1123,11 +1123,18 @@ ModelInstanceEPrintVolumeState GLCanvas3D::check_volumes_outside_state() const void GLCanvas3D::toggle_sla_auxiliaries_visibility(bool visible, const ModelObject* mo, int instance_idx) { +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if (current_printer_technology() != ptSLA) + return; +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + m_render_sla_auxiliaries = visible; for (GLVolume* vol : m_volumes.volumes) { +#if !ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL if (vol->composite_id.object_id == 1000) continue; // the wipe tower +#endif // !ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL if ((mo == nullptr || m_model->objects[vol->composite_id.object_id] == mo) && (instance_idx == -1 || vol->composite_id.instance_id == instance_idx) && vol->composite_id.volume_id < 0) @@ -1138,9 +1145,14 @@ void GLCanvas3D::toggle_sla_auxiliaries_visibility(bool visible, const ModelObje void GLCanvas3D::toggle_model_objects_visibility(bool visible, const ModelObject* mo, int instance_idx, const ModelVolume* mv) { for (GLVolume* vol : m_volumes.volumes) { +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if (vol->is_wipe_tower) + vol->is_active = (visible && mo == nullptr); +#else if (vol->composite_id.object_id == 1000) { // wipe tower vol->is_active = (visible && mo == nullptr); } +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL else { if ((mo == nullptr || m_model->objects[vol->composite_id.object_id] == mo) && (instance_idx == -1 || vol->composite_id.instance_id == instance_idx) @@ -1165,6 +1177,7 @@ void GLCanvas3D::toggle_model_objects_visibility(bool visible, const ModelObject } } } + if (visible && !mo) toggle_sla_auxiliaries_visibility(true, mo, instance_idx); @@ -1182,7 +1195,7 @@ void GLCanvas3D::update_instance_printable_state_for_object(const size_t obj_idx ModelInstance* instance = model_object->instances[inst_idx]; for (GLVolume* volume : m_volumes.volumes) { - if ((volume->object_idx() == (int)obj_idx) && (volume->instance_idx() == inst_idx)) + if (volume->object_idx() == (int)obj_idx && volume->instance_idx() == inst_idx) volume->printable = instance->printable; } } @@ -2021,9 +2034,15 @@ void GLCanvas3D::reload_scene(bool refresh_immediately, bool force_full_scene_re float depth = print->wipe_tower_data(extruders_count).depth; float brim_width = print->wipe_tower_data(extruders_count).brim_width; +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + int volume_idx_wipe_tower_new = m_volumes.load_wipe_tower_preview( + x, y, w, depth, (float)height, a, !print->is_step_done(psWipeTower), + brim_width, m_initialized); +#else int volume_idx_wipe_tower_new = m_volumes.load_wipe_tower_preview( 1000, x, y, w, depth, (float)height, a, !print->is_step_done(psWipeTower), brim_width, m_initialized); +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL if (volume_idx_wipe_tower_old != -1) map_glvolume_old_to_new[volume_idx_wipe_tower_old] = volume_idx_wipe_tower_new; } @@ -3448,9 +3467,15 @@ void GLCanvas3D::do_move(const std::string& snapshot_type) model_object->invalidate_bounding_box(); } } +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + else if (v->is_wipe_tower) + // Move a wipe tower proxy. + wipe_tower_origin = v->get_volume_offset(); +#else else if (object_idx == 1000) // Move a wipe tower proxy. wipe_tower_origin = v->get_volume_offset(); +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL } // Fixes flying instances @@ -3510,11 +3535,18 @@ void GLCanvas3D::do_rotate(const std::string& snapshot_type) Selection::EMode selection_mode = m_selection.get_mode(); for (const GLVolume* v : m_volumes.volumes) { +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if (v->is_wipe_tower) { +#else int object_idx = v->object_idx(); if (object_idx == 1000) { // the wipe tower +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL Vec3d offset = v->get_volume_offset(); post_event(Vec3dEvent(EVT_GLCANVAS_WIPETOWER_ROTATED, Vec3d(offset(0), offset(1), v->get_volume_rotation()(2)))); } +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + int object_idx = v->object_idx(); +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL if (object_idx < 0 || (int)m_model->objects.size() <= object_idx) continue; diff --git a/src/slic3r/GUI/GUI_ObjectList.cpp b/src/slic3r/GUI/GUI_ObjectList.cpp index a02abc8494..d302bf5a84 100644 --- a/src/slic3r/GUI/GUI_ObjectList.cpp +++ b/src/slic3r/GUI/GUI_ObjectList.cpp @@ -1931,9 +1931,15 @@ void ObjectList::del_layers_from_object(const int obj_idx) bool ObjectList::del_subobject_from_object(const int obj_idx, const int idx, const int type) { assert(idx >= 0); - if (obj_idx == 1000 || idx<0) +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if (m_objects->empty() || int(m_objects->size()) <= obj_idx) + // Cannot delete a wipe tower + return false; +#else + if (obj_idx == 1000 || idx<0) // Cannot delete a wipe tower or volume with negative id return false; +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL ModelObject* object = (*m_objects)[obj_idx]; diff --git a/src/slic3r/GUI/Plater.cpp b/src/slic3r/GUI/Plater.cpp index 21aa5fc124..38789cd3f1 100644 --- a/src/slic3r/GUI/Plater.cpp +++ b/src/slic3r/GUI/Plater.cpp @@ -1245,7 +1245,11 @@ void Sidebar::show_info_sizer() ModelObjectPtrs objects = p->plater->model().objects; int obj_idx = selection.get_object_idx(); +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if (m_mode < comExpert || objects.empty() || obj_idx < 0 || objects.size() <= obj_idx || +#else if (m_mode < comExpert || objects.empty() || obj_idx < 0 || obj_idx == 1000 || +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL objects[obj_idx]->volumes.empty() || // hack to avoid crash when deleting the last object on the bed (selection.is_single_full_object() && objects[obj_idx]->instances.size()> 1) || !(selection.is_single_full_instance() || selection.is_single_volume())) { @@ -2866,14 +2870,22 @@ Selection& Plater::priv::get_selection() int Plater::priv::get_selected_object_idx() const { int idx = get_selection().get_object_idx(); +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + return (0 <= idx && idx < model.objects.size()) ? idx : -1; +#else return ((0 <= idx) && (idx < 1000)) ? idx : -1; +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL } int Plater::priv::get_selected_volume_idx() const { auto& selection = get_selection(); int idx = selection.get_object_idx(); +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if (idx < 0 || int(model.objects.size()) <= idx) +#else if ((0 > idx) || (idx > 1000)) +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL return-1; const GLVolume* v = selection.get_volume(*selection.get_volume_idxs().begin()); if (model.objects[idx]->volumes.size() > 1) diff --git a/src/slic3r/GUI/Selection.cpp b/src/slic3r/GUI/Selection.cpp index c4b7d2c3d3..f84f3cb9ac 100644 --- a/src/slic3r/GUI/Selection.cpp +++ b/src/slic3r/GUI/Selection.cpp @@ -539,7 +539,11 @@ bool Selection::is_single_full_instance() const bool Selection::is_from_single_object() const { const int idx = get_object_idx(); +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + return 0 <= idx && idx < int(m_model->objects.size()); +#else return 0 <= idx && idx < 1000; +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL } bool Selection::is_sla_compliant() const @@ -1067,9 +1071,16 @@ void Selection::translate(unsigned int object_idx, const Vec3d& displacement) if (done.size() == m_volumes->size()) break; +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if ((*m_volumes)[i]->is_wipe_tower) + continue; + + int object_idx = (*m_volumes)[i]->object_idx(); +#else int object_idx = (*m_volumes)[i]->object_idx(); if (object_idx >= 1000) continue; +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL // Process unselected volumes of the object. for (unsigned int j = 0; j < (unsigned int)m_volumes->size(); ++j) { @@ -1109,9 +1120,16 @@ void Selection::translate(unsigned int object_idx, unsigned int instance_idx, co if (done.size() == m_volumes->size()) break; +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if ((*m_volumes)[i]->is_wipe_tower) + continue; + + int object_idx = (*m_volumes)[i]->object_idx(); +#else int object_idx = (*m_volumes)[i]->object_idx(); if (object_idx >= 1000) continue; +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL // Process unselected volumes of the object. for (unsigned int j = 0; j < (unsigned int)m_volumes->size(); ++j) { @@ -2062,9 +2080,16 @@ void Selection::synchronize_unselected_instances(SyncRotationType sync_rotation_ break; const GLVolume* volume = (*m_volumes)[i]; +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if (volume->is_wipe_tower) + continue; + + const int object_idx = volume->object_idx(); +#else const int object_idx = volume->object_idx(); if (object_idx >= 1000) continue; +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL const int instance_idx = volume->instance_idx(); const Vec3d& rotation = volume->get_instance_rotation(); @@ -2116,9 +2141,16 @@ void Selection::synchronize_unselected_volumes() { for (unsigned int i : m_list) { const GLVolume* volume = (*m_volumes)[i]; +#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL + if (volume->is_wipe_tower) + continue; + + const int object_idx = volume->object_idx(); +#else const int object_idx = volume->object_idx(); if (object_idx >= 1000) continue; +#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL const int volume_idx = volume->volume_idx(); const Vec3d& offset = volume->get_volume_offset();