ENH: merge tree support layers to support layers

Will greately reduce repeated codes.

Change-Id: I506a97a907b5b393fe41e13ae53e2f7c9247c4c5
This commit is contained in:
Arthur 2022-12-09 14:08:30 +08:00 committed by Lane.Wei
parent b6ef31f7b9
commit 646b259972
11 changed files with 123 additions and 624 deletions

View File

@ -165,17 +165,6 @@ static Polygons top_level_outer_brim_islands(const ConstPrintObjectPtrs &top_lev
}
}
// BBS
if (!object->tree_support_layers().empty()) {
for (const ExPolygon& ex_poly : object->tree_support_layers().front()->lslices) {
Polygons contour_offset = offset(ex_poly.contour, brim_object_gap, ClipperLib::jtSquare);
for (Polygon& poly : contour_offset)
poly.douglas_peucker(scaled_resolution);
polygons_append(islands_object, std::move(contour_offset));
}
}
for (const PrintInstance &instance : object->instances())
append_and_translate(islands, islands_object, instance);
}
@ -248,19 +237,6 @@ static ExPolygons top_level_outer_brim_area(const Print &print
}
}
// BBS
if (!object->tree_support_layers().empty()) {
for (const ExPolygon& ex_poly : object->tree_support_layers().front()->lslices) {
if ((brim_type == BrimType::btOuterOnly || brim_type == BrimType::btOuterAndInner || brim_type == BrimType::btAutoBrim) && is_top_outer_brim)
append(brim_area_object, diff_ex(offset(ex_poly.contour, brim_width + brim_object_gap, jtRound, scaled_resolution), offset(ex_poly.contour, brim_object_gap)));
if (brim_type != BrimType::btNoBrim)
append(no_brim_area_object, offset_ex(ExPolygon(ex_poly.contour), brim_object_gap));
no_brim_area_object.emplace_back(ex_poly.contour);
}
}
for (const PrintInstance &instance : object->instances()) {
append_and_translate(brim_area, brim_area_object, instance);
append_and_translate(no_brim_area, no_brim_area_object, instance);
@ -360,21 +336,6 @@ static ExPolygons top_level_outer_brim_area(const Print& print, const ConstPrint
}
}
// BBS
if (!object->tree_support_layers().empty()) {
for (const ExPolygon& ex_poly : object->tree_support_layers().front()->lslices) {
if ((brim_type == BrimType::btOuterOnly || brim_type == BrimType::btOuterAndInner || brim_type == BrimType::btAutoBrim) && is_top_outer_brim)
append(brim_area_support, diff_ex(offset(ex_poly.contour, brim_width, jtRound, SCALED_RESOLUTION), offset(ex_poly.contour, 0)));
if (brim_type == BrimType::btOuterOnly || brim_type == BrimType::btNoBrim)
append(no_brim_area_support, offset_ex(ex_poly.holes, -no_brim_offset));
if (brim_type != BrimType::btNoBrim)
append(no_brim_area_support, offset_ex(ex_poly.contour, 0));
no_brim_area_support.emplace_back(ex_poly.contour);
}
}
brimToWrite.at(object->id()).sup = false;
for (const PrintInstance& instance : object->instances()) {
if (!brim_area_support.empty())
@ -543,26 +504,6 @@ static ExPolygons inner_brim_area(const Print& print, const ConstPrintObjectPtrs
no_brim_area_support.emplace_back(support_contour);
}
}
// BBS
if (!object->tree_support_layers().empty()) {
for (const ExPolygon& ex_poly : object->tree_support_layers().front()->lslices) {
if (brim_type == BrimType::btOuterOnly || brim_type == BrimType::btOuterAndInner || brim_type == BrimType::btAutoBrim) {
if (!top_outer_brim)
append(brim_area_support, diff_ex(offset_ex(ex_poly.contour, brim_width + brim_offset, jtRound, SCALED_RESOLUTION), offset_ex(ex_poly.contour, brim_offset)));
}
if (brim_type == BrimType::btInnerOnly || brim_type == BrimType::btOuterAndInner)
append(brim_area_support, diff_ex(offset_ex(ex_poly.holes, -brim_offset), offset_ex(ex_poly.holes, -brim_width - brim_offset)));
if (brim_type == BrimType::btInnerOnly || brim_type == BrimType::btNoBrim)
append(no_brim_area_support, diff_ex(offset(ex_poly.contour, no_brim_offset), ex_poly.holes));
if (brim_type == BrimType::btOuterOnly || brim_type == BrimType::btNoBrim)
append(no_brim_area_support, offset_ex(ex_poly.holes, -no_brim_offset));
append(holes_support, ex_poly.holes);
if (brim_type != BrimType::btNoBrim)
append(no_brim_area_support, offset_ex(ex_poly.contour, 0));
no_brim_area_support.emplace_back(ex_poly.contour);
}
}
}
brimToWrite.at(object->id()).sup = false;
for (const PrintInstance& instance : object->instances()) {
@ -988,7 +929,7 @@ static ExPolygons outer_inner_brim_area(const Print& print,
support_material_extruder = printExtruders.front() + 1;
}
if (support_material_extruder == extruderNo && brimToWrite.at(object->id()).sup) {
if (!object->support_layers().empty()) {
if (!object->support_layers().empty() && object->support_layers().front()->support_type==stInnerNormal) {
for (const Polygon& support_contour : object->support_layers().front()->support_fills.polygons_covered_by_spacing()) {
// Brim will not be generated for supports
/*
@ -1002,8 +943,8 @@ static ExPolygons outer_inner_brim_area(const Print& print,
}
}
// BBS
if (!object->tree_support_layers().empty()) {
for (const ExPolygon& ex_poly : object->tree_support_layers().front()->lslices) {
if (!object->support_layers().empty() && object->support_layers().front()->support_type == stInnerTree) {
for (const ExPolygon &ex_poly : object->support_layers().front()->lslices) {
// BBS: additional brim width will be added if adhension area is too small without brim
float brim_width_mod = ex_poly.area() / ex_poly.contour.length() < scaled_half_min_adh_length
&& brim_width < scaled_flow_width ? brim_width + scaled_additional_brim_width : brim_width;
@ -1222,13 +1163,6 @@ static void make_inner_island_brim(const Print& print, const ConstPrintObjectPtr
}
}
if (!object->tree_support_layers().empty()) {
for (const ExPolygon& ex_poly : object->tree_support_layers().front()->lslices) {
Polygon counter = ex_poly.contour;
save_polygon_if_is_inner_island(holes_area, counter, hole_island_pair);
}
}
//BBS: 3 generate loops, only save part of loop which inside hole
const float brim_offset = scale_(object->config().brim_object_gap.value);
const float brim_width = scale_(object->config().brim_width.value);
@ -1371,13 +1305,6 @@ static void make_inner_island_brim(const Print& print, const ConstPrintObjectPtr
}
}
if (!object->tree_support_layers().empty()) {
for (const ExPolygon& ex_poly : object->tree_support_layers().front()->lslices) {
Polygon counter = ex_poly.contour;
save_polygon_if_is_inner_island(holes_area, counter, hole_island_pair_supports);
}
}
//BBS: 3 generate loops, only save part of loop which inside hole
const float brim_offset = scale_(object->config().brim_object_gap.value);
const float brim_width = floor(scale_(object->config().brim_width.value) / 2 / flow.scaled_spacing()) * 2 * flow.scaled_spacing();
@ -1665,13 +1592,6 @@ void make_brim(const Print& print, PrintTryCancel try_cancel, Polygons& islands_
ex_poly_translated.translate(instance.shift.x(), instance.shift.y());
bbx.merge(get_extents(ex_poly_translated));
}
if (!object->tree_support_layers().empty())
for (const Polygon& ex_poly : object->tree_support_layers().front()->support_fills.polygons_covered_by_spacing())
for (const PrintInstance& instance : object->instances()) {
auto ex_poly_translated = ex_poly;
ex_poly_translated.translate(instance.shift.x(), instance.shift.y());
bbx.merge(get_extents(ex_poly_translated));
}
if (supportBrimAreaMap.find(printObjID) != supportBrimAreaMap.end()) {
for (const ExPolygon& ex_poly : supportBrimAreaMap.at(printObjID))
bbx.merge(get_extents(ex_poly.contour));

View File

@ -608,7 +608,7 @@ bool GCode::gcode_label_objects = false;
std::vector<GCode::LayerToPrint> GCode::collect_layers_to_print(const PrintObject& object)
{
std::vector<GCode::LayerToPrint> layers_to_print;
layers_to_print.reserve(object.layers().size() + object.support_layers().size() + object.tree_support_layers().size());
layers_to_print.reserve(object.layers().size() + object.support_layers().size());
/*
// Calculate a minimum support layer height as a minimum over all extruders, but not smaller than 10um.
@ -631,9 +631,8 @@ std::vector<GCode::LayerToPrint> GCode::collect_layers_to_print(const PrintObjec
// Pair the object layers with the support layers by z.
size_t idx_object_layer = 0;
size_t idx_support_layer = 0;
size_t idx_tree_support_layer = 0;
const LayerToPrint* last_extrusion_layer = nullptr;
while (idx_object_layer < object.layers().size() || idx_support_layer < object.support_layers().size() || idx_tree_support_layer < object.tree_support_layers().size()) {
while (idx_object_layer < object.layers().size() || idx_support_layer < object.support_layers().size()) {
LayerToPrint layer_to_print;
double print_z_min = std::numeric_limits<double>::max();
if (idx_object_layer < object.layers().size()) {
@ -646,11 +645,6 @@ std::vector<GCode::LayerToPrint> GCode::collect_layers_to_print(const PrintObjec
print_z_min = std::min(print_z_min, layer_to_print.support_layer->print_z);
}
if (idx_tree_support_layer < object.tree_support_layers().size()) {
layer_to_print.tree_support_layer = object.tree_support_layers()[idx_tree_support_layer++];
print_z_min = std::min(print_z_min, layer_to_print.tree_support_layer->print_z);
}
if (layer_to_print.object_layer && layer_to_print.object_layer->print_z > print_z_min + EPSILON) {
layer_to_print.object_layer = nullptr;
--idx_object_layer;
@ -661,17 +655,11 @@ std::vector<GCode::LayerToPrint> GCode::collect_layers_to_print(const PrintObjec
--idx_support_layer;
}
if (layer_to_print.tree_support_layer && layer_to_print.tree_support_layer->print_z > print_z_min + EPSILON) {
layer_to_print.tree_support_layer = nullptr;
--idx_tree_support_layer;
}
layer_to_print.original_object = &object;
layers_to_print.push_back(layer_to_print);
bool has_extrusions = (layer_to_print.object_layer && layer_to_print.object_layer->has_extrusions())
|| (layer_to_print.support_layer && layer_to_print.support_layer->has_extrusions()
|| (layer_to_print.tree_support_layer && layer_to_print.tree_support_layer->has_extrusions()));
|| (layer_to_print.support_layer && layer_to_print.support_layer->has_extrusions());
// Check that there are extrusions on the very first layer. The case with empty
// first layer may result in skirt/brim in the air and maybe other issues.
@ -683,13 +671,12 @@ std::vector<GCode::LayerToPrint> GCode::collect_layers_to_print(const PrintObjec
// In case there are extrusions on this layer, check there is a layer to lay it on.
if ((layer_to_print.object_layer && layer_to_print.object_layer->has_extrusions())
// Allow empty support layers, as the support generator may produce no extrusions for non-empty support regions.
|| (layer_to_print.support_layer /* && layer_to_print.support_layer->has_extrusions() */)
|| (layer_to_print.tree_support_layer)) {
|| (layer_to_print.support_layer /* && layer_to_print.support_layer->has_extrusions() */)) {
double top_cd = object.config().support_top_z_distance;
//double bottom_cd = object.config().support_bottom_z_distance == 0. ? top_cd : object.config().support_bottom_z_distance;
double bottom_cd = top_cd;
double extra_gap = ((layer_to_print.support_layer || layer_to_print.tree_support_layer) ? bottom_cd : top_cd);
double extra_gap = (layer_to_print.support_layer ? bottom_cd : top_cd);
double maximal_print_z = (last_extrusion_layer ? last_extrusion_layer->print_z() : 0.)
+ layer_to_print.layer()->height
@ -1316,8 +1303,7 @@ void GCode::_do_export(Print& print, GCodeOutputStream &file, ThumbnailsGenerato
zs.reserve(zs.size() + object->layers().size() + object->support_layers().size());
for (auto layer : object->layers())
zs.push_back(layer->print_z);
for (auto layer : object->support_layers())
zs.push_back(layer->print_z);
for (auto layer : object->support_layers()) zs.push_back(layer->print_z);
}
std::sort(zs.begin(), zs.end());
m_layer_count = (unsigned int)(std::unique(zs.begin(), zs.end()) - zs.begin());
@ -2371,7 +2357,6 @@ GCode::LayerResult GCode::process_layer(
// First object, support and raft layer, if available.
const Layer *object_layer = nullptr;
const SupportLayer *support_layer = nullptr;
const TreeSupportLayer* tree_support_layer = nullptr;
const SupportLayer *raft_layer = nullptr;
for (const LayerToPrint &l : layers) {
if (l.object_layer && ! object_layer)
@ -2382,16 +2367,6 @@ GCode::LayerResult GCode::process_layer(
if (! raft_layer && support_layer->id() < support_layer->object()->slicing_parameters().raft_layers())
raft_layer = support_layer;
}
if (l.tree_support_layer) {
if (!tree_support_layer)
tree_support_layer = l.tree_support_layer;
// BBS: to be checked.
#if 0
if (!raft_layer && tree_support_layer->id() < tree_support_layer->object()->slicing_parameters().raft_layers())
raft_layer = tree_support_layer;
#endif
}
}
const Layer* layer_ptr = nullptr;
@ -2399,8 +2374,6 @@ GCode::LayerResult GCode::process_layer(
layer_ptr = object_layer;
else if (support_layer != nullptr)
layer_ptr = support_layer;
else
layer_ptr = tree_support_layer;
const Layer& layer = *layer_ptr;
GCode::LayerResult result { {}, layer.id(), false, last_layer };
if (layer_tools.extruders.empty())
@ -2421,7 +2394,7 @@ GCode::LayerResult GCode::process_layer(
// Check whether it is possible to apply the spiral vase logic for this layer.
// Just a reminder: A spiral vase mode is allowed for a single object, single material print only.
m_enable_loop_clipping = true;
if (m_spiral_vase && layers.size() == 1 && support_layer == nullptr && tree_support_layer == nullptr) {
if (m_spiral_vase && layers.size() == 1 && support_layer == nullptr) {
bool enable = (layer.id() > 0 || !print.has_brim()) && (layer.id() >= (size_t)print.config().skirt_height.value && ! print.has_infinite_skirt());
if (enable) {
for (const LayerRegion *layer_region : layer.regions())
@ -2628,90 +2601,6 @@ GCode::LayerResult GCode::process_layer(
}
}
// BBS
if (layer_to_print.tree_support_layer != nullptr) {
const TreeSupportLayer& tree_support_layer = *layer_to_print.tree_support_layer;
const PrintObject& object = *layer_to_print.original_object;
if (!tree_support_layer.support_fills.entities.empty()) {
ExtrusionRole role = tree_support_layer.support_fills.role();
bool has_support = role == erMixed || role == erSupportMaterial || role == erSupportTransition;
bool has_interface = role == erMixed || role == erSupportMaterialInterface;
// Extruder ID of the support base. -1 if "don't care".
unsigned int support_extruder = object.config().support_filament.value - 1;
// Shall the support be printed with the active extruder, preferably with non-soluble, to avoid tool changes?
bool support_dontcare = object.config().support_filament.value == 0;
// Extruder ID of the support interface. -1 if "don't care".
unsigned int interface_extruder = object.config().support_interface_filament.value - 1;
// Shall the support interface be printed with the active extruder, preferably with non-soluble, to avoid tool changes?
bool interface_dontcare = object.config().support_interface_filament.value == 0;
// BBS: apply wiping overridden extruders
WipingExtrusions& wiping_extrusions = const_cast<LayerTools&>(layer_tools).wiping_extrusions();
if (support_dontcare) {
int extruder_override = wiping_extrusions.get_support_extruder_overrides(&object);
if (extruder_override >= 0) {
support_extruder = extruder_override;
support_dontcare = false;
}
}
if (interface_dontcare) {
int extruder_override = wiping_extrusions.get_support_interface_extruder_overrides(&object);
if (extruder_override >= 0) {
interface_extruder = extruder_override;
interface_dontcare = false;
}
}
// BBS: try to print support base with a filament other than interface filament
if (support_dontcare && !interface_dontcare) {
unsigned int dontcare_extruder = first_extruder_id;
for (unsigned int extruder_id : layer_tools.extruders) {
if (print.config().filament_soluble.get_at(extruder_id)) continue;
if (extruder_id == interface_extruder) continue;
dontcare_extruder = extruder_id;
break;
}
if (support_dontcare) support_extruder = dontcare_extruder;
}
else if (support_dontcare || interface_dontcare) {
// Some support will be printed with "don't care" material, preferably non-soluble.
// Is the current extruder assigned a soluble filament?
unsigned int dontcare_extruder = first_extruder_id;
if (print.config().filament_soluble.get_at(dontcare_extruder)) {
// The last extruder printed on the previous layer extrudes soluble filament.
// Try to find a non-soluble extruder on the same layer.
for (unsigned int extruder_id : layer_tools.extruders)
if (!print.config().filament_soluble.get_at(extruder_id)) {
dontcare_extruder = extruder_id;
break;
}
}
if (support_dontcare)
support_extruder = dontcare_extruder;
if (interface_dontcare)
interface_extruder = dontcare_extruder;
}
// Both the support and the support interface are printed with the same extruder, therefore
// the interface may be interleaved with the support base.
bool single_extruder = !has_support || support_extruder == interface_extruder;
// Assign an extruder to the base.
ObjectByExtruder& obj = object_by_extruder(by_extruder, has_support ? support_extruder : interface_extruder, &layer_to_print - layers.data(), layers.size());
obj.support = &tree_support_layer.support_fills;
obj.support_extrusion_role = single_extruder ? erMixed : erSupportMaterial;
if (!single_extruder && has_interface) {
ObjectByExtruder& obj_interface = object_by_extruder(by_extruder, interface_extruder, &layer_to_print - layers.data(), layers.size());
obj_interface.support = &tree_support_layer.support_fills;
obj_interface.support_extrusion_role = erSupportMaterialInterface;
}
}
}
if (layer_to_print.object_layer != nullptr) {
const Layer &layer = *layer_to_print.object_layer;
// We now define a strategy for building perimeters and fills. The separation
@ -2930,12 +2819,7 @@ GCode::LayerResult GCode::process_layer(
m_last_obj_copy = this_object_copy;
this->set_origin(unscale(offset));
if (instance_to_print.object_by_extruder.support != nullptr) {
if (layers[instance_to_print.layer_id].support_layer) {
m_layer = layers[instance_to_print.layer_id].support_layer;
}
else {
m_layer = layers[instance_to_print.layer_id].tree_support_layer;
}
m_layer = layers[instance_to_print.layer_id].support_layer;
m_object_layer_over_raft = false;
//BBS: print supports' brims first
@ -3854,10 +3738,9 @@ bool GCode::needs_retraction(const Polyline &travel, ExtrusionRole role)
return false;
//reduce the retractions in lightning infills for tree support
const TreeSupportLayer* ts_layer = dynamic_cast<const TreeSupportLayer*>(m_layer);
if (ts_layer != NULL)
for (auto& area : ts_layer->base_areas)
if(area.contains(travel))
if (support_layer != NULL && support_layer->support_type==stInnerTree)
for (auto &area : support_layer->base_areas)
if (area.contains(travel))
return false;
}

View File

@ -201,10 +201,9 @@ public:
// public, so that it could be accessed by free helper functions from GCode.cpp
struct LayerToPrint
{
LayerToPrint() : object_layer(nullptr), support_layer(nullptr), tree_support_layer(nullptr), original_object(nullptr) {}
LayerToPrint() : object_layer(nullptr), support_layer(nullptr), original_object(nullptr) {}
const Layer* object_layer;
const SupportLayer* support_layer;
const TreeSupportLayer* tree_support_layer;
const PrintObject* original_object; //BBS: used for shared object logic
const Layer* layer() const
{
@ -214,9 +213,6 @@ public:
if (support_layer != nullptr)
return support_layer;
if (tree_support_layer != nullptr)
return tree_support_layer;
return nullptr;
}
@ -238,10 +234,6 @@ public:
count++;
}
if (tree_support_layer != nullptr) {
sum_z += tree_support_layer->print_z;
count++;
}
return sum_z / count;
}
};

View File

@ -1135,8 +1135,7 @@ Polyline AvoidCrossingPerimeters::travel_to(const GCode &gcodegen, const Point &
const ExPolygons &lslices = gcodegen.layer()->lslices;
const std::vector<BoundingBox> &lslices_bboxes = gcodegen.layer()->lslices_bboxes;
bool is_support_layer = (dynamic_cast<const SupportLayer *>(gcodegen.layer()) != nullptr) ||
(dynamic_cast<const TreeSupportLayer *>(gcodegen.layer()) != nullptr);
bool is_support_layer = (dynamic_cast<const SupportLayer *>(gcodegen.layer()) != nullptr);
if (!use_external && (is_support_layer || (!lslices.empty() && !any_expolygon_contains(lslices, lslices_bboxes, m_grid_lslice, travel)))) {
// Initialize m_internal only when it is necessary.
if (m_internal.boundaries.empty())

View File

@ -175,10 +175,6 @@ ToolOrdering::ToolOrdering(const Print &print, unsigned int first_extruder, bool
for (auto layer : object->support_layers())
zs.emplace_back(layer->print_z);
// BBS
for (auto layer : object->tree_support_layers())
zs.emplace_back(layer->print_z);
// Find first object layer that is not empty and save its print_z
for (const Layer* layer : object->layers())
if (layer->has_extrusions()) {
@ -348,24 +344,6 @@ void ToolOrdering::collect_extruders(const PrintObject &object, const std::vecto
}
}
// BBS
for (auto tree_support_layer : object.tree_support_layers()) {
LayerTools &layer_tools = this->tools_for_layer(tree_support_layer->print_z);
ExtrusionRole role = tree_support_layer->support_fills.role();
bool has_support = role == erMixed || role == erSupportMaterial || role == erSupportTransition;;
bool has_interface = role == erMixed || role == erSupportMaterialInterface;
unsigned int extruder_support = object.config().support_filament.value;
unsigned int extruder_interface = object.config().support_interface_filament.value;
if (has_support)
layer_tools.extruders.push_back(extruder_support);
if (has_interface)
layer_tools.extruders.push_back(extruder_interface);
if (has_support || has_interface) {
layer_tools.has_support = true;
layer_tools.wiping_extrusions().is_support_overriddable_and_mark(role, object);
}
}
// Extruder overrides are ordered by print_z.
std::vector<std::pair<double, unsigned int>>::const_iterator it_per_layer_extruder_override;
it_per_layer_extruder_override = per_layer_extruder_switches.begin();
@ -1042,10 +1020,9 @@ float WipingExtrusions::mark_wiping_extrusions(const Print& print, unsigned int
if (object->config().flush_into_support) {
auto& object_config = object->config();
const SupportLayer* this_support_layer = object->get_support_layer_at_printz(lt.print_z, EPSILON);
const TreeSupportLayer* this_tree_support_layer = object->get_tree_support_layer_at_printz(lt.print_z, EPSILON);
do {
if (this_support_layer == nullptr && this_tree_support_layer == nullptr)
if (this_support_layer == nullptr)
break;
bool support_overriddable = object_config.support_filament == 0;
@ -1053,7 +1030,7 @@ float WipingExtrusions::mark_wiping_extrusions(const Print& print, unsigned int
if (!support_overriddable && !support_intf_overriddable)
break;
auto& entities = this_support_layer != nullptr ? this_support_layer->support_fills.entities : this_tree_support_layer->support_fills.entities;
auto &entities = this_support_layer->support_fills.entities;
if (support_overriddable && !is_support_overridden(object)) {
set_support_extruder_override(object, copy, new_extruder, num_of_copies);
for (const ExtrusionEntity* ee : entities) {

View File

@ -211,6 +211,11 @@ private:
LayerRegionPtrs m_regions;
};
enum SupportInnerType {
stInnerNormal,
stInnerTree
};
class SupportLayer : public Layer
{
public:
@ -219,6 +224,10 @@ public:
ExPolygonCollection support_islands;
// Extrusion paths for the support base and for the support interface and contacts.
ExtrusionEntityCollection support_fills;
SupportInnerType support_type = stInnerNormal;
// for tree supports
ExPolygons base_areas;
// Is there any valid extrusion assigned to this LayerRegion?
@ -231,33 +240,23 @@ public:
protected:
friend class PrintObject;
friend class TreeSupport;
// The constructor has been made public to be able to insert additional support layers for the skirt or a wipe tower
// between the raft and the object first layer.
SupportLayer(size_t id, size_t interface_id, PrintObject *object, coordf_t height, coordf_t print_z, coordf_t slice_z) :
Layer(id, object, height, print_z, slice_z), m_interface_id(interface_id) {}
Layer(id, object, height, print_z, slice_z), m_interface_id(interface_id), support_type(stInnerNormal) {}
virtual ~SupportLayer() = default;
size_t m_interface_id;
};
class TreeSupportLayer : public Layer
{
public:
ExtrusionEntityCollection support_fills;
ExPolygons overhang_areas;
ExPolygons roof_areas;
ExPolygons roof_1st_layer; // the layer just below roof. When working with PolySupport, this layer should be printed with regular material
ExPolygons floor_areas;
ExPolygons base_areas;
ExPolygons roof_gap_areas; // the areas in the gap between support roof and overhang
enum AreaType {
BaseType=0,
RoofType=1,
FloorType=2,
Roof1stLayer=3
};
// for tree support
ExPolygons overhang_areas;
ExPolygons roof_areas;
ExPolygons roof_1st_layer; // the layer just below roof. When working with PolySupport, this layer should be printed with regular material
ExPolygons floor_areas;
ExPolygons roof_gap_areas; // the areas in the gap between support roof and overhang
enum AreaType { BaseType = 0, RoofType = 1, FloorType = 2, Roof1stLayer = 3 };
struct AreaGroup
{
ExPolygon *area;
@ -265,23 +264,9 @@ public:
coordf_t dist_to_top; // mm dist to top
AreaGroup(ExPolygon *a, int t, coordf_t d) : area(a), type(t), dist_to_top(d) {}
};
std::vector<AreaGroup> area_groups;
enum OverhangType {
Detected=0,
Enforced
};
enum OverhangType { Detected = 0, Enforced };
std::vector<AreaGroup> area_groups;
std::map<const ExPolygon *, OverhangType> overhang_types;
virtual bool has_extrusions() const { return !support_fills.empty(); }
void simplify_support_extrusion_path() { this->simplify_support_entity_collection(&support_fills);}
protected:
friend class PrintObject;
TreeSupportLayer(size_t id, PrintObject* object, coordf_t height, coordf_t print_z, coordf_t slice_z) :
Layer(id, object, height, print_z, slice_z) {}
virtual ~TreeSupportLayer() = default;
};
template<typename LayerContainer>

View File

@ -1283,7 +1283,6 @@ void PrintObject::clear_shared_object()
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << boost::format(": this=%1%, clear previous shared object data %2%")%this %m_shared_object;
m_layers.clear();
m_support_layers.clear();
m_tree_support_layers.clear();
m_shared_object = nullptr;
@ -1296,7 +1295,6 @@ void PrintObject::copy_layers_from_shared_object()
if (m_shared_object) {
m_layers.clear();
m_support_layers.clear();
m_tree_support_layers.clear();
firstLayerObjSliceByVolume.clear();
firstLayerObjSliceByGroups.clear();
@ -1304,7 +1302,6 @@ void PrintObject::copy_layers_from_shared_object()
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << boost::format(": this=%1%, copied layers from object %2%")%this%m_shared_object;
m_layers = m_shared_object->layers();
m_support_layers = m_shared_object->support_layers();
m_tree_support_layers = m_shared_object->tree_support_layers();
firstLayerObjSliceByVolume = m_shared_object->firstLayerObjSlice();
firstLayerObjSliceByGroups = m_shared_object->firstLayerObjGroups();
@ -1706,13 +1703,6 @@ void Print::_make_skirt()
break;
layer->support_fills.collect_points(object_points);
}
// BBS
for (const TreeSupportLayer* layer : object->m_tree_support_layers) {
if (layer->print_z > skirt_height_z)
break;
layer->support_fills.collect_points(object_points);
}
object_convex_hulls.insert({ object, Slic3r::Geometry::convex_hull(object_points) });
@ -1859,12 +1849,12 @@ Polygons Print::first_layer_islands() const
Polygons object_islands;
for (ExPolygon &expoly : object->m_layers.front()->lslices)
object_islands.push_back(expoly.contour);
if (! object->support_layers().empty())
object->support_layers().front()->support_fills.polygons_covered_by_spacing(object_islands, float(SCALED_EPSILON));
if (! object->tree_support_layers().empty()) {
ExPolygons& expolys_first_layer = object->m_tree_support_layers.front()->lslices;
for (ExPolygon &expoly : expolys_first_layer) {
object_islands.push_back(expoly.contour);
if (!object->support_layers().empty()) {
if (object->support_layers().front()->support_type==stInnerNormal)
object->support_layers().front()->support_fills.polygons_covered_by_spacing(object_islands, float(SCALED_EPSILON));
else if(object->support_layers().front()->support_type==stInnerTree) {
ExPolygons &expolys_first_layer = object->m_support_layers.front()->lslices;
for (ExPolygon &expoly : expolys_first_layer) { object_islands.push_back(expoly.contour); }
}
}
islands.reserve(islands.size() + object_islands.size() * object->instances().size());
@ -2215,7 +2205,7 @@ std::string PrintStatistics::finalize_output_path(const std::string &path_in) co
#define JSON_SUPPORT_LAYER_ISLANDS "support_islands"
#define JSON_SUPPORT_LAYER_FILLS "support_fills"
#define JSON_SUPPORT_LAYER_INTERFACE_ID "interface_id"
#define JSON_SUPPORT_LAYER_TYPE "support_type"
#define JSON_LAYER_REGION_CONFIG_HASH "config_hash"
#define JSON_LAYER_REGION_SLICES "slices"
@ -2846,6 +2836,7 @@ void extract_layer(const json& layer_json, Layer& layer) {
void extract_support_layer(const json& support_layer_json, SupportLayer& support_layer) {
extract_layer(support_layer_json, support_layer);
support_layer.support_type = support_layer_json[JSON_SUPPORT_LAYER_TYPE];
//support_islands
int islands_count = support_layer_json[JSON_SUPPORT_LAYER_ISLANDS].size();
for (int islands_index = 0; islands_index < islands_count; islands_index++)
@ -2874,27 +2865,6 @@ void extract_support_layer(const json& support_layer_json, SupportLayer& support
return;
}
void extract_tree_support_layer(const json& tree_support_layer_json, TreeSupportLayer& tree_support_layer) {
extract_layer(tree_support_layer_json, tree_support_layer);
//support_fills
tree_support_layer.support_fills.no_sort = tree_support_layer_json[JSON_SUPPORT_LAYER_FILLS][JSON_EXTRUSION_NO_SORT];
int treesupport_fills_entities_count = tree_support_layer_json[JSON_SUPPORT_LAYER_FILLS][JSON_EXTRUSION_ENTITIES].size();
for (int treesupport_fills_entities_index = 0; treesupport_fills_entities_index < treesupport_fills_entities_count; treesupport_fills_entities_index++)
{
const json& extrusion_entity_json = tree_support_layer_json[JSON_SUPPORT_LAYER_FILLS][JSON_EXTRUSION_ENTITIES][treesupport_fills_entities_index];
bool ret = convert_extrusion_from_json(extrusion_entity_json, tree_support_layer.support_fills);
if (!ret) {
BOOST_LOG_TRIVIAL(error) << __FUNCTION__ << boost::format(": error parsing fills found at tree_support_layer %1%, print_z %2%")%tree_support_layer.id() %tree_support_layer.print_z;
char error_buf[1024];
::sprintf(error_buf, "Error while parsing fills at tree_support_layer %d, print_z %f", tree_support_layer.id(), tree_support_layer.print_z);
throw Slic3r::FileIOError(error_buf);
}
}
return;
}
int Print::export_cached_data(const std::string& directory, bool with_space)
{
int ret = 0;
@ -2960,7 +2930,7 @@ int Print::export_cached_data(const std::string& directory, bool with_space)
std::string file_name = directory +"/obj_"+std::to_string(arrange_order)+".json";
try {
json root_json, layers_json = json::array(), support_layers_json = json::array(), tree_support_layers_json = json::array();
json root_json, layers_json = json::array(), support_layers_json = json::array();
root_json[JSON_OBJECT_NAME] = model_obj->name;
root_json[JSON_ARRANGE_ORDER] = arrange_order;
@ -3005,6 +2975,7 @@ int Print::export_cached_data(const std::string& directory, bool with_space)
convert_layer_to_json(support_layer_json, support_layer);
support_layer_json[JSON_SUPPORT_LAYER_INTERFACE_ID] = support_layer->interface_id();
support_layer_json[JSON_SUPPORT_LAYER_TYPE] = support_layer->support_type;
//support_islands
for (const ExPolygon& support_island : support_layer->support_islands.expolygons) {
@ -3068,136 +3039,6 @@ int Print::export_cached_data(const std::string& directory, bool with_space)
} // for each layer*/
root_json[JSON_SUPPORT_LAYERS] = std::move(support_layers_json);
//export the tree support layers
std::vector<json> tree_support_layers_json_vector(obj->tree_support_layer_count());
tbb::parallel_for(
tbb::blocked_range<size_t>(0, obj->tree_support_layer_count()),
[&tree_support_layers_json_vector, obj, convert_layer_to_json](const tbb::blocked_range<size_t>& tree_support_layer_range) {
for (size_t ts_layer_index = tree_support_layer_range.begin(); ts_layer_index < tree_support_layer_range.end(); ++ ts_layer_index) {
const TreeSupportLayer *tree_support_layer = obj->get_tree_support_layer(ts_layer_index);
json treesupport_layer_json, treesupport_fills_json, treesupportfills_entities_json = json::array();
//json overhang_areas_json = json::array(), roof_areas_json = json::array(), roof_1st_layer_json = json::array(), floor_areas_json = json::array(), base_areas_json = json::array();
convert_layer_to_json(treesupport_layer_json, tree_support_layer);
//tree_support_fills
treesupport_fills_json[JSON_EXTRUSION_NO_SORT] = tree_support_layer->support_fills.no_sort;
treesupport_fills_json[JSON_EXTRUSION_ENTITY_TYPE] = JSON_EXTRUSION_TYPE_COLLECTION;
for (const ExtrusionEntity* extrusion_entity : tree_support_layer->support_fills.entities) {
json treesupportfill_entity_json, treesupportfill_entity_paths_json = json::array();
bool ret = convert_extrusion_to_json(treesupportfill_entity_json, treesupportfill_entity_paths_json, extrusion_entity);
if (!ret)
continue;
treesupportfills_entities_json.push_back(std::move(treesupportfill_entity_json));
}
treesupport_fills_json[JSON_EXTRUSION_ENTITIES] = std::move(treesupportfills_entities_json);
treesupport_layer_json[JSON_SUPPORT_LAYER_FILLS] = std::move(treesupport_fills_json);
//following data are not needed in the later stage
//overhang_areas
/*for (const ExPolygon& overhang_area : tree_support_layer->overhang_areas) {
json overhang_area_json = overhang_area;
overhang_areas_json.push_back(std::move(overhang_area_json));
}
treesupport_layer_json["overhang_areas"] = std::move(overhang_areas_json);
//roof_areas
for (const ExPolygon& roof_area : tree_support_layer->roof_areas) {
json roof_area_json = roof_area;
roof_areas_json.push_back(std::move(roof_area_json));
}
treesupport_layer_json["roof_areas"] = std::move(roof_areas_json);
//roof_1st_layer
for (const ExPolygon& layer_poly : tree_support_layer->roof_1st_layer) {
json layer_poly_json = layer_poly;
roof_1st_layer_json.push_back(std::move(layer_poly_json));
}
treesupport_layer_json["roof_1st_layer"] = std::move(roof_1st_layer_json);
//floor_areas
for (const ExPolygon& floor_area : tree_support_layer->floor_areas) {
json floor_area_json = floor_area;
floor_areas_json.push_back(std::move(floor_area_json));
}
treesupport_layer_json["floor_areas"] = std::move(floor_areas_json);
//base_areas
for (const ExPolygon& base_area : tree_support_layer->base_areas) {
json base_area_json = base_area;
base_areas_json.push_back(std::move(base_area_json));
}
treesupport_layer_json["base_areas"] = std::move(base_areas_json);*/
tree_support_layers_json_vector[ts_layer_index] = std::move(treesupport_layer_json);
}
}
);
for (int ts_index = 0; ts_index < tree_support_layers_json_vector.size(); ts_index++) {
tree_support_layers_json.push_back(std::move(tree_support_layers_json_vector[ts_index]));
}
tree_support_layers_json_vector.clear();
#if 0
for (const TreeSupportLayer *tree_support_layer : obj->tree_support_layers()) {
json treesupport_layer_json, treesupport_fills_json, treesupportfills_entities_json = json::array();
json overhang_areas_json = json::array(), roof_areas_json = json::array(), roof_1st_layer_json = json::array(), floor_areas_json = json::array(), base_areas_json = json::array();
convert_layer_to_json(treesupport_layer_json, tree_support_layer);
//tree_support_fills
treesupport_fills_json[JSON_EXTRUSION_NO_SORT] = tree_support_layer->support_fills.no_sort;
treesupport_fills_json[JSON_EXTRUSION_ENTITY_TYPE] = JSON_EXTRUSION_TYPE_COLLECTION;
for (const ExtrusionEntity* extrusion_entity : tree_support_layer->support_fills.entities) {
json treesupportfill_entity_json, treesupportfill_entity_paths_json = json::array();
bool ret = convert_extrusion_to_json(treesupportfill_entity_json, treesupportfill_entity_paths_json, extrusion_entity);
if (!ret)
continue;
treesupportfills_entities_json.push_back(std::move(treesupportfill_entity_json));
}
treesupport_fills_json[JSON_EXTRUSION_ENTITIES] = std::move(treesupportfills_entities_json);
treesupport_layer_json[JSON_SUPPORT_LAYER_FILLS] = std::move(treesupport_fills_json);
//overhang_areas
/*for (const ExPolygon& overhang_area : tree_support_layer->overhang_areas) {
json overhang_area_json = overhang_area;
overhang_areas_json.push_back(std::move(overhang_area_json));
}
treesupport_layer_json["overhang_areas"] = std::move(overhang_areas_json);
//roof_areas
for (const ExPolygon& roof_area : tree_support_layer->roof_areas) {
json roof_area_json = roof_area;
roof_areas_json.push_back(std::move(roof_area_json));
}
treesupport_layer_json["roof_areas"] = std::move(roof_areas_json);
//roof_1st_layer
for (const ExPolygon& layer_poly : tree_support_layer->roof_1st_layer) {
json layer_poly_json = layer_poly;
roof_1st_layer_json.push_back(std::move(layer_poly_json));
}
treesupport_layer_json["roof_1st_layer"] = std::move(roof_1st_layer_json);
//floor_areas
for (const ExPolygon& floor_area : tree_support_layer->floor_areas) {
json floor_area_json = floor_area;
floor_areas_json.push_back(std::move(floor_area_json));
}
treesupport_layer_json["floor_areas"] = std::move(floor_areas_json);
//base_areas
for (const ExPolygon& base_area : tree_support_layer->base_areas) {
json base_area_json = base_area;
base_areas_json.push_back(std::move(base_area_json));
}
treesupport_layer_json["base_areas"] = std::move(base_areas_json);*/
tree_support_layers_json.push_back(std::move(treesupport_layer_json));
} // for each layer
#endif
root_json[JSON_TREE_SUPPORT_LAYERS] = std::move(tree_support_layers_json);
filename_vector.push_back(file_name);
json_vector.push_back(std::move(root_json));
@ -3276,7 +3117,6 @@ int Print::load_cached_data(const std::string& directory)
obj->clear_layers();
obj->clear_support_layers();
obj->clear_tree_support_layers();
int arrange_order = model_instance->arrange_order;
if (arrange_order <= 0) {
@ -3328,13 +3168,12 @@ int Print::load_cached_data(const std::string& directory)
std::string name = root_json.at(JSON_OBJECT_NAME);
int order = root_json.at(JSON_ARRANGE_ORDER);
int layer_count = 0, support_layer_count = 0, treesupport_layer_count = 0;
int layer_count = 0, support_layer_count = 0;
layer_count = root_json[JSON_LAYERS].size();
support_layer_count = root_json[JSON_SUPPORT_LAYERS].size();
treesupport_layer_count = root_json[JSON_TREE_SUPPORT_LAYERS].size();
BOOST_LOG_TRIVIAL(info) << __FUNCTION__<<boost::format(":will load %1%, arrange_order %2%, layer_count %3%, support_layer_count %4%, treesupport_layer_count %5%")%name %order %layer_count %support_layer_count %treesupport_layer_count;
BOOST_LOG_TRIVIAL(info) << __FUNCTION__<<boost::format(":will load %1%, arrange_order %2%, layer_count %3%, support_layer_count %4%")%name %order %layer_count %support_layer_count;
Layer* previous_layer = NULL;
//create layer and layer regions
@ -3415,35 +3254,6 @@ int Print::load_cached_data(const std::string& directory)
}
);
//tree support layers
Layer* previous_tree_support_layer = NULL;
//create tree_support_layers
for (int index = 0; index < treesupport_layer_count; index++)
{
json& layer_json = root_json[JSON_TREE_SUPPORT_LAYERS][index];
TreeSupportLayer* new_tree_support_layer = obj->add_tree_support_layer(layer_json[JSON_LAYER_ID], layer_json[JSON_LAYER_HEIGHT], layer_json[JSON_LAYER_PRINT_Z], layer_json[JSON_LAYER_SLICE_Z]);
if (!new_tree_support_layer) {
BOOST_LOG_TRIVIAL(error) <<__FUNCTION__<< boost::format(":add_support_layer failed, out of memory");
return CLI_OUT_OF_MEMORY;
}
if (previous_tree_support_layer) {
previous_tree_support_layer->upper_layer = new_tree_support_layer;
new_tree_support_layer->lower_layer = previous_tree_support_layer;
}
previous_tree_support_layer = new_tree_support_layer;
}
BOOST_LOG_TRIVIAL(info) << __FUNCTION__<< boost::format(": finished load support_layers, start to load treesupport_layers.");
tbb::parallel_for(
tbb::blocked_range<size_t>(0, obj->tree_support_layer_count()),
[&root_json, &obj](const tbb::blocked_range<size_t>& tree_support_layer_range) {
for (size_t layer_index = tree_support_layer_range.begin(); layer_index < tree_support_layer_range.end(); ++ layer_index) {
const json& layer_json = root_json[JSON_TREE_SUPPORT_LAYERS][layer_index];
TreeSupportLayer* tree_support_layer = obj->get_tree_support_layer(layer_index);
extract_tree_support_layer(layer_json, *tree_support_layer);
}
}
);
count ++;
BOOST_LOG_TRIVIAL(info) << __FUNCTION__<< boost::format(": load object %1% from %2% successfully.")%count%object_filenames[obj_index].first;
}

View File

@ -31,7 +31,6 @@ class Print;
class PrintObject;
class SupportLayer;
// BBS
class TreeSupportLayer;
class TreeSupportData;
class TreeSupport;
@ -175,13 +174,6 @@ class ConstSupportLayerPtrsAdaptor : public ConstVectorOfPtrsAdaptor<SupportLaye
ConstSupportLayerPtrsAdaptor(const SupportLayerPtrs *data) : ConstVectorOfPtrsAdaptor<SupportLayer>(data) {}
};
// BBS
typedef std::vector<TreeSupportLayer*> TreeSupportLayerPtrs;
class ConstTreeSupportLayerPtrsAdaptor : public ConstVectorOfPtrsAdaptor<TreeSupportLayer> {
friend PrintObject;
ConstTreeSupportLayerPtrsAdaptor(const TreeSupportLayerPtrs* data) : ConstVectorOfPtrsAdaptor<TreeSupportLayer>(data) {}
};
class BoundingBoxf3; // TODO: for temporary constructor parameter
// Single instance of a PrintObject.
@ -296,14 +288,10 @@ public:
Transform3d trafo_centered() const
{ Transform3d t = this->trafo(); t.pretranslate(Vec3d(- unscale<double>(m_center_offset.x()), - unscale<double>(m_center_offset.y()), 0)); return t; }
const PrintInstances& instances() const { return m_instances; }
// BBS
ConstTreeSupportLayerPtrsAdaptor tree_support_layers() const { return ConstTreeSupportLayerPtrsAdaptor(&m_tree_support_layers); }
// Whoever will get a non-const pointer to PrintObject will be able to modify its layers.
LayerPtrs& layers() { return m_layers; }
SupportLayerPtrs& support_layers() { return m_support_layers; }
// BBS
TreeSupportLayerPtrs& tree_support_layers() { return m_tree_support_layers; }
template<typename PolysType>
static void remove_bridges_from_contacts(
@ -364,12 +352,7 @@ public:
Layer* add_layer(int id, coordf_t height, coordf_t print_z, coordf_t slice_z);
// BBS
TreeSupportLayer* get_tree_support_layer(int idx) { return m_tree_support_layers[idx]; }
const TreeSupportLayer* get_tree_support_layer_at_printz(coordf_t print_z, coordf_t epsilon) const;
TreeSupportLayer* get_tree_support_layer_at_printz(coordf_t print_z, coordf_t epsilon);
TreeSupportLayer* add_tree_support_layer(int id, coordf_t height, coordf_t print_z, coordf_t slice_z);
void clear_tree_support_layers();
size_t tree_support_layer_count() const { return m_tree_support_layers.size(); }
SupportLayer* add_tree_support_layer(int id, coordf_t height, coordf_t print_z, coordf_t slice_z);
std::shared_ptr<TreeSupportData> alloc_tree_support_preview_cache();
void clear_tree_support_preview_cache() { m_tree_support_preview_cache.reset(); }
@ -380,7 +363,6 @@ public:
SupportLayer* get_support_layer_at_printz(coordf_t print_z, coordf_t epsilon);
SupportLayer* add_support_layer(int id, int interface_id, coordf_t height, coordf_t print_z);
SupportLayerPtrs::iterator insert_support_layer(SupportLayerPtrs::iterator pos, size_t id, size_t interface_id, coordf_t height, coordf_t print_z, coordf_t slice_z);
void delete_support_layer(int idx);
// Initialize the layer_height_profile from the model_object's layer_height_profile, from model_object's layer height table, or from slicing parameters.
// Returns true, if the layer_height_profile was changed.
@ -497,7 +479,6 @@ private:
LayerPtrs m_layers;
SupportLayerPtrs m_support_layers;
// BBS
TreeSupportLayerPtrs m_tree_support_layers;
std::shared_ptr<TreeSupportData> m_tree_support_preview_cache;
// this is set to true when LayerRegion->slices is split in top/internal/bottom

View File

@ -91,7 +91,6 @@ PrintObject::~PrintObject()
if (m_shared_regions && -- m_shared_regions->m_ref_cnt == 0) delete m_shared_regions;
clear_layers();
clear_support_layers();
clear_tree_support_layers();
}
PrintBase::ApplyStatus PrintObject::set_instances(PrintInstances &&instances)
@ -414,7 +413,6 @@ void PrintObject::generate_support_material()
{
if (this->set_started(posSupportMaterial)) {
this->clear_support_layers();
this->clear_tree_support_layers();
if ((this->has_support() && m_layers.size() > 1) || (this->has_raft() && ! m_layers.empty())) {
m_print->set_status(50, L("Generating support"));
@ -483,16 +481,6 @@ void PrintObject::simplify_extrusion_path()
}
);
m_print->throw_if_canceled();
tbb::parallel_for(
tbb::blocked_range<size_t>(0, m_tree_support_layers.size()),
[this](const tbb::blocked_range<size_t>& range) {
for (size_t layer_idx = range.begin(); layer_idx < range.end(); ++ layer_idx) {
m_print->throw_if_canceled();
m_tree_support_layers[layer_idx]->simplify_support_extrusion_path();
}
}
);
m_print->throw_if_canceled();
BOOST_LOG_TRIVIAL(debug) << "Simplify extrusion path of support in parallel - end";
this->set_done(posSimplifySupportPath);
}
@ -564,19 +552,6 @@ Layer* PrintObject::add_layer(int id, coordf_t height, coordf_t print_z, coordf_
return m_layers.back();
}
// BBS
const TreeSupportLayer* PrintObject::get_tree_support_layer_at_printz(coordf_t print_z, coordf_t epsilon) const
{
coordf_t limit = print_z - epsilon;
auto it = Slic3r::lower_bound_by_predicate(m_tree_support_layers.begin(), m_tree_support_layers.end(), [limit](const TreeSupportLayer* layer) { return layer->print_z < limit; });
return (it == m_tree_support_layers.end() || (*it)->print_z > print_z + epsilon) ? nullptr : *it;
}
TreeSupportLayer* PrintObject::get_tree_support_layer_at_printz(coordf_t print_z, coordf_t epsilon)
{
return const_cast<TreeSupportLayer*>(std::as_const(*this).get_tree_support_layer_at_printz(print_z, epsilon));
}
const SupportLayer* PrintObject::get_support_layer_at_printz(coordf_t print_z, coordf_t epsilon) const
{
coordf_t limit = print_z - epsilon;
@ -589,12 +564,17 @@ SupportLayer* PrintObject::get_support_layer_at_printz(coordf_t print_z, coordf_
return const_cast<SupportLayer*>(std::as_const(*this).get_support_layer_at_printz(print_z, epsilon));
}
void PrintObject::clear_tree_support_layers()
void PrintObject::clear_support_layers()
{
if (!m_shared_object) {
for (TreeSupportLayer* l : m_tree_support_layers)
for (SupportLayer* l : m_support_layers)
delete l;
m_tree_support_layers.clear();
m_support_layers.clear();
for (auto l : m_layers) {
l->sharp_tails.clear();
l->sharp_tails_height.clear();
l->cantilevers.clear();
}
}
}
@ -614,19 +594,11 @@ std::shared_ptr<TreeSupportData> PrintObject::alloc_tree_support_preview_cache()
return m_tree_support_preview_cache;
}
TreeSupportLayer* PrintObject::add_tree_support_layer(int id, coordf_t height, coordf_t print_z, coordf_t slice_z)
SupportLayer* PrintObject::add_tree_support_layer(int id, coordf_t height, coordf_t print_z, coordf_t slice_z)
{
m_tree_support_layers.emplace_back(new TreeSupportLayer(id, this, height, print_z, slice_z));
return m_tree_support_layers.back();
}
void PrintObject::clear_support_layers()
{
if (!m_shared_object) {
for (Layer *l : m_support_layers)
delete l;
m_support_layers.clear();
}
m_support_layers.emplace_back(new SupportLayer(id, 0, this, height, print_z, slice_z));
m_support_layers.back()->support_type = stInnerTree;
return m_support_layers.back();
}
SupportLayer* PrintObject::add_support_layer(int id, int interface_id, coordf_t height, coordf_t print_z)

View File

@ -28,7 +28,7 @@
#define TAU (2.0 * M_PI)
#define NO_INDEX (std::numeric_limits<unsigned int>::max())
//#define SUPPORT_TREE_DEBUG_TO_SVG
// #define SUPPORT_TREE_DEBUG_TO_SVG
namespace Slic3r
{
@ -286,7 +286,7 @@ static void draw_layer_mst
svg.draw(spanning_tree.vertices(), "black", coord_t(scale_(0.1)));
}
static void draw_two_overhangs_to_svg(TreeSupportLayer* ts_layer, const ExPolygons& overhangs1, const ExPolygons& overhangs2)
static void draw_two_overhangs_to_svg(SupportLayer* ts_layer, const ExPolygons& overhangs1, const ExPolygons& overhangs2)
{
if (overhangs1.empty() && overhangs2.empty())
return;
@ -301,7 +301,7 @@ static void draw_two_overhangs_to_svg(TreeSupportLayer* ts_layer, const ExPolygo
svg.draw(union_ex(overhangs2), "red");
}
static void draw_polylines(TreeSupportLayer* ts_layer, Polylines& polylines)
static void draw_polylines(SupportLayer* ts_layer, Polylines& polylines)
{
if (polylines.empty())
return;
@ -711,11 +711,11 @@ TreeSupport::TreeSupport(PrintObject& object, const SlicingParameters &slicing_p
void TreeSupport::detect_object_overhangs()
{
// overhangs are already detected
if (m_object->tree_support_layer_count() >= m_object->layer_count())
if (m_object->support_layer_count() >= m_object->layer_count())
return;
// Clear and create Tree Support Layers
m_object->clear_tree_support_layers();
m_object->clear_support_layers();
m_object->clear_tree_support_preview_cache();
create_tree_support_layers();
@ -997,7 +997,7 @@ void TreeSupport::detect_object_overhangs()
m_object->remove_bridges_from_contacts(lower_layer, layer, extrusion_width_scaled, &overhang_areas, max_bridge_length, true);
}
TreeSupportLayer* ts_layer = m_object->get_tree_support_layer(layer_nr + m_raft_layers);
SupportLayer* ts_layer = m_object->get_support_layer(layer_nr + m_raft_layers);
for (ExPolygon& poly : overhang_areas) {
if (!offset_ex(poly, -0.1 * extrusion_width_scaled).empty())
ts_layer->overhang_areas.emplace_back(poly);
@ -1147,7 +1147,7 @@ void TreeSupport::detect_object_overhangs()
if (m_object->print()->canceled())
break;
TreeSupportLayer* ts_layer = m_object->get_tree_support_layer(layer_nr + m_raft_layers);
SupportLayer* ts_layer = m_object->get_support_layer(layer_nr + m_raft_layers);
if (support_critical_regions_only) {
auto layer = m_object->get_layer(layer_nr);
auto lower_layer = layer->lower_layer;
@ -1165,7 +1165,7 @@ void TreeSupport::detect_object_overhangs()
}
for (auto &area : ts_layer->overhang_areas) {
ts_layer->overhang_types.emplace(&area, TreeSupportLayer::Detected);
ts_layer->overhang_types.emplace(&area, SupportLayer::Detected);
}
// enforcers
if (layer_nr < enforcers.size()) {
@ -1176,7 +1176,7 @@ void TreeSupport::detect_object_overhangs()
enforcer = offset(enforcer, 0.1 * extrusion_width_scaled);
for (const Polygon& poly : enforcer) {
ts_layer->overhang_areas.emplace_back(poly);
ts_layer->overhang_types.emplace(&ts_layer->overhang_areas.back(), TreeSupportLayer::Enforced);
ts_layer->overhang_types.emplace(&ts_layer->overhang_areas.back(), SupportLayer::Enforced);
}
}
@ -1184,7 +1184,7 @@ void TreeSupport::detect_object_overhangs()
}
#ifdef SUPPORT_TREE_DEBUG_TO_SVG
for (const TreeSupportLayer* layer : m_object->tree_support_layers()) {
for (const SupportLayer* layer : m_object->support_layers()) {
if (layer->overhang_areas.empty())
continue;
@ -1221,9 +1221,9 @@ void TreeSupport::create_tree_support_layers()
}
for (Layer *layer : m_object->layers()) {
TreeSupportLayer* ts_layer = m_object->add_tree_support_layer(layer->id(), layer->height, layer->print_z, layer->slice_z);
SupportLayer* ts_layer = m_object->add_tree_support_layer(layer->id(), layer->height, layer->print_z, layer->slice_z);
if (ts_layer->id() > m_raft_layers) {
TreeSupportLayer* lower_layer = m_object->get_tree_support_layer(ts_layer->id() - 1);
SupportLayer* lower_layer = m_object->get_support_layer(ts_layer->id() - 1);
lower_layer->upper_layer = ts_layer;
ts_layer->lower_layer = lower_layer;
}
@ -1435,7 +1435,7 @@ void TreeSupport::generate_toolpaths()
const coordf_t branch_radius = object_config.tree_support_branch_diameter.value / 2;
const coordf_t branch_radius_scaled = scale_(branch_radius);
if (m_object->tree_support_layers().empty())
if (m_object->support_layers().empty())
return;
// calculate fill areas for raft layers
@ -1447,8 +1447,8 @@ void TreeSupport::generate_toolpaths()
}
}
if (m_object->tree_support_layer_count() > m_raft_layers) {
const TreeSupportLayer *ts_layer = m_object->get_tree_support_layer(m_raft_layers);
if (m_object->support_layer_count() > m_raft_layers) {
const SupportLayer *ts_layer = m_object->get_support_layer(m_raft_layers);
for (const ExPolygon expoly : ts_layer->floor_areas)
raft_areas.push_back(expoly);
for (const ExPolygon expoly : ts_layer->roof_areas)
@ -1463,7 +1463,7 @@ void TreeSupport::generate_toolpaths()
if (m_raft_layers > 0)
{
ExtrusionRole raft_contour_er = m_slicing_params.base_raft_layers > 0 ? erSupportMaterial : erSupportMaterialInterface;
TreeSupportLayer *ts_layer = m_object->tree_support_layers().front();
SupportLayer *ts_layer = m_object->support_layers().front();
Flow flow = m_object->print()->brim_flow();
Polygons loops;
@ -1477,7 +1477,7 @@ void TreeSupport::generate_toolpaths()
}
for (size_t layer_nr = 0; layer_nr < m_slicing_params.base_raft_layers; layer_nr++) {
TreeSupportLayer *ts_layer = m_object->get_tree_support_layer(layer_nr);
SupportLayer *ts_layer = m_object->get_support_layer(layer_nr);
coordf_t expand_offset = (layer_nr == 0 ? 0. : -1.);
Flow support_flow = layer_nr == 0 ? m_object->print()->brim_flow() : Flow(support_extrusion_width, ts_layer->height, nozzle_diameter);
@ -1497,7 +1497,7 @@ void TreeSupport::generate_toolpaths()
layer_nr < m_slicing_params.base_raft_layers + m_slicing_params.interface_raft_layers;
layer_nr++)
{
TreeSupportLayer *ts_layer = m_object->get_tree_support_layer(layer_nr);
SupportLayer *ts_layer = m_object->get_support_layer(layer_nr);
coordf_t expand_offset = (layer_nr == 0 ? 0. : -1.);
Flow support_flow(support_extrusion_width, ts_layer->height, nozzle_diameter);
@ -1529,7 +1529,7 @@ void TreeSupport::generate_toolpaths()
// generate tree support tool paths
tbb::parallel_for(
tbb::blocked_range<size_t>(m_raft_layers, m_object->tree_support_layer_count()),
tbb::blocked_range<size_t>(m_raft_layers, m_object->support_layer_count()),
[&](const tbb::blocked_range<size_t>& range)
{
for (size_t layer_id = range.begin(); layer_id < range.end(); layer_id++) {
@ -1538,7 +1538,7 @@ void TreeSupport::generate_toolpaths()
m_object->print()->set_status(70, (boost::format(_L("Support: generate toolpath at layer %d")) % layer_id).str());
TreeSupportLayer* ts_layer = m_object->get_tree_support_layer(layer_id);
SupportLayer* ts_layer = m_object->get_support_layer(layer_id);
Flow support_flow(support_extrusion_width, ts_layer->height, nozzle_diameter);
coordf_t support_spacing = object_config.support_base_pattern_spacing.value + support_flow.spacing();
coordf_t support_density = std::min(1., support_flow.spacing() / support_spacing);
@ -1549,14 +1549,14 @@ void TreeSupport::generate_toolpaths()
ExPolygon& poly = *area_group.area;
ExPolygons polys;
FillParams fill_params;
if (area_group.type != TreeSupportLayer::BaseType) {
if (area_group.type != SupportLayer::BaseType) {
// interface
if (layer_id == 0) {
Flow flow = m_raft_layers == 0 ? m_object->print()->brim_flow() : support_flow;
make_perimeter_and_inner_brim(ts_layer->support_fills.entities, poly, wall_count, flow,
area_group.type == TreeSupportLayer::RoofType ? erSupportMaterialInterface : erSupportMaterial);
area_group.type == SupportLayer::RoofType ? erSupportMaterialInterface : erSupportMaterial);
polys = std::move(offset_ex(poly, -flow.scaled_spacing()));
} else if (area_group.type == TreeSupportLayer::Roof1stLayer) {
} else if (area_group.type == SupportLayer::Roof1stLayer) {
polys = std::move(offset_ex(poly, 0.5*support_flow.scaled_width()));
}
else {
@ -1565,7 +1565,7 @@ void TreeSupport::generate_toolpaths()
fill_params.density = interface_density;
fill_params.dont_adjust = true;
}
if (area_group.type == TreeSupportLayer::Roof1stLayer) {
if (area_group.type == SupportLayer::Roof1stLayer) {
// roof_1st_layer
fill_params.density = interface_density;
// Note: spacing means the separation between two lines as if they are tightly extruded
@ -1579,13 +1579,13 @@ void TreeSupport::generate_toolpaths()
ts_layer->support_fills.entities.push_back(temp_support_fills);
else
delete temp_support_fills;
} else if (area_group.type == TreeSupportLayer::FloorType) {
} else if (area_group.type == SupportLayer::FloorType) {
// floor_areas
fill_params.density = bottom_interface_density;
filler_interface->spacing = m_support_material_interface_flow.spacing();
fill_expolygons_generate_paths(ts_layer->support_fills.entities, std::move(polys),
filler_interface.get(), fill_params, erSupportMaterialInterface, m_support_material_interface_flow);
} else if (area_group.type == TreeSupportLayer::RoofType) {
} else if (area_group.type == SupportLayer::RoofType) {
// roof_areas
fill_params.density = interface_density;
filler_interface->spacing = m_support_material_interface_flow.spacing();
@ -2072,7 +2072,7 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
break;
const std::vector<Node*>& curr_layer_nodes = contact_nodes[layer_nr];
TreeSupportLayer* ts_layer = m_object->get_tree_support_layer(layer_nr + m_raft_layers);
SupportLayer* ts_layer = m_object->get_support_layer(layer_nr + m_raft_layers);
assert(ts_layer != nullptr);
// skip if current layer has no points. This fixes potential crash in get_collision (see jira BBL001-355)
@ -2248,10 +2248,10 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
}
}
auto &area_groups = ts_layer->area_groups;
for (auto &area : ts_layer->base_areas) area_groups.emplace_back(&area, TreeSupportLayer::BaseType, max_layers_above_base);
for (auto &area : ts_layer->roof_areas) area_groups.emplace_back(&area, TreeSupportLayer::RoofType, max_layers_above_roof);
for (auto &area : ts_layer->floor_areas) area_groups.emplace_back(&area, TreeSupportLayer::FloorType, 10000);
for (auto &area : ts_layer->roof_1st_layer) area_groups.emplace_back(&area, TreeSupportLayer::Roof1stLayer, max_layers_above_roof1);
for (auto &area : ts_layer->base_areas) area_groups.emplace_back(&area, SupportLayer::BaseType, max_layers_above_base);
for (auto &area : ts_layer->roof_areas) area_groups.emplace_back(&area, SupportLayer::RoofType, max_layers_above_roof);
for (auto &area : ts_layer->floor_areas) area_groups.emplace_back(&area, SupportLayer::FloorType, 10000);
for (auto &area : ts_layer->roof_1st_layer) area_groups.emplace_back(&area, SupportLayer::Roof1stLayer, max_layers_above_roof1);
for (auto &area_group : area_groups) {
auto& expoly = area_group.area;
@ -2276,7 +2276,7 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
for (int layer_nr = 1; layer_nr < m_object->layer_count(); layer_nr++) {
if (print->canceled()) break;
const std::vector<Node*>& curr_layer_nodes = contact_nodes[layer_nr];
TreeSupportLayer* ts_layer = m_object->get_tree_support_layer(layer_nr + m_raft_layers);
SupportLayer* ts_layer = m_object->get_support_layer(layer_nr + m_raft_layers);
assert(ts_layer != nullptr);
// skip if current layer has no points. This fixes potential crash in get_collision (see jira BBL001-355)
@ -2288,10 +2288,10 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
int layer_nr_lower = layer_nr - 1;
for (layer_nr_lower; layer_nr_lower >= 0; layer_nr_lower--) {
if (!m_object->get_tree_support_layer(layer_nr_lower + m_raft_layers)->area_groups.empty()) break;
if (!m_object->get_support_layer(layer_nr_lower + m_raft_layers)->area_groups.empty()) break;
}
TreeSupportLayer* lower_layer = m_object->get_tree_support_layer(layer_nr_lower + m_raft_layers);
ExPolygons& base_areas_lower = m_object->get_tree_support_layer(layer_nr_lower + m_raft_layers)->base_areas;
SupportLayer* lower_layer = m_object->get_support_layer(layer_nr_lower + m_raft_layers);
ExPolygons& base_areas_lower = m_object->get_support_layer(layer_nr_lower + m_raft_layers)->base_areas;
ExPolygons overhang;
@ -2325,7 +2325,7 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
printZ_to_lightninglayer[lower_layer->print_z] = overhangs.size() - 1;
#ifdef SUPPORT_TREE_DEBUG_TO_SVG
draw_two_overhangs_to_svg(m_object->get_tree_support_layer(layer_nr_lower + m_raft_layers), base_areas_lower, to_expolygons(overhangs.back()));
draw_two_overhangs_to_svg(m_object->get_support_layer(layer_nr_lower + m_raft_layers), base_areas_lower, to_expolygons(overhangs.back()));
#endif
}
@ -2365,7 +2365,7 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
m_object->print()->set_status(66, (boost::format(_L("Support: fix holes at layer %d")) % layer_nr).str());
const std::vector<Node*>& curr_layer_nodes = contact_nodes[layer_nr];
TreeSupportLayer* ts_layer = m_object->get_tree_support_layer(layer_nr + m_raft_layers);
SupportLayer* ts_layer = m_object->get_support_layer(layer_nr + m_raft_layers);
assert(ts_layer != nullptr);
// skip if current layer has no points. This fixes potential crash in get_collision (see jira BBL001-355)
@ -2375,18 +2375,18 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
int layer_nr_lower = layer_nr - 1;
for (layer_nr_lower; layer_nr_lower >= 0; layer_nr_lower--) {
if (!m_object->get_tree_support_layer(layer_nr_lower + m_raft_layers)->area_groups.empty()) break;
if (!m_object->get_support_layer(layer_nr_lower + m_raft_layers)->area_groups.empty()) break;
}
if (layer_nr_lower < 0) continue;
auto& area_groups_lower = m_object->get_tree_support_layer(layer_nr_lower + m_raft_layers)->area_groups;
auto& area_groups_lower = m_object->get_support_layer(layer_nr_lower + m_raft_layers)->area_groups;
for (const auto& area_group : ts_layer->area_groups) {
if (area_group.type != TreeSupportLayer::BaseType) continue;
if (area_group.type != SupportLayer::BaseType) continue;
const auto& area = area_group.area;
for (const auto& hole : area->holes) {
// auto hole_bbox = get_extents(hole).polygon();
for (auto& area_group_lower : area_groups_lower) {
if (area_group.type != TreeSupportLayer::BaseType) continue;
if (area_group.type != SupportLayer::BaseType) continue;
auto& base_area_lower = *area_group_lower.area;
Point pt_on_poly, pt_on_expoly, pt_far_on_poly;
// if a hole doesn't intersect with lower layer's contours, add a hole to lower layer and move it slightly to the contour
@ -2451,8 +2451,8 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
#endif
#ifdef SUPPORT_TREE_DEBUG_TO_SVG
for (int layer_nr = m_object->layer_count() - 1; layer_nr > 0; layer_nr--) {
TreeSupportLayer* ts_layer = m_object->get_tree_support_layer(layer_nr + m_raft_layers);
for (int layer_nr = m_object->layer_count() - 1; layer_nr >= 0; layer_nr--) {
SupportLayer* ts_layer = m_object->get_support_layer(layer_nr + m_raft_layers);
ExPolygons& base_areas = ts_layer->base_areas;
ExPolygons& roof_areas = ts_layer->roof_areas;
ExPolygons& roof_1st_layer = ts_layer->roof_1st_layer;
@ -2467,7 +2467,7 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
draw_circles_layer_out.open("./SVG/layer_heights_draw_circles.txt");
if (draw_circles_layer_out.is_open()) {
for (int layer_nr = m_object->layer_count() - 1; layer_nr > 0; layer_nr--) {
TreeSupportLayer* ts_layer = m_object->get_tree_support_layer(layer_nr + m_raft_layers);
SupportLayer* ts_layer = m_object->get_support_layer(layer_nr + m_raft_layers);
ExPolygons& base_areas = ts_layer->base_areas;
ExPolygons& roof_areas = ts_layer->roof_areas;
ExPolygons& roof_1st_layer = ts_layer->roof_1st_layer;
@ -2478,8 +2478,8 @@ void TreeSupport::draw_circles(const std::vector<std::vector<Node*>>& contact_no
}
#endif // SUPPORT_TREE_DEBUG_TO_SVG
TreeSupportLayerPtrs& ts_layers = m_object->tree_support_layers();
auto iter = std::remove_if(ts_layers.begin(), ts_layers.end(), [](TreeSupportLayer* ts_layer) { return ts_layer->height < EPSILON; });
SupportLayerPtrs& ts_layers = m_object->support_layers();
auto iter = std::remove_if(ts_layers.begin(), ts_layers.end(), [](SupportLayer* ts_layer) { return ts_layer->height < EPSILON; });
ts_layers.erase(iter, ts_layers.end());
for (int layer_nr = 0; layer_nr < ts_layers.size(); layer_nr++) {
ts_layers[layer_nr]->upper_layer = layer_nr != ts_layers.size() - 1 ? ts_layers[layer_nr + 1] : nullptr;
@ -2585,7 +2585,7 @@ void TreeSupport::drop_nodes(std::vector<std::vector<Node*>>& contact_nodes)
coordf_t height_next = layer_heights[layer_nr_next].second;
std::deque<std::pair<size_t, Node*>> unsupported_branch_leaves; // All nodes that are leaves on this layer that would result in unsupported ('mid-air') branches.
const Layer* ts_layer = m_object->get_tree_support_layer(layer_nr);
const Layer* ts_layer = m_object->get_support_layer(layer_nr);
m_object->print()->set_status(60, (boost::format(_L("Support: propagate branches at layer %d")) % layer_nr).str());
@ -3347,7 +3347,7 @@ void TreeSupport::generate_contact_points(std::vector<std::vector<TreeSupport::N
{
if (m_object->print()->canceled())
break;
auto ts_layer = m_object->get_tree_support_layer(layer_nr + m_raft_layers);
auto ts_layer = m_object->get_support_layer(layer_nr + m_raft_layers);
const ExPolygons &overhang = ts_layer->overhang_areas;
auto & curr_nodes = contact_nodes[layer_nr];
if (overhang.empty())
@ -3406,7 +3406,7 @@ void TreeSupport::generate_contact_points(std::vector<std::vector<TreeSupport::N
{
auto bbox = overhang_part.contour.bounding_box();
Points candidates;
if (ts_layer->overhang_types[&overhang_part] == TreeSupportLayer::Detected)
if (ts_layer->overhang_types[&overhang_part] == SupportLayer::Detected)
candidates = {bbox.min, bounding_box_middle(bbox), bbox.max};
else
candidates = {bounding_box_middle(bbox)};
@ -3421,7 +3421,7 @@ void TreeSupport::generate_contact_points(std::vector<std::vector<TreeSupport::N
curr_nodes.emplace_back(contact_node);
}
}
if (ts_layer->overhang_types[&overhang_part] == TreeSupportLayer::Detected) {
if (ts_layer->overhang_types[&overhang_part] == SupportLayer::Detected) {
// add points at corners
auto &points = overhang_part.contour.points;
int nSize = points.size();
@ -3438,7 +3438,7 @@ void TreeSupport::generate_contact_points(std::vector<std::vector<TreeSupport::N
}
}
}
if(ts_layer->overhang_types[&overhang_part] == TreeSupportLayer::Enforced || is_slim){
if(ts_layer->overhang_types[&overhang_part] == SupportLayer::Enforced || is_slim){
// remove close points in Enforcers
// auto above_nodes = contact_nodes[layer_nr - 1];
if (!curr_nodes.empty() /*&& !above_nodes.empty()*/) {

View File

@ -865,42 +865,22 @@ void GLGizmoFdmSupports::run_thread()
goto _finished;
}
if (m_is_tree_support)
if (!m_print_instance.print_object->support_layers().size())
{
if (!m_print_instance.print_object->tree_support_layers().size())
{
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ",no tree support layer found, update status to 100%\n";
print->set_status(100, L("Support Generated"));
goto _finished;
}
for (const TreeSupportLayer *support_layer : m_print_instance.print_object->tree_support_layers())
{
for (const ExtrusionEntity *extrusion_entity : support_layer->support_fills.entities)
{
_3DScene::extrusionentity_to_verts(extrusion_entity, float(support_layer->print_z), m_print_instance.shift, *m_support_volume);
}
}
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ", finished extrusionentity_to_verts, update status to 100%";
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ",no support layer found, update status to 100%\n";
print->set_status(100, L("Support Generated"));
goto _finished;
}
else
for (const SupportLayer *support_layer : m_print_instance.print_object->support_layers())
{
if (!m_print_instance.print_object->support_layers().size())
for (const ExtrusionEntity *extrusion_entity : support_layer->support_fills.entities)
{
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ",no support layer found, update status to 100%\n";
print->set_status(100, L("Support Generated"));
goto _finished;
_3DScene::extrusionentity_to_verts(extrusion_entity, float(support_layer->print_z), m_print_instance.shift, *m_support_volume);
}
for (const SupportLayer *support_layer : m_print_instance.print_object->support_layers())
{
for (const ExtrusionEntity *extrusion_entity : support_layer->support_fills.entities)
{
_3DScene::extrusionentity_to_verts(extrusion_entity, float(support_layer->print_z), m_print_instance.shift, *m_support_volume);
}
}
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ", finished extrusionentity_to_verts, update status to 100%";
print->set_status(100, L("Support Generated"));
}
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ", finished extrusionentity_to_verts, update status to 100%";
print->set_status(100, L("Support Generated"));
record_timestamp();
}
catch (...) {