⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 wxpyplot.py

📁 PyChem是用Python语言编写的多元变量分析软件。它包括一个前端图形界面用于管理和保存试验数据
💻 PY
📖 第 1 页 / 共 4 页
字号:
        self.SetBackgroundColour(wx.wxNamedColour("white"))
        
        wx.EVT_PAINT(self, self.OnPaint)
        wx.EVT_SIZE(self,self.OnSize)
        
        #Create some mouse events for zooming
        wx.EVT_LEFT_DOWN(self, self.OnMouseLeftDown)
        wx.EVT_LEFT_UP(self, self.OnMouseLeftUp)
        wx.EVT_MOTION(self, self.OnMotion)
        wx.EVT_LEFT_DCLICK(self, self.OnMouseDoubleClick)
        wx.EVT_RIGHT_DOWN(self, self.OnMouseRightDown)

        # set curser as cross-hairs
        self.SetCursor(wx.wxCROSS_CURSOR)

        #Things for printing
        self.print_data = wx.wxPrintData()
        self.print_data.SetPaperId(wx.wxPAPER_LETTER)
        self.print_data.SetOrientation(wx.wxLANDSCAPE)
        self.pageSetupData= wx.wxPageSetupDialogData()
        self.pageSetupData.SetMarginBottomRight((25,25))
        self.pageSetupData.SetMarginTopLeft((25,25))
        self.pageSetupData.SetPrintData(self.print_data)
        self.printerScale = 1
        self.parent= parent

        #Zooming variables
        self._zoomInFactor =  0.5
        self._zoomOutFactor = 2
        self._zoomCorner1= scipy.array([0.0, 0.0]) #left mouse down corner
        self._zoomCorner2= scipy.array([0.0, 0.0])   #left mouse up corner
        self._zoomEnabled= False
        self._hasDragged= False
        
        #Drawing Variables
        self.last_draw = None
        self.original_draw = None
        self._pointScale= 1
        self._pointShift= 0
        self._xSpec= 'auto'
        self._ySpec= 'auto'
        self._gridEnabled= False
        self._legendEnabled= False
        self._legendItems = None
        
        #Fonts
        self._fontCache = {}
        self._fontSizeAxis= 10
        self._fontSizeTitle= 15
        self._fontSizeLegend= 7

        # OnSize called to make sure the buffer is initialized.
        # This might result in OnSize getting called twice on some
        # platforms at initialization, but little harm done.
        self.OnSize(None) #sets the initial size based on client size
        
        #SaveFile
        wx.wxInitAllImageHandlers()
        
    def SaveFile(self, fileName= ''):
        """Saves the file to the type specified in the extension. If no file
        name is specified a dialog box is provided.  Returns True if sucessful,
        otherwise False.
        
        .bmp  Save a Windows bitmap file.
        .xbm  Save an X bitmap file.
        .xpm  Save an XPM bitmap file.
        .png  Save a Portable Network Graphics file.
        .jpg  Save a Joint Photographic Experts Group file.
        """
        if string.lower(fileName[-3:]) not in ['bmp','xbm','xpm','png','jpg']:
            dlg1 = wx.wxFileDialog(self, "Choose a file with extension bmp, gif, xbm, xpm, png, or jpg", ".", "",
             "BMP files (*.bmp)|*.bmp|XBM files (*.xbm)|*.xbm|XPM file (*.xpm)|*.xpm|PNG files (*.png)|*.png|JPG files (*.jpg)|*.jpg",
             wx.wxSAVE|wx.wxOVERWRITE_PROMPT)
            try:
                while 1:
                    if dlg1.ShowModal() == wx.wxID_OK:
                        fileName = dlg1.GetPath()
                        #Check for proper exension
                        if string.lower(fileName[-3:]) not in ['bmp','xbm','xpm','png','jpg']:
                            dlg2 = wx.wxMessageDialog(self, 'File name extension\n'
                            'must be one of\n'
                            'bmp, xbm, xpm, png, or jpg',
                              'File Name Error', wx.wxOK | wx.wxICON_ERROR)
                            try:
                                dlg2.ShowModal()
                            finally:
                                dlg2.Destroy()
                        else:
                            break #now save file
                    else: #exit without saving
                        return False
            finally:
                dlg1.Destroy()

        #File name has required extension
        fType = string.lower(fileName[-3:])
        if fType == "bmp":
            tp= wx.wxBITMAP_TYPE_BMP       #Save a Windows bitmap file.
        elif fType == "xbm":
            tp= wx.wxBITMAP_TYPE_XBM       #Save an X bitmap file.
        elif fType == "xpm":
            tp= wx.wxBITMAP_TYPE_XPM       #Save an XPM bitmap file.
        elif fType == "jpg":
            tp= wx.wxBITMAP_TYPE_JPEG      #Save a JPG file.
        else:
            tp= wx.wxBITMAP_TYPE_PNG       #Save a PNG file.
        #Save Bitmap
        res= self._Buffer.SaveFile(fileName, tp)
        return res

    def PageSetup(self):
        """Brings up the page setup dialog"""
        data = self.pageSetupData
        data.SetPrintData(self.print_data)
        dlg = wx.wxPageSetupDialog(self.parent, data)
        try:
            if dlg.ShowModal() == wx.wxID_OK:
                data = dlg.GetPageSetupData() #returns wxPageSetupDialogData
                #updates page parameters from dialog
                self.pageSetupData.SetMarginBottomRight(data.GetMarginBottomRight())
                self.pageSetupData.SetMarginTopLeft(data.GetMarginTopLeft())
                self.pageSetupData.SetPrintData(data.GetPrintData())
                self.print_data=data.GetPrintData() #updates print_data
        finally:
            dlg.Destroy()
                
    def Printout(self, paper=None):
        """Print current plot."""
        if paper != None:
            self.print_data.SetPaperId(paper)
        pdd = wx.wxPrintDialogData()
        pdd.SetPrintData(self.print_data)
        printer = wx.wxPrinter(pdd)
        out = plot_printout(self)
        print_ok = printer.Print(self.parent, out)
        if print_ok:
            self.print_data = printer.GetPrintDialogData().GetPrintData()
        out.Destroy()

    def PrintPreview(self):
        """Print-preview current plot."""
        printout = plot_printout(self)
        printout2 = plot_printout(self)
        self.preview = wx.wxPrintPreview(printout, printout2, self.print_data)
        if not self.preview.Ok():
            wx.wxMessageDialog(self, "Print Preview failed.\n" \
                               "Check that default printer is configured\n", \
                               "Print error", wx.wxOK|wx.wxCENTRE).ShowModal()
        self.preview.SetZoom(30)
        #search up tree to find frame instance
        frameInst= self
        while not isinstance(frameInst, wx.wxFrame):
            frameInst= frameInst.GetParent()
        frame = wx.wxPreviewFrame(self.preview, frameInst, "Preview")
        frame.Initialize()
        frame.SetPosition(self.GetPosition())
        frame.SetSize((500,400))
        frame.Centre(wx.wxBOTH)
        frame.Show(True)

    def SetFontSizeAxis(self, point= 10):
        """Set the tick and axis label font size (default is 10 point)"""
        self._fontSizeAxis= point
        
    def GetFontSizeAxis(self):
        """Get current tick and axis label font size in points"""
        return self._fontSizeAxis
    
    def SetFontSizeTitle(self, point= 15):
        """Set Title font size (default is 15 point)"""
        self._fontSizeTitle= point

    def GetFontSizeTitle(self):
        """Get current Title font size in points"""
        return self._fontSizeTitle
    
    def SetFontSizeLegend(self, point= 7):
        """Set Legend font size (default is 7 point)"""
        self._fontSizeLegend= point
        
    def GetFontSizeLegend(self):
        """Get current Legend font size in points"""
        return self._fontSizeLegend

    def SetEnableZoom(self, value):
        """Set True to enable zooming."""
        if value not in [True,False]:
            raise TypeError, "Value should be True or False"
        self._zoomEnabled= value

    def GetEnableZoom(self):
        """True if zooming enabled."""
        return self._zoomEnabled

    def SetEnableGrid(self, value):
        """Set True to enable grid."""
        if value not in [True,False]:
            raise TypeError, "Value should be True or False"
        self._gridEnabled= value
        self.Redraw()

    def GetEnableGrid(self):
        """True if grid enabled."""
        return self._gridEnabled

    def SetEnableLegend(self, value):
        """Set True to enable legend."""
        if value not in [True,False]:
            raise TypeError, "Value should be True or False"
        self._legendEnabled= value 
        self.Redraw()

    def GetEnableLegend(self):
        """True if Legend enabled."""
        return self._legendEnabled

    def Reset(self):
        """Unzoom the plot."""
        if self.original_draw is not None:
            self.Draw(self.original_draw[0],self.original_draw[1],self.original_draw[2])
        
    def ScrollRight(self, units):          
        """Move view right number of axis units."""
        if self.last_draw is not None:
            graphics, xAxis, yAxis= self.last_draw
            xAxis= (xAxis[0]+units, xAxis[1]+units)
            self.Draw(graphics,xAxis,yAxis)

    def ScrollUp(self, units):
        """Move view up number of axis units."""
        if self.last_draw is not None:
            graphics, xAxis, yAxis= self.last_draw
            yAxis= (yAxis[0]+units, yAxis[1]+units)
            self.Draw(graphics,xAxis,yAxis)
        
    def GetXY(self,event):
        """Takes a mouse event and returns the XY user axis values."""
        screenPos= scipy.array( event.GetPosition())
        x,y= (screenPos-self._pointShift)/self._pointScale
        return x,y

    def SetXSpec(self, type= 'auto'):
        """xSpec- defines x axis type. Can be 'none', 'min' or 'auto'
        where:
            'none' - shows no axis or tick mark values
            'min' - shows min bounding box values
            'auto' - rounds axis range to sensible values
        """
        self._xSpec= type
        
    def SetYSpec(self, type= 'auto'):
        """ySpec- defines x axis type. Can be 'none', 'min' or 'auto'
        where:
            'none' - shows no axis or tick mark values
            'min' - shows min bounding box values
            'auto' - rounds axis range to sensible values
        """
        self._ySpec= type
    
    def SetLegendItems(self,num= 10**5):
        """Truncate the legend so that only a few objects are returned"""
        self._legendItems = num
        
    def GetXSpec(self):
        """Returns current XSpec for axis"""
        return self._xSpec
    
    def GetYSpec(self):
        """Returns current YSpec for axis"""
        return self._ySpec
    
    def GetXMaxRange(self):
        """Returns (minX, maxX) x-axis range for displayed graph"""
        graphics= self.last_draw[0]
        p1, p2 = graphics.boundingBox()     #min, max points of graphics
        xAxis = self._axisInterval(self._xSpec, p1[0], p2[0]) #in user units
        return xAxis

    def GetYMaxRange(self):
        """Returns (minY, maxY) y-axis range for displayed graph"""
        graphics= self.last_draw[0]
        p1, p2 = graphics.boundingBox()     #min, max points of graphics
        yAxis = self._axisInterval(self._ySpec, p1[1], p2[1])
        return yAxis

    def GetXCurrentRange(self):
        """Returns (minX, maxX) x-axis for currently displayed portion of graph"""
        return self.last_draw[1]
    
    def GetYCurrentRange(self):
        """Returns (minY, maxY) y-axis for currently displayed portion of graph"""
        return self.last_draw[2]
        
    def Draw(self, graphics, xAxis = None, yAxis = None, dc = None):
        """Draw objects in graphics with specified x and y axis.
        graphics- instance of PlotGraphics with list of PolyXXX objects
        xAxis - tuple with (min, max) axis range to view
        yAxis - same as xAxis
        dc - drawing context - doesn't have to be specified.    
        If it's not, the offscreen buffer is used
        """
        #check Axis is either tuple or none
        if type(xAxis) not in [type(None),tuple]:
            raise TypeError, "xAxis should be None or (minX,maxX)"
        if type(yAxis) not in [type(None),tuple]:
            raise TypeError, "yAxis should be None or (minY,maxY)"
             
        #check case for axis = (a,b) where a==b caused by improper zooms
        if xAxis != None:
            if xAxis[0] == xAxis[1]:
                return
        if yAxis != None:
            if yAxis[0] == yAxis[1]:
                return
            
        if dc == None:
            # allows using floats for certain functions 
            dc = FloatDCWrapper(wx.wxBufferedDC(wx.wxClientDC(self), self._Buffer))
            dc.Clear()
            
        dc.BeginDrawing()
        #dc.Clear()
        
        #set font size for every thing but title and legend
        dc.SetFont(self._getFont(self._fontSizeAxis))

        #sizes axis to axis type, create lower left and upper right corners of plot
        if xAxis == None or yAxis == None:
            #One or both axis not specified in Draw
            p1, p2 = graphics.boundingBox()     #min, max points of graphics
            if xAxis == None:
                xAxis = self._axisInterval(self._xSpec, p1[0], p2[0]) #in user units
            if yAxis == None:
                yAxis = self._axisInterval(self._ySpec, p1[1], p2[1])
            #Adjust bounding box for axis spec
            p1[0],p1[1] = xAxis[0], yAxis[0]     #lower left corner user scale (xmin,ymin)
            p2[0],p2[1] = xAxis[1], yAxis[1]     #upper right corner user scale (xmax,ymax)                
        else:
            #Both axis specified in Draw
            p1= scipy.array([xAxis[0], yAxis[0]])    #lower left corner user scale (xmin,ymin)
            p2= scipy.array([xAxis[1], yAxis[1]])     #upper right corner user scale (xmax,ymax)
        
        if self.last_draw == None:
            self.x,self.y = xAxis,yAxis
        else:
            if abs(xAxis[0]-xAxis[1]) > abs(self.x[0]-self.x[1]):
                self.x = xAxis
            if abs(yAxis[0]-yAxis[1]) > abs(self.y[0]-self.y[1]):
                self.y = yAxis
            self.original_draw = (graphics, self.x, self.y)
            
        self.last_draw = (graphics, xAxis, yAxis)       #saves most recient values

        #Get ticks and textExtents for axis if required
        if self._xSpec is not 'none':        
            xticks = self._ticks(xAxis[0], xAxis[1])
            xTextExtent = dc.GetTextExtent(xticks[-1][1])#w h of x axis text last number on axis
        else:
            xticks = None
            xTextExtent= (0,0) #No text for ticks
        if self._ySpec is not 'none':
            yticks = self._ticks(yAxis[0], yAxis[1])
            yTextExtentBottom= dc.GetTextExtent(yticks[0][1])
            yTextExtentTop   = dc.GetTextExtent(yticks[-1][1])
            yTextExtent= (max(yTextExtentBottom[0],yTextExtentTop[0]),
                        max(yTextExtentBottom[1],yTextExtentTop[1]))
        else:
            yticks = None
            yTextExtent= (0,0) #No text for ticks

        #TextExtents for Title and Axis Labels

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -