mirror of
https://github.com/SoftFever/OrcaSlicer.git
synced 2025-07-21 21:58:03 -06:00
Follow-up cedfc5e3fb
- Next code refactoring to avoid inconsistency between AutoColorChangeDetection in Preview and DoubleSlider
This commit is contained in:
parent
8befc43739
commit
5990f05418
3 changed files with 65 additions and 62 deletions
|
@ -38,23 +38,12 @@ using GUI::format_wxstr;
|
||||||
|
|
||||||
namespace DoubleSlider {
|
namespace DoubleSlider {
|
||||||
|
|
||||||
bool possible_threshold(const double& bottom_area, const double& top_area)
|
constexpr double min_delta_area = scale_(scale_(25)); // equal to 25 mm2
|
||||||
{
|
constexpr double miscalculation = scale_(scale_(1)); // equal to 1 mm2
|
||||||
// Check percent of the area decrease.
|
|
||||||
// This value have to be more than 25 mm2
|
|
||||||
return (bottom_area - top_area > min_delta_area()) &&
|
|
||||||
// and more 10%
|
|
||||||
(top_area / bottom_area < 0.9);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool equivalent_areas(const double& bottom_area, const double& top_area)
|
bool equivalent_areas(const double& bottom_area, const double& top_area)
|
||||||
{
|
{
|
||||||
return fabs(bottom_area - top_area <= min_threshold());
|
return fabs(bottom_area - top_area <= miscalculation);
|
||||||
}
|
|
||||||
|
|
||||||
bool overhang(const double& bottom_area, const double& top_area)
|
|
||||||
{
|
|
||||||
return top_area > bottom_area && !equivalent_areas(bottom_area, top_area);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
wxDEFINE_EVENT(wxCUSTOMEVT_TICKSCHANGED, wxEvent);
|
wxDEFINE_EVENT(wxCUSTOMEVT_TICKSCHANGED, wxEvent);
|
||||||
|
@ -2053,6 +2042,32 @@ void Control::show_cog_icon_context_menu()
|
||||||
GUI::wxGetApp().plater()->PopupMenu(&menu);
|
GUI::wxGetApp().plater()->PopupMenu(&menu);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool check_color_change(PrintObject* object, size_t frst_layer_id, size_t layers_cnt, std::function<bool(Layer*)> break_condition)
|
||||||
|
{
|
||||||
|
double prev_area = area(object->get_layer(frst_layer_id)->lslices);
|
||||||
|
|
||||||
|
bool detected = false;
|
||||||
|
for (size_t i = frst_layer_id+1; i < layers_cnt; i++) {
|
||||||
|
Layer* layer = object->get_layer(i);
|
||||||
|
double cur_area = area(layer->lslices);
|
||||||
|
|
||||||
|
// check for overhangs
|
||||||
|
if (cur_area > prev_area && !equivalent_areas(prev_area, cur_area))
|
||||||
|
break;
|
||||||
|
|
||||||
|
// Check percent of the area decrease.
|
||||||
|
// This value have to be more than min_delta_area and more then 10%
|
||||||
|
if ((prev_area - cur_area > min_delta_area) && (cur_area / prev_area < 0.9)) {
|
||||||
|
detected = true;
|
||||||
|
if (break_condition(layer))
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
prev_area = cur_area;
|
||||||
|
}
|
||||||
|
return detected;
|
||||||
|
}
|
||||||
|
|
||||||
void Control::auto_color_change()
|
void Control::auto_color_change()
|
||||||
{
|
{
|
||||||
if (!m_ticks.empty()) {
|
if (!m_ticks.empty()) {
|
||||||
|
@ -2071,16 +2086,9 @@ void Control::auto_color_change()
|
||||||
for (auto object : print.objects()) {
|
for (auto object : print.objects()) {
|
||||||
if (object->layer_count() == 0)
|
if (object->layer_count() == 0)
|
||||||
continue;
|
continue;
|
||||||
double prev_area = area(object->get_layer(0)->lslices);
|
|
||||||
|
|
||||||
for (size_t i = 1; i < object->layers().size(); i++) {
|
check_color_change(object, 1, object->layers().size(), [this, extruders_cnt](Layer* layer)
|
||||||
Layer* layer = object->get_layer(i);
|
{
|
||||||
double cur_area = area(layer->lslices);
|
|
||||||
|
|
||||||
if (overhang(prev_area, cur_area))
|
|
||||||
break;
|
|
||||||
|
|
||||||
if (possible_threshold(prev_area, cur_area)) {
|
|
||||||
int tick = get_tick_from_value(layer->print_z);
|
int tick = get_tick_from_value(layer->print_z);
|
||||||
if (tick >= 0 && !m_ticks.has_tick(tick)) {
|
if (tick >= 0 && !m_ticks.has_tick(tick)) {
|
||||||
if (m_mode == SingleExtruder) {
|
if (m_mode == SingleExtruder) {
|
||||||
|
@ -2088,19 +2096,20 @@ void Control::auto_color_change()
|
||||||
m_ticks.add_tick(tick, ColorChange, 1, layer->print_z);
|
m_ticks.add_tick(tick, ColorChange, 1, layer->print_z);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
m_ticks.add_tick(tick, ToolChange, extruder, layer->print_z);
|
int extruder = 2;
|
||||||
if (++extruder > extruders_cnt)
|
if (!m_ticks.empty()) {
|
||||||
|
auto it = m_ticks.ticks.end();
|
||||||
|
it--;
|
||||||
|
extruder = it->extruder + 1;
|
||||||
|
if (extruder > extruders_cnt)
|
||||||
extruder = 1;
|
extruder = 1;
|
||||||
}
|
}
|
||||||
|
m_ticks.add_tick(tick, ToolChange, extruder, layer->print_z);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// allow max 3 auto color changes
|
// allow max 3 auto color changes
|
||||||
if (m_ticks.ticks.size() == 3)
|
return m_ticks.ticks.size() > 2;
|
||||||
break;
|
});
|
||||||
}
|
|
||||||
|
|
||||||
prev_area = cur_area;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (m_ticks.empty())
|
if (m_ticks.empty())
|
||||||
|
|
|
@ -17,6 +17,8 @@ class wxMenu;
|
||||||
namespace Slic3r {
|
namespace Slic3r {
|
||||||
|
|
||||||
using namespace CustomGCode;
|
using namespace CustomGCode;
|
||||||
|
class PrintObject;
|
||||||
|
class Layer;
|
||||||
|
|
||||||
namespace DoubleSlider {
|
namespace DoubleSlider {
|
||||||
|
|
||||||
|
@ -25,12 +27,14 @@ namespace DoubleSlider {
|
||||||
*/
|
*/
|
||||||
constexpr double epsilon() { return 0.0011; }
|
constexpr double epsilon() { return 0.0011; }
|
||||||
|
|
||||||
constexpr double min_delta_area() { return scale_(scale_(25)); } // equal to 25 mm2
|
// return true when areas are mostly equivalent
|
||||||
constexpr double min_threshold() { return scale_(scale_(1)); } // equal to 1 mm2
|
|
||||||
|
|
||||||
bool possible_threshold(const double& bottom_area, const double& top_area);
|
|
||||||
bool equivalent_areas(const double& bottom_area, const double& top_area);
|
bool equivalent_areas(const double& bottom_area, const double& top_area);
|
||||||
bool overhang(const double& bottom_area, const double& top_area);
|
|
||||||
|
// return true if color change was detected
|
||||||
|
bool check_color_change(PrintObject* object, size_t frst_layer_id, size_t layers_cnt,
|
||||||
|
// what to do with detected color change
|
||||||
|
// and return true when detection have to be desturbed
|
||||||
|
std::function<bool(Layer*)> break_condition);
|
||||||
|
|
||||||
// custom message the slider sends to its parent to notify a tick-change:
|
// custom message the slider sends to its parent to notify a tick-change:
|
||||||
wxDECLARE_EVENT(wxCUSTOMEVT_TICKSCHANGED, wxEvent);
|
wxDECLARE_EVENT(wxCUSTOMEVT_TICKSCHANGED, wxEvent);
|
||||||
|
|
|
@ -720,35 +720,25 @@ void Preview::update_layers_slider(const std::vector<double>& layers_z, bool kee
|
||||||
if (i < min_solid_height)
|
if (i < min_solid_height)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
// bottom layer have to be a biggest, so control relation between bottom layer and object size
|
if (DoubleSlider::check_color_change(object, i, num_layers, [this, object](Layer*) {
|
||||||
double prev_area = area(object->get_layer(i)->lslices);
|
NotificationManager* notif_mngr = wxGetApp().plater()->get_notification_manager();
|
||||||
for ( i++; i < num_layers; i++) {
|
|
||||||
double cur_area = area(object->get_layer(i)->lslices);
|
|
||||||
if (DoubleSlider::overhang(prev_area, cur_area))
|
|
||||||
break;
|
|
||||||
prev_area = cur_area;
|
|
||||||
}
|
|
||||||
if (i < num_layers)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
double top_area = area(object->get_layer(int(object->layers().size()) - 1)->lslices);
|
|
||||||
if (DoubleSlider::possible_threshold(bottom_area, top_area)) {
|
|
||||||
NotificationManager *notif_mngr = wxGetApp().plater()->get_notification_manager();
|
|
||||||
notif_mngr->push_notification(
|
notif_mngr->push_notification(
|
||||||
NotificationType::SignDetected, NotificationManager::NotificationLevel::PrintInfoNotificationLevel,
|
NotificationType::SignDetected, NotificationManager::NotificationLevel::PrintInfoNotificationLevel,
|
||||||
_u8L("NOTE:") + "\n" + _u8L("Sliced object looks like the sign") + "\n",
|
_u8L("NOTE:") + "\n" +
|
||||||
_u8L("Apply auto color change to print"),
|
format(_u8L("Sliced object \"%1%\" looks like a logo or a sign"), object->model_object()->name) + "\n",
|
||||||
|
_u8L("Apply automatic color change"),
|
||||||
[this](wxEvtHandler*) {
|
[this](wxEvtHandler*) {
|
||||||
m_layers_slider->auto_color_change();
|
m_layers_slider->auto_color_change();
|
||||||
return true;
|
return true;
|
||||||
});
|
});
|
||||||
|
|
||||||
notif_mngr->apply_in_preview();
|
notif_mngr->apply_in_preview();
|
||||||
|
return true;
|
||||||
|
}) )
|
||||||
|
// first object with color chnages is found
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
m_layers_slider_sizer->Show((size_t)0);
|
m_layers_slider_sizer->Show((size_t)0);
|
||||||
Layout();
|
Layout();
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue