fix some bug

This commit is contained in:
QIDI TECH
2025-07-11 10:01:30 +08:00
parent f60592f1a0
commit 7f04d94ea1
5 changed files with 376 additions and 55 deletions

View File

@@ -44,6 +44,7 @@ set(IS_CROSS_COMPILE FALSE)
set(FLATPAK FALSE CACHE BOOL "Not copy FFMPEG file") set(FLATPAK FALSE CACHE BOOL "Not copy FFMPEG file")
if (APPLE) if (APPLE)
set(CMAKE_FIND_FRAMEWORK LAST) set(CMAKE_FIND_FRAMEWORK LAST)
set(CMAKE_FIND_APPBUNDLE LAST) set(CMAKE_FIND_APPBUNDLE LAST)
@@ -170,6 +171,14 @@ set(CMAKE_POSITION_INDEPENDENT_CODE ON)
# WIN10SDK_PATH is used to point CMake to the WIN10 SDK installation directory. # WIN10SDK_PATH is used to point CMake to the WIN10 SDK installation directory.
# We pick it from environment if it is not defined in another way # We pick it from environment if it is not defined in another way
if(WIN32) if(WIN32)
if(EXISTS "${CMAKE_SOURCE_DIR}/scripts/hooks/pre-commit" AND EXISTS "${CMAKE_SOURCE_DIR}/.git")
message(STATUS ".git: directory")
configure_file(
"${CMAKE_SOURCE_DIR}/scripts/hooks/pre-commit"
"${CMAKE_SOURCE_DIR}/.git/hooks/pre-commit"
)
endif()
find_package(PkgConfig REQUIRED) find_package(PkgConfig REQUIRED)
if(NOT DEFINED WIN10SDK_PATH) if(NOT DEFINED WIN10SDK_PATH)
if(DEFINED ENV{WIN10SDK_PATH}) if(DEFINED ENV{WIN10SDK_PATH})

View File

@@ -68,8 +68,11 @@ WORKDIR /QIDIStudio
# It might conflict with your mapped user, remove if user ubuntu exist # It might conflict with your mapped user, remove if user ubuntu exist
RUN if id "ubuntu" >/dev/null 2>&1; then userdel -r ubuntu; fi RUN if id "ubuntu" >/dev/null 2>&1; then userdel -r ubuntu; fi
# It's easier to run Bambu Studio as the same username,
# Use bash as the shell # UID and GID as your workstation. Since we bind mount
# your home directory into the container, it's handy
# to keep permissions the same. Just in case, defaults
# are root.
# Set ARG values # Set ARG values
# If user was passed from build it will create a user same # If user was passed from build it will create a user same
@@ -114,11 +117,8 @@ RUN ./BuildLinux.sh -s
ENV container=podman ENV container=podman
RUN ./BuildLinux.sh -i RUN ./BuildLinux.sh -i
# It's easier to run QIDI Studio as the same username,
# UID and GID as your workstation. Since we bind mount # Use bash as the shell
# your home directory into the container, it's handy
# to keep permissions the same. Just in case, defaults
# are root.
SHELL ["/bin/bash", "-l", "-c"] SHELL ["/bin/bash", "-l", "-c"]
# Point FFMPEG Library search to the binary built upon QIDIStudio build time # Point FFMPEG Library search to the binary built upon QIDIStudio build time

View File

@@ -438,7 +438,6 @@ static PrinterTechnology get_printer_technology(const DynamicConfig &config)
void record_exit_reson(std::string outputdir, int code, int plate_id, std::string error_message, sliced_info_t& sliced_info, std::map<std::string, std::string> key_values = std::map<std::string, std::string>()) void record_exit_reson(std::string outputdir, int code, int plate_id, std::string error_message, sliced_info_t& sliced_info, std::map<std::string, std::string> key_values = std::map<std::string, std::string>())
{ {
#if defined(__linux__) || defined(__LINUX__)
std::string result_file; std::string result_file;
if (!outputdir.empty()) if (!outputdir.empty())
@@ -460,6 +459,14 @@ void record_exit_reson(std::string outputdir, int code, int plate_id, std::strin
j["error_string"] = error_message; j["error_string"] = error_message;
j["prepare_time"] = sliced_info.prepare_time; j["prepare_time"] = sliced_info.prepare_time;
j["export_time"] = sliced_info.export_time; j["export_time"] = sliced_info.export_time;
if (code != 0)
{
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ":" << __LINE__
<< boost::format(" Slicer_Info_Report: plate_id=%1%, return_code=%2%, error_message=%3%\n") % plate_id % code % error_message;
}
for (size_t index = 0; index < sliced_info.sliced_plates.size(); index++) for (size_t index = 0; index < sliced_info.sliced_plates.size(); index++)
{ {
json plate_json; json plate_json;
@@ -504,6 +511,7 @@ void record_exit_reson(std::string outputdir, int code, int plate_id, std::strin
} }
//filament info //filament info
double filament_usage_g = 0.0;
if (!sliced_plate_info.filaments.empty()) if (!sliced_plate_info.filaments.empty())
{ {
for (size_t j = 0; j < sliced_plate_info.filaments.size(); j++) for (size_t j = 0; j < sliced_plate_info.filaments.size(); j++)
@@ -515,13 +523,23 @@ void record_exit_reson(std::string outputdir, int code, int plate_id, std::strin
filament_json["filament_id"] = filament.filament_id; filament_json["filament_id"] = filament.filament_id;
filament_json["total_used_g"] = filament.total_used_g; filament_json["total_used_g"] = filament.total_used_g;
filament_json["main_used_g"] = filament.main_used_g; filament_json["main_used_g"] = filament.main_used_g;
filament_usage_g += filament.total_used_g;
plate_json["filaments"].push_back(std::move(filament_json)); plate_json["filaments"].push_back(std::move(filament_json));
} }
} }
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ":" << __LINE__ << boost::format(" Slicer_Info_Report: plate_id=%1%, return_code=%2%, error_message=%3%, slice_time_s=%4%, pring_time_s=%5%, filament_usage_g=%6%\n")
% index
% code
% error_message
% (static_cast<double>(sliced_plate_info.sliced_time) / 1000.0)
% sliced_plate_info.total_predication
% filament_usage_g;
j["sliced_plates"].push_back(std::move(plate_json)); j["sliced_plates"].push_back(std::move(plate_json));
} }
#if defined(__linux__) || defined(__LINUX__)
for (auto& iter: key_values) for (auto& iter: key_values)
j[iter.first] = iter.second; j[iter.first] = iter.second;
@@ -529,11 +547,10 @@ void record_exit_reson(std::string outputdir, int code, int plate_id, std::strin
c.open(result_file, std::ios::out | std::ios::trunc); c.open(result_file, std::ios::out | std::ios::trunc);
c << std::setw(4) << j << std::endl; c << std::setw(4) << j << std::endl;
c.close(); c.close();
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ":" <<__LINE__ << boost::format(", saved config to %1%\n")%result_file; BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << ":" <<__LINE__ << boost::format(", saved config to %1%\n")%result_file;
#endif
} }
catch (...) {} catch (...) {}
#endif
} }
static int decode_png_to_thumbnail(std::string png_file, ThumbnailData& thumbnail_data) static int decode_png_to_thumbnail(std::string png_file, ThumbnailData& thumbnail_data)
@@ -1297,6 +1314,27 @@ static void load_downward_settings_list_from_config(std::string config_file, std
} }
} }
//y66
std::string normalizeString(const std::string& str) {
std::string result;
for (char ch : str) {
if (std::isalnum(ch) || ch == '.') {
result += std::tolower(ch);
}
}
return result;
}
//y66
bool containsSubstring(const std::string& str, const std::string& substr) {
std::string norm_str = normalizeString(str);
std::string norm_substr = normalizeString(substr);
if (norm_str.find(norm_substr) != std::string::npos) {
return true;
}
return false;
}
int CLI::run(int argc, char **argv) int CLI::run(int argc, char **argv)
{ {
// Mark the main thread for the debugger and for runtime checks. // Mark the main thread for the debugger and for runtime checks.
@@ -1381,6 +1419,7 @@ int CLI::run(int argc, char **argv)
boost::algorithm::iends_with(boost::filesystem::path(argv[0]).filename().string(), "gcodeviewer"); boost::algorithm::iends_with(boost::filesystem::path(argv[0]).filename().string(), "gcodeviewer");
#endif // _WIN32*/ #endif // _WIN32*/
bool translate_old = false, regenerate_thumbnails = false, keep_old_params = false, filament_color_changed = false, downward_check = false; bool translate_old = false, regenerate_thumbnails = false, keep_old_params = false, filament_color_changed = false, downward_check = false;
int current_printable_width, current_printable_depth, current_printable_height, shrink_to_new_bed = 0; int current_printable_width, current_printable_depth, current_printable_height, shrink_to_new_bed = 0;
int old_printable_height = 0, old_printable_width = 0, old_printable_depth = 0; int old_printable_height = 0, old_printable_width = 0, old_printable_depth = 0;
@@ -1388,7 +1427,7 @@ int CLI::run(int argc, char **argv)
float old_max_radius = 0.f, old_height_to_rod = 0.f, old_height_to_lid = 0.f, old_filament_prime_volume = 0.f; float old_max_radius = 0.f, old_height_to_rod = 0.f, old_height_to_lid = 0.f, old_filament_prime_volume = 0.f;
std::vector<double> old_max_layer_height, old_min_layer_height; std::vector<double> old_max_layer_height, old_min_layer_height;
std::string outfile_dir = m_config.opt_string("outputdir", true); std::string outfile_dir = m_config.opt_string("outputdir", true);
const std::vector<std::string> &load_configs = m_config.option<ConfigOptionStrings>("load_settings", true)->values; std::vector<std::string> &load_configs = m_config.option<ConfigOptionStrings>("load_settings", true)->values;
const std::vector<std::string> &uptodate_configs = m_config.option<ConfigOptionStrings>("uptodate_settings", true)->values; const std::vector<std::string> &uptodate_configs = m_config.option<ConfigOptionStrings>("uptodate_settings", true)->values;
const std::vector<std::string> &uptodate_filaments = m_config.option<ConfigOptionStrings>("uptodate_filaments", true)->values; const std::vector<std::string> &uptodate_filaments = m_config.option<ConfigOptionStrings>("uptodate_filaments", true)->values;
std::vector<std::string> downward_settings = m_config.option<ConfigOptionStrings>("downward_settings", true)->values; std::vector<std::string> downward_settings = m_config.option<ConfigOptionStrings>("downward_settings", true)->values;
@@ -1397,7 +1436,7 @@ int CLI::run(int argc, char **argv)
//QDS: always use ForwardCompatibilitySubstitutionRule::Enable //QDS: always use ForwardCompatibilitySubstitutionRule::Enable
//const ForwardCompatibilitySubstitutionRule config_substitution_rule = m_config.option<ConfigOptionEnum<ForwardCompatibilitySubstitutionRule>>("config_compatibility", true)->value; //const ForwardCompatibilitySubstitutionRule config_substitution_rule = m_config.option<ConfigOptionEnum<ForwardCompatibilitySubstitutionRule>>("config_compatibility", true)->value;
const ForwardCompatibilitySubstitutionRule config_substitution_rule = ForwardCompatibilitySubstitutionRule::Enable; const ForwardCompatibilitySubstitutionRule config_substitution_rule = ForwardCompatibilitySubstitutionRule::Enable;
const std::vector<std::string> &load_filaments = m_config.option<ConfigOptionStrings>("load_filaments", true)->values; std::vector<std::string> &load_filaments = m_config.option<ConfigOptionStrings>("load_filaments", true)->values;
//skip model object logic //skip model object logic
const std::vector<int> &skip_objects = m_config.option<ConfigOptionInts>("skip_objects", true)->values; const std::vector<int> &skip_objects = m_config.option<ConfigOptionInts>("skip_objects", true)->values;
std::map<int, bool> skip_maps; std::map<int, bool> skip_maps;
@@ -1410,6 +1449,168 @@ int CLI::run(int argc, char **argv)
if (downward_check_option) if (downward_check_option)
downward_check = downward_check_option->value; downward_check = downward_check_option->value;
#if 0
//y66
std::vector<std::string> temp_paths;
std::string default_serices = "X 4 Series";
std::string default_machine_type = "X-Plus 4";
std::string default_nozzle_type = "0.4";
std::string default_filament_type = "QIDI PLA Rapido";
std::string default_print_quality = "0.20mm Standard";
std::string target_path = "";
{
std::string machine_path_base = resources_dir() + "\\profiles\\" + default_serices + "\\machine";
for (const auto& entry : fs::directory_iterator(machine_path_base)) {
std::string filename = entry.path().filename().string();
if (containsSubstring(filename, default_machine_type) && containsSubstring(filename, default_nozzle_type)) {
target_path = entry.path().string();
break;
}
}
DynamicPrintConfig config;
ConfigSubstitutions config_substitutions;
std::map<std::string, std::string> key_values;
std::string reason;
config_substitutions = config.load_from_json(target_path, config_substitution_rule, key_values, reason);
std::string inherits = "";
if (config.has("inherits")) {
std::string new_inherits = config.opt_string("inherits");
while (inherits != new_inherits) {
for (const auto& entry : fs::directory_iterator(machine_path_base)) {
std::string filename = entry.path().filename().string();
if (containsSubstring(filename, new_inherits)) {
target_path = entry.path().string();
break;
}
}
DynamicPrintConfig new_config;
config_substitutions = new_config.load_from_json(target_path, config_substitution_rule, key_values, reason);
inherits = new_inherits;
if (new_config.has("inherits")) {
new_inherits = new_config.opt_string("inherits");
}
t_config_option_keys& new_config_keys = new_config.keys();
for (auto key : new_config_keys) {
if (!config.has(key)) {
ConfigOption* dest_opt = config.option(key, true);
dest_opt->set(new_config.option(key));
}
}
config.set_key_value("inherits", new ConfigOptionString(new_inherits));
}
}
std::string store_path = resources_dir() + "\\profiles\\temp_machine.json";
config.save_to_temp_json(store_path, key_values);
load_configs.emplace_back(store_path);
temp_paths.emplace_back(store_path);
}
{
std::string machine_path_base = resources_dir() + "\\profiles\\" + default_serices + "\\process";
for (const auto& entry : fs::directory_iterator(machine_path_base)) {
std::string filename = entry.path().filename().string();
if (containsSubstring(filename, default_print_quality) && containsSubstring(filename, default_machine_type)) {
target_path = entry.path().string();
break;
}
}
DynamicPrintConfig config;
ConfigSubstitutions config_substitutions;
std::map<std::string, std::string> key_values;
std::string reason;
config_substitutions = config.load_from_json(target_path, config_substitution_rule, key_values, reason);
std::string inherits = "";
if (config.has("inherits")) {
std::string new_inherits = config.opt_string("inherits");
while (inherits != new_inherits) {
for (const auto& entry : fs::directory_iterator(machine_path_base)) {
std::string filename = entry.path().filename().string();
if (containsSubstring(filename, new_inherits)) {
target_path = entry.path().string();
break;
}
}
DynamicPrintConfig new_config;
config_substitutions = new_config.load_from_json(target_path, config_substitution_rule, key_values, reason);
inherits = new_inherits;
if (new_config.has("inherits")) {
new_inherits = new_config.opt_string("inherits");
}
t_config_option_keys& new_config_keys = new_config.keys();
for (auto key : new_config_keys) {
if (!config.has(key)) {
ConfigOption* dest_opt = config.option(key, true);
dest_opt->set(new_config.option(key));
}
}
config.set_key_value("inherits", new ConfigOptionString(new_inherits));
}
}
std::string store_path = resources_dir() + "\\profiles\\temp_process.json";
config.save_to_temp_json(store_path, key_values);
load_configs.emplace_back(store_path);
temp_paths.emplace_back(store_path);
}
{
std::string machine_path_base = resources_dir() + "\\profiles\\" + default_serices + "\\filament";
for (const auto& entry : fs::directory_iterator(machine_path_base)) {
std::string filename = entry.path().filename().string();
std::string target_filename = default_filament_type + " @Qidi" + default_machine_type + " " + default_nozzle_type;
if (containsSubstring(filename, target_filename)) {
target_path = entry.path().string();
break;
}
}
DynamicPrintConfig config;
ConfigSubstitutions config_substitutions;
std::map<std::string, std::string> key_values;
std::string reason;
config_substitutions = config.load_from_json(target_path, config_substitution_rule, key_values, reason);
std::string inherits = "";
if (config.has("inherits")) {
std::string new_inherits = config.opt_string("inherits");
while (inherits != new_inherits) {
for (const auto& entry : fs::directory_iterator(machine_path_base)) {
DynamicPrintConfig temp_config;
std::map<std::string, std::string> temp_key_values;
std::string temp_reason;
config_substitutions = temp_config.load_from_json(entry.path().string(), config_substitution_rule, temp_key_values, temp_reason);
if (containsSubstring(temp_key_values["name"], new_inherits)) {
target_path = entry.path().string();
break;
}
}
DynamicPrintConfig new_config;
config_substitutions = new_config.load_from_json(target_path, config_substitution_rule, key_values, reason);
inherits = new_inherits;
if (new_config.has("inherits")) {
new_inherits = new_config.opt_string("inherits");
}
t_config_option_keys& new_config_keys = new_config.keys();
for (auto key : new_config_keys) {
if (!config.has(key)) {
ConfigOption* dest_opt = config.option(key, true);
dest_opt->set(new_config.option(key));
}
}
config.set_key_value("inherits", new ConfigOptionString(new_inherits));
}
}
std::string store_path = resources_dir() + "\\profiles\\temp_filament.json";
config.save_to_temp_json(store_path, key_values);
load_filaments.emplace_back(store_path);
temp_paths.emplace_back(store_path);
}
#endif
bool start_gui = m_actions.empty() && !downward_check; bool start_gui = m_actions.empty() && !downward_check;
if (start_gui) { if (start_gui) {
BOOST_LOG_TRIVIAL(info) << "no action, start gui directly" << std::endl; BOOST_LOG_TRIVIAL(info) << "no action, start gui directly" << std::endl;
@@ -1485,6 +1686,7 @@ int CLI::run(int argc, char **argv)
bool first_file = true, is_qdt_3mf = false, need_arrange = true, has_thumbnails = false, up_config_to_date = false, normative_check = true, duplicate_single_object = false, use_first_fila_as_default = false, minimum_save = false, enable_timelapse = false; bool first_file = true, is_qdt_3mf = false, need_arrange = true, has_thumbnails = false, up_config_to_date = false, normative_check = true, duplicate_single_object = false, use_first_fila_as_default = false, minimum_save = false, enable_timelapse = false;
bool allow_rotations = true, skip_modified_gcodes = false, avoid_extrusion_cali_region = false, skip_useless_pick = false, allow_newer_file = false, current_is_multi_extruder = false, new_is_multi_extruder = false, allow_mix_temp = false; bool allow_rotations = true, skip_modified_gcodes = false, avoid_extrusion_cali_region = false, skip_useless_pick = false, allow_newer_file = false, current_is_multi_extruder = false, new_is_multi_extruder = false, allow_mix_temp = false;
Semver file_version; Semver file_version;
Slic3r::GUI::Camera::ViewAngleType camera_view = Slic3r::GUI::Camera::ViewAngleType::Iso;
std::map<size_t, bool> orients_requirement; std::map<size_t, bool> orients_requirement;
std::vector<Preset*> project_presets; std::vector<Preset*> project_presets;
std::string new_printer_name, current_printer_name, new_process_name, current_process_name, current_printer_system_name, current_process_system_name, new_process_system_name, new_printer_system_name, printer_model_id, current_printer_model, printer_model, new_default_process_name; std::string new_printer_name, current_printer_name, new_process_name, current_process_name, current_printer_system_name, current_process_system_name, new_process_system_name, new_printer_system_name, printer_model_id, current_printer_model, printer_model, new_default_process_name;
@@ -1549,6 +1751,10 @@ int CLI::run(int argc, char **argv)
if (allow_mix_temp_option) if (allow_mix_temp_option)
allow_mix_temp = allow_mix_temp_option->value; allow_mix_temp = allow_mix_temp_option->value;
ConfigOptionInt* camera_view_option = m_config.option<ConfigOptionInt>("camera_view");
if (camera_view_option)
camera_view = (Slic3r::GUI::Camera::ViewAngleType)(camera_view_option->value);
ConfigOptionBool* avoid_extrusion_cali_region_option = m_config.option<ConfigOptionBool>("avoid_extrusion_cali_region"); ConfigOptionBool* avoid_extrusion_cali_region_option = m_config.option<ConfigOptionBool>("avoid_extrusion_cali_region");
if (avoid_extrusion_cali_region_option) if (avoid_extrusion_cali_region_option)
avoid_extrusion_cali_region = avoid_extrusion_cali_region_option->value; avoid_extrusion_cali_region = avoid_extrusion_cali_region_option->value;
@@ -2133,6 +2339,7 @@ int CLI::run(int argc, char **argv)
if (!is_qdt_3mf && config.option<ConfigOptionStrings>("different_settings_to_system")) { if (!is_qdt_3mf && config.option<ConfigOptionStrings>("different_settings_to_system")) {
std::vector<std::string> diff_settings = config.option<ConfigOptionStrings>("different_settings_to_system")->values; std::vector<std::string> diff_settings = config.option<ConfigOptionStrings>("different_settings_to_system")->values;
different_process_setting = diff_settings[0]; different_process_setting = diff_settings[0];
config.erase("different_settings_to_system");
} }
load_process_config = std::move(config); load_process_config = std::move(config);
BOOST_LOG_TRIVIAL(info) << boost::format("loaded process config %1%, type %2%, name %3%, inherits %4%")%file %config_name %config_from % new_process_system_name; BOOST_LOG_TRIVIAL(info) << boost::format("loaded process config %1%, type %2%, name %3%, inherits %4%")%file %config_name %config_from % new_process_system_name;
@@ -2946,7 +3153,7 @@ int CLI::run(int argc, char **argv)
} }
else { else {
//todo: support system process preset //todo: support system process preset
different_settings[0] = ""; different_settings[0] = different_process_setting;
if (new_process_config_is_system) if (new_process_config_is_system)
inherits_group[0] = ""; inherits_group[0] = "";
else else
@@ -3087,7 +3294,17 @@ int CLI::run(int argc, char **argv)
config.erase("filament_settings_id"); config.erase("filament_settings_id");
//todo: update different settings of filaments //todo: update different settings of filaments
if (config.option("different_settings_to_system")) {
std::vector<std::string> filament_different_settings = config.option<ConfigOptionStrings>("different_settings_to_system", true)->values;
if (filament_different_settings.empty())
different_settings[filament_index] = ""; different_settings[filament_index] = "";
else
different_settings[filament_index] = filament_different_settings[0];
config.erase("different_settings_to_system");
}
else {
different_settings[filament_index] = "";
}
inherits_group[filament_index] = load_filaments_inherit[index]; inherits_group[filament_index] = load_filaments_inherit[index];
} }
else { else {
@@ -3775,7 +3992,10 @@ int CLI::run(int argc, char **argv)
ConfigOptionFloat* brim_width_option = print_config.option<ConfigOptionFloat>("prime_tower_brim_width", true); ConfigOptionFloat* brim_width_option = print_config.option<ConfigOptionFloat>("prime_tower_brim_width", true);
float brim_width = brim_width_option->value; float brim_width = brim_width_option->value;
if (brim_width < 0) brim_width = WipeTower::get_auto_brim_by_height((float)plate_obj_size_info.obj_bbox.max.z()); if (brim_width < 0)
brim_width = WipeTower::get_auto_brim_by_height((float)plate_obj_size_info.obj_bbox.max.z());
//if (brim_width < WIPE_TOWER_MARGIN)
// brim_width = WIPE_TOWER_MARGIN;
ConfigOptionFloats* volume_option = print_config.option<ConfigOptionFloats>("filament_prime_volume", true); ConfigOptionFloats* volume_option = print_config.option<ConfigOptionFloats>("filament_prime_volume", true);
std::vector<double> wipe_volume = volume_option->values; std::vector<double> wipe_volume = volume_option->values;
@@ -3785,9 +4005,9 @@ int CLI::run(int argc, char **argv)
plate_obj_size_info.wipe_depth = wipe_tower_size(1); plate_obj_size_info.wipe_depth = wipe_tower_size(1);
Vec3d origin = plate->get_origin(); Vec3d origin = plate->get_origin();
Vec3d start(origin(0) + plate_obj_size_info.wipe_x - brim_width, origin(1) + plate_obj_size_info.wipe_y, 0.f); Vec3d start(origin(0) + plate_obj_size_info.wipe_x - brim_width, origin(1) + plate_obj_size_info.wipe_y - brim_width, 0.f);
plate_obj_size_info.obj_bbox.merge(start); plate_obj_size_info.obj_bbox.merge(start);
Vec3d end(origin(0) + plate_obj_size_info.wipe_x + plate_obj_size_info.wipe_width + brim_width, origin(1) + plate_obj_size_info.wipe_y + plate_obj_size_info.wipe_depth, 0.f); Vec3d end(origin(0) + plate_obj_size_info.wipe_x + plate_obj_size_info.wipe_width + brim_width, origin(1) + plate_obj_size_info.wipe_y + plate_obj_size_info.wipe_depth + brim_width, 0.f);
plate_obj_size_info.obj_bbox.merge(end); plate_obj_size_info.obj_bbox.merge(end);
plate_obj_size_info.has_wipe_tower = true; plate_obj_size_info.has_wipe_tower = true;
BOOST_LOG_TRIVIAL(info) << boost::format("plate %1%, has wipe tower, wipe bbox: min {%2%, %3%, %4%} - max {%5%, %6%, %7%}") BOOST_LOG_TRIVIAL(info) << boost::format("plate %1%, has wipe tower, wipe bbox: min {%2%, %3%, %4%} - max {%5%, %6%, %7%}")
@@ -4386,6 +4606,10 @@ int CLI::run(int argc, char **argv)
if (orients_requirement[o->id().id]) if (orients_requirement[o->id().id])
{ {
BOOST_LOG_TRIVIAL(info) << "Before process command, Orient object, name=" << o->name <<",id="<<o->id().id<<std::endl; BOOST_LOG_TRIVIAL(info) << "Before process command, Orient object, name=" << o->name <<",id="<<o->id().id<<std::endl;
if (!load_process_config.empty())
{
o->config.assign_config(load_process_config);
}
orientation::orient(o); orientation::orient(o);
oriented_or_arranged = true; oriented_or_arranged = true;
} }
@@ -5322,11 +5546,12 @@ int CLI::run(int argc, char **argv)
// loop through action options // loop through action options
bool export_to_3mf = false, load_slicedata = false, export_slicedata = false, export_slicedata_error = false; bool export_to_3mf = false, load_slicedata = false, export_slicedata = false, export_slicedata_error = false;
bool export_to_gcode = false;
bool no_check = false; bool no_check = false;
std::string export_3mf_file, load_slice_data_dir, export_slice_data_dir, export_stls_dir; std::string export_3mf_file, load_slice_data_dir, export_slice_data_dir, export_stls_dir, export_gcode_file;
std::vector<ThumbnailData*> calibration_thumbnails; std::vector<ThumbnailData*> calibration_thumbnails;
std::vector<int> plate_object_count(partplate_list.get_plate_count(), 0); std::vector<int> plate_object_count(partplate_list.get_plate_count(), 0);
int max_slicing_time_per_plate = 0, max_triangle_count_per_plate = 0, sliced_plate = -1; int max_slicing_time_per_plate = 0, max_triangle_count_per_plate = 0, sliced_plate = -1, export_png = -1;
std::vector<bool> plate_has_skips(partplate_list.get_plate_count(), false); std::vector<bool> plate_has_skips(partplate_list.get_plate_count(), false);
std::vector<std::vector<size_t>> plate_skipped_objects(partplate_list.get_plate_count()); std::vector<std::vector<size_t>> plate_skipped_objects(partplate_list.get_plate_count());
@@ -5538,9 +5763,21 @@ int CLI::run(int argc, char **argv)
} */else if (opt_key == "export_3mf") { } */else if (opt_key == "export_3mf") {
export_to_3mf = true; export_to_3mf = true;
export_3mf_file = m_config.opt_string(opt_key); export_3mf_file = m_config.opt_string(opt_key);
}else if(opt_key=="no_check"){ }
else if (opt_key == "export_png") {
export_png = m_config.option<ConfigOptionInt>("export_png")->value;
if (m_actions.size() > 1) {
BOOST_LOG_TRIVIAL(error) << "should not set export_png with other actions together." << std::endl;
record_exit_reson(outfile_dir, CLI_INVALID_PARAMS, 0, cli_errors[CLI_INVALID_PARAMS], sliced_info);
flush_and_exit(CLI_INVALID_PARAMS);
}
}
else if(opt_key=="no_check"){
no_check = m_config.opt_bool(opt_key); no_check = m_config.opt_bool(opt_key);
//} else if (opt_key == "export_gcode" || opt_key == "export_sla" || opt_key == "slice") { //} else if (opt_key == "export_gcode" || opt_key == "export_sla" || opt_key == "slice") {
}else if(opt_key == "export_gcode"){
export_to_gcode = true;
export_gcode_file = m_config.opt_string(opt_key);
} else if (opt_key == "normative_check") { } else if (opt_key == "normative_check") {
//already processed before //already processed before
} else if (opt_key == "export_slicedata") { } else if (opt_key == "export_slicedata") {
@@ -5820,17 +6057,6 @@ int CLI::run(int argc, char **argv)
else else
filament_maps = part_plate->get_real_filament_maps(m_print_config); filament_maps = part_plate->get_real_filament_maps(m_print_config);
std::vector<std::string>& unprintable_filament_types = m_print_config.option<ConfigOptionStrings>("unprintable_filament_types", true)->values;
std::vector<std::vector<std::string>>unprintable_filament_type_list;
unprintable_filament_type_list.resize(new_extruder_count);
for (int index = 0; index < new_extruder_count; index++)
{
std::vector<std::string> unprintable_list;
if (unprintable_filament_types.size() > index)
unprintable_list = split_string(unprintable_filament_types[index], ',');
unprintable_filament_type_list[index] = unprintable_list;
}
for (int index = 0; index < filament_maps.size(); index++) for (int index = 0; index < filament_maps.size(); index++)
{ {
int filament_extruder = filament_maps[index]; int filament_extruder = filament_maps[index];
@@ -5842,18 +6068,22 @@ int CLI::run(int argc, char **argv)
} }
} }
for (int f_index = 0; f_index < plate_filaments.size(); f_index++) {
for (int f_index = 0; f_index < plate_filaments.size(); f_index++) { for (int f_index = 0; f_index < plate_filaments.size(); f_index++) {
if (plate_filaments[f_index] <= filament_count) { if (plate_filaments[f_index] <= filament_count) {
int filament_extruder = filament_maps[plate_filaments[f_index] - 1]; int filament_extruder = filament_maps[plate_filaments[f_index] - 1];
std::vector<std::string>& unprintable_list = unprintable_filament_type_list[filament_extruder-1];
std::string filament_type; std::string filament_type;
m_print_config.get_filament_type(filament_type, plate_filaments[f_index] - 1); m_print_config.get_filament_type(filament_type, plate_filaments[f_index] - 1);
if (unprintable_list.size() > 0) auto *filament_printable_status = dynamic_cast<const ConfigOptionInts *>(m_print_config.option("filament_printable"));
{ if (filament_printable_status && (filament_printable_status->values.size() >= plate_filaments[f_index])) {
auto iter = std::find(unprintable_list.begin(), unprintable_list.end(), filament_type); int status = filament_printable_status->values.at(plate_filaments[f_index] - 1);
if (iter != unprintable_list.end()) { if (!(status >> (filament_extruder - 1) & 1)) {
BOOST_LOG_TRIVIAL(error) << boost::format("plate %1% : filament %2% can not be printed on extruder %3%, under manual mode for multi extruder printer") % (index + 1) %filament_type %filament_extruder; BOOST_LOG_TRIVIAL(error)
record_exit_reson(outfile_dir, CLI_FILAMENTS_NOT_SUPPORTED_BY_EXTRUDER, index + 1, cli_errors[CLI_FILAMENTS_NOT_SUPPORTED_BY_EXTRUDER], sliced_info); << boost::format(
"plate %1% : filament %2% can not be printed on extruder %3%, under manual mode for multi extruder printer") %
(index + 1) % filament_type % filament_extruder;
record_exit_reson(outfile_dir, CLI_FILAMENTS_NOT_SUPPORTED_BY_EXTRUDER, index + 1,
cli_errors[CLI_FILAMENTS_NOT_SUPPORTED_BY_EXTRUDER], sliced_info);
flush_and_exit(CLI_FILAMENTS_NOT_SUPPORTED_BY_EXTRUDER); flush_and_exit(CLI_FILAMENTS_NOT_SUPPORTED_BY_EXTRUDER);
} }
} }
@@ -5861,6 +6091,7 @@ int CLI::run(int argc, char **argv)
} }
} }
} }
}
plate_triangle_counts[index] = triangle_count; plate_triangle_counts[index] = triangle_count;
plate_object_count[index] = printable_instances; plate_object_count[index] = printable_instances;
@@ -7011,6 +7242,62 @@ int CLI::run(int argc, char **argv)
for (int i = 0; i < plate_bboxes.size(); i++) for (int i = 0; i < plate_bboxes.size(); i++)
delete plate_bboxes[i]; delete plate_bboxes[i];
} }
else if (export_png >= 0)
{
std::vector<ThumbnailData*> thumbnails;
PlateDataPtrs plate_data_list;
partplate_list.store_to_3mf_structure(plate_data_list);
if (!opengl_valid)
opengl_valid = init_opengl_and_colors(m_models[0], colors);
if (opengl_valid) {
Model& model = m_models[0];
p_opengl_mgr->bind_vao();
p_opengl_mgr->bind_shader(shader);
for (int i = 0; i < partplate_list.get_plate_count(); i++) {
Slic3r::GUI::PartPlate* part_plate = partplate_list.get_plate(i);
PlateData* plate_data = plate_data_list[i];
ThumbnailData* thumbnail_data = &plate_data->plate_thumbnail;
if ((export_png != 0) && (export_png != (i + 1))) {
BOOST_LOG_TRIVIAL(info) << boost::format("Line %1%: export png, Skip plate %2%.") % __LINE__ % (i + 1);
}
else {
unsigned int thumbnail_width = 512, thumbnail_height = 512;
const ThumbnailsParams thumbnail_params = { {}, false, true, true, true, i };
BOOST_LOG_TRIVIAL(info) << boost::format("plate %1%'s png, need to generate") % (i + 1);
Slic3r::GUI::GLCanvas3D::render_thumbnail_framebuffer(p_opengl_mgr, *thumbnail_data,
thumbnail_width, thumbnail_height, thumbnail_params,
partplate_list, model.objects, glvolume_collection, colors_out, shader, Slic3r::GUI::Camera::EType::Ortho, camera_view);
BOOST_LOG_TRIVIAL(info) << boost::format("plate %1%'s png,finished rendering") % (i + 1);
std::string pnf_file = "plate_" + std::to_string(i + 1) + "_" + std::to_string((int)camera_view)+".png";
if (!outfile_dir.empty()) {
pnf_file = outfile_dir + "/" + pnf_file;
}
bool write_result = Slic3r::png::write_gl_rgba_to_file(pnf_file.c_str(), thumbnail_width, thumbnail_height, (const uint8_t*)thumbnail_data->pixels.data());
if (write_result)
BOOST_LOG_TRIVIAL(info) << boost::format("plate %1%'s png write to %2% success") % (i + 1) % pnf_file;
else {
BOOST_LOG_TRIVIAL(error) << boost::format("plate %1%'s png write to %2% failed") % (i + 1) % pnf_file;
record_exit_reson(outfile_dir, CLI_EXPORT_3MF_ERROR, 0, cli_errors[CLI_EXPORT_3MF_ERROR], sliced_info);
flush_and_exit(CLI_EXPORT_3MF_ERROR);
}
}
}
p_opengl_mgr->unbind_shader();
p_opengl_mgr->unbind_vao();
}
}
if(export_to_gcode){
for (int index = 0; index < partplate_list.get_plate_count(); index ++){
Slic3r::GUI::PartPlate* part_plate = partplate_list.get_plate(index);
std::string temp_gcode = part_plate->get_tmp_gcode_path();
fs::copy_file(temp_gcode, export_gcode_file, fs::copy_options::overwrite_existing);
}
}
if (plate_data_src.size() > 0) if (plate_data_src.size() > 0)
{ {
@@ -7055,6 +7342,14 @@ int CLI::run(int argc, char **argv)
boost::nowide::cout.flush(); boost::nowide::cout.flush();
boost::nowide::cerr.flush(); boost::nowide::cerr.flush();
#if 0
if(temp_paths.empty()){
for(auto temp_path : temp_paths){
fs::remove(temp_path);
}
}
#endif
return 0; return 0;
} }

