Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[CURA-10829] Option to not use small skin areas on surface #1925

Merged
merged 28 commits into from
Aug 22, 2023
Merged
Show file tree
Hide file tree
Changes from 27 commits
Commits
Show all changes
28 commits
Select commit Hold shift + click to select a range
2fddaf0
Merge remote-tracking branch 'origin/main' into CURA-10670_reenable_s…
rburema Aug 8, 2023
b4d1828
Add setting to prevent the top layer from doing small-skin behaviour.
rburema Aug 8, 2023
279d938
Applied clang-format.
rburema Aug 8, 2023
8677b10
Fix include-issue exposed by auto-formatter.
rburema Aug 8, 2023
6c375d0
Applied clang-format.
rburema Aug 8, 2023
2b2aa3e
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 9, 2023
5460306
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 9, 2023
0bc6953
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
4ca463b
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
fca128c
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
4f34f34
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
6a31cc3
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
a3e122c
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
921af0e
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
6ac1860
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
2c64929
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
4cebd6d
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
abbed4c
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
4ac9c44
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
jellespijker Aug 10, 2023
63386af
Merge branch 'CURA-10927_fix_numtype_regression_candidate0' into CURA…
rburema Aug 10, 2023
a2ed0bc
Merge branch 'CURA-10670_reenable_small_skin_area' into CURA-10829_do…
rburema Aug 12, 2023
ac86c03
Applied clang-format.
rburema Aug 12, 2023
f8818e1
Also possible to exclude bottom from small skin behaviour.
rburema Aug 15, 2023
3e8d340
Applied clang-format.
rburema Aug 15, 2023
28d365a
Merge branch 'main' into CURA-10829_dont_expose_small_skin_to_air
rburema Aug 15, 2023
b85dd9f
Correct typo: to -> too.
rburema Aug 15, 2023
5a0ae57
Inner countour needs to be unioned and re-intersected anyway to fix s…
rburema Aug 16, 2023
ef687fe
Update header
casperlamboo Aug 20, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 4 additions & 3 deletions include/TopSurface.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
//Copyright (c) 2018 Ultimaker B.V.
//CuraEngine is released under the terms of the AGPLv3 or higher.
// Copyright (c) 2018 Ultimaker B.V.
// CuraEngine is released under the terms of the AGPLv3 or higher.

#ifndef TOPSURFACE_H
#define TOPSURFACE_H
Expand All @@ -12,6 +12,7 @@ namespace cura
class GCodePathConfig;
class FffGcodeWriter;
class LayerPlan;
class SliceDataStorage;
class SliceMeshStorage;

class TopSurface
Expand Down Expand Up @@ -59,6 +60,6 @@ class TopSurface
Polygons areas;
};

}
} // namespace cura

#endif /* TOPSURFACE_H */
3 changes: 2 additions & 1 deletion include/infill.h
Original file line number Diff line number Diff line change
Expand Up @@ -130,7 +130,8 @@ class Infill
SectionType section_type,
const SierpinskiFillProvider* cross_fill_provider = nullptr,
const LightningLayer* lightning_layer = nullptr,
const SliceMeshStorage* mesh = nullptr);
const SliceMeshStorage* mesh = nullptr,
const Polygons& prevent_small_exposed_to_air = Polygons());

