mirror of
https://github.com/OrcaSlicer/OrcaSlicer.git
synced 2026-08-04 00:32:08 +00:00
Sync WipeTower from BambuStudio(through ca1881761)
This commit is contained in:
@@ -4017,10 +4017,33 @@ void Print::_make_wipe_tower()
|
||||
// in BBL machine, wipe tower is only use to prime extruder. So just use a global wipe volume.
|
||||
WipeTower wipe_tower(m_config, m_plate_index, m_origin, m_wipe_tower_data.tool_ordering.first_extruder(),
|
||||
m_wipe_tower_data.tool_ordering.empty() ? 0.f : m_wipe_tower_data.tool_ordering.back().print_z, m_wipe_tower_data.tool_ordering.all_extruders());
|
||||
// Orca: the tower's first-layer flow follows the user's first-layer flow ratio (BBS reads
|
||||
// its initial_layer_flow_ratio here — STUDIO-14254; first_layer_flow_ratio is Orca's analog,
|
||||
// default 1.0 in both). Honor the set_other_flow_ratios gate that governs the option
|
||||
// everywhere else.
|
||||
wipe_tower.set_first_layer_flow_ratio(m_default_object_config.set_other_flow_ratios
|
||||
? float(m_default_region_config.first_layer_flow_ratio)
|
||||
: 1.f);
|
||||
wipe_tower.set_has_tpu_filament(this->has_tpu_filament());
|
||||
wipe_tower.set_filament_map(this->get_filament_maps());
|
||||
// Vortek H2C: pass nozzle-level map for carousel rotation detection in tool_change_new()
|
||||
wipe_tower.set_filament_nozzle_map(this->get_filament_nozzle_maps());
|
||||
// Per-layer filament->nozzle grouping. sort_and_build_data() above publishes it on the Print
|
||||
// for by-layer prints; by-object prints publish only later (psSkirtBrim), so fall back to the
|
||||
// ToolOrdering's own copy there. set_extruder() below dereferences it, so it must be set first.
|
||||
auto print_group_result = get_layered_nozzle_group_result();
|
||||
const MultiNozzleUtils::LayeredNozzleGroupResult &nozzle_group_result =
|
||||
print_group_result ? *print_group_result : m_wipe_tower_data.tool_ordering.get_layered_nozzle_group_result();
|
||||
wipe_tower.set_nozzle_group_result(nozzle_group_result);
|
||||
{
|
||||
// Orca: acceleration options are object-scope (PrintConfig members in BBS), so resolve
|
||||
// the per-variant columns here; initial_layer_travel_acceleration is FloatOrPercent
|
||||
// over travel_acceleration and needs the full config to resolve.
|
||||
std::vector<double> first_layer_travel_accels;
|
||||
for (size_t i = 0; i < m_config.initial_layer_travel_acceleration.values.size(); ++i)
|
||||
first_layer_travel_accels.emplace_back(m_full_print_config.get_abs_value_at("initial_layer_travel_acceleration", i));
|
||||
wipe_tower.set_accelerations(m_default_object_config.default_acceleration.values,
|
||||
m_default_object_config.initial_layer_acceleration.values,
|
||||
m_default_object_config.travel_acceleration.values,
|
||||
first_layer_travel_accels);
|
||||
}
|
||||
// Feed the has_filament_switcher device flag (develop-only dynamic key, read defensively from
|
||||
// the full config — no shipping profile sets it) and the shared printable bed used by the PETG
|
||||
// pre-extrusion offset clamp. Both are inert unless has_filament_switcher is set.
|
||||
@@ -4056,27 +4079,19 @@ void Print::_make_wipe_tower()
|
||||
multi_extruder_flush.emplace_back(wipe_volumes);
|
||||
}
|
||||
|
||||
// Use NozzleStatusRecorder for per-carousel-slot tracking (BBS pattern).
|
||||
// The original Orca code tracked per-extruder (2 slots), which collapsed all
|
||||
// carousel filaments into one slot and caused massive redundant AMS flushing.
|
||||
auto group_result = get_layered_nozzle_group_result();
|
||||
// Per-carousel-slot purge tracking via NozzleStatusRecorder (BBS pattern); the layered
|
||||
// group result set on the tower above resolves each filament to its nozzle slot per layer.
|
||||
MultiNozzleUtils::NozzleStatusRecorder nozzle_recorder;
|
||||
// Fallback (group_result == null) per-physical-nozzle tracking, matching the original
|
||||
// pre-port behavior: remembers the last filament loaded in each physical nozzle slot.
|
||||
std::vector<unsigned int> nozzle_cur_filament_ids(nozzle_nums, (unsigned int) -1);
|
||||
|
||||
std::vector<int>filament_maps = get_filament_maps();
|
||||
int layer_idx = -1;
|
||||
|
||||
unsigned int current_filament_id = m_wipe_tower_data.tool_ordering.first_extruder();
|
||||
// Initialize NozzleStatusRecorder with the first filament's carousel slot
|
||||
if (group_result) {
|
||||
auto nozzle = group_result->get_nozzle_for_filament(current_filament_id, layer_idx);
|
||||
{
|
||||
auto nozzle = nozzle_group_result.get_nozzle_for_filament(current_filament_id, layer_idx);
|
||||
if (nozzle)
|
||||
nozzle_recorder.set_nozzle_status(nozzle->group_id, current_filament_id, nozzle->extruder_id);
|
||||
} else {
|
||||
size_t cur_nozzle_id = filament_maps[current_filament_id] - 1;
|
||||
nozzle_cur_filament_ids[cur_nozzle_id] = current_filament_id;
|
||||
}
|
||||
|
||||
for (auto& layer_tools : m_wipe_tower_data.tool_ordering.layer_tools()) { // for all layers
|
||||
@@ -4095,8 +4110,8 @@ void Print::_make_wipe_tower()
|
||||
float volume_to_purge = 0;
|
||||
|
||||
// Per-carousel-slot purge tracking via NozzleStatusRecorder
|
||||
if (group_result) {
|
||||
auto nozzle_info = group_result->get_nozzle_for_filament(filament_id, layer_idx);
|
||||
{
|
||||
auto nozzle_info = nozzle_group_result.get_nozzle_for_filament(filament_id, layer_idx);
|
||||
if (nozzle_info) {
|
||||
int extruder_id = nozzle_info->extruder_id;
|
||||
int nozzle_id = nozzle_info->group_id;
|
||||
@@ -4115,22 +4130,6 @@ void Print::_make_wipe_tower()
|
||||
}
|
||||
nozzle_recorder.set_nozzle_status(nozzle_id, filament_id, extruder_id);
|
||||
}
|
||||
} else {
|
||||
// Fallback: original Orca per-physical-nozzle path (non-carousel printers).
|
||||
// Flush source is the last filament that occupied THIS nozzle, guarded so the
|
||||
// first use of a nozzle incurs no flush.
|
||||
int nozzle_id = filament_maps[filament_id] - 1;
|
||||
unsigned int pre_filament_id = nozzle_cur_filament_ids[nozzle_id];
|
||||
if (pre_filament_id != (unsigned int) -1 && pre_filament_id != filament_id) {
|
||||
volume_to_purge = multi_extruder_flush[nozzle_id][pre_filament_id][filament_id];
|
||||
float flush_multiplier = (m_config.prime_volume_mode == PrimeVolumeMode::pvmFast)
|
||||
? m_config.flush_multiplier_fast.get_at(nozzle_id)
|
||||
: m_config.flush_multiplier.get_at(nozzle_id);
|
||||
volume_to_purge *= flush_multiplier;
|
||||
volume_to_purge = layer_tools.wiping_extrusions().mark_wiping_extrusions(
|
||||
*this, current_filament_id, filament_id, volume_to_purge);
|
||||
}
|
||||
nozzle_cur_filament_ids[nozzle_id] = filament_id;
|
||||
}
|
||||
|
||||
//During the filament change, the extruder will extrude an extra length of grab_length for the corresponding detection, so the purge can reduce this length.
|
||||
@@ -4138,29 +4137,21 @@ void Print::_make_wipe_tower()
|
||||
float grab_purge_volume = m_config.grab_length.get_at(grab_extruder_id) * 2.4; //(diameter/2)^2*PI=2.4
|
||||
volume_to_purge = std::max(0.f, volume_to_purge - grab_purge_volume);
|
||||
|
||||
// Select prime volume per-filament: nozzle change (carousel rotation) uses
|
||||
// filament_prime_volume_nc, filament change (same nozzle slot) uses filament_prime_volume.
|
||||
// Prime volume per-filament: the tower now picks extruder-change vs nozzle-change
|
||||
// (carousel) internally per plan layer, so pass both candidates (BBS pattern).
|
||||
float wipe_volume_ec = filament_id < m_config.filament_prime_volume.values.size()
|
||||
? m_config.filament_prime_volume.values[filament_id]
|
||||
: (float) m_config.prime_volume;
|
||||
float wipe_volume_nc = filament_id < m_config.filament_prime_volume_nc.values.size()
|
||||
? m_config.filament_prime_volume_nc.values[filament_id]
|
||||
: (float) m_config.prime_volume;
|
||||
|
||||
float prime_volume = wipe_volume_ec;
|
||||
if (group_result) {
|
||||
bool is_nozzle_change = group_result->are_filaments_same_extruder(current_filament_id, filament_id, layer_idx) &&
|
||||
!group_result->are_filaments_same_nozzle(current_filament_id, filament_id, layer_idx);
|
||||
if (is_nozzle_change) {
|
||||
prime_volume = wipe_volume_nc;
|
||||
}
|
||||
}
|
||||
if (m_config.prime_volume_mode == PrimeVolumeMode::pvmSaving) {
|
||||
prime_volume = 15.f;
|
||||
wipe_volume_ec = 15.f;
|
||||
wipe_volume_nc = 15.f;
|
||||
}
|
||||
|
||||
wipe_tower.plan_toolchange((float)layer_tools.print_z, (float)layer_tools.wipe_tower_layer_height, current_filament_id, filament_id,
|
||||
prime_volume, volume_to_purge);
|
||||
wipe_volume_ec, wipe_volume_nc, volume_to_purge);
|
||||
current_filament_id = filament_id;
|
||||
}
|
||||
layer_tools.wiping_extrusions().ensure_perimeters_infills_order(*this);
|
||||
|
||||
Reference in New Issue
Block a user