Finding the Field Editor in UI Tests

On macOS, the field editor is a NSText instance that appears whenever you edit a NSTextField. This means the text fields themselves offer no editing features; they just tell the shared field editor to appear in their drawing area and show their content.

When you write XCUITests, you may want to edit cells in a table or fill out a form with many text fields. Today I learned that you don't get to the field editor in UI tests and send it the typeText message. You work with the text fields like the user does: as if they themselves accepted user input.

So there's no reason to filter XCUIApplication().textViews and search for the field editor. Stick to textFields.element(matching: NSPredicate(format: "hasKeyboardFocus == true")) and you're good. Note that it's not hasFocus. The XCUIElementAttributes doc seems to suggest the element objects don't respond to much more than what's listed here, but that's not the case.

let fieldEditor = XCUIApplication()
    .textFields
    .element(matching: 
        NSPredicate(format: "hasKeyboardFocus == true"))

I found this especially puzzling when editing NSTableCellView contents. Then again, the cell labels are NSTextFields, but with all the drawing attributes of a label. Think different.

TL;DR: There's no point in searching for the field editor. All XCUIElementSnapshot objects that you can get to will not respond to NSText.isFieldEditor anyway. Just look for a text field that has focus.

Browse the blog archive