Recently, some non-weak discussions (for an example, see
here ,
here and
here , and
this one ) on Electron and its influence on the development of desktop applications have developed on programming forums.
If you do not know
Electron , then this is essentially a web browser (
Chromium ) in which only your web application works ... like a real desktop program (no, this is not a joke) ... it gives you the opportunity to use the web stack and develop cross-platform desktop applications.
The newest, hipster desktop applications nowadays are made on Electron, including
Slack ,
VS Code ,
Atom and
GitHub Desktop . Extraordinary success.
')
We have been writing desktop programs for decades. On the other hand, the web only began to evolve less than 20 years ago, and for almost all of this time it served only to deliver documents and animated gifs. Nobody used it to create full-fledged applications, even the simplest ones!
Ten years ago, it was impossible to imagine that a stack of web technologies could be used to create a desktop application. But 2017 has come, and many
smart people believe that Electron is a great idea!
This is not so much the result of the superiority of the web stack for creating applications (it is far from such superiority, and hardly anyone would argue that the
web is a mess ), as the failure of existing frameworks for developing UI on desktops. If people prefer to ship an entire web browser with their programs just to use great tools like JavaScript (sarcasm) for development, something went completely wrong.
So what are these terrible alternatives that have lost the web stack competition?
I decided to take a look and create a real application on one of these technologies.
Alternatives to Electron
If you don't mind that several development groups will create different versions of the application for different OSs, the options look like this:
AppKit for MacOS,
WPF for Windows (I'm not a developer for specific platforms, so let me know what options these days are more popular).
However, the real competitors of Electron are multiplatform frameworks. I think among them the most popular today are
GTK + ,
Qt and
JavaFX .
GTK +
GTK + is written in C, but is associated with many
other languages . This framework has been used to develop the excellent
GNOME-3 platform.
Qt
Qt seems to be the most popular alternative to Electron in discussions that I came across ... This is a C ++ library, but also related to
other languages (although it seems that none of them are supported on a commercial basis, and it is difficult to say how fine-tuned they are). Qt seems to be a
popular choice for embedded systems.
Javafx
However, in this article I will focus on developing JavaFX desktop applications, because I believe that JavaFX and JVM are great for desktop programs.
Whatever you think of JVM, there is no other platform (except maybe Electron itself!), So simple for cross-platform development. Once you have created your jar, on any platform, you can distribute it among users of all OSes - and it will just work.
With a
wide variety of languages that are currently supported in the JVM, the choice of language should not be a problem either: there is definitely one you like (
including JavaScript , if you are not able to refuse it), and you can use JavaFX with any JVM language without any problems. In this article, besides Java, I will show some code on
Kotlin .
The UI itself is created simply by code (if you have great IDE support from
IntelliJ ,
Eclipse or
NetBeans : these are all great free IDEs that probably outperform any competitors and, by the way, are the best examples of desktop Java applications) or in visual designer UI:
SceneBuilder (which can integrate into IntelliJ) or NetBeans
Visual Debugger .
Javafx history
JavaFX is not a new technology. She appeared in December 2008 and was very different from what we see today. The idea was to create a modern UI framework to replace the outdated Swing Framework, which has been the official JVM framework since the late 90s.
Oracle almost spoiled everything from the very beginning, starting to create a special, declarative language that was supposed to be used to create UI applications. This was not well received by Java developers, and that initiative almost ruined JavaFX.
Noticing the problem, Oracle decided to release JavaFX 2 in 2011 without its own special language, and instead using FXML as an option for pure Java code (as we will see later).
Around 2012, JavaFX gained some popularity, and Oracle made considerable efforts to improve and popularize this platform. Since version 2.2, the JavaFX framework has become a fairly solid framework, but it is still not included in the standard Java runtime (although it was always shipped with the JDK).
Only from JavaFX 8 version (version change made to match Java 8) has it become part of the standard Java runtime.
Today, the JavaFX framework may not be a major player in the UI world, but many real applications have been made on it, it has quite a few related libraries and it has been ported to a mobile platform .
Creating a JavaFX Application
In my application for viewing
LogFX logs, I decided to just use Java (because there is basically quite low-level code, and I wanted to concentrate on speed and small package size) and IntelliJ as an IDE. I almost decided to write on
Kotlin , but Java support in IntelliJ was so good, so writing in Java (more precisely, allowing IntelliJ to do it for me is closer to the truth) was not such a big problem to justify the extra 0.9 MB in distribution kit.
I decided not to use FXML (a GUI description language for JavaFX based on XML) or a visual UI designer, because the program interface is very simple.
So, look at some code!
Java Hello World
JavaFX — ,
javafx.application.Application
JavaFX
Stage
.
Hello World JavaFX:
public class JavaFxExample extends Application {
@Override
public void start(Stage primaryStage) throws Exception {
Text helloWorld = new Text("Hello world");
StackPane root = new StackPane(helloWorld);
primaryStage.setScene(new Scene(root, 300, 120));
primaryStage.centerOnScreen();
primaryStage.show();
}
public static void main(String[] args) {
launch(JavaFxExample.class, args);
}
}
src/main/java/main/JavaFxExample.java«» :

FXML+Java Hello World
UI , FXML:
<?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.layout.StackPane?>
<?import javafx.scene.Scene?>
<?import javafx.scene.text.Text?>
<Scene xmlns="http://javafx.com/javafx"
width="300.0" height="120.0">
<StackPane>
<Text>Hello world</Text>
</StackPane>
</Scene>
src/main/resources/main/Example.fxml public class JavaFxExample extends Application {
@Override
public void start(Stage primaryStage) throws Exception {
Scene scene = FXMLLoader.load(getClass().getResource("Example.fxml"));
primaryStage.setScene(scene);
primaryStage.centerOnScreen();
primaryStage.show();
}
public static void main(String[] args) {
launch(JavaFxExample.class, args);
}
}
src/main/java/main/JavaFxExample.java, IntelliJ FXML Java , , , , , … , FXML, UI … FXML. ,
FXML.
Hello World Kotlin+TornadoFX
, , Kotlin JavaFX,
TornadoFX:
class Main : App() {
override val primaryView = HelloWorld::class
}
class HelloWorld : View() {
override val root = stackpane {
prefWidth = 300.0
prefHeight = 120.0
text("Hello world")
}
}
src/main/kotlin/main/app.ktKotlin JavaFX, ( TornadoFX «
») 5 .
( ), Kotlin JavaFX.
JavaFX
, JavaFX, , JavaFX.
, JavaFX.
, , :

(, ) — :
root.setBackground(new Background(new BackgroundFill(
Color.DARKSLATEGRAY, CornerRadii.EMPTY, Insets.EMPTY)));
helloWorld.setStroke(Color.WHITE);
— CSS:
root.setStyle("-fx-background-color: darkslategray");
helloWorld.setStyle("-fx-stroke: white");
, IntelliJ .
FXML:
<StackPane style="-fx-background-color: darkslategray">
<Text style="-fx-stroke: white">Hello world</Text>
</StackPane>
…
, JavaFX ! , .
:
.root {
-fx-base: darkslategray;
}
Text {
-fx-stroke: white;
}
src/main/resources/css/hello.cssScene
:
primaryStage.getScene().getStylesheets().add("css/hello.css");
.
,
StackPane
darkslategray
, .
, «» , . , . , , .
, , «» , :
-fx-stroke: ladder(-fx-base, white 49%, black 50%);
JavaFX , .
CSS Reference Guide.
, . , , :
: JavaFX. : ,, , , .
LogFX
:

,
FontAwesome.
CSS. , :
Font.loadFont( LogFX.class.getResource( "/fonts/fontawesome-webfont.ttf" ).toExternalForm(), 12 );
. , Linux Mint:

, JavaFX. , .
, JavaFX… , .
JavaFX . (
GroovyFX):

:
Text {
-fx-fill: white;
}
#logfx-text-log {
-fx-font-family: sans-serif;
-fx-font-weight: 700;
-fx-font-size: 70;
-fx-fill: linear-gradient(to top, cyan, dodgerblue);
}
#logfx-text-fx {
-fx-font-family: sans-serif;
-fx-font-weight: 700;
-fx-font-size: 86;
-fx-fill: linear-gradient(to top, cyan, dodgerblue);
-fx-effect: dropshadow(gaussian, dodgerblue, 15, 0.25, 5, 5);
}
. .
.
, (), (hot reload) .
,
. UI «» UI.
JavaFX ( JVM) .
SceneBuilder
—
SceneBuilder, UI, FXML, UI.

Java IDE, ().
SceneBuilder , - -, .
, SceneBuilder, - , SceneBuilder — .
ScenicView
, ScenicView .
.

ScenicView jar
-javaagent:/path-to/scenicView.jar
JVM.
ScenicView , Javadocs .
JVM
, UI, Java . Oracle JVM HotSpot. , OpenJDK JVM.
: .
HotSpot VM
DCEVM (Dynamic Code Evolution VM) : / , / , .
JVM.
LogFX — . , , , - Stage… , UI, ScenicView ScenicBuilder .
DCEVM
JVM. — IDE .
IntelliJ (Cmd+F9 «»):

JavaFX . LogFX , — .
LogFX — ,
FileChangeWatcher
, .
, ( jar).
, .
, . , ( , ).
( jar), , Unix/Mac Windows. , :
private static String toAbsoluteFileUri( File file ) {
String absolutePath = file.getAbsolutePath();
if ( File.separatorChar == '\\' ) {
// windows stuff
return "file:///" + absolutePath.replace( "\\", "/" );
} else {
return "file:" + absolutePath;
}
}
Mac, Windows Linux Mint. , ( — , Mac,
). JavaFX .
, , , :
Runnable resetStylesheet = () -> Platform.runLater( () -> {
scene.getStylesheets().clear();
scene.getStylesheets().add( stylesheet );
} );
. , ScenicView
( jar),
TornadoFX , .
JavaFX . JavaFX- ( JavaFX , ), … - , - - JVM.
LogFX, , , , . , :
curl -sSfL https://jcenter.bintray.com/com/athaydes/logfx/logfx/0.7.0/logfx-0.7.0-all.jar -o logfx.jar
, jar 303 . 0,3 , TTF, HTML CSS, Java!
, JVM, JVM ! Java 9 , JVM, jar, ,
( JVM 35 21 ).
LogFX 50 RAM ( , JavaFX). , :
java -Xmx50m -jar logfx.jar
Electron, 200 .
JavaFX , . — . ,
JNLP Java WebStart,
, ,
Getdown FxLauncher, ,
Install4J (, Install4J
open source).
JavaFX, , , , , :