예제 #1
0
class SlotViewWindow(QtGui.QMainWindow):
    """Main application window."""
    def __init__(self, struct, pid, tflux, cflux, ratio, time, phottype, sleep,
                 tx, ty, cx, cy, r, br1, br2, naxis1, naxis2, sigdet, contpix,
                 driftlimit):
        """Default constructor."""
        maxcolumn = 7
        self.struct = struct
        self.infile = struct._HDUList__file.name
        self.name = self.struct[0].header['OBJECT']
        self.pid = pid
        self.dtime = time.copy()
        self.tflux = tflux
        self.cflux = cflux
        self.ratio = ratio
        self.min_xlim = 10
        self.radius = r['comparison']
        self.r = r
        self.br1 = br1
        self.br2 = br2
        self.tx = tx
        self.ty = ty
        self.cx = cx
        self.cy = cy
        self.phottype = phottype
        self.naxis1 = naxis1
        self.naxis2 = naxis2
        self.sigdet = sigdet
        self.contpix = contpix
        self.driftlimit = driftlimit
        self.niter = 5
        self.sigback = 5
        self.fft = False
        self.stopplay = False
        self.sleep = sleep
        self.zbox = []
        self.npoint = 4
        self.id = 0
        self.nframes = len(self.struct)
        self.header = self.struct[int(self.pid[self.id])].header
        self.goodframes = self.dtime * 0 + 1
        if self.phottype == 'circular': self.npoint = 24

        # Setup widget
        QtGui.QMainWindow.__init__(self)

        # Set main widget
        self.main = QtGui.QWidget(self)

        # Set window title
        self.setWindowTitle("SlotView %s" % self.infile)

        #set up the different pages
        self.slotPage = QtGui.QWidget()

        #set up the differen panels
        self.set_optionpanel()
        self.set_imagepanel()
        self.set_controlpanel()
        self.set_plotpanel()
        self.set_infopanel()

        # Set up the layout
        slotLayout = QtGui.QVBoxLayout(self.slotPage)
        slotLayout.addWidget(self.plotpanel)
        slotLayout.addWidget(self.optipanel)
        slotLayout.addWidget(self.imdisplay)
        slotLayout.addWidget(self.contpanel)
        slotLayout.addWidget(self.infopanel)

        #create the tabs
        #self.tabWidget=QtGui.QTabWidget()
        #self.tabWidget.addTab(self.slotPage, 'Slot')

        #layout the widgets
        mainLayout = QtGui.QVBoxLayout(self.main)
        mainLayout.addWidget(self.slotPage)
        #mainLayout.addWidget(self.tabWidget)
        #self.setLayout(mainLayout)

        # Set focus to main widget
        self.main.setFocus()

        # Set the main widget as the central widget
        self.setCentralWidget(self.main)

        # Destroy widget on close
        self.setAttribute(QtCore.Qt.WA_DeleteOnClose)

        # Close when config dialog is closed
        self.connect(self.main, QtCore.SIGNAL('keyPressEvent'),
                     self.keyPressEvent)
        #self.connect(self.conf, QtCore.SIGNAL('destroyed()'), self, QtCore.SLOT('close()'))
        #self.connect(self.tabWidget, QtCore.SIGNAL('currentChanged(int)'), self.currentChanged)
        #self.connect(self.imagePage, QtCore.SIGNAL('regionChange(int,int)'), self.regionChange)
        #self.connect(self.imagePage, QtCore.SIGNAL('runauto(int, int, int)'), self.runauto)

    def keyPressEvent(self, event):
        #print "Key Pressed:", event.key()
        self.keyEvents(str(event.text()))

    def keyEvents(self, key, x=None, y=None):
        if key == '?':
            self.help()
        if key == 'q':
            self.close()
        if key == 'd':
            self.goodframes[self.id] = 0
            self.updatepage()
        if key == 'u':
            self.goodframes[self.id] = 1
        if key == 'p':
            self.redophot(self.id)
            self.updatedataplot()
        if key == 'P':
            self.thread = QtCore.QThread()
            self.thread.run = self.newphot
            self.thread.start()
        if key == 't' and x is not None and y is not None:
            tr = self.radius
            imarr = self.struct[int(self.pid[self.id])].data
            timage, tx, ty = st.calcdrift(imarr, x, y, tr, self.naxis1,
                                          self.naxis2)
            if tx >= 0 and ty >= 0:
                self.tx[self.id] = tx
                self.ty[self.id] = ty
            self.updatepage()
        if key == 'c' and x is not None and y is not None:
            r = self.radius
            imarr = self.struct[int(self.pid[self.id])].data
            cimage, cx, cy = st.calcdrift(imarr, x, y, r, self.naxis1,
                                          self.naxis2)
            if cx >= 0 and cy >= 0:
                self.cx[self.id] = cx
                self.cy[self.id] = cy
            self.updatepage()

    def onKeyPress(self, event):
        self.keyEvents(event.key, event.xdata, event.ydata)

    def onButtonPress(self, event):
        if event.button == 2:
            self.lcpickframe(event)

    def currentChanged(self, event):
        #print event
        pass

    def redophot(self, i):
        """Redo the photometry for a single frame"""
        self.id = i
        x = {}
        y = {}
        x['target'] = self.tx[self.id]
        y['target'] = self.ty[self.id]
        x['comparison'] = self.cx[self.id]
        y['comparison'] = self.cy[self.id]
        image = self.struct[int(self.pid[self.id])].data

        #these will need to be changed
        gain = 1
        rdnoise = 1
        verbose = False

        try:
            tflux, tflux_err, cflux, cflux_err, ratio, ratio_err = \
                st.dophot(self. phottype, image, x, y, self.r, self.br1, self.br2,  \
                gain, rdnoise, self.naxis1, self.naxis2)
        except:
            msg = "SLOTVIEW--ERROR:  Could not measure photometry in frame %i" % i
            raise SaltError(msg)

        self.tflux[self.id] = tflux
        self.cflux[self.id] = cflux
        self.ratio[self.id] = ratio

    def newphot(self):
        self.redophot(self.id)
        i = self.id + 1
        self.stopplay = True
        while i < self.nframes - 1 and self.stopplay:
            self.id = i
            imarr = self.struct[int(self.pid[self.id])].data
            carray, fx,fy = st.finddrift(imarr, self.cx[self.id-1], self.cy[self.id-1], self.radius,  \
                 self.naxis1, self.naxis2, self.sigdet, self.contpix, self.sigback, self.driftlimit, self.niter)
            if 0 <= fx < self.naxis1 and 0 <= fy < self.naxis2:
                dx = self.cx[i - 1] - fx
                dy = self.cy[i - 1] - fy
                self.cx[i] = fx
                self.cy[i] = fy
                self.tx[i] = self.tx[i - 1] - dx
                self.ty[i] = self.ty[i - 1] - dy
            self.redophot(i)
            i = i + 1
        print 'Stopped at', i
        self.updatepage()

    def changefluxplot(self, event):
        self.fluxplot = event
        self.updatedataplot(save_zoom=False)

    def changetstarplot(self, event):
        self.tstarplot = event
        self.updatedataplot(save_zoom=False)

    def changecstarplot(self, event):
        self.cstarplot = event
        self.updatedataplot(save_zoom=False)

    def plotlightcurve(self):
        """Plot the light curve"""

        #cut the data
        self.make_lcdata()

        #make the figure
        self.light_plot = self.lccanvas.figure.add_axes(
            [0.10, 0.15, 0.8, 0.80], autoscale_on=False, adjustable='datalim')
        self.light_plot.hold(True)

        #plot the curve
        self.lightcurve, = self.light_plot.plot(self.tarr,
                                                self.rarr,
                                                linewidth=0.5,
                                                linestyle='-',
                                                marker='',
                                                color='b')
        if self.fluxplot:
            self.lightcurve.set_visible(True)
        else:
            self.lightcurve.set_visible(False)

        #plot the flux curve for star 1
        self.tstarcurve, = self.light_plot.plot(self.tarr,
                                                self.tfarr,
                                                linewidth=0.5,
                                                linestyle='-',
                                                marker='',
                                                color='y')
        if self.tstarplot:
            self.tstarcurve.set_visible(True)
        else:
            self.tstarcurve.set_visible(False)

        #plot the flux curve for star 1
        self.cstarcurve, = self.light_plot.plot(self.tarr,
                                                self.cfarr,
                                                linewidth=0.5,
                                                linestyle='-',
                                                marker='',
                                                color='g')
        if self.cstarplot:
            self.cstarcurve.set_visible(True)
        else:
            self.cstarcurve.set_visible(False)

        #plot a point which matches the time
        self.ptime = self.dtime[self.id]
        self.pratio = self.ratio[self.id]
        self.light_point, = self.light_plot.plot(np.asarray([self.ptime]),
                                                 np.asarray([self.pratio]),
                                                 linestyle='',
                                                 marker='o',
                                                 mec='#FF0000',
                                                 mfc='#FF0000')

        self.find_lclimits()
        ylabel = 'Star1/Star2'
        self.light_plot.set_ylabel(ylabel)
        self.light_plot.set_xlabel('Time (s)')

    def make_lcdata(self):
        #cut the data
        mask = (self.goodframes > 0)
        self.tarr = np.compress(mask, self.dtime)
        self.rarr = np.compress(mask, self.ratio)
        self.tfarr = np.compress(mask, self.tflux)
        self.cfarr = np.compress(mask, self.cflux)

    def find_lclimits(self, save_zoom=False):
        """Find the limits on the Light Curve plot"""
        if save_zoom: return
        self.lcx1 = self.tarr.min()
        self.lcx2 = self.tarr.max()
        self.light_plot.set_xlim(self.lcx1, self.lcx2)
        #determine the minimum y value based on what plots are turned on
        if self.fluxplot:
            self.lcy1 = self.rarr.min()
            self.lcy2 = self.rarr.max()
        if self.tstarplot:
            self.lcy1 = self.tfarr.min()
            self.lcy2 = self.tfarr.max()
        if self.cstarplot:
            self.lcy1 = self.cfarr.min()
            self.lcy2 = self.cfarr.max()
        if self.fluxplot and self.tstarplot and self.cstarplot:
            self.lcy1 = min(self.rarr.min(), self.tfarr.min(),
                            self.cfarr.min())
            self.lcy2 = max(self.rarr.max(), self.tfarr.max(),
                            self.cfarr.max())
        if self.tstarplot and self.cstarplot and not self.fluxplot:
            self.lcy1 = min(self.tfarr.min(), self.cfarr.min())
            self.lcy2 = max(self.tfarr.max(), self.cfarr.max())
        if self.tstarplot and not self.cstarplot and self.fluxplot:
            self.lcy1 = min(self.tfarr.min(), self.rarr.min())
            self.lcy2 = max(self.tfarr.max(), self.rarr.max())
        if not self.tstarplot and self.cstarplot and self.fluxplot:
            self.lcy1 = min(self.rarr.min(), self.cfarr.min())
            self.lcy2 = max(self.rarr.max(), self.cfarr.max())

        self.light_plot.set_ylim(self.lcy1, self.lcy2)

    def lcpickframe(self, event):
        self.set_id(event.xdata)
        self.updatepage()

    def set_id(self, t):
        """Given a time, set the object id"""
        self.id = np.abs(self.dtime - t).argmin()

    def set_plotpanel(self, hmin=250):
        #set up the control panel
        self.plotpanel = QtGui.QWidget()

        self.lccanvas = MplCanvas()
        self.plotlightcurve()
        #add the actions
        self.lccanvas.mpl_connect('button_press_event', self.onButtonPress)

        # Add navigation toolbars for each widget to enable zooming
        self.toolbar = NavigationToolbar2QT(self.lccanvas, self)

        # Set up the layout
        plotLayout = QtGui.QVBoxLayout(self.plotpanel)
        plotLayout.addWidget(self.lccanvas)
        plotLayout.addWidget(self.toolbar)

    def set_optionpanel(self):
        #set up the control panel
        self.optipanel = QtGui.QWidget()

        #set up the options
        self.fluxplot = True
        self.tstarplot = False
        self.cstarplot = False
        self.fluxButton = QtGui.QCheckBox("Flux Ratio")
        self.fluxButton.setChecked(self.fluxplot)
        self.fluxButton.clicked.connect(self.changefluxplot)
        self.tstarButton = QtGui.QCheckBox("Target")
        self.tstarButton.clicked.connect(self.changetstarplot)
        self.cstarButton = QtGui.QCheckBox("Comparison")
        self.cstarButton.clicked.connect(self.changecstarplot)

        # Set up the layout
        optiLayout = QtGui.QGridLayout(self.optipanel)
        optiLayout.addWidget(self.fluxButton, 0, 0, 1, 1)
        optiLayout.addWidget(self.tstarButton, 0, 1, 1, 1)
        optiLayout.addWidget(self.cstarButton, 0, 2, 1, 1)
        #optiLayout.addWidget(self.imagtoolbar)

    def set_imagepanel(self,
                       name=None,
                       cmap='gray',
                       scale='zscale',
                       contrast=0.1):
        """set up the Image Panel"""
        hmin = 150
        wmin = 400
        #set up the control panel
        self.imagpanel = QtGui.QWidget()

        #hmin=wmin*self.naxis2/self.naxis1
        #print self.naxis1, self.naxis2, wmin, hmin

        # Add FITS display widget with mouse interaction and overplotting
        self.imdisplay = ImageDisplay()
        #self.imdisplay.setMinimumWidth(wmin)

        # Set colormap
        self.imdisplay.setColormap(cmap)

        # Set scale mode for dynamic range
        imarr = self.struct[int(self.pid[self.id])].data
        self.imdisplay.scale = scale
        self.imdisplay.contrast = contrast
        self.imdisplay.aspect = 'auto'
        self.imdisplay.loadImage(imarr)
        #self.imdisplay.drawImage()
        hmin = self.imdisplay.width() * self.naxis2 / self.naxis1
        self.imdisplay.setMaximumHeight(hmin)
        self.imdisplay.setMinimumHeight(hmin)

        #add the rectangles
        self.add_mark(self.tx[self.id],
                      self.ty[self.id],
                      'target',
                      color='b',
                      lw=2)
        self.add_mark(self.cx[self.id],
                      self.cy[self.id],
                      'comparison',
                      color='g',
                      lw=2)
        self.imdisplay.redraw_canvas()
        self.imdisplay.axes.set_xticklabels([])
        self.imdisplay.axes.set_yticklabels([])

        self.imdisplay.connectMatplotlibMouseMotion()
        self.imdisplay.mpl_connect('button_press_event', self.onButtonPress)
        self.imdisplay.mpl_connect('key_press_event', self.onKeyPress)

        # Add navigation toolbars for each widget to enable zooming
        self.imagtoolbar = NavigationToolbar2QT(self.imdisplay, self)

        # Set up the layout
        imagLayout = QtGui.QVBoxLayout(self.imagpanel)
        #imagLayout.addWidget(self.imdisplay)
        imagLayout.addWidget(MplCanvas())
        imagLayout.addWidget(self.imagtoolbar)

    def add_mark(self, x1, y1, label, color='g', lw=2):
        """Add the rectangle for the object"""
        self.imdisplay.removePatch(label)
        r1 = self.r[label]
        rect = self.imdisplay.addSquare(label, x1, y1, r1, color=color, lw=lw)

    def set_controlpanel(self):
        """set up the Control Panel"""
        #set up the control panel
        self.contpanel = QtGui.QWidget()

        #set up the buttons
        self.frevButton = QtGui.QPushButton("<<")
        self.frevButton.clicked.connect(self.freverse)
        self.revButton = QtGui.QPushButton("<")
        self.revButton.clicked.connect(self.reverse)
        self.rev1Button = QtGui.QPushButton("-")
        self.rev1Button.clicked.connect(self.revone)
        self.stopButton = QtGui.QPushButton("Stop")
        self.stopButton.clicked.connect(self.stop)
        self.play1Button = QtGui.QPushButton("+")
        self.play1Button.clicked.connect(self.playone)
        self.playButton = QtGui.QPushButton(">")
        self.playButton.clicked.connect(self.play)
        self.fplayButton = QtGui.QPushButton(">>")
        self.fplayButton.clicked.connect(self.fplay)

        #set up the info panel layout
        contLayout = QtGui.QGridLayout(self.contpanel)
        #contLayout.addWidget(self.frevButton, 0, 0, 1, 1)
        #contLayout.addWidget(self.revButton,  0, 1, 1, 1)
        contLayout.addWidget(self.rev1Button, 0, 2, 1, 1)
        contLayout.addWidget(self.stopButton, 0, 3, 1, 1)
        contLayout.addWidget(self.play1Button, 0, 4, 1, 1)
        #contLayout.addWidget(self.playButton, 0, 5, 1, 1)
        #contLayout.addWidget(self.fplayButton,0, 6, 1, 1)

    def set_infopanel(self):
        """Set up the information panel"""

        #set up the information panel
        self.infopanel = QtGui.QWidget()

        #add the name of the file
        self.IDValueLabel = QtGui.QLabel("%i" % self.pid[self.id])
        self.IDValueLabel.setFrameStyle(QtGui.QFrame.Panel
                                        | QtGui.QFrame.Sunken)
        self.NameValueLabel = QtGui.QLabel("%s" % self.name)
        self.NameValueLabel.setFrameStyle(QtGui.QFrame.Panel
                                          | QtGui.QFrame.Sunken)
        self.timeValueLabel = QtGui.QLabel("%s" % self.get_time())
        self.timeValueLabel.setFrameStyle(QtGui.QFrame.Panel
                                          | QtGui.QFrame.Sunken)

        #set up the info panel layout
        infoLayout = QtGui.QGridLayout(self.infopanel)
        infoLayout.addWidget(self.IDValueLabel, 0, 0, 1, 1)
        infoLayout.addWidget(self.NameValueLabel, 0, 1, 1, 1)
        infoLayout.addWidget(self.timeValueLabel, 0, 2, 1, 1)

    def get_time(self):
        #set the time
        try:
            utime = self.struct[int(self.pid[self.id])].header['UTC-OBS']
        except:
            utime = ''
        return utime

    def help(self):
        """Print the help message and the key-bindings available to the user"""
        helpmessage = """
    The following commands are available to the user:
    ? - Print this information           q - quit the viewer
    n - Move to the next image           b - move back an image
    D - Delete this image                u - undelete this image
    p - Perform photometry on this image
    P - Perform photometry starting at this image
    stop button-Stop photometry or display
    reset button-Reset the light curve plot
    Middle Click-Display image corresponding to this time
        """
        print helpmessage
        return

    def stop(self):
        self.stopplay = False
        print self.stopplay

    def playone(self):
        stopid = self.nframes - 2
        if self.id < (stopid): self.id = self.id + 1
        self.updatepage()

    def play(self):
        self.stopplay = True
        stopid = self.nframes - 2
        while self.stopplay and self.id < stopid:
            self.id = self.id + 1
            time.sleep(self.sleep)
            self.updatepage()

    def fplay(self):
        self.stopplay = True
        stopid = self.nframes - 2
        while self.stopplay and self.id < stopid:
            self.id = self.id + 1
            self.updatepage()

    def revone(self):
        if self.id > 0: self.id = self.id - 1
        self.updatepage()

    def reverse(self):
        self.stopplay = True
        while self.stopplay and self.id > 0:
            self.id = self.id - 1
            time.sleep(self.sleep)
            self.updatepage()

    def freverse(self):
        self.stopplay = True
        while self.stopplay and self.id > 0:
            self.id = self.id - 1
            self.updatepage()

    def updatepage(self):
        """Update all the values on the page that need updating"""
        self.IDValueLabel.setText("%i" % self.pid[self.id])
        self.timeValueLabel.setText("%s" % self.get_time())

        #update the image
        imarr = self.struct[int(self.pid[self.id])].data
        self.imdisplay.loadImage(imarr)

        #update the boxes
        self.add_mark(self.tx[self.id],
                      self.ty[self.id],
                      'target',
                      color='b',
                      lw=2)
        self.add_mark(self.cx[self.id],
                      self.cy[self.id],
                      'comparison',
                      color='g',
                      lw=2)
        self.imdisplay.redraw_canvas()
        self.imdisplay.axes.set_xticklabels([])
        self.imdisplay.axes.set_yticklabels([])

        self.updatedataplot()

    def updatedataplot(self, save_zoom=True):
        """Update the data plot for changes in the options
       """
        #redraw the lines
        self.make_lcdata()
        self.lightcurve.set_xdata(self.tarr)
        self.lightcurve.set_ydata(self.rarr)
        self.tstarcurve.set_xdata(self.tarr)
        self.tstarcurve.set_ydata(self.tfarr)
        self.cstarcurve.set_xdata(self.tarr)
        self.cstarcurve.set_ydata(self.cfarr)

        #move the point
        self.light_point.set_xdata([self.dtime[self.id]])
        self.light_point.set_ydata([self.ratio[self.id]])

        if self.fluxplot:
            self.lightcurve.set_visible(True)
        else:
            self.lightcurve.set_visible(False)
        #plot the flux curve for star 1
        if self.tstarplot:
            self.tstarcurve.set_visible(True)
        else:
            self.tstarcurve.set_visible(False)

        #plot the flux curve for star 1
        if self.cstarplot:
            self.cstarcurve.set_visible(True)
        else:
            self.cstarcurve.set_visible(False)
        self.find_lclimits(save_zoom=save_zoom)
        self.lccanvas.draw()
예제 #2
0
class FpRingWidget (QtGui.QWidget):

    def __init__(self,filenumber,flatnumber,parent=None):
        super(FpRingWidget,self).__init__(parent)
        
        self.filenumber=filenumber
        self.flatnumber=flatnumber


        #set up the ring plot
        self.ringplot=MplCanvas()

        self.axes=self.ringplot.figure.add_subplot(211)
        self.erraxes=self.ringplot.figure.add_subplot(212)

        self.ringplot.setMinimumHeight(500)
#        self.ringplot.setMinimumHeight(500)

        self.loadfpring()
        self.plotRing()

#        self.redraw_canvas()

       #set up the information panel
        self.infopanel=QtGui.QWidget()

        # add a label:
        self.NameLabel = QtGui.QLabel("File number:")

       #add the name of the file
        self.NameValueLabel = QtGui.QLineEdit(str(self.filenumber))

        # and a button to process the new ring
        self.ringButton = QtGui.QPushButton('Load new ring')
        self.ringButton.clicked.connect(self.redrawRing)

        # add a label for the flat field:
        self.flatLabel = QtGui.QLabel("Flat file number:")

       #add the name of the file
        self.flatValueLabel = QtGui.QLineEdit(str(self.flatnumber))


       #set up info panel layout

        infoLayout=QtGui.QGridLayout(self.infopanel)
        infoLayout.addWidget(self.NameLabel,0,0,1,1)
        infoLayout.addWidget(self.NameValueLabel,0,1,1,1)
        infoLayout.addWidget(self.ringButton,0,2,2,1)
        infoLayout.addWidget(self.flatLabel,0,3,1,1)
        infoLayout.addWidget(self.flatValueLabel,0,4,1,1)
#        fitLayout=QtGui.QGridLayout(self.infopanel)


        # add a panel to display the fit results

        self.fitpanel=QtGui.QWidget()

        self.fitLabel = QtGui.QLabel("Fit Results:")

        fitXresult="X:" + str(self.etalon_x)
        fitYresult="Y:" + str(self.etalon_y)
        fitZresult="Z:" + str(self.etalon_z)
        fitRresult="R: %.1f" % float(self.pars['R'][0])
        fitAmpresult="Amplitude: %.1f" % float(self.pars['Amplitude'][0])
        fitRmsresult="RMS: %.1f" % float(self.rms)
        fitGammaresult="Gamma: %.1f" % float(self.pars['Gamma'][0])
        fitFWHMresult="FWHM: %.1f" % float(self.pars['FWHM'][0])


        #add the text to the fit results panel
        self.fitX = QtGui.QLabel(fitXresult)
        self.fitY = QtGui.QLabel(fitYresult)
        self.fitZ = QtGui.QLabel(fitZresult)
        self.fitR = QtGui.QLabel(fitRresult)
        self.fitAmp = QtGui.QLabel(fitAmpresult)
        self.fitRms = QtGui.QLabel(fitRmsresult)
        self.fitGamma = QtGui.QLabel(fitGammaresult)
        self.fitFWHM = QtGui.QLabel(fitFWHMresult)

        # lay them out nicely...

        fitLayout=QtGui.QGridLayout(self.fitpanel)
        fitLayout.addWidget(self.fitLabel,0,0,1,1)
        fitLayout.addWidget(self.fitX,0,1,1,1)
        fitLayout.addWidget(self.fitY,0,2,1,1)
        fitLayout.addWidget(self.fitZ,0,3,1,1)
        fitLayout.addWidget(self.fitR,0,4,1,1)
        fitLayout.addWidget(self.fitAmp,0,5,1,2)
        fitLayout.addWidget(self.fitRms,0,7,1,1)
        fitLayout.addWidget(self.fitGamma,0,8,1,1)
        fitLayout.addWidget(self.fitFWHM,0,9,1,1)
 

       # Set up the main layout
        mainLayout = QtGui.QVBoxLayout()
        mainLayout.addWidget(self.infopanel)
        mainLayout.addWidget(self.ringplot)
        mainLayout.addWidget(self.fitpanel)
        self.setLayout(mainLayout)

    def loadfpring(self):

        date = os.getcwd().split('/')[-1]
        
        self.getFitsHeader()
        fits = "mbxpP%s%04d.fits" % (date, self.filenumber)
        if self.flatnumber != 0:
            flat = "mbxpP%s%04d.fits" % (date, self.flatnumber)
        else:
            flat="/home/ccd/erc/FP_utils/DefaultNeFlat.fits"

        ffits='f'+fits
        fpfile='p'+ffits
        maskedfile='m'+fpfile


        if (not os.path.isfile(maskedfile)): 
             saltflat(fits,ffits,'',flat, clobber='yes',verbose='no')
             
             saltfpprep(ffits,fpfile,'',clobber='yes',verbose='no')
             
             saltfpmask(fpfile,maskedfile,'',axc=798*4/self.xbin,ayc=503*4/self.ybin,arad=450*4/self.xbin,clobber='yes', verbose='no')

        self.good, self.rsq, self.prof, self.fit, self.pars = fit_rings(maskedfile)
        self.resid = self.prof - self.fit
        self.rms = self.resid.std()

        self.saveFitToFile()
        
        return
    

    def plotRing(self):
        #set up the plots....

        self.axes.plot(self.rsq, self.prof, label="Profile")
        self.axes.plot(self.rsq, self.fit, label="Fit")
        self.axes.legend(bbox_to_anchor=(0., 1.02, 1., .102), loc=3,
                  ncol=2, mode="expand", borderaxespad=0.)
        self.erraxes.plot(self.rsq, self.resid, label="Profile - Fit")
        self.erraxes.legend(loc=1)
        self.show()

        return

    def redrawRing(self):
        # read the new filenumber from the input box
        self.filenumber=int(self.NameValueLabel.text())
        # recalculate and re-draw
        self.loadfpring()
        self.axes.clear()
        self.erraxes.clear()
        self.plotRing()
        #Force a redraw!!!
        self.ringplot.draw()


    def getFitsHeader(self):

        date = os.getcwd().split('/')[-1]
        fits = "mbxpP%s%04d.fits" % (date, self.filenumber)
        hdu = pyfits.open(fits)
        (data, header) = (hdu[0].data, hdu[0].header)
        etalon = int(header['ET-STATE'].split()[3])
        hetalon_x = "ET%dX" % etalon
        hetalon_y = "ET%dY" % etalon
        hetalon_z = "ET%dZ" % etalon

        self.etalon_x=int(header[hetalon_x])
        self.etalon_y=int(header[hetalon_y])
        self.etalon_z=int(header[hetalon_z])
        self.xbin=int(header['CCDSUM'].split()[0])
        self.ybin=int(header['CCDSUM'].split()[1])
        
        print self.xbin,self.ybin
  
        return

    def saveFitToFile(self):

        pars=self.pars
        self.getFitsHeader()

        if os.path.isfile('outparams'): 
            try:
                outparams=open('outparams','a')
                
            except IOError, e:
                print 'Failed to open the ring file'


        else:
예제 #3
0
class ArcDisplay(QtGui.QWidget):
    """Class for displaying Arc Spectra using matplotlib and embedded in a Qt 4 GUI.
    """
    def __init__(self,
                 xarr,
                 farr,
                 slines,
                 sfluxes,
                 ws,
                 xp=[],
                 wp=[],
                 xdiff=20,
                 res=2.0,
                 dres=0.1,
                 sigma=5,
                 niter=5):
        """Default constructor."""
        QtGui.QWidget.__init__(self)

        # Initialize base class
        self.arcfigure = MplCanvas()
        self.errfigure = MplCanvas()

        # Add central axes instance
        self.axes = self.arcfigure.figure.add_subplot(111)
        self.erraxes = self.errfigure.figure.add_subplot(111)

        # Connect mouse events
        self.arcfigure.connectMatplotlibMouseMotion()
        self.arcfigure.mpl_connect('button_press_event', self.onButtonPress)
        self.arcfigure.mpl_connect('key_press_event', self.onKeyPress)

        self.errfigure.connectMatplotlibMouseMotion()
        self.errfigure.mpl_connect('button_press_event', self.onButtonPress)
        self.errfigure.mpl_connect('key_press_event', self.onKeyPress)

        # load the data
        self.xarr = xarr
        self.farr = farr
        self.slines = slines
        self.sfluxes = sfluxes
        self.ws = ws
        self.xdiff = xdiff
        self.sigma = sigma
        self.niter = niter
        self.res = res
        self.dres = dres

        self.xp = xp
        self.wp = wp

        # set up the artificial spectra
        self.spectrum = Spectrum.Spectrum(self.slines,
                                          self.sfluxes,
                                          dw=self.dres,
                                          stype='line',
                                          sigma=self.res)
        self.swarr = self.spectrum.wavelength
        self.sfarr = self.spectrum.flux * self.farr.max(
        ) / self.spectrum.flux.max()

        # set up the wavelength solution
        if self.ws.function == 'line':
            self.ws.set_xarr(self.xarr)
            self.ws.farr = self.farr
            self.ws.spectrum = self.spectrum

        # set up the list of deleted points
        self.dxp = []
        self.dwp = []

        # set up other variables
        self.isArt = False
        self.isFeature = False

        # Set display parameters
        self.xmin = self.xarr.min()
        self.xmax = self.xarr.max()
        self.ymin = self.farr.min()
        self.ymax = self.farr.max()

    def onKeyPress(self, event):
        """Emit signal on key press"""
        if event.key == '?':
            # return the help file
            print('?:', event.key)
        elif event.key == 'c':
            # return the centroid
            if event.xdata:
                cx = st.mcentroid(self.xarr,
                                  self.farr,
                                  xc=event.xdata,
                                  xdiff=self.xdiff)
                self.emit(QtCore.SIGNAL("updatex(float)"), cx)
        elif event.key == 'x':
            # return the x position
            if event.xdata:
                self.emit(QtCore.SIGNAL("updatex(float)"), event.xdata)
        elif event.key == 'f':
            # find the fit
            self.findfit()
            self.emit(QtCore.SIGNAL("fitUpdate()"))
        elif event.key == 'b':
            # auto-idenitfy features
            self.findfeatures()
        elif event.key == 'z':
            # Assume the solution is correct and find the zeropoint
            # that best matches it from cross correllation
            self.findzp()
        elif event.key == 'e':
            # find closest feature from existing fit and line list
            # and match it
            pass
        elif event.key == 'l':
            # plot the features from existing list
            self.plotFeatures()
            self.redraw_canvas()
        elif event.key == 'i':
            # reset identified features
            pass
        elif event.key == 'r':
            # redraw graph
            self.redraw_canvas()
        elif event.key == 'a':
            # draw artificial spectrum
            self.isArt = not self.isArt
            self.redraw_canvas()
        elif event.key == 'd':
            # Delete feature
            save = False
            if event.canvas == self.errfigure:
                save = True
            self.deletepoints(event.xdata, save=save)
            self.redraw_canvas(keepzoom=True)
        elif event.key:
            self.emit(QtCore.SIGNAL("keyPressEvent(string)"), event.key)

    def onButtonPress(self, event):
        """Emit signal on selecting valid image position."""

        if event.xdata and event.ydata:
            print(event.xdata, event.ydata, event.canvas, event.name)
            self.emit(QtCore.SIGNAL("positionSelected(float, float)"),
                      float(event.xdata), float(event.ydata))

    def plotArc(self):
        """Draw image to canvas."""

        # plot the spectra
        self.spcurve, = self.axes.plot(self.xarr,
                                       self.farr,
                                       linewidth=0.5,
                                       linestyle='-',
                                       marker=None,
                                       color='b')

    def plotArt(self):
        """Plot the artificial spectrum"""
        self.isArt = True
        warr = self.ws.value(self.xarr)
        asfarr = st.interpolate(warr,
                                self.swarr,
                                self.sfarr,
                                left=0.0,
                                right=0.0)
        self.fpcurve, = self.axes.plot(self.xarr,
                                       asfarr,
                                       linewidth=0.5,
                                       linestyle='-',
                                       marker=None,
                                       color='r')

    def plotFeatures(self):
        """Plot features identified in the line list"""
        self.isFeature = True
        fl = np.array(self.xp) * 0.0 + 0.25 * self.farr.max()
        self.splines = self.axes.plot(self.xp,
                                      fl,
                                      ls='',
                                      marker='|',
                                      ms=20,
                                      color='#00FF00')
        # set up the text position
        tsize = 0.83
        self.ymin, self.ymax = self.axes.get_ylim()
        ppp = (self.ymax - self.ymin) / (self.arcfigure.figure.get_figheight()
                                         * self.arcfigure.figure.get_dpi())
        f = self.ymax - 10 * tsize * ppp
        for x, w in zip(self.xp, self.wp):
            w = '%6.2f' % float(w)
            self.axes.text(x,
                           f,
                           w,
                           size='small',
                           rotation='vertical',
                           color='#00FF00')

    def plotErr(self):
        """Draw image to canvas."""
        if self.xp and self.wp:
            # plot the spectra
            w = self.ws.value(self.xp)
            self.errcurve, = self.erraxes.plot(self.xp,
                                               self.wp - w,
                                               linewidth=0.5,
                                               linestyle='',
                                               marker='o',
                                               color='b')
        if self.dxp and self.dwp:
            # plot the spectra
            dw = self.ws.value(self.dxp)
            self.delerrcurve, = self.erraxes.plot(self.dxp,
                                                  self.dwp - dw,
                                                  linewidth=0.5,
                                                  linestyle='',
                                                  marker='x',
                                                  color='b')

    def findfeatures(self):
        """Given a set of features, find other features that might
           correspond to those features
        """
        xp, wp = st.findfeatures(self.xarr,
                                 self.farr,
                                 self.slines,
                                 self.sfluxes,
                                 self.ws,
                                 sigma=self.sigma,
                                 niter=self.niter)
        for x, w in zip(xp, wp):
            if w not in self.wp and w > -1:
                self.xp.append(x)
                self.wp.append(w)
        self.plotFeatures()
        self.redraw_canvas()

    def findzp(self):
        """Find the zeropoint for the source and plot of the new value
        """
        self.ws = st.findzeropoint(self.xarr,
                                   self.farr,
                                   self.swarr,
                                   self.sfarr,
                                   self.ws,
                                   dc=10,
                                   nstep=20,
                                   inttype='interp')
        self.plotArt()
        self.redraw_canvas()

    def findfit(self):
        print(self.xp)
        print(self.wp)
        self.ws = st.findfit(self.xp,
                             self.wp,
                             function=self.ws.function,
                             order=self.ws.order)
        self.err_redraw_canvas()

    def addpoints(self, x, w):
        """Add points to the line list
        """
        if isinstance(x, list) and isinstance(w, list):
            self.xp.extend(x)
            self.wp.extend(w)
        else:
            self.xp.append(x)
            self.wp.append(w)
        print(self.xp)

    def deletepoints(self, x, save=False):
        """ Delete points from the line list
        """
        in_minw = np.abs(np.array(self.xp) - x).argmin()
        if save:
            self.dxp.append(self.xp[in_minw])
            self.dwp.append(self.wp[in_minw])
        self.xp.__delitem__(in_minw)
        self.wp.__delitem__(in_minw)

    def redraw_canvas(self, keepzoom=False):
        if keepzoom:
            # Store current zoom level
            xmin, xmax = self.axes.get_xlim()
            ymin, ymax = self.axes.get_ylim()

        # Clear plot
        self.axes.clear()

        # Draw image
        self.plotArc()

        # if necessary, redraw the features
        if self.isFeature:
            self.plotFeatures()

        # if necessary, draw the artificial spectrum
        if self.isArt:
            self.plotArt()

        # Restore zoom level
        if keepzoom:
            self.axes.set_xlim((self.xmin, self.xmax))
            self.axes.set_ylim((self.ymin, self.ymax))

        # Force redraw
        self.arcfigure.draw()

        self.err_redraw_canvas()

    def err_redraw_canvas(self, keepzoom=False):
        if keepzoom:
            # Store current zoom level
            xmin, xmax = self.erraxes.get_xlim()
            ymin, ymax = self.erraxes.get_ylim()
        else:
            self.xmin, self.xmax = self.axes.get_xlim()

        # Clear plot
        self.erraxes.clear()

        # Draw image
        self.plotErr()

        # Restore zoom level
        if keepzoom:
            self.erraxes.set_xlim((xmin, xmax))
            self.erraxes.set_ylim((ymin, ymax))
        else:
            self.erraxes.set_xlim((self.xmin, self.xmax))

        self.errfigure.draw()

        self.emit(QtCore.SIGNAL("fitUpdate()"))
예제 #4
0
class ArcDisplay(QtGui.QWidget):

    """Class for displaying Arc Spectra using matplotlib and embedded in a Qt 4 GUI.
    """

    def __init__(self, xarr, farr, slines, sfluxes, ws, xp=[], wp=[], xdiff=20,
                 res=2.0, dres=0.1, sigma=5, niter=5):
        """Default constructor."""
        QtGui.QWidget.__init__(self)

        # Initialize base class
        self.arcfigure = MplCanvas()
        self.errfigure = MplCanvas()

        # Add central axes instance
        self.axes = self.arcfigure.figure.add_subplot(111)
        self.erraxes = self.errfigure.figure.add_subplot(111)

        # Connect mouse events
        self.arcfigure.connectMatplotlibMouseMotion()
        self.arcfigure.mpl_connect('button_press_event', self.onButtonPress)
        self.arcfigure.mpl_connect('key_press_event', self.onKeyPress)

        self.errfigure.connectMatplotlibMouseMotion()
        self.errfigure.mpl_connect('button_press_event', self.onButtonPress)
        self.errfigure.mpl_connect('key_press_event', self.onKeyPress)

        # load the data
        self.xarr = xarr
        self.farr = farr
        self.slines = slines
        self.sfluxes = sfluxes
        self.ws = ws
        self.xdiff = xdiff
        self.sigma = sigma
        self.niter = niter
        self.res = res
        self.dres = dres

        self.xp = xp
        self.wp = wp

        # set up the artificial spectra
        self.spectrum = Spectrum.Spectrum(self.slines, self.sfluxes, dw=self.dres, stype='line', sigma=self.res)
        self.swarr = self.spectrum.wavelength
        self.sfarr = self.spectrum.flux * self.farr.max() / self.spectrum.flux.max()

        # set up the wavelength solution
        if self.ws.function == 'line':
            self.ws.set_xarr(self.xarr)
            self.ws.farr = self.farr
            self.ws.spectrum = self.spectrum

        # set up the list of deleted points
        self.dxp = []
        self.dwp = []

        # set up other variables
        self.isArt = False
        self.isFeature = False

        # Set display parameters
        self.xmin = self.xarr.min()
        self.xmax = self.xarr.max()
        self.ymin = self.farr.min()
        self.ymax = self.farr.max()

    def onKeyPress(self, event):
        """Emit signal on key press"""
        if event.key == '?':
            # return the help file
            print '?:', event.key
        elif event.key == 'c':
            # return the centroid
            if event.xdata:
                cx = st.mcentroid(self.xarr, self.farr, xc=event.xdata, xdiff=self.xdiff)
                self.emit(QtCore.SIGNAL("updatex(float)"), cx)
        elif event.key == 'x':
            # return the x position
            if event.xdata:
                self.emit(QtCore.SIGNAL("updatex(float)"), event.xdata)
        elif event.key == 'f':
            # find the fit
            self.findfit()
            self.emit(QtCore.SIGNAL("fitUpdate()"))
        elif event.key == 'b':
            # auto-idenitfy features
            self.findfeatures()
        elif event.key == 'z':
            # Assume the solution is correct and find the zeropoint
            # that best matches it from cross correllation
            self.findzp()
        elif event.key == 'e':
            # find closest feature from existing fit and line list
            # and match it
            pass
        elif event.key == 'l':
            # plot the features from existing list
            self.plotFeatures()
            self.redraw_canvas()
        elif event.key == 'i':
            # reset identified features
            pass
        elif event.key == 'r':
            # redraw graph
            self.redraw_canvas()
        elif event.key == 'a':
            # draw artificial spectrum
            self.isArt = not self.isArt
            self.redraw_canvas()
        elif event.key == 'd':
            # Delete feature
            save = False
            if event.canvas == self.errfigure:
                save = True
            self.deletepoints(event.xdata, save=save)
            self.redraw_canvas(keepzoom=True)
        elif event.key:
            self.emit(QtCore.SIGNAL("keyPressEvent(string)"), event.key)

    def onButtonPress(self, event):
        """Emit signal on selecting valid image position."""

        if event.xdata and event.ydata:
            print event.xdata, event.ydata, event.canvas, event.name
            self.emit(QtCore.SIGNAL("positionSelected(float, float)"),
                      float(event.xdata), float(event.ydata))

    def plotArc(self):
        """Draw image to canvas."""

        # plot the spectra
        self.spcurve, = self.axes.plot(self.xarr, self.farr, linewidth=0.5, linestyle='-', marker=None, color='b')

    def plotArt(self):
        """Plot the artificial spectrum"""
        self.isArt = True
        warr = self.ws.value(self.xarr)
        asfarr = st.interpolate(warr, self.swarr, self.sfarr, left=0.0, right=0.0)
        self.fpcurve, = self.axes.plot(self.xarr, asfarr, linewidth=0.5, linestyle='-',
                                       marker=None, color='r')

    def plotFeatures(self):
        """Plot features identified in the line list"""
        self.isFeature = True
        fl = np.array(self.xp) * 0.0 + 0.25 * self.farr.max()
        self.splines = self.axes.plot(self.xp, fl, ls='', marker='|', ms=20, color='#00FF00')
        # set up the text position
        tsize = 0.83
        self.ymin, self.ymax = self.axes.get_ylim()
        ppp = (self.ymax - self.ymin) / (self.arcfigure.figure.get_figheight() * self.arcfigure.figure.get_dpi())
        f = self.ymax - 10 * tsize * ppp
        for x, w in zip(self.xp, self.wp):
            w = '%6.2f' % float(w)
            self.axes.text(x, f, w, size='small', rotation='vertical', color='#00FF00')

    def plotErr(self):
        """Draw image to canvas."""
        if self.xp and self.wp:
            # plot the spectra
            w = self.ws.value(self.xp)
            self.errcurve, = self.erraxes.plot(self.xp, self.wp - w, linewidth=0.5, linestyle='', marker='o', color='b')
        if self.dxp and self.dwp:
            # plot the spectra
            dw = self.ws.value(self.dxp)
            self.delerrcurve, = self.erraxes.plot(
                self.dxp, self.dwp - dw, linewidth=0.5, linestyle='', marker='x', color='b')

    def findfeatures(self):
        """Given a set of features, find other features that might
           correspond to those features
        """
        xp, wp = st.findfeatures(self.xarr, self.farr, self.slines, self.sfluxes,
                                 self.ws, sigma=self.sigma, niter=self.niter)
        for x, w in zip(xp, wp):
            if w not in self.wp and w > -1:
                self.xp.append(x)
                self.wp.append(w)
        self.plotFeatures()
        self.redraw_canvas()

    def findzp(self):
        """Find the zeropoint for the source and plot of the new value
        """
        self.ws = st.findzeropoint(self.xarr, self.farr, self.swarr, self.sfarr,
                                   self.ws, dc=10, nstep=20, inttype='interp')
        self.plotArt()
        self.redraw_canvas()

    def findfit(self):
        print self.xp
        print self.wp
        self.ws = st.findfit(self.xp, self.wp, function=self.ws.function, order=self.ws.order)
        self.err_redraw_canvas()

    def addpoints(self, x, w):
        """Add points to the line list
        """
        if isinstance(x, list) and isinstance(w, list):
            self.xp.extend(x)
            self.wp.extend(w)
        else:
            self.xp.append(x)
            self.wp.append(w)
        print self.xp

    def deletepoints(self, x, save=False):
        """ Delete points from the line list
        """
        in_minw = np.abs(np.array(self.xp) - x).argmin()
        if save:
            self.dxp.append(self.xp[in_minw])
            self.dwp.append(self.wp[in_minw])
        self.xp.__delitem__(in_minw)
        self.wp.__delitem__(in_minw)

    def redraw_canvas(self, keepzoom=False):
        if keepzoom:
            # Store current zoom level
            xmin, xmax = self.axes.get_xlim()
            ymin, ymax = self.axes.get_ylim()

        # Clear plot
        self.axes.clear()

        # Draw image
        self.plotArc()

        # if necessary, redraw the features
        if self.isFeature:
            self.plotFeatures()

        # if necessary, draw the artificial spectrum
        if self.isArt:
            self.plotArt()

        # Restore zoom level
        if keepzoom:
            self.axes.set_xlim((self.xmin, self.xmax))
            self.axes.set_ylim((self.ymin, self.ymax))

        # Force redraw
        self.arcfigure.draw()

        self.err_redraw_canvas()

    def err_redraw_canvas(self, keepzoom=False):
        if keepzoom:
            # Store current zoom level
            xmin, xmax = self.erraxes.get_xlim()
            ymin, ymax = self.erraxes.get_ylim()
        else:
            self.xmin, self.xmax = self.axes.get_xlim()

        # Clear plot
        self.erraxes.clear()

        # Draw image
        self.plotErr()

        # Restore zoom level
        if keepzoom:
            self.erraxes.set_xlim((xmin, xmax))
            self.erraxes.set_ylim((ymin, ymax))
        else:
            self.erraxes.set_xlim((self.xmin, self.xmax))

        self.errfigure.draw()

        self.emit(QtCore.SIGNAL("fitUpdate()"))
예제 #5
0
class FpParallWidget (QtGui.QWidget):

    def __init__(self,parent=None):
        super(FpParallWidget,self).__init__(parent)

        #Load up the data:
        self.loadOutparams()


       #set up the file range panel
        self.rangepanel=QtGui.QWidget()

        # add a label:
        self.FromLabel = QtGui.QLabel("From file number:")
        self.ToLabel = QtGui.QLabel("To file number:")

       #add the name of the file
        self.FromValueLabel = QtGui.QLineEdit(str(min(self.outparams[:,0])))
        self.ToValueLabel = QtGui.QLineEdit(str(max(self.outparams[:,0])))

        # and a button to process the new range
        self.refreshButton = QtGui.QPushButton('Refresh')
        self.refreshButton.clicked.connect(self.plotOutparams)

       #set up file range panel layout

        rangeLayout=QtGui.QGridLayout(self.rangepanel)
        rangeLayout.addWidget(self.FromLabel,0,0,1,1)
        rangeLayout.addWidget(self.FromValueLabel,0,1,1,1)
        rangeLayout.addWidget(self.refreshButton,0,2,2,1)
        rangeLayout.addWidget(self.ToLabel,0,3,1,1)
        rangeLayout.addWidget(self.ToValueLabel,0,4,1,1)


        #add the radio buttons for the choice of x axis...


        self.radioFilenumber= QtGui.QRadioButton("Plot vs Filenumber")
        self.radioX= QtGui.QRadioButton("Plot vs etalon X")
        self.radioY= QtGui.QRadioButton("Plot vs etalon Y")

        #create a gropu for them:
        self.radioGroupX=QtGui.QButtonGroup()
        self.radioGroupX.addButton(self.radioFilenumber)
        self.radioGroupX.addButton(self.radioX)
        self.radioGroupX.addButton(self.radioY)

        #make sure the filenumber is the default
        self.radioFilenumber.setChecked(True)


        #create radio buttons for the choice of y axis:
        self.radioFWHM=QtGui.QRadioButton("Plots vs FWHM")
        self.radioAmp=QtGui.QRadioButton("Plots vs Amplitude")
        
        #add a group for the y axis:
        self.radioGroupY=QtGui.QButtonGroup()
        self.radioGroupY.addButton(self.radioFWHM)
        self.radioGroupY.addButton(self.radioAmp)

        #add a default:
        self.radioFWHM.setChecked(True)


        # display best fit in range:

        self.fitpanel=QtGui.QWidget()

        self.fitLabel = QtGui.QLabel("Lowest FWHM in file range:")
        self.cleanOutparams()
        self.getBestparams()

        fitFileresult="File number: %i" %int(self.bestparams[0])
        fitXresult="X: %i" % int(self.bestparams[1])
        fitYresult="Y: %i" % int(self.bestparams[2])
        fitZresult="Z: %i " % int(self.bestparams[3])
        fitRresult="R: %.1f" % float(self.bestparams[4])
        fitAmpresult="Amplitude: %.1f" % float(self.bestparams[5])
        fitRmsresult="RMS: %.3f" % float(self.bestparams[6])
        fitGammaresult="Gamma: %.2f" % float(self.bestparams[7])
        fitFWHMresult="FWHM: %.3f" % float(self.bestparams[8])


        #add the text to the fit results panel
                                    
        self.fitFile = QtGui.QLabel(fitFileresult)
        self.fitX = QtGui.QLabel(fitXresult)
        self.fitY = QtGui.QLabel(fitYresult)
        self.fitZ = QtGui.QLabel(fitZresult)
        self.fitR = QtGui.QLabel(fitRresult)
        self.fitAmp = QtGui.QLabel(fitAmpresult)
        self.fitRms = QtGui.QLabel(fitRmsresult)
        self.fitGamma = QtGui.QLabel(fitGammaresult)
        self.fitFWHM = QtGui.QLabel(fitFWHMresult)

        # lay them out nicely...

        fitLayout=QtGui.QGridLayout(self.fitpanel)
        fitLayout.addWidget(self.fitLabel,0,0,1,4)
        fitLayout.addWidget(self.fitFile,3,0,1,1)
        fitLayout.addWidget(self.fitX,3,1,1,1)
        fitLayout.addWidget(self.fitY,3,2,1,1)
        fitLayout.addWidget(self.fitZ,3,3,1,1)
        fitLayout.addWidget(self.fitR,3,4,1,1)
        fitLayout.addWidget(self.fitAmp,3,5,1,1)
        fitLayout.addWidget(self.fitRms,3,6,1,1)
        fitLayout.addWidget(self.fitGamma,3,7,1,1)
        fitLayout.addWidget(self.fitFWHM,3,8,1,1)
 

        
        #set up the fwhm plot

        self.fwhmplot=MplCanvas()

        self.fwhmaxes=self.fwhmplot.figure.add_subplot(111)

        #connect mouse clicks
        
        self.fwhmplot.mpl_connect('button_press_event',self.onClick)



        #and now we know what the X and Y axis should be, make the fwhm/amp plot

        self.plotOutparams()

        # and check for radio button event signals!

        self.radioGroupX.buttonClicked.connect(self.plotOutparams)
        self.radioGroupY.buttonClicked.connect(self.plotOutparams)

        #Add the X radio buttons to a horizontal layout
        
        self.radiopanel= QtGui.QWidget()

        radioLayout=QtGui.QHBoxLayout(self.radiopanel)
        radioLayout.addWidget(self.radioFilenumber)
        radioLayout.addWidget(self.radioX)
        radioLayout.addWidget(self.radioY)

        #Add the Y radio buttons to a vertical layout

        self.radioYpanel=QtGui.QWidget()
        
        radioYLayout=QtGui.QVBoxLayout(self.radioYpanel)
        radioYLayout.addWidget(self.radioFWHM)
        radioYLayout.addWidget(self.radioAmp)

       # Set up the main layout
        mainLayout = QtGui.QGridLayout()
        mainLayout.addWidget(self.rangepanel,0,0,1,9)
        mainLayout.addWidget(self.fitpanel,1,0,1,9)
        mainLayout.addWidget(self.fwhmplot,2,0,1,4)
        mainLayout.addWidget(self.radioYpanel,2,5,1,1)
        mainLayout.addWidget(self.radiopanel,3,1,1,1)
        self.setLayout(mainLayout)



    def loadOutparams(self):

        self.outparams=np.genfromtxt('outparams', skip_header=1)

        return

    def cleanOutparams(self):

        minFile=float(self.FromValueLabel.text())
        maxFile=float(self.ToValueLabel.text())
#        print "reloading from %i to %i" % (minFile, maxFile)

        self.cleanarr=[]

        mask = (minFile <= self.outparams[:,0]) * (self.outparams[:,0] <= maxFile)
        self.cleanarr = self.outparams[mask]

#        print self.cleanarr[:,0]

        return

    def plotOutparams(self):
        #reload outparams

        self.loadOutparams()

        #set up the plot....

        self.cleanOutparams()
        self.fwhmaxes.clear()

        if self.radioFilenumber.isChecked():
            x=self.cleanarr[:,0]
        elif self.radioX.isChecked():
            x=self.cleanarr[:,1]
        elif self.radioY.isChecked():
            x=self.cleanarr[:,2]

        # Work out the Y axis:

        if self.radioFWHM.isChecked():
            y=self.cleanarr[:,8]
        elif self.radioAmp.isChecked():
            y=self.cleanarr[:,5]



        self.fwhmaxes.plot(x, y, 'bo')

#        self.show()
        
        # don't forget to force a redraw!

        self.fwhmplot.draw()

        #ummmm we forgot to update the best fit..
        self.getBestparams()

        self.fitFile.setText("File number: %i" %int(self.bestparams[0]))
        self.fitX.setText("X: %i" % int(self.bestparams[1]))
        self.fitX.setText("X: %i" % int(self.bestparams[1]))
        self.fitY.setText("Y %i:" % int(self.bestparams[2]))
        self.fitZ.setText("Z: %i " % int(self.bestparams[3]))
        self.fitR.setText("R: %.1f" % float(self.bestparams[4]))
        self.fitAmp.setText("Amplitude: %.1f" % float(self.bestparams[5]))
        self.fitRms.setText("RMS: %.2f" % float(self.bestparams[6]))
        self.fitGamma.setText("Gamma: %.2f" % float(self.bestparams[7]))
        self.fitFWHM.setText("FWHM: %.3f" % float(self.bestparams[8]))

#        self.fitpanel.show()

        return

    def onClick(self,event):

#        What's on the X axis?

        if self.radioFilenumber.isChecked():
            mask = (self.cleanarr[:,0]==round(event.xdata))
        elif self.radioX.isChecked():
            mask = (self.cleanarr[:,1]==round(event.xdata))
        elif self.radioY.isChecked():
            mask = (self.cleanarr[:,2]==round(event.xdata))

        # get from the array the first row that matches the X value)
        datapoint = self.cleanarr[mask][0]

        #format it ready for the tooltip:
        text="FileNumber: %i, \nX: %i, \nY: %i, \nZ:%i, \nAmp: %.2f, \nRMS: %.2f, \nGamma: %.2f, \nFWHM: %.3f" % (int(datapoint[0]), int(datapoint[1]),int(datapoint[2]),int(datapoint[3]),datapoint[5],datapoint[6],datapoint[7],datapoint[8])

        #and plonk it on! :)
        QtGui.QToolTip.showText(QtCore.QPoint(338,314),text)

        return

    def getBestparams(self):

        if self.radioFWHM.isChecked():
            self.fitLabel.setText("Lowest FWHM in file range:")
            mask = (self.cleanarr[:,8]==min(self.cleanarr[:,8]))
            self.bestparams = self.cleanarr[mask][0]
        elif self.radioAmp.isChecked():
            self.fitLabel.setText("Highest Amplitude in file range:")
            mask = (self.cleanarr[:,5]==max(self.cleanarr[:,5]))
            self.bestparams = self.cleanarr[mask][0]


        return
예제 #6
0
class FpParallWidget (QtGui.QWidget):

    def __init__(self,parent=None):
        super(FpParallWidget,self).__init__(parent)

        #Load up the data:
        self.loadOutparams()


       #set up the file range panel
        self.rangepanel=QtGui.QWidget()

        # add a label:
        self.FromLabel = QtGui.QLabel("From file number:")
        self.ToLabel = QtGui.QLabel("To file number:")

       #add the name of the file
        self.FromValueLabel = QtGui.QLineEdit(str(min(self.outparams[:,0])))
        self.ToValueLabel = QtGui.QLineEdit(str(max(self.outparams[:,0])))

        # and a button to process the new range
        self.refreshButton = QtGui.QPushButton('Refresh')
        self.refreshButton.clicked.connect(self.plotOutparams)

       #set up file range panel layout

        rangeLayout=QtGui.QGridLayout(self.rangepanel)
        rangeLayout.addWidget(self.FromLabel,0,0,1,1)
        rangeLayout.addWidget(self.FromValueLabel,0,1,1,1)
        rangeLayout.addWidget(self.refreshButton,0,2,2,1)
        rangeLayout.addWidget(self.ToLabel,0,3,1,1)
        rangeLayout.addWidget(self.ToValueLabel,0,4,1,1)


        #add the radio buttons for the choice of x axis...


        self.radioFilenumber= QtGui.QRadioButton("Plot vs Filenumber")
        self.radioX= QtGui.QRadioButton("Plot vs etalon X")
        self.radioY= QtGui.QRadioButton("Plot vs etalon Y")

        #create a gropu for them:
        self.radioGroupX=QtGui.QButtonGroup()
        self.radioGroupX.addButton(self.radioFilenumber)
        self.radioGroupX.addButton(self.radioX)
        self.radioGroupX.addButton(self.radioY)

        #make sure the filenumber is the default
        self.radioFilenumber.setChecked(True)


        #create radio buttons for the choice of y axis:
        self.radioFWHM=QtGui.QRadioButton("Plots vs FWHM")
        self.radioAmp=QtGui.QRadioButton("Plots vs Amplitude")
        
        #add a group for the y axis:
        self.radioGroupY=QtGui.QButtonGroup()
        self.radioGroupY.addButton(self.radioFWHM)
        self.radioGroupY.addButton(self.radioAmp)

        #add a default:
        self.radioFWHM.setChecked(True)


        # display best fit in range:

        self.fitpanel=QtGui.QWidget()

        self.fitLabel = QtGui.QLabel("Lowest FWHM in file range:")
        self.cleanOutparams()
        self.getBestparams()

        fitFileresult="File number: %i" %int(self.bestparams[0])
        fitXresult="X: %i" % int(self.bestparams[1])
        fitYresult="Y: %i" % int(self.bestparams[2])
        fitZresult="Z: %i " % int(self.bestparams[3])
        fitRresult="R: %.1f" % float(self.bestparams[4])
        fitAmpresult="Amplitude: %.1f" % float(self.bestparams[5])
        fitRmsresult="RMS: %.3f" % float(self.bestparams[6])
        fitGammaresult="Gamma: %.2f" % float(self.bestparams[7])
        fitFWHMresult="FWHM: %.3f" % float(self.bestparams[8])


        #add the text to the fit results panel
                                    
        self.fitFile = QtGui.QLabel(fitFileresult)
        self.fitX = QtGui.QLabel(fitXresult)
        self.fitY = QtGui.QLabel(fitYresult)
        self.fitZ = QtGui.QLabel(fitZresult)
        self.fitR = QtGui.QLabel(fitRresult)
        self.fitAmp = QtGui.QLabel(fitAmpresult)
        self.fitRms = QtGui.QLabel(fitRmsresult)
        self.fitGamma = QtGui.QLabel(fitGammaresult)
        self.fitFWHM = QtGui.QLabel(fitFWHMresult)

        # lay them out nicely...

        fitLayout=QtGui.QGridLayout(self.fitpanel)
        fitLayout.addWidget(self.fitLabel,0,0,1,4)
        fitLayout.addWidget(self.fitFile,3,0,1,1)
        fitLayout.addWidget(self.fitX,3,1,1,1)
        fitLayout.addWidget(self.fitY,3,2,1,1)
        fitLayout.addWidget(self.fitZ,3,3,1,1)
        fitLayout.addWidget(self.fitR,3,4,1,1)
        fitLayout.addWidget(self.fitAmp,3,5,1,1)
        fitLayout.addWidget(self.fitRms,3,6,1,1)
        fitLayout.addWidget(self.fitGamma,3,7,1,1)
        fitLayout.addWidget(self.fitFWHM,3,8,1,1)
 

        
        #set up the fwhm plot

        self.fwhmplot=MplCanvas()

        self.fwhmaxes=self.fwhmplot.figure.add_subplot(111)

        #connect mouse clicks
        
        self.fwhmplot.mpl_connect('button_press_event',self.onClick)



        #and now we know what the X and Y axis should be, make the fwhm/amp plot

        self.plotOutparams()

        # and check for radio button event signals!

        self.radioGroupX.buttonClicked.connect(self.plotOutparams)
        self.radioGroupY.buttonClicked.connect(self.plotOutparams)

        #Add the X radio buttons to a horizontal layout
        
        self.radiopanel= QtGui.QWidget()

        radioLayout=QtGui.QHBoxLayout(self.radiopanel)
        radioLayout.addWidget(self.radioFilenumber)
        radioLayout.addWidget(self.radioX)
        radioLayout.addWidget(self.radioY)

        #Add the Y radio buttons to a vertical layout

        self.radioYpanel=QtGui.QWidget()
        
        radioYLayout=QtGui.QVBoxLayout(self.radioYpanel)
        radioYLayout.addWidget(self.radioFWHM)
        radioYLayout.addWidget(self.radioAmp)

       # Set up the main layout
        mainLayout = QtGui.QGridLayout()
        mainLayout.addWidget(self.rangepanel,0,0,1,9)
        mainLayout.addWidget(self.fitpanel,1,0,1,9)
        mainLayout.addWidget(self.fwhmplot,2,0,1,4)
        mainLayout.addWidget(self.radioYpanel,2,5,1,1)
        mainLayout.addWidget(self.radiopanel,3,1,1,1)
        self.setLayout(mainLayout)



    def loadOutparams(self):

        self.outparams=np.genfromtxt('outparams', skip_header=1)

        return

    def cleanOutparams(self):

        minFile=float(self.FromValueLabel.text())
        maxFile=float(self.ToValueLabel.text())
#        print "reloading from %i to %i" % (minFile, maxFile)

        self.cleanarr=[]

        mask = (minFile <= self.outparams[:,0]) * (self.outparams[:,0] <= maxFile)
        self.cleanarr = self.outparams[mask]

#        print self.cleanarr[:,0]

        return

    def plotOutparams(self):
        #reload outparams

        self.loadOutparams()

        #set up the plot....

        self.cleanOutparams()
        self.fwhmaxes.clear()

        if self.radioFilenumber.isChecked():
            x=self.cleanarr[:,0]
        elif self.radioX.isChecked():
            x=self.cleanarr[:,1]
        elif self.radioY.isChecked():
            x=self.cleanarr[:,2]

        # Work out the Y axis:

        if self.radioFWHM.isChecked():
            y=self.cleanarr[:,8]
        elif self.radioAmp.isChecked():
            y=self.cleanarr[:,5]



        self.fwhmaxes.plot(x, y, 'bo')

#        self.show()
        
        # don't forget to force a redraw!

        self.fwhmplot.draw()

        #ummmm we forgot to update the best fit..
        self.getBestparams()

        self.fitFile.setText("File number: %i" %int(self.bestparams[0]))
        self.fitX.setText("X: %i" % int(self.bestparams[1]))
        self.fitX.setText("X: %i" % int(self.bestparams[1]))
        self.fitY.setText("Y %i:" % int(self.bestparams[2]))
        self.fitZ.setText("Z: %i " % int(self.bestparams[3]))
        self.fitR.setText("R: %.1f" % float(self.bestparams[4]))
        self.fitAmp.setText("Amplitude: %.1f" % float(self.bestparams[5]))
        self.fitRms.setText("RMS: %.2f" % float(self.bestparams[6]))
        self.fitGamma.setText("Gamma: %.2f" % float(self.bestparams[7]))
        self.fitFWHM.setText("FWHM: %.3f" % float(self.bestparams[8]))

#        self.fitpanel.show()

        return

    def onClick(self,event):

#        What's on the X axis?

        if self.radioFilenumber.isChecked():
            mask = (self.cleanarr[:,0]==round(event.xdata))
        elif self.radioX.isChecked():
            mask = (self.cleanarr[:,1]==round(event.xdata))
        elif self.radioY.isChecked():
            mask = (self.cleanarr[:,2]==round(event.xdata))

        # get from the array the first row that matches the X value)
        datapoint = self.cleanarr[mask][0]

        #format it ready for the tooltip:
        text="FileNumber: %i, \nX: %i, \nY: %i, \nZ:%i, \nAmp: %.2f, \nRMS: %.2f, \nGamma: %.2f, \nFWHM: %.3f" % (int(datapoint[0]), int(datapoint[1]),int(datapoint[2]),int(datapoint[3]),datapoint[5],datapoint[6],datapoint[7],datapoint[8])

        #and plonk it on! :)
        QtGui.QToolTip.showText(QtCore.QPoint(338,314),text)

        return

    def getBestparams(self):

        if self.radioFWHM.isChecked():
            self.fitLabel.setText("Lowest FWHM in file range:")
            mask = (self.cleanarr[:,8]==min(self.cleanarr[:,8]))
            self.bestparams = self.cleanarr[mask][0]
        elif self.radioAmp.isChecked():
            self.fitLabel.setText("Highest Amplitude in file range:")
            mask = (self.cleanarr[:,5]==max(self.cleanarr[:,5]))
            self.bestparams = self.cleanarr[mask][0]


        return
                                    
                                    
예제 #7
0
class SpectraViewWidget(QtGui.QWidget):
    def __init__(self,
                 warr,
                 farr,
                 snarr,
                 name='',
                 y1=1010,
                 y2=1030,
                 hmin=150,
                 wmin=400,
                 smooth=5,
                 parent=None):
        super(SpectraViewWidget, self).__init__(parent)

        self.y1 = y1
        self.y2 = y2
        self.smooth = smooth
        self.name = name

        #set up the arc display
        self.arcfigure = MplCanvas()

        # Add central axes instance
        self.axes = self.arcfigure.figure.add_subplot(111)

        #set up the variables
        self.loaddata(warr, farr, snarr, name)

        #force a re-draw
        self.redraw_canvas()

        # Add navigation toolbars for each widget to enable zooming
        self.toolbar = NavigationToolbar2QTAgg(self.arcfigure, self)

        #set up the information panel
        self.infopanel = QtGui.QWidget()

        #add the name of the file
        self.NameLabel = QtGui.QLabel("Filename:")
        self.NameLabel.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Raised)
        self.NameValueLabel = QtGui.QLabel(self.name)
        self.NameValueLabel.setFrameStyle(QtGui.QFrame.Panel
                                          | QtGui.QFrame.Sunken)

        #add extraction window

        self.y1Label = QtGui.QLabel("y1:")
        self.y1Label.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Raised)
        self.y1ValueLabel = QtGui.QLineEdit(str(self.y1))
        self.y2Label = QtGui.QLabel("y2:")
        self.y2Label.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Raised)
        self.y2ValueLabel = QtGui.QLineEdit(str(self.y2))
        self.apButton = QtGui.QPushButton('Extract')
        self.apButton.clicked.connect(self.extractspectra)

        #add default button
        self.defaultBox = QtGui.QCheckBox('Use values as default')
        self.defaultBox.stateChanged.connect(self.updatedefaults)

        #add smoothing
        self.smoothLabel = QtGui.QLabel("Smooth")
        self.smoothLabel.setFrameStyle(QtGui.QFrame.Panel
                                       | QtGui.QFrame.Raised)
        self.smoothValueLabel = QtGui.QLineEdit(str(self.smooth))
        self.smoothValueLabel.textChanged.connect(self.updatesmooth)

        #set up the info panel layout
        infoLayout = QtGui.QGridLayout(self.infopanel)
        infoLayout.addWidget(self.NameLabel, 0, 0, 1, 1)
        infoLayout.addWidget(self.NameValueLabel, 0, 1, 1, 5)
        infoLayout.addWidget(self.y1Label, 1, 0, 1, 1)
        infoLayout.addWidget(self.y1ValueLabel, 1, 1, 1, 1)
        infoLayout.addWidget(self.y2Label, 1, 2, 1, 1)
        infoLayout.addWidget(self.y2ValueLabel, 1, 3, 1, 1)
        infoLayout.addWidget(self.apButton, 1, 4, 1, 1)
        infoLayout.addWidget(self.defaultBox, 2, 0, 1, 2)
        infoLayout.addWidget(self.smoothLabel, 2, 2, 1, 1)
        infoLayout.addWidget(self.smoothValueLabel, 2, 3, 1, 1)

        # Set up the layout
        mainLayout = QtGui.QVBoxLayout()
        mainLayout.addWidget(self.arcfigure)
        mainLayout.addWidget(self.toolbar)
        mainLayout.addWidget(self.infopanel)
        self.setLayout(mainLayout)

    def updatedefaults(self):
        print self.defaultBox.checkState()
        return

    def updatesmooth(self):
        try:
            self.smooth = int(self.smoothValueLabel.text())
        except ValueError:
            return
        print self.smooth
        self.redraw_canvas()

    def updatename(self, name):
        self.name = name
        self.NameValueLabel.setText(self.name)
        print self.name

    def updaterange(self, y1, y2):
        self.y1 = y1
        self.y2 = y2
        self.y1ValueLabel.setText(str(self.y1))
        self.y2ValueLabel.setText(str(self.y2))

    def extractspectra(self):
        y1 = int(self.y1ValueLabel.text())
        y2 = int(self.y2ValueLabel.text())
        print self.name
        self.emit(QtCore.SIGNAL("updateextract(int, int)"), y1, y2)

    def loaddata(self, warr, farr, snarr, name=''):
        print "Loading data"
        self.warr = warr
        self.farr = farr
        self.snarr = snarr
        self.name = name
        return

    def plotSpectra(self):
        if self.smooth > 0 and self.farr is not None:
            farr = np.convolve(self.farr, np.ones(self.smooth),
                               mode='same') / self.smooth
        else:
            farr = self.farr
        self.splot = self.axes.plot(self.warr,
                                    farr,
                                    linewidth=0.5,
                                    linestyle='-',
                                    marker='None',
                                    color='b')

    def redraw_canvas(self, keepzoom=False):
        if keepzoom:
            # Store current zoom level
            xmin, xmax = self.axes.get_xlim()
            ymin, ymax = self.axes.get_ylim()

        # Clear plot
        self.axes.clear()

        # Draw image
        self.plotSpectra()

        # Restore zoom level
        if keepzoom:
            self.axes.set_xlim((self.xmin, self.xmax))
            self.axes.set_ylim((self.ymin, self.ymax))

        # Force redraw
        self.arcfigure.draw()