/*!
* Generate the wall toolpaths of an infill area. It will return the inner contour and set the inner-contour.
Expand Down
73 changes: 42 additions & 31 deletions include/sliceDataStorage.h
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
//Copyright (c) 2022 Ultimaker B.V.
//CuraEngine is released under the terms of the AGPLv3 or higher.
// Copyright (c) 2022 Ultimaker B.V.
// CuraEngine is released under the terms of the AGPLv3 or higher.
casperlamboo marked this conversation as resolved.
Show resolved Hide resolved

#ifndef SLICE_DATA_STORAGE_H
#define SLICE_DATA_STORAGE_H

#include <map>
#include <optional>

#include "PrimeTower.h"
#include "RetractionConfig.h"
#include "SupportInfillPart.h"
#include "TopSurface.h"
#include "WipeScriptConfig.h"
#include "settings/Settings.h" //For MAX_EXTRUDERS.
#include "settings/types/Angle.h" //Infill angles.
#include "settings/types/LayerIndex.h"
Expand All @@ -19,7 +17,9 @@
#include "utils/IntPoint.h"
#include "utils/NoCopy.h"
#include "utils/polygon.h"
#include "WipeScriptConfig.h"

#include <map>
#include <optional>

// libArachne
#include "utils/ExtrusionLine.h"
Expand All @@ -32,14 +32,15 @@ class SierpinskiFillProvider;
class LightningGenerator;

/*!
* A SkinPart is a connected area designated as top and/or bottom skin.
* A SkinPart is a connected area designated as top and/or bottom skin.
* Surrounding each non-bridged skin area with an outline may result in better top skins.
* It's filled during FffProcessor.processSliceData(.) and used in FffProcessor.writeGCode(.) to generate the final gcode.
*/
class SkinPart
{
public:
PolygonsPart outline; //!< The skinOutline is the area which needs to be 100% filled to generate a proper top&bottom filling. It's filled by the "skin" module. Includes both roofing and non-roofing.
PolygonsPart outline; //!< The skinOutline is the area which needs to be 100% filled to generate a proper top&bottom filling. It's filled by the "skin" module. Includes both
//!< roofing and non-roofing.
Polygons skin_fill; //!< The part of the skin which is not roofing.
Polygons roofing_fill; //!< The inner infill which has air directly above
Polygons top_most_surface_fill; //!< The inner infill of the uppermost top layer which has air directly above.
Expand All @@ -64,7 +65,7 @@ class SliceLayerPart
//!< Too small parts will be omitted compared to the outline.
Polygons spiral_wall; //!< The centerline of the wall used by spiralize mode. Only computed if spiralize mode is enabled.
Polygons inner_area; //!< The area of the outline, minus the walls. This will be filled with either skin or infill.
std::vector<SkinPart> skin_parts; //!< The skin parts which are filled for 100% with lines and/or insets.
std::vector<SkinPart> skin_parts; //!< The skin parts which are filled for 100% with lines and/or insets.
std::vector<VariableWidthLines> wall_toolpaths; //!< toolpaths for walls, will replace(?) the insets. Binned by inset_idx.
std::vector<VariableWidthLines> infill_wall_toolpaths; //!< toolpaths for the walls of the infill areas. Binned by inset_idx.

Expand Down Expand Up @@ -125,7 +126,7 @@ class SliceLayerPart
* This maximum number of layers we can combine is a user setting. This number, say "n", means the maximum number of layers we can combine into one.
* On the combined layers, the extrusion amount will be higher than the normal extrusion amount because it needs to extrude for multiple layers instead of one.
*
* infill_area[x][n] is infill_area of (n+1) layers thick.
* infill_area[x][n] is infill_area of (n+1) layers thick.
*
* infill_area[0] corresponds to the most dense infill area.
* infill_area[x] will lie fully inside infill_area[x+1].
Expand Down Expand Up @@ -161,9 +162,9 @@ class SliceLayerPart
class SliceLayer
{
public:
coord_t printZ; //!< The height at which this layer needs to be printed. Can differ from sliceZ due to the raft.
coord_t thickness; //!< The thickness of this layer. Can be different when using variable layer heights.
std::vector<SliceLayerPart> parts; //!< An array of LayerParts which contain the actual data. The parts are printed one at a time to minimize travel outside of the 3D model.
coord_t printZ; //!< The height at which this layer needs to be printed. Can differ from sliceZ due to the raft.
coord_t thickness; //!< The thickness of this layer. Can be different when using variable layer heights.
std::vector<SliceLayerPart> parts; //!< An array of LayerParts which contain the actual data. The parts are printed one at a time to minimize travel outside of the 3D model.
Polygons openPolyLines; //!< A list of lines which were never hooked up into a 2D polygon. (Currently unused in normal operation)

/*!
Expand All @@ -174,9 +175,16 @@ class SliceLayer
*/
TopSurface top_surface;

/*!
* \brief The parts of the model that are exposed at the bottom(s) of the model.
*
* Note: Filled only when needed.
*/
Polygons bottom_surface;

/*!
* Get the all outlines of all layer parts in this layer.
*
*
* \param external_polys_only Whether to only include the outermost outline of each layer part
* \return A collection of all the outline polygons
*/
Expand All @@ -185,7 +193,7 @@ class SliceLayer
/*!
* Get the all outlines of all layer parts in this layer.
* Add those polygons to @p result.
*
*
* \param external_polys_only Whether to only include the outermost outline of each layer part
* \param result The result: a collection of all the outline polygons
*/
Expand All @@ -197,12 +205,10 @@ class SliceLayer
/******************/




class SupportLayer
{
public:
std::vector<SupportInfillPart> support_infill_parts; //!< a list of support infill parts
std::vector<SupportInfillPart> support_infill_parts; //!< a list of support infill parts
Polygons support_bottom; //!< Piece of support below the support and above the model. This must not overlap with any of the support_infill_parts or support_roof.
Polygons support_roof; //!< Piece of support above the support and below the model. This must not overlap with any of the support_infill_parts or support_bottom.
Polygons support_mesh_drop_down; //!< Areas from support meshes which should be supported by more support
Expand Down Expand Up @@ -253,8 +259,10 @@ class SliceMeshStorage
std::vector<AngleDegrees> roofing_angles; //!< a list of angle values which is cycled through to determine the roofing angle of each layer
std::vector<AngleDegrees> skin_angles; //!< a list of angle values which is cycled through to determine the skin angle of each layer
std::vector<Polygons> overhang_areas; //!< For each layer the areas that are classified as overhang on this mesh.
std::vector<Polygons> full_overhang_areas; //!< For each layer the full overhang without the tangent of the overhang angle removed, such that the overhang area adjoins the areas of the next layers.
std::vector<std::vector<Polygons>> overhang_points; //!< For each layer a list of points where point-overhang is detected. This is overhang that hasn't got any surface area, such as a corner pointing downwards.
std::vector<Polygons> full_overhang_areas; //!< For each layer the full overhang without the tangent of the overhang angle removed, such that the overhang area adjoins the
//!< areas of the next layers.
std::vector<std::vector<Polygons>> overhang_points; //!< For each layer a list of points where point-overhang is detected. This is overhang that hasn't got any surface area,
//!< such as a corner pointing downwards.
AABB3D bounding_box; //!< the mesh's bounding box

SubDivCube* base_subdiv_cube;
Expand Down Expand Up @@ -322,22 +330,23 @@ class SliceDataStorage : public NoCopy
std::vector<RetractionAndWipeConfig> retraction_wipe_config_per_extruder; //!< Config for retractions, extruder switch retractions, and wipes, per extruder.

SupportStorage support;

std::vector<SkirtBrimLine> skirt_brim[MAX_EXTRUDERS]; //!< Skirt/brim polygons per extruder, ordered from inner to outer polygons.
Polygons support_brim; //!< brim lines for support, going from the edge of the support inward. \note Not ordered by inset.
Polygons raftOutline; //Storage for the outline of the raft. Will be filled with lines when the GCode is generated.
Polygons primeRaftOutline; // ... the raft underneath the prime-tower will have to be printed first, if there is one. (When the raft has top layers with a different extruder for example.)
Polygons raftOutline; // Storage for the outline of the raft. Will be filled with lines when the GCode is generated.
Polygons primeRaftOutline; // ... the raft underneath the prime-tower will have to be printed first, if there is one. (When the raft has top layers with a different extruder
// for example.)

int max_print_height_second_to_last_extruder; //!< Used in multi-extrusion: the layer number beyond which all models are printed with the same extruder
std::vector<int> max_print_height_per_extruder; //!< For each extruder the highest layer number at which it is used.
std::vector<size_t> max_print_height_order; //!< Ordered indices into max_print_height_per_extruder: back() will return the extruder number with the highest print height.

std::vector<int> spiralize_seam_vertex_indices; //!< the index of the seam vertex for each layer
std::vector<Polygons* > spiralize_wall_outlines; //!< the wall outline polygons for each layer
std::vector<Polygons*> spiralize_wall_outlines; //!< the wall outline polygons for each layer

PrimeTower primeTower;

std::vector<Polygons> oozeShield; //oozeShield per layer
std::vector<Polygons> oozeShield; // oozeShield per layer
Polygons draft_protection_shield; //!< The polygons for a heightened skirt which protects from warping by gusts of wind and acts as a heated chamber.

/*!
Expand All @@ -352,7 +361,7 @@ class SliceDataStorage : public NoCopy

/*!
* Get all outlines within a given layer.
*
*
* \param layer_nr The index of the layer for which to get the outlines
* (negative layer numbers indicate the raft).
* \param include_support Whether to include support in the outline.
Expand All @@ -361,19 +370,21 @@ class SliceDataStorage : public NoCopy
* \param external_polys_only Whether to disregard all hole polygons.
* \param extruder_nr (optional) only give back outlines for this extruder (where the walls are printed with this extruder)
*/
Polygons getLayerOutlines(const LayerIndex layer_nr, const bool include_support, const bool include_prime_tower, const bool external_polys_only = false, const int extruder_nr = -1) const;
Polygons
getLayerOutlines(const LayerIndex layer_nr, const bool include_support, const bool include_prime_tower, const bool external_polys_only = false, const int extruder_nr = -1)
const;

/*!
* Get the extruders used.
*
*
* \return A vector of booleans indicating whether the extruder with the
* corresponding index is used in the mesh group.
*/
std::vector<bool> getExtrudersUsed() const;

/*!
* Get the extruders used on a particular layer.
*
*
* \param layer_nr the layer for which to check
* \return a vector of bools indicating whether the extruder with corresponding index is used in this layer.
*/
Expand Down Expand Up @@ -402,6 +413,6 @@ class SliceDataStorage : public NoCopy
std::vector<RetractionAndWipeConfig> initializeRetractionAndWipeConfigs();
};

}//namespace cura
} // namespace cura

