diff --git a/designer-base/src/main/java/com/fine/theme/light/ui/FineComboBoxUI.java b/designer-base/src/main/java/com/fine/theme/light/ui/FineComboBoxUI.java index 1e712238df..b410afc207 100644 --- a/designer-base/src/main/java/com/fine/theme/light/ui/FineComboBoxUI.java +++ b/designer-base/src/main/java/com/fine/theme/light/ui/FineComboBoxUI.java @@ -2,16 +2,21 @@ package com.fine.theme.light.ui; import com.fine.theme.utils.FineClientProperties; import com.fine.theme.utils.FineUIScale; +import com.fine.theme.utils.FineUIUtils; import com.formdev.flatlaf.ui.FlatComboBoxUI; import com.formdev.flatlaf.ui.FlatUIUtils; -import org.jetbrains.annotations.Nullable; import javax.swing.JButton; +import javax.swing.JComboBox; import javax.swing.JComponent; +import javax.swing.JScrollPane; +import javax.swing.ScrollPaneConstants; import javax.swing.SwingConstants; import javax.swing.plaf.ComponentUI; +import javax.swing.plaf.basic.ComboPopup; import java.awt.Dimension; import java.awt.Graphics2D; +import java.awt.Rectangle; /** * 提供 {@link javax.swing.JComboBox} 的UI类 @@ -47,8 +52,10 @@ public class FineComboBoxUI extends FlatComboBoxUI { @Override public Dimension getMinimumSize(JComponent c) { // ComboBox基于子组件计算适配尺寸性能一般,仅考虑部分ComboBox进行适配计算,其他采用默认值 - if (FineClientProperties.ADAPTIVE_COMBO_BOX.equals(getComboBoxTypeStr(c))) { - return super.getMinimumSize(c); + if (isAdaptiveComboBox(c)) { + Dimension dimension = super.getMinimumSize(c); + return new Dimension(Math.min(dimension.width, + FineUIUtils.getAndScaleInt("ComboBox.maximumWidth", 400)), dimension.height); } return FineUIScale.scale(new Dimension( FlatUIUtils.getUIInt("ComboBox.minimumWidth", 72), @@ -56,12 +63,41 @@ public class FineComboBoxUI extends FlatComboBoxUI { )); } - @Nullable - static String getComboBoxTypeStr(JComponent c) { + static boolean isAdaptiveComboBox(JComponent c) { Object value = c.getClientProperty(FineClientProperties.COMBO_BOX_TYPE); if (value instanceof String) { - return (String) value; + return FineClientProperties.ADAPTIVE_COMBO_BOX.equals(value); + } + return false; + } + + @Override + protected ComboPopup createPopup() { + return new FineComboPopup(this.comboBox); + } + + protected class FineComboPopup extends FlatComboPopup { + + protected FineComboPopup(JComboBox combo) { + super(combo); + } + + @Override + protected Rectangle computePopupBounds(int px, int py, int pw, int ph) { + Rectangle fitRectangle = super.computePopupBounds(px, py, pw, ph); + // 限制最大宽度,如超出则高度预留展示横向滚动条所需宽度 + int comboWidth = comboBox.getWidth(); + if (fitRectangle.width > comboWidth) { + return new Rectangle(px, py, comboWidth, fitRectangle.height + FlatUIUtils.getUIInt("ScrollBar.width", 10)); + } + return fitRectangle; + } + + @Override + protected JScrollPane createScroller() { + return new JScrollPane( list, + ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED, + ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED); } - return null; } } diff --git a/designer-base/src/main/resources/com/fine/theme/light/ui/laf/FineLightLaf.properties b/designer-base/src/main/resources/com/fine/theme/light/ui/laf/FineLightLaf.properties index 34e9f8e3c5..0adc8cf686 100644 --- a/designer-base/src/main/resources/com/fine/theme/light/ui/laf/FineLightLaf.properties +++ b/designer-base/src/main/resources/com/fine/theme/light/ui/laf/FineLightLaf.properties @@ -302,6 +302,7 @@ ColorChooser.swatchesDefaultRecentColor = $control ComboBox.border = com.fine.theme.light.ui.FineRoundBorder ComboBox.padding = @componentMargin ComboBox.minimumWidth = 72 +ComboBox.maximumWidth = 400 ComboBox.editorColumns = 0 ComboBox.maximumRowCount = 15 [mac]ComboBox.showPopupOnNavigation = true diff --git a/designer-chart/src/main/java/com/fr/design/chartx/component/MapAreaMatchPane.java b/designer-chart/src/main/java/com/fr/design/chartx/component/MapAreaMatchPane.java index 0334044235..970b5ea9fc 100644 --- a/designer-chart/src/main/java/com/fr/design/chartx/component/MapAreaMatchPane.java +++ b/designer-chart/src/main/java/com/fr/design/chartx/component/MapAreaMatchPane.java @@ -1,7 +1,6 @@ package com.fr.design.chartx.component; import com.fine.theme.icon.LazyIcon; -import com.fine.theme.utils.FineLayoutBuilder; import com.fine.theme.utils.FineUIUtils; import com.formdev.flatlaf.util.ScaledEmptyBorder; import com.fr.chartx.TwoTuple; @@ -48,8 +47,8 @@ import java.awt.event.ItemListener; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent; -import static com.fine.theme.utils.FineClientProperties.ADAPTIVE_COMBO_BOX; -import static com.fine.theme.utils.FineClientProperties.COMBO_BOX_TYPE; +import static com.fine.swing.ui.layout.Layouts.cell; +import static com.fine.swing.ui.layout.Layouts.row; import static com.fine.theme.utils.FineUIScale.scale; /** @@ -102,12 +101,13 @@ public class MapAreaMatchPane extends BasicBeanPane { } private JPanel createContentPane() { - tableNameCombox.putClientProperty(COMBO_BOX_TYPE, ADAPTIVE_COMBO_BOX); - areaNameBox.putClientProperty(COMBO_BOX_TYPE, ADAPTIVE_COMBO_BOX); - return FineLayoutBuilder.createHorizontalLayout(10, - new UILabel(Toolkit.i18nText("Fine-Design_Chart_Table_Data") + ":"), tableNameCombox, - new UILabel(Toolkit.i18nText("Fine-Design_Chart_Area_Name") + ":"), areaNameBox, - refreshLabel); + return row(10, + cell(new UILabel(Toolkit.i18nText("Fine-Design_Chart_Table_Data") + ":")), + cell(tableNameCombox).weight(1), + cell(new UILabel(Toolkit.i18nText("Fine-Design_Chart_Area_Name") + ":")), + cell(areaNameBox).weight(1), + cell(refreshLabel) + ).getComponent(); } private void initTable(TwoTuple> treeNodeAndItems) {