最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Java?Swing自定義復(fù)選框CusCheckBox組件(附源碼)

 更新時(shí)間:2026年05月27日 08:41:03   作者:RainCity  
Swing 原生 JCheckBox 的復(fù)選框圖標(biāo)是系統(tǒng)默認(rèn)樣式,不同操作系統(tǒng)下風(fēng)格不一致,且無(wú)法自定義圓角、顏色、懸停效果等, 下面我們就用Java Swing實(shí)現(xiàn)自定義的復(fù)選框組件吧

一、背景

Swing 原生 JCheckBox 的復(fù)選框圖標(biāo)是系統(tǒng)默認(rèn)樣式,不同操作系統(tǒng)下風(fēng)格不一致,且無(wú)法自定義圓角、顏色、懸停效果等。 要實(shí)現(xiàn)統(tǒng)一的復(fù)選框樣式,需要自己繪制圖標(biāo)。CusCheckBox 通過(guò)實(shí)現(xiàn) Icon 接口自定義復(fù)選框的繪制邏輯,支持圓角、自定義顏色、懸停效果、禁用狀態(tài)等。

二、核心設(shè)計(jì)

CusCheckBox 由兩個(gè)類組成:

  • CheckBoxIcon:實(shí)現(xiàn) Icon 接口,負(fù)責(zé)繪制復(fù)選框圖標(biāo)(背景、邊框、對(duì)勾/叉號(hào))
  • CusCheckBox:繼承 JCheckBox,使用 CheckBoxIcon 作為圖標(biāo),提供豐富的樣式設(shè)置方法

三、CheckBoxIcon 源碼

import lombok.Setter;

import javax.swing.*;
import java.awt.*;

/**
 * 自定義 JCheckBox 圖標(biāo)類
 * 實(shí)現(xiàn) Icon 接口,負(fù)責(zé)繪制復(fù)選框的圖標(biāo)部分
 *
 * 使用示例:
 * CheckBoxIcon icon = new CheckBoxIcon(20, Color.decode("#409EFF"), Color.WHITE);
 */
@Setter
public class CheckBoxIcon implements Icon {
    /** 復(fù)選框大小 */
    private int size;
    /** 圓角 */
    private boolean rounded = true;
    /** 圓角半徑 */
    private int borderRadius = 8;
    /** 邊框?qū)挾?*/
    private int borderThickness = 1;
    /** 邊框顏色 */
    private Color borderColor = Color.GRAY;
    /** 選中背景顏色 */
    private Color selectedBg;
    /** 對(duì)勾顏色 */
    private Color checkColor;
    /** 懸停顏色 */
    private Color hoverColor;
    /** 禁用顏色 */
    private Color disabledColor = Color.decode("#E4E7ED");
    /** 對(duì)勾寬度 */
    private float checkThickness = 2.0f;
    /** 是否使用對(duì)勾(true=對(duì)勾,false=叉號(hào)) */
    private boolean useCheckMark = true;
    /** 是否啟用 */
    private boolean enabled = true;

    /**
     * 構(gòu)造函數(shù)
     * @param size 圖標(biāo)尺寸
     * @param selectedBg 選中時(shí)的背景色
     * @param checkColor 對(duì)勾顏色
     */
    public CheckBoxIcon(int size, Color selectedBg, Color checkColor) {
        this.size = Math.max(16, size);
        this.selectedBg = selectedBg;
        this.checkColor = checkColor;
    }

    @Override
    public void paintIcon(Component c, Graphics g, int x, int y) {
        AbstractButton button = (AbstractButton) c;
        ButtonModel model = button.getModel();
        Graphics2D g2 = (Graphics2D) g;
        // 啟用抗鋸齒
        g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
        // 獲取狀態(tài)
        boolean isSelected = model.isSelected();
        boolean isPressed = model.isPressed();
        boolean isRollover = model.isRollover();
        // 計(jì)算實(shí)際繪制區(qū)域
        int drawWidth = size - 1;
        int drawHeight = size - 1;
        // 根據(jù)狀態(tài)選擇顏色
        Color currentBorder = enabled ? borderColor : disabledColor;
        Color currentBg = Color.WHITE;
        if (isSelected) {
            currentBg = enabled ? selectedBg : disabledColor.brighter();
        }
        if (isRollover && !isPressed && enabled && null != hoverColor) {
            currentBg = hoverColor;
        }
        if (isPressed && enabled) {
            currentBg = selectedBg.darker();
        }
        if (!enabled) {
            currentBg = disabledColor;
        }
        // 繪制背景
        g2.setColor(currentBg);
        if (rounded) {
            g2.fillRoundRect(x, y, drawWidth, drawHeight, borderRadius, borderRadius);
        } else {
            g2.fillRect(x, y, drawWidth, drawHeight);
        }
        // 繪制邊框
        g2.setColor(currentBorder);
        g2.setStroke(new BasicStroke(borderThickness));
        if (rounded) {
            g2.drawRoundRect(x, y, drawWidth, drawHeight, borderRadius, borderRadius);
        } else {
            g2.drawRect(x, y, drawWidth, drawHeight);
        }
        // 繪制選中標(biāo)記
        if (isSelected) {
            drawCheckMark(g2, x, y, drawWidth, drawHeight);
        }
    }

    /**
     * 繪制選中標(biāo)記(對(duì)勾或叉號(hào))
     * @param g2 Graphics2D 對(duì)象
     * @param x 起始 X 坐標(biāo)
     * @param y 起始 Y 坐標(biāo)
     * @param width 繪制寬度
     * @param height 繪制高度
     */
    private void drawCheckMark(Graphics2D g2, int x, int y, int width, int height) {
        Color currentCheckColor = enabled ? checkColor : Color.DARK_GRAY;
        g2.setColor(currentCheckColor);
        g2.setStroke(new BasicStroke(checkThickness, BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND));
        // 20% 內(nèi)邊距
        float padding = width * 0.2f;
        int startX = (int) (x + padding);
        int startY = y + height / 2;
        int midX = x + width / 2;
        int midY = (int) (y + height - padding);
        int endX = (int) (x + width - padding);
        int endY = (int) (y + padding);
        if (useCheckMark) {
            // 對(duì)勾
            g2.drawLine(startX, startY, midX, midY);
            g2.drawLine(midX, midY, endX, endY);
        } else {
            // 叉號(hào)
            g2.drawLine(startX, startY, endX, endY);
            g2.drawLine(startX, endY, endX, startY);
        }
    }

    @Override
    public int getIconWidth() {
        return size;
    }

    @Override
    public int getIconHeight() {
        return size;
    }

    /**
     * 設(shè)置圖標(biāo)尺寸
     * @param size 尺寸
     */
    public void setSize(int size) {
        this.size = Math.max(16, size);
    }
}

四、CusCheckBox 源碼

import javax.swing.*;
import java.awt.*;

/**
 * 自定義復(fù)選框
 * 通過(guò)自定義 Icon 實(shí)現(xiàn)統(tǒng)一的復(fù)選框樣式
 *
 * 使用示例:
 * CusCheckBox checkBox = new CusCheckBox("同意協(xié)議");
 * checkBox.setSelected(true);
 * checkBox.setHoverColor(Color.LIGHT_GRAY);
 */
public class CusCheckBox extends JCheckBox {
    /** 默認(rèn)尺寸 */
    private static final int DEFAULT_SIZE = 20;
    /** 默認(rèn)選中背景顏色 */
    private static final Color DEFAULT_BG = Color.decode("#409EFF");
    /** 默認(rèn)選中對(duì)勾顏色 */
    private static final Color DEFAULT_CHECK = Color.WHITE;
    /** 內(nèi)部圖標(biāo)實(shí)例 */
    private final CheckBoxIcon icon;

    /**
     * 默認(rèn)構(gòu)造函數(shù)
     * @param text 復(fù)選框文本
     */
    public CusCheckBox(String text) {
        this(text, DEFAULT_SIZE, DEFAULT_BG, DEFAULT_CHECK, false);
    }

    /**
     * 指定選中狀態(tài)
     * @param text 復(fù)選框文本
     * @param selected 是否選中
     */
    public CusCheckBox(String text, boolean selected) {
        this(text, DEFAULT_SIZE, DEFAULT_BG, DEFAULT_CHECK, selected);
    }

    /**
     * 指定尺寸
     * @param text 復(fù)選框文本
     * @param size 圖標(biāo)尺寸
     */
    public CusCheckBox(String text, int size) {
        this(text, size, DEFAULT_BG, DEFAULT_CHECK, false);
    }

    /**
     * 指定尺寸和選中狀態(tài)
     * @param text 復(fù)選框文本
     * @param size 圖標(biāo)尺寸
     * @param selected 是否選中
     */
    public CusCheckBox(String text, int size, boolean selected) {
        this(text, size, DEFAULT_BG, DEFAULT_CHECK, selected);
    }

    /**
     * 指定顏色
     * @param text 復(fù)選框文本
     * @param bg 選中時(shí)背景色
     * @param check 對(duì)勾顏色
     */
    public CusCheckBox(String text, Color bg, Color check) {
        this(text, DEFAULT_SIZE, bg, check, false);
    }

