mirror of
				https://github.com/SoftFever/OrcaSlicer.git
				synced 2025-10-31 20:51:12 -06:00 
			
		
		
		
	Merge branch 'master' of github.com:alexrj/Slic3r
This commit is contained in:
		
						commit
						f3db284e2a
					
				
					 19 changed files with 448 additions and 347 deletions
				
			
		|  | @ -16,6 +16,7 @@ BoundingBoxBase<PointClass>::BoundingBoxBase(const std::vector<PointClass> &poin | |||
|         this->max.x = std::max(it->x, this->max.x); | ||||
|         this->max.y = std::max(it->y, this->max.y); | ||||
|     } | ||||
|     this->defined = true; | ||||
| } | ||||
| template BoundingBoxBase<Point>::BoundingBoxBase(const std::vector<Point> &points); | ||||
| template BoundingBoxBase<Pointf>::BoundingBoxBase(const std::vector<Pointf> &points); | ||||
|  | @ -80,10 +81,15 @@ template void BoundingBoxBase<Pointf3>::scale(double factor); | |||
| template <class PointClass> void | ||||
| BoundingBoxBase<PointClass>::merge(const PointClass &point) | ||||
| { | ||||
|     this->min.x = std::min(point.x, this->min.x); | ||||
|     this->min.y = std::min(point.y, this->min.y); | ||||
|     this->max.x = std::max(point.x, this->max.x); | ||||
|     this->max.y = std::max(point.y, this->max.y); | ||||
|     if (this->defined) { | ||||
|         this->min.x = std::min(point.x, this->min.x); | ||||
|         this->min.y = std::min(point.y, this->min.y); | ||||
|         this->max.x = std::max(point.x, this->max.x); | ||||
|         this->max.y = std::max(point.y, this->max.y); | ||||
|     } else { | ||||
|         this->min = this->max = point; | ||||
|         this->defined = true; | ||||
|     } | ||||
| } | ||||
| template void BoundingBoxBase<Point>::merge(const Point &point); | ||||
| template void BoundingBoxBase<Pointf>::merge(const Pointf &point); | ||||
|  | @ -91,10 +97,16 @@ template void BoundingBoxBase<Pointf>::merge(const Pointf &point); | |||
| template <class PointClass> void | ||||
| BoundingBoxBase<PointClass>::merge(const BoundingBoxBase<PointClass> &bb) | ||||
| { | ||||
|     this->min.x = std::min(bb.min.x, this->min.x); | ||||
|     this->min.y = std::min(bb.min.y, this->min.y); | ||||
|     this->max.x = std::max(bb.max.x, this->max.x); | ||||
|     this->max.y = std::max(bb.max.y, this->max.y); | ||||
|     if (this->defined) { | ||||
|         this->min.x = std::min(bb.min.x, this->min.x); | ||||
|         this->min.y = std::min(bb.min.y, this->min.y); | ||||
|         this->max.x = std::max(bb.max.x, this->max.x); | ||||
|         this->max.y = std::max(bb.max.y, this->max.y); | ||||
|     } else { | ||||
|         this->min = bb.min; | ||||
|         this->max = bb.max; | ||||
|         this->defined = true; | ||||
|     } | ||||
| } | ||||
| template void BoundingBoxBase<Point>::merge(const BoundingBoxBase<Point> &bb); | ||||
| template void BoundingBoxBase<Pointf>::merge(const BoundingBoxBase<Pointf> &bb); | ||||
|  | @ -102,18 +114,22 @@ template void BoundingBoxBase<Pointf>::merge(const BoundingBoxBase<Pointf> &bb); | |||
| template <class PointClass> void | ||||
| BoundingBox3Base<PointClass>::merge(const PointClass &point) | ||||
| { | ||||
|     if (this->defined) { | ||||
|         this->min.z = std::min(point.z, this->min.z); | ||||
|         this->max.z = std::max(point.z, this->max.z); | ||||
|     } | ||||
|     BoundingBoxBase<PointClass>::merge(point); | ||||
|     this->min.z = std::min(point.z, this->min.z); | ||||
|     this->max.z = std::max(point.z, this->max.z); | ||||
| } | ||||
| template void BoundingBox3Base<Pointf3>::merge(const Pointf3 &point); | ||||
| 
 | ||||
| template <class PointClass> void | ||||
| BoundingBox3Base<PointClass>::merge(const BoundingBox3Base<PointClass> &bb) | ||||
| { | ||||
|     if (this->defined) { | ||||
|         this->min.z = std::min(bb.min.z, this->min.z); | ||||
|         this->max.z = std::max(bb.max.z, this->max.z); | ||||
|     } | ||||
|     BoundingBoxBase<PointClass>::merge(bb); | ||||
|     this->min.z = std::min(bb.min.z, this->min.z); | ||||
|     this->max.z = std::max(bb.max.z, this->max.z); | ||||
| } | ||||
| template void BoundingBox3Base<Pointf3>::merge(const BoundingBox3Base<Pointf3> &bb); | ||||
| 
 | ||||
