Ejemplo n.º 1
0
    def mix(self,tipMask,preaspirateAir=False,nmix=4):
        if self.isMixed() and self.wellMixed:
            logging.notice( "mix() called for sample %s, which is already mixed"%self.name)
            return False
        logging.mixwarning("Pipette mixing of %s may introduce bubbles"%self.name)

        self.volcheck(tipMask,[self.well],0)

        blowvol=5
        mstr=""
        extraspace=blowvol+0.1
        if preaspirateAir:
            extraspace+=5
        mixvol=self.volume		  # -self.plate.unusableVolume;  # Can mix entire volume, if air is aspirated, it will just be dispensed first without making a bubble
        if self.volume>MAXVOLUME-extraspace:
            mixvol=MAXVOLUME-extraspace
            logging.mixwarning("Mix of %s limited to %.0f ul instead of full volume of %.0ful"%(self.name,mixvol,self.volume))
        well=[self.well if self.well!=None else 2**(tipMask-1)-1 ]
        mixprefillvol=5
        if mixvol<self.plate.unusableVolume-mixprefillvol:
            logging.notice("Not enough volume in sample %s (%.1f) to mix"%(self.name,self.volume))
            self.history+="(UNMIXED)"
            return False
        else:
            if preaspirateAir:
                # Aspirate some air to avoid mixing with excess volume aspirated into pipette from source in previous transfer
                self.aspirateAir(tipMask,5)
            if False:		# this results in losing mixprefillvol of sample which was not mixed; remainder has different concentration than planned
                worklist.aspirateNC(tipMask,well,self.inliquidLC,mixprefillvol,self.plate)
                self.volume-=mixprefillvol
                self.addhistory("(PRE)",-mixprefillvol,tipMask)
                worklist.mix(tipMask,well,self.mixLC,mixvol,self.plate,nmix)
                mstr="(MB)"
            elif False: # self.volume>=MINLIQUIDDETECTVOLUME:    # Another short-lived strategy
                worklist.mix(tipMask,well,self.inliquidLC,mixvol,self.plate,nmix)
                self.history+="(MLD)"
            else:
                height=self.plate.getliquidheight(self.volume)
                if height is None:
                    worklist.mix(tipMask,well,self.mixLC,mixvol,self.plate,nmix)
                    mstr="(MB)"
                else:
                    mixheight=math.floor(height-1)			# At least 1mm below liquid height
                    if mixheight<2:
                        mixheight=2
#                    print 'Vol=%.1f ul, height=%.1f mm, mix=%d, blow=%d'%(self.volume,height,mixheight,blowheight)
                    mixLC=liquidclass.LCMix[min(12,mixheight)]
                    if blowvol>0:
                        blowoutLC=liquidclass.LCBlowoutLD
                        worklist.aspirateNC(tipMask,well,self.airLC,(blowvol+0.1),self.plate)
                    if self.volume<30:
                        worklist.mix(tipMask,well,self.mixLC,mixvol,self.plate,nmix)
                        mstr="(MB)"
                    else:
                        for _ in range(nmix):
                            worklist.aspirateNC(tipMask,well,mixLC,mixvol,self.plate)
                            worklist.dispense(tipMask,well,mixLC,mixvol,self.plate)
                        mstr="(M@%d)"%(mixheight)
                    if blowvol>0:
                        worklist.dispense(tipMask,well,blowoutLC,blowvol,self.plate)
                        worklist.dispense(tipMask,well,liquidclass.LCDip,0.1,self.plate)

            self.volume-=MIXLOSS
            self.addhistory(mstr,-MIXLOSS,tipMask)
            self.lastMixed=clock.elapsed()
            self.wellMixed=True
            return True
