Expand|Select|Wrap|Line Numbers
- #Boa:Dialog:TiltCalibrate
- import wx
- import Multiply
- from PMD import DefaultMultiplier
- from time import sleep
- from string import digits
- from wxdbtools import MySQLInsert, MySQLUpdate, MySQLSelect
- SlopeChan = 0
- GradeChan = 1
- DistChann = 2
- CalPhaseButtonText = ["Begin Calibration", "Calibrate Grade", "Calibrate X-Slope", "Can\'t Calibrate"]
- CalPhasePromptText = ["Set data collection vehicle in starting position:",
- "Rotate the vehicle 180 degrees (in place):",
- "Roll the vehicle forward until rear wheels are at starting position",
- "Invalid data has been received. Check PMD Setup for further information"]
- HETAP_table_sql = """CREATE TABLE `HETAP_Setup`.`setup` (
- `setupID` int(4) unsigned NOT NULL auto_increment,
- `xctSerNum` varchar(45) NOT NULL default '',
- `xAxisSensitivity` decimal(5,3) default NULL,
- `yAxisSensitivity` decimal(5,3) default NULL,
- `xAxisOffset` decimal(7,6) default NULL,
- `yAxisOffset` decimal(7,6) default NULL,
- `zAxisSensitivity` decimal(7,6) default NULL,
- PRIMARY KEY (`setupID`)
- ) ENGINE=InnoDB DEFAULT CHARSET=latin1;"""
- def create(parent):
- return TiltCalibrate(parent)
- [wxID_TILTCALIBRATE, wxID_TILTCALIBRATECALIBRATEBUTTON,
- wxID_TILTCALIBRATECANCELBUTTON, wxID_TILTCALIBRATEDONEBUTTON,
- wxID_TILTCALIBRATEGRADEOFFSETTEXTCTRL, wxID_TILTCALIBRATEGRADESENSETEXTCTRL,
- wxID_TILTCALIBRATEGRADETEXTCTRL, wxID_TILTCALIBRATESERNUMCOMBOBOX,
- wxID_TILTCALIBRATESLOPEOFFSETTEXTCTRL, wxID_TILTCALIBRATESLOPESENSETEXTCTRL,
- wxID_TILTCALIBRATESLOPETEXTCTRL, wxID_TILTCALIBRATESTATICBITMAP1,
- wxID_TILTCALIBRATESTATICTEXT1, wxID_TILTCALIBRATESTATICTEXT2,
- wxID_TILTCALIBRATESTATICTEXT3, wxID_TILTCALIBRATESTATICTEXT4,
- wxID_TILTCALIBRATESTATICTEXT5, wxID_TILTCALIBRATESTATICTEXT6,
- wxID_TILTCALIBRATESTATICTEXT7, wxID_TILTCALIBRATESTATICTEXT8,
- wxID_TILTCALIBRATESTATICTEXT9,
- ] = [wx.NewId() for _init_ctrls in range(21)]
- class TiltCalibrate(wx.Dialog):
- def _init_ctrls(self, prnt):
- # generated method, don't edit
- # instantiate widgets
- def __init__(self, parent):
- self._init_ctrls(parent)
- self.publisher = self.Subscribe(parent)
- ## self.widgetList = [self.gradeSenseTextCtrl, self.slopeSenseTextCtrl,
- ## ]
- self.dbServer = parent.GetDBServer()
- self.CheckDatabase()
- self.calibPhase = 0
- self.bitmapList = []
- self.GetCalibBitmaps()
- self.staticBitmap1.SetBitmap(self.bitmapList[0])
- self.FillFromDB()
- self.SetupMultipliers()
- def CheckDatabase(self):
- dbServer = self.dbServer
- if not dbServer.DBExists("HETAP_Setup".lower()):
- dbServer.Execute("CREATE DATABASE HETAP_Setup")
- dbServer.Execute(HETAP_table_sql)
- self.db_is_new = True # probably don't need this flag
- else:
- self.db_is_new = False
- print "db_is_new = ", self.db_is_new
- def FillFromDB(self):
- varList = []
- cursor = self.dbServer.Execute("SELECT * FROM `HETAP_Setup`.`setup`")
- if cursor.rowcount:
- rows = cursor.fetchall()
- for i in range(4):
- try:
- varList.append(float(rows[0][i+2]))
- except TypeError:
- varList.append(0)
- for row in rows:
- self.sernumComboBox.Append(row[1])
- self.gradeSense = varList[0]/1000 or Multiply.DefaultTiltSense
- self.slopeSense = varList[1]/1000 or Multiply.DefaultTiltSense
- self.gradeOffset = varList[2] or Multiply.DefaultOffset
- self.slopeOffset = varList[3] or Multiply.DefaultOffset
- self.ShowOffsets()
- def Subscribe(self, dataSource):
- publisher = dataSource.GetPublisher()
- publisher.RegisterClientCallback(self.Update)
- return publisher
- def SetupMultipliers(self):
- ## Create multipliers and submit them to the publisher
- self.gradeMultiplier = gm = Multiply.CrossbowMultiplier(GradeChan, self.gradeOffset, self.gradeSense)
- self.slopeMultiplier = sm = Multiply.CrossbowMultiplier(SlopeChan, self.slopeOffset, self.slopeSense)
- self.SubmitMultipliers(gm, sm)
- def SubmitMultipliers(self, gradeMult, slopeMult):
- self.publisher.SetMultiplier(gradeMult)
- self.publisher.SetMultiplier(slopeMult)
- def ResetMultipliers(self):
- gradeMult = DefaultMultiplier(0)
- slopeMult = DefaultMultiplier(1)
- self.SubmitMultipliers(gradeMult, slopeMult)
- self.staticText3.SetLabel("Old calibration data is being reset")
- sleep(2)
- def Update(self, dataList):
- i = self.calibPhase
- try:
- # Publisher sent valid data to us
- self.grade = grade = dataList[GradeChan]
- self.slope = slope = dataList[SlopeChan]
- if i == 3: # From waiting to begin phase
- self.calibPhase = 0
- self.SetWidgetText()
- except TypeError:
- # Publisher can't get valid data
- if i == 3:
- return
- self.slope = slope = 0
- self.grade = grade = 0
- self.calibPhase = 3 # Set phase to waiting
- self.SetWidgetText()
- # Upadate calibration display regardless
- self.gradeTextCtrl.SetValue("%.1f %%" %grade)
- self.slopeTextCtrl.SetValue("%.1f %%" %slope)
- def GetCalibBitmaps(self):
- for i in range(4):
- filename = "calib%d.bmp" %i
- bitmap = wx.Bitmap(filename, wx.BITMAP_TYPE_BMP)
- self.bitmapList.append(bitmap)
- def SetWidgetText(self):
- """Caller must ensure calibration phase is set correctly."""
- i = self.calibPhase
- buttonText = CalPhaseButtonText[i]
- staticText = CalPhasePromptText[i]
- self.CalibrateButton.SetLabel(buttonText)
- self.staticText3.SetLabel(staticText)
- self.staticBitmap1.SetBitmap(self.bitmapList[i])
- def NextPhase(self, i):
- i += 1
- self.calibPhase = i * bool(i % 3)
- def PostWarning(self, msg):
- wx.MessageBox(msg, "Error", wx.OK|wx.ICON_EXCLAMATION, self)
- def ShowOffsets(self):
- self.gradeOffsetTextCtrl.SetValue("%.3f V" %self.gradeOffset)
- self.slopeOffsetTextCtrl.SetValue("%.3f V" %self.slopeOffset)
- def OnCalibrateButton(self, event):
- i = self.calibPhase
- self.NextPhase(i)
- resultList = self.publisher.GetRawData()
- if i == 3:
- return
- if i == 0:
- self.p0Grade = resultList[GradeChan]
- self.p0Slope = resultList[SlopeChan]
- elif i == 1:
- p1Grade = resultList[GradeChan]
- self.gradeOffset = gradeOffset = (self.p0Grade + p1Grade) / 2.0
- # print self.p0Grade, p1Grade, gradeOffset
- self.gradeMultiplier.InitMultiplier(gradeOffset, self.gradeSense)
- elif i == 2:
- p1Slope = resultList[SlopeChan]
- self.slopeOffset = slopeOffset = (self.p0Slope + p1Slope) / 2.0
- # print self.p0Slope, p1Slope, slopeOffset
- self.slopeMultiplier.InitMultiplier(slopeOffset, self.slopeSense)
- self.SetWidgetText()
- self.ShowOffsets()
- def OnTextCtrlChar(self, event):
- event.Skip()
- def OnDoneButton(self, event):
- sernum = self.sernumComboBox.GetValue()
- if not sernum:
- self.PostWarning("Serial Number field is blank")
- return
- try:
- gradeSense = float(self.gradeSenseTextCtrl.GetValue())
- except ValueError:
- self.PostWarning("X (Grade) sensitivity field has a bad value in it")
- return
- try:
- slopeSense = float(self.slopeSenseTextCtrl.GetValue())
- except ValueError:
- self.PostWarning("Y (X-Slope) sensitivity field has a bad value in it")
- return
- query = MySQLSelect("`HETAP_Setup`.`setup`", xctSerNum=sernum)
- cursor = self.dbServer.Execute(query)
- nRows = cursor.rowcount
- if nRows:
- query = MySQLUpdate("`HETAP_Setup`.`setup`", dict(xAxisSensitivity=gradeSense,
- yAxisSensitivity=slopeSense, xAxisOffset=self.gradeOffset,
- yAxisOffset=self.slopeOffset), {}, xctSerNum=sernum)
- else:
- query = MySQLInsert("`HETAP_Setup`.`setup`", {}, xctSerNum=sernum,
- xAxisSensitivity=gradeSense, yAxisSensitivity=slopeSense,
- xAxisOffset=self.gradeOffset, yAxisOffset=self.slopeOffset)
- self.dbServer.Execute(query)
- self.Hide()
- def OnCancelButton(self, event):
- self.Hide()