xref: /webtrees/app/Menu.php (revision e7f56f2af615447ab1a7646851f88b465ace9e04)
1a25f0a04SGreg Roach<?php
2a25f0a04SGreg Roach/**
3a25f0a04SGreg Roach * webtrees: online genealogy
41062a142SGreg Roach * Copyright (C) 2018 webtrees development team
5a25f0a04SGreg Roach * This program is free software: you can redistribute it and/or modify
6a25f0a04SGreg Roach * it under the terms of the GNU General Public License as published by
7a25f0a04SGreg Roach * the Free Software Foundation, either version 3 of the License, or
8a25f0a04SGreg Roach * (at your option) any later version.
9a25f0a04SGreg Roach * This program is distributed in the hope that it will be useful,
10a25f0a04SGreg Roach * but WITHOUT ANY WARRANTY; without even the implied warranty of
11a25f0a04SGreg Roach * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12a25f0a04SGreg Roach * GNU General Public License for more details.
13a25f0a04SGreg Roach * You should have received a copy of the GNU General Public License
14a25f0a04SGreg Roach * along with this program. If not, see <http://www.gnu.org/licenses/>.
15a25f0a04SGreg Roach */
16*e7f56f2aSGreg Roachdeclare(strict_types=1);
17*e7f56f2aSGreg Roach
1876692c8bSGreg Roachnamespace Fisharebest\Webtrees;
19a25f0a04SGreg Roach
20a25f0a04SGreg Roach/**
2176692c8bSGreg Roach * System for generating menus.
22a25f0a04SGreg Roach */
23c1010edaSGreg Roachclass Menu
24c1010edaSGreg Roach{
25a25f0a04SGreg Roach    /** @var string The text to be displayed in the mneu */
26a25f0a04SGreg Roach    private $label;
27a25f0a04SGreg Roach
28a25f0a04SGreg Roach    /** @var string The target URL or href */
29a25f0a04SGreg Roach    private $link;
30a25f0a04SGreg Roach
313d0a6fa1SGreg Roach    /** @var string The CSS class used to style this menu item */
323d0a6fa1SGreg Roach    private $class;
33a25f0a04SGreg Roach
343cf92ae2SGreg Roach    /** @var string[] A list of optional HTML attributes, such as onclick or data-xxx */
353cf92ae2SGreg Roach    private $attrs;
36a25f0a04SGreg Roach
3776692c8bSGreg Roach    /** @var Menu[] An optional list of sub-menus. */
38a25f0a04SGreg Roach    private $submenus;
39a25f0a04SGreg Roach
40a25f0a04SGreg Roach    /**
41a25f0a04SGreg Roach     * Constructor for the menu class
42a25f0a04SGreg Roach     *
43a25f0a04SGreg Roach     * @param string   $label    The label for the menu item
44a25f0a04SGreg Roach     * @param string   $link     The target URL
453cf92ae2SGreg Roach     * @param string   $class    A CSS class
463cf92ae2SGreg Roach     * @param string[] $attrs    Optional attributes, such as onclick or data-xxx
47a25f0a04SGreg Roach     * @param Menu[]   $submenus Any submenus
48a25f0a04SGreg Roach     */
49c1010edaSGreg Roach    public function __construct($label, $link = '#', $class = '', array $attrs = [], array $submenus = [])
50c1010edaSGreg Roach    {
51a25f0a04SGreg Roach        $this
52a25f0a04SGreg Roach            ->setLabel($label)
53a25f0a04SGreg Roach            ->setLink($link)
543d0a6fa1SGreg Roach            ->setClass($class)
553cf92ae2SGreg Roach            ->setAttrs($attrs)
56a25f0a04SGreg Roach            ->setSubmenus($submenus);
57a25f0a04SGreg Roach    }
58a25f0a04SGreg Roach
59a25f0a04SGreg Roach    /**
6015d603e7SGreg Roach     * Render this menu using Bootstrap4 markup
61a25f0a04SGreg Roach     *
62a25f0a04SGreg Roach     * @return string
63a25f0a04SGreg Roach     */
64c1010edaSGreg Roach    public function bootstrap4()
65c1010edaSGreg Roach    {
66a25f0a04SGreg Roach        if ($this->submenus) {
67a25f0a04SGreg Roach            $submenus = '';
68a25f0a04SGreg Roach            foreach ($this->submenus as $submenu) {
6915d603e7SGreg Roach                $attrs = '';
7015d603e7SGreg Roach                foreach ($submenu->attrs as $key => $value) {
71d53324c9SGreg Roach                    $attrs .= ' ' . $key . '="' . e($value) . '"';
72a25f0a04SGreg Roach                }
73a25f0a04SGreg Roach
7415d603e7SGreg Roach                $class = trim('dropdown-item ' . $submenu->class);
7525b2dde3SGreg Roach                $submenus .= '<a class="' . $class . '" href="' . e($submenu->link) . '"' . $attrs . '>' . $submenu->label . '</a>';
7615d603e7SGreg Roach            }
7715d603e7SGreg Roach
7815d603e7SGreg Roach            $class = trim('nav-item dropdown ' . $this->class);
7915d603e7SGreg Roach
80a25f0a04SGreg Roach            return
8115d603e7SGreg Roach                '<li class="' . $class . '">' .
8215d603e7SGreg Roach                '<a href="#" class="nav-link dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">' .
83a25f0a04SGreg Roach                $this->label .
84a25f0a04SGreg Roach                '<span class="caret"></span></a>' .
8515d603e7SGreg Roach                '<div class="dropdown-menu" role="menu">' .
86a25f0a04SGreg Roach                $submenus .
8715d603e7SGreg Roach                '</div>' .
88a25f0a04SGreg Roach                '</li>';
89b2ce94c6SRico Sonntag        }
90b2ce94c6SRico Sonntag
913cf92ae2SGreg Roach        $attrs = '';
923cf92ae2SGreg Roach        foreach ($this->attrs as $key => $value) {
93d53324c9SGreg Roach            $attrs .= ' ' . $key . '="' . e($value) . '"';
94a25f0a04SGreg Roach        }
95a25f0a04SGreg Roach
9615d603e7SGreg Roach        $class = trim('nav-item ' . $this->class);
9715d603e7SGreg Roach
9825b2dde3SGreg Roach        return '<li class="' . $class . '"><a class="nav-link" href="' . e($this->link) . '"' . $attrs . '>' . $this->label . '</a></li>';
99a25f0a04SGreg Roach    }
100a25f0a04SGreg Roach
101a25f0a04SGreg Roach    /**
1023cf92ae2SGreg Roach     * Get the optional attributes.
1033cf92ae2SGreg Roach     *
1043cf92ae2SGreg Roach     * @return string[]
1053cf92ae2SGreg Roach     */
1068f53f488SRico Sonntag    public function getAttrs(): array
107c1010edaSGreg Roach    {
1083cf92ae2SGreg Roach        return $this->attrs;
1093cf92ae2SGreg Roach    }
1103cf92ae2SGreg Roach
1113cf92ae2SGreg Roach    /**
1123cf92ae2SGreg Roach     * Set the optional attributes.
1133cf92ae2SGreg Roach     *
1143cf92ae2SGreg Roach     * @param string[] $attrs
1153cf92ae2SGreg Roach     *
1163cf92ae2SGreg Roach     * @return $this
1173cf92ae2SGreg Roach     */
1188f53f488SRico Sonntag    public function setAttrs(array $attrs): self
119c1010edaSGreg Roach    {
1203cf92ae2SGreg Roach        $this->attrs = $attrs;
1213cf92ae2SGreg Roach
1223cf92ae2SGreg Roach        return $this;
1233cf92ae2SGreg Roach    }
1243cf92ae2SGreg Roach
1253cf92ae2SGreg Roach    /**
12676692c8bSGreg Roach     * Get the class.
12776692c8bSGreg Roach     *
128a25f0a04SGreg Roach     * @return string
129a25f0a04SGreg Roach     */
1308f53f488SRico Sonntag    public function getClass(): string
131c1010edaSGreg Roach    {
1323d0a6fa1SGreg Roach        return $this->class;
133a25f0a04SGreg Roach    }
134a25f0a04SGreg Roach
135a25f0a04SGreg Roach    /**
13676692c8bSGreg Roach     * Set the class.
13776692c8bSGreg Roach     *
1383d0a6fa1SGreg Roach     * @param string $class
139a25f0a04SGreg Roach     *
140a25f0a04SGreg Roach     * @return $this
141a25f0a04SGreg Roach     */
1428f53f488SRico Sonntag    public function setClass($class): self
143c1010edaSGreg Roach    {
1443d0a6fa1SGreg Roach        $this->class = $class;
145a25f0a04SGreg Roach
146a25f0a04SGreg Roach        return $this;
147a25f0a04SGreg Roach    }
148a25f0a04SGreg Roach
149a25f0a04SGreg Roach    /**
15076692c8bSGreg Roach     * Get the label.
15176692c8bSGreg Roach     *
152a25f0a04SGreg Roach     * @return string
153a25f0a04SGreg Roach     */
1548f53f488SRico Sonntag    public function getLabel(): string
155c1010edaSGreg Roach    {
156a25f0a04SGreg Roach        return $this->label;
157a25f0a04SGreg Roach    }
158a25f0a04SGreg Roach
159a25f0a04SGreg Roach    /**
16076692c8bSGreg Roach     * Set the label.
16176692c8bSGreg Roach     *
162a25f0a04SGreg Roach     * @param string $label
163a25f0a04SGreg Roach     *
164a25f0a04SGreg Roach     * @return $this
165a25f0a04SGreg Roach     */
1668f53f488SRico Sonntag    public function setLabel($label): self
167c1010edaSGreg Roach    {
168a25f0a04SGreg Roach        $this->label = $label;
169a25f0a04SGreg Roach
170a25f0a04SGreg Roach        return $this;
171a25f0a04SGreg Roach    }
172a25f0a04SGreg Roach
173a25f0a04SGreg Roach    /**
17476692c8bSGreg Roach     * Get the link.
1753cf92ae2SGreg Roach     *
176a25f0a04SGreg Roach     * @return string
177a25f0a04SGreg Roach     */
1788f53f488SRico Sonntag    public function getLink(): string
179c1010edaSGreg Roach    {
180a25f0a04SGreg Roach        return $this->link;
181a25f0a04SGreg Roach    }
182a25f0a04SGreg Roach
183a25f0a04SGreg Roach    /**
18476692c8bSGreg Roach     * Set the link.
18576692c8bSGreg Roach     *
186a25f0a04SGreg Roach     * @param string $link
187a25f0a04SGreg Roach     *
188a25f0a04SGreg Roach     * @return $this
189a25f0a04SGreg Roach     */
1908f53f488SRico Sonntag    public function setLink($link): self
191c1010edaSGreg Roach    {
192a25f0a04SGreg Roach        $this->link = $link;
193a25f0a04SGreg Roach
194a25f0a04SGreg Roach        return $this;
195a25f0a04SGreg Roach    }
196a25f0a04SGreg Roach
197a25f0a04SGreg Roach    /**
198a25f0a04SGreg Roach     * Add a submenu to this menu
199a25f0a04SGreg Roach     *
200ecb5b5e9SGreg Roach     * @param Menu $menu
201ecb5b5e9SGreg Roach     *
202ecb5b5e9SGreg Roach     * @return $this
203a25f0a04SGreg Roach     */
2048f53f488SRico Sonntag    public function addSubmenu($menu): self
205c1010edaSGreg Roach    {
206a25f0a04SGreg Roach        $this->submenus[] = $menu;
207ecb5b5e9SGreg Roach
208ecb5b5e9SGreg Roach        return $this;
209a25f0a04SGreg Roach    }
210a25f0a04SGreg Roach
211a25f0a04SGreg Roach    /**
212a25f0a04SGreg Roach     * Render this menu as an HTML list
213a25f0a04SGreg Roach     *
214a25f0a04SGreg Roach     * @return string
215a25f0a04SGreg Roach     */
2168f53f488SRico Sonntag    public function getMenuAsList(): string
217c1010edaSGreg Roach    {
2183cf92ae2SGreg Roach        $attrs = '';
2193cf92ae2SGreg Roach        foreach ($this->attrs as $key => $value) {
220d53324c9SGreg Roach            $attrs .= ' ' . $key . '="' . e($value) . '"';
221a25f0a04SGreg Roach        }
222a25f0a04SGreg Roach        if ($this->link) {
22325b2dde3SGreg Roach            $link = ' href="' . e($this->link) . '"';
224a25f0a04SGreg Roach        } else {
225a25f0a04SGreg Roach            $link = '';
226a25f0a04SGreg Roach        }
2273cf92ae2SGreg Roach        $html = '<a' . $link . $attrs . '>' . $this->label . '</a>';
228a25f0a04SGreg Roach        if ($this->submenus) {
229a25f0a04SGreg Roach            $html .= '<ul>';
230a25f0a04SGreg Roach            foreach ($this->submenus as $submenu) {
231a25f0a04SGreg Roach                $html .= $submenu->getMenuAsList();
232a25f0a04SGreg Roach            }
233a25f0a04SGreg Roach            $html .= '</ul>';
234a25f0a04SGreg Roach        }
235a25f0a04SGreg Roach
2363d0a6fa1SGreg Roach        return '<li class="' . $this->class . '">' . $html . '</li>';
237a25f0a04SGreg Roach    }
238a25f0a04SGreg Roach
239a25f0a04SGreg Roach    /**
24076692c8bSGreg Roach     * Get the sub-menus.
24176692c8bSGreg Roach     *
242a25f0a04SGreg Roach     * @return Menu[]
243a25f0a04SGreg Roach     */
2448f53f488SRico Sonntag    public function getSubmenus(): array
245c1010edaSGreg Roach    {
246a25f0a04SGreg Roach        return $this->submenus;
247a25f0a04SGreg Roach    }
248a25f0a04SGreg Roach
249a25f0a04SGreg Roach    /**
25076692c8bSGreg Roach     * Set the sub-menus.
25176692c8bSGreg Roach     *
252a25f0a04SGreg Roach     * @param Menu[] $submenus
253a25f0a04SGreg Roach     *
254a25f0a04SGreg Roach     * @return $this
255a25f0a04SGreg Roach     */
2568f53f488SRico Sonntag    public function setSubmenus(array $submenus): self
257c1010edaSGreg Roach    {
258a25f0a04SGreg Roach        $this->submenus = $submenus;
259a25f0a04SGreg Roach
260a25f0a04SGreg Roach        return $this;
261a25f0a04SGreg Roach    }
262a25f0a04SGreg Roach}
263