How to set focus the already running application?

2020-03-31 04:16发布

问题:

I am using a ServerSocket port to run one instance only of my Java Swing application, so if a user tries to open another instance of the program, i show him a warning that "Another instance is already open". This works fine, but instead of showing this message i want to set focus on the running application itself, like some programs does (MSN Messenger), even if it was minimized.

Is there a solution for this for various operating systems ?

回答1:

Since you use a server socket I assume that you use the java.net.BindException to detect that you application is already running. If you start a second instance you could send a control message which instructs you first app to normalize (if minimized) before exiting.

if (msg == BRING_TO_FRONT ) {
   frame.setState(Frame.NORMAL);
   frame.toFront();
}


回答2:

I don't know if this is absolutely right, but here's the final code i've used and it works fine for me :

public class Loader {
private static final int PORT = 9999;
private static ServerSocket serverSocket = null;  // Server
private static Socket socket = null;  // CLient
private static final String focusProgram = "FOCUS";

public static void main(String[] args) {
    if( !isProgramRunning() ) {
        Main main = new Main();
        main.setVisible( true );
    }
    else {
        System.exit( 2 );
    }
}

private static boolean isProgramRunning() {
    try {
        serverSocket = new ServerSocket(PORT,0,InetAddress.getByAddress(new byte[] {127,0,0,1}));  // Bind to localhost adapter with a zero connection queue. 
        SwingWorker<String, Void> anotherThread = new SwingWorker<String, Void>() {  // Do some code in another normal thread.
            @Override
            public String doInBackground() {  // This method is to execute a long code in the other thread in background.
                serverSocketListener();
                return "";
            }
        };
        anotherThread.execute();  // Execute the other tread.
    }
    catch (BindException e) {
        System.err.println("Already running.");
        clientSocketListener();

        return true;
    }
    catch (IOException e) {
        System.err.println("Unexpected error.");
        e.printStackTrace();

        return true;
    }

    return false;
}

public static void serverSocketListener() {  // Server socket
    try {
        System.out.println( "Listener socket opened to prevent any other program instance." );
        socket = serverSocket.accept();
        BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream()));

        if( in.readLine().equals( focusProgram ) ) {  // Restore the opened instance however you want.
            Global.getCurrentFrame().setState(Frame.NORMAL);
            Global.getCurrentFrame().toFront();
        }       
    } catch (IOException e) {
        e.printStackTrace();
        System.exit(-1);
    }
}

public static void clientSocketListener() {  // Client socket
    try{
        socket = new Socket(InetAddress.getByAddress( new byte[] {127,0,0,1}), PORT );
        PrintWriter out = new PrintWriter( socket.getOutputStream(), true );
        out.println( focusProgram );
    } catch  (IOException e) {
        System.out.println("No I/O");
        System.exit(1);
    }
}

}