    /**
     * 指定顏色和選中狀態(tài)
     * @param text 復(fù)選框文本
     * @param bg 選中時(shí)背景色
     * @param check 對(duì)勾顏色
     * @param selected 是否選中
     */
    public CusCheckBox(String text, Color bg, Color check, boolean selected) {
        this(text, DEFAULT_SIZE, bg, check, selected);
    }

    /**
     * 指定尺寸和顏色
     * @param text 復(fù)選框文本
     * @param size 圖標(biāo)尺寸
     * @param bg 選中時(shí)背景色
     * @param check 對(duì)勾顏色
     */
    public CusCheckBox(String text, int size, Color bg, Color check) {
        this(text, size, bg, check, false);
    }

    /**
     * 完整構(gòu)造函數(shù)
     * @param text 復(fù)選框文本
     * @param size 圖標(biāo)尺寸
     * @param bg 選中時(shí)背景色
     * @param check 對(duì)勾顏色
     * @param selected 是否選中
     */
    public CusCheckBox(String text, int size, Color bg, Color check, boolean selected) {
        super(text);
        // 創(chuàng)建自定義圖標(biāo)
        this.icon = new CheckBoxIcon(size, bg, check);
        // 設(shè)置圖標(biāo)(選中和未選中共用同一個(gè)圖標(biāo)實(shí)例,通過(guò)狀態(tài)區(qū)分繪制)
        this.setIcon(icon);
        this.setSelectedIcon(icon);
        // 設(shè)置選中狀態(tài)
        this.setSelected(selected);
        // 設(shè)置文本顏色和字體
        this.setForeground(Color.BLACK);
        this.setFont(new Font("Microsoft YaHei", Font.PLAIN, 16));
        // 設(shè)置透明背景,讓父容器背景顯示
        this.setOpaque(false);
        // 禁用默認(rèn)內(nèi)容區(qū)域填充
        this.setContentAreaFilled(false);
        // 禁用邊框繪制
        this.setBorderPainted(false);
        // 圖標(biāo)與文字間距
        this.setIconTextGap(10);
    }

    /**
     * 獲取自定義圖標(biāo)
     * @return 圖標(biāo)對(duì)象
     */
    @Override
    public CheckBoxIcon getIcon() {
        return icon;
    }

    /**
     * 設(shè)置圖標(biāo)尺寸
     * @param size 尺寸
     */
    public void setIconSize(int size) {
        icon.setSize(size);
        revalidate();
        repaint();
    }

    /**
     * 設(shè)置選中時(shí)的背景色
     * @param color 顏色
     */
    public void setSelectedBackground(Color color) {
        icon.setSelectedBg(color);
        repaint();
    }

    /**
     * 設(shè)置對(duì)勾顏色
     * @param color 顏色
     */
    public void setCheckColor(Color color) {
        icon.setCheckColor(color);
        repaint();
    }

    /**
     * 設(shè)置邊框顏色
     * @param color 顏色
     */
    public void setBorderColor(Color color) {
        icon.setBorderColor(color);
        repaint();
    }

    /**
     * 設(shè)置是否圓角
     * @param rounded 是否圓角
     */
    public void setRounded(boolean rounded) {
        icon.setRounded(rounded);
        repaint();
    }

    /**
     * 設(shè)置圓角半徑
     * @param radius 半徑
     */
    public void setBorderRadius(int radius) {
        icon.setRounded(true);
        icon.setBorderRadius(radius);
        repaint();
    }

    /**
     * 設(shè)置邊框粗細(xì)
     * @param thickness 粗細(xì)
     */
    public void setBorderThickness(int thickness) {
        icon.setBorderThickness(thickness);
        repaint();
    }

    /**
     * 設(shè)置對(duì)勾線條粗細(xì)
     * @param thickness 粗細(xì)
     */
    public void setCheckThickness(float thickness) {
        icon.setCheckThickness(thickness);
        repaint();
    }

    /**
     * 設(shè)置使用對(duì)勾還是叉號(hào)
     * @param useCheckMark true=對(duì)勾,false=叉號(hào)
     */
    public void setUseCheckMark(boolean useCheckMark) {
        icon.setUseCheckMark(useCheckMark);
        repaint();
    }

    /**
     * 設(shè)置懸停時(shí)的背景色
     * @param color 顏色
     */
    public void setHoverColor(Color color) {
        icon.setHoverColor(color);
        repaint();
    }

