简体   繁体   English

Angular.js关闭,点击任何地方但在元素上

[英]Angular.js closing with click anywhere but on the element

It's pretty common thing, like if you click on inbox here here on stackoverflow. 这很常见,比如你在这里点击stackoverflow上的收件箱。 I'll be calling that dialog or whatever gets opened a thing . 我会打电话给那个对话框或任何被打开的东西

Now there are two ways I know of to deal with this, 现在有两种方法可以解决这个问题,

  1. you create an invisible overlay where only the element you opened has bigger zindex, and you close your thing by clicking on the overlay 你创建了一个不可见的叠加层,其中只有你打开的元素有更大的zindex,你通过点击叠加来关闭你的东西
  2. click event on the document, and you check upon clicking whether you clicked on your thing or outside it, in which case you close your thing . 单击文档上的事件,然后单击是否单击了您的项目或其外部,在这种情况下,您关闭了您的项目

In either case I'd ideally like to use ng-class to add/remove class that would show/hide the thing . 在任何一种情况下,我都希望使用ng-class来添加/删除显示/隐藏事物的类

Now how would I do this with angular, so it could be used on any component(thing) I might add. 现在我将如何使用angular进行此操作,因此它可以用于我可能添加的任何组件(事物)。 It's not like I have single modal, I might have quite a few different components, with different html structure, positioning and stuff. 它不像我有单模态,我可能有不同的组件,具有不同的html结构,定位和东西。

Which approach would be better, document event, overlay or something completely else? 哪种方法会更好,记录事件,叠加或其他什么呢?

Since angular doesn't really have any reference to dom, document approach could be a problem, right, since I can't quite check whether I'm clicking on the thing element? 由于angular实际上并没有对dom的任何引用,因此,文档方法可能是个问题,因为我无法确定是否点击了thing元素? Unless I'd give every thing the same class.. 除非我给所有的东西都是同一个班级..

Overlay approach on the other hand doesn't require any reference to dom elements. 另一方面,叠加方法不需要任何对dom元素的引用。

Both approaches would need a unique var at rootScope for that ng-class to work.. which bring the question whether to use ng-class or something custom.. 这两种方法都需要在rootScope上使用一个唯一的var来使该ng-class工作..这带来了是否使用ng-class或者自定义的问题。

Anyway just throwing my ideas out there, maybe I'm thinking about it wrong from the beginning, has anyone dealt with this before? 无论如何只是把我的想法扔到那里,也许我从一开始就认为它是错的,有没有人以前处理过这个?

The way I've tackled things like this before is using inheritedData to communicate to the click handler whether it's in or out of the thing: 我之前处理过这样的事情的方式是使用inheritedData与click处理程序进行通信,无论它是在事物内还是外部:

  • In the custom directive for the thing, add a data variable to the element, using jqLite data, say element.data('myThing',true) . 在事物的自定义指令中,使用jqLit​​e数据向元素添加数据变量,例如element.data('myThing',true) If you want to distinguish between multiple instances of the the thing, you might need to use some uniquely generated key. 如果要区分该事物的多个实例,则可能需要使用一些唯一生成的密钥。

  • In the same custom directive, in a click event handler on document.body, you can check angular.element(event.target).inheritedData('myThing') 在同一个自定义指令中,在document.body上的单击事件处理程序中,您可以检查angular.element(event.target).inheritedData('myThing')

An example directive that uses this technique is below 下面是使用此技术的示例指令

app.directive('thing', function($document,$window) {
  return {
    restrict: 'E',
    template: '<div><span>Inner thing</span></div>',
    replace: true,
    link: function(scope,element) {
      element.data('thing',true);

      angular.element($document[0].body).on('click',function(e) {
        var inThing =  angular.element(e.target).inheritedData('thing');
        if (inThing) {
          $window.alert('in');
        } else {
          $window.alert('out');
        }
      })
    }
  }
});

and can be seen in this Plunker http://plnkr.co/edit/bRDLcLoesM7Z0BIxKxYu?p=preview 并且可以在这个Plunker中看到http://plnkr.co/edit/bRDLcLoesM7Z0BIxKxYu?p=preview

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM