Supporting the Mac OS menubar in JavaFX

Daniel Zwolenski zonski at googlemail.com
Wed Dec 14 16:09:22 PST 2011


On Thu, Dec 15, 2011 at 10:31 AM, Jonathan Giles
<jonathan.giles at oracle.com>wrote:

> Hi All,
>
> Here's an update from the UI controls team as to how we see the native Mac
> OS menubar support working. Your thoughts are appreciated.
>
> After discussing it again today, we think that the approach suggested by
> Richard in an earlier email in this thread makes the best sense, in terms
> of modularity and code cleanliness. I'll explain this further shortly...
>
> The thinking is to add a new property to javafx.scene.control.MenuBar. We
> haven't settled on a name, but it's something along the lines of 'native',
> 'global', 'globalMenuBar', 'screenMenuBar', or 'applicationMenuBar'.
> Whatever property name we use, we'll expand it out to have the usual
> set*/get*/*property methods. This would be the only public API we end up
> adding for native menubar support. For the remainder of this email I refer
> to this property as 'native'.
>
> This property will by default be true, indicating that on platforms where
> we support native integration, it'll happen by default.
>

This is not backwards compatible with 2.0. Everyone is going to have to
start being very careful about this unfortunately in all future updates.

Backwards compatibility for a GUI is more than just the API, it is also the
visual appearance. If I have a GUI written in 2.0 that has a MenuBar in it
somewhere in the GUI that never moves to a native level, and then suddenly
in a future release that menu bar has jumped out to a higher level, my GUI
has changed just because of a JFX update - definitely not what we want to
see happen.

If JFX wasn't (planned to be) part of the JDK and hence getting included in
the auto-updating stuff, we could be more relaxed on backwards
compatibility as the developer can specify specific version and control the
upgrade path and timing. According to conversations with Igor about the
deployment, the JFX install will always upgrade to the latest version, you
can't fix it to an old version. There's a definite argument here against
co-bundling but that's another debate.

I would very much suggest going for a default value of 'false' on this for
backwards compatibility. It also reduces the chance of someone using a menu
bar and having it become the application level one accidentally.


> On a platform that supports native integration, we'll find the 'first'
> MenuBar in the scene that has the 'native' property set to true. We can't
> guarantee that we'll find necessarily the physically top-most MenuBar as
> that is really a matter of how the scenegraph is laid out. Of course, this
> is only a problem in situations where the scene contains multiple MenuBars
> where 'native' is true in more than one of them, which we hope won't often
> be the case. If a Scene does have multiple MenuBars with 'native' set to
> true, the behaviour is undefined. If the wrong MenuBar is made native, you
> can help provide a hint by setting 'native' to false in the relevant
> place(s).
>

Sounds a bit loose. Might it not be better to fail with an error if more
than one MenuBar is flagged as native.


> We'll also hook into the Stage and listen to the relevant events, such
> that when a Stage gains focus, we'll switch in any native menubars found in
> the scene of that stage.


What's the plan for specifying a MenuBar for when all stages are closed?
Isn't that a requirement for Mac?


> If no relevant MenuBar is found, then we can either retain the MenuBar
> from the previous stage, or null it out. I'm going to assume the former is
> by far going to win this vote, but feel free to surprise me.
>
> Using this approach, developer code should be cleaner. Your user interface
> should position a MenuBar where it makes sense for your application,
> regardless of the operating system (normally at the very top of your
> scene).


I disagree with the "top of screen" bit, but also with the whole idea that
a MenuBar should be handled at the OS level - this is very specific to Mac.
The modern trend on Windows is to not use a MenuBar at all. You could for
example have a 'page' of menu options that you go to (popularised by the
web), or a drop-down menu like chrome does, or a ribbon-menu-bar like
Office has, or no menu bar at all like Windows Explorer in Win7 (you can
get to it by pressing ALT but this is just there so us admin geeks and
power users don't complain).

None of my apps have menu bars. What will go in the Menu bar on mac in this
case? I suspect I will have to do something on Mac for the menu bar (just
because Mac users expect it) - I don't want to have to put a visible
'MenuBar' in my windows application as a result?

On platforms where native integration is supported, the JavaFX-rendered
> MenuBar will not be rendered (although it'll likely remain in the
> scenegraph as a no-op control). If the 'native' property changes, we'll
> flick between the native and JavaFX-rendered MenuBar as expected. This
> approach means there is no operating system dependent code in your user
> interface.
>
> As I mentioned - we're totally open to discussion on any of these points.
> Any thoughts?
>
> -- Jonathan
>
>
> On 10/12/2011 8:56 a.m., Jonathan Giles wrote:
>
>> Hi all,
>>
>> One of the things we're planning to support in JavaFX 2.1 is the native
>> Mac OS menubar. This email is intended primarily to discuss the API one
>> expects to see to set a MenuBar in the native Mac OS menubar area. Your
>> feedback is sought and will be very much appreciated.
>>
>> The current thinking is that Application feels like the right place to
>> specify a global, application-wide javafx.scene.control.MenuBar on. It
>> could be assumed that if a developer were to set this property, and the
>> operating system upon which the end-user was running the JavaFX application
>> was Mac OS, that the menubar will be displayed using the native Mac OS
>> menubar. Of course, if a developer wants a cross-platform look and feel,
>> they could just place the MenuBar in the stage as per usual and it would
>> display as it currently does. This approach opens up a number of questions
>> and issues:
>>
>> 1) What happens in the case of the end-user being on Windows? Is the
>> Application.MenuBar ignored, or is it automagically added to the main
>> Stage? (I would argue for totally ignoring it....but that leads to the next
>> point).
>> 2) This approach means there needs to be operating specific code in the
>> UI to test whether a non-native MenuBar should be added (in the case of
>> Windows, for example). This starts to clutter the UI code, and without
>> careful consideration by the developer may result in needing to duplicate
>> their MenuBar code. Is there a better approach?
>>
>> Another place to specify a MenuBar would be on Stage, rather than (or in
>> addition to), Application. Having a MenuBar property on Stage would allow
>> for the MenuBar to change based on the currently focused Stage - but I'm
>> not certain this is desirable or even the expected behaviour of Mac OS.
>> Therefore, I'm thinking that this is not likely to happen unless we hear
>> otherwise.
>>
>> Like I said, we're at a very early exploration point in this process. The
>> controls team is very keen to hear feedback from the community, as well as
>> from the owners of the Application API, and the Mac OS experts on this list.
>>
>> Thanks,
>> -- Jonathan
>>
>


More information about the openjfx-dev mailing list