|  |  | |||
|  | @ -18,8 +18,9 @@ class BoundingBoxBase | |||
|     public: | ||||
|     PointClass min; | ||||
|     PointClass max; | ||||
|     bool defined; | ||||
|      | ||||
|     BoundingBoxBase() {}; | ||||
|     BoundingBoxBase() : defined(false) {}; | ||||
|     BoundingBoxBase(const std::vector<PointClass> &points); | ||||
|     void merge(const PointClass &point); | ||||
|     void merge(const BoundingBoxBase<PointClass> &bb); | ||||
|  | @ -34,7 +35,7 @@ template <class PointClass> | |||
| class BoundingBox3Base : public BoundingBoxBase<PointClass> | ||||
| { | ||||
|     public: | ||||
|     BoundingBox3Base() {}; | ||||
|     BoundingBox3Base() : BoundingBoxBase<PointClass>() {}; | ||||
|     BoundingBox3Base(const std::vector<PointClass> &points); | ||||
|     void merge(const PointClass &point); | ||||
|     void merge(const BoundingBox3Base<PointClass> &bb); | ||||
|  | @ -50,7 +51,7 @@ class BoundingBox : public BoundingBoxBase<Point> | |||
|     void polygon(Polygon* polygon) const; | ||||
|     Polygon polygon() const; | ||||
|      | ||||
|     BoundingBox() {}; | ||||
|     BoundingBox() : BoundingBoxBase<Point>() {}; | ||||
|     BoundingBox(const Points &points) : BoundingBoxBase<Point>(points) {}; | ||||
|     BoundingBox(const Lines &lines); | ||||
| }; | ||||
|  | @ -61,13 +62,13 @@ class BoundingBox3  : public BoundingBox3Base<Point3> {}; | |||
| 
 | ||||
| class BoundingBoxf : public BoundingBoxBase<Pointf> { | ||||
|     public: | ||||
|     BoundingBoxf() {}; | ||||
|     BoundingBoxf() : BoundingBoxBase<Pointf>() {}; | ||||
|     BoundingBoxf(const std::vector<Pointf> &points) : BoundingBoxBase<Pointf>(points) {}; | ||||
| }; | ||||
| 
 | ||||
| class BoundingBoxf3 : public BoundingBox3Base<Pointf3> { | ||||
|     public: | ||||
|     BoundingBoxf3() {}; | ||||
|     BoundingBoxf3() : BoundingBox3Base<Pointf3>() {}; | ||||
|     BoundingBoxf3(const std::vector<Pointf3> &points) : BoundingBox3Base<Pointf3>(points) {}; | ||||
| }; | ||||
| 
 | ||||
|  |  | |||
|  | @ -158,6 +158,91 @@ Model::has_objects_with_no_instances() const | |||
|     return false; | ||||
| } | ||||
| 
 | ||||
| // makes sure all objects have at least one instance
 | ||||
| bool | ||||
| Model::add_default_instances() | ||||
| { | ||||
|     bool added = false; | ||||
|     // apply a default position to all objects not having one
 | ||||
|     for (ModelObjectPtrs::const_iterator o = this->objects.begin(); o != this->objects.end(); ++o) { | ||||
|         if ((*o)->instances.empty()) { | ||||
|             (*o)->add_instance(); | ||||
|             added = true; | ||||
|         } | ||||
|     } | ||||
|     return true; | ||||
| } | ||||
| 
 | ||||
| // this returns the bounding box of the *transformed* instances
 | ||||
