Fix flushing-volume warning for single-filament plates (#14704)

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Rodrigo Faselli <162915171+RF47@users.noreply.github.com>
This commit is contained in:
Robert J Audas
2026-08-13 14:50:55 -06:00
committed by GitHub
parent 56d2c527cb
commit 78eef79ffe
3 changed files with 104 additions and 15 deletions

View File

@@ -2397,6 +2397,55 @@ static void set_flush_volumes_matrix(std::vector<T> &out_matrix, const std::vect
}
}
template<class T>
static bool has_zero_flush_volume_for_used_filaments(const std::vector<T> &fv_matrix,
const std::vector<T> &flush_multipliers,
const std::vector<int> &used_filaments)
{
if (used_filaments.size() < 2 || flush_multipliers.empty())
return false;
if (fv_matrix.size() % flush_multipliers.size() != 0)
return false;
const size_t matrix_len = fv_matrix.size() / flush_multipliers.size();
const size_t row_len = size_t(std::sqrt(double(matrix_len)));
if (row_len < 2 || row_len * row_len != matrix_len)
return false;
std::vector<int> filtered_filaments;
filtered_filaments.reserve(used_filaments.size());
for (int filament_id : used_filaments) {
if (filament_id <= 0 || filament_id > int(row_len))
continue;
if (std::find(filtered_filaments.begin(), filtered_filaments.end(), filament_id) == filtered_filaments.end())
filtered_filaments.push_back(filament_id);
}
if (filtered_filaments.size() < 2)
return false;
for (T multiplier : flush_multipliers) {
if (multiplier == 0)
return true;
}
for (size_t nozzle_idx = 0; nozzle_idx < flush_multipliers.size(); nozzle_idx++) {
const size_t block_offset = nozzle_idx * matrix_len;
for (int from_id : filtered_filaments) {
for (int to_id : filtered_filaments) {
if (from_id == to_id)
continue;
const size_t matrix_idx = block_offset + size_t(from_id - 1) * row_len + size_t(to_id - 1);
if (matrix_idx < fv_matrix.size() && fv_matrix[matrix_idx] == 0)
return true;
}
}
}
return false;
}
size_t get_extruder_index(const GCodeConfig& config, unsigned int filament_id);
} // namespace Slic3r

View File

@@ -10738,24 +10738,14 @@ bool GLCanvas3D::is_flushing_matrix_error() {
if (!Sidebar::should_show_SEMM_buttons())
return false;
std::vector<int> plate_extruders = wxGetApp().plater()->get_partplate_list().get_curr_plate()->get_extruders(true);
if (plate_extruders.size() < 2)
return false;
const auto &project_config = wxGetApp().preset_bundle->project_config;
const std::vector<double> &config_matrix = (project_config.option<ConfigOptionFloats>("flush_volumes_matrix"))->values;
const std::vector<double> &config_multiplier = (project_config.option<ConfigOptionFloats>("flush_multiplier"))->values;
for (auto multiplier : config_multiplier) {
if (multiplier == 0) return true;
}
int matrix_len = config_matrix.size() / config_multiplier.size();
int row_len = std::sqrt(matrix_len);
for (int i = 0; i < config_matrix.size(); i++)
{
int relative_id = i % matrix_len;
int row_id = relative_id / row_len;
int col_id = relative_id % row_len;
if (row_id != col_id && config_matrix[i] == 0) return true;
}
return false;
return has_zero_flush_volume_for_used_filaments(config_matrix, config_multiplier, plate_extruders);
}
bool GLCanvas3D::_is_any_volume_outside() const

View File

@@ -235,6 +235,56 @@ SCENARIO("Config ini load/save interface", "[Config]") {
}
}
TEST_CASE("Flush-volume warning predicate respects used filament transitions", "[Config][Regression]")
{
const std::vector<double> multipliers = {1.0};
SECTION("Single used filament does not trigger warning with zero transition entries")
{
const std::vector<double> matrix = {
0.0, 0.0,
0.0, 0.0
};
const std::vector<int> used_filaments = {1};
REQUIRE_FALSE(has_zero_flush_volume_for_used_filaments(matrix, multipliers, used_filaments));
}
SECTION("Two used filaments trigger warning when transition flush entry is zero")
{
const std::vector<double> matrix = {
0.0, 0.0,
0.0, 0.0
};
const std::vector<int> used_filaments = {1, 2};
REQUIRE(has_zero_flush_volume_for_used_filaments(matrix, multipliers, used_filaments));
}
SECTION("Two used filaments do not trigger warning when transitions are non-zero")
{
const std::vector<double> matrix = {
0.0, 280.0,
280.0, 0.0
};
const std::vector<int> used_filaments = {1, 2};
REQUIRE_FALSE(has_zero_flush_volume_for_used_filaments(matrix, multipliers, used_filaments));
}
SECTION("Zero multiplier still triggers warning when multiple filaments are used")
{
const std::vector<double> matrix = {
0.0, 280.0,
280.0, 0.0
};
const std::vector<double> zero_multiplier = {0.0};
const std::vector<int> used_filaments = {1, 2};
REQUIRE(has_zero_flush_volume_for_used_filaments(matrix, zero_multiplier, used_filaments));
}
}
// TODO: https://github.com/SoftFever/OrcaSlicer/issues/11269 - Is this test still relevant? Delete if not.
// It was failing so at least "nozzle_type" and "extruder_printable_area" could not be serialized
// and an exception was thrown, but "nozzle_type" has been around for at least 3 months now.