View File

@@ -1142,6 +1142,7 @@ void TreeSupport::detect_overhangs(bool check_support_necessity/* = false*/)
} }
} }
for (auto &cluster : overhangClusters) { for (auto &cluster : overhangClusters) {
bool enforce_add = false; bool enforce_add = false;
// remove small overhangs // remove small overhangs
@@ -1621,7 +1622,6 @@ void TreeSupport::generate_toolpaths()
if (m_object->support_layer_count() <= m_raft_layers) if (m_object->support_layer_count() <= m_raft_layers)
return; return;
// generate tree support tool paths // generate tree support tool paths
tbb::parallel_for( tbb::parallel_for(
tbb::blocked_range<size_t>(m_raft_layers, m_object->support_layer_count()), tbb::blocked_range<size_t>(m_raft_layers, m_object->support_layer_count()),
@@ -3267,7 +3267,7 @@ void TreeSupport::drop_nodes()
Point candidate_vertex = node.position; Point candidate_vertex = node.position;
const coordf_t max_move_between_samples = max_move_distance + radius_sample_resolution + EPSILON; // 100 micron extra for rounding errors. const coordf_t max_move_between_samples = max_move_distance + radius_sample_resolution + EPSILON; // 100 micron extra for rounding errors.
// use get_collision instead of get_avoidance here (See STUDIO-4252) // use get_collision instead of get_avoidance here (See STUDIO-4252)
bool is_outside = move_out_expolys(get_collision(next_radius,layer_nr_next), candidate_vertex, max_move_between_samples, max_move_between_samples); bool is_outside = move_out_expolys(get_collision(next_radius,obj_layer_nr_next), candidate_vertex, max_move_between_samples, max_move_between_samples);
if (is_outside) { if (is_outside) {
direction_to_outer = candidate_vertex - node.position; direction_to_outer = candidate_vertex - node.position;
dist2_to_outer = vsize2_with_unscale(direction_to_outer); dist2_to_outer = vsize2_with_unscale(direction_to_outer);

View File

@@ -258,6 +258,23 @@ int Http::priv::xfercb_legacy(void *userp, double dltotal, double dlnow, double
size_t Http::priv::form_file_read_cb(char *buffer, size_t size, size_t nitems, void *userp) size_t Http::priv::form_file_read_cb(char *buffer, size_t size, size_t nitems, void *userp)
{ {
//y65
// try {
// auto putFile = reinterpret_cast<std::unique_ptr<fs::ifstream>*>(userp);
// if (!putFile) { throw std::runtime_error(std::string("The unique_ptr is nullptr! please check")); return CURL_READFUNC_ABORT; }
// fs::ifstream* fstream = putFile->get();
// if (!fstream) { throw std::runtime_error(std::string("The fstream is nullptr! please check")); return CURL_READFUNC_ABORT; }
// fstream->read(buffer, size * nitems);
// return fstream->gcount();
// } catch (const std::exception &) {
// return CURL_READFUNC_ABORT;
// }
// return CURL_READFUNC_ABORT;
auto stream = reinterpret_cast<fs::ifstream*>(userp); auto stream = reinterpret_cast<fs::ifstream*>(userp);
try { try {