|
1 #!/usr/bin/perl |
|
2 |
|
3 # Make a nice multi-view picture of an object |
|
4 # Command line arguments contain materials and object files |
|
5 # |
|
6 # This is a re-write of Greg's objpict.csh and should be a drop-in |
|
7 # replacement, with no funcionality added or removed |
|
8 |
|
9 use strict; |
|
10 use warnings; |
|
11 |
|
12 use File::Temp qw/ tempdir /; |
|
13 my $td = tempdir( CLEANUP => 1 ); |
|
14 |
|
15 my $xres = 800; |
|
16 my $yres = 800; |
|
17 my $rpict_cmd = "rpict -av .2 .2 .2 -x $xres -y $yres"; |
|
18 |
|
19 my $inprad = "$td/op$$.rad"; |
|
20 my $testroom = "$td/testroom.rad"; |
|
21 my $octree = "$td/op.oct"; |
|
22 |
|
23 # See if files actually exist. |
|
24 foreach (@ARGV) { |
|
25 if (! -e) { |
|
26 die("Can't read file $_\n"); |
|
27 } |
|
28 } |
|
29 |
|
30 # Dump files passed on command line or from STDIN to a temp file. |
|
31 open(FH, ">$inprad") or |
|
32 die("Can\'t write to temporary file $inprad"); |
|
33 while (<>) { |
|
34 print FH; |
|
35 } |
|
36 close(FH); |
|
37 |
|
38 # Create some lights and a box as back drop. |
|
39 # The objects and view points will be inside the box. |
|
40 open(FH, ">$testroom") or |
|
41 die("Can\'t write to temporary file $testroom"); |
|
42 print FH <<EndOfTestroom; |
|
43 void plastic wall_mat 0 0 5 .681 .543 .686 0 .2 |
|
44 void light bright 0 0 3 3000 3000 3000 |
|
45 |
|
46 bright sphere lamp0 0 0 4 4 4 -4 .1 |
|
47 bright sphere lamp1 0 0 4 4 0 4 .1 |
|
48 bright sphere lamp2 0 0 4 0 4 4 .1 |
|
49 |
|
50 wall_mat polygon box.1540 0 0 12 5 -5 -5 5 -5 5 -5 -5 5 -5 -5 -5 |
|
51 wall_mat polygon box.4620 0 0 12 -5 -5 5 -5 5 5 -5 5 -5 -5 -5 -5 |
|
52 wall_mat polygon box.2310 0 0 12 -5 5 -5 5 5 -5 5 -5 -5 -5 -5 -5 |
|
53 wall_mat polygon box.3267 0 0 12 5 5 -5 -5 5 -5 -5 5 5 5 5 5 |
|
54 wall_mat polygon box.5137 0 0 12 5 -5 5 5 -5 -5 5 5 -5 5 5 5 |
|
55 wall_mat polygon box.6457 0 0 12 -5 5 5 -5 -5 5 5 -5 5 5 5 5 |
|
56 EndOfTestroom |
|
57 close(FH); |
|
58 |
|
59 my $dimstr = `getbbox -h $inprad`; |
|
60 # Values returned by getbbox are indented and padded with spaces. |
|
61 $dimstr =~ s/(\s)+/\ /g; # squeeze spaces |
|
62 $dimstr =~ s/^\ //; # remove leading space |
|
63 my @dims = split(/\ /, $dimstr); # convert to array |
|
64 |
|
65 # Find largest axes-aligned dimension |
|
66 my @diffs = ($dims[1]-$dims[0], $dims[3]-$dims[2], $dims[5]-$dims[4]); |
|
67 @diffs = reverse sort { $a <=> $b } @diffs; |
|
68 my $size = $diffs[0]; |
|
69 |
|
70 my $vw1 = "-vtl -vp 2 .5 .5 -vd -1 0 0 -vh 1 -vv 1"; |
|
71 my $vw2 = "-vtl -vp .5 2 .5 -vd 0 -1 0 -vh 1 -vv 1"; |
|
72 my $vw3 = "-vtl -vp .5 .5 2 -vd 0 0 -1 -vu -1 0 0 -vh 1 -vv 1"; |
|
73 my $vw4 = "-vp 3 3 3 -vd -1 -1 -1 -vh 20 -vv 20"; |
|
74 |
|
75 # Move objects so centre is at origin |
|
76 my $xtrans = -1.0 * ($dims[0] + $dims[1]) / 2; |
|
77 my $ytrans = -1.0 * ($dims[2] + $dims[3]) / 2; |
|
78 my $ztrans = -1.0 * ($dims[4] + $dims[5]) / 2; |
|
79 # Scale so that largest object dimension is unity |
|
80 my $scale = 1 / $size; |
|
81 |
|
82 my $cmd = "xform -t $xtrans $ytrans $ztrans -s $scale -t .5 .5 .5 $inprad"; |
|
83 $cmd .= " |oconv $testroom - > $octree"; |
|
84 system "$cmd"; |
|
85 |
|
86 # Render four different views of the objects |
|
87 system "$rpict_cmd $vw1 $octree > $td/right.hdr"; |
|
88 system "$rpict_cmd $vw2 $octree > $td/front.hdr"; |
|
89 system "$rpict_cmd $vw3 $octree > $td/down.hdr"; |
|
90 system "$rpict_cmd $vw4 $octree > $td/oblique.hdr"; |
|
91 |
|
92 # Compose the four views into one image |
|
93 $cmd = "pcompos $td/down.hdr 0 $xres $td/oblique.hdr $xres $yres"; |
|
94 $cmd .= " $td/right.hdr 0 0 $td/front.hdr $xres 0"; |
|
95 $cmd .= " |pfilt -1 -r .6 -x /2 -y /2"; |
|
96 exec "$cmd"; |
|
97 |
|
98 #EOF |