Merge branch 'main' into dev/bbl-network-upd

This commit is contained in:
Noisyfox
2025-06-01 19:25:21 +08:00
committed by GitHub
26 changed files with 164 additions and 155 deletions
+3 -3
View File
@@ -130,7 +130,7 @@ fi
if [[ -n "${BUILD_DEPS}" ]]
then
echo "Configuring dependencies..."
BUILD_ARGS="-DDEP_WX_GTK3=ON"
BUILD_ARGS="${DEPS_EXTRA_BUILD_ARGS} -DDEP_WX_GTK3=ON"
if [[ -n "${CLEAN_BUILD}" ]]
then
rm -fr deps/build
@@ -164,10 +164,10 @@ then
then
rm -fr build
fi
BUILD_ARGS=""
BUILD_ARGS="${ORCA_EXTRA_BUILD_ARGS}"
if [[ -n "${FOUND_GTK3_DEV}" ]]
then
BUILD_ARGS="-DSLIC3R_GTK=3"
BUILD_ARGS="${BUILD_ARGS} -DSLIC3R_GTK=3"
fi
if [[ -n "${BUILD_DEBUG}" ]]
then
+7 -3
View File
@@ -176,7 +176,9 @@ Ussualy the recommended values modes are ``MZV`` or ``EI`` for Delta printers.
1. Pre-requisites:
1. In OrcaSlicer, set:
1. Acceleration high enough to trigger ringing (e.g., 2000 mm/s²).
2. Speed high enough to trigger ringing (e.g., 100 mm/s).
2. Speed high enough to trigger ringing (e.g., 200 mm/s).
> [!NOTE]
> These settings depend on your printer's motion ability and the filament's max volumetric speed. If you can't reach speeds that cause ringing, try increasing the filament's max volumetric speed (avoid materials below 10 mm³/s).
3. Jerk [Klipper Square Corner Velocity](https://www.klipper3d.org/Kinematics.html?h=square+corner+velocity#look-ahead) to 5 or a high value (e.g., 20).
2. In printer settigs:
1. Set the Shaper Type to ``MZV`` or ``EI``.
@@ -223,8 +225,10 @@ ZV Input Shaping introduces an anti-vibration signal into the stepper motion for
1. Pre-requisites:
1. In OrcaSlicer, set:
1. Acceleration high enough to trigger ringing (e.g., 2000 mm/s²).
2. Speed high enough to trigger ringing (e.g., 100 mm/s).
3. Jerk
2. Speed high enough to trigger ringing (e.g., 200 mm/s).
> [!NOTE]
> These settings depend on your printer's motion ability and the filament's max volumetric speed. If you can't reach speeds that cause ringing, try increasing the filament's max volumetric speed (avoid materials below 10 mm³/s).
4. Jerk
1. If using [Classic Jerk](https://marlinfw.org/docs/configuration/configuration.html#jerk-) use a high value (e.g., 20).
2. If using [Junction Deviation](https://marlinfw.org/docs/features/junction_deviation.html) (new Marlin default mode) this test will use 0.25 (high enough to most printers).
2. Use an opaque, high-gloss filament to make the ringing more visible.

Before

Width:  |  Height:  |  Size: 8.7 KiB

After

Width:  |  Height:  |  Size: 8.7 KiB

@@ -50,7 +50,8 @@
],
"gcode_flavor": "klipper",
"change_filament_gcode": "M600",
"layer_change_gcode": "SET_PRINT_STATS_INFO CURRENT_LAYER={layer_num + 1}",
"machine_pause_gcode": "M600",
"machine_start_gcode": ";;===== date: 20240520 =====================\n;printer_model:[printer_model]\n;initial_filament:{filament_type[initial_extruder]}\n;curr_bed_type:{curr_bed_type}\nM400 ; wait for buffer to clear\nM220 S100 ;Set the feed speed to 100%\nM221 S100 ;Set the flow rate to 100%\nM104 S140\nM190 S[bed_temperature_initial_layer_single]\nG90\nG28 ;home\nM729 ;Clean Nozzle\n\n\n;=============turn on fans to prevent PLA jamming=================\n{if filament_type[initial_no_support_extruder]==\"PLA\"}\n {if (bed_temperature[initial_no_support_extruder] >50)||(bed_temperature_initial_layer[initial_no_support_extruder] >50)}\n M106 P3 S255\n {elsif (bed_temperature[initial_no_support_extruder] >45)||(bed_temperature_initial_layer[initial_no_support_extruder] >45)}\n M106 P3 S180\n {endif};Prevent PLA from jamming\n{endif}\n\n;enable_pressure_advance:{enable_pressure_advance[initial_extruder]}\n;This value is called if pressure advance is enabled\n{if enable_pressure_advance[initial_extruder] == \"true\"}\nSET_PRESSURE_ADVANCE ADVANCE=[pressure_advance] ;\nM400\n{endif}\nM204 S{min(20000,max(1000,outer_wall_acceleration))} ;Call exterior wall print acceleration\n\n\nG1 X{print_bed_max[0]*0.5} Y-1.2 F20000\nG1 Z0.3 F900\nM109 S[nozzle_temperature_initial_layer]\nM83\nG92 E0 ;Reset Extruder\nG1 F{min(6000, max(900, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X-1.2 E10.156 ;Draw the first line\nG1 Y98.8 E7.934\nG1 X-0.5 Y100 E0.1\nG1 Y-0.3 E7.934\nG1 X{print_bed_max[0]*0.5-50} E6.284\nG1 F{0.2*min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5-30} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5-10} E2\nG1 F{0.2*min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+10} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+30} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+50} E2\n;End PA test.\n\n\nG3 I-1 J0 Z0.6 F1200.0 ;Move to side a little\nG1 F20000\nG92 E0 ;Reset Extruder\n;LAYER_COUNT:[total_layer_count]\n;LAYER:0",
"machine_start_gcode": ";;===== date: 20240520 =====================\n;printer_model:[printer_model]\n;initial_filament:{filament_type[initial_extruder]}\n;curr_bed_type:{curr_bed_type}\nM400 ; wait for buffer to clear\nM220 S100 ;Set the feed speed to 100%\nM221 S100 ;Set the flow rate to 100%\nM104 S140\nM140 S[bed_temperature_initial_layer_single]\nG90\nG28 ;home\nM729 ;Clean Nozzle\nM106 P2 S255\nM190 S[bed_temperature_initial_layer_single]\nM106 P2 S0\n\n\n;=============turn on fans to prevent PLA jamming=================\n{if filament_type[initial_no_support_extruder]==\"PLA\"}\n {if (bed_temperature[initial_no_support_extruder] >50)||(bed_temperature_initial_layer[initial_no_support_extruder] >50)}\n M106 P3 S255\n {elsif (bed_temperature[initial_no_support_extruder] >45)||(bed_temperature_initial_layer[initial_no_support_extruder] >45)}\n M106 P3 S180\n {endif};Prevent PLA from jamming\n{endif}\n\n;enable_pressure_advance:{enable_pressure_advance[initial_extruder]}\n;This value is called if pressure advance is enabled\n{if enable_pressure_advance[initial_extruder] == \"true\"}\nSET_PRESSURE_ADVANCE ADVANCE=[pressure_advance] ;\nM400\n{endif}\nM204 S{min(20000,max(1000,outer_wall_acceleration))} ;Call exterior wall print acceleration\n\n\nG1 X{print_bed_max[0]*0.5} Y-1.2 F20000\nG1 Z0.3 F900\nM109 S[nozzle_temperature_initial_layer]\nM83\nG92 E0 ;Reset Extruder\nG1 F{min(6000, max(900, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X-1.2 E10.156 ;Draw the first line\nG1 Y98.8 E7.934\nG1 X-0.5 Y100 E0.1\nG1 Y-0.3 E7.934\nG1 X{print_bed_max[0]*0.5-50} E6.284\nG1 F{0.2*min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5-30} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5-10} E2\nG1 F{0.2*min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+10} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+30} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+50} E2\n;End PA test.\n\n\nG3 I-1 J0 Z0.6 F1200.0 ;Move to side a little\nG1 F20000\nG92 E0 ;Reset Extruder\nSET_PRINT_STATS_INFO TOTAL_LAYER=[total_layer_count]\n;LAYER_COUNT:[total_layer_count]\n;LAYER:0",
"machine_end_gcode": ";===== date: 20250109 =====================\nM400 ; wait for buffer to clear\nM140 S0 ;Turn-off bed\nM106 S255 ;Cooling nozzle\nM83\nG92 E0 ; zero the extruder\nG2 I1 J0 Z{max_layer_z+0.5} E-1 F3000 ; lower z a little\nG90\n{if max_layer_z > 50}G1 Z{min(max_layer_z+50, printable_height+0.5)} F20000{else}G1 Z100 F20000 {endif}; Move print head up \nM204 S5000\nM400\nM83\nG1 X202 F20000\nM400\nG1 Y250 F20000\nG1 Y264.5 F1200\nM400\nG92 E0\nM104 S0 ;Turn-off hotend\nM140 S0 ;Turn-off bed\nM106 S0 ; turn off fan\nM106 P2 S0 ; turn off remote part cooling fan\nM106 P3 S0 ; turn off chamber cooling fan\nM84 ;Disable all steppers"
}
@@ -52,6 +52,6 @@
"change_filament_gcode": "M600",
"layer_change_gcode": "SET_PRINT_STATS_INFO CURRENT_LAYER={layer_num + 1}",
"machine_pause_gcode": "M600",
"machine_start_gcode": ";;===== date: 20240520 =====================\n;printer_model:[printer_model]\n;initial_filament:{filament_type[initial_extruder]}\n;curr_bed_type:{curr_bed_type}\nM400 ; wait for buffer to clear\nM220 S100 ;Set the feed speed to 100%\nM221 S100 ;Set the flow rate to 100%\nM104 S140\nM190 S[bed_temperature_initial_layer_single]\nG90\nG28 ;home\nM729 ;Clean Nozzle\n\n\n;=============turn on fans to prevent PLA jamming=================\n{if filament_type[initial_no_support_extruder]==\"PLA\"}\n {if (bed_temperature[initial_no_support_extruder] >50)||(bed_temperature_initial_layer[initial_no_support_extruder] >50)}\n M106 P3 S255\n {elsif (bed_temperature[initial_no_support_extruder] >45)||(bed_temperature_initial_layer[initial_no_support_extruder] >45)}\n M106 P3 S180\n {endif};Prevent PLA from jamming\n{endif}\n\n;enable_pressure_advance:{enable_pressure_advance[initial_extruder]}\n;This value is called if pressure advance is enabled\n{if enable_pressure_advance[initial_extruder] == \"true\"}\nSET_PRESSURE_ADVANCE ADVANCE=[pressure_advance] ;\nM400\n{endif}\nM204 S{min(20000,max(1000,outer_wall_acceleration))} ;Call exterior wall print acceleration\n\n\nG1 X{print_bed_max[0]*0.5} Y-1.2 F20000\nG1 Z0.3 F900\nM109 S[nozzle_temperature_initial_layer]\nM83\nG92 E0 ;Reset Extruder\nG1 F{min(6000, max(900, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X-1.2 E10.156 ;Draw the first line\nG1 Y98.8 E7.934\nG1 X-0.5 Y100 E0.1\nG1 Y-0.3 E7.934\nG1 X{print_bed_max[0]*0.5-50} E6.284\nG1 F{0.2*min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5-30} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5-10} E2\nG1 F{0.2*min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+10} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+30} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+50} E2\n;End PA test.\n\n\nG3 I-1 J0 Z0.6 F1200.0 ;Move to side a little\nG1 F20000\nG92 E0 ;Reset Extruder\nSET_PRINT_STATS_INFO TOTAL_LAYER=[total_layer_count]\n;LAYER_COUNT:[total_layer_count]\n;LAYER:0",
"machine_start_gcode": ";;===== date: 20240520 =====================\n;printer_model:[printer_model]\n;initial_filament:{filament_type[initial_extruder]}\n;curr_bed_type:{curr_bed_type}\nM400 ; wait for buffer to clear\nM220 S100 ;Set the feed speed to 100%\nM221 S100 ;Set the flow rate to 100%\nM104 S140\nM140 S[bed_temperature_initial_layer_single]\nG90\nG28 ;home\nM729 ;Clean Nozzle\nM106 P2 S255\nM190 S[bed_temperature_initial_layer_single]\nM106 P2 S0\n\n\n;=============turn on fans to prevent PLA jamming=================\n{if filament_type[initial_no_support_extruder]==\"PLA\"}\n {if (bed_temperature[initial_no_support_extruder] >50)||(bed_temperature_initial_layer[initial_no_support_extruder] >50)}\n M106 P3 S255\n {elsif (bed_temperature[initial_no_support_extruder] >45)||(bed_temperature_initial_layer[initial_no_support_extruder] >45)}\n M106 P3 S180\n {endif};Prevent PLA from jamming\n{endif}\n\n;enable_pressure_advance:{enable_pressure_advance[initial_extruder]}\n;This value is called if pressure advance is enabled\n{if enable_pressure_advance[initial_extruder] == \"true\"}\nSET_PRESSURE_ADVANCE ADVANCE=[pressure_advance] ;\nM400\n{endif}\nM204 S{min(20000,max(1000,outer_wall_acceleration))} ;Call exterior wall print acceleration\n\n\nG1 X{print_bed_max[0]*0.5} Y-1.2 F20000\nG1 Z0.3 F900\nM109 S[nozzle_temperature_initial_layer]\nM83\nG92 E0 ;Reset Extruder\nG1 F{min(6000, max(900, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X-1.2 E10.156 ;Draw the first line\nG1 Y98.8 E7.934\nG1 X-0.5 Y100 E0.1\nG1 Y-0.3 E7.934\nG1 X{print_bed_max[0]*0.5-50} E6.284\nG1 F{0.2*min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5-30} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5-10} E2\nG1 F{0.2*min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+10} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+30} E2\nG1 F{min(12000, max(1200, filament_max_volumetric_speed[initial_no_support_extruder]/0.5/0.3*60))} \nG1 X{print_bed_max[0]*0.5+50} E2\n;End PA test.\n\n\nG3 I-1 J0 Z0.6 F1200.0 ;Move to side a little\nG1 F20000\nG92 E0 ;Reset Extruder\nSET_PRINT_STATS_INFO TOTAL_LAYER=[total_layer_count]\n;LAYER_COUNT:[total_layer_count]\n;LAYER:0",
"machine_end_gcode": ";===== date: 20250109 =====================\nM400 ; wait for buffer to clear\nM140 S0 ;Turn-off bed\nM106 S255 ;Cooling nozzle\nM83\nG92 E0 ; zero the extruder\nG2 I1 J0 Z{max_layer_z+0.5} E-1 F3000 ; lower z a little\nG90\n{if max_layer_z > 50}G1 Z{min(max_layer_z+50, printable_height+0.5)} F20000{else}G1 Z100 F20000 {endif}; Move print head up \nM204 S5000\nM400\nM83\nG1 X202 F20000\nM400\nG1 Y250 F20000\nG1 Y264.5 F1200\nM400\nG92 E0\nM104 S0 ;Turn-off hotend\nM140 S0 ;Turn-off bed\nM106 S0 ; turn off fan\nM106 P2 S0 ; turn off remote part cooling fan\nM106 P3 S0 ; turn off chamber cooling fan\nM84 ;Disable all steppers"
}
@@ -5,7 +5,6 @@
"reduce_crossing_wall": "1",
"bottom_shell_layers": "5",
"outer_wall_speed": "120",
"print_flow_ratio": "0.95",
"sparse_infill_density": "20%",
"top_shell_layers": "6",
"wall_loops": "6",
@@ -5,7 +5,6 @@
"reduce_crossing_wall": "1",
"bottom_shell_layers": "5",
"outer_wall_speed": "120",
"print_flow_ratio": "0.95",
"sparse_infill_density": "20%",
"top_shell_layers": "6",
"wall_loops": "6",
@@ -88,6 +88,6 @@
"wipe_before_external_loop": "0",
"exclude_object": "1",
"wipe_speed": "100%",
"print_flow_ratio": "0.97",
"print_flow_ratio": "1.0",
"wall_sequence": "inner wall/outer wall"
}
@@ -11,7 +11,7 @@
"printer_variant": "0.25",
"max_layer_height": ["0.14"],
"min_layer_height": ["0.08"],
"machine_start_gcode": "M190 S[bed_temperature_initial_layer_single]\nM104 S[nozzle_temperature_initial_layer]\nG1 Z5 F6000\nG90 E0\nM83\nG1 E-1 F600\nG1 E8 F300\nG1 X85 Y110 Z0.2 F1200\nG1 X-110 E15 F2400\nG1 Y0 E4 F2400\nG1 X-109.6 F2400\nG1 Y110 E5 F2400\nG92 E0",
"machine_start_gcode": "M190 S[bed_temperature_initial_layer_single]\nM104 S[nozzle_temperature_initial_layer]\nG90\nM83\nG1 Z5 F6000\nG90 E0\nM83\nG1 E-1 F600\nG1 E8 F300\nG1 X85 Y110 Z0.2 F1200\nG1 X-110 E15 F2400\nG1 Y0 E4 F2400\nG1 X-109.6 F2400\nG1 Y110 E5 F2400\nG92 E0",
"retraction_length": ["1"],
"z_hop": ["0.3"],
"nozzle_type": "stainless_steel"
@@ -9,7 +9,7 @@
"default_print_profile": "0.40mm Standard @Flashforge AD5M 0.8 Nozzle",
"nozzle_diameter": ["0.8"],
"printer_variant": "0.8",
"machine_start_gcode": "M190 S[bed_temperature_initial_layer_single]\nM104 S[nozzle_temperature_initial_layer]\nG1 Z5 F6000\nG1 E-1.5 F600\nG1 E12 F800\nG1 X85 Y110 Z0.3 F1200\nG1 X-110 E30 F2400\nG1 Y0 E8 F2400\nG1 X-109.6 F2400\nG1 Y110 E10 F2400\nG92 E0",
"machine_start_gcode": "M190 S[bed_temperature_initial_layer_single]\nM104 S[nozzle_temperature_initial_layer]\nG90\nM83\nG1 Z5 F6000\nG1 E-1.5 F600\nG1 E12 F800\nG1 X85 Y110 Z0.3 F1200\nG1 X-110 E30 F2400\nG1 Y0 E8 F2400\nG1 X-109.6 F2400\nG1 Y110 E10 F2400\nG92 E0",
"max_layer_height": ["0.56"],
"min_layer_height": ["0.24"],
"retraction_length": ["1.5"],
@@ -11,7 +11,7 @@
"printer_variant": "0.25",
"max_layer_height": ["0.14"],
"min_layer_height": ["0.08"],
"machine_start_gcode": "M190 S[bed_temperature_initial_layer_single]\nM104 S[nozzle_temperature_initial_layer]\nG1 Z5 F6000\nG90 E0\nM83\nG1 E-1 F600\nG1 E8 F300\nG1 X85 Y110 Z0.2 F1200\nG1 X-110 E15 F2400\nG1 Y0 E4 F2400\nG1 X-109.6 F2400\nG1 Y110 E5 F2400\nG92 E0",
"machine_start_gcode": "M190 S[bed_temperature_initial_layer_single]\nM104 S[nozzle_temperature_initial_layer]\nG90\nM83\nG1 Z5 F6000\nG90 E0\nM83\nG1 E-1 F600\nG1 E8 F300\nG1 X85 Y110 Z0.2 F1200\nG1 X-110 E15 F2400\nG1 Y0 E4 F2400\nG1 X-109.6 F2400\nG1 Y110 E5 F2400\nG92 E0",
"retraction_length": ["1"],
"z_hop": ["0.3"],
"nozzle_type": "stainless_steel"
@@ -9,7 +9,7 @@
"default_print_profile": "0.40mm Standard @Flashforge AD5M Pro 0.8 Nozzle",
"nozzle_diameter": ["0.8"],
"printer_variant": "0.8",
"machine_start_gcode": "M190 S[bed_temperature_initial_layer_single]\nM104 S[nozzle_temperature_initial_layer]\nG1 Z5 F6000\nG1 E-1.5 F600\nG1 E12 F800\nG1 X85 Y110 Z0.3 F1200\nG1 X-110 E30 F2400\nG1 Y0 E8 F2400\nG1 X-109.6 F2400\nG1 Y110 E10 F2400\nG92 E0",
"machine_start_gcode": "M190 S[bed_temperature_initial_layer_single]\nM104 S[nozzle_temperature_initial_layer]\nG90\nM83\nG1 Z5 F6000\nG1 E-1.5 F600\nG1 E12 F800\nG1 X85 Y110 Z0.3 F1200\nG1 X-110 E30 F2400\nG1 Y0 E8 F2400\nG1 X-109.6 F2400\nG1 Y110 E10 F2400\nG92 E0",
"max_layer_height": ["0.56"],
"min_layer_height": ["0.24"],
"retraction_length": ["1.5"],
+1 -1
View File
@@ -76,7 +76,7 @@ void FillLine::_fill_surface_single(
size_t n_polylines_out_old = polylines_out.size();
// connect lines
if (! params.dont_connect() && ! polylines.empty()) { // prevent calling leftmost_point() on empty collections
if (! polylines.empty()) { // prevent calling leftmost_point() on empty collections
// offset the expolygon by max(min_spacing/2, extra)
ExPolygon expolygon_off;
{
+8 -24
View File
@@ -548,19 +548,11 @@ std::vector<size_t> Print::layers_sorted_for_object(float start, float end, std:
StringObjectException Print::sequential_print_clearance_valid(const Print &print, Polygons *polygons, std::vector<std::pair<Polygon, float>>* height_polygons)
{
StringObjectException single_object_exception;
auto print_config = print.config();
Pointfs excluse_area_points = print_config.bed_exclude_area.values;
Polygons exclude_polys;
Polygon exclude_poly;
const auto& print_config = print.config();
Polygons exclude_polys = get_bed_excluded_area(print_config);
const Vec3d print_origin = print.get_plate_origin();
for (int i = 0; i < excluse_area_points.size(); i++) {
auto pt = excluse_area_points[i];
exclude_poly.points.emplace_back(scale_(pt.x() + print_origin.x()), scale_(pt.y() + print_origin.y()));
if (i % 4 == 3) { // exclude areas are always rectangle
exclude_polys.push_back(exclude_poly);
exclude_poly.points.clear();
}
}
std::for_each(exclude_polys.begin(), exclude_polys.end(),
[&print_origin](Polygon& p) { p.translate(scale_(print_origin.x()), scale_(print_origin.y())); });
std::map<ObjectID, Polygon> map_model_object_to_convex_hull;
struct print_instance_info
@@ -887,19 +879,11 @@ static StringObjectException layered_print_cleareance_valid(const Print &print,
if (print_instances_ordered.size() < 1)
return {};
auto print_config = print.config();
Pointfs excluse_area_points = print_config.bed_exclude_area.values;
Polygons exclude_polys;
Polygon exclude_poly;
const auto& print_config = print.config();
Polygons exclude_polys = get_bed_excluded_area(print_config);
const Vec3d print_origin = print.get_plate_origin();
for (int i = 0; i < excluse_area_points.size(); i++) {
auto pt = excluse_area_points[i];
exclude_poly.points.emplace_back(scale_(pt.x() + print_origin.x()), scale_(pt.y() + print_origin.y()));
if (i % 4 == 3) { // exclude areas are always rectangle
exclude_polys.push_back(exclude_poly);
exclude_poly.points.clear();
}
}
std::for_each(exclude_polys.begin(), exclude_polys.end(),
[&print_origin](Polygon& p) { p.translate(scale_(print_origin.x()), scale_(print_origin.y())); });
std::map<const PrintInstance*, Polygon> map_model_object_to_convex_hull;
// sequential_print_horizontal_clearance_valid
+16 -11
View File
@@ -8154,22 +8154,27 @@ Points get_bed_shape(const PrintConfig &cfg)
Points get_bed_shape(const SLAPrinterConfig &cfg) { return to_points(make_counter_clockwise(cfg.printable_area.values)); }
Polygons get_bed_excluded_area(const PrintConfig& cfg)
{
const Pointfs exclude_area_points = cfg.bed_exclude_area.values;
Polygon exclude_poly;
for (int i = 0; i < exclude_area_points.size(); i++) {
auto pt = exclude_area_points[i];
exclude_poly.points.emplace_back(scale_(pt.x()), scale_(pt.y()));
}
exclude_poly.make_counter_clockwise();
return {exclude_poly};
}
Polygon get_bed_shape_with_excluded_area(const PrintConfig& cfg)
{
Polygon bed_poly;
bed_poly.points = get_bed_shape(cfg);
Points excluse_area_points = to_points(cfg.bed_exclude_area.values);
Polygons exclude_polys;
Polygon exclude_poly;
for (int i = 0; i < excluse_area_points.size(); i++) {
auto pt = excluse_area_points[i];
exclude_poly.points.emplace_back(pt);
if (i % 4 == 3) { // exclude areas are always rectangle
exclude_polys.push_back(exclude_poly);
exclude_poly.points.clear();
}
}
Polygons exclude_polys = get_bed_excluded_area(cfg);
auto tmp = diff({ bed_poly }, exclude_polys);
if (!tmp.empty()) bed_poly = tmp[0];
return bed_poly;
+1
View File
@@ -1751,6 +1751,7 @@ bool is_XL_printer(const PrintConfig &cfg);
Points get_bed_shape(const DynamicPrintConfig &cfg);
Points get_bed_shape(const PrintConfig &cfg);
Points get_bed_shape(const SLAPrinterConfig &cfg);
Slic3r::Polygons get_bed_excluded_area(const PrintConfig& cfg);
Slic3r::Polygon get_bed_shape_with_excluded_area(const PrintConfig& cfg);
bool has_skirt(const DynamicPrintConfig& cfg);
float get_real_skirt_dist(const DynamicPrintConfig& cfg);
+2 -2
View File
@@ -235,7 +235,7 @@ AboutDialog::AboutDialog()
bool is_dark = wxGetApp().app_config->get("dark_color_mode") == "1";
// logo
m_logo_bitmap = ScalableBitmap(this, is_dark ? "OrcaSlicer_about_dark" : "OrcaSlicer_about", FromDIP(125));
m_logo_bitmap = ScalableBitmap(this, is_dark ? "OrcaSlicer_about_dark" : "OrcaSlicer_about", 125);
m_logo = new wxStaticBitmap(this, wxID_ANY, m_logo_bitmap.bmp(), wxDefaultPosition,wxDefaultSize, 0);
m_logo->SetSizer(vesizer);
@@ -258,7 +258,7 @@ AboutDialog::AboutDialog()
#else
version_font.SetPointSize(11);
#endif
version_font.SetPointSize(FromDIP(20));
version_font.SetPointSize(20);
version->SetFont(version_font);
version->SetForegroundColour(wxColour("#949494"));
credits_string->SetForegroundColour(wxColour("#949494"));
+38 -21
View File
@@ -855,9 +855,9 @@ void AuxiliaryPanel::init_tabpanel()
sizer_side_tools->Add(back_btn, 1, wxEXPAND, 0);
m_tabpanel = new Tabbook(this, wxID_ANY, wxDefaultPosition, wxDefaultSize, sizer_side_tools, wxNB_LEFT | wxTAB_TRAVERSAL | wxNB_NOPAGETHEME);
m_tabpanel->SetBackgroundColour(wxColour("#FEFFFF"));
m_tabpanel->Bind(wxEVT_BOOKCTRL_PAGE_CHANGED, [this](wxBookCtrlEvent &e) { ; });
m_tabpanel->Bind(wxEVT_BOOKCTRL_PAGE_CHANGED, [](wxBookCtrlEvent &e) { /* Event handling */ });
m_designer_panel = new DesignerPanel(m_tabpanel, AuxiliaryFolderType::DESIGNER);
m_designer_panel = new DesignerPanel(m_tabpanel, AuxiliaryFolderType::DESIGNER);
m_pictures_panel = new AuFolderPanel(m_tabpanel, AuxiliaryFolderType::MODEL_PICTURE);
m_bill_of_materials_panel = new AuFolderPanel(m_tabpanel, AuxiliaryFolderType::BILL_OF_MATERIALS);
m_assembly_panel = new AuFolderPanel(m_tabpanel, AuxiliaryFolderType::ASSEMBLY_GUIDE);
@@ -1060,52 +1060,61 @@ void AuxiliaryPanel::update_all_cover()
{
SetBackgroundColour(AUFILE_GREY300);
wxBoxSizer *m_sizer_body = new wxBoxSizer(wxVERTICAL);
wxBoxSizer *m_sizer_designer = new wxBoxSizer(wxHORIZONTAL);
wxBoxSizer *m_sizer_designer = new wxBoxSizer(wxHORIZONTAL);
auto m_text_designer = new wxStaticText(this, wxID_ANY, _L("Author"), wxDefaultPosition, wxSize(180, -1), 0);
m_text_designer->Wrap(-1);
m_text_designer->SetForegroundColour(*wxBLACK);
m_sizer_designer->Add(m_text_designer, 0, wxALIGN_CENTER, 0);
m_input_designer = new ::TextInput(this, wxEmptyString, wxEmptyString, wxEmptyString, wxDefaultPosition, wxSize(FromDIP(450), FromDIP(30)), wxTE_PROCESS_ENTER);
m_input_designer->GetTextCtrl()->SetFont(::Label::Body_14);
m_input_designer->GetTextCtrl()->SetSize(wxSize(FromDIP(450), -1));
m_sizer_designer->Add(m_input_designer, 0, wxALIGN_CENTER, 0);
wxBoxSizer *m_sizer_model_name = new wxBoxSizer(wxHORIZONTAL);
auto m_text_model_name = new wxStaticText(this, wxID_ANY, _L("Model Name"), wxDefaultPosition, wxSize(180, -1), 0);
m_text_model_name->SetForegroundColour(*wxBLACK);
m_text_model_name->Wrap(-1);
m_sizer_model_name->Add(m_text_model_name, 0, wxALIGN_CENTER, 0);
m_imput_model_name = new ::TextInput(this, wxEmptyString, wxEmptyString, wxEmptyString, wxDefaultPosition,wxSize(FromDIP(450),FromDIP(30)), wxTE_PROCESS_ENTER);
m_imput_model_name->GetTextCtrl()->SetFont(::Label::Body_14);
m_imput_model_name->GetTextCtrl()->SetSize(wxSize(FromDIP(450), -1));
m_sizer_model_name->Add(m_imput_model_name, 0, wxALIGN_CENTER, 0);
m_input_model_name = new ::TextInput(this, wxEmptyString, wxEmptyString, wxEmptyString, wxDefaultPosition,wxSize(FromDIP(450),FromDIP(30)), wxTE_PROCESS_ENTER);
m_input_model_name->GetTextCtrl()->SetFont(::Label::Body_14);
m_input_model_name->GetTextCtrl()->SetSize(wxSize(FromDIP(450), -1));
m_sizer_model_name->Add(m_input_model_name, 0, wxALIGN_CENTER, 0);
wxBoxSizer *m_sizer_license = new wxBoxSizer(wxHORIZONTAL);
auto m_text_license = new wxStaticText(this, wxID_ANY, _L("License"), wxDefaultPosition, wxSize(180, -1), 0);
m_text_license->Wrap(-1);
m_sizer_license->Add(m_text_license, 0, wxALIGN_CENTER, 0);
m_combo_license = new ComboBox(this, wxID_ANY, wxEmptyString, wxDefaultPosition, wxSize(FromDIP(450), -1), 0, NULL, wxCB_READONLY);
m_sizer_license->Add(m_combo_license, 0, wxALIGN_CENTER, 0);
m_sizer_body->Add( 0, 0, 0, wxTOP, FromDIP(50) );
m_sizer_body->Add(m_sizer_designer, 0, wxLEFT, FromDIP(50));
m_sizer_body->Add( 0, 0, 0, wxTOP, FromDIP(20));
m_sizer_body->Add(m_sizer_model_name, 0, wxLEFT, FromDIP(50));
wxBoxSizer *m_sizer_description = new wxBoxSizer(wxHORIZONTAL);
auto m_text_description = new wxStaticText(this, wxID_ANY, _L("Description:"), wxDefaultPosition, wxSize(170, -1), 0); // Using "Description:" with the : because that already exists in the Localizations files
m_text_description->SetForegroundColour(*wxBLACK);
m_text_description->Wrap(-1);
m_sizer_description->Add(m_text_description, 0, wxALIGN_TOP | wxRIGHT, FromDIP(10));
m_input_description = new wxTextCtrl(this, wxID_ANY, wxEmptyString, wxDefaultPosition,
wxSize(FromDIP(450), FromDIP(300)), wxTE_MULTILINE | wxTE_PROCESS_ENTER);
m_input_description->SetFont(::Label::Body_14);
m_sizer_description->Add(m_input_description, 0, wxALIGN_CENTER, 0);
m_sizer_body->Add(0, 0, 0, wxTOP, FromDIP(50));
m_sizer_body->Add(m_sizer_designer, 0, wxLEFT | wxALIGN_LEFT, FromDIP(50));
m_sizer_body->Add(0, 0, 0, wxTOP, FromDIP(20));
m_sizer_body->Add(m_sizer_license, 0, wxLEFT, FromDIP(50));
m_sizer_body->Add(m_sizer_model_name, 0, wxLEFT | wxALIGN_LEFT, FromDIP(50));
m_sizer_body->Add(0, 0, 0, wxTOP, FromDIP(20));
m_sizer_body->Add(m_sizer_license, 0, wxLEFT | wxALIGN_LEFT, FromDIP(50));
init_license_list();
m_sizer_body->Add(0, 0, 0, wxTOP, FromDIP(20));
m_sizer_body->Add(m_sizer_description, 0, wxLEFT | wxALIGN_LEFT, FromDIP(50));
SetSizer(m_sizer_body);
Layout();
Fit();
m_input_designer->Bind(wxEVT_TEXT, &DesignerPanel::on_input_enter_designer, this);
m_imput_model_name->Bind(wxEVT_TEXT, &DesignerPanel::on_input_enter_model, this);
m_input_model_name->Bind(wxEVT_TEXT, &DesignerPanel::on_input_enter_model, this);
m_input_description->Bind(wxEVT_TEXT, &DesignerPanel::on_input_enter_description, this);
m_combo_license->Bind(wxEVT_COMMAND_COMBOBOX_SELECTED, &DesignerPanel::on_select_license, this);
}
@@ -1148,6 +1157,12 @@ void DesignerPanel::on_input_enter_model(wxCommandEvent &evt)
ensure_model_info()->model_name = std::string(text.ToUTF8().data());
}
void DesignerPanel::on_input_enter_description(wxCommandEvent &evt)
{
auto text = evt.GetString();
ensure_model_info()->description = std::string(text.ToUTF8().data());
}
void DesignerPanel::update_info()
{
if (wxGetApp().plater()->model().design_info != nullptr) {
@@ -1158,12 +1173,14 @@ void DesignerPanel::update_info()
}
if (wxGetApp().plater()->model().model_info != nullptr) {
m_imput_model_name->GetTextCtrl()->SetValue(wxString::FromUTF8(wxGetApp().plater()->model().model_info->model_name));
m_input_model_name->GetTextCtrl()->SetValue(wxString::FromUTF8(wxGetApp().plater()->model().model_info->model_name));
m_input_description->ChangeValue(wxString::FromUTF8(wxGetApp().plater()->model().model_info->description));
if (!m_combo_license->SetStringSelection(wxString::FromUTF8(wxGetApp().plater()->model().model_info->license))) {
m_combo_license->SetSelection(0);
}
} else {
m_imput_model_name->GetTextCtrl()->SetValue(wxEmptyString);
m_input_model_name->GetTextCtrl()->SetValue(wxEmptyString);
m_input_description->ChangeValue(wxEmptyString);
m_combo_license->SetSelection(0);
}
}
@@ -1171,8 +1188,8 @@ void DesignerPanel::update_info()
void DesignerPanel::msw_rescale()
{
m_input_designer->GetTextCtrl()->SetSize(wxSize(FromDIP(450), -1));
m_imput_model_name->GetTextCtrl()->SetSize(wxSize(FromDIP(450), -1));
m_input_model_name->GetTextCtrl()->SetSize(wxSize(FromDIP(450), -1));
m_combo_license->SetSize(wxSize(FromDIP(450), -1));
}
m_input_description->SetSize(wxSize(FromDIP(450), -1));}
}} // namespace Slic3r::GUI
+3 -1
View File
@@ -180,12 +180,14 @@ public:
~DesignerPanel();
::TextInput* m_input_designer {nullptr};
::TextInput* m_imput_model_name {nullptr};
::TextInput* m_input_model_name {nullptr};
wxTextCtrl* m_input_description {nullptr};
ComboBox* m_combo_license {nullptr};
bool Show(bool show) override;
void init_license_list();
void on_input_enter_designer(wxCommandEvent &evt);
void on_input_enter_model(wxCommandEvent &evt);
void on_input_enter_description(wxCommandEvent &evt);
void on_select_license(wxCommandEvent& evt);
void update_info();
void msw_rescale();
+4 -1
View File
@@ -521,8 +521,11 @@ void ConfigManipulation::toggle_print_fff_options(DynamicPrintConfig *config, co
bool have_combined_infill = config->opt_bool("infill_combination") && have_infill;
toggle_line("infill_combination_max_layer_height", have_combined_infill);
bool infill_anchor = config->opt_enum<InfillPattern>("sparse_infill_pattern") != ipLine;
toggle_field("infill_anchor_max",infill_anchor);
// Only allow configuration of open anchors if the anchoring is enabled.
bool has_infill_anchors = have_infill && config->option<ConfigOptionFloatOrPercent>("infill_anchor_max")->value > 0;
bool has_infill_anchors = have_infill && config->option<ConfigOptionFloatOrPercent>("infill_anchor_max")->value > 0 && infill_anchor;
toggle_field("infill_anchor", has_infill_anchors);
bool has_spiral_vase = config->opt_bool("spiral_mode");
+11 -12
View File
@@ -7911,11 +7911,11 @@ void GLCanvas3D::_render_imgui_select_plate_toolbar()
m_render_preview = true;
// places the toolbar on the top_left corner of the 3d scene
#if ENABLE_RETINA_GL
float f_scale = m_retina_helper->get_scale_factor();
#else
float f_scale = wxGetApp().em_unit() / 10; // ORCA add scaling support
#endif
float f_scale = get_scale();
#ifdef WIN32
const int dpi = get_dpi_for_window(wxGetApp().GetTopWindow());
f_scale *= (float) dpi / (float) DPI_DEFAULT;
#endif // WIN32
Size cnv_size = get_canvas_size();
auto canvas_w = float(cnv_size.get_width());
auto canvas_h = float(cnv_size.get_height());
@@ -7935,16 +7935,15 @@ void GLCanvas3D::_render_imgui_select_plate_toolbar()
// Make sure the window does not overlap the 3d navigator
auto window_height_max = canvas_h - y_offset;
if (wxGetApp().show_3d_navigator()) {
float sc = get_scale();
#ifdef WIN32
const int dpi = get_dpi_for_window(wxGetApp().GetTopWindow());
sc *= (float) dpi / (float) DPI_DEFAULT;
#endif // WIN32
window_height_max -= (128 * sc + 5);
window_height_max -= (128 * f_scale + 5);
}
// ORCA simplify and correct window size and margin calculations and get values from style
ImGuiWrapper& imgui = *wxGetApp().imgui();
ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(8.0f, 8.0f) * f_scale);
ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(4.0f, 4.0f) * f_scale);
int item_count = m_sel_plate_toolbar.m_items.size() + (m_sel_plate_toolbar.show_stats_item ? 1 : 0);
float window_height_calc = (item_count * (button_height + (margin_size + button_margin) * 2.0f) + (item_count - 1) * ImGui::GetStyle().ItemSpacing.y + ImGui::GetStyle().WindowPadding.y * 2.0f);
bool show_scroll = m_sel_plate_toolbar.is_display_scrollbar && (window_height_calc > window_height_max);
@@ -8180,7 +8179,7 @@ void GLCanvas3D::_render_imgui_select_plate_toolbar()
}
ImGui::SetWindowFontScale(1.0f);
ImGui::PopStyleColor(8);
ImGui::PopStyleVar(5);
ImGui::PopStyleVar(7);
if (ImGui::IsWindowHovered() || is_hovered) {
m_sel_plate_toolbar.is_display_scrollbar = true;
+1 -11
View File
@@ -458,17 +458,7 @@ void ArrangeJob::prepare()
auto& print = wxGetApp().plater()->get_partplate_list().get_current_fff_print();
auto print_config = print.config();
bed_poly.points = get_bed_shape(*m_plater->config());
Pointfs excluse_area_points = print_config.bed_exclude_area.values;
Polygons exclude_polys;
Polygon exclude_poly;
for (int i = 0; i < excluse_area_points.size(); i++) {
auto pt = excluse_area_points[i];
exclude_poly.points.emplace_back(scale_(pt.x()), scale_(pt.y()));
if (i % 4 == 3) { // exclude areas are always rectangle
exclude_polys.push_back(exclude_poly);
exclude_poly.points.clear();
}
}
Polygons exclude_polys = get_bed_excluded_area(print_config);
bed_poly = diff({ bed_poly }, exclude_polys)[0];
}
+6 -8
View File
@@ -1562,9 +1562,9 @@ wxBoxSizer* MainFrame::create_side_tools()
// m_publish_btn = new Button(this, _L("Upload"), "bar_publish", 0, FromDIP(16));
m_slice_btn = new SideButton(this, _L("Slice plate"), "");
m_slice_option_btn = new SideButton(this, "", "sidebutton_dropdown", 0, FromDIP(14));
m_slice_option_btn = new SideButton(this, "", "sidebutton_dropdown", 0, 14);
m_print_btn = new SideButton(this, _L("Print plate"), "");
m_print_option_btn = new SideButton(this, "", "sidebutton_dropdown", 0, FromDIP(14));
m_print_option_btn = new SideButton(this, "", "sidebutton_dropdown", 0, 14);
update_side_button_style();
// m_publish_btn->Hide();
@@ -1572,12 +1572,10 @@ wxBoxSizer* MainFrame::create_side_tools()
m_print_option_btn->Enable();
// sizer->Add(m_publish_btn, 0, wxLEFT | wxALIGN_CENTER_VERTICAL, FromDIP(1));
// sizer->Add(FromDIP(15), 0, 0, 0, 0);
sizer->Add(m_slice_option_btn, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, FromDIP(1));
sizer->Add(m_slice_btn, 0, wxLEFT | wxALIGN_CENTER_VERTICAL, FromDIP(1));
sizer->Add(FromDIP(15), 0, 0, 0, 0);
sizer->Add(m_print_option_btn, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, FromDIP(1));
sizer->Add(m_print_btn, 0, wxLEFT | wxALIGN_CENTER_VERTICAL, FromDIP(1));
sizer->Add(FromDIP(19), 0, 0, 0, 0);
sizer->Add(m_slice_option_btn, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, FromDIP(2));
sizer->Add(m_slice_btn , 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, FromDIP(15));
sizer->Add(m_print_option_btn, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, FromDIP(2));
sizer->Add(m_print_btn , 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, FromDIP(19));
sizer->Layout();
-3
View File
@@ -10185,7 +10185,6 @@ void Plater::calib_VFA(const Calib_Params& params)
auto print_config = &wxGetApp().preset_bundle->prints.get_edited_preset().config;
auto filament_config = &wxGetApp().preset_bundle->filaments.get_edited_preset().config;
filament_config->set_key_value("slow_down_layer_time", new ConfigOptionFloats { 0.0 });
filament_config->set_key_value("filament_max_volumetric_speed", new ConfigOptionFloats { 200 });
print_config->set_key_value("enable_overhang_speed", new ConfigOptionBool { false });
print_config->set_key_value("timelapse_type", new ConfigOptionEnum<TimelapseType>(tlTraditional));
print_config->set_key_value("wall_loops", new ConfigOptionInt(1));
@@ -10232,7 +10231,6 @@ void Plater::calib_input_shaping_freq(const Calib_Params& params)
filament_config->set_key_value("slow_down_layer_time", new ConfigOptionFloats { 0.0 });
filament_config->set_key_value("slow_down_min_speed", new ConfigOptionFloats { 0.0 });
filament_config->set_key_value("slow_down_for_layer_cooling", new ConfigOptionBools{false});
filament_config->set_key_value("filament_max_volumetric_speed", new ConfigOptionFloats { 200 });
filament_config->set_key_value("enable_pressure_advance", new ConfigOptionBools {false });
filament_config->set_key_value("pressure_advance", new ConfigOptionFloats { 0.0 });
print_config->set_key_value("layer_height", new ConfigOptionFloat(0.2));
@@ -10279,7 +10277,6 @@ void Plater::calib_input_shaping_damp(const Calib_Params& params)
filament_config->set_key_value("slow_down_layer_time", new ConfigOptionFloats { 0.0 });
filament_config->set_key_value("slow_down_min_speed", new ConfigOptionFloats { 0.0 });
filament_config->set_key_value("slow_down_for_layer_cooling", new ConfigOptionBools{false});
filament_config->set_key_value("filament_max_volumetric_speed", new ConfigOptionFloats { 200 });
filament_config->set_key_value("enable_pressure_advance", new ConfigOptionBools{false});
filament_config->set_key_value("pressure_advance", new ConfigOptionFloats{0.0});
print_config->set_key_value("layer_height", new ConfigOptionFloat(0.2));
+11 -1
View File
@@ -76,6 +76,16 @@ ProjectPanel::ProjectPanel(wxWindow *parent, wxWindowID id, const wxPoint &pos,
ProjectPanel::~ProjectPanel() {}
// Helper to convert newlines to <br>
static std::string convert_newlines_to_br(const std::string& text) {
std::string result = text;
size_t pos = 0;
while ((pos = result.find('\n', pos)) != std::string::npos) {
result.replace(pos, 1, "<br>");
pos += 4;
}
return result;
}
void ProjectPanel::onWebNavigating(wxWebViewEvent& evt)
{
@@ -189,7 +199,7 @@ void ProjectPanel::on_reload(wxCommandEvent& evt)
j["model"]["name"] = wxGetApp().url_encode(model_name);
j["model"]["author"] = wxGetApp().url_encode(model_author);;
j["model"]["cover_img"] = wxGetApp().url_encode(cover_file);
j["model"]["description"] = wxGetApp().url_encode(description);
j["model"]["description"] = wxGetApp().url_encode(convert_newlines_to_br(description));
j["model"]["preview_img"] = files["Model Pictures"];
j["model"]["upload_type"] = update_type;