Ejemplo n.º 2
0
    def dispense(self,tipMask,volume,src):
        self.evapcheck('dispense')
        if self.plate.curloc=='PTC':
            logging.error("Dispense to PTC!, loc=(%d,%d)"%(self.plate.grid,self.plate.pos))

        if volume<0.1:
            logging.warning("attempt to dispense only %.1f ul to %s ignored"%(volume,self.name))
            return

        if self.volume+volume < MINDEPOSITVOLUME:
            logging.warning("Dispense of %.1ful into %s results in total of %.1ful which is less than minimum deposit volume of %.1f ul"%(volume,self.name,self.volume+volume,MINDEPOSITVOLUME))

        #well=[self.well if self.well!=None else 2**(tipMask-1)-1 ]
        well=[self.well if self.well!=None else int(math.log(tipMask,2)) ]
        if self.well is None:
            logging.warning("Dispense with well is None, not sure what right logic is..., using well=%d"%well[0])

        if self.volume+volume > self.plate.maxVolume:
            logging.error("Dispense of %.1ful into %s results in total of %.1ful which is more than the maximum volume of %.1f ul"%(volume,self.name,self.volume+volume,self.plate.maxVolume))

        if self.hasBeads and self.plate.curloc=="Magnet":
            worklist.dispense(tipMask,well,self.beadsLC,volume,self.plate)
        elif self.volume>=MINLIQUIDDETECTVOLUME:
            worklist.dispense(tipMask,well,self.inliquidLC,volume,self.plate)
        elif self.volume+volume>=MINSIDEDISPENSEVOLUME:
            worklist.dispense(tipMask,well,self.bottomSideLC,volume,self.plate)
        else:
            worklist.dispense(tipMask,well,self.bottomLC,volume,self.plate)

        # Assume we're diluting the contents
        if self.conc is None and src.conc is None:
            pass
        elif src.conc is None or volume==0:
            if self.volume==0:
                self.conc=None
            else:
                self.conc=self.conc.dilute((self.volume+volume)/self.volume)
        elif self.conc is None or self.volume==0 or self.conc.final is None or src.conc.final is None:
            self.conc=src.conc.dilute((self.volume+volume)/volume)
        else:
            # Both have concentrations, they should match
            c1=self.conc.dilute((self.volume+volume)/self.volume)
            c2=src.conc.dilute((self.volume+volume)/volume)
            if abs(c1.stock/c1.final-c2.stock/c2.final)>.01:
                logging.warning("Dispense of %.1ful of %s@%.2fx into %.1ful of %s@%.2fx does not equalize concentrations"%(volume,src.name,src.conc.dilutionneeded(),self.volume,self.name,self.conc.dilutionneeded()))
                #assert abs(c1.stock/c1.final-c2.stock/c2.final)<.01
                self.conc=None
            else:
                self.conc=Concentration(c1.stock/c1.final,1.0,'x')  # Since there are multiple ingredients express concentration as x

         # Set to not mixed after second ingredient added
        if self.volume>0:
            self.lastMixed=None
            self.wellMixed=False

        if src.hasBeads and src.plate.curloc!="Magnet":
            #print "Set %s to have beads since %s does\n"%(self.name,src.name)
            self.hasBeads=True

        self.volume=self.volume+volume
        self.emptied=False
        #self.addhistory("%06x %s"%(self.getHash(w)&0xffffff,src.name),volume,tipMask)
        self.addhistory(src.name,volume,tipMask)
        self.addingredients(src,volume)
Ejemplo n.º 3
0
import worklist
import plate

