1

I have a menu item that looks like a checkbox:

enter image description here

I would like to click/not-click on it depending on the current value. How do I get the current value?

My code for accessing and clicking it looks like this:

let menuBars = application.menuBars
let outlineModeMenuItem = menuBars.menuItems["outline_mode"]
outlineModeMenuItem.click()

The element structure looks like this:

Attributes: MenuItem, {{0.0, 401.0}, {220.0, 22.0}}, identifier: 'outline_mode', title: 'Outline Mode', Disabled
Element subtree:
 →MenuItem, 0x11e14e410, {{0.0, 401.0}, {220.0, 22.0}}, identifier: 'outline_mode', title: 'Outline Mode', Disabled
Path to element:
 →Application, 0x10f10cf00, pid: 90531, title: 'Vectornator', Disabled
  ↳MenuBar, 0x11e1178a0, {{0.0, 0.0}, {1440.0, 24.0}}
   ↳MenuBarItem, 0x11ce5bad0, {{401.0, 0.0}, {50.0, 24.0}}, title: 'View'
    ↳Menu, 0x11ce5bbe0, {{401.0, 24.0}, {220.0, 682.0}}
     ↳MenuItem, 0x11e14e410, {{0.0, 401.0}, {220.0, 22.0}}, identifier: 'outline_mode', title: 'Outline Mode', Disabled

So it doesn't have any "checkbox" item above or below it. value for it is empty :/ UI reads checkbox value from UICommand.state, but that doesn't seem to be exposed on XCUIElement.

Paulius Liekis
  • 1,676
  • 3
  • 18
  • 26

3 Answers3

0

outlineModeMenuItem.isEnabled is the call you're looking for. It should return true when it is checked and false when it's not.

https://developer.apple.com/documentation/xctest/xcuielementattributes documents other attribute checks you might be interested in. I've not worked with a MenuItem before so it is possible isSelected might be what you're looking for.

Mike Collins
  • 4,108
  • 1
  • 21
  • 28
  • If this doesn't work, you may want to looking into the `setAccessibilityValue()` function, which can be modified dynamically on click. – Mike Collins Sep 14 '21 at 15:18
  • 1
    `isEnabled` tells you whether the button is enabled/disabled, i.e. greyed out or not. `isSelected` comes back as false no matter what the value is. – Paulius Liekis Sep 15 '21 at 10:28
  • 1
    For checkboxes as far as I understood `value` is the property that works, but it doesn't work for `MenuItem`. I guess I could try `setAccessibilityValue`, but that sounds like a lot of overhead as I would have to modify every use of `UICommand`... – Paulius Liekis Sep 15 '21 at 10:49
  • Bummer. I was worried the last resort was going to be the answer. Sorry I couldn’t be more help without a similar interface in front of me. And yeah, not the cleanest solution. – Mike Collins Sep 15 '21 at 14:27
  • I'm just surprised how difficult the seemingly simple things are in XCTest... – Paulius Liekis Sep 15 '21 at 20:27
  • It's definitely a immature tech, but there isn't much better :/ – Mike Collins Sep 16 '21 at 03:25
  • We used TestComplete in another company - it feels like we had way fewer issues for the problems that I'm solving. Although it's a completely different type of QA automation (i.e. it can be much more image-based). – Paulius Liekis Sep 16 '21 at 09:41
  • Yeah, that’s the only real alternative (image-based); anything similar to this is just a layer built on top of XCUITest. – Mike Collins Sep 16 '21 at 14:53
  • Turns out that there is `accessibilityValue` property on `UICommand`, but whatever value you set on it - it doesn't get retained. It doesn't even retain `accessibilityIdentifier` if I set that. I get an impression that `UICommand` properties are cloned at which point they loose all those values. I know that because I tried deriving `UICommand` class and the object "turns" from my class back to `UICommand` at some point. They definetelly didn't make it easy... – Paulius Liekis Sep 17 '21 at 07:45
0

So far everything points that it is not possible.

UICommand has accessibilityValue but it seems not to have any effect and actually loses value. This answer seems to confirm that too: https://stackoverflow.com/a/60317536/217022

The only way I found was to modify the title when you know that you're running UI tests. Or expose these values in some other way unrelated to UICommand.

Paulius Liekis
  • 1,676
  • 3
  • 18
  • 26
0

I don't know if that could be applied in your case but a hacky workaround you can use is to check the startX coordinate or the length of the MenuItem element to determine whether there is a checkmark there or not. I would not actually recommend it though because it is not very flexible and should probably be handled for all possible device widths

drunkencheetah
  • 354
  • 1
  • 8