0

I've viewed quite a few solutions on stackoverflow with no success. Just to add as reference, I've viewed the following solutions:

Explanation of the component:

I have a list of names shown. Each name, you can click on and an input field will show. If you lose focus of the input field, it should "save" any changes to the name made in the input field.

There is a button and input field below for adding new people to the list as well.

So I have a dynamic list of names, that should be editable.

Current Behavior:

When clicking on a name, the input field shows. I added "autofocus" to the input field. But when the input field does show, focus is not set on the input field.

When clicking again into the input field, I gain focus. So basically I never had focus to begin with..

Behavior I want:

When clicking on a name, the input field should show. Focus should be in the input field. So right away I can edit the name after clicking it. If I click outside of the input field, I should lose focus.

Here is an example plunker. Included in the code is a copy-paste of a solution given from one of the stackoverflow answers I linked at the beginning of my post. My code is in app/app.component.ts starting from where I wrote: // begin my code:

https://plnkr.co/edit/pFMUsNuVqalnv2lR0nQC?p=preview

To comply with stackoverflow rules, I need to add code with a plunker link. Below is a copy-paste of my component from the plunker (WITHOUT the directive):

import {Component} from '@angular/core';

interface Person {
  name: string
}

@Component({
  selector: 'sample-app',
  template: `
    <div *ngFor="let person of listOfPeople">
      <span *ngIf="personOnEdit !== person" (click)="edit(person)">{{ person.name }}</span>
      <input *ngIf="personOnEdit === person"
             [(ngModel)]="person.name"
             autofocus
             (focusout)="edit(null)" />
    </div>
    <br/>
    <div>
      <form (submit)="addPerson()">
        <input placeholder="New Person Name" #newPersonName />
        <button (click)="addPerson(newPersonName.value); newPersonName.value = ''">Add Person</button>
      </form>
    </div>
  `
})
export class AppComponent {
  personOnEdit: Person = null;
  listOfPeople: Array<Person> = [
    {
      name: "Bob",
    },
    {
      name: "Catie",
    },
    {
      name: "Dan",
    }
  ];

  edit(person) {
    this.personOnEdit = person;
  }

  addPerson(personName) {
    this.listOfPeople.push({ name: personName })
  }
}

Any help is appreciated. If you need any clarifications, please post. Sorry if my response is slow, it is quite late for me and I need to wake up early tomorrow :) Thank you

philip yoo
  • 2,462
  • 5
  • 22
  • 37

1 Answers1

2

a directive like

@Directive({
  selector: "[autofocus]"
})
export class AutoFocusDirective {
  constructor(public elementRef: ElementRef) {}

  ngOnInit() {
    setTimeout(() => {
      this.elementRef.nativeElement.focus();
    });
  }
}

In a

<div *ngFor="let item of items">
  <input autofocus>
</div>
<button (click)="items.push(1)">add</button>

See stackblitz Must be work

Eliseo
  • 50,109
  • 4
  • 29
  • 67
  • I'm still getting the same behavior, not getting focus on the input field. Can you add a working plunker using this solution off of the plunker I provided? – philip yoo Oct 10 '19 at 12:36
  • 1
    https://stackblitz.com/edit/angular-f9g1yg?file=src%2Fapp%2Fapp.component.ts NOTE: you need declare the directive in your module.ts, DISCLAMER there was some errors in my answer, just updated – Eliseo Oct 10 '19 at 18:39
  • great thank you for the follow up! I have tested with my codebase and it works. One funny issue I found was that it doesn't work when including the directive in my base level app.module file. My code structure has sub modules imported into the base app.module. If I include the directive in the sub-module currently needing this directive, it works fine. But this is another issue I need to address in a separate post. For now, this solution works as intended. Thank you! – philip yoo Oct 11 '19 at 15:04
  • And for posterity.. here is an edited stackblitz (https://stackblitz.com/edit/angular-qw6a2e?file=src/app/app.component.ts) applying the directive of this answer to my previous code. Also, on my previous issue of sub-modules (unrelated to this SO question) that I mentioned just above this comment, stackoverflow.com/a/41435478/4803039 – philip yoo Oct 11 '19 at 16:47