    /**
     * 重寫 setEnabled 以同步圖標(biāo)狀態(tài)
     * @param enabled 是否啟用
     */
    @Override
    public void setEnabled(boolean enabled) {
        super.setEnabled(enabled);
        if (icon != null) {
            icon.setEnabled(enabled);
            repaint();
        }
    }
}

五、核心功能說(shuō)明

圖標(biāo)繪制(CheckBoxIcon):

  • paintIcon:核心繪制方法,根據(jù)按鈕狀態(tài)(選中/懸停/按下/禁用)繪制不同樣式
  • drawCheckMark:繪制對(duì)勾或叉號(hào),支持線條粗細(xì)和顏色定制
  • 支持圓角/直角、邊框顏色/粗細(xì)、背景色、懸停色、禁用色等配置

復(fù)選框封裝(CusCheckBox):

  • 使用 CheckBoxIcon 替換原生圖標(biāo)
  • 提供多個(gè)構(gòu)造函數(shù)簡(jiǎn)化使用(尺寸/顏色/選中狀態(tài)組合)
  • 提供樣式設(shè)置方法(圓角、顏色、懸停、對(duì)勾樣式等)
  • 透明背景,便于融入父容器

六、使用示例

6.1 基本用法

CusCheckBox checkBox = new CusCheckBox("同意用戶協(xié)議");
panel.add(checkBox);

6.2 指定選中狀態(tài)

CusCheckBox checkBox = new CusCheckBox("記住密碼", true);
panel.add(checkBox);

6.3 自定義顏色和尺寸

CusCheckBox checkBox = new CusCheckBox("自定義樣式", 24, Color.decode("#67C23A"), Color.WHITE);
checkBox.setHoverColor(Color.decode("#E6F7E6"));
panel.add(checkBox);

6.4 圓角半徑調(diào)整

CusCheckBox checkBox = new CusCheckBox("圓角復(fù)選框");
checkBox.setBorderRadius(12);
panel.add(checkBox);

6.5 使用叉號(hào)代替對(duì)勾

CusCheckBox checkBox = new CusCheckBox("拒絕");
checkBox.setUseCheckMark(false);
checkBox.setSelectedBackground(Color.decode("#F56C6C"));
panel.add(checkBox);

6.6 禁用狀態(tài)

CusCheckBox checkBox = new CusCheckBox("不可選");
checkBox.setEnabled(false);
panel.add(checkBox);

6.7 監(jiān)聽(tīng)選中事件

CusCheckBox checkBox = new CusCheckBox("接收通知");
checkBox.addItemListener(e -> {
    boolean selected = e.getStateChange() == ItemEvent.SELECTED;
    System.out.println("選中狀態(tài):" + selected);
});

七、注意事項(xiàng)

  • con 共用:選中和未選中共用同一個(gè) CheckBoxIcon 實(shí)例,通過(guò) ButtonModel.isSelected() 區(qū)分繪制狀態(tài)
  • 透明背景:setOpaque(false) 和 setContentAreaFilled(false) 確保背景不覆蓋父容器
  • 字體設(shè)置:代碼中使用 Microsoft YaHei,非 Windows 系統(tǒng)需替換為 DejaVu Sans 或 Serif
  • 顏色默認(rèn)值:默認(rèn)主題色為 #409EFF(Element UI 風(fēng)格),可根據(jù)項(xiàng)目調(diào)整
  • 圖標(biāo)尺寸:最小值限制為 16px,避免過(guò)小無(wú)法交互

八、小結(jié)

CusCheckBox 通過(guò)自定義 Icon 實(shí)現(xiàn)了樣式統(tǒng)一的復(fù)選框組件。核心思路是:

  • 實(shí)現(xiàn) Icon 接口,重寫 paintIcon 方法自繪圖標(biāo)
  • 根據(jù)按鈕狀態(tài)(選中/懸停/禁用/按下)繪制不同樣式
  • 通過(guò)多個(gè)構(gòu)造函數(shù)和 setter 方法提供靈活配置

這種實(shí)現(xiàn)方式可以推廣到其他自定義組件(如單選框、開(kāi)關(guān)等)。

