File Coverage

blib/lib/CSS/Object/Value.pm
Criterion Covered Total %
statement 44 75 58.6
branch 8 36 22.2
condition 1 17 5.8
subroutine 12 17 70.5
pod 4 7 57.1
total 69 152 45.3


line stmt bran cond sub pod time code
1             ##----------------------------------------------------------------------------
2             ## CSS Object Oriented - ~/lib/CSS/Object/Value.pm
3             ## Version v0.2.0
4             ## Copyright(c) 2020 DEGUEST Pte. Ltd.
5             ## Author: Jacques Deguest <jack@deguest.jp>
6             ## Created 2020/06/21
7             ## Modified 2024/09/05
8             ## All rights reserved
9             ##
10             ## This program is free software; you can redistribute it and/or modify it
11             ## under the same terms as Perl itself.
12             ##----------------------------------------------------------------------------
13             package CSS::Object::Value;
14             BEGIN
15             {
16 6     6   38 use strict;
  6         10  
  6         222  
17 6     6   26 use warnings;
  6         11  
  6         325  
18 6     6   31 use parent qw( CSS::Object::Element );
  6         7  
  6         62  
19 6     6   426 use CSS::Object::Comment;
  6         11  
  6         37  
20 6     6   1667 use CSS::Object::Format;
  6         13  
  6         40  
21             use overload (
22 6         40 '""' => 'as_string',
23             fallback => 1,
24 6     6   1286 );
  6         11  
25 6     6   7508 our $VERSION = 'v0.2.0';
26             };
27              
28             sub init
29             {
30 45     45 1 7801 my $self = shift( @_ );
31 45         102 my $val;
32 45 100       243 $val = shift( @_ ) if( ( scalar( @_ ) % 2 ) );
33 45         594 $self->{format} = '';
34 45         134 $self->{value} = '';
35 45         100 $self->{_init_strict_use_sub} = 1;
36 45         280 $self->SUPER::init( @_ );
37 45 100       291 $self->value( $val ) if( defined( $val ) );
38 45         73036 return( $self );
39             }
40              
41             # Inherited
42             # sub format
43              
44             sub as_string
45             {
46 258     258 1 30941 my $self = shift( @_ );
47 258 50       1495 return( '' ) if( !$self->format );
48 258         7508 return( $self->format->value_as_string( $self ) );
49             # return(
50             # $self->comment_before->map(sub{ $_->as_string })->scalar . ( $self->comment_before->length ? ' ' : '' ) .
51             # $self->format->value_as_string( $self ) .
52             # ( $self->comment_after->length ? ' ' : '' ) . $self->comment_after->map(sub{ $_->as_string })->scalar
53             # );
54             }
55              
56 0     0 0 0 sub comment { return( shift->_set_get_object_array_object( 'comment_after', 'CSS::Object::Comment', @_ ) ); }
57              
58 516     516 0 9519511 sub comment_after { return( shift->_set_get_object_array_object( 'comment_after', 'CSS::Object::Comment', @_ ) ); }
59              
60 518     518 0 240643 sub comment_before { return( shift->_set_get_object_array_object( 'comment_before', 'CSS::Object::Comment', @_ ) ); }
61              
62             sub value
63             {
64 302     302 1 9271488 my $self = shift( @_ );
65 302 100       1530 if( @_ )
66             {
67 44         144 my $val = shift( @_ );
68 44 50       132 if( $self->_is_a( $val, 'CSS::Object::Value' ) )
69             {
70             ## If the value object provided has some comments attached to it
71             ## Make sure each data stored is an object, or else we create an object before adding it
72 0 0       0 if( $val->comment_after->length )
73             {
74             $val->comment_after->foreach(sub
75             {
76 0     0   0 my $cmt = $self->_comment_data_to_object( $_ );
77 0 0       0 $self->comment_after->push( $cmt ) if( defined( $cmt ) );
78 0         0 });
79             }
80 0 0       0 if( $val->comment_before->length )
81             {
82             $val->comment_before->foreach(sub
83             {
84 0     0   0 my $cmt = $self->_comment_data_to_object( $_ );
85 0 0       0 $self->comment_before->push( $cmt ) if( defined( $cmt ) );
86 0         0 });
87             }
88 0         0 $val = $val->value->scalar;
89             }
90             else
91             {
92 44         785 while( $val =~ s/^[[:blank:]\h]*\/\*[[:blank:]\h]*(.*?)[[:blank:]\h]*\*\///s )
93             {
94 2   50     23 my $cmt = CSS::Object::Comment->new( [split( /\r\n/, $1 )] ) ||
95             return( $self->error( "Cannot create comment object: ", CSS::Object::Comment->error ) );
96 2         1344 $self->comment_before->push( $cmt );
97             }
98 44         1765 while( $val =~ s/[[:blank:]\h]*\/\*[[:blank:]\h]*(.*?)[[:blank:]\h]*\*\/$//s )
99             {
100 0   0     0 my $cmt = CSS::Object::Comment->new( [split( /\r\n/, $1 )] ) ||
101             return( $self->error( "Cannot create comment object: ", CSS::Object::Comment->error ) );
102 0         0 $self->comment_after->push( $cmt );
103             }
104 44         477 $val =~ s/^[[:blank:]\h]*|[[:blank:]\h]*$//gs;
105             }
106 44         220 return( $self->_set_get_scalar_as_object( 'value', $val ) );
107             }
108 258         1414 return( $self->_set_get_scalar_as_object( 'value' ) );
109             }
110              
111             sub with_comment
112             {
113 0     0 1   my $self = shift( @_ );
114 0           my $opts = {};
115 0 0         $opts = shift( @_ ) if( $self->_is_hash( $_[0] ) );
116 0 0         if( $opts->{before} )
117             {
118 0           my $cmt = $self->_comment_data_to_object( $opts->{before} );
119 0 0         defined( $cmt ) || return( $self->pass_error );
120 0 0 0       $self->comment_before->push( $cmt ) if( defined( $cmt ) && CORE::length( $cmt ) );
121             }
122 0 0         if( $opts->{after} )
123             {
124 0           my $cmt = $self->_comment_data_to_object( $opts->{after} );
125 0 0         defined( $cmt ) || return( $self->pass_error );
126 0 0 0       $self->comment_after->push( $cmt ) if( defined( $cmt ) && CORE::length( $cmt ) );
127             }
128 0           return( $self );
129             }
130              
131             sub _comment_data_to_object
132             {
133 0     0     my $self = shift( @_ );
134             # No data received, we silently return false
135 0   0       my $this = shift( @_ ) || return( '' );
136 0 0 0       if( $self->_is_a( $this, 'CSS::Objet::Comment' ) )
    0          
137             {
138 0           return( $this );
139             }
140             elsif( $self->_is_array( $this ) || !ref( $this ) )
141             {
142 0   0       my $cmt = CSS::Object::Comment->new( $this, debug => $self->debug ) ||
143             return( $self->error( "Cannot create a new comment from array provided in this property value: ", CSS::Object::Comment->error ) );
144 0           return( $cmt );
145             }
146             else
147             {
148 0           return( $self->error( "I do not know what to do with comment data \"$this\"." ) );
149             }
150             }
151              
152             1;
153             # NOTE: POD
154             __END__
155              
156             =encoding utf-8
157              
158             =head1 NAME
159              
160             CSS::Object::Value - CSS Object Oriented Value
161              
162             =head1 SYNOPSIS
163              
164             use CSS::Object::Value;
165             # For font-size property for example
166             my $val = CSS::Object::Value->new( '1.2rem',
167             debug => 3,
168             format => $format_object,
169             ) || die( CSS::Object::Value->error );
170              
171             # Adding value with comment inside
172             my $val = CSS::Object::Value->new( '1.2rem', with_comment =>
173             {
174             before => 'This is 12px',
175             after => ["Might want to change this", "to something else"],
176             }) || die( "Cannot add value with comments: ", CSS::Object::Value->error );
177            
178             my $val = CSS::Object::Value->new( '/* Might need to change this */ 1.2rem /* Maybe move this to px instead? */',
179             debug => 3,
180             format => $format_object,
181             ) || die( CSS::Object::Value->error );
182              
183             # or
184             $val->comment_before->push( $css->new_comment( "More comment before value" ));
185             #val->comment_after->push( $css->new_comment( "Another comment after too" ));
186              
187             # or
188             $val->with_comment({
189             before => 'This is 12px',
190             after => ["Might want to change this", "to something else"],
191             }) || die( $val->error );
192              
193             =head1 VERSION
194              
195             v0.2.0
196              
197             =head1 DESCRIPTION
198              
199             L<CSS::Object::Value> is a module to contain the CSS properties' value.
200              
201             =head1 CONSTRUCTOR
202              
203             =head2 new
204              
205             To instantiate a new L<CSS::Object::Value> object, pass an hash reference of following parameters:
206              
207             =over 4
208              
209             =item I<debug>
210              
211             This is an integer. The bigger it is and the more verbose is the output.
212              
213             =item I<format>
214              
215             This is a L<CSS::Object::Format> object or one of its child modules.
216              
217             =item I<value>
218              
219             The property value, which can also be called as the sole argument:
220              
221             # For display property for example
222             my $val = CSS::Object::Value->new( 'none' );
223              
224             =item I<with_comment>
225              
226             This parameter must be an hash reference with 2 possible properties: I<before> and I<after>. Each of thoe properties can contain either a simple string, an array reference of string, or an L<CSS::Object::Comment> object.
227              
228             It returns our object
229              
230             =back
231              
232             =head1 METHODS
233              
234             =head2 as_string
235              
236             This calls the L</format> and its method L<CSS::Object::Format/value_as_string>
237              
238             It returns the css string produce or undef and sets an L<Module::Generic::Exception> upon error.
239              
240             =head2 format
241              
242             This is a L<CSS::Object::Format> object or one of its child modules.
243              
244             =head2 value
245              
246             Sets or gets the value for this property value. The value stored here becomes a L<Module::Generic::Scalar> and thus all its object methods can be used
247              
248             Alternatively, it accepts a L<CSS::Object::Value> and will call its L</value> method to get the actual string to store.
249              
250             It returns the value currently stored.
251              
252             =head2 with_comment
253              
254             This method takes an hash reference with 2 possible properties: I<before> and I<after>. Each of thoe properties can contain either a simple string, an array reference of string, or an L<CSS::Object::Comment> object.
255              
256             It returns the object used to call this method, or undef if there was an error.
257              
258             =head1 AUTHOR
259              
260             Jacques Deguest E<lt>F<jack@deguest.jp>E<gt>
261              
262             =head1 SEE ALSO
263              
264             L<CSS::Object>
265              
266             =head1 COPYRIGHT & LICENSE
267              
268             Copyright (c) 2020 DEGUEST Pte. Ltd.
269              
270             You can use, copy, modify and redistribute this package and associated
271             files under the same terms as Perl itself.
272              
273             =cut