Tip Handling for Widely Varying Volumes

Wondering if anyone has a good solution for this problem:

I’m trying to create a universal, one-size-fits-all solution to cherry picking using incoming worklists for plate mapping and transfer volumes. The issue that keeps coming up is the huge range of transfer volume that we can expect (anywhere from 1 uL to ~800 uL, essentially the full range of a STAR channel pipette). The difficulty is programming the robot to pick up appropriately sized tips for each transfer; what I’ve done so far is:

  1. sort the worklist based on volume
  2. get the next 8 transfer volumes and add them to an array
  3. read through the array, and if all 8 of the volumes are less than 50 uL or more than 300 uL, use exclusively 50 or 1000 uL tips
  4. for a sequence of 8 where some of the volumes are greater than 300, the system defaults to just using 1000 tips. This hasn’t been much of an issue, as the pipetting accuracy for the 1000 uL tips is relatively equal to the 300’s
  5. for a sequence of 8 where some of the volumes are less than 50 and some are greater, I’ve defaulted to using 300’s, but this is the issue, as the pipetting accuracy of the 50’s is much greater than the 300’s for small volumes
  6. the real tricky bit is when even when sorted, the worklist has a small transfer (<50 uL) followed by a larger transfer (>300 uL). The system defaults to 1000’s for this, greatly reducing the pipetting accuracy of the small transfer.

So really the challenge is how to best handle when a series of volumes from 1 uL to ~800 uL comes up with respect to tips. I’ve thought of having the array loop through with a loop break and handle the small transfers with however many 50 uL tips are needed, then handle the larger ones with 300 uL or 1000 uL tips, but I’m wondering if there’s a better way anyone has come up with. Has anyone played around with using firmware commands to run an 8 channel pipetting sequence with different tips on each channel?


1 Like

Hello @LordNorm,

You can pick up different tip sizes on different channels without Firmware Commands. You would need one Tip Pickup per tip type and use a variable Channel Pattern (one per tip type). Once you have those tips, you can use a single Aspirate and Dispense command to perform the pipetting with all channels regardless of tip type. You would just need to pass in the Liquid Class and volumes as arrays, making sure you match the Liquid Class and volume to the tip picked up on each channel.

Here’s a basic example:

Please let me know if I misunderstood your end goal.



Ah! that’s awesome! The biggest obstacle for me was the liquid class definitions, I didn’t know liquid classes could be passed in as an indexed location in an array. This is very helpful, thanks so much!


I agree. When I have done it in the past, I do it the way that @WilliamCham_Hamilton says here. Works well!

1 Like

Indeed, William beat me to the answer! I built something to do exactly this a while back using different tip sizes on different channels. I combined everything into a sub-method library just to make my life easier.

1 Like

If your goal is to get this done in the fastest manner possible and limit the back and forth between tip racks I would sort and group by volume. This will allow the machine to deal with one tip size at a time and eliminate the pickup of multiple tip types simultaneously. Something to consider.

In my experience the 300ul Hamilton tips are typically good down to 10ul. Of course your mileage will vary depending on other factors but <2% CV/R at 10ul is pretty typical when pipetting aqueous solutions with the correct liquid class setup.

Hope this helps!


I would also rather recommend to virtually group and sort by volumes to keep it simple

1 Like

This is awesome. I didn’t know this is possible.

1 Like

Another things which i do is when you are creating sequences you can create different seuqences based on Volume and then pass it accordingly.


This a nice trick William. I recently had to do the same thing but I ended up grouping the asp/disp per tip type. Not as elegant as yours here. But I know what to do next time.
Thanks for sharing the trick.

One question, would this work with smart steps? In my case, I used the smart steps because the volumes might be larger than 1mL in some cases and I just didnt want to deal with calculating volumes per asp/disp.

Hello @Starrif2263,

Smart Steps take away a degree of control and flexibility in order to add convenience (such as not having to perform calculations). They therefore have to apply certain restrictions and make assumptions. In the case of “1000ul Channel Pipette - Simple (1-1)” for example, I can see that the liquid class input is limited to a single value from the list and cannot be set as an array, making my approach unusable with Smart Steps.


1 Like

Thanks Wiliam, that makes sense.
Question about the strategy you gave, i noticed that your arrays have [1] for referencing the elements, i have used the [] many time, but i am not familiar with [*1], how does that access the array index? What is the difference between [1] and []?

@Starrif2263 - In VENUS using the ‘*’ character in reference to an array element(s) denotes the use of multiple array indices as opposed to a single index. This is only supported as default in select commands.


This is especially useful for many parameters supported by the ML_STAR 1000uL Channel Aspiration and Dispense commands, as while these commands may only consist of a single line of your method, these commands are in fact parameterizing individual plunger/motor/liquid handling behaviors of all the 1mL channels activated by your channel pattern at the same time. By using arrays as inputs for supported parameters, you can specify individual values on a channel by channel basis.

When specifying to use multiple array elements for a pipetting parameter, the element indices will match the channel indices when assigning values to a channel. If your size of your array inputs match the number of channels on your system, then you can simply check ‘Automatic array index selection’ and VENUS will automatically assign the array elements to the corresponding channels. If your array sizes are greater than the number of channels, then you need to tell VENUS which index to start at.

When using a variable as an input, or a single array element, that value will be assigned to all channels in the command.

The following parameters support individual channel value assignment via arrays:

Volume (flt)
Aspiration/dispense mode (int)
Liquid class (str)
Liquid following (bln)
Mix cycles (int)
Additional mix position (flt)
Mix volume (flt)

If using cLLD OR pLLD:
Sensitivity (int)
Submerge depth (flt)

If using cLLD AND pLLD :
Above two parameters
Max height difference (flt)

If using fixed height:
Fixed height (flt)
Retract height (flt)

If using touch off:
Touch off height (flt)
Asp position above touch (flt)


Just to further clarify:

  • [1] denotes a single array element
  • [*] denotes multiple array elements where the size of the array is the same as the reference data/component (e.g. number of channels)
  • [*1] denotes multiple array elements beginning at index 1 (in many cases in VENUS, arrays start at 1 instead of 0 - see Help file to know when that is the case, but generally an index only starts at 0 when using HSL)

So that [*1] could have easily been [*9] indicating to use sequential array contents beginning at index 9.



@NickHealy_Hamilton, these are incredibles tips. My mind just exploded at the possibilities they create in programming any method. Thanks a bunch guys!!!
@WilliamCham_Hamilton and @EricSindelar_Hamilton this forum is amazing!!!

Follow up question. In VoV, I have noticed that that some parameters like gripper pick height or opening width do not accept variables. I am running Instinct 1.9 with VoV. Is that a limitation of instinct 1.9 or am I not setting the parameters correctly.


@Starrif2263 - No problem, genuinely happy to help!

Regarding track gripper and entry exit module VoV commands, those parameters do in fact accept variables, though it isn’t initially obvious. For parameters that do not support dropdowns containing available variable names for compatible types, you can actually type in the name of an existing variable, instead of hardcoding the value.

For some parameters, there may be a character limit for the name of the variable you pass in, due to the size of the parameter box.