Browser like BoxShadow for JavaFX coming with e(fx)clipse 3.7.0


Using BoxShadow is a very common thing in modern UIs, so it might not be suprising that designers defining UIs often also use them heavily.

Unfortunately JavaFX has NO 100% compatible effect and even worse one who is closest (DropShadow) leads to a massive performance hit as shown in this video

On the left hand side is a Node who has a DropShadow-Effect applied to it and you notice that once the effect is applied that the animation isn’t smooth any more. On the right hand side you see a new Node we’ll release with e(fx)clipse 3.7.0 who provides a new BoxShadow-Node (named BoxShadow2).

Beside getting a huge performance win, the BoxShadow-Node uses the same semantics the browser counterpart does so you can port CSS definition to your JavaFX-Application.

For completness here’s the code for this demo video.

package org.eclipse.fx.ui.controls.demo;

import org.eclipse.fx.ui.controls.effects.BoxShadow2;

import javafx.animation.Animation;
import javafx.animation.Animation.Status;
import javafx.animation.TranslateTransition;
import javafx.application.Application;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Node;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.effect.DropShadow;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.Region;
import javafx.scene.layout.StackPane;
import javafx.scene.paint.Color;
import javafx.stage.Stage;
import javafx.util.Duration;

public class InTheShadow extends Application {

	public static void main(String[] args) {
		launch(args);
	}

	@Override
	public void start(Stage primaryStage) throws Exception {
		BorderPane p = new BorderPane();
		p.setPadding(new Insets(20));

		Button shadowMe = new Button("Toggle Shadow");
		p.setTop(shadowMe);

		Region pane;

		if (Boolean.getBoolean("efxclipse-shadow")) {
			BoxShadow2 shadow = new BoxShadow2(createComplexUI());
			shadow.setShadowVisible(false);
			pane = shadow;
		} else {
			pane = new StackPane(createComplexUI());
		}

		p.setCenter(pane);

		shadowMe.setOnAction(evt -> toggleShadow(pane));

		Scene s = new Scene(p, 1200, 800);
		primaryStage.setTitle("efxclipse-shadow: " + Boolean.getBoolean("efxclipse-shadow"));
		primaryStage.setScene(s);
		primaryStage.show();
	}

	private void toggleShadow(Region pane) {
		if (pane instanceof BoxShadow2) {
			BoxShadow2 s = (BoxShadow2) pane;
			s.setShadowVisible(!s.isShadowVisible());
		} else {
			if (pane.getEffect() != null) {
				pane.setEffect(null);
			} else {
				DropShadow dropShadow = new DropShadow();
				dropShadow.setRadius(5.0);
				dropShadow.setOffsetX(3.0);
				dropShadow.setOffsetY(3.0);
				dropShadow.setColor(Color.color(0.4, 0.5, 0.5));
				pane.setEffect(dropShadow);
			}
		}
	}

	private Node createComplexUI() {
		StackPane pane = new StackPane();
		pane.setStyle("-fx-background-color: white");

		for (int i = 0; i < 100; i++) {
			Button b = new Button("Button " + i);
			b.setTranslateX(i % 100);
			pane.getChildren().add(b);
		}

		Button animated = new Button("Animated");
		StackPane.setAlignment(animated, Pos.BOTTOM_CENTER);

		TranslateTransition t = new TranslateTransition(Duration.millis(1000), animated);
		t.setAutoReverse(true);
		t.setFromX(-300);
		t.setToX(300);
		t.setCycleCount(Animation.INDEFINITE);
		animated.setOnAction(evt -> {
			if (t.getStatus() == Status.RUNNING) {
				t.pause();
			} else {
				t.play();
			}
		});

		pane.getChildren().add(animated);

		return pane;
	}

}
This entry was posted in e(fx)clipse, Uncategorized. Bookmark the permalink.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

This site uses Akismet to reduce spam. Learn how your comment data is processed.