使用 Python 使用 threading.Timer 以固定的时间间隔截取屏幕截图

发布于 2024-11-05 16:36:48 字数 3933 浏览 1 评论 0原文

我正在使用 pyGTK 编写一个简单的 GUI 应用程序,以固定的时间间隔截取桌面屏幕截图。为了安排拍摄,我使用 threading.Timer 类,为了拍摄,我使用 os.system 调用 scrot。

当我单击开始截屏按钮时,将调用 GlapseMain.startScreenshots 方法。当我单击停止截屏按钮时,将调用 GlapseMain.stopScreenshots 方法。

问题是,当 GTK 应用程序运行时,不会截取屏幕截图,尽管它应该截取屏幕截图。当我单击关闭按钮时,它会无限期地开始截屏。

这是我的代码:

#!/usr/bin/env python
# -*- coding: utf8  -*-

import threading
import os

class GlapseMain:

def __init__(self):
    self.outputDir = os.getenv('HOME')
    self.quality = 80
    self.interval = 10
    self.numDigits = 15
    self.currentShot = 0

def startScreenshots(self, output, quality, interval):
    print 'Starting taking screenshots...'
    print 'Output folder: ' + str(output)
    print 'Quality: ' + str(quality)
    print 'Interval: ' + str(interval)

    # Update attributes
    self.outputDir = output
    self.quality = quality
    self.interval = interval
    self.currentShot = 0

    # Create timer (first screenshot scheduled 1s ahead)
    self.timer = threading.Timer(1.0, self._takeScreenshot)
    self.timer.start()


def stopScreenshots(self):
    print 'Stopped taking screenshots.'

    self.timer.cancel()


def _takeScreenshot(self):
    # Build scrot command
    fileNumber = str(self.currentShot)
    fileNumber = fileNumber.zfill(self.numDigits - len(fileNumber))
    fileName = 'scr-' + fileNumber + '.jpg'

    command = 'scrot -q ' + str(self.quality) + ' ' + self.outputDir + os.sep + fileName

    print 'Taking screenshot: ' + command + '...'

    os.system(command)

    # Schedule next screenshot
    self.currentShot = self.currentShot + 1
    self.timer = threading.Timer(self.interval, self._takeScreenshot)
    self.timer.start()

我的输出看起来像这样:

Starting taking screenshots...
Output folder: /home/david/glapse-screens
Quality: 80.0
Interval: 2.0
Stopped taking screenshots.
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000000.jpg...
Closing gLapse...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000001.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000002.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000003.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000004.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000005.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000006.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000007.jpg...

希望你能帮助我,非常感谢。

编辑:

我改变了方法,现在我使用线程:

def startScreenshots(self, output, quality, interval):
    print 'Starting taking screenshots...'
    print 'Output folder: ' + str(output)
    print 'Quality: ' + str(quality)
    print 'Interval: ' + str(interval)

    # Update attributes
    self.outputDir = output
    self.quality = quality
    self.interval = interval
    self.currentShot = 0

    # Start a thread to take screenshots
    self.done = False
    self.thread = threading.Thread(target=self._takeScreenshot)
    self.thread.start()

def stopScreenshots(self):
    print 'Stopped taking screenshots.'
    self.done = True
    self.thread.join()


def _takeScreenshot(self):
    # Run until we're done
    while not self.done:
        # Build scrot command
        fileNumber = str(self.currentShot)
        fileNumber = fileNumber.zfill(self.numDigits - len(fileNumber))
        fileName = 'scr-' + fileNumber + '.jpg'

        command = 'scrot -q ' + str(self.quality) + ' ' + self.outputDir + os.sep + fileName

        print 'Taking screenshot: ' + command + '...'

        os.system(command)

        # Schedule next screenshot
        print 'Scheduling next screenshot...'
        self.currentShot = self.currentShot + 1
        time.sleep(self.interval)

它打印消息,但不执行 os.system 指令,直到我按下停止按钮。

I'm writing a simple GUI application with pyGTK to take desktop screenshots at fixed intervals. To schedule the shots I use the threading.Timer class and to take shots I use os.system calls to scrot.

When I click the start taking screenshots button the GlapseMain.startScreenshots method is called. When I click the stop taking screenshot button the GlapseMain.stopScreenshots method is called.

The thing is while the GTK app is working no screenshot is taken although it should. When I click the close button, it starts taking screenshots idefinitely.

