added offcanvas navigation feature
This commit is contained in:
parent
0a1ff00cc0
commit
91e31dd164
@ -49,13 +49,19 @@ class NavBar extends Widget
|
|||||||
*/
|
*/
|
||||||
public $options = [];
|
public $options = [];
|
||||||
/**
|
/**
|
||||||
* @var array the HTML attributes for the container tag. The following special options are recognized:
|
* @var array|bool the HTML attributes for the collapse container tag. The following special options are recognized:
|
||||||
*
|
*
|
||||||
* - tag: string, defaults to "div", the name of the container tag.
|
* - tag: string, defaults to "div", the name of the container tag.
|
||||||
*
|
*
|
||||||
* @see \yii\helpers\Html::renderTagAttributes() for details on how attributes are being rendered.
|
* @see \yii\helpers\Html::renderTagAttributes() for details on how attributes are being rendered.
|
||||||
*/
|
*/
|
||||||
public $collapseOptions = [];
|
public $collapseOptions = [];
|
||||||
|
/**
|
||||||
|
* @var array|bool the HTML attributes for the offcanvas container tag.
|
||||||
|
*
|
||||||
|
* @see \yii\helpers\Html::renderTagAttributes() for details on how attributes are being rendered.
|
||||||
|
*/
|
||||||
|
public $offcanvasOptions = false;
|
||||||
/**
|
/**
|
||||||
* @var string|bool the text of the brand or false if it's not used. Note that this is not HTML-encoded.
|
* @var string|bool the text of the brand or false if it's not used. Note that this is not HTML-encoded.
|
||||||
* @see https://getbootstrap.com/docs/5.1/components/navbar/
|
* @see https://getbootstrap.com/docs/5.1/components/navbar/
|
||||||
@ -130,8 +136,10 @@ class NavBar extends Widget
|
|||||||
if (!isset($this->innerContainerOptions['class'])) {
|
if (!isset($this->innerContainerOptions['class'])) {
|
||||||
Html::addCssClass($this->innerContainerOptions, ['panel' => 'container']);
|
Html::addCssClass($this->innerContainerOptions, ['panel' => 'container']);
|
||||||
}
|
}
|
||||||
if (!isset($this->collapseOptions['id'])) {
|
if ($this->collapseOptions !== false && !isset($this->collapseOptions['id'])) {
|
||||||
$this->collapseOptions['id'] = "{$this->options['id']}-collapse";
|
$this->collapseOptions['id'] = "{$this->options['id']}-collapse";
|
||||||
|
} elseif ($this->offcanvasOptions !== false && !isset($this->offcanvasOptions['id'])) {
|
||||||
|
$this->offcanvasOptions['id'] = "{$this->options['id']}-offcanvas";
|
||||||
}
|
}
|
||||||
if ($this->brandImage !== false) {
|
if ($this->brandImage !== false) {
|
||||||
$this->brandLabel = Html::img($this->brandImage);
|
$this->brandLabel = Html::img($this->brandImage);
|
||||||
@ -148,9 +156,6 @@ class NavBar extends Widget
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Html::addCssClass($this->collapseOptions, ['collapse' => 'collapse', 'widget' => 'navbar-collapse']);
|
|
||||||
$collapseOptions = $this->collapseOptions;
|
|
||||||
$collapseTag = ArrayHelper::remove($collapseOptions, 'tag', 'div');
|
|
||||||
|
|
||||||
echo Html::beginTag($navTag, $navOptions) . "\n";
|
echo Html::beginTag($navTag, $navOptions) . "\n";
|
||||||
if ($this->renderInnerContainer) {
|
if ($this->renderInnerContainer) {
|
||||||
@ -158,7 +163,14 @@ class NavBar extends Widget
|
|||||||
}
|
}
|
||||||
echo $brand . "\n";
|
echo $brand . "\n";
|
||||||
echo $this->renderToggleButton() . "\n";
|
echo $this->renderToggleButton() . "\n";
|
||||||
echo Html::beginTag($collapseTag, $collapseOptions) . "\n";
|
if ($this->collapseOptions !== false) {
|
||||||
|
Html::addCssClass($this->collapseOptions, ['collapse' => 'collapse', 'widget' => 'navbar-collapse']);
|
||||||
|
$collapseOptions = $this->collapseOptions;
|
||||||
|
$collapseTag = ArrayHelper::remove($collapseOptions, 'tag', 'div');
|
||||||
|
echo Html::beginTag($collapseTag, $collapseOptions) . "\n";
|
||||||
|
} elseif ($this->offcanvasOptions !== false) {
|
||||||
|
Offcanvas::begin($this->offcanvasOptions);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -166,8 +178,12 @@ class NavBar extends Widget
|
|||||||
*/
|
*/
|
||||||
public function run()
|
public function run()
|
||||||
{
|
{
|
||||||
$tag = ArrayHelper::remove($this->collapseOptions, 'tag', 'div');
|
if ($this->collapseOptions !== false) {
|
||||||
echo Html::endTag($tag) . "\n";
|
$tag = ArrayHelper::remove($this->collapseOptions, 'tag', 'div');
|
||||||
|
echo Html::endTag($tag) . "\n";
|
||||||
|
} elseif ($this->offcanvasOptions !== false) {
|
||||||
|
Offcanvas::end();
|
||||||
|
}
|
||||||
if ($this->renderInnerContainer) {
|
if ($this->renderInnerContainer) {
|
||||||
echo Html::endTag('div') . "\n";
|
echo Html::endTag('div') . "\n";
|
||||||
}
|
}
|
||||||
@ -194,17 +210,22 @@ class NavBar extends Widget
|
|||||||
{
|
{
|
||||||
$options = $this->togglerOptions;
|
$options = $this->togglerOptions;
|
||||||
Html::addCssClass($options, ['widget' => 'navbar-toggler']);
|
Html::addCssClass($options, ['widget' => 'navbar-toggler']);
|
||||||
|
if ($this->offcanvasOptions !== false) {
|
||||||
|
$bsData = ['bs-toggle' => 'offcanvas', 'bs-target' => '#' . $this->offcanvasOptions['id']];
|
||||||
|
$aria = $this->offcanvasOptions['id'];
|
||||||
|
} else {
|
||||||
|
$bsData = ['bs-toggle' => 'collapse', 'bs-target' => '#' . $this->collapseOptions['id']];
|
||||||
|
$aria = $this->collapseOptions['id'];
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
return Html::button(
|
return Html::button(
|
||||||
$this->togglerContent,
|
$this->togglerContent,
|
||||||
ArrayHelper::merge($options, [
|
ArrayHelper::merge($options, [
|
||||||
'type' => 'button',
|
'type' => 'button',
|
||||||
'data' => [
|
'data' => $bsData,
|
||||||
'bs-toggle' => 'collapse',
|
|
||||||
'bs-target' => '#' . $this->collapseOptions['id'],
|
|
||||||
],
|
|
||||||
'aria' => [
|
'aria' => [
|
||||||
'controls' => $this->collapseOptions['id'],
|
'controls' => $aria,
|
||||||
'expanded' => 'false',
|
'expanded' => 'false',
|
||||||
'label' => $this->screenReaderToggleText,
|
'label' => $this->screenReaderToggleText,
|
||||||
]
|
]
|
||||||
|
@ -4,6 +4,7 @@ namespace yiiunit\extensions\bootstrap5;
|
|||||||
|
|
||||||
use yii\bootstrap5\Nav;
|
use yii\bootstrap5\Nav;
|
||||||
use yii\bootstrap5\NavBar;
|
use yii\bootstrap5\NavBar;
|
||||||
|
use yii\bootstrap5\Offcanvas;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Tests for NavBar widget
|
* Tests for NavBar widget
|
||||||
@ -127,4 +128,68 @@ EXPECTED;
|
|||||||
|
|
||||||
$this->assertEqualsWithoutLE($expected, $out);
|
$this->assertEqualsWithoutLE($expected, $out);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function testOffcanvasNavigation()
|
||||||
|
{
|
||||||
|
NavBar::$counter = 0;
|
||||||
|
|
||||||
|
ob_start();
|
||||||
|
NavBar::begin([
|
||||||
|
'brandLabel' => 'Offcanvas navbar',
|
||||||
|
'brandUrl' => ['/'],
|
||||||
|
'options' => [
|
||||||
|
'class' => ['navbar', 'navbar-light', 'bg-light', 'fixed-top']
|
||||||
|
],
|
||||||
|
'innerContainerOptions' => [
|
||||||
|
'class' => ['container-fluid']
|
||||||
|
],
|
||||||
|
'collapseOptions' => false,
|
||||||
|
'offcanvasOptions' => [
|
||||||
|
'title' => 'Offcanvas',
|
||||||
|
'placement' => Offcanvas::PLACEMENT_END
|
||||||
|
]
|
||||||
|
]);
|
||||||
|
echo Nav::widget([
|
||||||
|
'options' => [
|
||||||
|
'class' => ['navbar-nav']
|
||||||
|
],
|
||||||
|
'items' => [
|
||||||
|
['label' => 'Home', 'url' => '#'],
|
||||||
|
['label' => 'Link', 'url' => '#'],
|
||||||
|
['label' => 'Dropdown', 'items' => [
|
||||||
|
['label' => 'Action', 'url' => '#'],
|
||||||
|
['label' => 'Another action', 'url' => '#'],
|
||||||
|
'-',
|
||||||
|
['label' => 'Something else here', 'url' => '#'],
|
||||||
|
]]
|
||||||
|
]
|
||||||
|
]);
|
||||||
|
NavBar::end();
|
||||||
|
$out = ob_get_clean();
|
||||||
|
|
||||||
|
$expected = <<<HTML
|
||||||
|
<nav id="w0" class="navbar navbar-light bg-light fixed-top">
|
||||||
|
<div class="container-fluid">
|
||||||
|
<a class="navbar-brand" href="/index.php?r=">Offcanvas navbar</a>
|
||||||
|
<button type="button" class="navbar-toggler" data-bs-toggle="offcanvas" data-bs-target="#w0-offcanvas" aria-controls="w0-offcanvas" aria-expanded="false" aria-label="Toggle navigation"><span class="navbar-toggler-icon"></span></button>
|
||||||
|
|
||||||
|
<div id="w0-offcanvas" class="offcanvas offcanvas-end" tabindex="-1" data-bs-backdrop="true" data-bs-scroll="false" aria-labelledby="w0-offcanvas-label">
|
||||||
|
<div class="offcanvas-header">
|
||||||
|
<h5 id="w0-offcanvas-label" class="offcanvas-title">Offcanvas</h5>
|
||||||
|
<button type="button" class="btn-close text-reset" data-bs-dismiss="offcanvas" aria-label="Close"></button>
|
||||||
|
</div>
|
||||||
|
<div class="offcanvas-body">
|
||||||
|
<ul id="w1" class="navbar-nav nav"><li class="nav-item"><a class="nav-link" href="#">Home</a></li>
|
||||||
|
<li class="nav-item"><a class="nav-link" href="#">Link</a></li>
|
||||||
|
<li class="dropdown nav-item"><a class="dropdown-toggle nav-link" href="#" data-bs-toggle="dropdown" role="button" aria-expanded="false">Dropdown</a><div id="w2" class="dropdown-menu"><a class="dropdown-item" href="#">Action</a>
|
||||||
|
<a class="dropdown-item" href="#">Another action</a>
|
||||||
|
<hr class="dropdown-divider">
|
||||||
|
<a class="dropdown-item" href="#">Something else here</a></div></li></ul>
|
||||||
|
</div>
|
||||||
|
</div></div>
|
||||||
|
</nav>
|
||||||
|
HTML;
|
||||||
|
|
||||||
|
$this->assertEqualsWithoutLE($expected, $out);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user