mirror of
				https://github.com/SoftFever/OrcaSlicer.git
				synced 2025-10-30 12:11:15 -06:00 
			
		
		
		
	Add support for circular bed
This commit is contained in:
		
							parent
							
								
									7cc0bce97d
								
							
						
					
					
						commit
						4d8ecccc5e
					
				
					 3 changed files with 60 additions and 14 deletions
				
			
		|  | @ -6,7 +6,7 @@ use utf8; | |||
| use List::Util qw(min max); | ||||
| use Slic3r::Geometry qw(PI X Y unscale); | ||||
| use Wx qw(:dialog :id :misc :sizer :choicebook wxTAB_TRAVERSAL); | ||||
| use Wx::Event qw(EVT_CLOSE EVT_BUTTON EVT_CHOICE); | ||||
| use Wx::Event qw(EVT_CLOSE); | ||||
| use base 'Wx::Dialog'; | ||||
| 
 | ||||
| sub new { | ||||
|  | @ -40,10 +40,10 @@ sub GetValue { | |||
| 
 | ||||
| package Slic3r::GUI::BedShapePanel; | ||||
| 
 | ||||
| use List::Util qw(min max); | ||||
| use Slic3r::Geometry qw(PI X Y unscale); | ||||
| use List::Util qw(min max sum first); | ||||
| use Slic3r::Geometry qw(PI X Y unscale scaled_epsilon); | ||||
| use Wx qw(:dialog :id :misc :sizer :choicebook wxTAB_TRAVERSAL); | ||||
| use Wx::Event qw(EVT_CLOSE EVT_BUTTON EVT_CHOICE); | ||||
| use Wx::Event qw(EVT_CLOSE EVT_CHOICEBOOK_PAGE_CHANGED); | ||||
| use base 'Wx::Panel'; | ||||
| 
 | ||||
| use constant SHAPE_RECTANGULAR  => 0; | ||||
|  | @ -83,6 +83,20 @@ sub new { | |||
|             default     => 'corner', | ||||
|         }, | ||||
|     ]); | ||||
|     $self->_init_shape_options_page('Circular', [ | ||||
|         { | ||||
|             opt_key     => 'diameter', | ||||
|             type        => 'f', | ||||
|             label       => 'Diameter', | ||||
|             tooltip     => 'Diameter of the print bed. It is assumed that origin (0,0) is located in the center.', | ||||
|             sidetext    => 'mm', | ||||
|             default     => 200, | ||||
|         }, | ||||
|     ]); | ||||
|      | ||||
|     EVT_CHOICEBOOK_PAGE_CHANGED($self, -1, sub { | ||||
|         $self->_update_shape; | ||||
|     }); | ||||
|      | ||||
|     # right pane with preview canvas | ||||
|     my $canvas; | ||||
|  | @ -137,6 +151,21 @@ sub _set_shape { | |||
|         } | ||||
|     } | ||||
|      | ||||
|     # is this a circle? | ||||
|     { | ||||
|         my $polygon = Slic3r::Polygon->new_scale(@$points); | ||||
|         my $center = $polygon->bounding_box->center; | ||||
|         my @vertex_distances = map $center->distance_to($_), @$polygon; | ||||
|         my $avg_dist = sum(@vertex_distances)/@vertex_distances; | ||||
|         if (!defined first { abs($_ - $avg_dist) > scaled_epsilon } @vertex_distances) { | ||||
|             # all vertices are equidistant to center | ||||
|             $self->{shape_options_book}->SetSelection(SHAPE_CIRCULAR); | ||||
|             my $optgroup = $self->{optgroups}[SHAPE_CIRCULAR]; | ||||
|             $optgroup->set_value('diameter', sprintf("%.0f", unscale($avg_dist*2))); | ||||
|             return; | ||||
|         } | ||||
|     } | ||||
|      | ||||
|     $self->{shape_options_book}->SetSelection(SHAPE_CUSTOM); | ||||
| } | ||||
| 
 | ||||
|  | @ -161,6 +190,18 @@ sub _update_shape { | |||
|             [$x1,$y1], | ||||
|             [$x0,$y1], | ||||
|         ]; | ||||
|     } elsif ($page_idx == SHAPE_CIRCULAR) { | ||||
|         return if grep !defined($self->{"_$_"}), qw(diameter);  # not loaded yet | ||||
|         my $r = $self->{_diameter}/2; | ||||
|         my $twopi = 2*PI; | ||||
|         my $edges = 60; | ||||
|         my $polygon = Slic3r::Polygon->new_scale( | ||||
|             map [ $r * cos $_, $r * sin $_ ], | ||||
|                 map { $twopi/$edges*$_ } 1..$edges | ||||
|         ); | ||||
|         $self->{bed_shape} = [ | ||||
|             map [ unscale($_->x), unscale($_->y) ], @$polygon  #)) | ||||
|         ]; | ||||
|     } | ||||
|      | ||||
|     $self->{on_change}->(); | ||||
|  | @ -176,18 +217,21 @@ sub _update_preview { | |||
| sub _init_shape_options_page { | ||||
|     my ($self, $title, $options) = @_; | ||||
|      | ||||
|     my $on_change = sub { | ||||
|         my ($opt_key, $value) = @_; | ||||
|         $self->{"_$opt_key"} = $value; | ||||
|         $self->_update_shape; | ||||
|     }; | ||||
|      | ||||
|     my $panel = Wx::Panel->new($self->{shape_options_book}); | ||||
|     push @{$self->{optgroups}}, my $optgroup = Slic3r::GUI::OptionsGroup->new( | ||||
|         parent      => $panel, | ||||
|         title       => 'Settings', | ||||
|         options     => $options, | ||||
|         on_change   => sub { | ||||
|             my ($opt_key, $value) = @_; | ||||
|             $self->{"_$opt_key"} = $value; | ||||
|             $self->_update_shape; | ||||
|         }, | ||||
|         on_change   => $on_change, | ||||
|         label_width => 100, | ||||
|     ); | ||||
|     $on_change->($_->{opt_key}, $_->{default}) for @$options;  # populate with defaults | ||||
|     $panel->SetSizerAndFit($optgroup->sizer); | ||||
|     $self->{shape_options_book}->AddPage($panel, $title); | ||||
| } | ||||
|  |  | |||
|  | @ -5,7 +5,7 @@ use utf8; | |||
| 
 | ||||
| use List::Util qw(min max first); | ||||
| use Slic3r::Geometry qw(X Y scale unscale convex_hull); | ||||
| use Slic3r::Geometry::Clipper qw(offset JT_ROUND); | ||||
| use Slic3r::Geometry::Clipper qw(offset JT_ROUND intersection_pl); | ||||
| use Wx qw(:misc :pen :brush :sizer :font :cursor wxTAB_TRAVERSAL); | ||||
| use Wx::Event qw(EVT_MOUSE_EVENTS EVT_PAINT EVT_SIZE); | ||||
| use base 'Wx::Panel'; | ||||
|  | @ -261,13 +261,15 @@ sub update_bed_size { | |||
|     # cache bed contours and grid | ||||
|     { | ||||
|         my $step = scale 10;  # 1cm grid | ||||
|         $self->{grid} = my $grid = [];   # arrayref of lines | ||||
|         my @polylines = (); | ||||
|         for (my $x = $bb->x_min + $step; $x < $bb->x_max; $x += $step) { | ||||
|             push @$grid, $self->scaled_points_to_pixel([[$x, $bb->y_min], [$x, $bb->y_max]], 1); | ||||
|             push @polylines, Slic3r::Polyline->new([$x, $bb->y_min], [$x, $bb->y_max]); | ||||
|         } | ||||
|         for (my $y = $bb->y_min + $step; $y < $bb->y_max; $y += $step) { | ||||
|             push @$grid, $self->scaled_points_to_pixel([[$bb->x_min, $y], [$bb->x_max, $y]], 1); | ||||
|             push @polylines, Slic3r::Polyline->new([$bb->x_min, $y], [$bb->x_max, $y]); | ||||
|         } | ||||
|         @polylines = @{intersection_pl(\@polylines, [$polygon])}; | ||||
|         $self->{grid} = [ map $self->scaled_points_to_pixel(\@$_, 1), @polylines ]; | ||||
|     } | ||||
| } | ||||
| 
 | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Alessandro Ranellucci
						Alessandro Ranellucci