X

Geertjan's Blog

  • January 31, 2010

Create Your Own Window System on the NetBeans Window System

Geertjan Wielenga
Product Manager
One big reason for using the NetBeans Platform is its out-of-the-box window system. However, maybe you like the concept of a window system, but not how it is implemented in the NetBeans Platform? Not to worry. You can create your own window system on top of the NetBeans Platform's Window System API, which means you'll have a custom window system that still integrates with all of the other NetBeans idioms, via ExplorerManager to explorer views (e.g., BeanTreeView) and Nodes.

Eppleton, the Munich-based NetBeans Platform consultancy, has been learning about this area of the NetBeans Platform recently, for one of its customers. The end result was the integration of the SwingX project's "org.jdesktop.swingx.JXPanel", together with "javax.swing.JLayeredPane", to create the translucent effects of the TopComponents in the screenshot below:

I.e., your TopComponents could be JXPanels, if that's the way you'd prefer them to be. Or something else.

In the image above, there are in fact 3 TopComponents, one of which has this client property in its constructor:

// setting this property informs the Windowmanager that this window is
// our Main Window. Not a standard property.
putClientProperty(TranslucentWindowManager.MAINWINDOW, Boolean.TRUE);

But how to get started with all of this? There's a "DummyWindowManager" in the NetBeans sources that you can start experimenting with. Let's do so now.

  1. In your application, remove core-windows.jar, i.e., you do not want the "Core - Windows" module to be installed in your application, since you'll be providing your own window system.

    A simple way to remove that JAR is to go to "platform.properties" in your application and use this list of disabled modules (definitely won't work in all cases, since your dependencies will be different depending on what else you're using, but if you're starting from scratch, this will be all you'll need):

    disabled.modules=\\
    org.netbeans.api.visual,\\
    org.netbeans.core.execution,\\
    org.netbeans.core.multiview,\\
    org.netbeans.core.nativeaccess,\\org.netbeans.core.windows,\\
    org.netbeans.libs.jsr223,\\
    org.netbeans.modules.applemenu,\\
    org.netbeans.modules.autoupdate.services,\\
    org.netbeans.modules.autoupdate.ui,\\
    org.netbeans.modules.core.kit,\\
    org.netbeans.modules.favorites,\\
    org.netbeans.modules.options.keymap,\\
    org.netbeans.modules.templates,\\
    org.openide.compat,\\
    org.openide.execution,\\
    org.openide.options,\\
    org.openide.util.enumerations

    Note the line in bold below, i.e., that's the line that will result in the "core-windows.jar" to be excluded.


  2. Now add this class to a module in your application:

    MyWindowManager.java

    Especially note this class-level annotation, which results in your window manager replacing the one provided by the NetBeans Platform:

    @ServiceProvider(service = WindowManager.class, supersedes = "org.netbeans.core.windows.WindowManagerImpl")

    In other words, when the module has been built, you'll find a META-INF/services registration consisting of these entries:

    org.demo.winsys.MyWindowManager
    #-org.netbeans.core.windows.WindowManagerImpl

    Note: Make sure to add the required NetBeans API modules to the application (i.e., Nodes API, Window System API, and Utilities API).


  3. Somehow you now need to open your TopComponents into your new window system. Normally the opening of the TopComponents would be handled by core-windows.jar, which you have now excluded. So now you need to open them manually, i.e., yourself. For example, in a ModuleInstall class, add this code:
    @Override
    public void restored() {
    WindowManager.getDefault().invokeWhenUIReady(new Runnable() {
    public void run() {
    View1TopComponent.findInstance().open();
    View2TopComponent.findInstance().open();
    }
    });
    }

  4. When you run the application, you'll see this result:

Now look more closely at MyWindowManager.java and change it to fit your business requirements.

Join the discussion

Comments ( 15 )
  • Jesse Glick Sunday, January 31, 2010

    If you omit core.windows from your app, then there is no need to supersede core.windows.WindowManagerImpl.


  • Geertjan Wielenga Sunday, January 31, 2010

    I would have thought the same. Tried that too. But then there's a class cast problem or as Toni puts it in an e-mail to me: "

    One small thing: core.windows has to be excluded due to a bug. Something get's the WindowManager from Lookup and tries to cast it to a concrete implementation. This leads to an exception. If that could easily be fixed we could probably also reuse the window system functionality like persistence and launching windows automatically."


  • Eduardo Costa Monday, February 1, 2010

    This is incredibly cool! I asked about this "feature" on NB forum, without any concrete answer. Now, you gave me the answer with an "example" as a bonus. IMHO, you really deserve a "NB-guru" status! :)


  • Geertjan Wielenga Monday, February 1, 2010

    Thanks Eduardo. Would be great to get a screenshot from you when you've made some progress with creating your own window system. :-)


  • Eduardo Costa Thursday, February 4, 2010

    Nice! Worked like a charm! Using Feed Reader sample, I created a "window manager" module with your MyWindowManager and voila! Good bye NB WM and welcome lots of ideas! :)

    PS: I will post some screenshots as soon as I have something useful


  • Eduardo Costa Thursday, February 4, 2010

    Nice! Worked like a charm using Feed Reader sample! Good bye NB WM and welcome lots of ideas!

    PS: I will post some screenshots as soon as I have something useful


  • Vincent Cantin Wednesday, February 10, 2010

    An opened door on the 3rd dimension ? :-)


  • guest Sunday, April 15, 2012

    You need to update your url for MyWindowManager.java to this: https://blogs.oracle.com/geertjan/resource/MyWindowManager.java


  • Geertjan Sunday, April 15, 2012

    Thanks, done!


  • guest Tuesday, June 18, 2013

    Thinking one step further:

    Is it possible to start MyWindowManager in fullscreen mode?

    So I could think of a desktop-manager for Java apps...


  • Geertjan Tuesday, June 18, 2013

    import org.openide.awt.Actions;

    import org.openide.windows.OnShowing;

    @OnShowing

    public class FullScreenAtStartUp implements Runnable {

    @Override

    public void run() {

    Actions.forID("Window", "org.netbeans.core.windows.actions.ToggleFullScreenAction").actionPerformed(null);

    }

    }


  • guest Tuesday, June 18, 2013

    MyWindowManager.java can not find the function "invokeWhenUIReady" and "PROP_TC_OPENED" and "PROP_TC_CLOSED".


  • guest Tuesday, June 18, 2013

    can not find the function "invokeWhenUIReady" and two fields "PROP_TC_OPENED" and "PROP_TC_CLOSED".


  • Geertjan Tuesday, June 18, 2013

    Two seconds of googling the terms "invokeWhenUIReady netbeans" gives me the answer to your question. Try google. It's free. It works.


  • guest Friday, June 28, 2013

    Is this windows manager still keep the tearing off tab feature of netbeans platform? Are the Main Window and View1 windows independent (if Main window is closed and View1 window is still open)?

    Thank you very much!


Please enter your name.Please provide a valid email address.Please enter a comment.CAPTCHA challenge response provided was incorrect. Please try again.