Skip to main content

Element Interaction

Interacting with elements is something you'd do in every test. ZWL provides easy to use functions and an extensive documentation to help you explorer every possible feature and functionality.

There are mainly two groups of APIs for interacting with elements:

  • The first group provide functions of type 'do what I mean'

    Functions in this group are made for specific and predefined tasks such as 'typing into text field', 'sending keys to page', uploading file etc. A task can be made of multiple internally handled smaller tasks. All edge cases in these tasks are handled so that you get the expected result. This group of APIs don't have specific name but to separate it from the other one we will call it non-action API.

  • The second group provide functions of type 'do as I say'

    Functions in this group are made for composing custom tasks such as 'hover over menu item, hold for a second and move out', 'click, hold and move pointer for X pixels and release' etc. There are no hidden or behind the scene tasks. Only the specified actions are performed, and in the same order they are mentioned. These are helpful for specific pointer and keyboard device related interactions involving series of defined actions. These group of APIs are specifically called Action Api.

Which one should I use?: Depends on what you're trying to accomplish. Action Api must only be used when there is no equivalent function available in non-action API or if there is a requirement of doing series of mouse and/or keyboard device actions.

NON-ACTION API#


Clicking and double clicking on elements#

click(elemId) # clicks on given element
clickAll(elemId, elemId, ...) # clicks on all of the given elements
clickSwitchNew(elemId)# if a link is clicked, browser moves the focus to the window/tab but# to run further commands on new url, webdriver has to be switched. This# function does that automatically.
clickNoSwitch(elemId)# emulates right click. If a link is clicked and browser moves focus to# new tab, this will bring focus to original tab.
dblClick(elemId) # clicks on element twice

Clear element#

clear(elemId)
clearAll(elemId, elemId, ...)
clearActive() # clears the focused element

Typing into text type fields#

ZWL has specific functions for typing text into text type fields because it works differently than sending keyboard keys to other elements like document, body or non text type field element. We strongly suggest you use only the designated functions for a particular use to avoid any surprises. ZWL has made sure your key inputs yields the expected results no matter which element on page you want to give input.

type(elemId, keys/string, keys/string, ...)# type given keys or string data into given text type field
typeActive(keys/string, keys/string, ...) # type into focused text type field
typeIntoElements(string, elemId, elemId, ...) # type the same data into multiple text type fields

The element passed to type functions should be a text type field such as input[type='text'], textarea or contentEditable elements.

The keys or string passed allows following:

  • string data can include any unicode character such as 'This is going be a 💥'.
  • Any modifier or non printable keys (such as Ctrl, Cmd, Shift, Enter) can be given from keys constant. All values in this constant are auto suggested when you press keys. in IDE.
  • When a modifier key is given, it will remain depressed until all non modifier keys have been printed to text field. If you want to release a modifier key in between (such as doing Ctrl + Enter to switch to next line and releasing Ctrl), pass keys.null which will release all depressed modifier keys.
  • Values in keys constant is of type string. You can even concatenate them with any other string data to make a single string. For example to use in typeIntoElements that accepts only one argument for the data.

Example,

type(  findElement('description', by.name),  'This starts a new ticket for fixing most',  keys.enter,  'designs of the site',  keys.shift,  ' to increase conversion',  keys.tab)

Testing keyboard shortcuts#

Many applications allow users to trigger actions using keyboard shortcuts. If you need to test keyboard shortcuts on your application, use functions:

sendKeysToPage(elemId, keys, keys, ...)
sendKeysToPageF(keys, keys, ...)
  • sendKeysToPage require you to provide an element on page so that the element can be first clicked to get a focus on the page before keys can be sent to it. The element must be a static, visible element with no js attached to it so that clicking doesn't trigger any event (such as main or header). Note that body element shouldn't be given as certain browser drivers (webdriver) can't use it for clicking being it's size is 0.

  • If you know that the page is focused sendKeysToPageF can be used that doesn't require an element.

  • Modifier and non modifier keys can be sent together.

Example:

sendKeysToPage(findElement('main', by.role), keys.shift, 'G') # will send Shift + G to page

Drag-drop#

Utility methods created using Action API.

dragAndDrop(firstElemId, secondElemId) # drags first element over second
dragAndDrop(elemId, x, y) # drags element to an offset of x, y

Scrolling#

Utility methods created using Action API.

scroll(elemId) # scroll to element
scroll(elemId, x, y) # scroll to an offset from element
scroll(x, y) # scroll to an offset from current position

Uploading a file from test#

