点击父下拉菜单中的链接时,我必须显示一个子菜单,显示时,父母应该隐藏,而子项显示
我的尝试:
<ul class="nav navbar-nav navbar-right " >
<li class="dropdown">
<a class="dropdown-toggle" data-toggle="dropdown" title=""></a>
<ul id="dropdown-menu" class="dropdown-menu" role="menu" ng-hide="showSubMenu">
<li> <a href="#" ng-click="showSubMenu = ! showSubMenu">Hide me and show submenu</a></li>
</ul>
<ul class="dropdown-menu" role="menu" ng-hide="!showSubMenu">
<li><a href="#" ng-click="showSubMenu =!showSubMenu">Hide me and t show back parent</a></li>
</ul>
</li>
</ul>
更改可见性正在运行,但是不会触发放置事件,我必须再次单击以切换下拉列表,我需要在更改可见性状态后自动完成
答案 0 :(得分:1)
您必须使用
自定义下拉列表Angular
sintax
var app = angular.module("app", []);
app.directive('offClick', ['$rootScope', '$parse', function ($rootScope, $parse) {
var id = 0;
var listeners = {};
// add variable to detect touch users moving..
var touchMove = false;
// Add event listeners to handle various events. Destop will ignore touch events
document.addEventListener("touchmove", offClickEventHandler, true);
document.addEventListener("touchend", offClickEventHandler, true);
document.addEventListener('click', offClickEventHandler, true);
function targetInFilter(target, elms) {
if (!target || !elms) return false;
var elmsLen = elms.length;
for (var i = 0; i < elmsLen; ++i) {
var currentElem = elms[i];
var containsTarget = false;
try {
containsTarget = currentElem.contains(target);
} catch (e) {
// If the node is not an Element (e.g., an SVGElement) node.contains() throws Exception in IE,
// see https://connect.microsoft.com/IE/feedback/details/780874/node-contains-is-incorrect
// In this case we use compareDocumentPosition() instead.
if (typeof currentElem.compareDocumentPosition !== 'undefined') {
containsTarget = currentElem === target || Boolean(currentElem.compareDocumentPosition(target) & 16);
}
}
if (containsTarget) {
return true;
}
}
return false;
}
function offClickEventHandler(event) {
// If event is a touchmove adjust touchMove state
if (event.type === 'touchmove') {
touchMove = true;
// And end function
return false;
}
// This will always fire on the touchend after the touchmove runs...
if (touchMove) {
// Reset touchmove to false
touchMove = false;
// And end function
return false;
}
var target = event.target || event.srcElement;
angular.forEach(listeners, function (listener, i) {
if (!(listener.elm.contains(target) || targetInFilter(target, listener.offClickFilter))) {
$rootScope.$evalAsync(function () {
listener.cb(listener.scope, {
$event: event
});
})
}
});
}
return {
restrict: 'A',
compile: function ($element, attr) {
var fn = $parse(attr.offClick);
return function (scope, element) {
var elmId = id++;
var offClickFilter;
var removeWatcher;
offClickFilter = document.querySelectorAll(scope.$eval(attr.offClickFilter));
if (attr.offClickIf) {
removeWatcher = $rootScope.$watch(function () {
return $parse(attr.offClickIf)(scope);
}, function (newVal) {
if (newVal) {
on();
} else if (!newVal) {
off();
}
});
} else {
on();
}
attr.$observe('offClickFilter', function (value) {
offClickFilter = document.querySelectorAll(scope.$eval(value));
});
scope.$on('$destroy', function () {
off();
if (removeWatcher) {
removeWatcher();
}
});
function on() {
listeners[elmId] = {
elm: element[0],
cb: fn,
scope: scope,
offClickFilter: offClickFilter
};
}
function off() {
delete listeners[elmId];
}
};
}
};
}]);
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta.2/css/bootstrap.min.css" integrity="sha384-PsH8R72JQ3SOdhVi3uxftmaW6Vc51MKb0q5P2rRUpPvrszuE4W1povHYgTpBfshb" crossorigin="anonymous">
<script src="https://code.jquery.com/jquery-3.2.1.slim.min.js" integrity="sha384-KJ3o2DKtIkvYIK3UENzmM7KCkRr/rE9/Qpg6aAZGJwFDMVNA/GpGFF93hXpG5KkN" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.12.3/umd/popper.min.js" integrity="sha384-vFJXuSJphROIrBnz7yo7oB41mKfc8JzQZiCq4NCceLEaO4IHwicKwpJf9c9IpFgh" crossorigin="anonymous"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta.2/js/bootstrap.min.js" integrity="sha384-alpBpkh1PFOepccYVYDB4do5UnbKysX5WZXm3XxPqe5iKTfUKjNkCk9SaVuEZflJ" crossorigin="anonymous"></script>
<div ng-app="app">
<div class="dropdown" ng-class="{'show': dropdown}" off-click="dropdown=false;secDropdown=false">
<button class="btn btn-secondary" type="button" ng-click="dropdown = !dropdown" >
Dropdown button
</button>
<div class="dropdown-menu" ng-class="{'show': dropdown && !secDropdown}">
<a class="dropdown-item" href="#" ng-click="secDropdown = true">Call Hero!</a>
</div>
<div class="dropdown-menu" ng-class="{'show': secDropdown}">
<a class="dropdown-item" href="#">I'm Hero!</a>
<div class="dropdown-divider"></div>
<a class="dropdown-item" href="#" ng-click="secDropdown = false">Back</a>
</div>
</div>
</div>