htmlangularautofocus

Autofocus attribute does not work properly on <input> with Angular


I'm facing impediments with an HTML <input /> with autofocus attribute using Angular.
I made a component InputComponent that has an @Input autoFocus.
My goal is to reflect this attribute on the tag <input /> in order to focus it when the page is loaded / refreshed.
The following syntaxes do work with raw code:

    <input autofocus />
    <input autofocus="" />
    <input autofocus="true" />
    <input autofocus="'true'" />
    <input autofocus="autofocus" />
    <input autofocus="'autofocus'" />

But I'm not able to make it work using the @Input autoFocus valued as true, 'true' or 'autofocus', trying the following syntaxes:

    <input [autofocus]="autoFocus" />
    <input [attr.autofocus]="autoFocus" />
    <input autofocus="{{ autoFocus }}" />

I even tested these syntaxes with raw values without anymore success:

    <input [autofocus]="'autofocus'" />
    <input [autofocus]="'true'" />
    <input [autofocus]="true" />
    <input [attr.autofocus]="'autofocus'" />
    <input [attr.autofocus]="'true'" />
    <input [attr.autofocus]="true" />
    <input autofocus="{{ 'autofocus' }}" />
    <input autofocus="{{ 'true' }}" />
    <input autofocus="{{ true }}" />

If I inspect the HTML DOM with chrome debugger, everything seems fine, final code is always <input autofocus="true" />. But the <input /> is still not focused when the page is loaded / refreshed !
It feels like interpreted code is done too late for the autofocus to be taken in account.
I wonder if someone else faced the same issue and found a solution ?
I guess I would use a directive like this exemple if I do not find a better solution.


Solution

  • Use a Directive with ElementRef and AfterViewInit

    A custom directive is the most reliable way to ensure autofocus behavior in Angular.

    Example code:

    // auto-focus.directive.ts
    import { Directive, ElementRef, Input, AfterViewInit } from '@angular/core';
    
    @Directive({
      selector: '[appAutoFocus]'
    })
    export class AutoFocusDirective implements AfterViewInit {
      @Input('appAutoFocus') autoFocus = false;
    
      constructor(private el: ElementRef<HTMLInputElement>) {}
    
      ngAfterViewInit() {
        if (this.autoFocus) {
          // Focus after view initialization
          this.el.nativeElement.focus();
        }
      }
    }
    

    Usage in Your Component Template:

    <input type="text" [appAutoFocus]="autoFocus" />
    

    Or if you want it always to autofocus:

    <input type="text" appAutoFocus="true" />
    

    ngAfterViewInit() ensures that the DOM is fully initialized before trying to focus the element.

    The browser’s native autofocus attribute only works on initial HTML render, not after Angular initializes the view.