java - 为什么我的 Combobox 不能正确更新其颜色?
问题描述
我在我的程序中实现了一个暗模式,一切都很好,除了一个不想改变它的颜色的组合框。
如您所见,组合框的“弹出窗口”会很好地改变颜色,但组合框本身不会。组合框的前景色也会发生变化,但背景不会发生变化。
我想,外观可能会导致问题。
在我的主要课程中:
UIManager.setLookAndFeel( UIManager.getSystemLookAndFeelClassName() );
我更改为暗模式的地方:
TeamInterface.userFilterComboBox.setBackground( darkBackgroundColor );
TeamInterface.userFilterComboBox.setForeground( fontColor );
SwingUtilities.updateComponentTreeUI( TeamInterface.userFilterComboBox );
我必须使用 updateComponentTreeUI-Method,否则“弹出窗口”也会保持白色。如果我删除主类中的外观,组合框看起来不错,正如您在这张图片中看到的那样,
但我不想摆脱系统外观,所以我尝试使用以下代码手动将组合框的 UI 编辑为金属:
userFilterComboBox.setUI( new MetalComboBoxUI() );
但是..结果很糟糕,即使理论上(至少我认为)它应该看起来和没有外观和感觉一样
解决方案
Combobox 不仅是背景和前景的组件,而且是复杂的组件。一个例子:JComboBox 由以下组成:
- 箭头按钮
- 项目列表
- 边框(并且有颜色)
- 选择的项目
所以为了改变你可以在你的 UIManager 中添加的所有内容,所有常量或者你可以定义一个新的 UIComponent。
因此PersonalComboBoxUI可以执行以下操作:
/**
* @contributor https://github.com/vincenzopalazzo
*/
public class PersonalComboBoxUI extends BasicComboBoxUI {
public static ComponentUI createUI (JComponent c) {
return new PersonalComboBoxUI ();
}
@Override
public void installUI (JComponent c) {
super.installUI (c);
JComboBox<?> comboBox = (JComboBox<?>) c;
comboBox.setBackground (UIManager.getColor ("ComboBox.background"));
comboBox.setForeground (UIManager.getColor ("ComboBox.foreground"));
comboBox.setBorder (UIManager.getBorder ("ComboBox.border"));
comboBox.setLightWeightPopupEnabled (true);
}
@Override
protected JButton createArrowButton () {
Icon icon = UIManager.getIcon ("ComboBox.buttonIcon");
JButton button;
if (icon != null) {
button = new JButton (icon);
}
else {
button = new BasicArrowButton (SwingConstants.SOUTH);
}
button.setOpaque (true);
button.setBackground (UIManager.getColor ("ComboBox.buttonBackground"));
button.setBorder (BorderFactory.createLineBorder(Color.black));
return button;
}
@Override
protected ListCellRenderer createRenderer() {
return new MaterialComboBoxRenderer();
}
}
您还应该定义 PersonalComboBoxRenderer
/**
* @contributor https://github.com/vincenzopalazzo
*/
public class PersonalComboBoxRenderer extends BasicComboBoxRenderer {
@Override
public Component getListCellRendererComponent (JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
JComponent component = (JComponent) super.getListCellRendererComponent (list, value, index, isSelected, cellHasFocus);
component.setBorder (BorderFactory.createEmptyBorder (5, 5, 5, 5));
component.setForeground (UIManager.getColor ("ComboBox.foreground"));
component.setBackground (isSelected || cellHasFocus ?
UIManager.getColor("ComboBox.selectedInDropDownBackground") :
UIManager.getColor("ComboBox.background"));
return component;
}
}
ps:在这种情况下,我使用 UIManager.put("ComboBox.background", COLOR) 在 JComponent 内部进行添加和分层。
因此,我想添加两个信息,说明您是否在 UIManager 或 PersonalComboBoxUI 中使用个人颜色,颜色应使用此代码定义
Color PINK_400 = new ColorUIResource (236, 64, 122);
因为当您去移除外观时,颜色无法移除,但如果您使用ColorUIResource,外观应该被正确移除。
最后,如果您不需要默认外观,我建议您使用库。
material-UI-swing有一个系统主题,用于在您的应用程序中创建个人计时,并且所有主题都是可个性化的。
这是 repo vincenzoapalazzo/material -ui-swing和atarw/material-ui-swing是相同的存储库和相同的开发人员,所以vincenzoapalazzo/material-us-swing是开发人员分支,包含更多修复和测试。
图书馆的一个例子是
.
Ps:我是MaterialTheming System的设计师。
推荐阅读
- python - 如何从可迭代对象中删除项目?
- python - JSON(嵌套)对象到 Pandas Dataframe
- ruby-on-rails - 无法从 Rails 中的库中获取变量
- amazon-web-services - 如何删除 Hive 默认分区值,__HIVE_DEFAULT_PARTITION__
- javascript - React + PostgreSQL + Node.js 在数据库中插入复选框值
- c# - Linux 应用服务中最简单的 AspNetCore MVC 应用无法连接到 SQL Server 数据库
- python - 使用 Python 发布 JSON 请求时出现 400 错误
- java - 为什么使用 jdk 14 构建 LibGDX 失败
- android - 无法使用android studio虚拟机
- c++ - C ++打印控制台输出到txt文件?