Question

I'm trying to use Javas JFileChooser in my LibGDX scene2d project, but as soon as I launch JFileChooser my program freezes.

Here is the code I use to launch file chooser:

private String getPath(){
    String path = "";
        fc.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);

        int returnVal = fc.showOpenDialog(null);
        if (returnVal == JFileChooser.APPROVE_OPTION) {
            file = fc.getSelectedFile();
            try {
                path = file.getAbsolutePath();
            } catch (Exception ex) {
                System.out.println("problem accessing file" + file.getAbsolutePath() + "\n" + ex.getMessage());
            }
        } else {
            System.out.println("File access cancelled by user.");
        }
        return path;
    }

is it swing and libgdx compability problem or is there something I am missing? Same code works perfectly with nativa java projects. Except instead of: fc.showOpenDialog(null); I use: fc.showOpenDialog(button); // button is the JButton that triggers the event.

any idea what am I doing wrong?

EDIT: I don't really mind if it wont work on other platforms than Windows.

BUT if I choose to go with cross platform solution, and use LibGDX's method, do I have to create file chooser class with UI from scratch all by myself?

Was it helpful?

Solution

Ok based on your comments from the answer above I get a sense that what you are trying to do is invoke a swing window INSIDE your LibGDX game window, which is an open GL rendering scene.

Let me stop you right there. The swing toolkit invokes its own rendering engine, because it's not intended for this purpose at all - it's intended for desktop applications. So when you instantiate the dialogue, all sorts of other oracle java stuff gets instantiated along with it, like the Graphics2D class. You can't just add this class to a scene2D stage and expect that it draws. They don't implement the same interfaces or inherit from the same base classes. The draw(Graphics2D graphics) method that your JFileChooser implements is not the same as whatever draw(SomeClass foo) method that your libGDX classes implement.

So if you want to make a file chooser window, you need to start looking at the libGDX widget libraries. There might be something that someone has put together already, but my approach for my next libGDX project is going to be to extend these classes for my own UI libraries. I don't know what your project is, or what your timeline is like, but it's certainly a better approach then trying to adapt the swing toolkit to render in an OpenGL rendering scene.

edit

After some quick reading, I'm going to go one further and hazard a guess that the way the swing toolkit gets rendered is entirely dependent on the implementation of the JVM for a specific platform. Now this is where my CS knowledge starts to be a little limited, but I would hazard another guess that this is way way different than the LWJGL implementation of OpenGl by way of using Java wrappers for C libraries.

OTHER TIPS

Personally I dislike the existing FileChooser UIs inside LibGDX. So I created a solution which works using the JFileChooser. Here is some quick and dirty code:

new Thread(new Runnable() {             
    @Override
    public void run() {
        JFileChooser chooser = new JFileChooser();
        JFrame f = new JFrame();
        f.setVisible(true);
        f.toFront();
        f.setVisible(false);
        int res = chooser.showSaveDialog(f);
        f.dispose();
        if (res == JFileChooser.APPROVE_OPTION) {
            //Do some stuff     
        }
    }
}).start();

This will open the FileChooser in front of the LibGDX window without blocking the main Thread. Just tested this on Windows 7, 8, 10 and it only works in window mode ofc.

Coming late to the party but if the point of the question is to invoke a "native" ie. non-gdx file chooser from a libgdx project I made a library to do so here: https://github.com/spookygames/gdx-nativefilechooser.

Example from the readme:

// Configure
NativeFileChooserConfiguration conf = new NativeFileChooserConfiguration();

// Starting from user's dir
conf.directory = Gdx.files.absolute(System.getProperty("user.home"));

// Filter out all files which do not have the .ogg extension and are not of an audio MIME type - belt and braces
conf.mimeFilter = "audio/*";
conf.nameFilter = new FilenameFilter() {
    @Override
    public boolean accept(File dir, String name) {
        return name.endsWith("ogg");
    }
};

// Add a nice title
conf.title = "Choose audio file";

fileChooser.chooseFile(conf, new NativeFileChooserCallback() {
    @Override
    public void onFileChosen(FileHandle file) {
        // Do stuff with file, yay!
    }

    @Override
    public void onCancellation() {
        // Warn user how rude it can be to cancel developer's effort
    }

    @Override
    public void onError(Exception exception) {
        // Handle error (hint: use exception type)
    }
});

On the desktop, this example will currently launch an AWT FileDialog (not exactly what is asked) yet a Swing version is currently on the master branch and should be incorporated to the next version of the lib.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top