File Coverage

blib/lib/Chart/Gnuplot/Pie.pm
Criterion Covered Total %
statement 63 137 45.9
branch 9 32 28.1
condition 9 27 33.3
subroutine 10 13 76.9
pod 3 3 100.0
total 94 212 44.3


line stmt bran cond sub pod time code
1             package Chart::Gnuplot::Pie;
2 3     3   94627 use strict;
  3         9  
  3         133  
3 3     3   17 use vars qw($VERSION);
  3         6  
  3         181  
4 3     3   16 use base 'Chart::Gnuplot';
  3         16  
  3         4485  
5 3     3   197060 use Carp;
  3         8  
  3         1929  
6             $VERSION = '0.04';
7              
8              
9             sub new
10             {
11 2     2 1 39 my ($self, %opt) = @_;
12 2         28 my $obj = $self->SUPER::new(%opt);
13 2         1793 $obj->set(
14             parametric => '',
15             xyplane => 'at 0',
16             urange => '[0:1]',
17             vrange => '[0:1]',
18             zrange => '[-1:1]',
19             cbrange => '[-1:1]',
20             );
21 2         238 $obj->command(join("\n", (
22             'unset border',
23             'unset tics',
24             'unset key',
25             'unset colorbox',
26             )));
27 2         372 return($obj);
28             }
29              
30              
31             # Plot 2D pie chart
32             sub plot2d
33             {
34 0     0 1 0 my ($self, $dataSet) = @_;
35 0         0 $self->set(
36             xrange => '[-1.5:1.5]',
37             yrange => '[-1.5:1.5]',
38             size => 'square',
39             view => 'map',
40             );
41 0         0 $self->SUPER::_setChart([$dataSet]);
42              
43 0 0       0 open(CHT, ">>$self->{_script}") || confess("Can't write $self->{_script}");
44 0         0 print CHT "set multiplot\n";
45 0         0 print CHT $dataSet->_thaw2d($self);
46 0         0 print CHT "unset multiplot\n";
47 0         0 close(CHT);
48              
49 0         0 $self->SUPER::execute();
50 0         0 return($self);
51             }
52              
53              
54             # Plot 3D pie chart
55             sub plot3d
56             {
57 0     0 1 0 my ($self, $dataSet) = @_;
58 0         0 $self->set(
59             xrange => '[-1:1]',
60             yrange => '[-1:1]',
61             );
62 0         0 $self->SUPER::_setChart([$dataSet]);
63              
64 0 0       0 open(CHT, ">>$self->{_script}") || confess("Can't write $self->{_script}");
65 0         0 print CHT "set multiplot\n";
66 0         0 print CHT $dataSet->_thaw3d($self);
67 0         0 print CHT "unset multiplot\n";
68 0         0 close(CHT);
69              
70 0         0 $self->SUPER::execute();
71 0         0 return($self);
72             }
73              
74             1;
75              
76             ##############################################################
77              
78             package Chart::Gnuplot::Pie::DataSet;
79 3     3   25 use strict;
  3         6  
  3         141  
80 3     3   17 use base 'Chart::Gnuplot::DataSet';
  3         5  
  3         6574  
