线程不会在我想要的时候停止? (JAVA) [英] Thread won't stop when I want it to? (Java)
问题描述
我的屏幕录制应用程序中有一个不合作的帖子:
I have a thread in my screen recording application that won't cooperate:
package recorder;
import java.awt.AWTException;
import java.awt.Insets;
import java.io.IOException;
import javax.swing.JFrame;
public class RepeatThread extends Thread {
volatile boolean stop;
public volatile Thread recordingThread;
JFrame frame;
int count = 0;
RepeatThread( JFrame myFrame ) {
stop = false;
frame = myFrame;
}
public void run() {
while( stop == false ) {
int loopDelay = 33; // 33 is approx. 1000/30, or 30 fps
long loopStartTime = System.currentTimeMillis();
Insets insets = frame.getInsets(); // Get the shape we're recording
try {
ScreenRecorder.capture( frame.getX() + insets.left,
frame.getY() + insets.top, frame.getWidth()
- ( insets.left + insets.right ),
frame.getHeight() - ( insets.top + insets.bottom ) );
}
catch( AWTException e1 ) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
catch( IOException e1 ) {
// TODO Auto-generated catch block
e1.printStackTrace();
} // Add another picture
long loopEndTime = System.currentTimeMillis();
int loopTime = (int )( loopEndTime - loopStartTime );
if( loopTime < loopDelay ) {
try {
sleep( loopDelay - loopTime ); // If we have extra time,
// sleep
}
catch( Exception e ) {
} // If something interrupts it, I don't give a crap; just
// ignore it
}
}
}
public void endThread() {
stop = true;
count = 0;
ScreenRecorder.reset();
// Once I get this annoying thread to work, I have to make the pictures
// into a video here!
}
}
多年来一直困扰着我。它会定期将截图截取到指定区域。
It's been bugging me for ages. It periodically takes screenshots to the specified area.
当您开始录制时,它会隐藏(取消激活)窗口。在Mac上,当您提供应用程序焦点时,任何隐藏的窗口都将激活。在我的班级 WListener
(我已经确认工作),我有:
When you start recording, it hides (decativates) the window. On a Mac, when you give an application focus, any hidden windows will activate. In my class WListener
(which I have confirmed to work), I have:
public void windowActivated(WindowEvent e) {
if(ScreenRecorder.recordingThread != null) {
ScreenRecorder.recordingThread.endThread();
}
}
那么应该发生的是,截屏时,线程停止点击应用程序。但是,我必须粗暴地搞砸了一些东西,因为当线程运行时,它甚至不会让窗口重新出现。这是我的第一个帖子,所以我期待这样一个奇怪的问题。你知道什么是错的吗?
So what SHOULD happen is, the screenshot-taking thread stops when he clicks on the application. However, I must be brutally screwing something up, because when the thread is running, it won't even let the window reappear. This is my first thread, so I expected a weird problem like this. Do you know what's wrong?
编辑:好的,我做了停止波动,这里是我做线程的地方:
Okay, I made stop volatile, and here is the place where I make the thread:
package recorder;
import java.awt.AWTException;
import java.awt.Robot;
import java.awt.Rectangle;
import java.awt.image.BufferedImage;
import java.io.*;
import javax.imageio.ImageIO;
import javax.swing.JFrame;
public class ScreenRecorder {
static RepeatThread recordingThread;
static int count;
public static void record(JFrame frame) {
if(recordingThread == null) { //Make a new thread if we don't have one
recordingThread = new RepeatThread(frame);
recordingThread.start();
}
}
public static void capture(int x, int y, int width, int height) throws AWTException, IOException {
// capture the whole screen
//BufferedImage screencapture = new Robot().createScreenCapture(
// new Rectangle(Toolkit.getDefaultToolkit().getScreenSize()) );
BufferedImage screencapture = new Robot().createScreenCapture(
new Rectangle( x, y, width, height));
// Save as JPEG
File directory = new File("/Users/stuart/Movies/temp");
if(directory.exists() == false) {
directory.mkdirs();
}
count ++;
File file = new File("/Users/stuart/Movies/temp/screencapture" + count + ".jpg");
ImageIO.write(screencapture, "jpg", file);
// Save as PNG
// File file = new File("screencapture.png");
// ImageIO.write(screencapture, "png", file);
}
public static void stop() {
}
public static void reset() {
count = 0;
}
}
推荐答案
自你显然试图每X毫秒执行一个工作单元,如果你使用Java的执行程序,这将会容易得多:
Since you are clearly trying to execute a unit of work every X milliseconds, this will be far far easier if you use Java's Executors:
ScheduledExecutorService service = executors.newSingleThreadScheduledExecutor();
service.scheduleAtFixedRate(new Runnable() {
public void run() {
// do one iteration of your work
ScreenRecorder.capture(...);
...
}
}, 0L, 33L, TimeUnit.MILLISECONDS);
...
service.shutdown(); // to stop
使用线程
并不像你所做的那样凌乱(不是在挖你,只是说它在Java中并不那么糟糕),但上述仍然是迄今为止最简单的选择。
Doing this manually with Thread
isn't nearly as messy as you're making it (not a dig at you, just saying it's not that terrible in Java), but the above is still by far the simplest option.
这篇关于线程不会在我想要的时候停止? (JAVA)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!