您的位置:首页 > Web前端 > JavaScript

带下拉箭头的按钮(JSplitButton)

2011-01-15 23:58 295 查看
最近需要用到带下拉箭头的按钮这样的组件,本来以为java是自带的有,在网上搜了N次,就是没有收到,最后就只有自己写了。写了几次,几次都觉得难看,后来又去网上搜,还是很令我失望,最后自己又硬着头皮来重写原来的了。现在终于写了一个自己比较满意的出来。先来看哈截图。



效果基本上还看得过去。

下面是具体代码:

/**
* All rights reserved,2010,mengke
*/
package com.mengke.j2se.swing;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.Insets;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import java.util.ArrayList;
import java.util.List;

import javax.swing.BorderFactory;
import javax.swing.Icon;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JPopupMenu;
import javax.swing.JSeparator;
/**
*@author mengke
* @email wqjsir@foxmail.com
*@version 2011-1-15下午11:35:31
*/
public class JSplitButton extends JButton {
private static final long serialVersionUID = -7431955200320586601L;
private JLabel textLabel = new JLabel();
private JLabel arrowButton = new JLabel();
private JPanel separatePanel = new JPanel(new BorderLayout());
private JPanel textPanel = new JPanel(new GridBagLayout());
private JPanel arrowButtonPanel = new JPanel(new GridBagLayout());
private JSeparator separator = new JSeparator(JSeparator.NORTH);
private boolean separatorVisible = true;
private boolean locationLeft = true;
private JPopupMenu optionPopMenu;
private JPopupMenu buttonPopMenu;
private List<ActionListener> listeners = new ArrayList<ActionListener>();
private static Color DEFAULT_BORDER_COLOR = Color.LIGHT_GRAY;
private Color borderColor =DEFAULT_BORDER_COLOR;

public JSplitButton() {
decorate();
}

public JSplitButton(String text) {
textLabel.setText(text);
decorate();
}

public JSplitButton(Icon icon) {
textLabel.setIcon(icon);
decorate();
}

public JSplitButton(String text, Icon icon) {
textLabel.setText(text);
textLabel.setIcon(icon);
decorate();
}

protected void decorate() {
setLayout(new GridBagLayout());
separatePanel.setOpaque(false);
arrowButtonPanel.setOpaque(false);
textPanel.setOpaque(false);
//这里主要是给分割条占一个位置,如果不约束的话,则在显示和隐藏分割条时,按钮界面就会扭动
separatePanel.setPreferredSize(new Dimension(2, 10));
separatePanel.add(separator, BorderLayout.CENTER);
arrowButton.setIcon(new ImageIcon("./images/option_7x7.png"));
arrowButtonPanel.add(arrowButton, new GridBagConstraints(0, 0, 1, 1, 1, 1, GridBagConstraints.WEST,
GridBagConstraints.NONE, new Insets(0, 2, 0, 2), 0, 0));
arrowButtonPanel.setBorder(BorderFactory.createEmptyBorder(1, 0, 1, 1));
textPanel.add(textLabel, new GridBagConstraints(0, 0, 1, 1, 1, 1, GridBagConstraints.WEST,
GridBagConstraints.BOTH, new Insets(0, 2, 0, 2), 0, 0));
textPanel.setBorder(BorderFactory.createEmptyBorder(1, 1, 1, 0));
add(textPanel, new GridBagConstraints(0, 0, 1, 1, 1, 1, GridBagConstraints.WEST, GridBagConstraints.BOTH,
new Insets(0, 0, 0, 0), 0, 0));

add(separatePanel, new GridBagConstraints(1, 0, 1, 1, 1, 1, GridBagConstraints.CENTER,
GridBagConstraints.VERTICAL, new Insets(0, 0, 0, 0), 0, 0));
add(arrowButtonPanel, new GridBagConstraints(2, 0, 1, 1, 1, 1, GridBagConstraints.EAST,
GridBagConstraints.BOTH, new Insets(0, 0, 0, 0), 0, 0));

setMargin(new Insets(0, 0, 0, 0));
addMouseListener(new MouseAdapter() {
public void mouseEntered(MouseEvent e) {
if (isEnabled()) {
separator.setVisible(true);
}
}

public void mouseExited(MouseEvent e) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
arrowButton.setIcon(new ImageIcon("./images/option_7x7.png"));
if (!isSeparatorVisible()) {
separator.setVisible(false);
}
textPanel.setBorder(BorderFactory.createEmptyBorder(1, 1, 1, 0));
arrowButtonPanel.setBorder(BorderFactory.createEmptyBorder(1, 0, 1, 1));
}
});

}

@Override
public void mouseClicked(final MouseEvent e) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
int x = separatePanel.getX();
if (e.getPoint().x > x) {
arrowButton.setIcon(new ImageIcon("./images/option_7x9.png"));
if (optionPopMenu != null) {
if(locationLeft){
optionPopMenu.show(JSplitButton.this, 0, JSplitButton.this.getHeight());
}else{
optionPopMenu.show(arrowButtonPanel, 0, arrowButtonPanel.getHeight());
}
}
} else {
for (ActionListener action : listeners) {
ActionEvent actionEvent = new ActionEvent(JSplitButton.this, ActionEvent.ACTION_FIRST,
"");
action.actionPerformed(actionEvent);
}
if(buttonPopMenu!=null){
buttonPopMenu.show(JSplitButton.this, 0, JSplitButton.this.getHeight());
}
}
}
});
}

