Java can';我录屏幕的速度不够快
我正在尝试用Java制作一个记录程序。我宁愿不使用JMF(Java媒体框架)以外的任何外部库。我使用两个Swing计时器(作为Swing应用程序),一个用来捕获屏幕并将其添加到队列,另一个用来将BuffereImage从队列中取出并写入文件。这是我的计时器: 要插入队列,请执行以下操作:Java can';我录屏幕的速度不够快,java,swing,screen-capture,recording,Java,Swing,Screen Capture,Recording,我正在尝试用Java制作一个记录程序。我宁愿不使用JMF(Java媒体框架)以外的任何外部库。我使用两个Swing计时器(作为Swing应用程序),一个用来捕获屏幕并将其添加到队列,另一个用来将BuffereImage从队列中取出并写入文件。这是我的计时器: 要插入队列,请执行以下操作: timer = new Timer(1000/FPS, new ActionListener() { //FPS is a user-inputed value from 1-60 by default its
timer = new Timer(1000/FPS, new ActionListener() { //FPS is a user-inputed value from 1-60 by default its 25
@Override
public void actionPerformed(ActionEvent ae) {
executor.execute(new Runnable() { //executor is a java.util.concurrent.Executor;
//I put them in an executor so the timer wouldn't wait for the code to finish
@Override
public void run() {
try {
images.insert(R.createScreenCapture(Screen)); //Images is my own queue & R is a java.awt.Robot
//Screen is a rectangle that is Toolkit.getDefaultToolkit().getScreenSize()
} catch (Exception e) {
ExceptionPrinter.PrintE(e); //This is just a method to print the exception to me
System.out.print(images.length());
timer.stop();
timer2.stop();
} catch (OutOfMemoryError e) { //This is mainly a debug catch
timer.stop();
timer2.stop();
System.out.print(images.length());
e.printStackTrace();
}
}
});
}
});
要写入图像,请执行以下操作:
timer2 = new Timer(1000 / FPS, new ActionListener() {
@Override
public void actionPerformed(ActionEvent ae) {
executor.execute(new Runnable() {
@Override
public void run() {
try {
if (images.length() != 0) {
if (!(new File("C:").getFreeSpace() <= 10000000)) {
String path=AppRunner.AppR3Directory + "VideoTemp" + File.pathSeparator + file + getModifier() + File.pathSeparator + image + ".JPEG";
//AppRunner.AppR3Directory is the working directory of the program (never changes)
//file is the user-inputed filename & getModifier() is either "" or a number above 0 (for when the program auto-starts another record)
ImageIO.write(images.pop(), "JPEG", new java.io.File(path));
imagelist.add(path); //This adds it to my list of images for when i change it to a .mov (custom array)
image++;
} else {
throw new SecurityException("Not enough memory!");
}
}
} catch (IOException e) {
ExceptionPrinter.PrintE(e);
timer.stop();
timer2.stop();
} catch (SecurityException e) {
ExceptionPrinter.PrintE(e);
timer.stop();
timer2.stop();
}
}
});
timer2=新定时器(1000/FPS,新ActionListener(){
@凌驾
已执行的公共无效行动(行动事件ae){
executor.execute(新的Runnable(){
@凌驾
公开募捐{
试一试{
如果(images.length()!=0){
如果(!(新文件(“C:”).getFreeSpace()尝试从计时器独立运行这些线程。我的意思是,不要使用这些计时器。启动线程,并使用睡眠(1000/FPS)实现计时/>代码> < P>使用Swing <代码>定时器保持屏幕捕获任务是值得的,但是图像写入任务应该被移动到一个简单的<代码>线程在添加时将图像从队列中拉出来。因为您将在多个线程之间进行协调,考虑将队列更改为<代码>阻塞队列< /代码。>.试试。上次测试时,我得到了很好的结果
Windows Media Player说它无法打开它
AFAIR WMP对所有的MOV都这么说。非常恼人,因为它声称文件关联。请与非WMP的玩家一起尝试
从长远来看,您可能希望将MOV转换为另一种格式。使用JMF生成的格式非常大。“例如,默认值为25 FPS,我只能获得6 FPS。”这是什么屏幕分辨率?为了更快地获得更好的帮助,请发布一个。什么是FPS
声明为?这也是一个常见问题,捕获整个屏幕需要花费很多时间…@安德鲁·汤普森:我的屏幕分辨率是1366 x768@MadProgrammer这是一个从JSLIDER中检索到的int值。速度部分已被询问f几个月前:。2004年的bug还没有关闭。我要尝试一下。不,这并没有改变结果。据我所知,在EDT之外调用Robot\createScreenCapture应该是安全的……我可能错了,所以我只是想问你是否知道一些我不知道的事情;)