Programmatically Connect to Serial Devices with Player Triggers

I like to use the Player (Serial Only) driver a lot. It’s my preferred way of connecting to devices like Zebra printers, as all your message configuration is done in the App Editor - no need to switch between App, App Editor, and Device Configuration to make code changes!

But a common issue here is that the driver needs to reference a COM port - the PC’s internal reference for the specific USB port plugged into the device. If the device is moved, plugged into a different port on my PC - even if it’s the same type of port - the COM number will be different, and my app will no longer work.

With the newly-added ARRAY_INDEX_OF() function, I’m now able to determine this port programmatically and remove this “it must always be this port” dependency from my app.
(If you’re familiar with Excel, this method will look similar to index-match)

In the App Editor:

The List Ports function displays a list of objects in a Tulip App. Normally, I manually read this list and hard-code a port (here, COM3) into my subsequent serial triggers:

If I know what number row (what index) my printer connection is on, I can pull the correct COM port regardless of what it may have changed to.

I know the manufacturer “FTDI” is going to be unique enough to reliably find this device at this PC, so I’ll use that as my search term. However, to search I need to create a single-width list of that column “manufacturer”…

Store expression MAP_TO_TEXT_LIST(@Variable.ports, 'manufacturer') in variable “All Manufacturers List”

“All Manufacturers List” now has the value ['FTDI', '']

Then, I search through this list for the item in question:
Store expression ARRAY_INDEX_OF(@Variable.All Manufacturers List, 'FTDI') in variable “Target Port Index”

“Target Port Index” now has the value 0, indicating the first row in my table.
All that’s left is to pull the COM info from the row I just found:

Get from Index in Array, with:

  • Array >> “ports”
  • Index >> Variable >> “Target Port Index”

Store in Variable >> “COM Port Row”

“COM Port Row” is now an object with values:

COM Port Row: { "path": "COM3", "manufacturer": "FTDI", "serialnumber":"A9XE70R4", ... }

I can now reference COM Port Row.path in any future triggers (like a Connect or Send function)! I recommend putting this flow to run “At App Start”, so every time your user starts the app Tulip will search through all available COM ports and select the one relevant to your device.

Hope this helps!

1 Like