File Coverage

lib/Graphics/Toolkit/Color/Calculator.pm
Criterion Covered Total %
statement 65 65 100.0
branch 35 40 87.5
condition 6 12 50.0
subroutine 8 8 100.0
pod 0 5 0.0
total 114 130 87.6


line stmt bran cond sub pod time code
1              
2             # methods to compute one related color
3              
4             package Graphics::Toolkit::Color::Calculator;
5 6     6   248851 use v5.12;
  6         18  
6 6     6   27 use warnings;
  6         9  
  6         253  
7 6     6   2237 use Graphics::Toolkit::Color::Values;
  6         16  
  6         6390  
8              
9              
10             sub apply_gamma {
11 8     8 0 1467 my ($color_values, $gamma, $color_space) = @_;
12 8         9 my $gamma_array;
13 8 100       16 if (ref $gamma eq 'HASH'){
14 3         10 ($gamma_array, my $deduced_space_name) =
15             Graphics::Toolkit::Color::Space::Hub::deformat_partial_hash( $gamma, $color_space->name );
16 3 100       11 return 'axis names: '.join(', ', keys %$gamma).' do not correlate to the selected color space: '.
17             ($color_space->name).'!' unless ref $gamma_array;
18             } else {
19 5         12 $gamma_array = [ ($gamma) x $color_space->axis_count];
20             }
21 7         16 my $tuple = $color_values->normalized( $color_space->name );
22 7         14 for my $axis_nr ($color_space->basis->axis_iterator){
23 21 100       83 $tuple->[$axis_nr] = $tuple->[$axis_nr] ** $gamma_array->[$axis_nr] if exists $gamma_array->[$axis_nr];
24             }
25 7         13 return $color_values->new_from_tuple( $tuple, $color_space->name, 'normal' );
26             }
27              
28             sub set_value { # .values, %newval -- ~space_name --> _
29 13     13 0 1876 my ($color_values, $partial_hash, $preselected_space_name) = @_;
30 13         30 my ($new_values, $deduced_space_name) =
31             Graphics::Toolkit::Color::Space::Hub::deformat_partial_hash( $partial_hash, $preselected_space_name );
32 13 100       23 unless (ref $new_values){
33 4         16 my $help_start = 'axis names: '.join(', ', keys %$partial_hash).' do not correlate to ';
34 4 100       17 return (defined $preselected_space_name) ? $help_start.'the selected color space: '.$preselected_space_name.'!'
35             : 'any supported color space!';
36             }
37 9         29 my $tuple = $color_values->shaped( $deduced_space_name );
38 9         17 my $color_space = Graphics::Toolkit::Color::Space::Hub::get_space( $deduced_space_name );
39 9         16 for my $pos ($color_space->basis->axis_iterator) {
40 27 100       42 $tuple->[$pos] = $new_values->[$pos] if defined $new_values->[$pos];
41             }
42 9         19 return $color_values->new_from_tuple( $tuple, $color_space->name );
43             }
44              
45             sub add_value { # .values, %newval -- ~space_name --> _
46 13     13 0 2059 my ($color_values, $partial_hash, $preselected_space_name) = @_;
47 13         30 my ($new_values, $deduced_space_name) =
48             Graphics::Toolkit::Color::Space::Hub::deformat_partial_hash( $partial_hash, $preselected_space_name );
49 13 100       27 unless (ref $new_values){
50 5         18 my $help_start = 'axis names: '.join(', ', keys %$partial_hash).' do not correlate to ';
51 5 100       28 return (defined $preselected_space_name) ? $help_start.'the selected color space: '.$preselected_space_name.'!'
52             : 'any supported color space!';
53             }
54 8         28 my $tuple = $color_values->shaped( $deduced_space_name );
55 8         18 my $color_space = Graphics::Toolkit::Color::Space::Hub::get_space( $deduced_space_name );
56 8         18 for my $pos ($color_space->basis->axis_iterator) {
57 24 100       44 $tuple->[$pos] += $new_values->[$pos] if defined $new_values->[$pos];
58             }
59 8         19 return $color_values->new_from_tuple( $tuple, $color_space->name );
60             }
61              
62             sub mix { # @%(+percent, _color) -- ~space_name --> _
63 75     75 0 707 my ($color_values, $recipe, $color_space ) = @_;
64 75 50       224 return if ref $recipe ne 'ARRAY';
65 75         226 my $result_values = [(0) x $color_space->axis_count];
66 75         178 for my $ingredient (@$recipe){
67             return if ref $ingredient ne 'HASH' or not exists $ingredient->{'percent'}
68 153 50 33     1214 or not exists $ingredient->{'color'} or ref $ingredient->{'color'} ne ref $color_values;
      33        
      33        
69 153         446 my $tuple = $ingredient->{'color'}->shaped( $color_space->name );
70 153         1206 $result_values->[$_] += $tuple->[$_] * $ingredient->{'percent'} / 100 for 0 .. $#$tuple;
71             }
72 75         243 return $color_values->new_from_tuple( $result_values, $color_space->name );
73             }
74              
75             sub invert {
76 23     23 0 631 my ($color_values, $only, $color_space ) = @_;
77 23 50       74 return unless ref $color_space;
78 23 100 100     70 $only = [$only] if defined $only and not ref $only; # check which axis selected
79 23 100       73 my $selected_axis = (defined $only) ? [ ] : [$color_space->basis->axis_iterator];
80 23 100       49 if (defined $only) {
81 5         14 for my $axis_name (@$only){
82 7         23 my $pos = $color_space->pos_from_axis_name( $axis_name );
83 7 50       18 return "axis name '$axis_name' is not part of color space '".$color_space->name.
84             "', please try: ".(join(' ', $color_space->long_axis_names)).
85             ' or '.(join(' ', $color_space->short_axis_names)).' !' unless defined $pos;
86 7 50       34 return "axis '$axis_name' is already selected for inversion" if exists $selected_axis->[$pos];
87 7         18 $selected_axis->[$pos] = $pos;
88             }
89             }
90 23         59 my $tuple = $color_values->normalized( $color_space->name );
91 23         70 for my $axis_nr ($color_space->basis->axis_iterator){
92 69 100       148 next unless defined $selected_axis->[$axis_nr];
93 61 100       115 if ($color_space->shape->is_axis_euclidean( $axis_nr )){
94 54         120 $tuple->[$axis_nr] = 0.5 - ($tuple->[$axis_nr] - 0.5);
95             } else {
96 7         21 $tuple->[$axis_nr]++ while $tuple->[$axis_nr] < 0;
97 7         19 $tuple->[$axis_nr]-- while $tuple->[$axis_nr] > 1;
98 7 100       24 $tuple->[$axis_nr] = ($tuple->[$axis_nr] < 0.5)
99             ? $tuple->[$axis_nr] + 0.5
100             : $tuple->[$axis_nr] - 0.5;
101             }
102             }
103 23         55 return $color_values->new_from_tuple( $tuple, $color_space->name, 'normal' );
104             }
105              
106             1;