imagej / imagej-launcher

The ImageJ native launcher
https://imagej.net/learn/launcher
BSD 2-Clause "Simplified" License
21 stars 23 forks source link

Switch to JavaFX native launcher #33

Closed hinerm closed 1 month ago

hinerm commented 9 years ago

Our goal is to simplify the ImageJ launch process so we are not so intimately tied to a custom, complex launcher with its own JDK version concerns.

Perfect world goals include:

JavaFX is currently our first choice for deployment. It appears to be capable of building standalone (no bundled JRE) and self-contained (bundled JRE) apps cross-platform. These is also a maven plugin

JavaFX issues that need to be solved:

hinerm commented 9 years ago

JavaFX may solve this issue

hinerm commented 9 years ago

However, we need to document what features we may be losing from migrating to JavaFX..

hinerm commented 9 years ago

Note that whatever solution we settle on we also should ensure our Java3D problems are solved forever and ever.

@ctrueden has a fork of Java 3D 1.6 that is Mavenized.. that may be sufficient..

ctrueden commented 9 years ago

JavaFX provides a developer-facing API for controlling which parameters go to the JVM (e.g., memory settings). Devs can write code letting users set these in their UI of choice, and propagate the information to the JavaFX launcher in a platform-agnostic way (uses Java Prefs API internally). See UserJvmOptionsService API docs for details.

ctrueden commented 9 years ago

Experimental javafx branch can create standalone app (i.e., a double-clickable JAR file which leans on the installed system JRE) as well as a self-contained app (i.e., an app which bundles its own JRE).

Unfortunately, there is no middle ground in JavaFX by default: you cannot have an app (EXE on Windows, .app bundle on OS X, etc.) which does not bundle a JRE.

Or can you? Yes you can! This would be great so that users still get JRE security updates without it being ImageJ's responsibility.

ctrueden commented 9 years ago

I updated the javafx branch in an attempt to use a custom preloader, but it doesn't work yet.

To test things at a lower level—and also to test the <fx:platform basedir=""/> hack for creating a self-contained app without JRE—it is probably time to start calling the Ant tasks directly. Once those are working, we can debug into the javafx-maven-plugin to figure out how to enhance/fix it accordingly.

ctrueden commented 9 years ago

I tested the <fx:platform basedir=""/> thing to create a self-contained bundle sans JRE, and it works. imagej/imagej@f29b4ec0472bfd1aea748e5d28bd4b699368716a Hooray!

This might not actually be the direction we want to go, but it is nice to know we can do it.

Now, we just have to fully understand preloaders...

hinerm commented 9 years ago

Added javafx-maven-plugin issues:

FibreFoX commented 9 years ago

Preloaders. WONTUSE preloaders live in the same JVM as the application. They will not meet our needs.

Just my two cents: preloaders are not fully supported on native app launchers, but can be archived by other ways (I noted it down here)

You could create that kind of "splash-screens" as first stage and just switching when ready (like proposed as solution 5 at stackoverflow)

FibreFoX commented 9 years ago

Hi, just wanted to inform you guys about a pull-request I made for supporting UserJvmOptionsService via javafx-maven-plugin, here is the issue-ticket about it, maybe you want to try this out (just checked back, because i remembered you thinking about using that API).

Hopefully you don't see this as spamming ;)

ctrueden commented 9 years ago

@FibreFoX Thanks for the heads up, and for your great responsiveness in general. :smile: Will try to process and review the linked issue later this month.

ctrueden commented 8 years ago

Reminder to myself: when progress is made on this issue, follow up on Fiji bug #933 with a link to a JavaFX-based Fiji application bundle, for Antonio Sechi to try out.

FibreFoX commented 8 years ago

To test: what happens if you try running a no-JRE JFX distribution on a platform without Java installed?

