JavaFX中FadeTransition仅渐变背景不影响子节点的实现方法
问题根因
FadeTransition的核心逻辑是动态修改目标节点的opacity属性,按照JavaFX的渲染规则,父节点的透明度会被所有子节点递归继承,因此直接将动画绑定在包含按钮的Pane上时,内部按钮必然会跟随父容器同步改变透明度,不存在可直接配置的参数能隔离父容器透明度对子节点的影响。
实现方法
不要把背景样式设置在承载按钮的父Pane上,将背景抽离为独立的、和内容层平级的节点,仅对这个独立背景节点应用淡入淡出动画即可。
修改后的完整代码:
import javafx.animation.FadeTransition; import javafx.animation.Timeline; import javafx.application.Application; import javafx.scene.Scene; import javafx.scene.control.Button; import javafx.scene.layout.Pane; import javafx.scene.layout.StackPane; import javafx.scene.paint.Color; import javafx.scene.shape.Rectangle; import javafx.stage.Stage; import javafx.util.Duration; public class Test extends Application { @Override public void start(Stage stage) throws Exception { StackPane root = new StackPane(); // 独立背景节点,和内容层平级 Rectangle bg = new Rectangle(500, 500, Color.RED); // 内容容器,存放不需要透明变化的控件 Pane contentPane = new Pane(); Button testButton = new Button("Test"); testButton.setStyle("-fx-background-color: green;"); contentPane.getChildren().add(testButton); // 动画仅作用于独立背景节点 FadeTransition transition = new FadeTransition(Duration.millis(5000), bg); transition.setFromValue(1.0); transition.setToValue(0.0); transition.setCycleCount(Timeline.INDEFINITE); transition.setAutoReverse(true); transition.play(); // 按层级添加:背景在最下,内容在最上 root.getChildren().addAll(bg, contentPane); Scene scene = new Scene(root, 500, 500); stage.setMinWidth(500); stage.setMinHeight(500); stage.setTitle("Test"); stage.setResizable(false); stage.setScene(scene); stage.show(); } }
如果不想用Rectangle做背景,也可以单独创建一个Pane设置红色背景作为独立背景层,核心逻辑始终是将需要做透明变化的背景和不需要变化的内容拆分为兄弟节点,避免父子嵌套带来的透明度继承。
运行后动画执行时仅红色背景会做淡入淡出,绿色按钮始终保持完全不透明,和预期效果一致。
内容的提问来源于stack exchange,提问作者parsecer
相关产品推荐
相关产品推荐

