GUI: the plate is open along Y for containment tests on an infinite-Y belt printer

PartPlate's containment tests treat the plate as open along Y on a belt printer with
belt_printer_infinite_y, so a long part is no longer flagged outside the plate in Prepare
while the slicer and the G-code checks accept it. The check reads the printer preset
through the app object, which does not exist headlessly, so it is guarded on the plater.
This commit is contained in:
harrierpigeon
2026-10-02 01:00:36 -05:00
parent b8a8e38ceb
commit f219431935
2 changed files with 20 additions and 0 deletions
+16
View File
@@ -2783,6 +2783,7 @@ bool PartPlate::check_outside(int obj_id, int instance_id, BoundingBoxf3* boundi
BoundingBoxf3 instance_box = bounding_box? *bounding_box: object->instance_convex_hull_bounding_box(instance_id);
Polygon hull = instance->convex_hull_2d();
BoundingBoxf3 plate_box = get_plate_box();
this->open_belt_y(plate_box);
if (instance_box.max.z() > plate_box.min.z())
plate_box.min.z() += instance_box.min.z(); // not considering outsize if sinking
@@ -3467,6 +3468,19 @@ Polygon PartPlate::get_shared_printable_polygon() const
return m_extruder_areas.empty() ? Polygon::new_scale(m_shape) : get_shared_poly(m_extruder_areas);
}
bool PartPlate::belt_open_y() const
{
// Headless (CLI) plates have no plater and no wxApp behind wxGetApp(); the CLI's own belt
// handling lives in Print::validate().
if (m_plater == nullptr || wxGetApp().preset_bundle == nullptr)
return false;
const DynamicPrintConfig &printer = wxGetApp().preset_bundle->printers.get_edited_preset().config;
const auto *belt = printer.option<ConfigOptionBool>("belt_printer");
const auto *infinite_y = printer.option<ConfigOptionBool>("belt_printer_infinite_y");
return belt != nullptr && belt->value && infinite_y != nullptr && infinite_y->value;
}
bool PartPlate::contains(const Vec3d& point) const
{
return m_bounding_box.contains(point);
@@ -3486,6 +3500,7 @@ bool PartPlate::contains(const BoundingBoxf3& bb) const
print_volume.min(1) -= Slic3r::BuildVolume::BedEpsilon;
print_volume.max(0) += Slic3r::BuildVolume::BedEpsilon;
print_volume.max(1) += Slic3r::BuildVolume::BedEpsilon;
this->open_belt_y(print_volume);
return print_volume.contains(bb);
}
@@ -3498,6 +3513,7 @@ bool PartPlate::intersects(const BoundingBoxf3& bb) const
print_volume.min(1) -= Slic3r::BuildVolume::BedEpsilon;
print_volume.max(0) += Slic3r::BuildVolume::BedEpsilon;
print_volume.max(1) += Slic3r::BuildVolume::BedEpsilon;
this->open_belt_y(print_volume);
return print_volume.intersects(bb);
}
+4
View File
@@ -427,6 +427,10 @@ public:
bool contains(const GLVolume& v) const;
bool contains(const BoundingBoxf3& bb) const;
bool intersects(const BoundingBoxf3& bb) const;
// A belt printer with belt_printer_infinite_y: the plate is open along Y for the
// containment tests (the drawn plate keeps its shape).
bool belt_open_y() const;
void open_belt_y(BoundingBoxf3 &box) const { if (this->belt_open_y()) { box.min.y() = -1e5; box.max.y() = 1e5; } }
void render(const Transform3d& view_matrix, const Transform3d& projection_matrix, bool bottom, bool only_body = false, bool force_background_color = false, HeightLimitMode mode = HEIGHT_LIMIT_NONE, int hover_id = -1, bool render_cali = false, bool show_grid = true);