Skip to content

Keyed <input> loses focus when earlier sibling is removed #660

Description

@SkaterDad

I've noticed some unexpected behavior with keyed children, particularly <input>.

Removing a sibling before the currently focused input causes it to lose focus. Removing a sibling after the input is okay.

For example, removing the <span> or one of the <input> in this mock dynamic form:

<div>
  { state.visible ? <span key={"theSpan"}>I might disappear</span> : null }
  { state.inputs.map(inputName => (
      <input
          key={name}
          oninput={ (event) => action.mightRemoveAnInputOrTheSpan(event.target.value)}
      />
    )
  }
</div>

An element.insertBefore call is being made for every keyed child beyond the removed one, which is likely when focus is lost. In this case, it is also an unecessary perf hit, since a single removeElement operation could have been performed instead.

          if (oldKey === newKey) {
            patch(element, keyedNode[0], keyedNode[1], children[k], isSvg)
            i++
          } else if (keyedNode[0]) {
            patch(
              element,
              element.insertBefore(keyedNode[0], oldElements[i]), // <--- THIS
              keyedNode[1],
              children[k],
              isSvg
            )

@jorgebucaran Is this an issue that will be resolved with the diffing re-write you've talked about? It seems like this could be solved by determining which keyed items are being added & removed before doing any DOM operations?

Reproduction (with instructions): https://codepen.io/SkaterDad/pen/jzLbBX

Similar demo in React which seems fine: https://codesandbox.io/s/z68rm906jx

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions