在JComboBox中更改选择的颜色(选择之后) [英] Change color of selection (after selection) in a JComboBox

查看:80
本文介绍了在JComboBox中更改选择的颜色(选择之后)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用Swing编写GUI.我有一个使用ListCellRendererBasicComboBoxEditor编写的自定义JComboBox.

I'm writing a GUI using Swing. I have a custom written JComboBox using a ListCellRenderer and a BasicComboBoxEditor.

在我的getListCellRendererComponent()方法中,我根据项目是否被选中"(鼠标悬停在上方)更改列表的颜色,这很好,但我不希望选择更改背景一旦做出选择,就可以进行颜色选择.

In my getListCellRendererComponent() method I change the color of the the list based on whether the item is "selected" (mouse is hovering above), which is nice and all, but I don't want the selection to change background color once a choice is made, which it currently does.

第一张图显示了在进行选择之前界面的外观,第二张图显示了在选择界面之后的外观.

The first picture shows how the interface looks before a selection is made, and the second one shows how it looks after.

如何将选择"的背景更改为"stockColor"?

How do I change the background of the "selection" to the "stockColor"?

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.util.Vector;

import javax.swing.DefaultComboBoxModel;
import javax.swing.JButton;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JPanel;
import javax.swing.ListCellRenderer;
import javax.swing.plaf.basic.BasicComboBoxEditor;

public class TFComboBox extends JComboBox{

    public static void main(String[] args){     
        createAndShowGUI();
    }

    public static void createAndShowGUI(){
        JFrame frame = new JFrame("MCVE");

        JPanel pane = new JPanel(new BorderLayout());
        TFComboBox cb = new TFComboBox();
        boolean[] tf = {true, false};
        cb.addItems(tf);

        JButton b = new JButton("Click me!");

        pane.add(cb, BorderLayout.CENTER);
        pane.add(b, BorderLayout.LINE_END);

        frame.add(pane);

        frame.setLocationRelativeTo(null);
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.pack();
        frame.setVisible(true);
    }

    private DefaultComboBoxModel model;
    private Vector<Boolean> comboBoxItems;
    private JComboBox comboBox;

    public TFComboBox(){
        comboBoxItems = new Vector<Boolean>();
        comboBoxItems.add(Boolean.TRUE);
        comboBoxItems.add(Boolean.FALSE);

        comboBox = new JComboBox(comboBoxItems);

        model = new DefaultComboBoxModel();
        setModel(model);
        setRenderer(new TrueFalseComboRenderer());
        setEditor(new TrueFalseComboEditor());
    }

    public void addItems(boolean[] items){
        for(boolean anItem : items){
            model.addElement(anItem);
        }
    }
}

class TrueFalseComboRenderer extends JPanel implements ListCellRenderer {

    private JLabel labelItem = new JLabel();
    private Color stockColor = labelItem.getBackground();

    public TrueFalseComboRenderer(){
        setLayout(new BorderLayout());
        labelItem.setOpaque(true);
        labelItem.setHorizontalAlignment(JLabel.CENTER);

        add(labelItem);

        setBackground(Color.LIGHT_GRAY);
    }

    @Override
    public Component getListCellRendererComponent(JList list, Object value, 
            int index, boolean isSelected, boolean cellHasFocus) {

        boolean tempValue = (boolean) value;    
        labelItem.setText(Boolean.toString(tempValue));

        if(isSelected){
            labelItem.setBackground(stockColor.darker());
            labelItem.setForeground(Color.WHITE);
        } else {
            labelItem.setBackground(stockColor);
            labelItem.setForeground(Color.BLACK);
        }

        return this;
    }   
}

class TrueFalseComboEditor extends BasicComboBoxEditor {

    private JLabel labelItem = new JLabel();
    private JPanel panel = new JPanel();
    private Object selectedItem;

    public TrueFalseComboEditor() {
        labelItem.setOpaque(false);
        labelItem.setHorizontalAlignment(JLabel.CENTER);
        labelItem.setForeground(Color.WHITE);

        panel.setLayout(new FlowLayout(FlowLayout.LEFT, 5, 2));
        panel.setBackground(Color.BLUE);
        panel.add(labelItem);
    }

    public Component getEditorComponent(){
        return this.panel;
    }

    public Object getItem(){
        return this.selectedItem;
    }

    public void setItem(Object item){
        if(item == null){
            return;
        }

        this.selectedItem = item;
        labelItem.setText(item.toString());
    }
}

编辑

我添加了一个MCVE,正如您所看到的,JComboBox关注的问题"与我的问题有关.我在ComboBox旁边放置了一个按钮,以帮助从ComboBox移开焦点.

EDIT

I've added a MCVE and as you can see it is the "problem" that the JComboBox is focused that has to do with my issue. I've placed a button next to the ComboBox to help with removing the focus from the ComboBox.

只需执行setFocusable(false)即可修复该问题,但同时也剥夺了该程序其余部分的某些功能,因此不希望这样做.

Simply doing a setFocusable(false) would fix it, but also take away some of the functionality of the rest of the program, so this is not desired.

推荐答案

  • 为了获得更好的帮助,请尽快在本地变量中发布SSCCE / MCVE,简短,可运行,可编译且具有JComboBox/XxxComboBoxModel的硬编码值
  • JList已将布尔数组实现为API中的默认值(不知道隐藏在其中的内容是什么) String trueFalseItem = Boolean.toString(tempValue);,其值存储在JComboBox model)
  • 这只是测试isSelected并在DefaultListCellRenderer内更改JList.setSelectionXxx的最小代码
    • for better help sooner post an SSCCE / MCVE, short, runnable, compilable, with hardcoded value for JComboBox / XxxComboBoxModel in local variable
    • JList has Boolean array implemented as default in API (no idea whats hidden in String trueFalseItem = Boolean.toString(tempValue); and with value stored JComboBox model)
    • this is just code minimum to test isSelected and to change JList.setSelectionXxx inside DefaultListCellRenderer
    • 例如(SSCCE/MCVE格式的代码)

      for example (code in SSCCE / MCVE form)

      .

      .

      import java.awt.Color;
      import java.awt.Component;
      import java.awt.event.ActionEvent;
      import java.util.Vector;
      import javax.swing.AbstractAction;
      import javax.swing.Action;
      import javax.swing.DefaultListCellRenderer;
      import javax.swing.JComboBox;
      import javax.swing.JFrame;
      import javax.swing.JLabel;
      import javax.swing.JList;
      import javax.swing.SwingUtilities;
      
      public class ComboBoxBooleanModel {
      
          private javax.swing.Timer timer = null;
          private Vector<Boolean> comboBoxItems;
          private JComboBox box;
      
          public ComboBoxBooleanModel() {
              comboBoxItems = new Vector<Boolean>();
              comboBoxItems.add(Boolean.TRUE);
              comboBoxItems.add(Boolean.FALSE);
              box = new JComboBox(comboBoxItems);
              box.setRenderer(new DefaultListCellRenderer() {
                  @Override
                  public Component getListCellRendererComponent(JList list, Object value,
                          int index, boolean isSelected, boolean cellHasFocus) {
                      Component c = super.getListCellRendererComponent(
                              list, value, index, isSelected, cellHasFocus);
                      if (c instanceof JLabel) {
                          JLabel l = (JLabel) c;
                          if (Boolean.TRUE.equals(value)) {
                              l.setBackground(Color.RED);
                              if (isSelected) {
                                  list.setSelectionForeground(Color.RED);
                                  list.setSelectionBackground(Color.BLUE);
                              }
                          } else if (Boolean.FALSE.equals(value)) {
                              l.setBackground(Color.BLUE);
                              if (isSelected) {
                                  list.setSelectionForeground(Color.BLUE);
                                  list.setSelectionBackground(Color.RED);
                              }
                          }
                          return l;
                      }
                      return c;
                  }
              });
              JFrame frame = new JFrame("");
              frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
              frame.add(box);
              frame.setLocationRelativeTo(null);
              frame.pack();
              frame.setVisible(true);
              SwingUtilities.invokeLater(new Runnable() {
                  @Override
                  public void run() {
                      box.setSelectedIndex(1);
                  }
              });
              start();
          }
      
          private void start() {
              timer = new javax.swing.Timer(2250, updateCol());
              timer.start();
          }
      
          public Action updateCol() {
              return new AbstractAction("text load action") {
                  private static final long serialVersionUID = 1L;
      
                  @Override
                  public void actionPerformed(ActionEvent e) {
                      if (box.getSelectedItem() == (Boolean) false) {
                          box.setSelectedItem((Boolean) true);
                      } else {
                          box.setSelectedItem((Boolean) false);
                      }
                  }
              };
          }
      
          public static void main(String[] args) {
              SwingUtilities.invokeLater(new Runnable() {
                  @Override
                  public void run() {
                      ComboBoxBooleanModel comboBoxModel = new ComboBoxBooleanModel();
                  }
              });
          }
      }
      

      这篇关于在JComboBox中更改选择的颜色(选择之后)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