当点击Angular UI引导窗口外时隐藏它

Hide Angular UI Bootstrap popover when clicking outside of it

本文关键字:窗口 隐藏 Angular UI      更新时间:2023-09-26

我试图手动关闭一个引导弹出窗口,让它关闭时,我点击任何地方的documentbody不是弹出窗口。

我发现最接近的事情来完成这是创建一个指令(找到这个答案),但这是一个手动触发,如果一个变量是truefalse

谁能帮我弄清楚如何让它关闭,如果我点击任何东西,不是弹出窗口?

我不介意使用jQuery $(document).click(function(e){});,我只是不知道如何调用关闭。

<div id="new_button" popover-template="plusButtonURL" popover-placement="right" popover-append-to-body="true" popover-animation="false">+</div>

通常popover-trigger="focus"会做的伎俩,但是我的弹出窗口包含需要点击的内容。我有一个ng-click在我的弹出窗口得到忽略,如果我使用焦点触发器,所以我正在寻找一个不那么传统的方式来解决这个问题。

UPDATE:在1.0版本中,我们添加了一个名为outsideClick的新触发器,当用户单击弹出窗口或工具提示外时,它将自动关闭弹出窗口或工具提示。

从0.14.0版本开始,我们增加了通过tooltip-is-openpopover-is-open属性以编程方式控制工具提示/弹出窗口打开或关闭的能力。

从Angular UI Bootstrap 1.0.0开始,有一个新的outsideClick触发器用于工具提示和弹出窗口(在这个pull request中引入)。在Angular UI Bootstrap 2.0.0中,popover-trigger已经被修改为使用Angular表达式(Changelog),所以这个值必须加引号。这段代码将适用于当前版本的angular-ui:

<div id="new_button" uib-popover-template="plusButtonURL" popover-trigger="'outsideClick'"
    popover-placement="right" popover-append-to-body="true" popover-animation="false">+</div>

这段代码可以在旧版本的Angular UI Bootstrap(2.0.0之前)中使用:

<div id="new_button" uib-popover-template="plusButtonURL" popover-trigger="outsideClick"
    popover-placement="right" popover-append-to-body="true" popover-animation="false">+</div>

编辑:

<标题> 恰好演示

下面是它的工作原理(仍然很长很详尽的解释):

  1. 创建一个自定义指令,允许你瞄准触发器元素。
  2. 创建一个添加到主体的自定义指令,当它被点击时,它会找到触发器元素并触发自定义事件。

创建一个针对触发器元素的自定义指令:

您需要从打开弹出窗口的元素触发自定义事件处理程序(在演示中,这是按钮)。挑战在于弹出窗口是作为兄弟元素附加到这个元素的,我一直认为,当您遍历DOM并期望它具有特定结构时,事情有更大的可能会中断。有几种方法可以瞄准触发器元素,但我的方法是在单击元素时向元素添加唯一的类名(我选择'trigger')。在这种情况下,一次只能打开一个弹出窗口,所以使用类名是安全的,但您可以根据自己的喜好进行修改。

自定义指令

app.directive('popoverElem', function(){
  return{
    link: function(scope, element, attrs) {
      element.on('click', function(){
        element.addClass('trigger');
      });
    }
  }
});

应用于按钮

<button popover-template="dynamicPopover.templateUrl" popover-title="{{dynamicPopover.title}}" class="btn btn-default" popover-elem>Popover With Template</button>

为文档主体(或任何其他元素)创建一个自定义指令来触发弹出窗口close:

最后一部分是创建一个自定义指令,它将定位触发元素,并在被应用的元素被点击时触发自定义事件来关闭弹出窗口。当然,你必须从"触发器"元素中排除初始点击事件,并在弹出窗口内部排除任何你想要与之交互的元素。因此,我添加了一个名为exclude-class的属性,这样您就可以定义一个类,您可以将其添加到点击事件应该被忽略(不会导致弹出窗口关闭)的元素中。

为了清理,当事件处理程序被触发时,我们删除添加到触发器元素中的触发器类。

