File Coverage

blib/lib/Tree/Simple/View/DHTML.pm
Criterion Covered Total %
statement 148 149 99.3
branch 47 48 97.9
condition 6 6 100.0
subroutine 25 25 100.0
pod 4 4 100.0
total 230 232 99.1


line stmt bran cond sub pod time code
1              
2             package Tree::Simple::View::DHTML;
3              
4 1     1   62120 use strict;
  1         9  
  1         28  
5 1     1   5 use warnings;
  1         1  
  1         53  
6              
7             our $VERSION = '0.20';
8              
9 1     1   416 use parent 'Tree::Simple::View::HTML';
  1         301  
  1         4  
10              
11 1     1   52 use Tree::Simple::View::Exceptions;
  1         15  
  1         19  
12              
13 1     1   5 use constant OPEN_TAG => 1;
  1         2  
  1         44  
14 1     1   5 use constant CLOSE_TAG => 2;
  1         2  
  1         35  
15 1     1   4 use constant EXPANDED => 3;
  1         1  
  1         1087  
16              
17             ## private methods
18              
19             sub _init {
20 17     17   54 my ($self, @args) = @_;
21 17         73 $self->SUPER::_init(@args);
22 17         33 $self->{list_counter_id} = 0;
23 17         138 ($self->{obj_id}) = ("$self" =~ /\((.*?)\)$/);
24             }
25              
26             sub _createUID {
27 85     85   127 my ($self, $tree) = @_;
28 85 100       165 return $tree->getUID() if $self->{config}->{use_tree_uids};
29 84         111 $self->{list_counter_id}++;
30 84         212 return join "_" => ($self->{obj_id}, $self->{list_counter_id});
31             }
32              
33             ## public methods
34              
35             sub expandPathSimple {
36 3     3 1 9 my ($self, $tree, $current_path, @path) = @_;
37 3         6 my @results = ("
    ");
38 3         10 my $root_depth = $tree->getDepth() + 1;
39 3         11 my $last_depth = -1;
40             my $traversal_sub = sub {
41 46     46   692 my ($t) = @_;
42 46         58 my $display_style = "none";
43 46 100 100     82 if (defined $current_path && $self->_compareNodeToPath($current_path, $t)) {
44 5         24 $display_style = "block";
45 5         8 $current_path = shift @path;
46             }
47 46         77 my $current_depth = $t->getDepth();
48 46 100       134 push @results => ("" x ($last_depth - $current_depth)) if ($last_depth > $current_depth);
49 46 100       68 unless ($t->isLeaf()) {
50 16         90 my $uid = $self->_createUID($t);
51 16         48 push @results => ("
  • " .
  • 52             $t->getNodeValue() . "");
    53 16         68 push @results => "
      ";
    54             }
    55             else {
    56 30         155 push @results => ("
  • " . $t->getNodeValue() . "
  • ");
    57             }
    58 46         126 $last_depth = $current_depth;
    59 3         17 };
    60 3 100       11 $traversal_sub->($self->{tree}) if $self->{include_trunk};
    61 3         11 $self->{tree}->traverse($traversal_sub);
    62 3         53 $last_depth -= $root_depth;
    63 3 100       6 $last_depth++ if $self->{include_trunk};
    64 3         10 push @results => ("" x ($last_depth + 1));
    65              
    66 3         43 return (join "\n" => @results);
    67             }
    68              
    69             sub expandPathComplex {
    70 5     5 1 19 my ($self, $tree, $config, $current_path, @path) = @_;
    71              
    72 5         22 my ($list_func, $list_item_func) = $self->_processConfig($config);
    73              
    74 5         94 my @results = $list_func->(OPEN_TAG);
    75 5         22 my $root_depth = $tree->getDepth() + 1;
    76 5         25 my $last_depth = -1;
    77             my $traversal_sub = sub {
    78 76     76   1345 my ($t) = @_;
    79 76         89 my $display_style = "none";
    80 76 100 100     160 if (defined $current_path && $self->_compareNodeToPath($current_path, $t)) {
    81 9         53 $display_style = "block";
    82 9         17 $current_path = shift @path;
    83             }
    84 76         189 my $current_depth = $t->getDepth();
    85 76 100       543 push @results => ($list_func->(CLOSE_TAG) x ($last_depth - $current_depth)) if ($last_depth > $current_depth);
    86 76 100       135 unless ($t->isLeaf()) {
    87 26         172 my $uid = $self->_createUID($t);
    88 26         455 push @results => ($list_item_func->($t, EXPANDED, $uid));
    89 26         522 push @results => $list_func->(OPEN_TAG, $uid, $display_style);
    90             }
    91             else {
    92 50         1105 push @results => ($list_item_func->($t));
    93             }
    94 76         310 $last_depth = $current_depth;
    95 5         23 };
    96 5 100       17 $traversal_sub->($self->{tree}) if $self->{include_trunk};
    97 5         25 $self->{tree}->traverse($traversal_sub);
    98 5         95 $last_depth -= $root_depth;
    99 5 100       16 $last_depth++ if $self->{include_trunk};
    100 5         91 push @results => ($list_func->(CLOSE_TAG) x ($last_depth + 1));
    101 5         281 return (join "\n" => @results);
    102             }
    103              
    104             sub expandAllSimple {
    105 2     2 1 3 my ($self) = @_;
    106 2         5 my @results = ("
      ");
    107 2         9 my $root_depth = $self->{tree}->getDepth() + 1;
    108 2         8 my $last_depth = -1;
    109             my $traversal_sub = sub {
    110 31     31   460 my ($t) = @_;
    111 31         65 my $current_depth = $t->getDepth();
    112 31 100       96 push @results => ("" x ($last_depth - $current_depth)) if ($last_depth > $current_depth);
    113 31 100       48 unless ($t->isLeaf()) {
    114 11         75 my $uid = $self->_createUID($t);
    115 11         26 push @results => ("
  • " .
  • 116             $t->getNodeValue() . "");
    117 11         68 push @results => "
      ";
    118             }
    119             else {
    120 20         104 push @results => ("
  • " . $t->getNodeValue() . "
  • ");
    121             }
    122 31         87 $last_depth = $current_depth;
    123 2         11 };
    124 2 100       10 $traversal_sub->($self->{tree}) if $self->{include_trunk};
    125 2         9 $self->{tree}->traverse($traversal_sub);
    126 2         35 $last_depth -= $root_depth;
    127 2 100       8 $last_depth++ if $self->{include_trunk};
    128 2         5 push @results => ("" x ($last_depth + 1));
    129 2         23 return (join "\n" => @results);
    130             }
    131              
    132             sub expandAllComplex {
    133 7     7 1 40 my ($self, $config) = @_;
    134              
    135 7         59 my ($list_func, $list_item_func) = $self->_processConfig($config);
    136              
    137 7         138 my @results = $list_func->(OPEN_TAG);
    138 7         36 my $root_depth = $self->{tree}->getDepth() + 1;
    139 7         35 my $last_depth = -1;
    140             my $traversal_sub = sub {
    141 94     94   1547 my ($t) = @_;
    142 94         150 my $current_depth = $t->getDepth();
    143 94 100       657 push @results => ($list_func->(CLOSE_TAG) x ($last_depth - $current_depth)) if ($last_depth > $current_depth);
    144 94 100       157 unless ($t->isLeaf()) {
    145 32         214 my $uid = $self->_createUID($t);
    146 32         596 push @results => ($list_item_func->($t, EXPANDED, $uid));
    147 32         884 push @results => $list_func->(OPEN_TAG, $uid);
    148             }
    149             else {
    150 62         1274 push @results => ($list_item_func->($t));
    151             }
    152 94         707 $last_depth = $current_depth;
    153 7         46 };
    154 7 100       26 $traversal_sub->($self->{tree}) if $self->{include_trunk};
    155 7         33 $self->{tree}->traverse($traversal_sub);
    156 7         127 $last_depth -= $root_depth;
    157 7 100       22 $last_depth++ if $self->{include_trunk};
    158 7         132 push @results => ($list_func->(CLOSE_TAG) x ($last_depth + 1));
    159 7         341 return (join "\n" => @results);
    160             }
    161              
    162             # code strings
    163              
    164 1         355 use constant LIST_FUNCTION_CODE_STRING => q|
    165             sub {
    166             my ($tag_type, $list_id, $display_style) = @_;
    167             # allow this to be found quickly
    168             return "" if ($tag_type == CLOSE_TAG);
    169             # test the most functional first
    170             if ($tag_type == OPEN_TAG && $list_id && $display_style) {
    171             my $temp_list_css;
    172             if ($list_css && $list_css !~ /CLASS/) {
    173             # in case someone has already set the list_css
    174             # property, we need to add out display property
    175             # to it, so we need to do a little text mangling
    176             $temp_list_css = $list_css;
    177             chop($temp_list_css);
    178             $temp_list_css .= " display: $display_style;'";
    179             }
    180             elsif ($list_css) {
    181             $temp_list_css = "${list_css} STYLE='display: $display_style;'"
    182             }
    183             else {
    184             $temp_list_css = " STYLE='display: $display_style;'"
    185             }
    186             return "<${list_type}${temp_list_css} ID='${list_id}'>"
    187             }
    188             # next...
    189             return "<${list_type}${list_css} ID='${list_id}'>"
    190             if ($tag_type == OPEN_TAG && $list_id);
    191             # and finally, something that does nothing really
    192             return "<${list_type}${list_css}>" if ($tag_type == OPEN_TAG);
    193             }
    194 1     1   9 |;
      1         2  
    195              
    196             sub _buildListItemFunction {
    197 12     12   48 my ($self, %config) = @_;
    198             # process the configuration directives
    199 12         50 my ($list_item_css, $expanded_item_css, $node_formatter) = $self->_processListItemConfig(%config);
    200              
    201 12         31 my $link_css = "";
    202 12 100       44 if (exists $config{link_css}) {
        100          
    203 2         7 $link_css = " STYLE='" . $config{link_css}. "'";
    204             }
    205             elsif (exists $config{link_css_class}) {
    206 3         8 $link_css = " CLASS='" . $config{link_css_class} . "'";
    207             }
    208              
    209 12         30 my $form_element_formatter;
    210 12 50       32 if (exists $config{form_element_formatter}) {
    211 0         0 $form_element_formatter = $config{form_element_formatter};
    212             }
    213             else {
    214 12 100       41 if (exists $config{radio_button}) {
        100          
    215 1         4 $form_element_formatter = $self->_makeRadioButtonFormatter($config{radio_button});
    216             }
    217             elsif (exists $config{checkbox}) {
    218 1         6 $form_element_formatter = $self->_makeCheckBoxFormatter($config{checkbox});
    219             }
    220             }
    221              
    222             # now compile the subroutine in the current environment
    223 12         1904 return eval $self->LIST_ITEM_FUNCTION_CODE_STRING;
    224             }
    225              
    226             sub _makeRadioButtonFormatter {
    227 1     1   4 my ($self, $radio_button_id) = @_;
    228             return sub {
    229 15     15   26 my ($t) = @_;
    230 15         33 return "";
    231             }
    232 1         5 }
    233              
    234             sub _makeCheckBoxFormatter {
    235 1     1   3 my ($self, $checkbox_id) = @_;
    236             return sub {
    237 15     15   20 my ($t) = @_;
    238 15         32 return "";
    239             }
    240 1         4 }
    241              
    242 1         59 use constant LIST_ITEM_FUNCTION_CODE_STRING => q|;
    243             sub {
    244             my ($t, $is_expanded, $tree_id) = @_;
    245             my $item_css = $list_item_css;
    246             if ($is_expanded) {
    247             $item_css = $expanded_item_css if $expanded_item_css;
    248             return "" .
    249             (($form_element_formatter) ? $form_element_formatter->($t) : "") .
    250             "" .
    251             (($node_formatter) ? $node_formatter->($t) : $t->getNodeValue()) .
    252             "";
    253             }
    254             return "" .
    255             (($form_element_formatter) ? $form_element_formatter->($t) : "") .
    256             (($node_formatter) ? $node_formatter->($t) : $t->getNodeValue()) .
    257             "";
    258             }
    259 1     1   7 |;
      1         2  
    260              
    261 1         61 use constant javascript => q|
    262            
    275 1     1   6 |;
      1         2  
    276              
    277             1;
    278              
    279             __END__