Works for only input[type='file'] elements. Since all Outomated tests runs in a VM, the file to be uploaded from a test need to be stored in the VM locally so that it can be picked from the local file system (just like manual file uploading work in a web page). For this reason, you first need to upload some files using IDE's Upload Test Files screen before you can use their names in tests. See below:

setFile(elemId, fileName)
setFiles(elemId, fileName, fileName, ...)

The fileName parameter must be the exact name of a file you've previously uploaded from IDE. If you use setFiles function, the element must be a input[type='file'] with multiple attribute and all files given must have already been uploaded from IDE.

You can view and manage all your uploaded files from IDE's Upload Test Files screen as well.

See Api Reference for all available functions in non-action API.

ACTION API#


As we discussed in the beginning of this part of documentation, Action API is used for composing custom actions and actions that aren't defined in non-action API. Let's begin with an example to get an overview:

The dragAndDrop(elemId, x, y) function we just saw is created using following sequence of action functions:

performAction(  move(elemId),  hold(),  move(x, y),  release())

The performAction function takes a series of action functions in arguments and executes them in the given order. The sequence of the previous snippet is straight forward and concise. Move the pointer to the element that has to be dragged, hold element using the pointing device, move to the desired offset, release the element. This will perform a drag and drop operation.

Similar to this, any type of sequences can be created using the built-in action functions and they will be executed exactly in the same way as defined.

performAction#

The performAction(...args) function executes a series of action functions provided as arguments. It just executes whatever sequences are given. It is the responsibility of caller to make sure that the sequence is suitable to run in the given order and will perform the desired operation.

action functions#

Functions that are used to compose an operation and are given as arguments to performAction. These functions don't do anything on their own unless passed into performAction. They just provide information about their intended action and any arguments to performAction. Action functions are of following types:

  • Keyboard device related#

    Action functions that use keyboard device. The following action types define these functions:

    • Focusing: Before sending keyboard actions to an element, it has to be focused. Use function focus(elemId) before using any other keyboard related action functions. If this is not done, other keyboard action functions will have no target.

    • Pressing and releasing modifier keys: ZWL defines all possible action functions for modifier keys that you may require. They are: shiftDown(), shiftUp(), ctrlDown(), ctrlUp(), cmdDown(), cmdUp(), cmdCtrlDown(), cmdCtrlUp, altDown(), altUp(). Use them in sequences to press or release a modifier key whenever you want.

      Note that if you don't need to release some depressed modifier keys within the sequence, just leave them depressed. All of them will be automatically released once the action is performed.

    • Sending non modifier keys: Use function sendKeys(stringData, stringData, ...) for sending only non modifier keys to the focused element. Don't use this for sending modifier keys and use only the dedicated function described in Pressing and releasing modifier keys because modifier keys will be pressed and released just like non modifier keys with this action function, therefor leaving no effect.

  • Pointing device related#

    Action functions that use pointing device such as mouse. The following action types define these functions:

    • Moving: Before doing any pointing actions on an element (such as dragging, hovering), the pointer first has to be moved onto the element. Use one of the following functions before using any other pointer related action functions:

      • move(elemId): Moves pointer to the center of an element.
      • move(elemId, x, y): Moves pointer to an offset from element’s center.
      • move(x, y): Moves pointer to an offset from current position.
    • Hold & Release: To hold the element (for example to drag) and release it, use functions hold() and release() respectively.

    • Clicking: To click, double click and right click on the element, use functions clickOnce() (note the suffix 'Once'), doubleClick() and contextClick() respectively.

  • Utility#

    These action functions are for general use and apply to all device types.

    • pause(milliseconds): Can be used to pause action execution for a given time. For instance, an example action sequence could move a mouse to a menu item and wait for 50 milliseconds before moving again.

Examples#

Hopefully you get a good knowledge for composing action sequences. It's doesn't just look easy but it's easy to use as well. Look at following use cases:

# A file viewer element shows a 'detail' link on hover. We want to click on that link# to view file details.# To do that, move mouse onto the element and wait for sometime before finding the# detail link and clicking on it.fileViewer = findElement('fileViewer', by.testId)performAction(  move(fileViewer),  pause(20))linkDetail = findElementFromElement(fileViewer, 'detail', by.text)click(linkDetail)
# An application shows some additional menu on Shift + Ctrl. When we move pointer# over the additional menu, it expands a list. We will then move pointer to a desired# option before clicking on it.performAction(  focus(findElement('main', by.role)),  shiftDown(),  ctrlDown(),  move(findElement('fileMenu', by.testId)),  move(findElement('Delete Unused Files', by.text)),  clickOnce())
note

performAction can process function arguments defined only in action functions. No other function should be given to it.

See Api Reference for a grater detail to all functions in Action API.