app.directive('popoverClose', function($timeout){
  return{
    scope: {
      excludeClass: '@'
    },
    link: function(scope, element, attrs) {
      var trigger = document.getElementsByClassName('trigger');
      function closeTrigger(i) {
        $timeout(function(){ 
          angular.element(trigger[0]).triggerHandler('click').removeClass('trigger'); 
        });
      }
      element.on('click', function(event){
        var etarget = angular.element(event.target);
        var tlength = trigger.length;
        if(!etarget.hasClass('trigger') && !etarget.hasClass(scope.excludeClass)) {
          for(var i=0; i<tlength; i++) {
            closeTrigger(i)
          }
        }
      });
    }
  };
});

我将这个添加到body标签中,以便整个页面*充当弹出窗口的背景:

<body popover-close exclude-class="exclude">

并且,我在弹出窗口中添加了exclude类:

<input type="text" ng-model="dynamicPopover.title" class="form-control exclude">

所以,有一些调整和陷阱,但我把它留给你:

  1. 你应该在popover-close指令的link函数中设置一个默认的排除类,以防没有定义。
  2. 你需要意识到popover-close指令是元素绑定的,所以如果你删除了我在html和body元素上设置的样式,给它们100%的高度,如果你的内容没有填充,你可能会在你的视窗中有"死区"。

在Chrome, Firefox和Safari测试。

popover-trigger="'outsideClick'"这将完美地工作。

popover-trigger="outsideClick"这将不会。

我花了一天的时间来弄清楚为什么它不适合我。

这是因为他们使用这个代码来检查这个,"if (trigger === 'outsideClick')"

这是由于强类型检查,我们需要将其传递为String

有一个名为popover-trigger的属性,您可以将属性focus分配给它。

<button 
      popover-placement="right" 
      popover="On the Right!" 
      popover-trigger="focus" 
      class="btn btn-default">
   Right
</button>

这个很有用!:)

编辑:要允许单击工具提示而不触发焦点丢失,请考虑类似于下面的方法

如果你想让它在angular中工作,试着创建你自己的触发器定义。关于如何做到这一点的建议可以在这里找到。

你要找的是

<button
      popover-trigger="outsideClick" 
      class="btn btn-default">
   Right
</button>

来自文档- outsideClick触发器将导致弹出窗口在单击时切换,并在单击其他任何内容时隐藏。

您可以使用:

标记

<div ng-app="Module">
    <div ng-controller="formController">
        <button uib-popover-template="dynamicPopover.templateUrl" popover-trigger="focus" 
          popover-placement="left" type="button" class="btn btn-default">
             Popover With Template
        </button>
        <script type="text/ng-template" id="myPopoverTemplate.html">
            <div>
                <span>prasad!!</span>
            </div>
        </script>
    </div>
</div>
Javascript

<script type="text/javascript">
    var app = angular.module("Module", ['ui.bootstrap']);
    app.controller("formController", ['$scope', function($scope) {
        $scope.dynamicPopover = {
            templateUrl: 'myPopoverTemplate.html'
        };
    }]);
</script>

我也有同样的问题,popover-trigger="'outsideClick'"为我工作。有趣的是,文档并没有说明这个问题。

关于'$uibTooltipProvider' setTriggers方法中的' outereclick '选项。文档中说"outsideClick触发器将导致工具提示在单击时切换,并在单击其他任何内容时隐藏。"

Angular bootstrap ui新版本1。X具有方便的外侧击功能。升级到新版本。

<button uib-popover-template="updatePassword.templateUrl" popover-title="Update Password" popover-trigger="outsideClick" popover-placement="right" popover-append-to-body="true">Click here</button>

这是我的工作。

如果弹出窗口中有提交按钮或单击事件,

焦点将不起作用。这是一个很有用的方法。

为你的一些背景元素添加onclick="void(0)"行为,当点击时将摆脱弹出窗口

看看https://github.com/angular-ui/bootstrap/issues/2123

1)使用ng-bootstrap为Popover

2)将ng-bootstrap版本更新到3.0.0或以上。即NPM install——save @ng-bootstrap/ng-bootstrap@3.0.0

3)更新后,您可以使用Ngbpopover的[autoClose]功能。

<button type="button" class="btn btn-outline-secondary" popoverTitle="Pop title" [autoClose]="true" ngbPopover="Click anywhere or press Escape to close (try the toggling element too)">Click to toggle</button>