Here is my code:

#!/usr/bin/env python
# -*- coding: utf8  -*-

import threading
import os

class GlapseMain:

def __init__(self):
    self.outputDir = os.getenv('HOME')
    self.quality = 80
    self.interval = 10
    self.numDigits = 15
    self.currentShot = 0

def startScreenshots(self, output, quality, interval):
    print 'Starting taking screenshots...'
    print 'Output folder: ' + str(output)
    print 'Quality: ' + str(quality)
    print 'Interval: ' + str(interval)

    # Update attributes
    self.outputDir = output
    self.quality = quality
    self.interval = interval
    self.currentShot = 0

    # Create timer (first screenshot scheduled 1s ahead)
    self.timer = threading.Timer(1.0, self._takeScreenshot)
    self.timer.start()


def stopScreenshots(self):
    print 'Stopped taking screenshots.'

    self.timer.cancel()


def _takeScreenshot(self):
    # Build scrot command
    fileNumber = str(self.currentShot)
    fileNumber = fileNumber.zfill(self.numDigits - len(fileNumber))
    fileName = 'scr-' + fileNumber + '.jpg'

    command = 'scrot -q ' + str(self.quality) + ' ' + self.outputDir + os.sep + fileName

    print 'Taking screenshot: ' + command + '...'

    os.system(command)

    # Schedule next screenshot
    self.currentShot = self.currentShot + 1
    self.timer = threading.Timer(self.interval, self._takeScreenshot)
    self.timer.start()

My output looks something like this:

Starting taking screenshots...
Output folder: /home/david/glapse-screens
Quality: 80.0
Interval: 2.0
Stopped taking screenshots.
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000000.jpg...
Closing gLapse...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000001.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000002.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000003.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000004.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000005.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000006.jpg...
Taking screenshot: scrot -q 80.0 /home/david/glapse-screens/scr-00000000000007.jpg...

Hope you could help me, thank you very much.

Edit:

I've changed the approach and now I'm using threads:

def startScreenshots(self, output, quality, interval):
    print 'Starting taking screenshots...'
    print 'Output folder: ' + str(output)
    print 'Quality: ' + str(quality)
    print 'Interval: ' + str(interval)

    # Update attributes
    self.outputDir = output
    self.quality = quality
    self.interval = interval
    self.currentShot = 0

    # Start a thread to take screenshots
    self.done = False
    self.thread = threading.Thread(target=self._takeScreenshot)
    self.thread.start()

def stopScreenshots(self):
    print 'Stopped taking screenshots.'
    self.done = True
    self.thread.join()


def _takeScreenshot(self):
    # Run until we're done
    while not self.done:
        # Build scrot command
        fileNumber = str(self.currentShot)
        fileNumber = fileNumber.zfill(self.numDigits - len(fileNumber))
        fileName = 'scr-' + fileNumber + '.jpg'

        command = 'scrot -q ' + str(self.quality) + ' ' + self.outputDir + os.sep + fileName

        print 'Taking screenshot: ' + command + '...'

        os.system(command)

        # Schedule next screenshot
        print 'Scheduling next screenshot...'
        self.currentShot = self.currentShot + 1
        time.sleep(self.interval)

It prints the message but not executes the os.system instruction until I press the stop button.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

浴红衣 2024-11-12 16:36:48

响应:

您还需要在调用

gtk.gdk.threads_init()

如果您想要使用 gtk 的线程,


gtk.main() 之前调用让 _takeScreenshot() 有一个 while 循环,并且不要为下一个屏幕截图启动新线程。您已经有一个工作线程,例如

您还需要一个线程而不是计时器

def _takeScreenshot(self):
    while self.notDone:
         # take screen shot
         # ..
         time.sleep(self.interval)

然后在您的取消方法中执行以下操作:

def stopScreenshots(self):
    self.notDone = False
    self.timer.join() # wait for thread to finish 

To response:

You also need to call

gtk.gdk.threads_init()

before gtk.main() is called if you want threads with gtk


Let _takeScreenshot() have a while loop instead and do not start a new thread for the next screenshot. You already have a worker thread for this, e.g.

You also need a Thread instead of a Timer

def _takeScreenshot(self):
    while self.notDone:
         # take screen shot
         # ..
         time.sleep(self.interval)

Then in your cancel method do something like:

def stopScreenshots(self):
    self.notDone = False
    self.timer.join() # wait for thread to finish 
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文