#endif//SLICE_DATA_STORAGE_H
#endif // SLICE_DATA_STORAGE_H
15 changes: 14 additions & 1 deletion src/FffGcodeWriter.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2763,6 +2763,9 @@ void FffGcodeWriter::processSkinPrintFeature(
constexpr bool skip_some_zags = false;
constexpr int zag_skip_count = 0;
constexpr coord_t pocket_size = 0;
const bool small_areas_on_surface = mesh.settings.get<bool>("small_skin_on_surface");
const auto& current_layer = mesh.layers[gcode_layer.getLayerNr()];
const auto& exposed_to_air = current_layer.top_surface.areas.unionPolygons(current_layer.bottom_surface);

Infill infill_comp(
pattern,
Expand All @@ -2788,7 +2791,17 @@ void FffGcodeWriter::processSkinPrintFeature(
skip_some_zags,
zag_skip_count,
pocket_size);
infill_comp.generate(skin_paths, skin_polygons, skin_lines, mesh.settings, gcode_layer.getLayerNr(), SectionType::SKIN);
infill_comp.generate(
skin_paths,
skin_polygons,
skin_lines,
mesh.settings,
gcode_layer.getLayerNr(),
SectionType::SKIN,
nullptr,
nullptr,
nullptr,
small_areas_on_surface ? Polygons() : exposed_to_air);

// add paths
if (! skin_polygons.empty() || ! skin_lines.empty() || ! skin_paths.empty())
Expand Down
13 changes: 12 additions & 1 deletion src/FffPolygonGenerator.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -824,11 +824,22 @@ void FffPolygonGenerator::processSkinsAndInfill(SliceMeshStorage& mesh, const La
SkinInfillAreaComputation skin_infill_area_computation(layer_nr, mesh, process_infill);
skin_infill_area_computation.generateSkinsAndInfill();

if (mesh.settings.get<bool>("ironing_enabled") && (! mesh.settings.get<bool>("ironing_only_highest_layer") || mesh.layer_nr_max_filled_layer == layer_nr))
if (mesh.settings.get<bool>("ironing_enabled") && (! mesh.settings.get<bool>("ironing_only_highest_layer") || mesh.layer_nr_max_filled_layer == layer_nr)
|| ! mesh.settings.get<bool>("small_skin_on_surface"))
{
// Generate the top surface to iron over.
mesh.layers[layer_nr].top_surface.setAreasFromMeshAndLayerNumber(mesh, layer_nr);
}

if (layer_nr >= 0 && ! mesh.settings.get<bool>("small_skin_on_surface"))
{
// Generate the bottom surface.
mesh.layers[layer_nr].bottom_surface = mesh.layers[layer_nr].getOutlines();
if (layer_nr > 0)
{
mesh.layers[layer_nr].bottom_surface = mesh.layers[layer_nr].bottom_surface.difference(mesh.layers[layer_nr - 1].getOutlines());
}
}
}

void FffPolygonGenerator::computePrintHeightStatistics(SliceDataStorage& storage)
Expand Down
Loading
Loading