@Override
public void mouseReleased(MouseEvent e) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
arrowButton.setIcon(new ImageIcon("./images/option_7x7.png"));
arrowButton.updateUI();
}
});
}
});

addMouseMotionListener(new MouseMotionListener() {
@Override
public void mouseDragged(MouseEvent e) {
}

@Override
public void mouseMoved(MouseEvent e) {
int x = separatePanel.getX();
if (e.getPoint().x > x) {
arrowButtonPanel.setBorder(BorderFactory.createMatteBorder(1, 0, 1, 1,borderColor));
textPanel.setBorder(BorderFactory.createEmptyBorder(1, 1, 1, 0));
} else {
textPanel.setBorder(BorderFactory.createMatteBorder(1, 1, 1, 0, borderColor));
arrowButtonPanel.setBorder(BorderFactory.createEmptyBorder(1, 0, 1, 1));
}
}
});
}
/**
* 获得中间的分割条是否显示。为true时表示,一直显示,为false时表示单鼠标进入才显示。默认为true,即一直显示
*
* @return
*/
public boolean isSeparatorVisible() {
return separatorVisible;
}

/**
* 设置中间的分割条是否显示。为true时表示,一直显示,为false时表示单鼠标进入才显示。默认为true,即一直显示
*
* @param separatorVisible
*/
public void setSeparatorVisible(boolean separatorVisible) {
this.separatorVisible = separatorVisible;
separator.setVisible(separatorVisible);
}

/**
* 获取右边箭头按钮菜单的菜单显示对其方式。true表示与按钮左边对齐,false表示与箭头按钮对齐。默认为左对齐
* @return
*/
public boolean isLocationLeft() {
return locationLeft;
}

/**
*  设置右边箭头按钮菜单的菜单显示对其方式。true表示与按钮左边对齐,false表示与箭头按钮对齐。默认为左对齐
* @param locationLeft
*/
public void setLocationLeft(boolean locationLeft) {
this.locationLeft = locationLeft;
}

/**
* 获得鼠标进入按钮时绘制的边框的颜色。默认为Color.LIGHT_GRAY
*
* @return
*/
public Color getBorderColor() {
return borderColor;
}

/**
* 设置鼠标进入按钮时绘制的边框的颜色。默认为Color.LIGHT_GRAY
*
* @param borderColor
*/
public void setBorderColor(Color borderColor) {
if(borderColor==null){
throw new IllegalArgumentException("边框颜色不能为空");
}
this.borderColor = borderColor;
}

/**
* 添加按钮监听事件,这里添加到的是按钮左边部分的事件监听。
*/
public void addActionListener(ActionListener action) {
listeners.add(action);
}

/**
* 移除按钮监听事件。
*/
public void removeActionListener(ActionListener action) {
listeners.remove(action);
}

/**
* 设置按钮的文本内容。这里设置到按钮左边部分。
*/
@Override
public void setText(String text) {
textLabel.setText(text);
}

/**
* 覆盖父类的设置图标方法。设置按钮的图标,这里是设置按钮左边部分图标。
*/
@Override
public void setIcon(Icon icon){
textLabel.setIcon(icon);
}

/**
* 设置点击右边箭头按钮时的菜单
*
* @param popupMenu
*/
public void setOptionPopMenu(JPopupMenu popupMenu) {
this.optionPopMenu = popupMenu;
}

/**
* 获取右边箭头按钮的菜单
*
* @return
*/
public JPopupMenu getOptionPopMenu() {
return optionPopMenu;
}

/**
* 获得按钮左边部分菜单
*
* @return
*/
public JPopupMenu getButtonPopMenu() {
return buttonPopMenu;
}

/**
* 设置箭头左边部分菜单
*
* @param buttonPopMenu
*/
public void setButtonPopMenu(JPopupMenu buttonPopMenu) {
this.buttonPopMenu = buttonPopMenu;
}
}


再贴出测试类代码如下:

/**
* All rights reserved,2010,mengke
*/
package com.mengke.j2se.ui.test;

import java.awt.Color;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import javax.swing.JFrame;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.JPopupMenu;

import com.mengke.j2se.swing.JSplitButton;

/**
*@author mengke
* @email wqjsir@foxmail.com
*@version 2011-1-15下午11:35:31
*/
public class JSplitButtonTest {
public static void main(String[] args) {
JSplitButton button = new JSplitButton("splitButton");
button.setSeparatorVisible(false);
button.setBorderColor(Color.green);
button.setLocationLeft(false);
//button.setIcon(new ImageIcon("./images/option_7x7.png"));
button.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
System.out.println("点击了按钮左边部分");
}
});
JFrame frame = new JFrame();
JPanel panel = new JPanel(new FlowLayout(FlowLayout.CENTER,20,20));

JPopupMenu popMenu = new JPopupMenu();
popMenu.add(new JMenuItem("Item1"));
popMenu.add(new JMenuItem("Item2"));
popMenu.add(new JMenuItem("Item3"));
button.setOptionPopMenu(popMenu);
panel.add(button);
frame.add(panel);
frame.setSize(new Dimension(200, 300));
frame.setVisible(true);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}


一切OK了。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