| void | ||||
| Model::bounding_box(BoundingBoxf3* bb) | ||||
| { | ||||
|     for (ModelObjectPtrs::const_iterator o = this->objects.begin(); o != this->objects.end(); ++o) { | ||||
|         BoundingBoxf3 obb; | ||||
|         (*o)->bounding_box(&obb); | ||||
|         bb->merge(obb); | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| void | ||||
| Model::center_instances_around_point(const Pointf &point) | ||||
| { | ||||
|     BoundingBoxf3 bb; | ||||
|     this->bounding_box(&bb); | ||||
|      | ||||
|     Sizef3 size = bb.size(); | ||||
|     double shift_x = -bb.min.x + point.x - size.x/2; | ||||
|     double shift_y = -bb.min.y + point.y - size.y/2; | ||||
|      | ||||
|     for (ModelObjectPtrs::const_iterator o = this->objects.begin(); o != this->objects.end(); ++o) { | ||||
|         for (ModelInstancePtrs::const_iterator i = (*o)->instances.begin(); i != (*o)->instances.end(); ++i) { | ||||
|             (*i)->offset.translate(shift_x, shift_y); | ||||
|         } | ||||
|         (*o)->update_bounding_box(); | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| void | ||||
| Model::align_instances_to_origin() | ||||
| { | ||||
|     BoundingBoxf3 bb; | ||||
|     this->bounding_box(&bb); | ||||
|      | ||||
|     Pointf new_center = (Pointf)bb.size(); | ||||
|     new_center.translate(-new_center.x/2, -new_center.y/2); | ||||
|     this->center_instances_around_point(new_center); | ||||
| } | ||||
| 
 | ||||
| void | ||||
| Model::translate(coordf_t x, coordf_t y, coordf_t z) | ||||
| { | ||||
|     for (ModelObjectPtrs::const_iterator o = this->objects.begin(); o != this->objects.end(); ++o) { | ||||
|         (*o)->translate(x, y, z); | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| // flattens everything to a single mesh
 | ||||
| void | ||||
| Model::mesh(TriangleMesh* mesh) const | ||||
| { | ||||
|     for (ModelObjectPtrs::const_iterator o = this->objects.begin(); o != this->objects.end(); ++o) { | ||||
|         TriangleMesh omesh; | ||||
|         (*o)->mesh(&omesh); | ||||
|         mesh->merge(omesh); | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| // flattens everything to a single mesh
 | ||||
| void | ||||
| Model::raw_mesh(TriangleMesh* mesh) const | ||||
| { | ||||
|     for (ModelObjectPtrs::const_iterator o = this->objects.begin(); o != this->objects.end(); ++o) { | ||||
|         TriangleMesh omesh; | ||||
|         (*o)->raw_mesh(&omesh); | ||||
|         mesh->merge(omesh); | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| #ifdef SLIC3RXS | ||||
| REGISTER_CLASS(Model, "Model"); | ||||
| #endif | ||||
|  | @ -306,12 +391,45 @@ ModelObject::clear_instances() | |||
|         this->delete_instance(i); | ||||
| } | ||||
| 
 | ||||
| // this returns the bounding box of the *transformed* instances
 | ||||
| void | ||||
| ModelObject::bounding_box(BoundingBoxf3* bb) | ||||
| { | ||||
|     if (!this->_bounding_box_valid) this->update_bounding_box(); | ||||
|     *bb = this->_bounding_box; | ||||
| } | ||||
| 
 | ||||
| void | ||||
| ModelObject::invalidate_bounding_box() | ||||
| { | ||||
|     this->_bounding_box_valid = false; | ||||
| } | ||||
| 
 | ||||
| void | ||||
| ModelObject::update_bounding_box() | ||||
| { | ||||
|     TriangleMesh mesh; | ||||
|     this->mesh(&mesh); | ||||
|      | ||||
|     mesh.bounding_box(&this->_bounding_box); | ||||
|     this->_bounding_box_valid = true; | ||||
| } | ||||
| 
 | ||||
| // flattens all volumes and instances into a single mesh
 | ||||
| void | ||||
| ModelObject::mesh(TriangleMesh* mesh) const | ||||
| { | ||||
|     TriangleMesh raw_mesh; | ||||
|     this->raw_mesh(&raw_mesh); | ||||
|      | ||||
|      | ||||
|     for (ModelInstancePtrs::const_iterator i = this->instances.begin(); i != this->instances.end(); ++i) { | ||||
|         TriangleMesh m = raw_mesh; | ||||
|         (*i)->transform_mesh(&m); | ||||
|         mesh->merge(m); | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| void | ||||
| ModelObject::raw_mesh(TriangleMesh* mesh) const | ||||
| { | ||||
|  | @ -321,6 +439,156 @@ ModelObject::raw_mesh(TriangleMesh* mesh) const | |||
|     } | ||||
| } | ||||
| 
 | ||||
| void | ||||
| ModelObject::raw_bounding_box(BoundingBoxf3* bb) const | ||||
| { | ||||
|     for (ModelVolumePtrs::const_iterator v = this->volumes.begin(); v != this->volumes.end(); ++v) { | ||||
|         if ((*v)->modifier) continue; | ||||
|         TriangleMesh mesh = (*v)->mesh; | ||||
|          | ||||
|         if (this->instances.empty()) CONFESS("Can't call raw_bounding_box() with no instances"); | ||||
|         this->instances.front()->transform_mesh(&mesh, true); | ||||
|          | ||||
|         BoundingBoxf3 mbb; | ||||
|         mesh.bounding_box(&mbb); | ||||
|         bb->merge(mbb); | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| // this returns the bounding box of the *transformed* given instance
 | ||||
| void | ||||
| ModelObject::instance_bounding_box(size_t instance_idx, BoundingBoxf3* bb) const | ||||
| { | ||||
|     TriangleMesh mesh; | ||||
|     this->raw_mesh(&mesh); | ||||
|      | ||||
|     this->instances[instance_idx]->transform_mesh(&mesh); | ||||
|      | ||||
|     mesh.bounding_box(bb); | ||||
| } | ||||
| 
 | ||||
| void | ||||
| ModelObject::center_around_origin() | ||||
| { | ||||
|     // calculate the displacements needed to 
 | ||||
|     // center this object around the origin
 | ||||
|     BoundingBoxf3 bb; | ||||
|     { | ||||
|         TriangleMesh mesh; | ||||
|         this->raw_mesh(&mesh); | ||||
|         mesh.bounding_box(&bb); | ||||
|     } | ||||
|      | ||||
|     // first align to origin on XY
 | ||||
|     double shift_x = -bb.min.x; | ||||
|     double shift_y = -bb.min.y; | ||||
|      | ||||
|     // then center it on XY
 | ||||
|     Sizef3 size = bb.size(); | ||||
|     shift_x -= size.x/2; | ||||
|     shift_y -= size.y/2; | ||||
|      | ||||
|     this->translate(shift_x, shift_y, 0); | ||||
|     this->origin_translation.translate(shift_x, shift_y); | ||||
|      | ||||
|     if (!this->instances.empty()) { | ||||
|         for (ModelInstancePtrs::const_iterator i = this->instances.begin(); i != this->instances.end(); ++i) { | ||||
|             (*i)->offset.translate(-shift_x, -shift_y); | ||||
|         } | ||||
|         this->update_bounding_box(); | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| void | ||||
| ModelObject::translate(coordf_t x, coordf_t y, coordf_t z) | ||||
| { | ||||
|     for (ModelVolumePtrs::const_iterator v = this->volumes.begin(); v != this->volumes.end(); ++v) { | ||||
|         (*v)->mesh.translate(x, y, z); | ||||
|     } | ||||
|     if (this->_bounding_box_valid) this->_bounding_box.translate(x, y, z); | ||||
| } | ||||
| 
 | ||||
| void | ||||
| ModelObject::scale(const Pointf3 &versor) | ||||
| { | ||||
|     for (ModelVolumePtrs::const_iterator v = this->volumes.begin(); v != this->volumes.end(); ++v) { | ||||
|         (*v)->mesh.scale(versor); | ||||
|     } | ||||
|     this->invalidate_bounding_box(); | ||||
| } | ||||
| 
 | ||||
| size_t | ||||
| ModelObject::materials_count() const | ||||
| { | ||||
|     std::set<t_model_material_id> material_ids; | ||||
|     for (ModelVolumePtrs::const_iterator v = this->volumes.begin(); v != this->volumes.end(); ++v) { | ||||
|         material_ids.insert((*v)->material_id()); | ||||
|     } | ||||
|     return material_ids.size(); | ||||
| } | ||||
| 
 | ||||
| size_t | ||||
| ModelObject::facets_count() const | ||||
| { | ||||
|     size_t num = 0; | ||||
|     for (ModelVolumePtrs::const_iterator v = this->volumes.begin(); v != this->volumes.end(); ++v) { | ||||
|         if ((*v)->modifier) continue; | ||||
|         num += (*v)->mesh.stl.stats.number_of_facets; | ||||
|     } | ||||
|     return num; | ||||
| } | ||||
| 
 | ||||
| bool | ||||
| ModelObject::needed_repair() const | ||||
| { | ||||
|     for (ModelVolumePtrs::const_iterator v = this->volumes.begin(); v != this->volumes.end(); ++v) { | ||||
|         if ((*v)->modifier) continue; | ||||
|         if ((*v)->mesh.needed_repair()) return true; | ||||
|     } | ||||
|     return false; | ||||
| } | ||||
| 
 | ||||
| void | ||||
| ModelObject::cut(coordf_t z, Model* model) const | ||||
| { | ||||
|     // clone this one to duplicate instances, materials etc.
 | ||||
|     ModelObject* upper = model->add_object(*this); | ||||
|     ModelObject* lower = model->add_object(*this); | ||||
|     upper->clear_volumes(); | ||||
|     lower->clear_volumes(); | ||||
|      | ||||
|     for (ModelVolumePtrs::const_iterator v = this->volumes.begin(); v != this->volumes.end(); ++v) { | ||||
|         ModelVolume* volume = *v; | ||||
|         if (volume->modifier) { | ||||
|             // don't cut modifiers
 | ||||
|             upper->add_volume(*volume); | ||||
|             lower->add_volume(*volume); | ||||
|         } else { | ||||
|             TriangleMeshSlicer tms(&volume->mesh); | ||||
|             TriangleMesh upper_mesh, lower_mesh; | ||||
|             // TODO: shouldn't we use object bounding box instead of per-volume bb?
 | ||||
|             tms.cut(z + volume->mesh.bounding_box().min.z, &upper_mesh, &lower_mesh); | ||||
|             upper_mesh.repair(); | ||||
|             lower_mesh.repair(); | ||||
|             upper_mesh.reset_repair_stats(); | ||||
|             lower_mesh.reset_repair_stats(); | ||||
|              | ||||
|             if (upper_mesh.facets_count() > 0) { | ||||
|                 ModelVolume* vol    = upper->add_volume(upper_mesh); | ||||
|                 vol->name           = volume->name; | ||||
|                 vol->config         = volume->config; | ||||
|                 vol->set_material(volume->material_id(), *volume->material()); | ||||
|             } | ||||
|             if (lower_mesh.facets_count() > 0) { | ||||
|                 ModelVolume* vol    = lower->add_volume(lower_mesh); | ||||
|                 vol->name           = volume->name; | ||||
|                 vol->config         = volume->config; | ||||
|                 vol->set_material(volume->material_id(), *volume->material()); | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| #ifdef SLIC3RXS | ||||
| REGISTER_CLASS(ModelObject, "Model::Object"); | ||||
| #endif | ||||
|  | @ -358,6 +626,13 @@ ModelVolume::material() const | |||
|     return this->object->get_model()->get_material(this->_material_id); | ||||
| } | ||||
| 
 | ||||
| void | ||||
| ModelVolume::set_material(t_model_material_id material_id, const ModelMaterial &material) | ||||
| { | ||||
|     this->_material_id = material_id; | ||||
|     (void)this->object->get_model()->add_material(material_id, material); | ||||
| } | ||||
| 
 | ||||
| ModelMaterial* | ||||
| ModelVolume::assign_unique_material() | ||||
| { | ||||
|  |  | |||
|  | @ -53,11 +53,13 @@ class Model | |||
|     // void arrange_objects(coordf_t distance, const BoundingBox &bb);
 | ||||
|     // void duplicate(size_t copies_num, coordf_t distance, const BoundingBox &bb);
 | ||||
|     bool has_objects_with_no_instances() const; | ||||
|     // void bounding_box(BoundingBox* bb) const;
 | ||||
|     // void align_to_origin();
 | ||||
|     // void center_instances_around_point(const Pointf &point);
 | ||||
|     // void translate(coordf_t x, coordf_t y, coordf_t z);
 | ||||
|     // void mesh(TriangleMesh* mesh) const;
 | ||||
|     bool add_default_instances(); | ||||
|     void bounding_box(BoundingBoxf3* bb); | ||||
|     void center_instances_around_point(const Pointf &point); | ||||
|     void align_instances_to_origin(); | ||||
|     void translate(coordf_t x, coordf_t y, coordf_t z); | ||||
|     void mesh(TriangleMesh* mesh) const; | ||||
|     void raw_mesh(TriangleMesh* mesh) const; | ||||
|     // void split_meshes();
 | ||||
|     // std::string get_material_name(t_model_material_id material_id);
 | ||||
| 
 | ||||
|  | @ -112,17 +114,21 @@ class ModelObject | |||
|     void delete_last_instance(); | ||||
|     void clear_instances(); | ||||
| 
 | ||||
|     void bounding_box(BoundingBoxf3* bb); | ||||
|     void invalidate_bounding_box(); | ||||
| 
 | ||||
|     void mesh(TriangleMesh* mesh) const; | ||||
|     void raw_mesh(TriangleMesh* mesh) const; | ||||
|     //void mesh(TriangleMesh* mesh) const;
 | ||||
|     //void instance_bounding_box(size_t instance_idx, BoundingBox* bb) const;
 | ||||
|     //void center_around_origin();
 | ||||
|     //void translate(coordf_t x, coordf_t y, coordf_t z);
 | ||||
|     //size_t materials_count() const;
 | ||||
|     //void unique_materials(std::vector<t_model_material_id>* materials) const;
 | ||||
|     //size_t facets_count() const;
 | ||||
|     //bool needed_repair() const;
 | ||||
|     void raw_bounding_box(BoundingBoxf3* bb) const; | ||||
|     void instance_bounding_box(size_t instance_idx, BoundingBoxf3* bb) const; | ||||
|     void center_around_origin(); | ||||
|     void translate(coordf_t x, coordf_t y, coordf_t z); | ||||
|     void scale(const Pointf3 &versor); | ||||
|     size_t materials_count() const; | ||||
|     size_t facets_count() const; | ||||
|     bool needed_repair() const; | ||||
|     void cut(coordf_t z, Model* model) const; | ||||
|     void update_bounding_box();   // this is a private method but we expose it until we need to expose it via XS
 | ||||
|      | ||||
|     private: | ||||
|     Model* model; | ||||
|  | @ -132,7 +138,6 @@ class ModelObject | |||
|     ModelObject& operator= (ModelObject other); | ||||
|     void swap(ModelObject &other); | ||||
|     ~ModelObject(); | ||||
|     void update_bounding_box(); | ||||
| }; | ||||
| 
 | ||||
| class ModelVolume | ||||
|  | @ -148,6 +153,7 @@ class ModelVolume | |||
|     t_model_material_id material_id() const; | ||||
|     void material_id(t_model_material_id material_id); | ||||
|     ModelMaterial* material() const; | ||||
|     void set_material(t_model_material_id material_id, const ModelMaterial &material); | ||||
|      | ||||
|     ModelMaterial* assign_unique_material(); | ||||
|      | ||||
|  |  | |||
|  | @ -153,6 +153,23 @@ TriangleMesh::reset_repair_stats() { | |||
|     this->stl.stats.normals_fixed       = 0; | ||||
| } | ||||
| 
 | ||||
| bool | ||||
| TriangleMesh::needed_repair() const | ||||
| { | ||||
|     return this->stl.stats.degenerate_facets    > 0 | ||||
|         || this->stl.stats.edges_fixed          > 0 | ||||
|         || this->stl.stats.facets_removed       > 0 | ||||
|         || this->stl.stats.facets_added         > 0 | ||||
|         || this->stl.stats.facets_reversed      > 0 | ||||
|         || this->stl.stats.backwards_edges      > 0; | ||||
| } | ||||
| 
 | ||||
| size_t | ||||
| TriangleMesh::facets_count() const | ||||
| { | ||||
|     return this->stl.stats.number_of_facets; | ||||
| } | ||||
| 
 | ||||
| void | ||||
| TriangleMesh::WriteOBJFile(char* output_file) { | ||||
|     stl_generate_shared_vertices(&stl); | ||||
|  | @ -164,12 +181,12 @@ void TriangleMesh::scale(float factor) | |||
|     stl_scale(&(this->stl), factor); | ||||
| } | ||||
| 
 | ||||
| void TriangleMesh::scale(std::vector<double> versor) | ||||
| void TriangleMesh::scale(const Pointf3 &versor) | ||||
| { | ||||
|     float fversor[3]; | ||||
|     fversor[0] = versor[0]; | ||||
|     fversor[1] = versor[1]; | ||||
|     fversor[2] = versor[2]; | ||||
|     fversor[0] = versor.x; | ||||
|     fversor[1] = versor.y; | ||||
|     fversor[2] = versor.z; | ||||
|     stl_scale_versor(&this->stl, fversor); | ||||
| } | ||||
| 
 | ||||
|  | @ -344,6 +361,14 @@ TriangleMesh::bounding_box(BoundingBoxf3* bb) const | |||
|     bb->max.z = this->stl.stats.max.z; | ||||
| } | ||||
| 
 | ||||
| BoundingBoxf3 | ||||
| TriangleMesh::bounding_box() const | ||||
| { | ||||
|     BoundingBoxf3 bb; | ||||
|     this->bounding_box(&bb); | ||||
|     return bb; | ||||
| } | ||||
| 
 | ||||
| void | ||||
| TriangleMesh::require_shared_vertices() | ||||
| { | ||||
|  |  | |||
|  | @ -29,7 +29,7 @@ class TriangleMesh | |||
|     void repair(); | ||||
|     void WriteOBJFile(char* output_file); | ||||
|     void scale(float factor); | ||||
|     void scale(std::vector<double> versor); | ||||
|     void scale(const Pointf3 &versor); | ||||
|     void translate(float x, float y, float z); | ||||
|     void rotate_x(float angle); | ||||
|     void rotate_y(float angle); | ||||
|  | @ -44,7 +44,10 @@ class TriangleMesh | |||
|     void horizontal_projection(ExPolygons &retval) const; | ||||
|     void convex_hull(Polygon* hull); | ||||
|     void bounding_box(BoundingBoxf3* bb) const; | ||||
|     BoundingBoxf3 bounding_box() const; | ||||
|     void reset_repair_stats(); | ||||
|     bool needed_repair() const; | ||||
|     size_t facets_count() const; | ||||
|     stl_file stl; | ||||
|     bool repaired; | ||||
|      | ||||
|  |  | |||
|  | @ -40,7 +40,7 @@ my $cube = { | |||
|     $m->scale(2); | ||||
|     ok abs($m->stats->{volume} - 40*40*40) < 1E-2, 'scale'; | ||||
|      | ||||
|     $m->scale_xyz([2,1,1]); | ||||
|     $m->scale_xyz(Slic3r::Pointf3->new(2,1,1)); | ||||
|     ok abs($m->stats->{volume} - 2*40*40*40) < 1E-2, 'scale_xyz'; | ||||
|      | ||||
|     $m->translate(5,10,0); | ||||
|  | @ -51,7 +51,7 @@ my $cube = { | |||
|      | ||||
|     is_deeply $m->size, [80,40,40], 'size'; | ||||
|      | ||||
|     $m->scale_xyz([0.5,1,1]); | ||||
|     $m->scale_xyz(Slic3r::Pointf3->new(0.5,1,1)); | ||||
|     $m->rotate(45, Slic3r::Point->new(20,20)); | ||||
|     ok abs($m->size->[0] - sqrt(2)*40) < 1E-4, 'rotate'; | ||||
|      | ||||
|  |  | |||
|  | @ -4,7 +4,7 @@ use strict; | |||
| use warnings; | ||||
| 
 | ||||
| use Slic3r::XS; | ||||
| use Test::More tests => 3; | ||||
| use Test::More tests => 5; | ||||
| 
 | ||||
| { | ||||
|     my @points = ( | ||||
|  | @ -17,4 +17,11 @@ use Test::More tests => 3; | |||
|     is_deeply $bb->max_point->pp, [500,200], 'max_point'; | ||||
| } | ||||
| 
 | ||||
| { | ||||
|     my $bb = Slic3r::Geometry::BoundingBox->new; | ||||
|     $bb->merge_point(Slic3r::Point->new(10, 10)); | ||||
|     is_deeply $bb->min_point->pp, [10,10], 'min_point equals to the only defined point'; | ||||
|     is_deeply $bb->max_point->pp, [10,10], 'max_point equals to the only defined point'; | ||||
| } | ||||
| 
 | ||||
| __END__ | ||||
|  |  | |||
|  | @ -7,6 +7,7 @@ | |||
| %} | ||||
| 
 | ||||
| %name{Slic3r::Geometry::BoundingBox} class BoundingBox { | ||||
|     BoundingBox(); | ||||
|     ~BoundingBox(); | ||||
|     Clone<BoundingBox> clone() | ||||
|         %code{% RETVAL = THIS; %}; | ||||
|  | @ -41,6 +42,7 @@ new_from_points(CLASS, points) | |||
| }; | ||||
| 
 | ||||
| %name{Slic3r::Geometry::BoundingBoxf} class BoundingBoxf { | ||||
|     BoundingBoxf(); | ||||
|     ~BoundingBoxf(); | ||||
|     Clone<BoundingBoxf> clone() | ||||
|         %code{% RETVAL = THIS; %}; | ||||
|  | @ -76,6 +78,7 @@ new_from_points(CLASS, points) | |||
| }; | ||||
| 
 | ||||
| %name{Slic3r::Geometry::BoundingBoxf3} class BoundingBoxf3 { | ||||
|     BoundingBoxf3(); | ||||
|     ~BoundingBoxf3(); | ||||
|     Clone<BoundingBoxf3> clone() | ||||
|         %code{% RETVAL = THIS; %}; | ||||
|  |  | |||
|  | @ -55,12 +55,21 @@ | |||
|     // void duplicate_objects(size_t copies_num, coordf_t distance, const BoundingBox &bb); | ||||
|     // void arrange_objects(coordf_t distance, const BoundingBox &bb); | ||||
|     // void duplicate(size_t copies_num, coordf_t distance, const BoundingBox &bb); | ||||
|     bool has_objects_with_no_instances() const; | ||||
|     // void bounding_box(BoundingBox* bb) const; | ||||
|     // void center_instances_around_point(const Pointf &point); | ||||
|     // void align_instances_to_origin(); | ||||
|     // void translate(coordf_t x, coordf_t y, coordf_t z); | ||||
|     // void mesh(TriangleMesh* mesh) const; | ||||
|     bool has_objects_with_no_instances(); | ||||
|     bool add_default_instances(); | ||||
|     BoundingBoxf3* bounding_box() | ||||
|         %code%{ | ||||
|             RETVAL = new BoundingBoxf3(); | ||||
|             THIS->bounding_box(RETVAL); | ||||
|         %}; | ||||
|     void center_instances_around_point(Pointf* point) | ||||
|         %code%{ THIS->center_instances_around_point(*point); %}; | ||||
|     void align_instances_to_origin(); | ||||
|     void translate(double x, double y, double z); | ||||
|     TriangleMesh* mesh() | ||||
|         %code%{ RETVAL = new TriangleMesh(); THIS->mesh(RETVAL); %}; | ||||
|     TriangleMesh* raw_mesh() | ||||
|         %code%{ RETVAL = new TriangleMesh(); THIS->raw_mesh(RETVAL); %}; | ||||
|     // void split_meshes(); | ||||
|     // std::string get_material_name(t_model_material_id material_id); | ||||
| 
 | ||||
|  | @ -107,8 +116,21 @@ ModelMaterial::attributes() | |||
|         %code%{ RETVAL = &THIS->instances; %}; | ||||
|      | ||||
|     void invalidate_bounding_box(); | ||||
|     void update_bounding_box(); | ||||
|     TriangleMesh* mesh() | ||||
|         %code%{ RETVAL = new TriangleMesh(); THIS->mesh(RETVAL); %}; | ||||
|     TriangleMesh* raw_mesh() | ||||
|         %code%{ RETVAL = new TriangleMesh(); THIS->raw_mesh(RETVAL); %}; | ||||
|     BoundingBoxf3* raw_bounding_box() | ||||
|         %code%{ | ||||
|             RETVAL = new BoundingBoxf3(); | ||||
|             THIS->raw_bounding_box(RETVAL); | ||||
|         %}; | ||||
|     BoundingBoxf3* instance_bounding_box(int idx) | ||||
|         %code%{ | ||||
|             RETVAL = new BoundingBoxf3(); | ||||
|             THIS->instance_bounding_box(idx, RETVAL); | ||||
|         %}; | ||||
| 
 | ||||
|     Ref<BoundingBoxf3> _bounding_box(BoundingBoxf3* new_bbox = NULL) | ||||
|         %code{% | ||||
|  | @ -123,6 +145,11 @@ ModelMaterial::attributes() | |||
| 
 | ||||
|             RETVAL = &THIS->_bounding_box; | ||||
|         %}; | ||||
|     BoundingBoxf3* bounding_box() | ||||
|         %code%{ | ||||
|             RETVAL = new BoundingBoxf3(); | ||||
|             THIS->bounding_box(RETVAL); | ||||
|         %}; | ||||
| 
 | ||||
|     %name{_add_volume} Ref<ModelVolume> add_volume(TriangleMesh* mesh) | ||||
|         %code%{ RETVAL = THIS->add_volume(*mesh); %}; | ||||
|  | @ -131,6 +158,8 @@ ModelMaterial::attributes() | |||
| 
 | ||||
|     void delete_volume(size_t idx); | ||||
|     void clear_volumes(); | ||||
|     int volumes_count() | ||||
|         %code%{ RETVAL = THIS->volumes.size(); %}; | ||||
| 
 | ||||
|     %name{_add_instance} Ref<ModelInstance> add_instance(); | ||||
|     Ref<ModelInstance> _add_instance_clone(ModelInstance* other) | ||||
|  | @ -163,6 +192,20 @@ ModelMaterial::attributes() | |||
|         %code%{ RETVAL = &THIS->origin_translation; %}; | ||||
|     void set_origin_translation(Pointf* point) | ||||
|         %code%{ THIS->origin_translation = *point; %}; | ||||
|      | ||||
|     bool needed_repair() const; | ||||
|     int materials_count() const; | ||||
|     int facets_count(); | ||||
|     void center_around_origin(); | ||||
|     void translate(double x, double y, double z); | ||||
|     void scale_xyz(Pointf3* versor) | ||||
|         %code{% THIS->scale(*versor); %}; | ||||
|      | ||||
|     Model* cut(double z) | ||||
|         %code%{ | ||||
|             RETVAL = new Model(); | ||||
|             THIS->cut(z, RETVAL); | ||||
|         %}; | ||||
| }; | ||||
| 
 | ||||
| 
 | ||||
|  |  | |||
|  | @ -17,8 +17,8 @@ | |||
|     void repair(); | ||||
|     void WriteOBJFile(char* output_file); | ||||
|     void scale(float factor); | ||||
|     void scale_xyz(std::vector<double> versor) | ||||
|         %code{% THIS->scale(versor); %}; | ||||
|     void scale_xyz(Pointf3* versor) | ||||
|         %code{% THIS->scale(*versor); %}; | ||||
|     void translate(float x, float y, float z); | ||||
|     void rotate_x(float angle); | ||||
|     void rotate_y(float angle); | ||||
|  | @ -38,8 +38,13 @@ | |||
|             RETVAL = new BoundingBoxf3(); | ||||
|             THIS->bounding_box(RETVAL); | ||||
|         %}; | ||||
|     int facets_count() | ||||
|         %code{% RETVAL = THIS->stl.stats.number_of_facets; %}; | ||||
|     Pointf3* center() | ||||
|         %code{% | ||||
|             BoundingBoxf3 bb; | ||||
|             THIS->bounding_box(&bb); | ||||
|             RETVAL = new Pointf3(bb.center()); | ||||
|         %}; | ||||
|     int facets_count(); | ||||
|     void reset_repair_stats(); | ||||
| %{ | ||||
| 
 | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Alessandro Ranellucci
						Alessandro Ranellucci