我正在尝试根据特定条件为下拉框设置自定义渲染器:
themeComboBox.setRenderer(
settings == null ? themeComboBox.getRenderer() : new ThemeNameRenderer());
其中themeComboBox
是javax.swing.JComboBox<Path>
的实例,ThemeNameRenderer
是扩展DefaultListCellRenderer
的自定义类。
这不会编译,出现以下错误
method setRenderer in class JComboBox<E> cannot be applied to given types;
themeComboBox.setRenderer(settings == null ? themeComboBox.getRenderer() : new ThemeNameRenderer());
required: ListCellRenderer<? super Path>
found: ListCellRenderer<CAP#1>
reason: actual argument ListCellRenderer<CAP#1> cannot be converted to ListCellRenderer<? super Path> by method invocation conversion
where E is a type-variable:
E extends Object declared in class JComboBox
where CAP#1 is a fresh type-variable:
CAP#1 extends Object from capture of ? extends Object
如何使用条件运算符实现此功能?
我无法使用if语句或类似语句对setRenderer
的调用进行包围,因为我通过NetBeans GUI编辑器自定义代码。事实上,我需要做的全部原因是ThemeNameRenderer
使用在编辑器中设计GUI时不应加载的依赖项。
我的目标是Java 1.7。我认为代码在Java 1.8上编译。
我发现以下代码确实有效,但我想尽可能避免使用额外的方法。
themeComboBox.setRenderer(pickRenderer());
private ListCellRenderer<? super Path> pickRenderer() {
if (settings == null) {
return themeComboBox.getRenderer();
} else {
return new ThemeNameRenderer();
}
}
答案 0 :(得分:0)
似乎他们在Java 8中对类型推断添加了一些改进,这可能解释了行为的差异。
检查此页面中的“目标类型”部分:
https://docs.oracle.com/javase/tutorial/java/generics/genTypeInference.html
什么是目标类型的概念已经扩展到包括方法参数
这段代码很适合我使用Java 1.7(需要添加一个强制转换):
themeComboBox.setRenderer(
(ListCellRenderer<? super Path>) (settings == null ? themeComboBox.getRenderer() : new ThemeNameRenderer()));
使用Java 1.8编译原始代码:
themeComboBox.setRenderer(
settings == null ? themeComboBox.getRenderer() : new ThemeNameRenderer());