Mercurial > pub > Impl
comparison Lib/IMPL/DOM/Navigator.pm @ 36:1828103371d0
DOM in works
| author | Sergey |
|---|---|
| date | Fri, 20 Nov 2009 16:48:08 +0300 |
| parents | a8086f85a571 |
| children | 16ada169ca75 |
comparison
equal
deleted
inserted
replaced
| 35:f25d021780b3 | 36:1828103371d0 |
|---|---|
| 18 die IMPL::InvalidArgumentException("A starting node is a required paramater") unless $CurrentNode; | 18 die IMPL::InvalidArgumentException("A starting node is a required paramater") unless $CurrentNode; |
| 19 | 19 |
| 20 $this->{$_state} = { alternatives => [ $CurrentNode ], current => 0 }; | 20 $this->{$_state} = { alternatives => [ $CurrentNode ], current => 0 }; |
| 21 } | 21 } |
| 22 | 22 |
| 23 sub _initNavigator { | |
| 24 my ($this,$CurrentNode) = @_; | |
| 25 | |
| 26 die IMPL::InvalidArgumentException("A starting node is a required paramater") unless $CurrentNode; | |
| 27 | |
| 28 $this->{$_state} = { alternatives => [ $CurrentNode ], current => 0 }; | |
| 29 delete $this->{$_path}; | |
| 30 delete $this->{$_savedstates}; | |
| 31 } | |
| 32 | |
| 23 sub _getCurrent { | 33 sub _getCurrent { |
| 24 $_[0]->{$_state}{alternatives}[$_[0]->{$_state}{current}] | 34 $_[0]->{$_state}{alternatives}[$_[0]->{$_state}{current}] |
| 25 } | 35 } |
| 26 | 36 |
| 27 sub Navigate { | 37 sub Navigate { |
| 28 my ($this,@path) = @_; | 38 my ($this,@path) = @_; |
| 29 | 39 |
| 30 return unless @path; | 40 return unless @path; |
| 31 | 41 |
| 42 my $node; | |
| 43 | |
| 32 foreach my $query (@path) { | 44 foreach my $query (@path) { |
| 33 if (my $current = $this->Current) { | 45 if (my $current = $this->Current) { |
| 34 | 46 |
| 35 my @alternatives = $this->Current->selectNodes($query); | 47 my @alternatives = $current->selectNodes($query); |
| 36 | 48 |
| 37 unless (@alternatives) { | 49 unless (@alternatives) { |
| 38 $this->advanceNavigator or return undef; | 50 $current = $this->advanceNavigator or return undef; |
| 39 @alternatives = $this->Current->selectNodes($query); | 51 @alternatives = $current->selectNodes($query); |
| 40 } | 52 } |
| 41 | 53 |
| 42 push @{$this->{$_path}},$this->{$_state}; | 54 push @{$this->{$_path}},$this->{$_state}; |
| 43 $this->{$_state} = { | 55 $this->{$_state} = { |
| 44 alternatives => \@alternatives, | 56 alternatives => \@alternatives, |
| 45 current => 0, | 57 current => 0, |
| 46 query => $query | 58 query => $query |
| 47 } | 59 }; |
| 60 | |
| 61 $node = $alternatives[0]; | |
| 48 } else { | 62 } else { |
| 49 return undef; | 63 return undef; |
| 50 } | 64 } |
| 51 } | 65 } |
| 52 | 66 |
| 53 return $this->Current; | 67 $node; |
| 54 } | 68 } |
| 55 | 69 |
| 56 sub selectNodes { | 70 sub selectNodes { |
| 57 my ($this,@path) = @_; | 71 my ($this,@path) = @_; |
| 58 | 72 |
| 78 $this->{$_state} = { | 92 $this->{$_state} = { |
| 79 alternatives => \@nodeSet, | 93 alternatives => \@nodeSet, |
| 80 current => 0 | 94 current => 0 |
| 81 }; | 95 }; |
| 82 | 96 |
| 83 return $this->Current; | 97 $nodeSet[0]; |
| 84 } | 98 } |
| 85 | 99 |
| 86 sub fetch { | 100 sub fetch { |
| 87 my ($this) = @_; | 101 my ($this) = @_; |
| 88 | 102 |
| 98 | 112 |
| 99 if (@{$this->{$_state}{alternatives}} <= $this->{$_state}{current}) { | 113 if (@{$this->{$_state}{alternatives}} <= $this->{$_state}{current}) { |
| 100 if ( exists $this->{$_state}{query} ) { | 114 if ( exists $this->{$_state}{query} ) { |
| 101 my $query = $this->{$_state}{query}; | 115 my $query = $this->{$_state}{query}; |
| 102 | 116 |
| 103 $this->Back or return 0; # that meams the end of the history | 117 $this->Back or return undef; # that meams the end of the history |
| 104 | 118 |
| 105 undef while ( $this->advanceNavigator and not $this->Navigate($query)); | 119 undef while ( $this->advanceNavigator and not $this->Navigate($query)); |
| 106 | 120 |
| 107 return $this->Current ? 1 : 0; | 121 return $this->Current; |
| 108 } | 122 } |
| 109 return 0; | 123 return undef; |
| 110 } | 124 } |
| 111 | 125 |
| 112 return 1; | 126 return $this->Current; |
| 113 } | 127 } |
| 114 | 128 |
| 115 sub doeach { | 129 sub doeach { |
| 116 my ($this,$code) = @_; | 130 my ($this,$code) = @_; |
| 117 local $_; | 131 local $_; |
| 119 do { | 133 do { |
| 120 for (my $i = $this->{$_state}{current}; $i < @{$this->{$_state}{alternatives}}; $i++) { | 134 for (my $i = $this->{$_state}{current}; $i < @{$this->{$_state}{alternatives}}; $i++) { |
| 121 $_ = $this->{$_state}{alternatives}[$i]; | 135 $_ = $this->{$_state}{alternatives}[$i]; |
| 122 $code->(); | 136 $code->(); |
| 123 } | 137 } |
| 124 $this->{$_state}{current} = @{$this->{$_state}{alternatives}}; | 138 $this->{$_state}{current} = @{$this->{$_state}{alternatives}}; |
| 125 } while ($this->advanceNavigator); | 139 } while ($this->advanceNavigator); |
| 126 } | 140 } |
| 127 | 141 |
| 128 sub Back { | 142 sub Back { |
| 129 my ($this,$steps) = @_; | 143 my ($this,$steps) = @_; |
| 130 | |
| 131 $steps ||= 1; | |
| 132 | |
| 133 if ($this->{$_path} and @{$this->{$_path}}) { | 144 if ($this->{$_path} and @{$this->{$_path}}) { |
| 134 | 145 if ( (not $steps) || $steps == 1) { |
| 135 $steps = @{$this->{$_path}} - 1 if $steps >= @{$this->{$_path}}; | 146 $this->{$_state} = pop @{$this->{$_path}}; |
| 136 | 147 } else { |
| 137 ($this->{$_state}) = splice @{$this->{$_path}},-$steps; | 148 $steps ||= 1; |
| 138 | 149 |
| 139 $this->Current; | 150 $steps = @{$this->{$_path}} - 1 if $steps >= @{$this->{$_path}}; |
| 151 | |
| 152 $this->{$_state} = (splice @{$this->{$_path}},-$steps)[0]; | |
| 153 } | |
| 154 $this->Current if defined wantarray; | |
| 140 } else { | 155 } else { |
| 141 return undef; | 156 return undef; |
| 142 } | 157 } |
| 143 } | 158 } |
| 144 | 159 |
