Quaqua JSheet - Display a sheet in a Java Swing application on Mac OS X

I'm always looking for ways to make my Java Swing applications on Mac OS X look more and more like native Mac applications, and when a co-worker mentioned the name Quaqua, I decided to take a look at that library/framework one more time. I had looked at it before, but this time, looking at it with a new mindset, I noticed it offers a JSheet implementation. As their documentation states, the "JSheet roughly implements the look and feel of a Mac OS X Cocoa NSSheet component."

It would be very cool if I could use the Mac "sheet" approach in my Swing applications (as opposed to a traditional JDialog on other platforms), so I thought I'd take a look at what Quaqua has to offer.

A sample Java program

To that end I created the following Java sample application to see what the Quaqua JSheet implementation looks like. I'll share the Java source code here first, then describe what it does:

package com.devdaily.quaqua.test;

import java.awt.*;
import javax.swing.*;
import ch.randelshofer.quaqua.JSheet;
import ch.randelshofer.quaqua.SheetEvent;
import ch.randelshofer.quaqua.SheetListener;

/**
 * A free Java program to test and demonstrate the Quaqua JSheet
 * implementation.
 * Created by Alvin Alexander, devdaily.com.
 */
public class QuaquaTest
{

  public static void main(String[] args)
  throws Exception
  {
    System.setProperty("Quaqua.tabLayoutPolicy", "wrap");
    UIManager.setLookAndFeel("ch.randelshofer.quaqua.QuaquaLookAndFeel");
    new QuaquaTest();
  }

  public QuaquaTest()
  {
    SwingUtilities.invokeLater(new Runnable()
    {
      public void run()
      {
        JFrame editorFrame = new JFrame("Java Mac OS X Quaqua Test");
        constructAndDisplayJFrame(editorFrame);
        displayJSheet(editorFrame);
      }
      
    });
  }

  private void constructAndDisplayJFrame(JFrame editorFrame)
  {
    editorFrame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
    editorFrame.setPreferredSize(new Dimension(300, 185));
    editorFrame.pack();
    editorFrame.setLocationRelativeTo(null);
    editorFrame.setVisible(true);
  }

  /**
   * Displays a JSheet using the Quaqua framework.
   * This code was just copied from the Quaqua help pages.
   */
  private void displayJSheet(final JFrame editorFrame)
  {
    JOptionPane pane = new JOptionPane(
        "<html>"+UIManager.getString("OptionPane.css")+
        "<b>Do you want to save changes to this document<br>"+
        "before closing?</b><p>"+
        "If you don't save, your changes will be lost.",
        JOptionPane.WARNING_MESSAGE
    );
    Object[] options = { "Save", "Cancel", "Don't Save" };
    pane.setOptions(options);
    pane.setInitialValue(options[0]);
    pane.putClientProperty("Quaqua.OptionPane.destructiveOption", new Integer(2));
    JSheet.showSheet(pane, editorFrame, new SheetListener() {
        public void optionSelected(SheetEvent evt) {
            Object value = evt.getValue();
            if (value == null || value.equals("Cancel")) {
              editorFrame.setEnabled(true);
            } else if (value.equals("Don't Save")) {
              editorFrame.dispose();
            } else if (value.equals("Save")) {
               //saveChanges();
            }
        }
    });
  }
}

Discussion

This program does the following things:

  1. Does a little Quaqua setup work in the main method.
  2. Creates an empty JFrame.
  3. Uses some source code from the Quaqua help documentation to create a JOptionPane then display that JOptionPane with a Quaqua JSheet.

If you compile and run this program on your own system, you'll see that all of this happens as soon as the program is run. That is, the JFrame will be displayed, and then the JSheet will be displayed immediately.