Skip to content
This repository was archived by the owner on Apr 12, 2024. It is now read-only.
This repository was archived by the owner on Apr 12, 2024. It is now read-only.

support blur and focus events #1277

Closed
Closed

Description

@gops

Almost all events are supported by angularjs but blur and focus events are left out. please add support for this.

Activity

  1. avimar commented on Sep 10, 2012

    @avimar

    ToDoMVC wrote angular directives for blur/focus:

    https://github.com/addyosmani/todomvc/blob/master/architecture-examples/angularjs/js/directives/

    <body ng-app="editer">
    
    
    var editer = angular.module('editer', []);
    
    
    editer.directive('ngBlur', function() {
      return function( scope, elem, attrs ) {
        elem.bind('blur', function() {
          scope.$apply(attrs.ngBlur);
        });
      };
    });
    
    editer.directive('ngFocus', function( $timeout ) {
      return function( scope, elem, attrs ) {
        scope.$watch(attrs.ngFocus, function( newval ) {
          if ( newval ) {
            $timeout(function() {
              elem[0].focus();
            }, 0, false);
          }
        });
      };
    });
    

    Also see other example here:
    http://jsfiddle.net/vmjj4/1/

  2. andershessellund commented on Sep 27, 2012

    @andershessellund
    Contributor

    ngFocus should definitely not work like this.

    Angular is based on bidirectional data binding, which means that if the focus attribute is bound to a model, the model should be updated when the element looses focus.

    An ngFocus which works analogous to the ngBlur directive above would be a good idea.

    A directive which focuses an element when it becomes visible could be a good idea.

  3. narenana commented on Dec 27, 2012

    @narenana

    Any updates on this ?

  4. philips commented on Dec 31, 2012

    @philips

    Thanks for posting this even if it isn't a great longterm solution. I needed ng-focus too. 👍

  5. arcanis commented on Jan 2, 2013

    @arcanis

    I'm using the following snippet to support blur, focus, keydown, keyup and keypress. Almost all the code comes from the original source code of angular, except that I'm using Array#reduce to avoid creating a named temporary object to store the directives.

    .directive( [ 'focus', 'blur', 'keyup', 'keydown', 'keypress' ].reduce( function ( container, name ) {
        var directiveName = 'ng' + name[ 0 ].toUpperCase( ) + name.substr( 1 );
    
        container[ directiveName ] = [ '$parse', function ( $parse ) {
            return function ( scope, element, attr ) {
                var fn = $parse( attr[ directiveName ] );
                element.bind( name, function ( event ) {
                    scope.$apply( function ( ) {
                        fn( scope, {
                            $event : event
                        } );
                    } );
                } );
            };
        } ];
    
        return container;
    }, { } ) );
    
  6. andriytyurnikov commented on Jan 13, 2013

    @andriytyurnikov

    @andershessellund or someone else, could you please give deeper explanation about why model should care about element focus or blur at all?

    Any HTML element is able to get focus - link or table header cell.

    From what I understand now, it will be enough if one should be able to trigger 'change' event manually.

    Also, as far as I know ngChange and ngModel directives are implemented only for input, select, and textarea tags.
    And keyboard and focus events can be used with any DOM element, and not necessary will modify models (think about gestures, hotkey shortcuts and key-combos).

  7. saden1 commented on Jan 16, 2013

    @saden1

    @andriytyurnikov

    One use-case I can think of is the ability to increase the number of rows in a textarea when it's focused and reduce it when it loses focus. Sorta like the tweet box on twitter.

  8. andershessellund commented on Jan 27, 2013

    @andershessellund
    Contributor

    @andriytyurnikov

    Just to clarify, I think that ngFocus and ngBlur should simply bind events to event handlers, like the code by @arcanis . My point was if one was to write a directive that that binds the focus status of an element to a boolean value on the model, it should be two-way. The code snippet posted by @avimar above, which is an ng-focus directive that sets focus on an element when a boolean attribute on the model changes to true should be handled using an event instead.

    A two-way binding directive could perhaps be implemented, but it would be different than directives such as ng-selected or ng-disabled, because elements do not actually have a 'focused' property. In my opinion, such a directive does not really belong in core angular.

    A directive that sets focus on an element when it becomes visible could be a good idea.

    A directive that sets focus on an element when an angular event occurs could also be a good idea.

  9. amfern commented on Mar 28, 2013

    @amfern

    +1

  10. ganarajpr commented on Apr 7, 2013

    @ganarajpr

    So I have been working on an implementation of ngFocus that is two way bound to a boolean. I would like to solicit comments and feedback before I bring in a pull request of the same.

    Here is a plunk which contains an implementation of the same.

    http://plnkr.co/edit/CvPCVxy4MfJEM1UksrrA?p=preview

    Points of consideration :

    1. Multiple objects / elements cannot have focus at the same time. So if we set the same variable to multiple elements it creates a race condition and goes into an infinite loop with focus jumping between the elements infinitely. This has to be prevented.
    2. Its two way data-binding. So we cannot be assigning a function to focus unless the function is also a setter.

    Feedback and comments are welcome. I would like to push this to the core if it is approved.

    Is this the right way to handle focus and blur? ( we would create ngFocus and ngBlur like ngShow and ngHide ). Are there any problems with this implementation ?

  11. defel commented on Apr 11, 2013

    @defel

    +1 for @ganarajpr solution

  12. chadwhitacre commented on Apr 13, 2013

    @chadwhitacre
    Contributor

    +1

  13. fabsor commented on Apr 14, 2013

    @fabsor

    @ganarajpr Solution looks good. Would it work with jqlite if we change $(element).focus and $(element).blur to element.bind("focus") and element.bind("blur") ?

  14. 25 remaining items

  15. uri commented on Jul 4, 2013

    @uri

    @arcanis I've been using your solution for a while now and it's great! The only issue is that reduce is only supported in IE 9 or lower.

  16. rayshan commented on Jul 6, 2013

    @rayshan

    +1

  17. leefernandes commented on Jul 8, 2013

    @leefernandes
    Contributor

    +100,000

  18. tanweihao commented on Jul 12, 2013

    @tanweihao

    +1 for arcanis's solution. This should really be in the default API.

  19. mbielski commented on Jul 12, 2013

    @mbielski

    If the purpose is setting the focus or causing a blur on a specific element, @ganarajpr has the best solution. I am using this directive and am happy with it, but there are no unit tests for it, and I am going to end up writing them myself unless the author posts some. There is also a good checklist for submitting a PR to be found here: #2979.

    If the purpose is reacting to a focus or blur event, the folks at AngularUI have a very good solution: https://github.com/angular-ui/ui-utils/blob/master/modules/event/event.js. I use this module in several places and am very happy with it.

  20. 29x10 commented on Jul 18, 2013

    @29x10

    @ganarajpr thanks +1

  21. added a commit that references this issue on Jul 18, 2013
    2bb27d4
  22. pkozlowski-opensource commented on Jul 18, 2013

    @pkozlowski-opensource
    Member

    Read only support for blur / focus events just landed in master. Let's move the discussion about setting focus to #2012

  23. added a commit that references this issue on Jul 22, 2013
    0f5f893
  24. Narretz commented on Sep 6, 2013

    @Narretz
    Contributor

    for anyone else wondering where exactly the commit landed: 2bb27d4

  25. andreas-gruenbacher commented on Oct 2, 2013

    @andreas-gruenbacher
    Contributor

    @ganarajpr: thanks for your solution, it works well enough given how hard Angular makes this kind of thing. (The hack for detecting multiple bound elements is an abomination though.)

    An issue I have with setting focus in JavaScript with .focus() in general is that it doesn't behave the same as when the user sets the focus on a text field (when jumping between fields or clicking on a label): when the user jumps to a field, the field automatically gets selected, but .focus() doesn't .select() the text; it doesn't even focus to the end of the text. I need consistent behavior for this.

    So whichever directive eventually gets added to Angular should either implement "focus and select" or should allow to customize what happens.

  26. fopsdev commented on Oct 20, 2013

    @fopsdev

    @andreas-gruenbacher yes having the same issue here. i've workarounded it by also sending a "cklick" event.
    would be great to have focus & click in an angular way

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions