Merge and fix conflicts

This commit is contained in:
Lam Wei Lun
2026-09-10 12:11:20 +08:00
33 changed files with 121 additions and 71 deletions
+2 -2
View File
@@ -162,7 +162,7 @@ static bool stl_read(stl_file *stl, FILE *fp, int first_facet, bool first, Impor
rewind(fp); rewind(fp);
try{ try{
char solid_name[256]; char solid_name[256];
int res_solid = fscanf(fp, " solid %[^\n]", solid_name); int res_solid = fscanf(fp, " solid %255[^\n]", solid_name);
if (res_solid == 1) { if (res_solid == 1) {
char* mw_position = strstr(solid_name, "MW"); char* mw_position = strstr(solid_name, "MW");
if (mw_position != NULL) { if (mw_position != NULL) {
@@ -170,7 +170,7 @@ static bool stl_read(stl_file *stl, FILE *fp, int first_facet, bool first, Impor
char version_str[16]; char version_str[16];
char model_id_str[128]; char model_id_str[128];
char country_code_str[16]; char country_code_str[16];
int num_values = sscanf(mw_position + 3, "%s %s %s", version_str, model_id_str, country_code_str); int num_values = sscanf(mw_position + 3, "%15s %127s %15s", version_str, model_id_str, country_code_str);
if (num_values == 3) { if (num_values == 3) {
if (strcmp(version_str, "1.0") == 0) { if (strcmp(version_str, "1.0") == 0) {
model_id = model_id_str; model_id = model_id_str;
+15 -9
View File
@@ -22,6 +22,7 @@
Match regexes; each must match at least one output line Match regexes; each must match at least one output line
NotMatch regexes; none may match any output line NotMatch regexes; none may match any output line
NotExists paths that must not exist after the case runs NotExists paths that must not exist after the case runs
DateStampedZip require a bundle date from during this case's invocation
.PARAMETER Name .PARAMETER Name
Run only the cases whose name matches this regex. Headings with no Run only the cases whose name matches this regex. Headings with no
@@ -109,12 +110,6 @@ $slnDir = Join-Path $fixtures 'sln'
New-Item -ItemType Directory -Force -Path $slnDir | Out-Null New-Item -ItemType Directory -Force -Path $slnDir | Out-Null
Set-Content -Path (Join-Path $slnDir 'OrcaSlicer.sln') -Value '' -Encoding ascii Set-Content -Path (Join-Path $slnDir 'OrcaSlicer.sln') -Value '' -Encoding ascii
# The pack stamp is checked against real dates, so a locale-dependent parse
# in the script cannot pass by looking date-shaped. Yesterday is accepted too,
# so a run that crosses midnight does not flake.
$dateStamps = @((Get-Date -Format 'yyyyMMdd'), (Get-Date).AddDays(-1).ToString('yyyyMMdd'))
$stampPattern = '_(' + ($dateStamps -join '|') + ')\.zip$'
$cases = @( $cases = @(
'argument handling' 'argument handling'
@{ Name = 'no arguments prints help'; Args = @(); DryRun = $false @{ Name = 'no arguments prints help'; Args = @(); DryRun = $false
@@ -326,12 +321,12 @@ $cases = @(
Contains = @('OrcaSlicer_dep_win-x64_') Contains = @('OrcaSlicer_dep_win-x64_')
NotContains = @('-clang', '-Release') } NotContains = @('-clang', '-Release') }
@{ Name = 'the bundle is stamped with today, not a shuffled date'; Args = @('-p') @{ Name = 'the bundle is stamped with today, not a shuffled date'; Args = @('-p')
Match = @($stampPattern) } DateStampedZip = $true }
# powershell.exe is not in System32 itself, so a trimmed PATH used to # powershell.exe is not in System32 itself, so a trimmed PATH used to
# leave the stamp empty and the bundle named OrcaSlicer_dep_win-x64_.zip. # leave the stamp empty and the bundle named OrcaSlicer_dep_win-x64_.zip.
@{ Name = 'the bundle is stamped even with a bare PATH'; Args = @('-p') @{ Name = 'the bundle is stamped even with a bare PATH'; Args = @('-p')
Env = @{ PATH = 'C:\Windows\system32;C:\Windows' } Env = @{ PATH = 'C:\Windows\system32;C:\Windows' }
Match = @($stampPattern) } DateStampedZip = $true }
@{ Name = '-p packs without rebuilding'; Args = @('-p') @{ Name = '-p packs without rebuilding'; Args = @('-p')
Match = @('^\+ .*(7z\.exe a|tar\.exe -a -c -f) ') Match = @('^\+ .*(7z\.exe a|tar\.exe -a -c -f) ')
NotContains = @('cmake -S deps') } NotContains = @('cmake -S deps') }
@@ -861,7 +856,7 @@ function Invoke-BuildScript {
$knownFields = @( $knownFields = @(
'Name', 'Args', 'ExpectExit', 'DryRun', 'First', 'Env', 'Name', 'Args', 'ExpectExit', 'DryRun', 'First', 'Env',
'Contains', 'NotContains', 'Match', 'NotMatch', 'NotExists' 'Contains', 'NotContains', 'Match', 'NotMatch', 'NotExists', 'DateStampedZip'
) )
function Test-Case { function Test-Case {
@@ -876,7 +871,9 @@ function Test-Case {
$expect = 0 $expect = 0
if ($Case.ContainsKey('ExpectExit')) { $expect = $Case['ExpectExit'] } if ($Case.ContainsKey('ExpectExit')) { $expect = $Case['ExpectExit'] }
$started = Get-Date
$result = Invoke-BuildScript -Arguments $argv -Environment $Case['Env'] $result = Invoke-BuildScript -Arguments $argv -Environment $Case['Env']
$finished = Get-Date
$problems = @() $problems = @()
@@ -902,6 +899,15 @@ function Test-Case {
$problems += "no line matching /$pattern/" $problems += "no line matching /$pattern/"
} }
} }
if ($Case['DateStampedZip']) {
# Bound the accepted dates to this invocation so crossing midnight is
# valid without allowing an unrelated past or future date.
$dateStamps = @($started.ToString('yyyyMMdd'), $finished.ToString('yyyyMMdd')) | Select-Object -Unique
$pattern = '_(' + ($dateStamps -join '|') + ')\.zip$'
if (@($lines | Where-Object { $_ -match $pattern }).Count -eq 0) {
$problems += "no line matching /$pattern/"
}
}
foreach ($pattern in $Case['NotMatch']) { foreach ($pattern in $Case['NotMatch']) {
foreach ($line in @($lines | Where-Object { $_ -match $pattern })) { foreach ($line in @($lines | Where-Object { $_ -match $pattern })) {
$problems += "line matches /$pattern/: $line" $problems += "line matches /$pattern/: $line"
+5 -5
View File
@@ -1925,7 +1925,7 @@ int CLI::run(int argc, char **argv)
} }
} }
catch (std::exception& e) { catch (std::exception& e) {
boost::nowide::cerr << construct_assemble_list << ": " << e.what() << std::endl; boost::nowide::cerr << "construct_assemble_list: " << e.what() << std::endl;
record_exit_reson(outfile_dir, CLI_DATA_FILE_ERROR, 0, cli_errors[CLI_DATA_FILE_ERROR], sliced_info); record_exit_reson(outfile_dir, CLI_DATA_FILE_ERROR, 0, cli_errors[CLI_DATA_FILE_ERROR], sliced_info);
flush_and_exit(CLI_DATA_FILE_ERROR); flush_and_exit(CLI_DATA_FILE_ERROR);
} }
@@ -1975,7 +1975,7 @@ int CLI::run(int argc, char **argv)
} }
std::unique_ptr<PresetBundle> cli_preset_bundle; std::unique_ptr<PresetBundle> cli_preset_bundle;
auto ensure_cli_preset_bundle = [&cli_preset_bundle, config_substitution_rule](std::string &error) -> PresetBundle * { auto ensure_cli_preset_bundle = [&cli_preset_bundle](std::string &error) -> PresetBundle * {
if (cli_preset_bundle) if (cli_preset_bundle)
return cli_preset_bundle.get(); return cli_preset_bundle.get();
try { try {
@@ -2002,7 +2002,7 @@ int CLI::run(int argc, char **argv)
} }
}; };
auto resolve_preset = [&ensure_cli_preset_bundle, config_substitution_rule](const std::string &file, DynamicPrintConfig &config, auto resolve_preset = [&ensure_cli_preset_bundle](const std::string &file, DynamicPrintConfig &config,
std::string &config_type, const std::string &config_from, std::string &config_type, const std::string &config_from,
bool probe_type, std::string &error) { bool probe_type, std::string &error) {
const auto *inherits = config.option<ConfigOptionString>(BBL_JSON_KEY_INHERITS); const auto *inherits = config.option<ConfigOptionString>(BBL_JSON_KEY_INHERITS);
@@ -2046,7 +2046,7 @@ int CLI::run(int argc, char **argv)
error, allow_source_manifest); error, allow_source_manifest);
}; };
auto load_config_file = [config_substitution_rule, &resolve_preset](const std::string& file, DynamicPrintConfig& config, std::string& config_type, auto load_config_file = [&resolve_preset](const std::string& file, DynamicPrintConfig& config, std::string& config_type,
std::string& config_name, std::string& filament_id, std::string& config_from) { std::string& config_name, std::string& filament_id, std::string& config_from) {
if (! boost::filesystem::exists(file)) { if (! boost::filesystem::exists(file)) {
boost::nowide::cerr << __FUNCTION__<< ": can not find setting file: " << file << std::endl; boost::nowide::cerr << __FUNCTION__<< ": can not find setting file: " << file << std::endl;
@@ -4826,7 +4826,7 @@ int CLI::run(int argc, char **argv)
} }
} }
if (!arrange_cfg.is_seq_print && (assemble_plate.filaments_count > 1)||(enable_wrapping_detect && !current_wrapping_exclude_area.empty())) if ((!arrange_cfg.is_seq_print && (assemble_plate.filaments_count > 1))||(enable_wrapping_detect && !current_wrapping_exclude_area.empty()))
{ {
//prepare the wipe tower //prepare the wipe tower
int plate_count = partplate_list.get_plate_count(); int plate_count = partplate_list.get_plate_count();
+1 -1
View File
@@ -297,7 +297,7 @@ int wmain(int argc, wchar_t **argv)
// printf("Loading Slic3r library: %S\n", path_to_slic3r); // printf("Loading Slic3r library: %S\n", path_to_slic3r);
HINSTANCE hInstance_Slic3r = LoadLibraryExW(path_to_slic3r, nullptr, 0); HINSTANCE hInstance_Slic3r = LoadLibraryExW(path_to_slic3r, nullptr, 0);
if (hInstance_Slic3r == nullptr) { if (hInstance_Slic3r == nullptr) {
printf("OrcaSlicer.dll was not loaded, error=%d\n", GetLastError()); printf("OrcaSlicer.dll was not loaded, error=%lu\n", GetLastError());
return -1; return -1;
} }
+1 -1
View File
@@ -364,7 +364,7 @@ void CStackWalker::GetModuleInformation(LPMODULE_INFO pmi)
if (dwInfoSize > 0) if (dwInfoSize > 0)
{ {
LPVOID lpData = new byte[dwInfoSize]; byte *lpData = new byte[dwInfoSize];
ZeroMemory(lpData, dwInfoSize * sizeof(byte)); ZeroMemory(lpData, dwInfoSize * sizeof(byte));
if (GetFileVersionInfo(pmi->szModulePath, dwHandle, dwInfoSize, lpData) > 0 ) if (GetFileVersionInfo(pmi->szModulePath, dwHandle, dwInfoSize, lpData) > 0 )
+1 -1
View File
@@ -49,7 +49,7 @@ SplittedLine split_line(const PathType& path, const ExPolygons& clip, bool close
// Convert the input path into an open ZPath // Convert the input path into an open ZPath
ClipperZUtils::ZPath p; ClipperZUtils::ZPath p;
p.reserve(path.size() + closed ? 1 : 0); p.reserve(path.size() + (closed ? 1 : 0));
ClipperLib_Z::cInt z = 0; ClipperLib_Z::cInt z = 0;
for (const auto& point : path) { for (const auto& point : path) {
p.emplace_back(point.x(), point.y(), z); p.emplace_back(point.x(), point.y(), z);
+11 -8
View File
@@ -3090,10 +3090,11 @@ bool FillRectilinear::fill_surface_trapezoidal(
case 0: // Grid / Trapezoidal case 0: // Grid / Trapezoidal
{ {
// Generate a non-crossing trapezoidal pattern to avoid overextrusion at intersections when `multiline > 1`. // Generate a non-crossing trapezoidal pattern to avoid overextrusion at intersections when `multiline > 1`.
// P2--P3 /*
// / \ * P2--P3
// P0_P1/ \P4_ * / \
// * P0_P1/ \P4_
*/
// P0xP1x=P4xP0x=d1/2 // P0xP1x=P4xP0x=d1/2
// P2xP3x=d1 // P2xP3x=d1
// P1yP2y=P2yP3y=d2 // P1yP2y=P2yP3y=d2
@@ -3171,10 +3172,12 @@ bool FillRectilinear::fill_surface_trapezoidal(
case 1: // Triangular case 1: // Triangular
{ {
// Generate a non-crossing trapezoidal pattern with a base line below. // Generate a non-crossing trapezoidal pattern with a base line below.
// P1-P2 /*
// / \ * P1-P2
// P0/ \P3_P4 * / \
// ---------------- * P0/ \P3_P4
* ----------------
*/
// P1xP2x=P3xP4x=d2 // P1xP2x=P3xP4x=d2
// P0yP1y=P2yP3y=h-2d1 // P0yP1y=P2yP3y=h-2d1
// //
+7 -4
View File
@@ -1468,9 +1468,11 @@ void GCodeProcessor::run_post_process()
// Append a per-filament usage block at a filament change. // Append a per-filament usage block at a filament change.
auto handle_filament_change = [&](int filament_id, int cur_line_id, int nozzle_id) { auto handle_filament_change = [&](int filament_id, int cur_line_id, int nozzle_id) {
// skip filament changes emitted inside the machine start / end gcode // Skip filament changes emitted inside the machine start / end gcode. One forward pass assigns
if (m_machine_start_gcode_end_line_id == (unsigned int) (-1) && (unsigned int) (cur_line_id) < m_machine_start_gcode_end_line_id || // the tag ids and tests them in the same loop, so inside the start gcode the end tag is unseen
m_machine_end_gcode_start_line_id != (unsigned int) (-1) && (unsigned int) (cur_line_id) > m_machine_end_gcode_start_line_id) // and the id still holds the sentinel. That is why the first clause tests == and the second !=.
if ((m_machine_start_gcode_end_line_id == (unsigned int) (-1) && (unsigned int) (cur_line_id) < m_machine_start_gcode_end_line_id) ||
(m_machine_end_gcode_start_line_id != (unsigned int) (-1) && (unsigned int) (cur_line_id) > m_machine_end_gcode_start_line_id))
return; return;
if (!m_filament_blocks.empty()) if (!m_filament_blocks.empty())
m_filament_blocks.back().upper_gcode_id = cur_line_id; m_filament_blocks.back().upper_gcode_id = cur_line_id;
@@ -2777,7 +2779,7 @@ bool GCodeProcessor::check_multi_extruder_gcode_valid(const int
std::map<int, std::map<int, GCodePosInfo>> gcode_path_pos; // object_id, filament_id, pos std::map<int, std::map<int, GCodePosInfo>> gcode_path_pos; // object_id, filament_id, pos
for (const GCodeProcessorResult::MoveVertex &move : m_result.moves) { for (const GCodeProcessorResult::MoveVertex &move : m_result.moves) {
// sometimes, the start line extrude was outside the edge of plate a little, this is allowed, so do not include into the gcode_path_pos // sometimes, the start line extrude was outside the edge of plate a little, this is allowed, so do not include into the gcode_path_pos
if (move.type == EMoveType::Extrude /* && move.extrusion_role != ExtrusionRole::erFlush || move.type == EMoveType::Travel*/) if (move.type == EMoveType::Extrude /* && move.extrusion_role != ExtrusionRole::erFlush || move.type == EMoveType::Travel*/) {
if (move.extrusion_role == ExtrusionRole::erCustom) { if (move.extrusion_role == ExtrusionRole::erCustom) {
/*if (move.is_arc_move_with_interpolation_points()) { /*if (move.is_arc_move_with_interpolation_points()) {
for (int i = 0; i < move.interpolation_points.size(); i++) { for (int i = 0; i < move.interpolation_points.size(); i++) {
@@ -2799,6 +2801,7 @@ bool GCodeProcessor::check_multi_extruder_gcode_valid(const int
gcode_path_pos[move.object_label_id][int(move.extruder_id)].max_print_z = std::max(gcode_path_pos[move.object_label_id][int(move.extruder_id)].max_print_z, gcode_path_pos[move.object_label_id][int(move.extruder_id)].max_print_z = std::max(gcode_path_pos[move.object_label_id][int(move.extruder_id)].max_print_z,
move.print_z); move.print_z);
} }
}
} }
bool valid = true; bool valid = true;
+1 -1
View File
@@ -3137,7 +3137,7 @@ void ToolOrdering::assign_custom_gcodes(const Print &print)
// Skip all custom G-codes above this layer and skip all extruder switches. // Skip all custom G-codes above this layer and skip all extruder switches.
for (; custom_gcode_it != custom_gcode_per_print_z.gcodes.rend() && ( for (; custom_gcode_it != custom_gcode_per_print_z.gcodes.rend() && (
(print_z_above > lt.print_z && custom_gcode_it->print_z > 0.5 * (lt.print_z + print_z_above)) (print_z_above > lt.print_z && custom_gcode_it->print_z > 0.5 * (lt.print_z + print_z_above))
|| custom_gcode_it->type == CustomGCode::ToolChange); ++ custom_gcode_it); || custom_gcode_it->type == CustomGCode::ToolChange); ++ custom_gcode_it) {}
print_z_above = lt.print_z; print_z_above = lt.print_z;
if (custom_gcode_it == custom_gcode_per_print_z.gcodes.rend()) if (custom_gcode_it == custom_gcode_per_print_z.gcodes.rend())
// Custom G-codes were processed. // Custom G-codes were processed.
+2 -6
View File
@@ -4971,12 +4971,8 @@ void WipeTower::generate_new(std::vector<std::vector<WipeTower::ToolChangeResult
} }
} }
if (!has_inserted) { if (!has_inserted && !finish_block_tcr.gcode.empty())
if (finish_block_tcr.gcode.empty()) finish_layer_tcr = merge_tcr(finish_layer_tcr, finish_block_tcr);
finish_block_tcr = finish_block_tcr;
else
finish_layer_tcr = merge_tcr(finish_layer_tcr, finish_block_tcr);
}
} }
} }
// record the contact layers of different categories // record the contact layers of different categories
+1 -1
View File
@@ -57,7 +57,7 @@
#define HAS_INTRINSIC_128_TYPE #define HAS_INTRINSIC_128_TYPE
#endif #endif
#if defined(_MSC_VER) && defined(_WIN64) #if defined(_MSC_VER) && defined(_M_X64)
#include <intrin.h> #include <intrin.h>
#pragma intrinsic(_mul128) #pragma intrinsic(_mul128)
#endif #endif
+4
View File
@@ -170,6 +170,10 @@ public:
this->m_check_sum = rhs.check_sum(); this->m_check_sum = rhs.check_sum();
this->m_connectors_cnt = rhs.connectors_cnt(); this->m_connectors_cnt = rhs.connectors_cnt();
} }
// A user-declared copy assignment or destructor deprecates the implicitly generated
// copy constructor, and this class has both, so declare it rather than rely on it.
CutObjectBase(const CutObjectBase &) = default;
CutObjectBase &operator=(const CutObjectBase &other) CutObjectBase &operator=(const CutObjectBase &other)
{ {
this->copy(other); this->copy(other);
+1 -1
View File
@@ -961,7 +961,7 @@ CopyFileResult copy_file(const std::string &from, const std::string &to, std::st
BOOL result = CopyFileW(src_wstr, dst_wstr, FALSE); BOOL result = CopyFileW(src_wstr, dst_wstr, FALSE);
if (!result) { if (!result) {
DWORD errCode = GetLastError(); DWORD errCode = GetLastError();
error_message = "Error: " + errCode; error_message = "Error: " + std::to_string(errCode);
ret = FAIL_COPY_FILE; ret = FAIL_COPY_FILE;
goto __finished; goto __finished;
} }
+1 -1
View File
@@ -406,7 +406,7 @@ void AmsMapingPopup::update_ams_data_multi_machines()
int ams_type = 1; int ams_type = 1;
int nozzle_id = 0; int nozzle_id = 0;
if (ams_type >= 1 || ams_type <= 3) { // 1:ams 2:ams-lite 3:n3f if (ams_type >= 1 && ams_type <= 3) { // 1:ams 2:ams-lite 3:n3f
auto sizer_mapping_list = new wxBoxSizer(wxHORIZONTAL); auto sizer_mapping_list = new wxBoxSizer(wxHORIZONTAL);
auto ams_mapping_item_container = new MappingContainer(nozzle_id == 0 ? m_right_marea_panel : m_left_marea_panel, "AMS-1", 4); auto ams_mapping_item_container = new MappingContainer(nozzle_id == 0 ? m_right_marea_panel : m_left_marea_panel, "AMS-1", 4);
+3 -1
View File
@@ -848,7 +848,9 @@ void BackgroundSlicingProcess::finalize_gcode()
case CopyFileResult::SUCCESS: break; // no error case CopyFileResult::SUCCESS: break; // no error
case CopyFileResult::FAIL_COPY_FILE: case CopyFileResult::FAIL_COPY_FILE:
throw Slic3r::ExportError(GUI::format( throw Slic3r::ExportError(GUI::format(
_L("Copying of the temporary G-code to the output G-code failed. Maybe the SD card is write locked?\nError message: %1%"), m_export_path_on_removable_media ?
_L("Copying of the temporary G-code to the output G-code failed. Maybe the SD card is write locked?\nError message: %1%") :
_L("Copying of the temporary G-code to the output G-code failed.\nError message: %1%"),
error_message)); error_message));
break; break;
case CopyFileResult::FAIL_FILES_DIFFERENT: case CopyFileResult::FAIL_FILES_DIFFERENT:
@@ -360,7 +360,7 @@ void CaliPresetCustomRangePanel::create_panel(wxWindow* parent)
int max_decimal_length; int max_decimal_length;
if (i <= 1) if (i <= 1)
max_decimal_length = 3; max_decimal_length = 3;
else if (i >= 2) else
max_decimal_length = 4; max_decimal_length = 4;
if (decimal_number > max_decimal_length) { if (decimal_number > max_decimal_length) {
int allowed_length = number.length() - decimal_number + max_decimal_length; int allowed_length = number.length() - decimal_number + max_decimal_length;
+1 -1
View File
@@ -872,7 +872,7 @@ namespace Slic3r
obj->m_is_online = elem["dev_online"].get<bool>(); obj->m_is_online = elem["dev_online"].get<bool>();
if (elem.contains("dev_model_name") && !elem["dev_model_name"].is_null()) { if (elem.contains("dev_model_name") && !elem["dev_model_name"].is_null()) {
auto printer_type = elem["dev_model_name"].get<std::string>(); auto printer_type = elem["dev_model_name"].get<std::string>();
for (const std::pair<std::string, std::vector<std::string>> &pair : device_subseries) { for (const auto &pair : device_subseries) {
auto it = std::find(pair.second.begin(), pair.second.end(), printer_type); auto it = std::find(pair.second.begin(), pair.second.end(), printer_type);
if (it != pair.second.end()) if (it != pair.second.end())
{ {
+2 -1
View File
@@ -2711,7 +2711,8 @@ void ColourPicker::set_value(const boost::any& value, bool change_event)
auto field = dynamic_cast<wxColourPickerCtrl*>(window); auto field = dynamic_cast<wxColourPickerCtrl*>(window);
#ifdef __WXMSW__ #ifdef __WXMSW__
wxColour clr = (clr_str.IsEmpty() || !clr.IsOk()) ? wxTransparentColour : clr_str; const wxColour parsed_clr(clr_str);
wxColour clr = (clr_str.IsEmpty() || !parsed_clr.IsOk()) ? wxTransparentColour : parsed_clr;
field->SetColour(clr); field->SetColour(clr);
draw_bmp_btn(field, clr); draw_bmp_btn(field, clr);
#else #else
+6 -6
View File
@@ -2191,7 +2191,7 @@ void GLCanvas3D::render(bool only_init)
// Negative coordinate means out of the window, likely because the window was deactivated. // Negative coordinate means out of the window, likely because the window was deactivated.
// In that case the tooltip should be hidden. // In that case the tooltip should be hidden.
if (m_mouse.position.x() >= 0. && m_mouse.position.y() >= 0. || has_mouse_capture()) { // ORCA continue to capture mouse pos mid drag if ((m_mouse.position.x() >= 0. && m_mouse.position.y() >= 0.) || has_mouse_capture()) { // ORCA continue to capture mouse pos mid drag
if (tooltip.empty()) if (tooltip.empty())
tooltip = m_layers_editing.get_tooltip(*this); tooltip = m_layers_editing.get_tooltip(*this);
@@ -9780,18 +9780,18 @@ void GLCanvas3D::_render_paint_toolbar() const
ImVec2 number_label_size = ImGui::CalcTextSize(std::to_string(i + 1).c_str()); ImVec2 number_label_size = ImGui::CalcTextSize(std::to_string(i + 1).c_str());
ImGui::SetCursorPosY(cursor_y + text_offset_y); ImGui::SetCursorPosY(cursor_y + text_offset_y);
ImGui::SetCursorPosX(spacing + i * (spacing + button_size.x) + (button_size.x - number_label_size.x) / 2); ImGui::SetCursorPosX(spacing + i * (spacing + button_size.x) + (button_size.x - number_label_size.x) / 2);
ImGui::TextColored(text_color, std::to_string(i + 1).c_str()); ImGui::TextColored(text_color, "%s", std::to_string(i + 1).c_str());
imgui.pop_bold_font(); imgui.pop_bold_font();
ImVec2 filament_first_line_label_size = ImGui::CalcTextSize(filament_text_first_line[i].c_str()); ImVec2 filament_first_line_label_size = ImGui::CalcTextSize(filament_text_first_line[i].c_str());
ImGui::SetCursorPosY(cursor_y + text_offset_y + number_label_size.y); ImGui::SetCursorPosY(cursor_y + text_offset_y + number_label_size.y);
ImGui::SetCursorPosX(spacing + i * (spacing + button_size.x) + (button_size.x - filament_first_line_label_size.x) / 2); ImGui::SetCursorPosX(spacing + i * (spacing + button_size.x) + (button_size.x - filament_first_line_label_size.x) / 2);
ImGui::TextColored(text_color, filament_text_first_line[i].c_str()); ImGui::TextColored(text_color, "%s", filament_text_first_line[i].c_str());
ImVec2 filament_second_line_label_size = ImGui::CalcTextSize(filament_text_second_line[i].c_str()); ImVec2 filament_second_line_label_size = ImGui::CalcTextSize(filament_text_second_line[i].c_str());
ImGui::SetCursorPosY(cursor_y + text_offset_y + number_label_size.y + filament_first_line_label_size.y); ImGui::SetCursorPosY(cursor_y + text_offset_y + number_label_size.y + filament_first_line_label_size.y);
ImGui::SetCursorPosX(spacing + i * (spacing + button_size.x) + (button_size.x - filament_second_line_label_size.x) / 2); ImGui::SetCursorPosX(spacing + i * (spacing + button_size.x) + (button_size.x - filament_second_line_label_size.x) / 2);
ImGui::TextColored(text_color, filament_text_second_line[i].c_str()); ImGui::TextColored(text_color, "%s", filament_text_second_line[i].c_str());
} }
if (ImGui::GetWindowWidth() == constraint_window_width) { if (ImGui::GetWindowWidth() == constraint_window_width) {
@@ -10018,9 +10018,9 @@ void GLCanvas3D::_render_assemble_info() const
double size1 = m_selection.get_bounding_box().size()(1); double size1 = m_selection.get_bounding_box().size()(1);
double size2 = m_selection.get_bounding_box().size()(2); double size2 = m_selection.get_bounding_box().size()(2);
if (!m_selection.is_empty()) { if (!m_selection.is_empty()) {
ImGui::Text(_L("Volume:").ToUTF8()); ImGui::SameLine(caption_max); ImGui::Text("%s", _L("Volume:").ToUTF8().data()); ImGui::SameLine(caption_max);
ImGui::Text("%.2f", size0 * size1 * size2); ImGui::Text("%.2f", size0 * size1 * size2);
ImGui::Text(_L("Size:").ToUTF8()); ImGui::SameLine(caption_max); ImGui::Text("%s", _L("Size:").ToUTF8().data()); ImGui::SameLine(caption_max);
ImGui::Text("%.2f x %.2f x %.2f", size0, size1, size2); ImGui::Text("%.2f x %.2f x %.2f", size0, size1, size2);
} }
imgui->end(); imgui->end();
+1 -1
View File
@@ -6808,7 +6808,7 @@ bool GUI_App::check_preset_parent_available(const std::pair<std::string, std::ma
void GUI_App::add_pending_vendor_preset(const std::pair<std::string, std::map<std::string, std::string>>& preset_data) void GUI_App::add_pending_vendor_preset(const std::pair<std::string, std::map<std::string, std::string>>& preset_data)
{ {
Preset::Type type; Preset::Type type = Preset::Type::TYPE_INVALID;
if (preset_data.second.at(BBL_JSON_KEY_TYPE) == PRESET_IOT_PRINT_TYPE) if (preset_data.second.at(BBL_JSON_KEY_TYPE) == PRESET_IOT_PRINT_TYPE)
type = Preset::Type::TYPE_PRINT; type = Preset::Type::TYPE_PRINT;
else if (preset_data.second.at(BBL_JSON_KEY_TYPE) == PRESET_IOT_PRINTER_TYPE) else if (preset_data.second.at(BBL_JSON_KEY_TYPE) == PRESET_IOT_PRINTER_TYPE)
+2 -2
View File
@@ -102,7 +102,7 @@ CopyFileResult copy_file_gui(const std::string &from, const std::string &to, std
result = ReadFile(handlesrc, buff, size, &dwRead, NULL); result = ReadFile(handlesrc, buff, size, &dwRead, NULL);
if (!result) { if (!result) {
DWORD errCode = GetLastError(); DWORD errCode = GetLastError();
error_message = "Error: " + errCode; error_message = "Error: " + std::to_string(errCode);
ret = FAIL_COPY_FILE; ret = FAIL_COPY_FILE;
goto __finished; goto __finished;
} }
@@ -110,7 +110,7 @@ CopyFileResult copy_file_gui(const std::string &from, const std::string &to, std
result = WriteFile(handledst,buff,size,&dwWrite,NULL); result = WriteFile(handledst,buff,size,&dwWrite,NULL);
if (!result) { if (!result) {
DWORD errCode = GetLastError(); DWORD errCode = GetLastError();
error_message = "Error: " + errCode; error_message = "Error: " + std::to_string(errCode);
ret = FAIL_COPY_FILE; ret = FAIL_COPY_FILE;
goto __finished; goto __finished;
} }
+1 -1
View File
@@ -342,7 +342,7 @@ bool GLGizmoBrimEars::on_mouse(const wxMouseEvent& mouse_event)
// concludes that the event was not intended for it, it should return false. // concludes that the event was not intended for it, it should return false.
bool GLGizmoBrimEars::gizmo_event(SLAGizmoEventType action, const Vec2d &mouse_position, bool shift_down, bool alt_down, bool control_down) bool GLGizmoBrimEars::gizmo_event(SLAGizmoEventType action, const Vec2d &mouse_position, bool shift_down, bool alt_down, bool control_down)
{ {
if (action != SLAGizmoEventType::MouseWheelDown || action != SLAGizmoEventType::MouseWheelUp || action != SLAGizmoEventType::Moving) { if (action != SLAGizmoEventType::MouseWheelDown && action != SLAGizmoEventType::MouseWheelUp && action != SLAGizmoEventType::Moving) {
apply_radius_change(); apply_radius_change();
} }
+1 -1
View File
@@ -122,7 +122,7 @@ bool GLGizmoFdmSupports::on_init()
{ctrl + _L("Mouse wheel"), _L("Gap area")} {ctrl + _L("Mouse wheel"), _L("Gap area")}
}; };
memset(&m_print_instance, 0, sizeof(m_print_instance)); m_print_instance = PrintInstance();
return true; return true;
} }
+2 -2
View File
@@ -343,12 +343,12 @@ void GLGizmoSimplify::on_render_input_window(float x, float y, float bottom_limi
ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing,ImVec2(10,20)); ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing,ImVec2(10,20));
if (is_worker_running) { // apply or preview if (is_worker_running) { // apply or preview
// draw progress bar // draw progress bar
std::string progress_text = GUI::format("%1%", std::to_string(progress)) + "%%"; std::string progress_text = GUI::format("%1%", std::to_string(progress)) + "%";
ImVec2 progress_size(bottom_left_width - space_size, 0.0f); ImVec2 progress_size(bottom_left_width - space_size, 0.0f);
ImGui::BBLProgressBar2(progress / 100., progress_size); ImGui::BBLProgressBar2(progress / 100., progress_size);
ImGui::SameLine(); ImGui::SameLine();
ImGui::AlignTextToFramePadding(); ImGui::AlignTextToFramePadding();
ImGui::TextColored(ImVec4(0.42f, 0.42f, 0.42f, 1.00f), progress_text.c_str()); ImGui::TextColored(ImVec4(0.42f, 0.42f, 0.42f, 1.00f), "%s", progress_text.c_str());
ImGui::SameLine(bottom_left_width + slider_width + m_imgui->scaled(1.0f)); ImGui::SameLine(bottom_left_width + slider_width + m_imgui->scaled(1.0f));
} else { } else {
ImGui::Dummy(ImVec2(bottom_left_width - space_size, -1)); ImGui::Dummy(ImVec2(bottom_left_width - space_size, -1));
+1 -1
View File
@@ -71,7 +71,7 @@ MediaPlayCtrl::MediaPlayCtrl(wxWindow *parent, wxMediaCtrl3 *media_ctrl, const w
auto ip = str.find(' ', ik); auto ip = str.find(' ', ik);
if (ip == wxString::npos) ip = str.Length(); if (ip == wxString::npos) ip = str.Length();
auto v = str.Mid(ik, ip - ik); auto v = str.Mid(ik, ip - ik);
if (k == "T:" && v.Length() == 8) { if (strcmp(k, "T:") == 0 && v.Length() == 8) {
long h = 0,m = 0,s = 0; long h = 0,m = 0,s = 0;
v.Left(2).ToLong(&h); v.Left(2).ToLong(&h);
v.Mid(3, 2).ToLong(&m); v.Mid(3, 2).ToLong(&m);
+1 -1
View File
@@ -498,7 +498,7 @@ void Mouse3DController::render_settings_dialog(GLCanvas3D& canvas) const
ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(20.0f, 20.0f)); ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(20.0f, 20.0f));
static ImVec2 last_win_size(0.0f, 0.0f); static ImVec2 last_win_size(0.0f, 0.0f);
bool shown = true; bool shown = true;
if (imgui.begin(_L("3Dconnexion settings"), &shown, ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoCollapse || ImGuiWindowFlags_NoTitleBar)) { if (imgui.begin(_L("3Dconnexion settings"), &shown, ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoTitleBar)) {
if (shown) { if (shown) {
ImVec2 win_size = ImGui::GetWindowSize(); ImVec2 win_size = ImGui::GetWindowSize();
if (last_win_size.x != win_size.x || last_win_size.y != win_size.y) { if (last_win_size.x != win_size.x || last_win_size.y != win_size.y) {
+2 -2
View File
@@ -3659,8 +3659,8 @@ void Sidebar::update_presets(Preset::Type preset_type)
// so extruders without an explicit sub-nozzle count never offer Hybrid. A nullable-int // so extruders without an explicit sub-nozzle count never offer Hybrid. A nullable-int
// nil is INT_MAX (> 1) and would otherwise falsely pass the gate, so exclude it too. // nil is INT_MAX (> 1) and would otherwise falsely pass the gate, so exclude it too.
if (boost::algorithm::contains(extruder_variants->values[index], type + " " + nozzle_volumes_def->enum_labels[i]) || if (boost::algorithm::contains(extruder_variants->values[index], type + " " + nozzle_volumes_def->enum_labels[i]) ||
extruder_max_nozzle_count->get_at(index) > 1 && extruder_max_nozzle_count->get_at(index) != ConfigOptionIntsNullable::nil_value() && (extruder_max_nozzle_count->get_at(index) > 1 && extruder_max_nozzle_count->get_at(index) != ConfigOptionIntsNullable::nil_value() &&
nozzle_volumes_def->enum_keys_map->at(nozzle_volumes_def->enum_values[i]) == nvtHybrid) { nozzle_volumes_def->enum_keys_map->at(nozzle_volumes_def->enum_values[i]) == nvtHybrid)) {
if (nozzle_volumes_def->enum_keys_map->at(nozzle_volumes_def->enum_values[i]) == NozzleVolumeType::nvtHighFlow &&(diameter == "0.2" || if (nozzle_volumes_def->enum_keys_map->at(nozzle_volumes_def->enum_values[i]) == NozzleVolumeType::nvtHighFlow &&(diameter == "0.2" ||
is_skip_high_flow_printer(printer_model))) is_skip_high_flow_printer(printer_model)))
continue; continue;
+1 -1
View File
@@ -3073,7 +3073,7 @@ static bool _HasExt(const std::vector<FilamentInfo> &ams_mapping_result) {
}; };
for (const auto &info : ams_mapping_result) { for (const auto &info : ams_mapping_result) {
if (info.ams_id == VIRTUAL_AMS_MAIN_ID_STR || info.ams_id == VIRTUAL_AMS_DEPUTY_ID_STR && !info.ams_id.empty()) { if (info.ams_id == VIRTUAL_AMS_MAIN_ID_STR || (info.ams_id == VIRTUAL_AMS_DEPUTY_ID_STR && !info.ams_id.empty())) {
return true; return true;
} }
} }
+2 -2
View File
@@ -678,7 +678,7 @@ SyncAmsInfoDialog::SyncAmsInfoDialog(wxWindow *parent, SyncInfo &info) :
wxBoxSizer *loading_Sizer = new wxBoxSizer(wxHORIZONTAL); wxBoxSizer *loading_Sizer = new wxBoxSizer(wxHORIZONTAL);
m_gif_ctrl = new wxAnimationCtrl(m_loading_page, wxID_ANY, wxNullAnimation, wxDefaultPosition, wxDefaultSize, wxAC_DEFAULT_STYLE); m_gif_ctrl = new wxAnimationCtrl(m_loading_page, wxID_ANY, wxNullAnimation, wxDefaultPosition, wxDefaultSize, wxAC_DEFAULT_STYLE);
auto gif_path = Slic3r::var("loading.gif").c_str(); const wxString gif_path = from_u8(Slic3r::var("loading.gif"));
if (m_gif_ctrl->LoadFile(gif_path)){ if (m_gif_ctrl->LoadFile(gif_path)){
m_gif_ctrl->SetSize(m_gif_ctrl->GetAnimation().GetSize()); m_gif_ctrl->SetSize(m_gif_ctrl->GetAnimation().GetSize());
m_gif_ctrl->Play(); m_gif_ctrl->Play();
@@ -1547,7 +1547,7 @@ bool SyncAmsInfoDialog::is_nozzle_type_match(DevExtderSystem data, wxString &err
auto sai_nz_pt = wxGetApp().preset_bundle->printers.get_edited_preset().get_printer_type(wxGetApp().preset_bundle); auto sai_nz_pt = wxGetApp().preset_bundle->printers.get_edited_preset().get_printer_type(wxGetApp().preset_bundle);
if (target_machine_nozzle_id == DEPUTY_EXTRUDER_ID) { if (target_machine_nozzle_id == DEPUTY_EXTRUDER_ID) {
pos = _L(DevPrinterConfigUtil::get_toolhead_display_name(sai_nz_pt, DEPUTY_EXTRUDER_ID, ToolHeadComponent::Nozzle, ToolHeadNameCase::LowerCase)); pos = _L(DevPrinterConfigUtil::get_toolhead_display_name(sai_nz_pt, DEPUTY_EXTRUDER_ID, ToolHeadComponent::Nozzle, ToolHeadNameCase::LowerCase));
} else if ((target_machine_nozzle_id == MAIN_EXTRUDER_ID)) { } else if (target_machine_nozzle_id == MAIN_EXTRUDER_ID) {
pos = _L(DevPrinterConfigUtil::get_toolhead_display_name(sai_nz_pt, MAIN_EXTRUDER_ID, ToolHeadComponent::Nozzle, ToolHeadNameCase::LowerCase)); pos = _L(DevPrinterConfigUtil::get_toolhead_display_name(sai_nz_pt, MAIN_EXTRUDER_ID, ToolHeadComponent::Nozzle, ToolHeadNameCase::LowerCase));
} }
-1
View File
@@ -23,7 +23,6 @@
#include "MsgDialog.hpp" #include "MsgDialog.hpp"
#include "PresetComboBoxes.hpp" #include "PresetComboBoxes.hpp"
#include "Widgets/RoundedRectangle.hpp"
#include "Widgets/CheckBox.hpp" #include "Widgets/CheckBox.hpp"
#include "Widgets/DialogButtons.hpp" #include "Widgets/DialogButtons.hpp"
#include "Widgets/HyperLink.hpp" #include "Widgets/HyperLink.hpp"
+4 -4
View File
@@ -254,10 +254,8 @@ int Http::priv::xfercb(void *userp, curl_off_t dltotal, curl_off_t dlnow, curl_o
bool cb_cancel = false; bool cb_cancel = false;
if (self->progressfn) { if (self->progressfn) {
double speed; double speed = 0.;
curl_easy_getinfo(self->curl, CURLINFO_SPEED_UPLOAD, &speed); curl_easy_getinfo(self->curl, CURLINFO_SPEED_UPLOAD, &speed);
if (speed > 0.01)
speed = speed;
Progress progress(dltotal, dlnow, ultotal, ulnow, self->buffer, speed); Progress progress(dltotal, dlnow, ultotal, ulnow, self->buffer, speed);
self->progressfn(progress, cb_cancel); self->progressfn(progress, cb_cancel);
} }
@@ -323,8 +321,10 @@ void Http::priv::form_add_file(const char *name, const fs::path &path, const cha
// We can't use CURLFORM_FILECONTENT, because curl doesn't support Unicode filenames on Windows // We can't use CURLFORM_FILECONTENT, because curl doesn't support Unicode filenames on Windows
// and so we use CURLFORM_STREAM with boost ifstream to read the file. // and so we use CURLFORM_STREAM with boost ifstream to read the file.
std::string filename_str;
if (filename == nullptr) { if (filename == nullptr) {
filename = path.string().c_str(); filename_str = path.string();
filename = filename_str.c_str();
} }
form_files.emplace_back(path, offset, length); form_files.emplace_back(path, offset, length);
+1 -1
View File
@@ -39,7 +39,7 @@ std::string find_closest_color_preset_by_vendor_and_type(const PresetCollection&
std::string p_color = p.config.opt_string("default_filament_colour", 0u); std::string p_color = p.config.opt_string("default_filament_colour", 0u);
unsigned int p_color_value; unsigned int p_color_value;
if (!p_color.empty()) { if (!p_color.empty()) {
unsigned int hash_pos = p_color.find("#"); size_t hash_pos = p_color.find("#");
p_color_value = std::stoul(p_color.substr(hash_pos != std::string::npos ? hash_pos + 1 : 0), nullptr, 16); p_color_value = std::stoul(p_color.substr(hash_pos != std::string::npos ? hash_pos + 1 : 0), nullptr, 16);
} else { } else {
// Default to black if no color specified in profile. Assume other profiles might be a closer color match. // Default to black if no color specified in profile. Assume other profiles might be a closer color match.
+36
View File
@@ -2,6 +2,13 @@
#include "libslic3r/Utils.hpp" #include "libslic3r/Utils.hpp"
#include "test_utils.hpp"
#include <algorithm>
#include <cctype>
#include <fstream>
#include <string>
#ifndef _WIN32 #ifndef _WIN32
#include <unistd.h> // getuid #include <unistd.h> // getuid
#endif #endif
@@ -52,3 +59,32 @@ TEST_CASE("per-user temp root is unchanged on Windows, isolated elsewhere", "[ut
REQUIRE_THAT(root, Catch::Matchers::StartsWith(base + "/orcaslicer_")); REQUIRE_THAT(root, Catch::Matchers::StartsWith(base + "/orcaslicer_"));
#endif #endif
} }
TEST_CASE("copy_file reports the OS error when the destination cannot be written", "[utils]") {
ScopedTemporaryFile source(".txt");
{
std::ofstream ofs(source.string(), std::ios::binary);
ofs << "orca";
}
REQUIRE(boost::filesystem::exists(source.path()));
// A directory that was never created, so the copy fails on every platform.
const boost::filesystem::path destination = source.path().parent_path() / "orca-missing-dir" / "copy.txt";
REQUIRE_FALSE(boost::filesystem::exists(destination.parent_path()));
std::string error_message;
REQUIRE(copy_file(source.string(), destination.string(), error_message) == FAIL_COPY_FILE);
REQUIRE_FALSE(error_message.empty());
#ifdef _WIN32
// The Windows branch formats GetLastError() itself. Writing that as
// "Error: " + errCode adds an integer to a string literal, which indexes into the
// literal instead of appending and runs off its end for any code above 7.
const std::string prefix = "Error: ";
REQUIRE(error_message.rfind(prefix, 0) == 0);
const std::string code = error_message.substr(prefix.size());
REQUIRE_FALSE(code.empty());
REQUIRE(std::all_of(code.begin(), code.end(), [](unsigned char c) { return std::isdigit(c) != 0; }));
#endif // _WIN32
}