python wxpython一例

前些天wxpython做得简单代码,目标是:
比如说c:\photos\....下面有很多头像图片,这些图片在上面或下面有一个圆点,呈现图片一段时间,判断圆点在上面还是下面,按1,2进行反应,记录反应时间。
注:是帮朋友进行孤独症儿童注意力分配实验写的,后面因为在处理*.gif图片的时候响应速度不够好,改为用delphi7写了。

程序涉及:
wxpython
事件响应
图片缩放和GIF动画操作

# -*- coding: cp936 -*-
import time
import wx,os
import wx.animate

from operator import or_
from func import *
from  threading import *


class M(object):
    idx = 0
    total = 0
    right = 0
    wrong = 0
    starticker = 0 #开始时间
    steps = []
    answer = 0
    pause = 1000
    pre = 'bmp' #0 is bmp,1 is if,2 is text

 
        
class FullScreenPanel(wx.Panel):

    def __init__(self,parent):
        wx.Panel.__init__(self,parent,name="FullScreenPanel",style= wx.DEFAULT_FRAME_STYLE | wx.WANTS_CHARS )
        self.SetBackgroundColour('black')
        

    
        self.TrialBtn = wx.Button(self,label="练习")
        self.TrialBtn.Bind(wx.EVT_BUTTON,self.BeginTrial)
        self.TestBtn = wx.Button(self,label="测试")
        self.TestBtn.Bind(wx.EVT_BUTTON,self.BeginTest)

        sizer = wx.BoxSizer(orient=wx.VERTICAL)  
        sizer.AddStretchSpacer()
        sizer.Add(self.TrialBtn,0, wx.ALIGN_CENTER )
        sizer.Add(self.TestBtn,0, wx.ALIGN_CENTER )
        sizer.AddStretchSpacer() 
        self.SetSizer(sizer)
        

        self.Layout()
        


    
    def hideImg(self):
        try:
            self.curImg.Show(False)
        except:
            pass
    def hideGif(self):
        try:
            self.curGif.Stop()
            self.curGif.Close()
            self.curGif.Show(False)
        except:
            print "hide gif error"
            pass
    def hideText(self):
        try:
            self.curText.Show(False)
        except:
            pass
            
    
    def KeyDownResponse(self,evt):        
        code = evt.GetKeyCode()
        if code in (49,50):
            self.stopTimer()
            self.Bind(wx.EVT_KEY_DOWN,self.KeyDownNull)
            if code == 49:
                code = 1
            else:
                code = 2
            if code == M.answer:
                slapedTime = time.time() - M.starticker 

                self.show(response['right'])
                M.right = M.right + 1
                M.total = M.total + 1
                rate = M.right/float(M.total)
            else:
                slapedTime = time.time() - M.starticker 
                self.show(response['wrong'])
                M.wrong = M.wrong + 1
                M.total = M.total + 1
                rate = M.right/float(M.total)

            text = "正确率:%.3f 耗时:%.3f" % (rate,slapedTime)
            if self.practice:
                self.addText(text)
            self.fp.write(text+"\n") 
            self.timer = wx.CallLater(M.pause,self.next)
          
        else:
            pass
        
    def addText(self,text):
        mm=wx.DisplaySize()
        x0 = 100
        y0 = 600
        self.curText = wx.StaticText(self,-1,text,(x0,y0),(160,0),wx.ALIGN_CENTER)
        font=wx.Font(18,wx.DECORATIVE,wx.NORMAL,wx.NORMAL)        
        self.curText.SetFont(font)
        self.curText.SetForegroundColour("white")
        self.curText.SetBackgroundColour("black")
        self.curText.Show(True)
                
    def KeyDownNull(self,evt):
        pass        
            
    def showText(self,text):
        mm=wx.DisplaySize()


        x0 = (mm[0] - 60) / 2
        y0 = (mm[1] - 60) / 2
        self.curText = wx.StaticText(self,-1,text,(x0,y0),(160,0),wx.ALIGN_CENTER)
        font=wx.Font(28,wx.DECORATIVE,wx.NORMAL,wx.NORMAL)        
        self.curText.SetFont(font)
        self.curText.SetForegroundColour("white")
        self.curText.SetBackgroundColour("black")
        self.curText.Show(True)
                
    def showBmp(self,fpath):
        try:
            self.curImg.Show(False)
        except:
            pass
        mm=wx.DisplaySize()
        img = wx.Image(fpath, wx.BITMAP_TYPE_BMP)
        x0 = (mm[0] - img.GetWidth()) / 2
        y0 = (mm[1] - img.GetHeight()) / 2
        wxBitmap = img.ConvertToBitmap()
       # self.curImg.SetBitmap(wxBitmap)
        self.curImg = wx.StaticBitmap(self, -1, img.ConvertToBitmap(), (x0,y0), (img.GetWidth(), img.GetHeight()))
        self.curImg.Show(True)
        print "end.."+fpath

    def showGif(self,fpath):
        mm=wx.DisplaySize()
        
        img = wx.Image(fpath, wx.BITMAP_TYPE_GIF)
        x0 = (mm[0] - img.GetWidth()) / 2
        y0 = (mm[1] - img.GetHeight()) / 2
        self.curGif = wx.animate.GIFAnimationCtrl(self, -1, fpath, (x0,y0), (img.GetWidth(), img.GetHeight()))            
        self.curGif.GetPlayer().UseBackgroundColour(True)
        self.curGif.Play()
        
    def show(self,fpath): 
        type = getType(fpath)
        self.hideText()
        self.hideGif()
        if not type == M.pre:
            if type == "gif":
                self.hideText()
                self.hideImg()
                self.hideGif()

            elif type == "bmp":
                self.hideGif()
                self.hideText()
            else:
                self.hideImg()
                self.hideGif()
            M.pre = type
                
        print 'show '+fpath
        if  type == "bmp":
            self.hideText()
            self.showBmp(fpath)
        elif type == "gif":
            self.hideText()
            self.showGif(fpath)
        elif type == "":
            self.showText(fpath)
    
    def stopTimer(self):
        self.timer.Stop()  
              
    def timeout(self):
        self.stopTimer()
        self.Bind(wx.EVT_KEY_DOWN,self.KeyDownNull)
        self.show(response['timeout'])     
        M.total += 1
        rate = M.right / float(M.total)
        slapedTime = time.time() - M.starticker 
        
        text = "正确率:%.3f %.3f" % (rate,slapedTime)
        if self.practice:
            self.addText(text)   
            
        self.fp.write(text+"\n") 
        self.timer = wx.CallLater(M.pause,self.next)
    

            
    def next(self):
        idx = M.idx
        if idx > len(M.steps)-1:
            self.stopTimer()
            print "over"
            return ""
        print 'current idx %s' %idx
        opType =  M.steps[idx][0]
        fpath = M.steps[idx][1]
        type = getType(fpath)
        sepTime = M.steps[idx][2]
        M.idx = idx+1

        self.show(fpath)
        if opType == 0: #退出
            self.Bind(wx.EVT_KEY_DOWN,self.KeyDownOver)
        if opType == 1: #等待space
            self.Bind(wx.EVT_KEY_DOWN,self.KeyDownTrigger)
        elif opType in (2,3): #空操作
            self.Bind(wx.EVT_KEY_DOWN,self.KeyDownNull)
            self.timer = wx.CallLater(sepTime, self.next)    
        elif opType == 4:  #等待反映,1500ms 后
            self.Bind(wx.EVT_KEY_DOWN,self.KeyDownResponse) #多做一次也无所谓,让逻辑
            M.starticker = time.time()
            self.timer = wx.CallLater(sepTime, self.timeout)    
        elif opType == 9:
            M.answer = M.steps[idx][3]
            self.Bind(wx.EVT_KEY_DOWN,self.KeyDownResponse)
            self.timer = wx.CallLater(sepTime, self.next)    

        

    def KeyDownOver(self,evt):
        self.stopTimer()
        self.hideGif()
        self.hideText()
        self.hideImg()
        self.TrialBtn.Show()
        self.TestBtn.Show() 
        try:
            self.fp.close()
        except:
            pass
        M.steps = []
        M.idx = 0
        M.total = 0
        M.right = 0
        M.wrong = 0
        M.starticker = 0 #开始时间
        M.steps = []
        M.answer = 0
        
    def KeyDownTrigger(self,evt):
        if evt.GetKeyCode() == 32:
            self.next()
        
    def getSavePath(self):
        sp = time.strftime("%Y-%m-%d-%H-%M-%S",time.localtime())+".txt"
        return os.path.join(os.getcwd(),sp)
            
    def BeginTest(self,evt):
        fpath = self.getSavePath()
        self.fp = open(fpath, 'w') 
        
        self.practice = False
        self.TrialBtn.Hide()
        self.TestBtn.Hide() 
        M.steps = getSteps(testConf) 
        print M.steps
        self.next()
        self.FullScreen(evt) 

            
    def BeginTrial(self,evt):
        fpath = self.getSavePath()
        self.fp = open(fpath, 'w') 
        self.practice = True
        self.TrialBtn.Hide()
        self.TestBtn.Hide() 
        M.steps = getSteps(trialConf) 
        self.next()
        self.FullScreen(evt)
        
    def GetFlags(self):
        res = []
        val = "FULLSCREEN_ALL"
        res.append(getattr(wx,val))
        return reduce(or_,res,0)

    def FullScreen(self,evt):
        top = self.GetTopLevelParent()
        top.OnFullScreen(evt)