예제 #8
0
class SlotViewWindow(QtGui.QMainWindow):
   """Main application window."""

   def __init__(self, struct, pid, tflux, cflux, ratio, time, phottype, sleep,  
                tx, ty, cx, cy, r, br1, br2, naxis1, naxis2, sigdet, contpix, driftlimit):
        """Default constructor."""
        maxcolumn=7
        self.struct = struct
        self.infile=struct._HDUList__file.name
        self.name=self.struct[0].header['OBJECT']
        self.pid=pid
        self.dtime=time.copy()
        self.tflux=tflux
        self.cflux=cflux
        self.ratio=ratio
        self.min_xlim=10
        self.radius=r['comparison']
        self.r=r
        self.br1=br1
        self.br2=br2
        self.tx=tx
        self.ty=ty
        self.cx=cx
        self.cy=cy
        self.phottype=phottype
        self.naxis1=naxis1
        self.naxis2=naxis2
        self.sigdet=sigdet
        self.contpix=contpix
        self.driftlimit=driftlimit
        self.niter=5
        self.sigback=5
        self.fft=False
        self.stopplay=False
        self.sleep=sleep
        self.zbox=[]
        self.npoint=4
        self.id=0
        self.nframes=len(self.struct)
        self.header=self.struct[int(self.pid[self.id])].header
        self.goodframes=self.dtime*0+1
        if self.phottype=='circular': self.npoint=24


        # Setup widget
        QtGui.QMainWindow.__init__(self)

        # Set main widget
        self.main = QtGui.QWidget(self)

        # Set window title
        self.setWindowTitle("SlotView %s" % self.infile)

        #set up the different pages
        self.slotPage=QtGui.QWidget()
        
        #set up the differen panels
        self.set_optionpanel()
        self.set_imagepanel()
        self.set_controlpanel()
        self.set_plotpanel()
        self.set_infopanel()

        # Set up the layout
        slotLayout = QtGui.QVBoxLayout(self.slotPage)
        slotLayout.addWidget(self.plotpanel)
        slotLayout.addWidget(self.optipanel)
        slotLayout.addWidget(self.imdisplay)
        slotLayout.addWidget(self.contpanel)
        slotLayout.addWidget(self.infopanel)


        #create the tabs
        #self.tabWidget=QtGui.QTabWidget()
        #self.tabWidget.addTab(self.slotPage, 'Slot')
 
        #layout the widgets
        mainLayout = QtGui.QVBoxLayout(self.main)
        mainLayout.addWidget(self.slotPage)
        #mainLayout.addWidget(self.tabWidget)
        #self.setLayout(mainLayout)


        # Set focus to main widget
        self.main.setFocus()

        # Set the main widget as the central widget
        self.setCentralWidget(self.main)

        # Destroy widget on close
        self.setAttribute(QtCore.Qt.WA_DeleteOnClose)

        # Close when config dialog is closed
        self.connect(self.main, QtCore.SIGNAL('keyPressEvent'), self.keyPressEvent)
        #self.connect(self.conf, QtCore.SIGNAL('destroyed()'), self, QtCore.SLOT('close()'))
        #self.connect(self.tabWidget, QtCore.SIGNAL('currentChanged(int)'), self.currentChanged)
        #self.connect(self.imagePage, QtCore.SIGNAL('regionChange(int,int)'), self.regionChange)
        #self.connect(self.imagePage, QtCore.SIGNAL('runauto(int, int, int)'), self.runauto)

   def keyPressEvent(self, event):
       #print "Key Pressed:", event.key()
       self.keyEvents(str(event.text()))

   def keyEvents(self, key, x=None, y=None):
       if key=='?':
           self.help()
       if key=='q':
           self.close()
       if key=='d':
           self.goodframes[self.id] = 0
           self.updatepage()
       if key=='u':
           self.goodframes[self.id] = 1
       if key=='p':
           self.redophot(self.id)
           self.updatedataplot()
       if key=='P':
           self.thread=QtCore.QThread()
           self.thread.run=self.newphot
           self.thread.start()
       if key=='t' and x is not None and y is not None:
           tr=self.radius
           imarr=self.struct[int(self.pid[self.id])].data
           timage, tx, ty  = st.calcdrift(imarr, x, y, tr, self.naxis1, self.naxis2)
           if tx >= 0 and ty >= 0:
                self.tx[self.id]=tx
                self.ty[self.id]=ty
           self.updatepage()
       if key=='c' and x is not None and y is not None:
           r=self.radius
           imarr=self.struct[int(self.pid[self.id])].data
           cimage, cx, cy  = st.calcdrift(imarr, x, y, r, self.naxis1, self.naxis2)
           if cx >= 0 and cy >= 0:
                self.cx[self.id]=cx
                self.cy[self.id]=cy
           self.updatepage()


   def onKeyPress(self, event):
       self.keyEvents(event.key, event.xdata, event.ydata)

   def onButtonPress(self, event):
       if event.button==2:
           self.lcpickframe(event)

   def currentChanged(self, event):
       #print event
       pass

   def redophot(self, i):
       """Redo the photometry for a single frame"""
       self.id=i
       x={}
       y={}
       x['target']=self.tx[self.id]
       y['target']=self.ty[self.id]
       x['comparison']=self.cx[self.id]
       y['comparison']=self.cy[self.id]
       image=self.struct[int(self.pid[self.id])].data

       #these will need to be changed
       gain=1
       rdnoise=1
       verbose=False

       try:
           tflux, tflux_err, cflux, cflux_err, ratio, ratio_err = \
               st.dophot(self. phottype, image, x, y, self.r, self.br1, self.br2,  \
               gain, rdnoise, self.naxis1, self.naxis2)
       except:
           msg="SLOTVIEW--ERROR:  Could not measure photometry in frame %i" % i
           raise SaltError(msg)
       
       self.tflux[self.id]=tflux
       self.cflux[self.id]=cflux
       self.ratio[self.id]=ratio

   def newphot(self):
       self.redophot(self.id)
       i=self.id+1
       self.stopplay=True
       while i < self.nframes-1 and self.stopplay:
           self.id=i
           imarr=self.struct[int(self.pid[self.id])].data
           carray, fx,fy = st.finddrift(imarr, self.cx[self.id-1], self.cy[self.id-1], self.radius,  \
                self.naxis1, self.naxis2, self.sigdet, self.contpix, self.sigback, self.driftlimit, self.niter)
           if 0 <= fx < self.naxis1 and 0 <= fy < self.naxis2:
               dx=self.cx[i-1]-fx
               dy=self.cy[i-1]-fy
               self.cx[i]=fx
               self.cy[i]=fy
               self.tx[i]=self.tx[i-1]-dx
               self.ty[i]=self.ty[i-1]-dy
           self.redophot(i)
           i = i+1
       print('Stopped at', i)
       self.updatepage()


   def changefluxplot(self, event):
       self.fluxplot=event
       self.updatedataplot(save_zoom=False)

   def changetstarplot(self, event):
       self.tstarplot=event
       self.updatedataplot(save_zoom=False)

   def changecstarplot(self, event):
       self.cstarplot=event
       self.updatedataplot(save_zoom=False)

   def plotlightcurve(self):
       """Plot the light curve"""
 
       #cut the data
       self.make_lcdata()

       #make the figure
       self.light_plot=self.lccanvas.figure.add_axes([0.10,0.15,0.8,0.80], autoscale_on=False, adjustable='datalim'  )
       self.light_plot.hold(True)

       #plot the curve
       self.lightcurve,=self.light_plot.plot(self.tarr,self.rarr,linewidth=0.5,linestyle='-',marker='',color='b')
       if self.fluxplot:
           self.lightcurve.set_visible(True)
       else:
           self.lightcurve.set_visible(False)

       #plot the flux curve for star 1
       self.tstarcurve,=self.light_plot.plot(self.tarr,self.tfarr,linewidth=0.5,linestyle='-',marker='',color='y')
       if  self.tstarplot:
           self.tstarcurve.set_visible(True)
       else:
           self.tstarcurve.set_visible(False)

       #plot the flux curve for star 1
       self.cstarcurve,=self.light_plot.plot(self.tarr,self.cfarr,linewidth=0.5,linestyle='-',marker='',color='g')
       if self.cstarplot:
           self.cstarcurve.set_visible(True)
       else:
           self.cstarcurve.set_visible(False)

       #plot a point which matches the time
       self.ptime=self.dtime[self.id]
       self.pratio=self.ratio[self.id]
       self.light_point,=self.light_plot.plot(np.asarray([self.ptime]), np.asarray([self.pratio]), linestyle='', marker='o', mec='#FF0000', mfc='#FF0000')


       self.find_lclimits()
       ylabel='Star1/Star2'
       self.light_plot.set_ylabel(ylabel)
       self.light_plot.set_xlabel('Time (s)')
 
   def make_lcdata(self):
       #cut the data
       mask = (self.goodframes>0)
       self.tarr=np.compress(mask,self.dtime)
       self.rarr=np.compress(mask,self.ratio)
       self.tfarr=np.compress(mask,self.tflux)
       self.cfarr=np.compress(mask,self.cflux)

   def find_lclimits(self, save_zoom=False):
       """Find the limits on the Light Curve plot"""
       if save_zoom: return
       self.lcx1=self.tarr.min()
       self.lcx2=self.tarr.max()
       self.light_plot.set_xlim(self.lcx1, self.lcx2)
       #determine the minimum y value based on what plots are turned on
       if self.fluxplot:
           self.lcy1=self.rarr.min()
           self.lcy2=self.rarr.max()
       if self.tstarplot:
           self.lcy1=self.tfarr.min()
           self.lcy2=self.tfarr.max()
       if self.cstarplot:
           self.lcy1=self.cfarr.min()
           self.lcy2=self.cfarr.max()
       if self.fluxplot and self.tstarplot and self.cstarplot:
           self.lcy1=min(self.rarr.min(), self.tfarr.min(), self.cfarr.min())
           self.lcy2=max(self.rarr.max(), self.tfarr.max(), self.cfarr.max())
       if self.tstarplot and self.cstarplot and not self.fluxplot:
           self.lcy1=min(self.tfarr.min(), self.cfarr.min())
           self.lcy2=max(self.tfarr.max(), self.cfarr.max())
       if self.tstarplot and not self.cstarplot and  self.fluxplot:
           self.lcy1=min(self.tfarr.min(), self.rarr.min())
           self.lcy2=max(self.tfarr.max(), self.rarr.max())
       if not self.tstarplot and self.cstarplot and self.fluxplot:
           self.lcy1=min(self.rarr.min(), self.cfarr.min())
           self.lcy2=max(self.rarr.max(), self.cfarr.max())
           
       self.light_plot.set_ylim(self.lcy1, self.lcy2)

   def lcpickframe(self, event):
       self.set_id(event.xdata)
       self.updatepage()

   def set_id(self, t):
       """Given a time, set the object id"""
       self.id=np.abs(self.dtime-t).argmin()
           

   def set_plotpanel(self, hmin=250):
       #set up the control panel
       self.plotpanel=QtGui.QWidget()

       self.lccanvas=MplCanvas()
       #self.lccanvas=FigureCanvasQTAgg(self.lcfigure)
       self.plotlightcurve()
       #add the actions
       self.lccanvas.mpl_connect('button_press_event',self.onButtonPress)

       # Add navigation toolbars for each widget to enable zooming
       self.toolbar=NavigationToolbar2QTAgg(self.lccanvas,self)

       # Set up the layout
       plotLayout = QtGui.QVBoxLayout(self.plotpanel)
       plotLayout.addWidget(self.lccanvas)
       plotLayout.addWidget(self.toolbar)

   def set_optionpanel(self):
       #set up the control panel
       self.optipanel=QtGui.QWidget()

       #set up the options
       self.fluxplot=True
       self.tstarplot=False
       self.cstarplot=False
       self.fluxButton = QtGui.QCheckBox("Flux Ratio")
       self.fluxButton.setChecked(self.fluxplot)
       self.fluxButton.clicked.connect(self.changefluxplot)
       self.tstarButton = QtGui.QCheckBox("Target")
       self.tstarButton.clicked.connect(self.changetstarplot)
       self.cstarButton = QtGui.QCheckBox("Comparison")
       self.cstarButton.clicked.connect(self.changecstarplot)

       # Set up the layout
       optiLayout=QtGui.QGridLayout(self.optipanel)
       optiLayout.addWidget(self.fluxButton, 0, 0, 1,1)
       optiLayout.addWidget(self.tstarButton, 0, 1, 1,1)
       optiLayout.addWidget(self.cstarButton, 0, 2, 1,1)
       #optiLayout.addWidget(self.imagtoolbar)

   def set_imagepanel(self, name=None, cmap='gray', scale='zscale', contrast=0.1):
       """set up the Image Panel"""
       hmin=150
       wmin=400
       #set up the control panel
       self.imagpanel=QtGui.QWidget()

       #hmin=wmin*self.naxis2/self.naxis1
       #print self.naxis1, self.naxis2, wmin, hmin

       # Add FITS display widget with mouse interaction and overplotting
       self.imdisplay = ImageDisplay()
       #self.imdisplay.setMinimumWidth(wmin)

       # Set colormap
       self.imdisplay.setColormap(cmap)

       # Set scale mode for dynamic range
       imarr=self.struct[int(self.pid[self.id])].data
       self.imdisplay.scale=scale
       self.imdisplay.contrast=contrast
       self.imdisplay.aspect='auto'
       self.imdisplay.loadImage(imarr)
       #self.imdisplay.drawImage()
       hmin=self.imdisplay.width()*self.naxis2/self.naxis1
       self.imdisplay.setMaximumHeight(hmin)
       self.imdisplay.setMinimumHeight(hmin)

       #add the rectangles
       self.add_mark(self.tx[self.id], self.ty[self.id], 'target',color='b', lw=2)
       self.add_mark(self.cx[self.id], self.cy[self.id], 'comparison',color='g', lw=2)
       self.imdisplay.redraw_canvas()
       self.imdisplay.axes.set_xticklabels([])
       self.imdisplay.axes.set_yticklabels([])

       self.imdisplay.connectMatplotlibMouseMotion()
       self.imdisplay.mpl_connect('button_press_event', self.onButtonPress)
       self.imdisplay.mpl_connect('key_press_event', self.onKeyPress)


       # Add navigation toolbars for each widget to enable zooming
       self.imagtoolbar=NavigationToolbar2QTAgg(self.imdisplay,self)

       # Set up the layout
       imagLayout = QtGui.QVBoxLayout(self.imagpanel)
       #imagLayout.addWidget(self.imdisplay)
       imagLayout.addWidget(MplCanvas())
       imagLayout.addWidget(self.imagtoolbar)

   def add_mark(self, x1, y1, label, color='g', lw=2):
       """Add the rectangle for the object"""
       self.imdisplay.removePatch(label)
       r1=self.r[label]
       rect=self.imdisplay.addSquare(label, x1, y1, r1, color=color, lw=lw)

   def set_controlpanel(self):
       """set up the Control Panel"""
       #set up the control panel
       self.contpanel=QtGui.QWidget()

       #set up the buttons
       self.frevButton = QtGui.QPushButton("<<")
       self.frevButton.clicked.connect(self.freverse)
       self.revButton = QtGui.QPushButton("<")
       self.revButton.clicked.connect(self.reverse)
       self.rev1Button = QtGui.QPushButton("-")
       self.rev1Button.clicked.connect(self.revone)
       self.stopButton = QtGui.QPushButton("Stop")
       self.stopButton.clicked.connect(self.stop)
       self.play1Button = QtGui.QPushButton("+")
       self.play1Button.clicked.connect(self.playone)
       self.playButton = QtGui.QPushButton(">")
       self.playButton.clicked.connect(self.play)
       self.fplayButton = QtGui.QPushButton(">>")
       self.fplayButton.clicked.connect(self.fplay)


       #set up the info panel layout
       contLayout=QtGui.QGridLayout(self.contpanel)
       #contLayout.addWidget(self.frevButton, 0, 0, 1, 1)
       #contLayout.addWidget(self.revButton,  0, 1, 1, 1)
       contLayout.addWidget(self.rev1Button, 0, 2, 1, 1)
       contLayout.addWidget(self.stopButton, 0, 3, 1, 1)
       contLayout.addWidget(self.play1Button,0, 4, 1, 1)
       #contLayout.addWidget(self.playButton, 0, 5, 1, 1)
       #contLayout.addWidget(self.fplayButton,0, 6, 1, 1)

   def set_infopanel(self):
       """Set up the information panel"""

       #set up the information panel
       self.infopanel=QtGui.QWidget()
        
       #add the name of the file
       self.IDValueLabel = QtGui.QLabel("%i" % self.pid[self.id])
       self.IDValueLabel.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Sunken )
       self.NameValueLabel = QtGui.QLabel("%s" % self.name)
       self.NameValueLabel.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Sunken )
       self.timeValueLabel = QtGui.QLabel("%s" % self.get_time())
       self.timeValueLabel.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Sunken )
  
       #set up the info panel layout
       infoLayout=QtGui.QGridLayout(self.infopanel)
       infoLayout.addWidget(self.IDValueLabel, 0, 0, 1, 1)
       infoLayout.addWidget(self.NameValueLabel, 0, 1, 1, 1)
       infoLayout.addWidget(self.timeValueLabel, 0, 2, 1, 1)
   
   def get_time(self):
       #set the time
       try:
            utime=self.struct[int(self.pid[self.id])].header['UTC-OBS']
       except:
            utime=''
       return utime


   def help(self):
        """Print the help message and the key-bindings available to the user"""
        helpmessage="""
    The following commands are available to the user:
    ? - Print this information           q - quit the viewer
    n - Move to the next image           b - move back an image
    D - Delete this image                u - undelete this image
    p - Perform photometry on this image
    P - Perform photometry starting at this image
    stop button-Stop photometry or display
    reset button-Reset the light curve plot
    Middle Click-Display image corresponding to this time
        """
        print(helpmessage)
        return

   def stop(self):
        self.stopplay=False
        print(self.stopplay)


   def playone(self):
        stopid = self.nframes-2
        if self.id < (stopid): self.id=self.id+1
        self.updatepage()


   def play(self):
        self.stopplay=True
        stopid = self.nframes-2
        while self.stopplay and self.id < stopid:
            self.id = self.id+1
            time.sleep(self.sleep)
            self.updatepage()

   def fplay(self):
        self.stopplay=True
        stopid = self.nframes-2
        while self.stopplay and self.id < stopid:
            self.id = self.id+1
            self.updatepage()

   def revone(self):
        if self.id > 0: self.id=self.id-1
        self.updatepage()


   def reverse(self):
        self.stopplay=True
        while self.stopplay and self.id > 0:
            self.id = self.id-1
            time.sleep(self.sleep)
            self.updatepage()

   def freverse(self):
        self.stopplay=True
        while self.stopplay and self.id > 0:
            self.id = self.id-1
            self.updatepage()

    
   def updatepage(self):
       """Update all the values on the page that need updating"""
       self.IDValueLabel.setText("%i" % self.pid[self.id])
       self.timeValueLabel.setText("%s" % self.get_time())

       #update the image
       imarr=self.struct[int(self.pid[self.id])].data
       self.imdisplay.loadImage(imarr)
       
       #update the boxes
       self.add_mark(self.tx[self.id], self.ty[self.id], 'target',color='b', lw=2)
       self.add_mark(self.cx[self.id], self.cy[self.id], 'comparison',color='g', lw=2)
       self.imdisplay.redraw_canvas()
       self.imdisplay.axes.set_xticklabels([])
       self.imdisplay.axes.set_yticklabels([])
 
       self.updatedataplot()

   def updatedataplot(self, save_zoom=True):
       """Update the data plot for changes in the options
       """
       #redraw the lines
       self.make_lcdata()
       self.lightcurve.set_xdata(self.tarr)
       self.lightcurve.set_ydata(self.rarr)
       self.tstarcurve.set_xdata(self.tarr)
       self.tstarcurve.set_ydata(self.tfarr)
       self.cstarcurve.set_xdata(self.tarr)
       self.cstarcurve.set_ydata(self.cfarr)
 
       #move the point
       self.light_point.set_xdata([self.dtime[self.id]])
       self.light_point.set_ydata([self.ratio[self.id]])

       if self.fluxplot:
           self.lightcurve.set_visible(True)
       else:
           self.lightcurve.set_visible(False)
       #plot the flux curve for star 1
       if  self.tstarplot:
           self.tstarcurve.set_visible(True)
       else:
           self.tstarcurve.set_visible(False)

       #plot the flux curve for star 1
       if self.cstarplot:
           self.cstarcurve.set_visible(True)
       else:
           self.cstarcurve.set_visible(False)
       self.find_lclimits(save_zoom=save_zoom)
       self.lccanvas.draw()
예제 #9
0
class ArcDisplay(QtGui.QWidget):

    """Class for displaying Arc Spectra using matplotlib and embedded in a Qt 4 GUI.
    """

    def __init__(self, xarr, farr, slines, sfluxes, ws, xp=[], wp=[], mdiff=20, specarr=None,
                 res=2.0, dres=0.1, dc=20, ndstep=20, sigma=5, smooth=0, niter=5, method='MatchZero',
                 textcolor='green', log=None, verbose=True):
        """Default constructor."""
        QtGui.QWidget.__init__(self)

        # Initialize base class
        self.arcfigure = MplCanvas()
        self.errfigure = MplCanvas()

        # Add central axes instance
        self.axes = self.arcfigure.figure.add_subplot(111)
        self.erraxes = self.errfigure.figure.add_subplot(111)

        # Connect mouse events
        self.arcfigure.connectMatplotlibMouseMotion()
        self.arcfigure.mpl_connect('button_press_event', self.onButtonPress)
        self.arcfigure.mpl_connect('key_press_event', self.onKeyPress)

        self.errfigure.connectMatplotlibMouseMotion()
        self.errfigure.mpl_connect('button_press_event', self.onButtonPress)
        self.errfigure.mpl_connect('key_press_event', self.onKeyPress)

        # load the data
        self.xarr = xarr
        self.farr = farr
        self.slines = slines
        self.sfluxes = sfluxes
        self.ws = ws
        self.orig_ws = copy.deepcopy(ws)
        self.specarr = specarr
        self.mdiff = mdiff
        self.sigma = sigma
        self.niter = int(niter)
        self.smooth = int(smooth)
        self.res = res
        self.dres = dres
        self.dc = dc
        self.sections = 6
        self.ndstep = ndstep
        self.method = method
        self.textcolor = textcolor
        self.log = log
        self.verbose = True

        # if asked, smooth the data
        if self.smooth > 0:
            self.farr = st.smooth_spectra(
                self.xarr,
                self.farr,
                sigma=self.smooth)

        self.xp = xp
        self.wp = wp

        self.rms = res

        # set up the artificial spectra
        self.spectrum = Spectrum.Spectrum(
            self.slines,
            self.sfluxes,
            dw=self.dres,
            stype='line',
            sigma=self.res)
        self.swarr = self.spectrum.wavelength
        self.sfarr = self.spectrum.flux * \
            self.farr.max() / self.spectrum.flux.max()

        # set up the wavelength solution
        if self.ws.function == 'line':
            self.ws.set_xarr(self.xarr)
            self.ws.farr = self.farr
            self.ws.spectrum = self.spectrum

        # set up the list of deleted points
        self.dxp = []
        self.dwp = []

        # set up other variables
        self.isArt = False
        self.isFeature = False

        # Set display parameters
        self.xmin = self.xarr.min()
        self.xmax = self.xarr.max()
        self.ymin = self.farr.min()
        self.ymax = self.farr.max()

    def help(self):
        helpoutput = """
 ? - Print this file     q - Quit the program
 c - centroid on line    x - print the current position
 a - Display spectrum    l - display features
 b - identify features   f - fit solution
 p - print features      P - print solution
 z - zeropoint fit       Z - find zeropoint and dispersion
 r - redraw spectrum     R - reset values
 e - add closest line    L - show detected peaks
 d - delete feature      u - undelete feature
 X - fit full X-cor
 """
        print helpoutput

    def onKeyPress(self, event):
        """Emit signal on key press"""
        if event.key == '?':
            # return the help file
            self.help()
        elif event.key == 'q':
            # exit the task
            self.emit(QtCore.SIGNAL("quit()"))
        elif event.key == 'c':
            # return the centroid
            if event.xdata:
                self.log.message(str(event.xdata), with_header=False)
                cx = st.mcentroid(
                    self.xarr,
                    self.farr,
                    xc=event.xdata,
                    xdiff=self.mdiff)
                self.emit(QtCore.SIGNAL("updatex(float)"), cx)
        elif event.key == 'x':
            # return the x position
            if event.xdata:
                self.log.message(str(event.xdata), with_header=False)
                self.emit(QtCore.SIGNAL("updatex(float)"), event.xdata)
        elif event.key == 'R':
            # reset the fit
            self.reset()
        elif event.key == 'f':
            # find the fit
            self.findfit()
            self.emit(QtCore.SIGNAL("fitUpdate()"))
        elif event.key == 'b':
            # auto-idenitfy features
            self.isFeature = True
            self.findfeatures()
        elif event.key == 'z':
            # Assume the solution is correct and find the zeropoint
            # that best matches it from cross correllation
            self.findzp()
        elif event.key == 'Z':
            # Assume the solution is correct and find the zeropoint
            # that best matches it from cross correllation
            self.findzpd()
        elif event.key == 'X':
            # Assume the solution is almost correct
            # Fit the full solution using the cross correlation coefficient
            self.findxcorfit()

        elif event.key == 'e':
            # find closest feature from existing fit and line list
            # and match it
            self.addclosestline(event.xdata)
        elif event.key == 'i':
            # reset identified features
            pass
        elif event.key == 't':
            # reset identified features
            self.isFeature = True
            self.testfeatures()
        elif event.key == 'l':
            # plot the features from existing list
            if self.isFeature:
                self.isFeature = False
                self.redraw_canvas()
            else:
                self.isFeature = True
                self.plotFeatures()
                self.redraw_canvas()
        elif event.key == 'L':
            # plot the sources that are detected
            self.plotDetections()
        elif event.key == 'p':
            # print information about features
            for i in range(len(self.xp)):
                print self.xp[i], self.wp[i]
        elif event.key == 'P':
            # print information about features
            print self.ws.coef
        elif event.key == 'r':
            # redraw graph
            self.redraw_canvas()
        elif event.key == 'a':
            # draw artificial spectrum
            self.isArt = not self.isArt
            self.redraw_canvas()
        elif event.key == 'd':
            # Delete feature
            save = False
            y = None
            if event.canvas == self.errfigure:
                y = event.ydata
                save = True
            self.deletepoints(event.xdata, y=y, save=save)
            self.redraw_canvas(keepzoom=True)
        elif event.key == 'u':
            # undelete
            self.undeletepoints(event.xdata, y=event.ydata)
            self.redraw_canvas(keepzoom=True)
        elif event.key:
            self.emit(QtCore.SIGNAL("keyPressEvent(string)"), event.key)

    def onButtonPress(self, event):
        """Emit signal on selecting valid image position."""

        if event.xdata and event.ydata:
            self.emit(QtCore.SIGNAL("positionSelected(float, float)"),
                      float(event.xdata), float(event.ydata))

    def plotArc(self):
        """Draw image to canvas."""

        # plot the spectra
        self.spcurve, = self.axes.plot(
            self.xarr, self.farr, linewidth=0.5, linestyle='-', marker='None', color='b')

    def plotArt(self):
        """Plot the artificial spectrum"""
        self.isArt = True
        warr = self.ws.value(self.xarr)
        asfarr = st.interpolate(
            warr,
            self.swarr,
            self.sfarr,
            left=0.0,
            right=0.0)
        asfarr = asfarr * self.farr.max() / asfarr.max()
        self.fpcurve, = self.axes.plot(self.xarr, asfarr, linewidth=0.5, linestyle='-',
                                       marker='None', color='r')

    def plotDetections(self):
        """Plot the lines that are detected"""
        xp, xf = st.findpoints(
            self.xarr, self.farr, self.sigma, self.niter, sections=self.sections)
        print xp
        self.axes.plot(xp, xf, ls='', marker='|', ms=20, color='#000000')

    def plotFeatures(self):
        """Plot features identified in the line list"""
        fl = np.array(self.xp) * 0.0 + 0.25 * self.farr.max()
        self.splines = self.axes.plot(
            self.xp,
            fl,
            ls='',
            marker='|',
            ms=20,
            color=self.textcolor)
        # set up the text position
        tsize = 0.83
        self.ymin, self.ymax = self.axes.get_ylim()
        ppp = (self.ymax - self.ymin) / (self.arcfigure.figure.get_figheight()
                                         * self.arcfigure.figure.get_dpi())
        f = self.ymax - 10 * tsize * ppp
        for x, w in zip(self.xp, self.wp):
            w = '%6.2f' % float(w)
            self.axes.text(
                x,
                f,
                w,
                size='small',
                rotation='vertical',
                color=self.textcolor)

    def plotErr(self):
        """Draw image to canvas."""
        if self.xp and self.wp:
            # plot the spectra
            w = self.ws.value(np.array(self.xp))
            self.errcurve, = self.erraxes.plot(
                self.xp, self.wp - w, linewidth=0.5, linestyle='', marker='o', color='b')
        if self.dxp and self.dwp:
            # plot the spectra
            dw = self.ws.value(np.array(self.dxp))
            self.delerrcurve, = self.erraxes.plot(
                self.dxp, self.dwp - dw, linewidth=0.5, linestyle='', marker='x', color='b')

    def set_wdiff(self):
        """Derive a value for wdiff"""
        try:
            self.wdiff = self.mdiff * self.ws.coef[1]
        except:
            self.wdiff = self.mdiff

    def testfeatures(self):
        """Run the test matching algorithm"""
        self.set_wdiff()
        res = max(self.res * 0.25, 2)
        xp, wp = st.crosslinematch(self.xarr, self.farr, self.slines, self.sfluxes, self.ws,
                                   res=res, mdiff=self.mdiff, wdiff=20, sigma=self.sigma,
                                   niter=self.niter, sections=self.sections)
        for x, w in zip(xp, wp):
            if w not in self.wp and w > -1:
                self.xp.append(x)
                self.wp.append(w)
        self.plotFeatures()
        self.redraw_canvas()

    def findfeatures(self):
        """Given a set of features, find other features that might
           correspond to those features
        """
        self.set_wdiff()

        # xp, wp=st.findfeatures(self.xarr, self.farr, self.slines, self.sfluxes,
        # self.ws, mdiff=self.mdiff, wdiff=self.wdiff, sigma=self.sigma,
        # niter=self.niter, sections=3)
        xp, wp = st.crosslinematch(self.xarr, self.farr, self.slines, self.sfluxes, self.ws,
                                   res=self.res, mdiff=self.mdiff, wdiff=20,
                                   sections=self.sections, sigma=self.sigma, niter=self.niter)
        for x, w in zip(xp, wp):
            if w not in self.wp and w > -1:
                self.xp.append(x)
                self.wp.append(w)
        # for i in range(len(self.xp)): print self.xp[i], self.wp[i]
        # print
        self.plotFeatures()
        self.redraw_canvas()

    def addclosestline(self, x):
        """Find the closes line to the centroided position and
           add it
        """
        cx = st.mcentroid(self.xarr, self.farr, xc=x, xdiff=self.mdiff)
        w = self.ws.value(cx)
        d = abs(self.slines - w)
        w = self.slines[d.argmin()]

        self.xp.append(x)
        self.wp.append(w)
        self.plotFeatures()
        self.redraw_canvas()

    def findzp(self):
        """Find the zeropoint for the source and plot of the new value
        """
        dc = 0.5 * self.rms * self.ndstep
        self.ws = st.findzeropoint(self.xarr, self.farr, self.swarr, self.sfarr,
                                   self.ws, dc=dc, ndstep=self.ndstep, inttype='interp')
        self.plotArt()
        self.redraw_canvas()

    def findzpd(self):
        """Find the zeropoint and dispersion for the source and plot of the new value
        """
        dc = 0.5 * self.rms * self.ndstep
        # fixed at 0.1 of the dispersion
        dd = 0.1 * self.ws.coef[1]

        # set upt he docef values
        dcoef = self.ws.coef * 0.0
        dcoef[0] = dc
        dcoef[1] = dd
        self.ws = st.findxcor(self.xarr, self.farr, self.swarr, self.sfarr, self.ws,
                              dcoef=dcoef, ndstep=self.ndstep, best=False, inttype='interp')
        self.plotArt()
        self.redraw_canvas()

    def findxcorfit(self):
        """Maximize the normalized correlation coefficient using the full wavelength solution.
        """
        self.ws = st.fitxcor(
            self.xarr,
            self.farr,
            self.swarr,
            self.sfarr,
            self.ws,
            interptype='interp')
        self.plotArt()
        self.redraw_canvas()

    def findfit(self):
        if len(self.xp) < self.ws.order:
            raise SALTSpecError(
                "Insufficient sources number of points for fit")
            return
        try:
            self.ws = st.findfit(
                np.array(
                    self.xp), np.array(
                    self.wp), ws=self.ws, thresh=self.ws.thresh)
        except SALTSpecError as e:
            self.log.warning(e)
            return

        del_list = []
        for i in range(len(self.ws.func.mask)):
            if self.ws.func.mask[i] == 0:
                self.deletepoints(self.ws.func.x[i], w=self.ws.func.y[i],
                                  save=True)
        self.rms = self.ws.sigma(self.ws.x_arr, self.ws.w_arr)
        self.redraw_canvas()

    def autoidentify(self, rstep=1, istart=None, nrows=1, oneline=True):
        """Run the autoidentify method for the current line"""
        # update the line list such that it is only the line list of selected
        # lines
        if self.wp:
            slines = np.array(self.wp)
            sfluxes = self.farr[self.xp]
            # sfluxes=np.zeros(len(slines))
            # for i in range(len(slines)):
            #    try:
            #       sfluxes[i]=self.sfluxes[self.slines==slines[i]][0]
            #    except:
            #       if sfluxes.mean()==0:
            #            sfluxes[i]=1
            #       else:
            #            sfluxes[i]=sfluxes.mean()

        else:
            slines = self.slines
            sfluxes = self.sfluxes

        iws = ai.AutoIdentify(self.xarr, self.specarr, slines, sfluxes, self.ws, farr=self.farr,
                              method=self.method, rstep=rstep, istart=istart, nrows=nrows,
                              res=self.res, dres=self.dres, mdiff=self.mdiff, sigma=self.sigma,
                              smooth=self.smooth, niter=self.niter, dc=self.dc, ndstep=self.ndstep,
                              oneline=oneline, log=self.log, verbose=self.verbose)
        if oneline:
            self.ws = iws
        else:
            return iws

    def addpoints(self, x, w):
        """Add points to the line list
        """
        if isinstance(x, list) and isinstance(w, list):
            self.xp.extend(x)
            self.wp.extend(w)
        else:
            self.xp.append(x)
            self.wp.append(w)

    def deletepoints(self, x, y=None, w=None, save=False):
        """ Delete points from the line list
        """
        dist = (np.array(self.xp) - x) ** 2

        # assumes you are using the error plot
        if y is not None:
            w = self.ws.value(np.array(self.xp))
            norm = self.xarr.max() / abs(self.wp - w).max()
            dist += norm * (self.wp - w - y) ** 2
            # print y, norm, dist.min()
            # print y, dist.min()
        elif w is not None:
            norm = self.xarr.max() / abs(self.wp - w).max()
            dist += norm * (self.wp - w)**2
        in_minw = dist.argmin()

        if save:
            self.dxp.append(self.xp[in_minw])
            self.dwp.append(self.wp[in_minw])
        self.xp.__delitem__(in_minw)
        self.wp.__delitem__(in_minw)

    def undeletepoints(self, x, y=None):
        """ Delete points from the line list
        """
        if len(self.dxp) < 1:
            return
        if len(self.dxp) == 1:
            self.xp.append(self.dxp[0])
            self.wp.append(self.dwp[0])
            self.dxp.__delitem__(0)
            self.dwp.__delitem__(0)
            return

        dist = (self.dxp - x) ** 2
        if y is not None:
            w = self.ws.value(np.array(self.dxp))
            # dist += (self.dwp-w-y)**2
        in_minw = dist.argmin()

        self.xp.append(self.dxp[in_minw])
        self.wp.append(self.dwp[in_minw])
        self.dxp.__delitem__(in_minw)
        self.dwp.__delitem__(in_minw)

        return

    def reset(self):
        self.ws = copy.deepcopy(self.orig_ws)
        self.redraw_canvas()

    def redraw_canvas(self, keepzoom=False):
        if keepzoom:
            # Store current zoom level
            xmin, xmax = self.axes.get_xlim()
            ymin, ymax = self.axes.get_ylim()

        # Clear plot
        self.axes.clear()

        # Draw image
        self.plotArc()

        # if necessary, redraw the features
        if self.isFeature:
            self.plotFeatures()

        # if necessary, draw the artificial spectrum
        if self.isArt:
            self.plotArt()

        # Restore zoom level
        if keepzoom:
            self.axes.set_xlim((self.xmin, self.xmax))
            self.axes.set_ylim((self.ymin, self.ymax))

        # Force redraw
        self.arcfigure.draw()

        self.err_redraw_canvas()

    def err_redraw_canvas(self, keepzoom=False):
        if keepzoom:
            # Store current zoom level
            xmin, xmax = self.erraxes.get_xlim()
            ymin, ymax = self.erraxes.get_ylim()
        else:
            self.xmin, self.xmax = self.axes.get_xlim()

        # Clear plot
        self.erraxes.clear()

        # Draw image
        self.plotErr()

        # Restore zoom level
        if keepzoom:
            self.erraxes.set_xlim((xmin, xmax))
            self.erraxes.set_ylim((ymin, ymax))
        else:
            self.erraxes.set_xlim((self.xmin, self.xmax))

        self.errfigure.draw()

        self.emit(QtCore.SIGNAL("fitUpdate()"))
예제 #10
0
class SpectraViewWidget(QtGui.QWidget):
   def __init__(self, warr, farr, snarr, name='', y1=1010, y2=1030, hmin=150, wmin=400, smooth=5, parent=None):
       super(SpectraViewWidget, self).__init__(parent)

       self.y1=y1
       self.y2=y2
       self.smooth = smooth
       self.name=name

       #set up the arc display 
       self.arcfigure=MplCanvas()

       # Add central axes instance
       self.axes = self.arcfigure.figure.add_subplot(111)

       #set up the variables
       self.loaddata(warr, farr, snarr, name)

       #force a re-draw
       self.redraw_canvas()

       # Add navigation toolbars for each widget to enable zooming
       self.toolbar=NavigationToolbar2QTAgg(self.arcfigure,self)

       #set up the information panel
       self.infopanel=QtGui.QWidget()

       #add the name of the file
       self.NameLabel = QtGui.QLabel("Filename:")
       self.NameLabel.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Raised )
       self.NameValueLabel = QtGui.QLabel(self.name)
       self.NameValueLabel.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Sunken )

       #add extraction window

       self.y1Label = QtGui.QLabel("y1:")
       self.y1Label.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Raised )
       self.y1ValueLabel = QtGui.QLineEdit(str(self.y1))
       self.y2Label = QtGui.QLabel("y2:")
       self.y2Label.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Raised )
       self.y2ValueLabel = QtGui.QLineEdit(str(self.y2))
       self.apButton = QtGui.QPushButton('Extract')
       self.apButton.clicked.connect(self.extractspectra)

       #add default button
       self.defaultBox = QtGui.QCheckBox('Use values as default')
       self.defaultBox.stateChanged.connect(self.updatedefaults)
 
       #add smoothing
       self.smoothLabel = QtGui.QLabel("Smooth")
       self.smoothLabel.setFrameStyle(QtGui.QFrame.Panel | QtGui.QFrame.Raised )
       self.smoothValueLabel = QtGui.QLineEdit(str(self.smooth))
       self.smoothValueLabel.textChanged.connect(self.updatesmooth)

       #set up the info panel layout
       infoLayout=QtGui.QGridLayout(self.infopanel)
       infoLayout.addWidget(self.NameLabel, 0, 0, 1, 1)
       infoLayout.addWidget(self.NameValueLabel, 0, 1, 1, 5)
       infoLayout.addWidget(self.y1Label, 1, 0, 1, 1)
       infoLayout.addWidget(self.y1ValueLabel, 1, 1, 1, 1)
       infoLayout.addWidget(self.y2Label, 1, 2, 1, 1)
       infoLayout.addWidget(self.y2ValueLabel, 1, 3, 1, 1)
       infoLayout.addWidget(self.apButton, 1, 4, 1, 1)
       infoLayout.addWidget(self.defaultBox, 2, 0, 1, 2)
       infoLayout.addWidget(self.smoothLabel, 2, 2, 1, 1)
       infoLayout.addWidget(self.smoothValueLabel, 2, 3, 1, 1)

       # Set up the layout
       mainLayout = QtGui.QVBoxLayout()
       mainLayout.addWidget(self.arcfigure)
       mainLayout.addWidget(self.toolbar)
       mainLayout.addWidget(self.infopanel)
       self.setLayout(mainLayout)

   def updatedefaults(self):
       print self.defaultBox.checkState()
       return

   def updatesmooth(self):
       try:
          self.smooth = int(self.smoothValueLabel.text())
       except ValueError:
          return
       print self.smooth
       self.redraw_canvas()
 
   def updatename(self, name):
       self.name=name
       self.NameValueLabel.setText(self.name)
       print self.name

   def updaterange(self, y1, y2):
       self.y1=y1
       self.y2=y2
       self.y1ValueLabel.setText(str(self.y1))
       self.y2ValueLabel.setText(str(self.y2))

   def extractspectra(self):
       y1=int(self.y1ValueLabel.text())
       y2=int(self.y2ValueLabel.text())
       print self.name
       self.emit(QtCore.SIGNAL("updateextract(int, int)"), y1,y2)

   def loaddata(self, warr, farr, snarr, name=''):
       print "Loading data"
       self.warr=warr
       self.farr=farr
       self.snarr=snarr
       self.name=name
       return

   def plotSpectra(self):
       if self.smooth > 0 and self.farr is not None:
           farr = np.convolve(self.farr, np.ones(self.smooth), mode='same')/self.smooth
       else:
           farr = self.farr
       self.splot=self.axes.plot(self.warr, farr, linewidth=0.5,linestyle='-',
                                marker='None',color='b')

   def redraw_canvas(self,keepzoom=False):
       if keepzoom:
            # Store current zoom level
            xmin, xmax = self.axes.get_xlim()
            ymin, ymax = self.axes.get_ylim()

       # Clear plot
       self.axes.clear()

       # Draw image
       self.plotSpectra()

       # Restore zoom level
       if keepzoom:
           self.axes.set_xlim((self.xmin,self.xmax))
           self.axes.set_ylim((self.ymin,self.ymax))

       # Force redraw
       self.arcfigure.draw()
예제 #11
0
class FpRingWidget(QtGui.QWidget):
    def __init__(self, filenumber, flatnumber, parent=None):
        super(FpRingWidget, self).__init__(parent)

        self.filenumber = filenumber
        self.flatnumber = flatnumber

        #set up the ring plot
        self.ringplot = MplCanvas()

        self.axes = self.ringplot.figure.add_subplot(211)
        self.erraxes = self.ringplot.figure.add_subplot(212)

        self.ringplot.setMinimumHeight(500)
        #        self.ringplot.setMinimumHeight(500)

        self.loadfpring()
        self.plotRing()

        #        self.redraw_canvas()

        #set up the information panel
        self.infopanel = QtGui.QWidget()

        # add a label:
        self.NameLabel = QtGui.QLabel("File number:")

        #add the name of the file
        self.NameValueLabel = QtGui.QLineEdit(str(self.filenumber))

        # and a button to process the new ring
        self.ringButton = QtGui.QPushButton('Load new ring')
        self.ringButton.clicked.connect(self.redrawRing)

        # add a label for the flat field:
        self.flatLabel = QtGui.QLabel("Flat file number:")

        #add the name of the file
        self.flatValueLabel = QtGui.QLineEdit(str(self.flatnumber))

        #set up info panel layout

        infoLayout = QtGui.QGridLayout(self.infopanel)
        infoLayout.addWidget(self.NameLabel, 0, 0, 1, 1)
        infoLayout.addWidget(self.NameValueLabel, 0, 1, 1, 1)
        infoLayout.addWidget(self.ringButton, 0, 2, 2, 1)
        infoLayout.addWidget(self.flatLabel, 0, 3, 1, 1)
        infoLayout.addWidget(self.flatValueLabel, 0, 4, 1, 1)
        #        fitLayout=QtGui.QGridLayout(self.infopanel)

        # add a panel to display the fit results

        self.fitpanel = QtGui.QWidget()

        self.fitLabel = QtGui.QLabel("Fit Results:")

        fitXresult = "X:" + str(self.etalon_x)
        fitYresult = "Y:" + str(self.etalon_y)
        fitZresult = "Z:" + str(self.etalon_z)
        fitRresult = "R: %.1f" % float(self.pars['R'][0])
        fitAmpresult = "Amplitude: %.1f" % float(self.pars['Amplitude'][0])
        fitRmsresult = "RMS: %.1f" % float(self.rms)
        fitGammaresult = "Gamma: %.1f" % float(self.pars['Gamma'][0])
        fitFWHMresult = "FWHM: %.1f" % float(self.pars['FWHM'][0])

        #add the text to the fit results panel
        self.fitX = QtGui.QLabel(fitXresult)
        self.fitY = QtGui.QLabel(fitYresult)
        self.fitZ = QtGui.QLabel(fitZresult)
        self.fitR = QtGui.QLabel(fitRresult)
        self.fitAmp = QtGui.QLabel(fitAmpresult)
        self.fitRms = QtGui.QLabel(fitRmsresult)
        self.fitGamma = QtGui.QLabel(fitGammaresult)
        self.fitFWHM = QtGui.QLabel(fitFWHMresult)

        # lay them out nicely...

        fitLayout = QtGui.QGridLayout(self.fitpanel)
        fitLayout.addWidget(self.fitLabel, 0, 0, 1, 1)
        fitLayout.addWidget(self.fitX, 0, 1, 1, 1)
        fitLayout.addWidget(self.fitY, 0, 2, 1, 1)
        fitLayout.addWidget(self.fitZ, 0, 3, 1, 1)
        fitLayout.addWidget(self.fitR, 0, 4, 1, 1)
        fitLayout.addWidget(self.fitAmp, 0, 5, 1, 2)
        fitLayout.addWidget(self.fitRms, 0, 7, 1, 1)
        fitLayout.addWidget(self.fitGamma, 0, 8, 1, 1)
        fitLayout.addWidget(self.fitFWHM, 0, 9, 1, 1)

        # Set up the main layout
        mainLayout = QtGui.QVBoxLayout()
        mainLayout.addWidget(self.infopanel)
        mainLayout.addWidget(self.ringplot)
        mainLayout.addWidget(self.fitpanel)
        self.setLayout(mainLayout)

    def loadfpring(self):

        date = os.getcwd().split('/')[-1]

        self.getFitsHeader()
        fits = "mbxpP%s%04d.fits" % (date, self.filenumber)
        if self.flatnumber != 0:
            flat = "mbxpP%s%04d.fits" % (date, self.flatnumber)
        else:
            flat = "/home/ccd/erc/FP_utils/DefaultNeFlat.fits"

        ffits = 'f' + fits
        fpfile = 'p' + ffits
        maskedfile = 'm' + fpfile

        if (not os.path.isfile(maskedfile)):
            saltflat(fits, ffits, '', flat, clobber='yes', verbose='no')

            saltfpprep(ffits, fpfile, '', clobber='yes', verbose='no')

            saltfpmask(fpfile,
                       maskedfile,
                       '',
                       axc=798 * 4 / self.xbin,
                       ayc=503 * 4 / self.ybin,
                       arad=450 * 4 / self.xbin,
                       clobber='yes',
                       verbose='no')

        self.good, self.rsq, self.prof, self.fit, self.pars = fit_rings(
            maskedfile)
        self.resid = self.prof - self.fit
        self.rms = self.resid.std()

        self.saveFitToFile()

        return

    def plotRing(self):
        #set up the plots....

        self.axes.plot(self.rsq, self.prof, label="Profile")
        self.axes.plot(self.rsq, self.fit, label="Fit")
        self.axes.legend(bbox_to_anchor=(0., 1.02, 1., .102),
                         loc=3,
                         ncol=2,
                         mode="expand",
                         borderaxespad=0.)
        self.erraxes.plot(self.rsq, self.resid, label="Profile - Fit")
        self.erraxes.legend(loc=1)
        self.show()

        return

    def redrawRing(self):
        # read the new filenumber from the input box
        self.filenumber = int(self.NameValueLabel.text())
        # recalculate and re-draw
        self.loadfpring()
        self.axes.clear()
        self.erraxes.clear()
        self.plotRing()
        #Force a redraw!!!
        self.ringplot.draw()

    def getFitsHeader(self):

        date = os.getcwd().split('/')[-1]
        fits = "mbxpP%s%04d.fits" % (date, self.filenumber)
        hdu = pyfits.open(fits)
        (data, header) = (hdu[0].data, hdu[0].header)
        etalon = int(header['ET-STATE'].split()[3])
        hetalon_x = "ET%dX" % etalon
        hetalon_y = "ET%dY" % etalon
        hetalon_z = "ET%dZ" % etalon

        self.etalon_x = int(header[hetalon_x])
        self.etalon_y = int(header[hetalon_y])
        self.etalon_z = int(header[hetalon_z])
        self.xbin = int(header['CCDSUM'].split()[0])
        self.ybin = int(header['CCDSUM'].split()[1])

        print self.xbin, self.ybin

        return

    def saveFitToFile(self):

        pars = self.pars
        self.getFitsHeader()

        if os.path.isfile('outparams'):
            try:
                outparams = open('outparams', 'a')

            except IOError, e:
                print 'Failed to open the ring file'

        else: