summaryrefslogtreecommitdiffstats
path: root/library/Icinga/Web/Navigation/Renderer/NavigationItemRenderer.php
diff options
context:
space:
mode:
Diffstat (limited to 'library/Icinga/Web/Navigation/Renderer/NavigationItemRenderer.php')
-rw-r--r--library/Icinga/Web/Navigation/Renderer/NavigationItemRenderer.php235
1 files changed, 235 insertions, 0 deletions
diff --git a/library/Icinga/Web/Navigation/Renderer/NavigationItemRenderer.php b/library/Icinga/Web/Navigation/Renderer/NavigationItemRenderer.php
new file mode 100644
index 0000000..51136ff
--- /dev/null
+++ b/library/Icinga/Web/Navigation/Renderer/NavigationItemRenderer.php
@@ -0,0 +1,235 @@
+<?php
+/* Icinga Web 2 | (c) 2015 Icinga Development Team | GPLv2+ */
+
+namespace Icinga\Web\Navigation\Renderer;
+
+use Icinga\Application\Icinga;
+use Icinga\Exception\ProgrammingError;
+use Icinga\Util\StringHelper;
+use Icinga\Web\Navigation\NavigationItem;
+use Icinga\Web\Url;
+use Icinga\Web\View;
+
+/**
+ * NavigationItemRenderer
+ */
+class NavigationItemRenderer
+{
+ /**
+ * View
+ *
+ * @var View
+ */
+ protected $view;
+
+ /**
+ * The item being rendered
+ *
+ * @var NavigationItem
+ */
+ protected $item;
+
+ /**
+ * Internal link targets provided by Icinga Web 2
+ *
+ * @var array
+ */
+ protected $internalLinkTargets;
+
+ /**
+ * Whether to escape the label
+ *
+ * @var bool
+ */
+ protected $escapeLabel;
+
+ /**
+ * Create a new NavigationItemRenderer
+ *
+ * @param array $options
+ */
+ public function __construct(array $options = null)
+ {
+ if (! empty($options)) {
+ $this->setOptions($options);
+ }
+
+ $this->internalLinkTargets = array('_main', '_self', '_next');
+ $this->init();
+ }
+
+ /**
+ * Initialize this renderer
+ */
+ public function init()
+ {
+ }
+
+ /**
+ * Set the given options
+ *
+ * @param array $options
+ *
+ * @return $this
+ */
+ public function setOptions(array $options)
+ {
+ foreach ($options as $name => $value) {
+ $setter = 'set' . StringHelper::cname($name);
+ if (method_exists($this, $setter)) {
+ $this->$setter($value);
+ }
+ }
+
+ return $this;
+ }
+
+ /**
+ * Set the view
+ *
+ * @param View $view
+ *
+ * @return $this
+ */
+ public function setView(View $view)
+ {
+ $this->view = $view;
+ return $this;
+ }
+
+ /**
+ * Return the view
+ *
+ * @return View
+ */
+ public function view()
+ {
+ if ($this->view === null) {
+ $this->setView(Icinga::app()->getViewRenderer()->view);
+ }
+
+ return $this->view;
+ }
+
+ /**
+ * Set the navigation item to render
+ *
+ * @param NavigationItem $item
+ *
+ * @return $this
+ */
+ public function setItem(NavigationItem $item)
+ {
+ $this->item = $item;
+ return $this;
+ }
+
+ /**
+ * Return the navigation item being rendered
+ *
+ * @return NavigationItem
+ */
+ public function getItem()
+ {
+ return $this->item;
+ }
+
+ /**
+ * Set whether to escape the label
+ *
+ * @param bool $state
+ *
+ * @return $this
+ */
+ public function setEscapeLabel($state = true)
+ {
+ $this->escapeLabel = (bool) $state;
+ return $this;
+ }
+
+ /**
+ * Return whether to escape the label
+ *
+ * @return bool
+ */
+ public function getEscapeLabel()
+ {
+ return $this->escapeLabel !== null ? $this->escapeLabel : true;
+ }
+
+ /**
+ * Render the given navigation item as HTML anchor
+ *
+ * @param NavigationItem $item
+ *
+ * @return string
+ */
+ public function render(NavigationItem $item = null)
+ {
+ if ($item !== null) {
+ $this->setItem($item);
+ } elseif (($item = $this->getItem()) === null) {
+ throw new ProgrammingError(
+ 'Cannot render nothing. Pass the item to render as part'
+ . ' of the call to render() or set it with setItem()'
+ );
+ }
+
+ $label = $this->getEscapeLabel()
+ ? $this->view()->escape($item->getLabel())
+ : $item->getLabel();
+ if (($icon = $item->getIcon()) !== null) {
+ $label = $this->view()->icon($icon) . $label;
+ } elseif ($item->getName()) {
+ $firstLetter = $item->getName()[0];
+ $label = $this->view()->icon('letter', null, ['data-letter' => strtolower($firstLetter)]) . $label;
+ }
+
+ if (($url = $item->getUrl()) !== null) {
+ $url->overwriteParams($item->getUrlParameters());
+
+ $target = $item->getTarget();
+ if ($url->isExternal() && (!$target || in_array($target, $this->internalLinkTargets, true))) {
+ $url = Url::fromPath('iframe', array('url' => $url));
+ }
+
+ $content = sprintf(
+ '<a%s href="%s"%s>%s</a>',
+ $this->view()->propertiesToString($item->getAttributes()),
+ $this->view()->escape($url->getAbsoluteUrl('&')),
+ $this->renderTargetAttribute(),
+ $label
+ );
+ } elseif ($label) {
+ $content = sprintf(
+ '<%1$s%2$s>%3$s</%1$s>',
+ $item::LINK_ALTERNATIVE,
+ $this->view()->propertiesToString($item->getAttributes()),
+ $label
+ );
+ } else {
+ $content = '';
+ }
+
+ return $content;
+ }
+
+ /**
+ * Render and return the attribute to provide a non-default target for the url
+ *
+ * @return string
+ */
+ protected function renderTargetAttribute()
+ {
+ $target = $this->getItem()->getTarget();
+ if ($target === null || $this->getItem()->getUrl()->getAbsoluteUrl() == '#') {
+ return '';
+ }
+
+ if (! in_array($target, $this->internalLinkTargets, true)) {
+ return ' target="' . $this->view()->escape($target) . '"';
+ }
+
+ return ' data-base-target="' . $target . '"';
+ }
+}