class MainFrame(wx.Frame):
    def __init__(self, parent):
        wx.Frame.__init__(self, parent, wx.ID_ANY, 'Test FullScreen', size=(600, 400))
        self.Bind(wx.EVT_CLOSE, self.OnCloseWindow)
        self.client = FullScreenPanel(self)

        mbar = wx.MenuBar()
        the_menu = wx.Menu()
        fullscreenMI = the_menu.Append(wx.ID_ANY,"Full Screen\tF12","Toggles Full Screen Mode")
        mbar.Append(the_menu,"File")
        self.SetMenuBar(mbar)
        self.Bind(wx.EVT_MENU,self.OnFullScreen,id=fullscreenMI.GetId())


    def OnCloseWindow(self, event):
        self.Destroy()

    def OnFullScreen(self,event):
        flags = self.client.GetFlags()
        self.ShowFullScreen(not self.IsFullScreen(),flags)

class MainApp(wx.App):
    def OnInit(self):
        self.main = MainFrame(None)
        self.main.Show()
        self.SetTopWindow(self.main)
        return True


def main():
    application = MainApp(redirect=False)
    application.MainLoop()

if __name__=='__main__':
    main()


# -*- coding: cp936 -*-
import os
import random
import wx

def opj(path):
    st = apply(os.path.join, tuple(path.split('/')))
    if path.startswith('/'):
        st = '/' + st
    return st


imgTypeDict = {
    'bmp':wx.BITMAP_TYPE_BMP,
    'gif':wx.BITMAP_TYPE_GIF,
    'png':wx.BITMAP_TYPE_PNG,
    'jpg':wx.BITMAP_TYPE_JPEG
}

#获取后缀
def getType(o):
    if o.rfind(".") > -1:
        idx=o.rindex(".")+1
        return o[idx:].lower() 
    else:
        return ""
    
    
p1 = opj('photos/right.bmp')
p2 = opj('photos/wrong.bmp')
p3 = opj('photos/no response.bmp')
response = {
    'right':p1,
    'wrong':p2,
    'timeout':p3
}
    
sep = (2,'+',1000)
sep0 = (2,'',1000)
trialConf = (
    (1,'photos/welcome.bmp'),      
    (1,'photos/instruction.bmp'), 
    (2,'+',1), #1000ms 文本
    (3,'photos/practice/face1', 400,200,1500),
 #探测的文件目录时间(面空时间,探测点时间,等待回答时间)
    (0,'photos/goodbye.bmp',5000)
)
testConf = (
    (1,'photos/welcome.bmp'),      
    (1,'photos/instruction.bmp'), 
    (2,'+',1000), #1000ms 文本
    (3,'photos/donghua', 400,50,1500),
 #探测的文件目录时间(面空时间,探测点时间,等待回答时间)
    (0,'photos/goodbye.bmp',5000)
)

def getSteps(conf):
    steps=[]
    for x in conf:
        type = x[0]
        img = x[1]
        if type == 0: #end
            item = (0,opj(x[1]),-1)
            steps.append(item)
            
        if type == 1: #单个图片
            item = (1,opj(x[1]),-1) #-1 means infinate
            steps.append(item)
        elif type == 2: #
            item = (2,x[1],x[2]) #内容,时间
            steps.append(item)
        elif type == 3:
            dir1 = x[1]   
            t1 = x[2]
            t2 = x[3]
            t3 = x[4]         
            face=[]
            probe=[]
            for root, dirs, files in os.walk(dir1, topdown=False):
                for name in files:
                    if name.endswith(".gif") or name.endswith(".bmp"):
                        face.append(opj(os.path.join(root, name)))
            face.sort()
            print face
            count = len(face)
            i=0
            while(i<count):
                curImg = face[i]
                i += 1
                nextImg = face[i]
                if nextImg.find("_2") > 0:   #存在2,就是下面有点
                    answer = 2
                else:
                    answer = 1
                i += 1
                curItem = (curImg,nextImg,answer)
                probe.append(curItem)
           # print face
            random.shuffle(probe)
            
            i=0
            count = len(probe)
          #  print probe
            while(i<count):
                curItem = probe[i]
                item = (3,curItem[0],t1)
                steps.append(item)
                item = (9,curItem[1],t2,curItem[2]) 
                #马上要激活keyboard反应,并置相应的时间处理函数 
                
                #(类型4需要响应,图片路径,呈现时间,正确答案,超时时间,
                steps.append(item)
                item = (4,curItem[0],t3)
                steps.append(item)
                steps.append(sep0)

                steps.append(sep)
                i += 1
            
    return steps

你可能感兴趣的:(python,OS,FP,wxPython)