1 <?php
2
3 4 5 6 7 8 9 10
11
12 namespace Icybee\Modules\Pages;
13
14 use Brickrouge\Element;
15 use Brickrouge\ElementIsEmpty;
16
17 class NavigationBranchElement extends Element
18 {
19 protected $page;
20
21 static public function markup_navigation_leaf(array $args, $patron, $template)
22 {
23 global $core;
24
25 $page = $core->request->context->page;
26
27 return new static($page);
28 }
29
30 public function __construct(Page $page, array $attributes=array())
31 {
32 $this->page = $page;
33
34 parent::__construct
35 (
36 'div', $attributes + array
37 (
38 'class' => 'nav-branch'
39 )
40 );
41 }
42
43 protected function build_blueprint($page, $parent_id)
44 {
45 global $core;
46
47 $trail = array();
48 $p = $page;
49
50 while ($p)
51 {
52 $trail[$p->nid] = $p->nid;
53
54 $p = $p->parent;
55 }
56
57 $blueprint = $core->models['pages']->blueprint($this->page->siteid);
58
59 $build_blueprint = function($parent_id, $max_depth) use (&$build_blueprint, $blueprint, $trail)
60 {
61 if (empty($blueprint->children[$parent_id]))
62 {
63 return;
64 }
65
66 $children = array();
67
68 foreach ($blueprint->children[$parent_id] as $nid)
69 {
70 $page_blueprint = $blueprint->index[$nid];
71
72 if (!$page_blueprint->is_online || $page_blueprint->is_navigation_excluded || $page_blueprint->pattern)
73 {
74 continue;
75 }
76
77 $page_blueprint = clone $page_blueprint;
78
79 unset($page_blueprint->parent);
80 $page_blueprint->children = array();
81
82 if (isset($trail[$nid]) && $page_blueprint->depth < $max_depth)
83 {
84 $page_blueprint->children = $build_blueprint($nid, $max_depth);
85 }
86
87 $children[] = $page_blueprint;
88 }
89
90 return $children;
91 };
92
93 return $build_blueprint($parent_id, 2);
94 }
95
96 protected function render_inner_html()
97 {
98 global $core;
99
100 $page = $this->page;
101 $parent = $this->page;
102
103 while ($parent->parent)
104 {
105 $parent = $parent->parent;
106 }
107
108 $parent_id = $parent->nid;
109
110
111
112 $tree_blueprint = $this->build_blueprint($page, $parent_id);
113
114 if (!$tree_blueprint)
115 {
116 throw new ElementIsEmpty;
117 }
118
119 new NavigationBranchElement\AlterBlueprintEvent($this, $tree_blueprint, $page, $parent_id);
120
121 $ids = array();
122
123 $collect_ids = function(array $blueprint) use(&$collect_ids, &$ids)
124 {
125 foreach ($blueprint as $page_blueprint)
126 {
127 $ids[] = $page_blueprint->nid;
128
129 if ($page_blueprint->children)
130 {
131 $collect_ids($page_blueprint->children);
132 }
133 }
134 };
135
136 $html = '<div class="nav-branch-header"><h5><a href="' . \Brickrouge\escape($parent->url) . '">' . \Brickrouge\escape($parent->label) . '</a></h5></div>';
137
138 if ($tree_blueprint)
139 {
140 $collect_ids($tree_blueprint);
141
142 $pages = $core->models['pages']->find($ids);
143 $html .= '<div class="nav-branch-content">' . $this->render_page_recursive($tree_blueprint, $pages, $parent->depth + 1, 0) . '</div>';
144 }
145
146 return $html;
147 }
148
149 protected function render_page_recursive(array $children, $pages, $depth, $relative_depth)
150 {
151 $html = '';
152
153 foreach ($children as $blueprint_child)
154 {
155 $child = $pages[$blueprint_child->nid];
156
157 $html .= '<li class="' . $child->css_class('active trail') . '"><a href="' . \Brickrouge\escape($child->url) . '">' . \Brickrouge\escape($child->label) . '</a>';
158
159 if ($blueprint_child->children)
160 {
161 $html .= $this->render_page_recursive($blueprint_child->children, $pages, $depth + 1, $relative_depth + 1);
162 }
163
164 $html .= '</li>';
165 }
166
167 if ($html)
168 {
169 return <<<EOT
170 <ul class="nav nav-depth-$depth nav-relative-depth-$relative_depth">$html</ul>
171 EOT;
172 }
173 }
174 }
175
176 namespace Icybee\Modules\Pages\NavigationBranchElement;
177
178 179 180
181 class AlterBlueprintEvent extends \ICanBoogie\Event
182 {
183 184 185 186 187
188 public $blueprint;
189
190 191 192 193 194
195 public $page;
196
197 198 199 200 201
202 public $parent_id;
203
204 205 206 207 208 209 210 211
212 public function __construct(\Icybee\Modules\Pages\NavigationBranchElement $target, array &$blueprint, \Icybee\Modules\Pages\Page $page, $parent_id)
213 {
214 $this->blueprint = &$blueprint;
215 $this->page = $page;
216 $this->parent_id = $parent_id;
217
218 parent::__construct($target, 'alter_blueprint');
219 }
220 }