Python:鼠标向下计数,当鼠标向上时停止
我试图做一个python脚本,当按下鼠标按钮时,它从0开始计数。我的想法是在按下鼠标左键时使用pyHook进入函数,释放鼠标左键时退出函数。我对python非常陌生,所以对于不好的解释感到抱歉。 一些伪代码:Python:鼠标向下计数,当鼠标向上时停止
import pyHook
import pythoncom
def termin():
return None
def counter(tell):
a=0
while True:
print a
a+=1
hm = pyHook.HookManager()
hm.SubscribeMouseLeftUp(termin)
hm = pyHook.HookManager()
hm.SubscribeMouseLeftDown(counter)
hm.HookMouse()
pythoncom.PumpMessages()
hm.UnhookMouse()
此代码是我的总体思路,但我不认为它会奏效,因为SubscribeMouseLeftUp发生在离散时间。我在寻找的可能是在某种线程或多处理模块中运行计数器函数和终止函数,并使用一个函数中的条件来终止其他运行函数。但我不确定如何使这项工作。
好了,所以我想这个脚本意志力的评论后:
import pyHook,time,pythoncom
def counter(go):
for a in range(5):
time.sleep(1)
print a
return True
hm=pyHook.HookManager()
hm.SubscribeMouseLeftDown(counter)
hm.HookMouse()
pythoncom.PumpMessages()
hm.UnhookMouse()
从willpower2727接受的答案是迄今为止我见过的最好的解决方案。之前,他使用线程张贴了他的解决方案,我做了如下代码:
from multiprocessing import Process,Queue
import pyHook
import time
import pythoncom
import ctypes
def counter(tellerstate,q):
while True:
a=0
tellerstate=q.get()
if tellerstate==1:
while True:
a+=1
print a
tellerstate=q.get()
if tellerstate==0:
break
time.sleep(0.1)
def mousesignal(q):
def OnDown(go):
tellstate=1
q.put(tellstate)
return None
def OnUp(go):
tellstate=0
q.put(tellstate)
return None
def terminate(go):
if chr(go.Ascii)=='q' or chr(go.Ascii)=='Q':
ctypes.windll.user32.PostQuitMessage(0)
hm.UnhookKeyboard()
hm.UnhookMouse()
q.close()
q.join_thread()
process_counter.join()
process_mousesignal.join()
return None
hm=pyHook.HookManager()
hm.KeyDown = terminate
hm.MouseLeftDown = OnDown
hm.MouseLeftUp = OnUp
hm.HookMouse()
hm.HookKeyboard()
pythoncom.PumpMessages()
if __name__ == '__main__':
tellerstate=0
q=Queue()
process_counter = Process(target=counter,args=(tellerstate,q))
process_mousesignal = Process(target=mousesignal,args=(q,))
process_mousesignal.start()
process_counter.start()
我预计这段代码的行为是柜台mousesignal功能应该运行为单独的进程。在mousesignal过程中,我根据鼠标输入将0或1放入队列中。计数器函数连续运行并读取队列并使用if语句在此函数中输入和退出循环。此代码根本不起作用,但我无法理解为什么。
好吧,我有使用线程当鼠标按键被按下做一些事情的一个例子。如果用户非常快速地双击鼠标,该示例就会中断/被卡住。它使用一个锁和一个只有在释放锁时才执行某些代码的线程(由鼠标触发)。
import time
import threading
import pyHook
import pythoncom
def DoThis(Cond):
while True:
with Cond: #calling "with" automatically calls acquire() on the lock
print(time.time())
print('stopping...')
global Cond
Cond = threading.Lock()#create a threading lock
Cond.acquire() #give the lock to the main thread
global t1
t1 = threading.Thread(target=DoThis,args=(Cond,)) #initialize the thread that does stuff while mouse button is down
t1.start() #start the thread, it won't do anything until mouse button is down
def OnDown(go):
global Cond
Cond.release() #allow the thread to acquire the lock
print('Lock released')
return True
def OnUp(go):
global Cond
Cond.acquire() #take the lock away from the thread
print('Lock acquired')
return True
hm = pyHook.HookManager()
hm.MouseLeftDown = OnDown
hm.MouseLeftUp = OnUp
hm.HookMouse()
pythoncom.PumpMessages()
所面临的挑战与使用线程的是,他们只能使用一次,所以你不能叫thread.start()每次用鼠标按下,它只会工作的第一次启动。通过允许线程保持活动状态,但不做任何事情(除非经常检查它是否应该),这样可以在鼠标关闭时仅执行一些代码。有一些更复杂的方法可以改善计算机上的处理负载(可能使用线程条件而不是常规锁定),但这是我的一般想法。
这看起来非常有希望,我非常感谢你的帮助,于是有时间完全理解了线程模块。我已经通过使用多处理更新了主帖,但是它不起作用。如果你想看看它,你非常欢迎。 – mathiasxx94
根据您提供的示例,它看起来像要计算鼠标按钮关闭的秒数?你可以做到这一点,而不使用多个线程。下面的例子将打印时的鼠标按钮被按下的金额:
import pyHook
import time
import pythoncom
global starttime
starttime = time.time()
global endtime
endtime = time.time()
def OnDown(go):
global starttime
starttime = time.time()
return True
def OnUp(go):
global starttime
global endtime
endtime = time.time()
etime = endtime-starttime
print(etime)
return True
hm = pyHook.HookManager()
hm.MouseLeftDown = OnDown
hm.MouseLeftUp = OnUp
hm.HookMouse()
pythoncom.PumpMessages()
非常感谢您的答案意志力。不幸的是,我可能用一些含糊不清的措辞来表达我的要求。只要鼠标按钮被按下,程序就会在循环中执行一个操作,我只是以计数为例。我不能想到没有多处理或线程的方式的原因是,据我所知,程序在进入函数时会停止监听鼠标输入。@willpower – mathiasxx94
只是一个建议,你可能会尝试得到一个pyhook程序的工作示例,然后尝试和调整以满足您的需求。一旦你有一个工作的例子,它会更容易帮助你。我建议这个例子作为一个可能的开始:https://gordoncluster.wordpress.com/2013/09/12/logging-all-keyboard-input-with-python-pyhook/ – willpower2727
增加了工作计数器代码。 – mathiasxx94
您是否有兴趣计算鼠标按钮关闭的累计时间?或者其他一些计数措施? – willpower2727