2012-02-25 16:35:25 +00:00
|
|
|
package Slic3r::Format::STL;
|
2011-09-06 09:50:43 +00:00
|
|
|
use Moo;
|
2011-09-01 19:06:28 +00:00
|
|
|
|
2012-02-19 14:45:27 +00:00
|
|
|
use Slic3r::Geometry qw(X Y Z triangle_normal);
|
2011-09-01 19:06:28 +00:00
|
|
|
|
2011-10-12 08:47:26 +00:00
|
|
|
sub read_file {
|
|
|
|
my $self = shift;
|
|
|
|
my ($file) = @_;
|
|
|
|
|
2013-06-24 18:34:57 +00:00
|
|
|
my $tmesh = Slic3r::TriangleMesh::XS->new;
|
2013-07-06 09:39:28 +00:00
|
|
|
$tmesh->ReadSTLFile(Slic3r::encode_path($file));
|
2013-06-24 18:34:57 +00:00
|
|
|
$tmesh->Repair;
|
|
|
|
my ($vertices, $facets) = @{$tmesh->ToPerl};
|
2012-02-17 12:49:33 +00:00
|
|
|
|
2012-08-29 14:49:38 +00:00
|
|
|
my $model = Slic3r::Model->new;
|
2013-07-13 18:23:03 +00:00
|
|
|
my $object = $model->add_object(vertices => $vertices, mesh_stats => $tmesh->stats);
|
2012-08-29 14:49:38 +00:00
|
|
|
my $volume = $object->add_volume(facets => $facets);
|
|
|
|
return $model;
|
2011-10-12 08:47:26 +00:00
|
|
|
}
|
|
|
|
|
2012-01-28 14:05:42 +00:00
|
|
|
sub write_file {
|
|
|
|
my $self = shift;
|
2012-08-29 14:49:38 +00:00
|
|
|
my ($file, $model, %params) = @_;
|
2012-01-28 14:05:42 +00:00
|
|
|
|
2013-01-13 09:18:34 +00:00
|
|
|
Slic3r::open(\my $fh, '>', $file);
|
2012-01-28 14:05:42 +00:00
|
|
|
|
2012-08-29 14:49:38 +00:00
|
|
|
$params{binary}
|
|
|
|
? _write_binary($fh, $model->mesh)
|
|
|
|
: _write_ascii($fh, $model->mesh);
|
2012-01-28 14:05:42 +00:00
|
|
|
|
|
|
|
close $fh;
|
|
|
|
}
|
|
|
|
|
|
|
|
sub _write_binary {
|
2012-02-18 19:36:14 +00:00
|
|
|
my ($fh, $mesh) = @_;
|
2012-01-28 14:05:42 +00:00
|
|
|
|
|
|
|
die "bigfloat" unless length(pack "f", 1) == 4;
|
|
|
|
|
|
|
|
binmode $fh;
|
|
|
|
print $fh pack 'x80';
|
2012-02-18 19:36:14 +00:00
|
|
|
print $fh pack 'L', scalar(@{$mesh->facets});
|
|
|
|
foreach my $facet (@{$mesh->facets}) {
|
2012-02-19 14:45:27 +00:00
|
|
|
print $fh pack '(f<3)4S',
|
|
|
|
@{_facet_normal($mesh, $facet)},
|
2012-07-30 07:59:41 +00:00
|
|
|
(map @{$mesh->vertices->[$_]}, @$facet[-3..-1]),
|
2012-02-19 14:45:27 +00:00
|
|
|
0;
|
2012-02-18 19:36:14 +00:00
|
|
|
}
|
2012-01-28 14:05:42 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
sub _write_ascii {
|
2012-02-18 19:36:14 +00:00
|
|
|
my ($fh, $mesh) = @_;
|
2012-01-28 14:05:42 +00:00
|
|
|
|
|
|
|
printf $fh "solid\n";
|
2012-02-18 19:36:14 +00:00
|
|
|
foreach my $facet (@{$mesh->facets}) {
|
2012-02-19 14:45:27 +00:00
|
|
|
printf $fh " facet normal %f %f %f\n", @{_facet_normal($mesh, $facet)};
|
2012-01-28 14:05:42 +00:00
|
|
|
printf $fh " outer loop\n";
|
2012-07-30 07:59:41 +00:00
|
|
|
printf $fh " vertex %f %f %f\n", @{$mesh->vertices->[$_]} for @$facet[-3..-1];
|
2012-01-28 14:05:42 +00:00
|
|
|
printf $fh " endloop\n";
|
|
|
|
printf $fh " endfacet\n";
|
|
|
|
}
|
|
|
|
printf $fh "endsolid\n";
|
|
|
|
}
|
|
|
|
|
2012-02-19 14:45:27 +00:00
|
|
|
sub _facet_normal {
|
|
|
|
my ($mesh, $facet) = @_;
|
2012-07-30 07:59:41 +00:00
|
|
|
return triangle_normal(map $mesh->vertices->[$_], @$facet[-3..-1]);
|
2012-02-19 14:45:27 +00:00
|
|
|
}
|
|
|
|
|
2011-09-01 19:06:28 +00:00
|
|
|
1;
|