Skip to content

Commit

Permalink
Merge pull request #472 from dlsc-software-consulting-gmbh/enhance-la…
Browse files Browse the repository at this point in the history
…zy-load-flippane-back

FlipPane should create back of pane lazily
  • Loading branch information
dlemmermann authored Sep 14, 2023
2 parents 225a497 + f7d3ac7 commit 4e4b87f
Show file tree
Hide file tree
Showing 4 changed files with 114 additions and 62 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,12 @@
import javafx.scene.Node;
import javafx.scene.control.Control;
import javafx.scene.control.Skin;
import javafx.scene.layout.StackPane;
import javafx.util.Duration;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.function.Supplier;

/**
* @author ggrec
Expand Down Expand Up @@ -58,32 +58,32 @@ protected Skin<?> createDefaultSkin() {
return flipViewSkin;
}

private final ObjectProperty<Node> frontNode = new SimpleObjectProperty<>(this, "frontNode", new StackPane());
private final ObjectProperty<Supplier<Node>> frontNodeSupplier = new SimpleObjectProperty<>(this, "frontNode");

public Node getFrontNode() {
return frontNode.get();
public Supplier<Node> getFrontNodeSupplier() {
return frontNodeSupplier.get();
}

public ObjectProperty<Node> frontNodeProperty() {
return frontNode;
public ObjectProperty<Supplier<Node>> frontNodeSupplierProperty() {
return frontNodeSupplier;
}

public void setFrontNode(Node frontNode) {
this.frontNode.set(frontNode);
public void setFrontNodeSupplier(Supplier<Node> frontNodeSupplier) {
this.frontNodeSupplier.set(frontNodeSupplier);
}

private final ObjectProperty<Node> backNode = new SimpleObjectProperty<>(this, "backNode", new StackPane());
private final ObjectProperty<Supplier<Node>> backNodeSupplier = new SimpleObjectProperty<>(this, "backNode");

public Node getBackNode() {
return backNode.get();
public Supplier<Node> getBackNodeSupplier() {
return backNodeSupplier.get();
}

public ObjectProperty<Node> backNodeProperty() {
return backNode;
public ObjectProperty<Supplier<Node>> backNodeSupplierProperty() {
return backNodeSupplier;
}

public void setBackNode(Node backNode) {
this.backNode.set(backNode);
public void setBackNodeSupplier(Supplier<Node> backNodeSupplier) {
this.backNodeSupplier.set(backNodeSupplier);
}

private final StyleableObjectProperty<Duration> flipTime = new SimpleStyleableObjectProperty<>(StyleableProperties.FLIP_TIME, this,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@
public class FlipViewSkin extends SkinBase<FlipView> {

private static final Double PIE = Math.PI;

private static final Double HALF_PIE = Math.PI / 2;
private final SimpleDoubleProperty angle = new SimpleDoubleProperty(HALF_PIE);

Expand All @@ -35,6 +34,10 @@ public class FlipViewSkin extends SkinBase<FlipView> {
private final StackPane flipPane = new StackPane();
private final FlipView control;
private Timeline flipAnimation;
private Node frontNode;
private Node backNode;
private boolean isFrontNodeSupplierChanged;
private boolean isBackNodeSupplierChanged;

public FlipViewSkin(FlipView control) {
super(control);
Expand All @@ -46,28 +49,32 @@ public FlipViewSkin(FlipView control) {
flipPane.heightProperty().addListener((ob, ov, nv) -> recalculateTransformation(angle.doubleValue()));
getChildren().add(flipPane);

control.frontNodeProperty().addListener((ob, ov, frontNode) -> {
flipPane.getChildren().clear();
frontNode.getStyleClass().add("front-node");
frontNode.visibleProperty().bind(flippedProperty);
frontNode.setEffect(control.getAnimateOnFlip() ? transform : null);
flipPane.getChildren().setAll(control.getBackNode(), frontNode);
control.frontNodeSupplierProperty().addListener((ob, ov, nv) -> {
isFrontNodeSupplierChanged = true;
if (flippedProperty.get()) {
initFrontNode();
if (frontNode != null) {
flipPane.getChildren().setAll(frontNode);
isFrontNodeSupplierChanged = false;
}
}
});

control.backNodeProperty().addListener((ob, ov, backNode) -> {
flipPane.getChildren().clear();
backNode.getStyleClass().add("back-node");
backNode.visibleProperty().bind(flippedProperty.not());
backNode.setEffect(control.getAnimateOnFlip() ? transform : null);
flipPane.getChildren().setAll(backNode, control.getFrontNode());
control.backNodeSupplierProperty().addListener((ob, ov, nv) -> {
isBackNodeSupplierChanged = true;
if (!flippedProperty.get()) {
initBackNode();
if (backNode != null) {
flipPane.getChildren().setAll(backNode);
isBackNodeSupplierChanged = false;
}
}
});

control.animateOnFlipProperty().addListener((ob, ov, nv) -> {
Node frontNode = control.getFrontNode();
if (frontNode != null) {
frontNode.setEffect(nv ? transform : null);
}
Node backNode = control.getBackNode();
if (backNode != null) {
backNode.setEffect(nv ? transform : null);
}
Expand All @@ -76,7 +83,6 @@ public FlipViewSkin(FlipView control) {
flipAnimation.stop();
flipAnimation = null;
}

});

control.flipTimeProperty().addListener((ob, ov, nv) -> {
Expand Down Expand Up @@ -122,19 +128,52 @@ private Timeline createAnimation() {
);
}

public void flipToFront() {
if (control.getFrontNode() != null && control.getBackNode() != null && control.getBackNode().isVisible()) {
flip(false);
private void initBackNode() {
if (control.getBackNodeSupplier() == null ) {
return;
}
if (backNode == null || isBackNodeSupplierChanged) {
backNode = control.getBackNodeSupplier().get();
backNode.getStyleClass().add("back-node");
backNode.visibleProperty().bind(flippedProperty.not());
backNode.setEffect(control.getAnimateOnFlip() ? transform : null);
isBackNodeSupplierChanged = false;
}
}

private void initFrontNode() {
if (control.getFrontNodeSupplier() == null) {
return;
}
if (frontNode == null || isFrontNodeSupplierChanged) {
frontNode = control.getFrontNodeSupplier().get();
frontNode.getStyleClass().add("front-node");
frontNode.visibleProperty().bind(flippedProperty);
frontNode.setEffect(control.getAnimateOnFlip() ? transform : null);
isFrontNodeSupplierChanged = false;
}
}

public void flipToBack() {
if (control.getFrontNode() != null && control.getBackNode() != null && control.getFrontNode().isVisible()) {
initFrontNode();
initBackNode();

if (frontNode != null && backNode != null && frontNode.isVisible()) {
flip(true);
}
}

public void flipToFront() {
initFrontNode();
initBackNode();

if (frontNode != null && backNode != null && backNode.isVisible()) {
flip(false);
}
}

private void flip(boolean isToBack) {
flipPane.getChildren().setAll(backNode, frontNode);
if (control.getAnimateOnFlip()) {
if (flipAnimation == null) {
flipAnimation = createAnimation();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -76,8 +76,9 @@ public TileView(T item) {
contentBox.setClip(clip);

// [Top] FlipView
flipView.frontNodeProperty().bind(Bindings.createObjectBinding(this::createFront, sizeProperty()));
flipView.setBackNode(createBack());
flipView.frontNodeSupplierProperty().bind(Bindings.createObjectBinding(()->this::createFront, sizeProperty()));
flipView.backNodeSupplierProperty().bind(Bindings.createObjectBinding(()->this::createBack, sizeProperty()));
flipView.setFocusTraversable(false);
VBox.setVgrow(flipView, Priority.ALWAYS);

// [Bottom] nodes,save button,like button
Expand Down Expand Up @@ -268,11 +269,13 @@ private Node createBack() {
closeButton.setContentDisplay(ContentDisplay.RIGHT);
closeButton.setOnMousePressed(event -> {
event.consume();
flipView.requestFocus();
flipView.flipToFront();
});
closeButton.setFocusTraversable(false);

TextArea descriptionArea = new TextArea();
descriptionArea.setFocusTraversable(false);
descriptionArea.setContextMenu(new ContextMenu());
descriptionArea.setEditable(false);
descriptionArea.setWrapText(true);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,31 +26,41 @@ public class HelloFlipView extends JFXCentralSampleBase {
protected Region createControl() {
flipView = new FlipView();
flipView.getStyleClass().add("hello-flip-view");
// create front node
ImageView frontImage = new ImageView(new Image(getClass().getResource("/com/dlsc/jfxcentral2/demo/components/images/quick-link-lg1.png").toExternalForm()));
frontImage.setPreserveRatio(true);
frontImage.setFitWidth(420);

Button flipToBackBtn = new Button("Click Flip to Back");
flipToBackBtn.setOnAction(evt -> flipView.flipToBack());
StackPane frontPane = new StackPane(frontImage, flipToBackBtn);
StackPane.setAlignment(flipToBackBtn, Pos.TOP_LEFT);
StackPane.setMargin(flipToBackBtn, new Insets(10));

flipView.setFrontNode(frontPane);

// create back node
ImageView backImage = new ImageView(new Image(getClass().getResource("/com/dlsc/jfxcentral2/demo/components/images/quick-link-lg2.png").toExternalForm()));
backImage.setPreserveRatio(true);
backImage.setFitWidth(420);

Button flipToFrontBtn = new Button("Click Flip to Front");
flipToFrontBtn.setOnAction(evt -> flipView.flipToFront());
StackPane backPane = new StackPane(backImage, flipToFrontBtn);
StackPane.setAlignment(flipToFrontBtn, Pos.TOP_LEFT);
StackPane.setMargin(flipToFrontBtn, new Insets(10));

flipView.setBackNode(backPane);

flipView.setFrontNodeSupplier(()-> {
// create front node
ImageView frontImage = new ImageView(new Image(getClass().getResource("/com/dlsc/jfxcentral2/demo/components/images/quick-link-lg1.png").toExternalForm()));
frontImage.setPreserveRatio(true);
frontImage.setFitWidth(420);

Button flipToBackBtn = new Button("Click Flip to Back");
flipToBackBtn.setOnAction(evt -> flipView.flipToBack());

StackPane frontPane = new StackPane(frontImage, flipToBackBtn);
StackPane.setAlignment(flipToBackBtn, Pos.TOP_LEFT);
StackPane.setMargin(flipToBackBtn, new Insets(10));
System.out.println("create front node");
return frontPane;
});



flipView.setBackNodeSupplier(()-> {
// create back node
ImageView backImage = new ImageView(new Image(getClass().getResource("/com/dlsc/jfxcentral2/demo/components/images/quick-link-lg2.png").toExternalForm()));
backImage.setPreserveRatio(true);
backImage.setFitWidth(420);

Button flipToFrontBtn = new Button("Click Flip to Front");
flipToFrontBtn.setOnAction(evt -> flipView.flipToFront());

StackPane backPane = new StackPane(backImage, flipToFrontBtn);
StackPane.setAlignment(flipToFrontBtn, Pos.TOP_LEFT);
StackPane.setMargin(flipToFrontBtn, new Insets(10));
System.out.println("create back node");
return backPane;
});

flipView.setMaxSize(Region.USE_PREF_SIZE, Region.USE_PREF_SIZE);
return new StackPane(flipView);
}
Expand Down

0 comments on commit 4e4b87f

Please sign in to comment.