#aspirate(1,"LC",[1,3,4],1,2,3,"wells")
plate1=plate.Plate("Samples",4,3,12,8)
worklist.aspirate(7,['B3','D3','E3'],"Water",[10,20,30],plate1)
worklist.aspirate(7,['B4','D4','F4'],"Water",[10,20,30],plate1)
worklist.aspirate(1,['B1'],"Water",[10],plate1)
worklist.dispense(2,['B1'],"Water",[10],plate1)
worklist.mix(2,['B1'],"Water",[10],plate1,7)
worklist.vector("ROMAVector",plate1,worklist.SAFETOEND,True,worklist.OPEN,worklist.CLOSE)
worklist.execute("python test",True,"result")
worklist.userprompt("Script done")
worklist.dump()
Ejemplo n.º 4
0
    def mix(self, tipMask, preaspirateAir=False, nmix=4):
        if self.isMixed() and self.wellMixed:
            logging.notice(
                "mix() called for sample %s, which is already mixed" %
                self.name)
            return False
        logging.mixwarning("Pipette mixing of %s may introduce bubbles" %
                           self.name)

        self.volcheck(tipMask, [self.well], 0)

        blowvol = 5
        mstr = ""
        extraspace = blowvol + 0.1
        if preaspirateAir:
            extraspace += 5
        mixvol = self.volume  # -self.plate.unusableVolume;  # Can mix entire volume, if air is aspirated, it will just be dispensed first without making a bubble
        if self.volume > MAXVOLUME - extraspace:
            mixvol = MAXVOLUME - extraspace
            logging.mixwarning(
                "Mix of %s limited to %.0f ul instead of full volume of %.0ful"
                % (self.name, mixvol, self.volume))
        well = [self.well if self.well != None else 2**(tipMask - 1) - 1]
        mixprefillvol = 5
        if mixvol < self.plate.unusableVolume - mixprefillvol:
            logging.notice("Not enough volume in sample %s (%.1f) to mix" %
                           (self.name, self.volume))
            self.history += "(UNMIXED)"
            return False
        else:
            if preaspirateAir:
                # Aspirate some air to avoid mixing with excess volume aspirated into pipette from source in previous transfer
                self.aspirateAir(tipMask, 5)
            if False:  # this results in losing mixprefillvol of sample which was not mixed; remainder has different concentration than planned
                worklist.aspirateNC(tipMask, well, self.inliquidLC,
                                    mixprefillvol, self.plate)
                self.removeVolume(mixprefillvol)
                self.addhistory("(PRE)", -mixprefillvol, tipMask)
                worklist.mix(tipMask, well, self.mixLC, mixvol, self.plate,
                             nmix)
                mstr = "(MB)"
            elif False:  # self.volume>=MINLIQUIDDETECTVOLUME:    # Another short-lived strategy
                worklist.mix(tipMask, well, self.inliquidLC, mixvol,
                             self.plate, nmix)
                self.history += "(MLD)"
            else:
                height = self.plate.getliquidheight(self.volume)
                if height is None:
                    worklist.mix(tipMask, well, self.mixLC, mixvol, self.plate,
                                 nmix)
                    mstr = "(MB)"
                else:
                    mixheight = math.floor(
                        height - 1)  # At least 1mm below liquid height
                    if mixheight < 2:
                        mixheight = 2
#                    print 'Vol=%.1f ul, height=%.1f mm, mix=%d, blow=%d'%(self.volume,height,mixheight,blowheight)
                    mixLC = liquidclass.LCMix[min(12, mixheight)]
                    if blowvol > 0:
                        blowoutLC = liquidclass.LCBlowoutLD
                        worklist.aspirateNC(tipMask, well, self.airLC,
                                            (blowvol + 0.1), self.plate)
                    if self.volume < 30:
                        worklist.mix(tipMask, well, self.mixLC, mixvol,
                                     self.plate, nmix)
                        mstr = "(MB)"
                    else:
                        for _ in range(nmix):
                            worklist.aspirateNC(tipMask, well, mixLC, mixvol,
                                                self.plate)
                            worklist.dispense(tipMask, well, mixLC, mixvol,
                                              self.plate)
                        mstr = "(M@%d)" % (mixheight)
                    if blowvol > 0:
                        worklist.dispense(tipMask, well, blowoutLC, blowvol,
                                          self.plate)
                        worklist.dispense(tipMask, well, liquidclass.LCDip,
                                          0.1, self.plate)

            self.removeVolume(MIXLOSS)
            self.addhistory(mstr, -MIXLOSS, tipMask)
            self.lastMixed = clock.elapsed()
            self.wellMixed = True
            return True