81              
82              
83             # Plot 2D pie chart
84             sub _thaw2d
85             {
86 1     1   439 my ($self, $chart) = @_;
87 1         2 my $string = '';
88 1 50       10 my $rotate = (defined $self->{rotate})? $self->{rotate} : 0;
89              
90 1         5 my $pt = $self->{data};
91 1         3 my $sum = 0;
92 1         5 for (my $i = 0; $i < @$pt; $i++)
93             {
94 4         13 $sum += $$pt[$i][1];
95             }
96              
97             # Print label
98 1         4 my $s = my $start = $rotate/360;
99 1         3 my (@r, @g, @b) = ();
100 1         5 for (my $i = 0; $i < @$pt; $i++)
101             {
102 4         11 my $e = $$pt[$i][1]/$sum + $s;
103              
104             # Print label
105 4         43 my $pos = "cos(($s+$e)*pi)*1.1, sin(($s+$e)*pi)*1.1";
106 4 100 66     18 $pos .= ", -0.1" if ($s+$e > 1 && $s+$e < 2);
107 4 100 66     19 $pos .= ", 0.2" if ($s+$e < 1 || $s+$e > 2);
108 4 100 100     24 $pos .= " right" if ($s+$e > 0.5 && $s+$e < 1.5);
109 4         7 $pos .= " front";
110 4         21 $chart->label(
111             text => $$pt[$i][0],
112             position => $pos,
113             );
114 4         100 $string .= "set label${$chart->{_labels}}[-1]\n";
  4         24  
115 4         14 $s = $e;
116             }
117              
118             # Draw top surface
119 1         2 $s = $start;
120 1         5 for (my $i = 0; $i < @$pt; $i++)
121             {
122 4         8 my $e = $$pt[$i][1]/$sum + $s;
123              
124             # Set colors of the slices
125             # - Initialize random color if not specified
126 4         5 my ($r, $g, $b);
127 4 50 33     14 if (!defined $self->{colors} || ${$self->{colors}}[$i] eq '')
  4         15  
128             {
129 0         0 $r = rand();
130 0         0 $g = rand();
131 0         0 $b = rand();
132             }
133             else
134             {
135 4         12 ($r, $g, $b) = &_rgb2real(${$self->{colors}}[$i]);
  4         12  
136             }
137              
138             # Draw top surface
139 4         29 $string .= "set palette model RGB functions $r, $g, $b\n";
140 4         34 $string .= "splot cos(2*pi*(($e-$s)*u+$s))*v, ".
141             "sin(2*pi*(($e-$s)*u+$s))*v, 0.1 with pm3d\n";
142 4         16 $s = $e;
143             }
144              
145             # Draw border around slice
146 1 50 33     6 if (defined $self->{border} && $self->{border} ne 'off')
147             {
148             # Set line properties
149 0         0 my $border = $self->{border};
150 0         0 my $linecolor = "black";
151 0         0 my $linewidth = 1;
152 0 0       0 if (ref($border) eq 'HASH')
153             {
154 0 0       0 $linecolor = $$border{color} if (defined $$border{color});
155 0 0       0 $linewidth = $$border{width} if (defined $$border{width});
156             }
157              
158 0         0 $s = $start;
159 0         0 for (my $i = 0; $i < @$pt; $i++)
160             {
161 0         0 my $e = $$pt[$i][1]/$sum + $s;
162 0         0 $string .= "splot cos(2*pi*(($e-$s)*u+$s)), ".
163             "sin(2*pi*(($e-$s)*u+$s)), 0.1 with lines lt 1 ".
164             "lw $linewidth lc rgb \"$linecolor\"";
165 0         0 $string .= ", u*cos(2*pi*$s), u*sin(2*pi*$s), 0.1 ".
166             "with lines lt 1 lw $linewidth lc rgb \"$linecolor\"\n";
167 0         0 $s = $e;
168             }
169             }
170              
171 1         6 return($string);
172             }
173              
174              
175             # Plot 3D pie chart
176             sub _thaw3d
177             {
178 0     0   0 my ($self, $chart) = @_;
179 0         0 my $string = '';
180 0 0       0 my $rotate = (defined $self->{rotate})? $self->{rotate} : 0;
181              
182 0         0 my $pt = $self->{data};
183 0         0 my $sum = 0;
184              
185 0         0 for (my $i = 0; $i < @$pt; $i++)
186             {
187 0         0 $sum += $$pt[$i][1];
188             }
189              
190             # Print label and draw side sureface
191 0         0 my $s = my $start = $rotate/360;
192 0         0 my (@r, @g, @b) = ();
193 0         0 for (my $i = 0; $i < @$pt; $i++)
194             {
195 0         0 my $e = $$pt[$i][1]/$sum + $s;
196              
197             # Print label
198 0         0 my $pos = "cos(($s+$e)*pi)*1.1, sin(($s+$e)*pi)*1.1";
199 0 0 0     0 $pos .= ", -0.1" if ($s+$e > 1 && $s+$e < 2);
200 0 0 0     0 $pos .= ", 0.2" if ($s+$e < 1 || $s+$e > 2);
201 0 0 0     0 $pos .= " right" if ($s+$e > 0.5 && $s+$e < 1.5);
202 0         0 $pos .= " front";
203 0         0 $chart->label(
204             text => $$pt[$i][0],
205             position => $pos,
206             );
207 0         0 $string .= "set label${$chart->{_labels}}[-1]\n";
  0         0  
208              
209             # Set colors of the slices
210             # - Initialize random color if not specified
211 0 0 0     0 if (!defined $self->{colors} || ${$self->{colors}}[$i] eq '')
  0         0  
212             {
213 0         0 push(@r, rand());
214 0         0 push(@g, rand());
215 0         0 push(@b, rand());
216             }
217             else
218             {
219 0         0 my ($r, $g, $b) = &_rgb2real(${$self->{colors}}[$i]);
  0         0  
220 0         0 push(@r, $r);
221 0         0 push(@g, $g);
222 0         0 push(@b, $b);
223             }
224 0         0 $string .= "set palette model RGB functions ".
225             "$r[$i]*0.8, $g[$i]*0.8, $b[$i]*0.8\n";
226              
227             # Draw side surface
228 0         0 $string .= "splot cos(2*pi*(($e-$s)*u+$s)), ".
229             "sin(2*pi*(($e-$s)*u+$s)), v*0.2 with pm3d\n";
230 0         0 $s = $e;
231             }
232              
233             # Draw top surface
234 0         0 $s = $start;
235 0         0 for (my $i = 0; $i < @$pt; $i++)
236             {
237 0         0 my $e = $$pt[$i][1]/$sum + $s;
238              
239             # Draw top surface
240 0         0 $string .= "set palette model RGB functions ".
241             "$r[$i], $g[$i], $b[$i]\n";
242 0         0 $string .= "splot cos(2*pi*(($e-$s)*u+$s))*v, ".
243             "sin(2*pi*(($e-$s)*u+$s))*v, 0.2 with pm3d\n";
244 0         0 $s = $e;
245             }
246              
247 0         0 return($string);
248             }
249              
250              
251             # Transform #RRGGBB to (0-1, 0-1, 0-1)
252             # - called by _thaw2d() and _thaw3d()
253             sub _rgb2real
254             {
255 4     4   7 my ($rgb) = @_;
256 4         20 my ($r, $g, $b) = ($rgb =~ /^#(.{2})(.{2})(.{2})/);
257 4         9 return(&_16to1($r)/255, &_16to1($g)/255, &_16to1($b)/255);
258             }
259              
260              
261             # Transform 0-H to 0-255
262             # - called by _rgb2real()
263             sub _16to1
264             {
265 12     12   22 my ($x) = @_;
266 12         105 my %tran = (
267             0 => 0, 1 => 1, 2 => 2, 3 => 3, 4 => 4,
268             5 => 5, 6 => 6, 7 => 7, 8 => 8, 9 => 9,
269             A => 10, B => 11, C => 12, D => 13, E => 14, F => 15,
270             a => 10, b => 11, c => 12, d => 13, e => 14, f => 15,
271             );
272 12         42 my ($a, $b) = ($x =~ /^(.)(.)$/);
273 12         76 return($tran{$a}*16 + $tran{$b});
274             }
275              
276              
277             1;
278              
279             __END__