以上就是Java Swing自定義復(fù)選框CusCheckBox組件(附源碼)的詳細(xì)內(nèi)容,更多關(guān)于Java Swing自定義復(fù)選框的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

  • Java中HttpServletRequestWrapper的使用與原理詳解

    Java中HttpServletRequestWrapper的使用與原理詳解

    這篇文章主要介紹了Java中HttpServletRequestWrapper的使用與原理詳解,HttpServletRequestWrapper 實(shí)現(xiàn)了 HttpServletRequest 接口,可以讓開(kāi)發(fā)人員很方便的改造發(fā)送給 Servlet 的請(qǐng)求,需要的朋友可以參考下
    2024-01-01
  • Spring中@RequestMapping、@RestController和Postman

    Spring中@RequestMapping、@RestController和Postman

    本文介紹了Spring框架中常用的@RequestMapping和@RestController注解,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2024-10-10
  • Springboot的yml配置文件用法

    Springboot的yml配置文件用法

    這篇文章主要介紹了Springboot的yml配置文件用法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2023-03-03
  • Spring Boot中使用Actuator的/info端點(diǎn)輸出Git版本信息

    Spring Boot中使用Actuator的/info端點(diǎn)輸出Git版本信息

    這篇文章主要介紹了Spring Boot中使用Actuator的/info端點(diǎn)輸出Git版本信息,需要的朋友可以參考下
    2017-06-06
  • Java實(shí)現(xiàn)簡(jiǎn)單日歷小程序 Java圖形界面小日歷開(kāi)發(fā)

    Java實(shí)現(xiàn)簡(jiǎn)單日歷小程序 Java圖形界面小日歷開(kāi)發(fā)

    這篇文章主要介紹了Java實(shí)現(xiàn)簡(jiǎn)單日歷小程序,如何用Java swing開(kāi)發(fā)一款簡(jiǎn)單的小日歷,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2018-02-02
  • spring基礎(chǔ)概念A(yù)OP與動(dòng)態(tài)代理理解

    spring基礎(chǔ)概念A(yù)OP與動(dòng)態(tài)代理理解

    這篇文章主要為大家詳細(xì)介紹了spring基礎(chǔ)概念A(yù)OP與動(dòng)態(tài)代理,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2016-10-10
  • Maven Profile中的資源過(guò)濾與屬性管理詳解

    Maven Profile中的資源過(guò)濾與屬性管理詳解

    在持續(xù)交付體系下,軟件需要面向開(kāi)發(fā)、測(cè)試、預(yù)發(fā)布、生產(chǎn)等多個(gè)環(huán)境進(jìn)行差異化配置,Maven作為Java生態(tài)的核心構(gòu)建工具,其Profile機(jī)制配合資源過(guò)濾功能,為多環(huán)境構(gòu)建提供了優(yōu)雅的解決方案,本文深入解析如何通過(guò)<resources>與<filters>的聯(lián)動(dòng)實(shí)現(xiàn)環(huán)境隔離
    2025-05-05
  • idea項(xiàng)目實(shí)現(xiàn)移除和添加git

    idea項(xiàng)目實(shí)現(xiàn)移除和添加git

    本文指導(dǎo)讀者如何從官網(wǎng)下載并安裝Git,以及在IDEA中配置Git的詳細(xì)步驟,首先,用戶需訪問(wèn)Git官方網(wǎng)站下載適合自己操作系統(tǒng)的Git版本并完成安裝,接著,在IDEA中通過(guò)設(shè)置找到git.exe文件以配置Gi
    2024-10-10
  • Struts2學(xué)習(xí)教程之入門小白的開(kāi)始基礎(chǔ)

    Struts2學(xué)習(xí)教程之入門小白的開(kāi)始基礎(chǔ)

    struts2其實(shí)就是為我們封裝了servlet,簡(jiǎn)化了jsp跳轉(zhuǎn)的復(fù)雜操作,并且提供了易于編寫的標(biāo)簽,可以快速開(kāi)發(fā)view層的代碼。下面這篇文章主要給各位想要學(xué)習(xí)Struts2的小白們?cè)敿?xì)介紹了關(guān)于Struts2入門的一些開(kāi)始基礎(chǔ),需要的朋友可以參考下
    2018-04-04
  • Java中forEach使用lambda表達(dá)式,數(shù)組和集合的區(qū)別說(shuō)明

    Java中forEach使用lambda表達(dá)式,數(shù)組和集合的區(qū)別說(shuō)明

    這篇文章主要介紹了Java中forEach使用lambda表達(dá)式,數(shù)組和集合的區(qū)別說(shuō)明,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2021-07-07

最新評(píng)論

洪江市| 桐乡市| 都昌县| 天水市| 云霄县| 会同县| 肥乡县| 阳泉市| 专栏| 科尔| 上思县| 虞城县| 滨州市| 新巴尔虎左旗| 吉林市| 农安县| 玛纳斯县| 通海县| 石首市| 左权县| 华蓥市| 洪泽县| 扎囊县| 岳阳市| 玉环县| 彰化市| 望城县| 启东市| 比如县| 泗水县| 花莲县| 抚远县| 元谋县| 徐水县| 东山县| 马关县| 互助| 长丰县| 兰州市| 武平县| 兰考县|