When the bundle does not contain the stripped JRE (which is generated by the javafx-bundler itself), the generated .cfg-file contains an "empty" entry app.runtime=, which can be seen here. Running the native launcher will search for the .cfg-file, if there was something specified, that path will be taken as JRE-root, which can be found here. I crossed these files while bugtracking issue 124. This means, that when not having the runtime bundled, at least on windows-systems, the local installed version will be taken (which might reduce the size of the bundle, but increases problems with not-tested java-versions, or outdated ones...)

There still is some problem which I found just right now with the javafx-maven-plugin: normal way for me was to specify an empty setting:

<bundleArguments>
    <runtime />
</bundleArguments>

But the resulting .cfg-file still containes the wrong line. This is something, I will fix in the next days. EDIT: this is fixed in current 8.1.6-snapshot

Command line arguments - we need to be able to support things like --debugger=8000 which the native launcher translated to JVM argument(s).

For the debugger-thing, maybe you want to create multiple native launchers, this feature is available with normal ant-version of java(fx)bundler and will come in the next days (I'm already developing this feature). All CLI-arguments can be passed normally (and accessed in the main-method, there exists a IT-project for this), but to activate special java-properties I suggest to have multiple pre-configured launchers. Maybe it'll work to have UserJvmOptionsService for this instead of different native launchers, this is supported by putting the packager.jar as system-scoped dependency to your project, like in this IT-project (not nice, but working). All in all these ways might remove the need of own native launchers.

ctrueden commented 8 years ago

Thanks @FibreFoX. All the links in particular are very helpful and much appreciated.

We are increasingly leaning toward always bundling a JRE in the platform-specific distributions, for the reasons you mention. We want to ship the app via modern "blessed" distribution mechanisms such as the App Store on OS X, to make our users' lives easier. So at least on OS X we would need to bundle a JRE anyway.

Regarding multiple native launchers: my current thinking is to have one native launcher with sensible defaults and configurability via the UserJvmOptionsService... and then one shell script launcher for developers which provides total customizability—e.g., launching with a debug port open. I cannot come up with a use case for non-developer users where specifying the desired JVM flags in a UI window, and then restarting, isn't good enough.

FibreFoX commented 8 years ago

Native launcher produced by debian bundler fails with no packaged JRE (message complains that JRE can't be found)

This might be since java 1.8.0 update 60, see the issue on javafx-maven-plugin, this got a workaround in latest snapshot-version (had this problem on windows too)

exe installer installed to C:\Users\username\AppData\Local\ImageJ msi installer installed to C:\Program Files\ImageJ

This can be changed by modifying the generated installer-file (wsx), which is placed under some temporary folder, will be shown/reported, when javafx-maven-plugin contains <verbose>true</verbose>, same goes for msi-installer. In current JDK (since update 60) there seems to exist one specific bundleArgument to make installation-target selectable, I have tried it and it seems to work as expected (but with defaults you listed above); bundle argument for both: exe-bundler and msi-bundler:

<bundleArgument>
    <installdirChooser>true</installdirChooser>
</bundleArgument>

The default installation paths will be determined by the bundle argument <systemWide>.

FibreFoX commented 8 years ago

For the splash-screen, because I don't want to have preloader-magic, I'm using some launcher-class which encapsulates some heavier calculationparts while showing slashscreen. I've created a GIST about this already which is free to use, but might not be the best solution. The reason I took that approach: Showing some messsages while loading user-settings or processing some signals which are business-logic, which does not fit into normal "splash-screen"-logic.

FibreFoX commented 8 years ago

:smile: oh, and sorry for spamming your thread here

ctrueden commented 5 years ago

Apparently there is now a Java Packager which is (will become?) part of Java 12.

Here is an article discussing it: https://medium.com/@adam_carroll/java-packager-with-jdk11-31b3d620f4a8

So the Java Packager will need to be evaluated as well, as part of this work.

ctrueden commented 1 month ago

We are switching the Fiji launcher to a new one we made called Jaunch. It is much more flexible than the built-in Java jpackage standalone app bundling tool.