Ejemplo n.º 5
0
    def dispense(self, tipMask, volume, src):
        self.evapcheck('dispense')
        if self.plate.curloc == 'PTC':
            logging.error("Dispense to PTC!, loc=(%d,%d)" %
                          (self.plate.grid, self.plate.pos))

        if volume < 0.1:
            logging.warning("attempt to dispense only %.1f ul to %s ignored" %
                            (volume, self.name))
            return

        if self.volume + volume < MINDEPOSITVOLUME:
            logging.warning(
                "Dispense of %.1ful into %s results in total of %.1ful which is less than minimum deposit volume of %.1f ul"
                % (volume, self.name, self.volume + volume, MINDEPOSITVOLUME))

        #well=[self.well if self.well!=None else 2**(tipMask-1)-1 ]
        well = [self.well if self.well != None else int(math.log(tipMask, 2))]
        if self.well is None:
            logging.warning(
                "Dispense with well is None, not sure what right logic is..., using well=%d"
                % well[0])

        if self.volume + volume > self.plate.maxVolume:
            logging.error(
                "Dispense of %.1ful into %s results in total of %.1ful which is more than the maximum volume of %.1f ul"
                % (volume, self.name, self.volume + volume,
                   self.plate.maxVolume))

        if self.hasBeads and self.plate.curloc == "Magnet":
            worklist.dispense(tipMask, well, self.beadsLC, volume, self.plate)
        elif self.volume >= MINLIQUIDDETECTVOLUME:
            worklist.dispense(tipMask, well, self.inliquidLC, volume,
                              self.plate)
        elif self.volume + volume >= MINSIDEDISPENSEVOLUME:
            worklist.dispense(tipMask, well, self.bottomSideLC, volume,
                              self.plate)
        else:
            worklist.dispense(tipMask, well, self.bottomLC, volume, self.plate)

        # Assume we're diluting the contents
        if self.conc is None and src.conc is None:
            pass
        elif src.conc is None or volume == 0:
            if self.volume == 0:
                self.conc = None
            else:
                self.conc = self.conc.dilute(
                    (self.volume + volume) / self.volume)
        elif self.conc is None or self.volume == 0 or self.conc.final is None or src.conc.final is None:
            self.conc = src.conc.dilute((self.volume + volume) / volume)
        else:
            # Both have concentrations, they should match
            c1 = self.conc.dilute((self.volume + volume) / self.volume)
            c2 = src.conc.dilute((self.volume + volume) / volume)
            if abs(c1.stock / c1.final - c2.stock / c2.final) > .01:
                logging.warning(
                    "Dispense of %.1ful of %s@%.2fx into %.1ful of %s@%.2fx does not equalize concentrations"
                    % (volume, src.name, src.conc.dilutionneeded(),
                       self.volume, self.name, self.conc.dilutionneeded()))
                #assert abs(c1.stock/c1.final-c2.stock/c2.final)<.01
                self.conc = None
            else:
                self.conc = Concentration(
                    c1.stock / c1.final, 1.0, 'x'
                )  # Since there are multiple ingredients express concentration as x

        # Set to not mixed after second ingredient added
        if self.volume > 0:
            self.lastMixed = None
            self.wellMixed = False

        if src.hasBeads and src.plate.curloc != "Magnet":
            #print "Set %s to have beads since %s does\n"%(self.name,src.name)
            self.hasBeads = True

        self.volume = self.volume + volume
        self.emptied = False
        #self.addhistory("%06x %s"%(self.getHash(w)&0xffffff,src.name),volume,tipMask)
        self.addhistory(src.name, volume, tipMask)
        self.addingredients(src, volume)
Ejemplo n.º 6
0
import worklist
import plate

#aspirate(1,"LC",[1,3,4],1,2,3,"wells")
plate1 = plate.Plate("Samples", 4, 3, 12, 8)
worklist.aspirate(7, ['B3', 'D3', 'E3'], "Water", [10, 20, 30], plate1)
worklist.aspirate(7, ['B4', 'D4', 'F4'], "Water", [10, 20, 30], plate1)
worklist.aspirate(1, ['B1'], "Water", [10], plate1)
worklist.dispense(2, ['B1'], "Water", [10], plate1)
worklist.mix(2, ['B1'], "Water", [10], plate1, 7)
worklist.vector("ROMAVector", plate1, worklist.SAFETOEND, True, worklist.OPEN,
                worklist.CLOSE)
worklist.execute("python test", True, "result")
worklist.userprompt("Script done")
worklist.dump()