I'm using Jpype to use a java class into a python script. The java class involves the use of AWT library: and this seems to be the problem.
This the python script:
import jpype
import os.path
import threading
jarpath = os.path.join(os.path.abspath('.'), 'build/jar')
target=jpype.startJVM(jpype.getDefaultJVMPath(), "-Djava.ext.dirs=%s" % jarpath)
Capture = jpype.JClass('Capture') # Capture is the class, contained in ./ folder
t = Capture(50,354,90,90,130,650,"num",36); # create the instance
jpype.shutdownJVM()
So I'm just trying to instantiate the class, and just exit. This the java class. I'm reporting only the code that is causing error:
class Capture {
public Capture(int x, int y, int width, int height, int mouseNextX, int mouseNextY, final String fnamestart, final int countmax) {
//...
images = new ArrayList<BufferedImage>();
getImages(fnamestart,countmax); //THIS is the problem
}
// reference to getImages() method:
public void getImages(String fname, int countmax) {
images.clear();
for(int i=0; i<=countmax; i++) {
try {
BufferedImage img = ImageIO.read(new File(fname+i+".bmp"));
images.add(img);
} catch(IOException e) {
images.add(null);
}
}
}
}
This code, when running python script, raise me the following error:
jpype._jexception.VirtualMachineErrorPyRaisable: java.lang.InternalError: Can't start
the AWT because Java was started on the first thread. Make sure StartOnFirstThread is
not specified in your application's Info.plist or on the command line
Long story short, this is a known problem: Eclipse had "its own version", then solved. Unfortunately no one spoke about this problem relating to jpype.
I tried these solutions, that didn't worked:
In python script, launching a thread before starting the JVM. And then starting the JVM in another thread.
In python script, starting the JVM with the parameter
-XstartOnFirstThread
:target=jpype.startJVM(jpype.getDefaultJVMPath(), "-XStartOnFirstThread -Djava.ext.dirs=%s" % jarpath)
In the java code: using the AWT method
invokeLater
, in the constructor:java.awt.EventQueue.invokeLater(new Runnable() { public void run() { images = new ArrayList<BufferedImage>(); getImages(fnamestart,countmax); } });
I really don't know what to do, hoping that you will help me. Thank you,
Giovanni