首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 相關知識

SwingX + TimingFramework 實現優雅淡入淡出動畫效果

     編輯:Java 相關知識

傳統 Swing 實現淡入淡出需繼承元件、重寫 paintComponent、配合 javax.swing.Timer 手動插值,代碼冗長且難維護。本文展示如何結合 SwingX (提供 JXPanel.setAlpha() 一鍵透明度) 與 TimingFramework (提供非線性插值動畫引擎),以極簡代碼實現專業級卡片切換淡入淡出效果。

核心優勢

  • JXPanel:繼承 JPanel,setAlpha(float) 即時影響自身及所有子元件透明度,無需自訂繪製
  • Animator:替代 Timer,支援加速/減速曲線、暫停/繼續/反向、多目標屬性同步動畫
  • PropertySetter:聲明式指定目標物件、屬性名、目標值,自動反射設值

完整範例:卡片切換淡入淡出

效果圖1

效果圖2

效果圖3


import org.jdesktop.animation.timing.Animator;
import org.jdesktop.animation.timing.interpolation.PropertySetter;
import org.jdesktop.swingx.JXPanel;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

public class FadingCardDemo extends JFrame {

    private static final long serialVersionUID = 8005909309849021746L;
    private final String CARD_A = "CARD_A";
    private final String CARD_B = "CARD_B";

    private JPanel cardPanel;
    private JXPanel panelA, panelB;
    private JButton buttonA, buttonB;

    public FadingCardDemo() {
        super("Fading Card Demo");
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        initUI();
    }

    private void initUI() {
        cardPanel = new JPanel(new CardLayout());

        // Panel A
        buttonA = new JButton("Button A");
        buttonA.addActionListener(actionHandler);
        panelA = new JXPanel(new BorderLayout());
        panelA.add(buttonA, BorderLayout.CENTER);
        cardPanel.add(panelA, CARD_A);

        // Panel B
        buttonB = new JButton("Button B");
        buttonB.addActionListener(actionHandler);
        panelB = new JXPanel(new BorderLayout());
        panelB.add(buttonB, BorderLayout.CENTER);
        cardPanel.add(panelB, CARD_B);

        Container container = getContentPane();
        container.setLayout(new BorderLayout());
        container.add(cardPanel, BorderLayout.CENTER);
    }

    private final ActionListener actionHandler = new ActionListener() {
        private Animator animator = null;

        @Override
        public void actionPerformed(ActionEvent e) {
            // 惰性初始化 Animator
            if (animator == null) {
                animator = new Animator(2000); // 2秒動畫時長
                animator.setDeceleration(0.2f); // 減速曲線
                animator.setAcceleration(0.4f); // 加速曲線
            } else if (animator.isRunning()) {
                animator.stop(); // 打斷正在進行的動畫
            }

            JButton source = (JButton) e.getSource();
            if (source == buttonA) {
                // 切換到 Panel B 並淡入
                animator.addTarget(new PropertySetter(panelB, "alpha", 1.0f));
                panelB.setAlpha(0.1f); // 起始透明度
                ((CardLayout) cardPanel.getLayout()).show(cardPanel, CARD_B);
            } else if (source == buttonB) {
                // 切換到 Panel A 並淡入
                animator.addTarget(new PropertySetter(panelA, "alpha", 1.0f));
                panelA.setAlpha(0.1f);
                ((CardLayout) cardPanel.getLayout()).show(cardPanel, CARD_A);
            }
            animator.start();
        }
    };

    public static void main(String[] args) {
        SwingUtilities.invokeLater(() -> {
            FadingCardDemo demo = new FadingCardDemo();
            demo.setSize(new Dimension(400, 300));
            demo.setVisible(true);
        });
    }
}

關鍵技術點解析

  1. 動畫生命週期管理:Animator 可重用,stop() 打斷當前動畫避免疊加
  2. 非線性插值:setAcceleration/Deceleration 模擬真實物理慣性,體驗更自然
  3. 屬性綁定:PropertySetter(target, "propertyName", endValue) 自動計算插值並反射調用 setter
  4. CardLayout 配合:先 show() 切換可見卡片,再啟動淡入動畫 (因 CardLayout 只顯示一張卡)

依賴庫獲取

將 JAR 加入類別路徑即可編譯執行。此模式易擴展至工具提示淡現、對話框彈出、狀態欄滑入等多種 UI 動畫場景。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved