diff --git a/designer-base/src/main/java/com/fr/design/gui/frpane/AbstractAttrNoScrollPane.java b/designer-base/src/main/java/com/fr/design/gui/frpane/AbstractAttrNoScrollPane.java index a9321879c..ce09568d6 100644 --- a/designer-base/src/main/java/com/fr/design/gui/frpane/AbstractAttrNoScrollPane.java +++ b/designer-base/src/main/java/com/fr/design/gui/frpane/AbstractAttrNoScrollPane.java @@ -76,6 +76,9 @@ public abstract class AbstractAttrNoScrollPane extends BasicPane { hasChangeListener = false; } + public AttributeChangeListener getListener() { + return listener; + } public void initListener(Container parentComponent) { for (int i = 0; i < parentComponent.getComponentCount(); i++) { diff --git a/designer-base/src/main/java/com/fr/design/gui/icheckbox/UICheckBox.java b/designer-base/src/main/java/com/fr/design/gui/icheckbox/UICheckBox.java index e294d8022..0ddd3e22d 100644 --- a/designer-base/src/main/java/com/fr/design/gui/icheckbox/UICheckBox.java +++ b/designer-base/src/main/java/com/fr/design/gui/icheckbox/UICheckBox.java @@ -58,7 +58,7 @@ public class UICheckBox extends JCheckBox implements UIObserver, GlobalNameObser super(locText, b); setUI(new UICheckBoxUI()); initListener(); - this.markMnemonic=markMnemonic; + this.markMnemonic = markMnemonic; } public UICheckBox(String text, Icon icon) { @@ -100,6 +100,10 @@ public class UICheckBox extends JCheckBox implements UIObserver, GlobalNameObser } + public void removeChangeListener() { + uiObserverListener = null; + } + @Override public void setGlobalName(String name) { checkboxName = name; diff --git a/designer-base/src/main/java/com/fr/design/mainframe/theme/edit/ui/ColorListPane.java b/designer-base/src/main/java/com/fr/design/mainframe/theme/edit/ui/ColorListPane.java index 5c282033f..ab5d8a4ec 100644 --- a/designer-base/src/main/java/com/fr/design/mainframe/theme/edit/ui/ColorListPane.java +++ b/designer-base/src/main/java/com/fr/design/mainframe/theme/edit/ui/ColorListPane.java @@ -139,7 +139,7 @@ public class ColorListPane extends JPanel implements UIObserver { return true; } - private static class ColorButton extends AbstractSelectBox { + public static class ColorButton extends AbstractSelectBox { private Color color; private NewColorSelectPane colorPane; private ChangeListener changeListener; diff --git a/designer-base/src/main/resources/com/fr/design/images/sort/add.png b/designer-base/src/main/resources/com/fr/design/images/sort/add.png new file mode 100644 index 000000000..a14e2a40b Binary files /dev/null and b/designer-base/src/main/resources/com/fr/design/images/sort/add.png differ diff --git a/designer-base/src/main/resources/com/fr/design/images/sort/asc.svg b/designer-base/src/main/resources/com/fr/design/images/sort/asc.svg new file mode 100644 index 000000000..67dd9e829 --- /dev/null +++ b/designer-base/src/main/resources/com/fr/design/images/sort/asc.svg @@ -0,0 +1,19 @@ + + + 升序备份 + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/designer-base/src/main/resources/com/fr/design/images/sort/des.svg b/designer-base/src/main/resources/com/fr/design/images/sort/des.svg new file mode 100644 index 000000000..2fcef077e --- /dev/null +++ b/designer-base/src/main/resources/com/fr/design/images/sort/des.svg @@ -0,0 +1,17 @@ + + + 降序 + + + + + + + + + + + + + + \ No newline at end of file diff --git a/designer-base/src/main/resources/com/fr/design/images/sort/down_arrow.png b/designer-base/src/main/resources/com/fr/design/images/sort/down_arrow.png new file mode 100644 index 000000000..84b4909ef Binary files /dev/null and b/designer-base/src/main/resources/com/fr/design/images/sort/down_arrow.png differ diff --git a/designer-base/src/main/resources/com/fr/design/images/sort/left_arrow.png b/designer-base/src/main/resources/com/fr/design/images/sort/left_arrow.png new file mode 100644 index 000000000..9166a9c96 Binary files /dev/null and b/designer-base/src/main/resources/com/fr/design/images/sort/left_arrow.png differ diff --git a/designer-base/src/main/resources/com/fr/design/images/sort/nosort.svg b/designer-base/src/main/resources/com/fr/design/images/sort/nosort.svg new file mode 100644 index 000000000..ca04928fc --- /dev/null +++ b/designer-base/src/main/resources/com/fr/design/images/sort/nosort.svg @@ -0,0 +1,41 @@ + + + 不排序 + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/designer-form/src/main/java/com/fr/design/mainframe/share/ui/base/PlaceholderTextArea.java b/designer-form/src/main/java/com/fr/design/mainframe/share/ui/base/PlaceholderTextArea.java index c463a4903..d37ee52c2 100644 --- a/designer-form/src/main/java/com/fr/design/mainframe/share/ui/base/PlaceholderTextArea.java +++ b/designer-form/src/main/java/com/fr/design/mainframe/share/ui/base/PlaceholderTextArea.java @@ -10,22 +10,27 @@ import java.awt.RenderingHints; * created by Harrison on 2020/04/21 **/ public class PlaceholderTextArea extends UITextArea { - + private String placeholder; - + public PlaceholderTextArea() { } - + public PlaceholderTextArea(String s, String placeholder) { super(s); this.placeholder = placeholder; } - + + public PlaceholderTextArea(int i, int j, String placeholder) { + super(i, j); + this.placeholder = placeholder; + } + public void setPlaceholder(String placeholder) { - + this.placeholder = placeholder; } - + @Override protected void paintComponent(final Graphics pG) { super.paintComponent(pG); @@ -37,6 +42,16 @@ public class PlaceholderTextArea extends UITextArea { RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); g.setColor(getDisabledTextColor()); - g.drawString(placeholder, getInsets().left, pG.getFontMetrics() - .getMaxAscent() + getInsets().top + 1); - }} + drawPlaceholder(pG); + } + + private void drawPlaceholder(Graphics g) { + int x = getInsets().left; + int y = g.getFontMetrics().getMaxAscent() + getInsets().top + 1; + for (String line : placeholder.split("\n")) { + g.drawString(line, x, y); + y += g.getFontMetrics().getHeight(); + } + + } +} diff --git a/designer-realize/src/main/java/com/fr/design/mainframe/cell/settingpane/CellExpandAttrPane.java b/designer-realize/src/main/java/com/fr/design/mainframe/cell/settingpane/CellExpandAttrPane.java index cd454660d..979d4534f 100644 --- a/designer-realize/src/main/java/com/fr/design/mainframe/cell/settingpane/CellExpandAttrPane.java +++ b/designer-realize/src/main/java/com/fr/design/mainframe/cell/settingpane/CellExpandAttrPane.java @@ -13,6 +13,7 @@ import com.fr.design.i18n.Toolkit; import com.fr.design.layout.TableLayout; import com.fr.design.layout.TableLayoutHelper; import com.fr.design.mainframe.theme.utils.DefaultThemedTemplateCellElementCase; +import com.fr.design.sort.cellexpand.CellExpandSortPane; import com.fr.general.ComparatorUtils; import com.fr.general.IOUtils; import com.fr.report.cell.TemplateCellElement; @@ -43,6 +44,7 @@ public class CellExpandAttrPane extends AbstractCellAttrPane { private JPanel basicPane; private JPanel seniorPane; private CellExpandExtraAttrPane extraPane; + private CellExpandSortPane cellExpandSortPane; /** @@ -81,8 +83,10 @@ public class CellExpandAttrPane extends AbstractCellAttrPane { seniorPane = new JPanel(); basicPane = new UIExpandablePane(Toolkit.i18nText("Fine-Design_Report_Basic"), 223, 24, basicPane()); seniorPane = new UIExpandablePane(Toolkit.i18nText("Fine-Design_Report_Advanced"), 223, 24, seniorPane()); + JPanel sortUIExpandablePane = new UIExpandablePane("扩展后排序", 223, 24, cellExpandSortPane = new CellExpandSortPane(this)); layoutPane.add(basicPane, BorderLayout.NORTH); layoutPane.add(seniorPane, BorderLayout.CENTER); + layoutPane.add(sortUIExpandablePane, BorderLayout.SOUTH); extraPane = CellExpandExtraAttrPane.getInstance(); @@ -172,6 +176,7 @@ public class CellExpandAttrPane extends AbstractCellAttrPane { sortAfterExpand.populate(cellExpandAttr); extraPane.populate(cellElement); + cellExpandSortPane.populateBean(cellElement); } @@ -222,6 +227,7 @@ public class CellExpandAttrPane extends AbstractCellAttrPane { } extraPane.update(cellElement); + cellExpandSortPane.updateBean(cellElement); } /** diff --git a/designer-realize/src/main/java/com/fr/design/sort/celldscolumn/CellDSColumnSortGroupPane.java b/designer-realize/src/main/java/com/fr/design/sort/celldscolumn/CellDSColumnSortGroupPane.java new file mode 100644 index 000000000..f5cdd0a8d --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/celldscolumn/CellDSColumnSortGroupPane.java @@ -0,0 +1,40 @@ +package com.fr.design.sort.celldscolumn; + +import com.fr.design.data.DesignTableDataManager; +import com.fr.design.data.tabledata.wrapper.TableDataWrapper; +import com.fr.design.file.HistoryTemplateListCache; +import com.fr.design.sort.common.AbstractSortGroupPane; +import com.fr.design.sort.common.AbstractSortItemPane; +import com.fr.report.cell.cellattr.core.group.DSColumn; +import com.fr.report.core.sort.sortexpression.SortExpression; + +public class CellDSColumnSortGroupPane extends AbstractSortGroupPane { + DSColumn dsColumn; + + + public CellDSColumnSortGroupPane(int sortGroupPaneWidth, int sortGroupPaneRightWidth) { + super(sortGroupPaneWidth, sortGroupPaneRightWidth); + } + + public void populateDsColumn( DSColumn dsColumn){ + this.dsColumn = dsColumn; + } + + + @Override + protected AbstractSortItemPane refreshSortItemPane(int sortItemPaneWidth, int sortItemPaneRightWidth, SortExpression sortExpression) { + CellDSColumnSortItemPane cellDSColumnSortItemPane = new CellDSColumnSortItemPane( sortItemPaneWidth, sortItemPaneRightWidth); + java.util.Map tableDataWrapperMap = + DesignTableDataManager.getAllEditingDataSet(HistoryTemplateListCache.getInstance().getCurrentEditingTemplate().getTarget()); + TableDataWrapper tableDataWrapper = tableDataWrapperMap.get(dsColumn.getDSName()); + java.util.List columnNameList = tableDataWrapper.calculateColumnNameList(); + String[] columnNames = new String[columnNameList.size()]; + columnNameList.toArray(columnNames); + cellDSColumnSortItemPane.sortAreaUiComboBox.removeAllItems(); + for (String columnName : columnNames) { + cellDSColumnSortItemPane.sortAreaUiComboBox.addItem(columnName); + } + cellDSColumnSortItemPane.populateBean(sortExpression); + return cellDSColumnSortItemPane; + } +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/celldscolumn/CellDSColumnSortItemPane.java b/designer-realize/src/main/java/com/fr/design/sort/celldscolumn/CellDSColumnSortItemPane.java new file mode 100644 index 000000000..c87b729e6 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/celldscolumn/CellDSColumnSortItemPane.java @@ -0,0 +1,52 @@ +package com.fr.design.sort.celldscolumn; + +import com.fr.design.event.UIObserverListener; +import com.fr.design.gui.icombobox.UIComboBox; +import com.fr.design.sort.common.AbstractSortItemPane; +import com.fr.design.sort.common.AbstractSortPane; +import com.fr.report.core.sort.sortexpression.SortExpression; + +import javax.swing.*; +import java.awt.*; + + +public class CellDSColumnSortItemPane extends AbstractSortItemPane { + + + UIComboBox sortAreaUiComboBox; + + public CellDSColumnSortItemPane(int sortItemPaneWidth, int sortItemPaneRightWidth) { + super(sortItemPaneWidth, sortItemPaneRightWidth); + } + + @Override + public void initMainSortAreaPane(JPanel sortAreaPane) { + sortAreaUiComboBox = new UIComboBox(new String[0]); + sortAreaUiComboBox.setPreferredSize(new Dimension(sortItemPaneRightWidth, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + sortAreaPane.add(sortAreaUiComboBox); + } + + public void populateBean(SortExpression sortExpression) { + sortAreaUiComboBox.setSelectedItem(sortExpression.getSortArea()); + super.populateBean(sortExpression); + } + + public SortExpression updateBean() { + SortExpression sortExpression = super.updateBean(); + if (sortExpression != null) { + sortExpression.setSortArea(sortAreaUiComboBox.getSelectedItem().toString()); + } + return sortExpression; + } + + public void addListener(UIObserverListener uiObserverListener) { + super.addListener(uiObserverListener); + sortAreaUiComboBox.registerChangeListener(uiObserverListener); + } + + + public void removeListener(UIObserverListener uiObserverListener) { + super.removeListener(uiObserverListener); + sortAreaUiComboBox.removeChangeListener(); + } +} \ No newline at end of file diff --git a/designer-realize/src/main/java/com/fr/design/sort/celldscolumn/CellDSColumnSortPane.java b/designer-realize/src/main/java/com/fr/design/sort/celldscolumn/CellDSColumnSortPane.java new file mode 100644 index 000000000..68865dca4 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/celldscolumn/CellDSColumnSortPane.java @@ -0,0 +1,57 @@ +package com.fr.design.sort.celldscolumn; + +import com.fr.design.sort.common.AbstractSortPane; +import com.fr.general.data.TableDataColumn; +import com.fr.report.cell.TemplateCellElement; +import com.fr.report.cell.cellattr.core.group.DSColumn; +import com.fr.report.core.sort.common.CellSortAttr; + + +public class CellDSColumnSortPane extends AbstractSortPane { + + + public CellDSColumnSortPane() { + super(220, 150); + + } + + + @Override + protected void initSortGroupPane() { + sortGroupPane = new CellDSColumnSortGroupPane(sortPaneWidth, sortPaneRightWidth); + this.add(sortGroupPane); + } + + + @Override + protected CellSortAttr getCellSortAttr(TemplateCellElement cellElement) { + if (cellElement.getValue() instanceof DSColumn) { + DSColumn dsColumn = ((DSColumn) cellElement.getValue()); + return dsColumn.getCellSortAttr(); + } + return new CellSortAttr(); + } + + protected void populateSortArea(TemplateCellElement cellElement) { + super.populateSortArea(cellElement); + if (cellElement.getValue() instanceof DSColumn) { + DSColumn dsColumn = ((DSColumn) cellElement.getValue()); + TableDataColumn tableDataColumn = dsColumn.getColumn(); + if (tableDataColumn instanceof TableDataColumn.ColumnName) { + selfSortArea = ((TableDataColumn.ColumnName) dsColumn.getColumn()).getName(); + } + } + } + + + public void populateBean(TemplateCellElement cellElement) { + if (cellElement.getValue() instanceof DSColumn) { + DSColumn dsColumn = ((DSColumn) cellElement.getValue()); + if (sortGroupPane != null) { + ((CellDSColumnSortGroupPane) sortGroupPane).populateDsColumn(dsColumn); + } + } + super.populateBean(cellElement); + } + +} \ No newline at end of file diff --git a/designer-realize/src/main/java/com/fr/design/sort/cellexpand/CellExpandSortGroupPane.java b/designer-realize/src/main/java/com/fr/design/sort/cellexpand/CellExpandSortGroupPane.java new file mode 100644 index 000000000..330b43d73 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/cellexpand/CellExpandSortGroupPane.java @@ -0,0 +1,20 @@ +package com.fr.design.sort.cellexpand; + +import com.fr.design.sort.common.AbstractSortGroupPane; +import com.fr.design.sort.common.AbstractSortItemPane; +import com.fr.report.core.sort.sortexpression.SortExpression; + +public class CellExpandSortGroupPane extends AbstractSortGroupPane { + + + public CellExpandSortGroupPane(int sortGroupPaneWidth, int sortGroupPaneRightWidth) { + super(sortGroupPaneWidth, sortGroupPaneRightWidth); + } + + @Override + protected AbstractSortItemPane refreshSortItemPane(int sortItemPaneWidth, int sortItemPaneRightWidth, SortExpression sortExpression) { + AbstractSortItemPane abstractSortItemPane = new CellExpandSortItemPane( sortItemPaneWidth, sortItemPaneRightWidth); + abstractSortItemPane.populateBean(sortExpression); + return abstractSortItemPane; + } +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/cellexpand/CellExpandSortItemPane.java b/designer-realize/src/main/java/com/fr/design/sort/cellexpand/CellExpandSortItemPane.java new file mode 100644 index 000000000..2b3bee994 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/cellexpand/CellExpandSortItemPane.java @@ -0,0 +1,49 @@ +package com.fr.design.sort.cellexpand; + +import com.fr.design.event.UIObserverListener; +import com.fr.design.sort.common.AbstractSortPane; +import com.fr.design.sort.common.SortColumnRowPane; +import com.fr.design.sort.common.AbstractSortItemPane; +import com.fr.report.core.sort.sortexpression.SortExpression; +import com.fr.stable.ColumnRow; + +import javax.swing.*; + +public class CellExpandSortItemPane extends AbstractSortItemPane { + SortColumnRowPane columnRowPane; + + public CellExpandSortItemPane(int sortItemPaneWidth, int sortItemPaneRightWidth) { + super(sortItemPaneWidth, sortItemPaneRightWidth); + } + + @Override + public void initMainSortAreaPane(JPanel sortAreaPane) { + columnRowPane = new SortColumnRowPane(sortItemPaneRightWidth, AbstractSortPane.PANE_COMPONENT_HEIGHT); + sortAreaPane.add(columnRowPane); + } + + public void populateBean(SortExpression sortExpression) { + columnRowPane.populateBean(ColumnRow.valueOf(sortExpression.getSortArea())); + super.populateBean(sortExpression); + } + + public SortExpression updateBean() { + SortExpression sortExpression = super.updateBean(); + if (sortExpression != null) { + ColumnRow columnRow = columnRowPane.updateBean(); + sortExpression.setSortArea(columnRow == null ? null : columnRow.toString()); + } + return sortExpression; + } + + public void addListener(UIObserverListener uiObserverListener) { + super.addListener(uiObserverListener); + columnRowPane.addListener(uiObserverListener); + } + + + public void removeListener(UIObserverListener uiObserverListener) { + super.removeListener(uiObserverListener); + columnRowPane.removeListener(uiObserverListener); + } +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/cellexpand/CellExpandSortPane.java b/designer-realize/src/main/java/com/fr/design/sort/cellexpand/CellExpandSortPane.java new file mode 100644 index 000000000..b1412d18b --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/cellexpand/CellExpandSortPane.java @@ -0,0 +1,58 @@ +package com.fr.design.sort.cellexpand; + +import com.fr.design.event.UIObserverListener; +import com.fr.design.gui.frpane.AttributeChangeListener; +import com.fr.design.mainframe.cell.settingpane.CellExpandAttrPane; +import com.fr.design.sort.common.AbstractSortPane; +import com.fr.report.cell.TemplateCellElement; +import com.fr.report.cell.cellattr.CellExpandAttr; +import com.fr.report.core.sort.common.CellSortAttr; +import com.fr.report.core.sort.sortexpression.FormulaSortExpression; +import com.fr.report.core.sort.sortexpression.SortExpression; +import com.fr.report.core.sort.header.SortHeader; +import com.fr.report.core.sort.common.SortRule; + + +import javax.swing.*; +import java.util.ArrayList; +import java.util.List; + +public class CellExpandSortPane extends AbstractSortPane { + CellExpandAttrPane cellExpandAttrPane; + + public CellExpandSortPane(CellExpandAttrPane cellExpandAttrPane) { + super(227, 155); + this.cellExpandAttrPane = cellExpandAttrPane; + this.setLayout(new BoxLayout(this, BoxLayout.Y_AXIS)); + } + + + @Override + protected void initSortGroupPane() { + sortGroupPane = new CellExpandSortGroupPane(sortPaneWidth, sortPaneRightWidth); + this.add(sortGroupPane); + } + + @Override + protected void initUIObserverListener() { + uiObserverListener = new UIObserverListener() { + @Override + public void doChange() { + AttributeChangeListener attributeChangeListener = cellExpandAttrPane.getListener(); + if (attributeChangeListener != null) { + attributeChangeListener.attributeChange(); + } + } + }; + } + + @Override + protected CellSortAttr getCellSortAttr(TemplateCellElement cellElement) { + CellExpandAttr cellExpandAttr = cellElement.getCellExpandAttr(); + if (cellExpandAttr != null) { + return cellExpandAttr.getCellSortAttr(); + } + return new CellSortAttr(); + } + +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/common/AbstractSortGroupPane.java b/designer-realize/src/main/java/com/fr/design/sort/common/AbstractSortGroupPane.java new file mode 100644 index 000000000..8aae8d30f --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/common/AbstractSortGroupPane.java @@ -0,0 +1,146 @@ +package com.fr.design.sort.common; + +import com.fr.base.svg.IconUtils; +import com.fr.design.event.UIObserverListener; +import com.fr.design.gui.ibutton.UIButton; +import com.fr.report.core.sort.sortexpression.CellSortExpression; +import com.fr.report.core.sort.sortexpression.SortExpression; + +import javax.swing.*; +import java.awt.*; +import java.awt.event.MouseAdapter; +import java.awt.event.MouseEvent; +import java.util.ArrayList; +import java.util.List; + + +public abstract class AbstractSortGroupPane extends JPanel { + + protected int sortGroupPaneWidth; + protected int sortGroupPaneRightWidth; + UIObserverListener uiObserverListener; + List sortExpressions; + List sortItemPanes = new ArrayList<>(); + AddSortItemBar addSortItemBar; + UIButton uiButton; + String selfSortArea; + + public AbstractSortGroupPane(int sortGroupPaneWidth, int sortGroupPaneRightWidth) { + this.sortGroupPaneRightWidth = sortGroupPaneRightWidth; + this.sortGroupPaneWidth = sortGroupPaneWidth; + this.setLayout(new BoxLayout(this, BoxLayout.Y_AXIS)); + + initComponents(); + } + + private void initComponents() { + addSortItemBar = new AddSortItemBar(this); + this.add(addSortItemBar); + } + + public void populateBean(List sortExpressions, String selfSortArea) { + this.selfSortArea = selfSortArea; + this.sortExpressions = sortExpressions; + refreshBean(); + } + + public void refreshBean() { + removeListener(uiObserverListener); + this.removeAll(); + sortItemPanes = new ArrayList<>(); + for (int i = 0; i < sortExpressions.size(); i++) { + int sortItemPaneWidth = sortGroupPaneWidth; + int sortItemPaneRightWidth = sortGroupPaneRightWidth; + if (i != 0) { + sortItemPaneWidth -= 12; + sortItemPaneRightWidth -= 12; + } + AbstractSortItemPane sortItemPane = refreshSortItemPane(sortItemPaneWidth, sortItemPaneRightWidth, sortExpressions.get(i)); + sortItemPanes.add(sortItemPane); + if (i == 0) { + this.add(sortItemPane); + } else { + SortUIExpandablePane sortUIExpandablePane = new SortUIExpandablePane(sortItemPane, this); + this.add(sortUIExpandablePane); + } + } + initComponents(); + addListener(uiObserverListener); + refresh(); + } + + protected abstract AbstractSortItemPane refreshSortItemPane(int sortItemPaneWidth, int sortItemPaneRightWidth, SortExpression sortExpression); + + public List updateBean() { + updateSortExpressions(); + return sortExpressions; + } + + private void updateSortExpressions() { + sortExpressions = new ArrayList<>(); + for (AbstractSortItemPane sortItemPane : sortItemPanes) { + SortExpression sortExpression = sortItemPane.updateBean(); + if (sortExpression != null) { + sortExpressions.add(sortExpression); + } + } + } + + public void removeSortItem(int no) { + updateSortExpressions(); + if (no < sortExpressions.size()) { + sortExpressions.remove(no); + } + refreshBean(); + } + + public void addSortItem() { + updateSortExpressions(); + sortExpressions.add(new CellSortExpression(selfSortArea)); + refreshBean(); + } + + + protected void refresh() { + validate(); + repaint(); + revalidate(); + } + + class AddSortItemBar extends JPanel { + AbstractSortGroupPane sortGroupPane; + + AddSortItemBar(AbstractSortGroupPane sortGroupPane) { + init(); + this.sortGroupPane = sortGroupPane; + } + + void init() { + uiButton = new UIButton("添加排序", IconUtils.readIcon("/com/fr/design/images/sort/add.png")); + uiButton.setPreferredSize(new Dimension(sortGroupPaneWidth - 4, 20)); + this.add(uiButton); + uiButton.addMouseListener(new MouseAdapter() { + @Override + public void mouseClicked(MouseEvent e) { + sortGroupPane.addSortItem(); + uiObserverListener.doChange(); + } + }); + } + } + + + public void addListener(UIObserverListener uiObserverListener) { + this.uiObserverListener = uiObserverListener; + for (AbstractSortItemPane abstractSortItemPane : sortItemPanes) { + abstractSortItemPane.addListener(uiObserverListener); + } + } + + public void removeListener(UIObserverListener uiObserverListener) { + for (AbstractSortItemPane abstractSortItemPane : sortItemPanes) { + abstractSortItemPane.removeListener(uiObserverListener); + } + } + +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/common/AbstractSortItemPane.java b/designer-realize/src/main/java/com/fr/design/sort/common/AbstractSortItemPane.java new file mode 100644 index 000000000..0bd3701bb --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/common/AbstractSortItemPane.java @@ -0,0 +1,173 @@ +package com.fr.design.sort.common; + +import com.fr.design.event.UIObserverListener; +import com.fr.design.gui.icombobox.UIComboBox; +import com.fr.design.gui.ilable.UILabel; + +import com.fr.design.sort.expressionpane.CellSortExpressionPane; +import com.fr.design.sort.expressionpane.CustomSequenceSortExpressionPane; +import com.fr.design.sort.expressionpane.EmptyExpressionPane; +import com.fr.design.sort.expressionpane.FormulaSortExpressionPane; +import com.fr.design.sort.expressionpane.SortExpressionPane; +import com.fr.report.core.sort.sortexpression.SortExpression; +import com.fr.report.core.sort.common.SortRule; +import com.fr.stable.StringUtils; + +import javax.swing.*; +import java.awt.*; +import java.awt.event.ItemEvent; +import java.awt.event.ItemListener; +import java.util.ArrayList; +import java.util.List; + +public abstract class AbstractSortItemPane extends JPanel { + + protected int sortItemPaneWidth; + protected int sortItemPaneRightWidth; + List sortExpressionPanes = new ArrayList<>(); + SortExpressionPane currentSortExpressionPane = null; + JPanel sortBasisPanel = null; + UIComboBox sortRuleUiComboBox; + UIComboBox sortBasisUiComboBox; + JPanel sortAreaPane; + JPanel sortRulePane; + + public AbstractSortItemPane(int sortItemPaneWidth, int sortItemPaneRightWidth) { + this.sortItemPaneWidth = sortItemPaneWidth; + this.sortItemPaneRightWidth = sortItemPaneRightWidth; + this.setLayout(new BoxLayout(this, BoxLayout.Y_AXIS)); + registerSortExpressionPanes(); + initComponents(); + } + + private void initComponents() { + initSortAreaPane(); + initSortBasisPanel(); + initSortRulePane(); + } + + private void registerSortExpressionPanes() { + sortExpressionPanes.add(new EmptyExpressionPane()); + sortExpressionPanes.add(new CellSortExpressionPane(sortItemPaneRightWidth)); + sortExpressionPanes.add(new FormulaSortExpressionPane(sortItemPaneRightWidth)); + sortExpressionPanes.add(new CustomSequenceSortExpressionPane(sortItemPaneWidth, sortItemPaneRightWidth)); + } + + void initSortAreaPane() { + sortAreaPane = new JPanel(new FlowLayout(FlowLayout.LEFT, 0, AbstractSortPane.PANE_COMPONENT_V_GAP)); + sortAreaPane.add(new UILabel("排序区域", SwingConstants.LEFT)); + sortAreaPane.add(AbstractSortPane.createIntervalUILabel()); + initMainSortAreaPane(sortAreaPane); + this.add(sortAreaPane); + } + + public abstract void initMainSortAreaPane(JPanel sortAreaPane); + + void initSortRulePane() { + sortRulePane = new JPanel(new FlowLayout(FlowLayout.LEFT, 0, AbstractSortPane.PANE_COMPONENT_V_GAP)); + sortRuleUiComboBox = new UIComboBox(new String[]{"升序", "降序", "不排序"}); + sortRuleUiComboBox.setPreferredSize(new Dimension(sortItemPaneRightWidth, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + sortRulePane.add(new UILabel("排序规则", SwingConstants.LEFT)); + sortRulePane.add(AbstractSortPane.createIntervalUILabel()); + sortRulePane.add(sortRuleUiComboBox); + this.add(sortRulePane); + } + + + void initSortBasisPanel() { + sortBasisPanel = new JPanel(new FlowLayout(FlowLayout.LEFT, 0, AbstractSortPane.PANE_COMPONENT_V_GAP)); + sortBasisUiComboBox = new UIComboBox(getSortNames()); + sortBasisUiComboBox.setPreferredSize(new Dimension(sortItemPaneRightWidth, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + sortBasisUiComboBox.addItemListener(new ItemListener() { + @Override + public void itemStateChanged(ItemEvent e) { + if (sortExpressionPanes.get(sortBasisUiComboBox.getSelectedIndex()) != currentSortExpressionPane) { + if (currentSortExpressionPane != null) { + currentSortExpressionPane.setVisible(false); + } + currentSortExpressionPane = sortExpressionPanes.get(sortBasisUiComboBox.getSelectedIndex()); + refreshCurrentSortExpressionPane(); + } + } + }); + + + sortBasisPanel.add(new UILabel("排序依据", SwingConstants.LEFT)); + sortBasisPanel.add(AbstractSortPane.createIntervalUILabel()); + sortBasisPanel.add(sortBasisUiComboBox); + this.add(sortBasisPanel); + for (SortExpressionPane sortExpressionPane : sortExpressionPanes) { + this.add(sortExpressionPane); + sortExpressionPane.setVisible(false); + } + } + + private void refreshCurrentSortExpressionPane() { + currentSortExpressionPane.setVisible(true); + sortAreaPane.setVisible(currentSortExpressionPane.needSortArea()); + sortRulePane.setVisible(currentSortExpressionPane.needSortRule()); + } + + private String[] getSortNames() { + String[] sortNames = new String[sortExpressionPanes.size()]; + for (int i = 0; i < sortExpressionPanes.size(); i++) { + sortNames[i] = sortExpressionPanes.get(i).getSortName(); + } + return sortNames; + } + + public void populateBean(SortExpression sortExpression) { + if (sortExpression.getSortRule() == SortRule.ASC) { + sortRuleUiComboBox.setSelectedIndex(0); + } else if (sortExpression.getSortRule() == SortRule.DES) { + sortRuleUiComboBox.setSelectedIndex(1); + } else if (sortExpression.getSortRule() == SortRule.NO_SORT) { + sortRuleUiComboBox.setSelectedIndex(2); + } + + for (int i = 0; i < sortExpressionPanes.size(); i++) { + if (StringUtils.equals(sortExpression.getSortName(), sortExpressionPanes.get(i).getSortName())) { + if (currentSortExpressionPane != null) { + currentSortExpressionPane.setVisible(false); + } + currentSortExpressionPane = sortExpressionPanes.get(i); + currentSortExpressionPane.populateBean(sortExpression); + sortBasisUiComboBox.setSelectedIndex(i); + refreshCurrentSortExpressionPane(); + break; + } + } + refresh(); + } + + public SortExpression updateBean() { + SortExpression sortExpression = currentSortExpressionPane.updateBean(); + if (sortExpression != null) { + if (StringUtils.equals(sortRuleUiComboBox.getSelectedItem().toString(), "升序")) { + sortExpression.setSortRule(SortRule.ASC); + } else if (StringUtils.equals(sortRuleUiComboBox.getSelectedItem().toString(), "降序")) { + sortExpression.setSortRule(SortRule.DES); + } else if (StringUtils.equals(sortRuleUiComboBox.getSelectedItem().toString(), "不排序")) { + sortExpression.setSortRule(SortRule.NO_SORT); + } + } + return sortExpression; + } + + public void addListener(UIObserverListener uiObserverListener) { + sortBasisUiComboBox.registerChangeListener(uiObserverListener); + sortRuleUiComboBox.registerChangeListener(uiObserverListener); + } + + + public void removeListener(UIObserverListener uiObserverListener) { + sortBasisUiComboBox.removeChangeListener(); + sortRuleUiComboBox.removeChangeListener(); + } + + protected void refresh() { + validate(); + repaint(); + revalidate(); + } +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/common/AbstractSortPane.java b/designer-realize/src/main/java/com/fr/design/sort/common/AbstractSortPane.java new file mode 100644 index 000000000..2febc4b6e --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/common/AbstractSortPane.java @@ -0,0 +1,118 @@ +package com.fr.design.sort.common; + +import com.fr.design.event.UIObserverListener; +import com.fr.design.gui.ilable.UILabel; +import com.fr.design.sort.header.SortHeaderPane; +import com.fr.report.cell.TemplateCellElement; +import com.fr.report.core.sort.common.CellSortAttr; +import com.fr.report.core.sort.sortexpression.CellSortExpression; +import com.fr.report.core.sort.sortexpression.SortExpression; +import com.fr.report.core.sort.header.SortHeader; +import com.fr.stable.ColumnRow; + +import javax.swing.*; +import java.awt.*; +import java.util.ArrayList; +import java.util.List; + + +public abstract class AbstractSortPane extends JPanel { + protected int sortPaneWidth; + protected int sortPaneRightWidth; + public static final int PANE_COMPONENT_HEIGHT = 20; + public static final int PANE_COMPONENT_V_GAP = 4; + public static final int PANE_COMPONENT_H_GAP = 14; + protected UIObserverListener uiObserverListener; + protected AbstractSortGroupPane sortGroupPane; + protected SortHeaderPane sortHeaderPane; + protected String selfSortArea; + protected String defaultHeaderArea; + + + public AbstractSortPane(int sortPaneWidth, int sortPaneRightWidth) { + this.sortPaneWidth = sortPaneWidth; + this.sortPaneRightWidth = sortPaneRightWidth; + initUIObserverListener(); + initComponents(); + } + + + private void initComponents() { + initSortGroupPane(); + sortHeaderPane = new SortHeaderPane(sortPaneWidth, sortPaneRightWidth + 5); + this.add(sortHeaderPane); + } + + protected abstract void initSortGroupPane(); + + protected void initUIObserverListener() { + + } + + protected abstract CellSortAttr getCellSortAttr(TemplateCellElement cellElement); + + public void populateBean(TemplateCellElement cellElement) { + System.out.println("sport pane populateBean"); + populateSortArea(cellElement); + CellSortAttr cellSortAttr = getCellSortAttr(cellElement); + List sortExpressions = cellSortAttr.getSortExpressions(); + if (sortExpressions == null || sortExpressions.size() == 0) { + sortExpressions = new ArrayList<>(); + sortExpressions.add(new CellSortExpression(selfSortArea)); + } + sortGroupPane.populateBean(sortExpressions, selfSortArea); + sortHeaderPane.populateBean(cellSortAttr.getSortHeader(),defaultHeaderArea); + addListener(uiObserverListener); + refresh(); + } + + + protected void populateSortArea(TemplateCellElement cellElement) { + int row = cellElement.getRow(); + int column = cellElement.getColumn(); + selfSortArea = ColumnRow.valueOf(column, row).toString(); + if (row > 1) { + defaultHeaderArea = ColumnRow.valueOf(column, row - 1).toString(); + } else { + defaultHeaderArea = null; + } + } + + public void updateBean(TemplateCellElement cellElement) { + System.out.println("sport pane updateBean"); + List sortExpressions = sortGroupPane.updateBean(); + SortHeader sortHeader = sortHeaderPane.updateBean(); + CellSortAttr cellSortAttr = getCellSortAttr(cellElement); + cellSortAttr.setSortExpressions(sortExpressions); + cellSortAttr.setSortHeader(sortHeader); + } + + + public void addListener(UIObserverListener uiObserverListener) { + sortGroupPane.addListener(uiObserverListener); + sortHeaderPane.addListener(uiObserverListener); + } + + + public void removeListener(UIObserverListener uiObserverListener) { + sortGroupPane.removeListener(uiObserverListener); + sortHeaderPane.removeListener(uiObserverListener); + } + + + protected void refresh() { + validate(); + repaint(); + revalidate(); + } + + public static UILabel createIntervalUILabel() { + return createIntervalUILabel(PANE_COMPONENT_H_GAP); + } + + public static UILabel createIntervalUILabel(int vGap) { + UILabel uiLabel = new UILabel(); + uiLabel.setPreferredSize(new Dimension(vGap, 10)); + return uiLabel; + } +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/common/SortColumnRowPane.java b/designer-realize/src/main/java/com/fr/design/sort/common/SortColumnRowPane.java new file mode 100644 index 000000000..16e0319cc --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/common/SortColumnRowPane.java @@ -0,0 +1,167 @@ +package com.fr.design.sort.common; + +import com.fr.base.BaseUtils; +import com.fr.design.designer.TargetComponent; +import com.fr.design.event.UIObserver; +import com.fr.design.event.UIObserverListener; +import com.fr.design.file.HistoryTemplateListCache; +import com.fr.design.gui.ibutton.UIButton; +import com.fr.design.gui.ilable.UILabel; +import com.fr.design.mainframe.ElementCasePane; +import com.fr.design.selection.SelectionEvent; +import com.fr.design.selection.SelectionListener; +import com.fr.grid.selection.CellSelection; +import com.fr.grid.selection.Selection; +import com.fr.log.FineLoggerFactory; +import com.fr.stable.ColumnRow; +import com.fr.stable.EssentialUtils; +import com.fr.stable.StringUtils; + +import javax.swing.*; +import javax.swing.event.ChangeEvent; +import javax.swing.event.ChangeListener; +import java.awt.*; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; + +public class SortColumnRowPane extends JPanel { + int paneWidth; + int paneHeight; + int jTextFieldWidth; + JTextField colJTextField; + JTextField rowJTextField; + UIButton selectButton; + private boolean isAlreadyAddListener = false; + private CellSelection oldSelection; + private SelectionListener gridSelectionChangeListener; + UIObserverListener uiObserverListener; + + public SortColumnRowPane(int paneWidth, int paneHeight) { + this.paneWidth = paneWidth; + this.paneHeight = paneHeight; + initComponents(); + } + + private void initComponents() { + initSize(); + this.setLayout(new FlowLayout(FlowLayout.LEFT, 0, 0)); + intUILabel(); + initTextField(); + initSelectButton(); + this.setSize(new Dimension(paneWidth, paneHeight)); + } + + void initSize() { + jTextFieldWidth = (paneWidth - 42) / 2; + } + + void intUILabel() { + UILabel uiLabel = new UILabel(BaseUtils.readIcon("com\\fr\\design\\images\\buttonicon\\propertiestab\\cellelement_normal.png")); + this.add(uiLabel); + } + + + void initTextField() { + colJTextField = new JTextField(); + colJTextField.setEditable(false); + rowJTextField = new JTextField(); + rowJTextField.setEditable(false); + colJTextField.setPreferredSize(new Dimension(jTextFieldWidth, paneHeight)); + rowJTextField.setPreferredSize(new Dimension(jTextFieldWidth, paneHeight)); + this.add(colJTextField); + this.add(rowJTextField); + } + + void initSelectButton() { + selectButton = new UIButton(BaseUtils.readIcon("com/fr/design/images/buttonicon/select.png")); + selectButton.addActionListener(new SelectActionListener(this)); + this.add(selectButton); + } + + public void populateBean(ColumnRow columnRow) { + if (columnRow != null && columnRow.getRow() != -1 && columnRow.getColumn() != -1) { + colJTextField.setText(EssentialUtils.convertIntToABC(columnRow.column + 1)); + rowJTextField.setText(String.valueOf(columnRow.row + 1)); + } + refresh(); + + } + + public ColumnRow updateBean() { + if (StringUtils.isNotBlank(colJTextField.getText()) && StringUtils.isNotBlank(rowJTextField.getText())) { + return ColumnRow.valueOf(colJTextField.getText() + rowJTextField.getText()); + } + return null; + } + + class SelectActionListener implements ActionListener { + SortColumnRowPane columnRowPane; + + SelectActionListener(SortColumnRowPane columnRowPane) { + this.columnRowPane = columnRowPane; + } + + @Override + public void actionPerformed(ActionEvent e) { + ElementCasePane elementCasePane = getCurrentElementCase(); + if (elementCasePane == null || isAlreadyAddListener) { + return; + } + oldSelection = (CellSelection) elementCasePane.getSelection(); + elementCasePane.getGrid().setNotShowingTableSelectPane(false); + elementCasePane.setEditable(false); + elementCasePane.repaint(10); + + gridSelectionChangeListener = new SelectionListener() { + @Override + public void selectionChanged(SelectionEvent e) { + Selection selection = elementCasePane.getSelection(); + if (selection instanceof CellSelection) { + CellSelection cellselection = (CellSelection) selection; + ColumnRow cr = ColumnRow.valueOf(cellselection.getColumn(), cellselection.getRow()); + elementCasePane.setOldSelecton(oldSelection); + columnRowPane.populateBean(cr); + if (columnRowPane.uiObserverListener != null) { + columnRowPane.uiObserverListener.doChange(); + } + } + elementCasePane.removeSelectionChangeListener(gridSelectionChangeListener); + isAlreadyAddListener = false; + elementCasePane.getGrid().setNotShowingTableSelectPane(true); + elementCasePane.setEditable(true); + elementCasePane.repaint(); + } + }; + elementCasePane.addSelectionChangeListener(gridSelectionChangeListener); + isAlreadyAddListener = true; + } + } + + private ElementCasePane getCurrentElementCase() { + try { + TargetComponent targetComponent + = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate().getCurrentElementCasePane(); + if (targetComponent instanceof ElementCasePane) { + return (ElementCasePane) targetComponent; + } + } catch (Exception e) { + FineLoggerFactory.getLogger().error(e, e.getMessage()); + } + return null; + } + + public void addListener(UIObserverListener uiObserverListener) { + this.uiObserverListener = uiObserverListener; + } + + + public void removeListener(UIObserverListener uiObserverListener) { + this.uiObserverListener = null; + } + + protected void refresh() { + validate(); + repaint(); + revalidate(); + } +} \ No newline at end of file diff --git a/designer-realize/src/main/java/com/fr/design/sort/common/SortUIExpandablePane.java b/designer-realize/src/main/java/com/fr/design/sort/common/SortUIExpandablePane.java new file mode 100644 index 000000000..ccee50fe7 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/common/SortUIExpandablePane.java @@ -0,0 +1,102 @@ +package com.fr.design.sort.common; + +import com.fr.base.BaseUtils; +import com.fr.base.svg.IconUtils; +import com.fr.design.gui.ibutton.UIButton; +import com.fr.design.gui.ilable.UILabel; + +import javax.swing.*; +import java.awt.*; +import java.awt.event.MouseAdapter; +import java.awt.event.MouseEvent; + + +public class SortUIExpandablePane extends JPanel { + + private static final long serialVersionUID = 1L; + private HeaderPane headerPane; + private AbstractSortItemPane contentPane; + private AbstractSortGroupPane sortGroupPane; + + private JPanel wrapPane; + + public JPanel getContentPane() { + return contentPane; + } + + public SortUIExpandablePane(AbstractSortItemPane contentPane, AbstractSortGroupPane sortGroupPane) { + super(); + this.sortGroupPane = sortGroupPane; + this.contentPane = contentPane; + initComponents(); + wrapPane.setBorder(BorderFactory.createLineBorder(Color.gray, 1)); + wrapPane.setBackground(Color.WHITE); + } + + + private void initComponents() { + wrapPane = new JPanel(); + wrapPane.setLayout(new BorderLayout()); + headerPane = new HeaderPane(sortGroupPane); + headerPane.addMouseListener(new MouseAdapter() { + @Override + public void mouseClicked(MouseEvent e) { + setContentPanelShow(!contentPane.isVisible()); + } + }); + headerPane.setBorder(BorderFactory.createMatteBorder(0, 0, 1, 0, Color.gray)); + contentPane.setBorder(BorderFactory.createEmptyBorder(0, 5, 0, 5)); + wrapPane.add(headerPane, BorderLayout.NORTH); + wrapPane.add(contentPane, BorderLayout.CENTER); + setContentPanelShow(false); + this.add(wrapPane); + } + + + private void setContentPanelShow(boolean show) { + contentPane.setVisible(show); + headerPane.setShow(show); + } + + class HeaderPane extends JPanel { + UILabel iconUiLabel; + UILabel closeButton; + AbstractSortGroupPane sortGroupPane; + + HeaderPane(AbstractSortGroupPane sortGroupPane) { + this.sortGroupPane = sortGroupPane; + this.setLayout(new FlowLayout(FlowLayout.LEFT, 3, 3)); + initComponents(); + + } + + private void initComponents() { + iconUiLabel = new UILabel(); + this.add(iconUiLabel); + UILabel uiLabel = new UILabel("次要排序列"); + this.add(uiLabel); + this.add(AbstractSortPane.createIntervalUILabel(114)); + + closeButton = new UILabel(IconUtils.readIcon("/com/fr/design/images/control/close.png")); + this.add(closeButton); + closeButton.addMouseListener(new MouseAdapter() { + @Override + public void mouseClicked(MouseEvent e) { + sortGroupPane.removeSortItem(1); + } + }); + System.out.println(contentPane.sortItemPaneWidth); + this.setPreferredSize(new Dimension(contentPane.sortItemPaneWidth+7, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + } + + public void setShow(boolean show) { + if (show) { + iconUiLabel.setIcon(IconUtils.readIcon("/com/fr/design/images/sort/down_arrow.png")); + } else { + iconUiLabel.setIcon(IconUtils.readIcon("/com/fr/design/images/sort/left_arrow.png")); + } + } + + } + +} \ No newline at end of file diff --git a/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CellSortExpressionPane.java b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CellSortExpressionPane.java new file mode 100644 index 000000000..863ca6d22 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CellSortExpressionPane.java @@ -0,0 +1,31 @@ +package com.fr.design.sort.expressionpane; + +import com.fr.report.core.sort.sortexpression.CellSortExpression; + + +import java.awt.*; + + +public class CellSortExpressionPane extends SortExpressionPane { + public CellSortExpressionPane(int with) { + this.setLayout(new FlowLayout(FlowLayout.LEFT, 0, 0)); + } + + + @Override + public String getSortName() { + return "单元格"; + } + + @Override + public void populateBean(CellSortExpression cellSortExpression) { + + } + + @Override + public CellSortExpression updateBean() { + return new CellSortExpression(); + } + + +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CustomSequenceEditPane.java b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CustomSequenceEditPane.java new file mode 100644 index 000000000..db3d3b920 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CustomSequenceEditPane.java @@ -0,0 +1,160 @@ +package com.fr.design.sort.expressionpane; + +import com.fr.design.dialog.BasicPane; +import com.fr.design.gui.icontainer.UIScrollPane; +import com.fr.design.gui.ilable.UILabel; +import com.fr.design.gui.ilist.UIList; +import com.fr.design.mainframe.dnd.SerializableTransferable; +import com.fr.design.mainframe.share.ui.base.PlaceholderTextArea; +import com.fr.report.core.sort.sortexpression.CustomSequenceSortExpression; + +import javax.swing.*; +import java.awt.*; +import java.awt.datatransfer.DataFlavor; +import java.awt.datatransfer.Transferable; +import java.awt.dnd.DnDConstants; +import java.awt.dnd.DragGestureEvent; +import java.awt.dnd.DragGestureListener; +import java.awt.dnd.DragSource; +import java.awt.dnd.DragSourceAdapter; +import java.awt.dnd.DropTarget; +import java.awt.dnd.DropTargetAdapter; +import java.awt.dnd.DropTargetDropEvent; +import java.util.ArrayList; +import java.util.List; + +public class CustomSequenceEditPane extends BasicPane { + java.util.List customSequence; + JPanel referenceSequencePanel; + JPanel editSequencePanel; + JTextArea jTextArea; + + CustomSequenceEditPane(java.util.List customSequence) { + this.customSequence = customSequence; + initComponents(); + } + + + void initComponents() { + this.setLayout(new BorderLayout()); + initReferenceSequencePanel(); + initEditSequencePanel(); + } + + void initReferenceSequencePanel() { + referenceSequencePanel = new JPanel(new FlowLayout(FlowLayout.LEFT)); + UILabel uiLabel = new UILabel("参考序列:"); + referenceSequencePanel.add(uiLabel); + UIScrollPane uiScrollPane = new UIScrollPane(getReferenceSequenceList()); + uiScrollPane.setPreferredSize(new Dimension(200, 300)); + referenceSequencePanel.add(uiScrollPane); + referenceSequencePanel.setPreferredSize(new Dimension(200, 400)); + this.add(referenceSequencePanel, BorderLayout.WEST); + } + + private UIList getReferenceSequenceList() { + UIList uiList = new UIList(getReferenceSequenceModel()); + new CustomSequenceEditDragSource(uiList, DnDConstants.ACTION_MOVE); + return uiList; + } + + private String[] getReferenceSequenceModel() { + List> customSequences = CustomSequenceSortExpression.getReferenceCustomSequences(); + String[] listModel = new String[customSequences.size()]; + for (int i = 0; i < customSequences.size(); i++) { + listModel[i] = CustomSequenceSortExpression.customSequenceToString(customSequences.get(i), ","); + } + return listModel; + } + + void initEditSequencePanel() { + editSequencePanel = new JPanel(new FlowLayout(FlowLayout.LEFT)); + UILabel uiLabel = new UILabel("输入序列(E):"); + editSequencePanel.add(uiLabel); + UILabel uiLabel2 = new UILabel("请将序列元素隔行输入"); + uiLabel2.setForeground(Color.lightGray); + editSequencePanel.add(uiLabel2); + jTextArea = getTextArea(); + UIScrollPane uiScrollPane = new UIScrollPane(jTextArea); + uiScrollPane.setPreferredSize(new Dimension(475, 300)); + editSequencePanel.add(uiScrollPane); + this.add(editSequencePanel, BorderLayout.CENTER); + + } + + + JTextArea getTextArea() { + PlaceholderTextArea placeholderTextArea = new PlaceholderTextArea(10, 10, getPlaceholderText()); + new CustomSequenceEditDropTarget(placeholderTextArea, CustomSequenceSortExpression.getReferenceCustomSequences()); + placeholderTextArea.setText(CustomSequenceSortExpression.customSequenceToString(customSequence, "\n")); + return placeholderTextArea; + } + + String getPlaceholderText() { + StringBuilder stringBuilder = new StringBuilder(); + stringBuilder.append("请将序列元素隔行输入,如:\n"); + stringBuilder.append("部门一\n"); + stringBuilder.append("部门二\n"); + stringBuilder.append("部门三\n"); + System.out.println(stringBuilder); + return stringBuilder.toString(); + } + + @Override + protected String title4PopupWindow() { + return "自定义序列"; + } + + + class CustomSequenceEditDragSource extends DragSourceAdapter implements DragGestureListener { + private DragSource source; + + public CustomSequenceEditDragSource(UIList uiList, int actions) { + source = new DragSource(); + source.createDefaultDragGestureRecognizer(uiList, actions, this); + } + + public void dragGestureRecognized(DragGestureEvent dge) { + Component comp = dge.getComponent(); + if (comp instanceof UIList) { + UIList uiList = (UIList) comp; + source.startDrag(dge, DragSource.DefaultLinkDrop, new SerializableTransferable(uiList.getSelectedIndex()), this); + } + } + } + + + class CustomSequenceEditDropTarget extends DropTargetAdapter { + java.util.List> customSequences = new ArrayList<>(); + + public CustomSequenceEditDropTarget(PlaceholderTextArea jPanel, java.util.List> customSequences) { + new DropTarget(jPanel, this); + this.customSequences = customSequences; + } + + @Override + public void drop(DropTargetDropEvent dtde) { + try { + Transferable transferable = dtde.getTransferable(); + DataFlavor[] dataFlavors = transferable.getTransferDataFlavors(); + if (dataFlavors.length == 1) { + Integer index = (Integer) transferable.getTransferData(dataFlavors[0]); + String text = ""; + java.util.List customSequence = customSequences.get(index); + for (int i = 0; i < customSequence.size(); i++) { + text += customSequence.get(i) + "\n"; + } + JTextArea jTextArea = (JTextArea) dtde.getDropTargetContext().getComponent(); + jTextArea.setText(text); + } + } catch (Exception e) { + + } + } + } + + public List updateBean() { + return CustomSequenceSortExpression.stringToCustomSequence(jTextArea.getText(), "\n"); + } + +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CustomSequencePane.java b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CustomSequencePane.java new file mode 100644 index 000000000..507ac204c --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CustomSequencePane.java @@ -0,0 +1,70 @@ +package com.fr.design.sort.expressionpane; + +import com.fr.base.BaseUtils; +import com.fr.design.dialog.DialogActionAdapter; +import com.fr.design.gui.ibutton.UIButton; +import com.fr.design.gui.itextfield.UITextField; +import com.fr.design.mainframe.DesignerContext; +import com.fr.design.sort.common.AbstractSortPane; +import com.fr.report.core.sort.sortexpression.CustomSequenceSortExpression; + +import javax.swing.*; +import java.awt.*; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.util.List; + + +public class CustomSequencePane extends JPanel { + + + protected UITextField textField; + protected UIButton button; + List customSequence; + + public CustomSequencePane(int width) { + this.setLayout(new FlowLayout(FlowLayout.RIGHT, 0, 0)); + this.initComponents(width); + } + + protected void initComponents(int width) { + + textField = new UITextField(); + textField.setEditable(false); + textField.setPreferredSize(new Dimension(width - 20, 20)); + + // 添加一公式编辑器按钮 + Icon icon = BaseUtils.readIcon("/com/fr/design/images/control/refresh.png"); + button = new UIButton(icon); + button.setBackground(Color.RED); + button.setPreferredSize(new Dimension(24, 20)); + button.setOpaque(false); + button.setCursor(new Cursor(Cursor.HAND_CURSOR)); + button.addActionListener(new ActionListener() { + public void actionPerformed(ActionEvent evt) { + CustomSequenceEditPane customSequenceEditPane = new CustomSequenceEditPane(customSequence); + customSequenceEditPane.showWindowWithCustomSize(DesignerContext.getDesignerFrame(), new DialogActionAdapter() { + @Override + public void doOk() { + customSequence = customSequenceEditPane.updateBean(); + textField.setText(CustomSequenceSortExpression.customSequenceToString(customSequence, ",")); + } + }, new Dimension(700, 400)).setVisible(true); + } + }); + button.setPreferredSize(new Dimension(24, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + + this.add(textField); + this.add(button); + } + + + public List updateBean() { + return customSequence; + } + + public void populateBean(List customSequence) { + this.customSequence = customSequence; + textField.setText(CustomSequenceSortExpression.customSequenceToString(customSequence, ",")); + } +} \ No newline at end of file diff --git a/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CustomSequenceSortExpressionPane.java b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CustomSequenceSortExpressionPane.java new file mode 100644 index 000000000..c9589f92e --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/CustomSequenceSortExpressionPane.java @@ -0,0 +1,37 @@ +package com.fr.design.sort.expressionpane; + + +import com.fr.design.sort.common.AbstractSortPane; +import com.fr.report.core.sort.sortexpression.CustomSequenceSortExpression; + +import java.awt.*; +import java.util.List; + + +public class CustomSequenceSortExpressionPane extends SortExpressionPane { + CustomSequencePane customSequencePane; + + public CustomSequenceSortExpressionPane(int width, int rightWidth) { + this.setLayout(new FlowLayout(FlowLayout.RIGHT, 0, 0)); + customSequencePane = new CustomSequencePane(rightWidth); + customSequencePane.setPreferredSize(new Dimension(width, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + this.add(customSequencePane); + } + + @Override + public String getSortName() { + return "自定义序列"; + } + + @Override + public void populateBean(CustomSequenceSortExpression customSequenceSortExpression) { + List customSequence = customSequenceSortExpression.getCustomSequence(); + customSequencePane.populateBean(customSequence); + } + + @Override + public CustomSequenceSortExpression updateBean() { + List customSequence = customSequencePane.updateBean(); + return new CustomSequenceSortExpression(customSequence); + } +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/expressionpane/EmptyExpressionPane.java b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/EmptyExpressionPane.java new file mode 100644 index 000000000..042be1b97 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/EmptyExpressionPane.java @@ -0,0 +1,37 @@ +package com.fr.design.sort.expressionpane; + + +import com.fr.report.core.sort.sortexpression.SortExpression; + +import java.awt.*; + + +public class EmptyExpressionPane extends SortExpressionPane { + + public EmptyExpressionPane() { + this.setLayout(new FlowLayout(FlowLayout.LEFT, 0, 0)); + } + + @Override + public String getSortName() { + return "无"; + } + + @Override + public void populateBean(SortExpression sortExpression) { + + } + + @Override + public SortExpression updateBean() { + return null; + } + + public boolean needSortArea() { + return false; + } + + public boolean needSortRule() { + return false; + } +} \ No newline at end of file diff --git a/designer-realize/src/main/java/com/fr/design/sort/expressionpane/FormulaSortExpressionPane.java b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/FormulaSortExpressionPane.java new file mode 100644 index 000000000..2dd098ab6 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/FormulaSortExpressionPane.java @@ -0,0 +1,41 @@ +package com.fr.design.sort.expressionpane; + +import com.fr.design.formula.TinyFormulaPane; +import com.fr.design.sort.common.AbstractSortPane; +import com.fr.report.core.sort.sortexpression.FormulaSortExpression; + +import java.awt.*; + +public class FormulaSortExpressionPane extends SortExpressionPane { + + TinyFormulaPane tinyFormulaPane; + + public FormulaSortExpressionPane(int width) { + this.setLayout(new FlowLayout(FlowLayout.RIGHT, 0, 1)); + tinyFormulaPane = new TinyFormulaPane(); + tinyFormulaPane.setPreferredSize(new Dimension(width, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + this.add(tinyFormulaPane); + } + + @Override + public String getSortName() { + return "公式"; + } + + @Override + public void populateBean(FormulaSortExpression formulaSortExpression) { + String formula = formulaSortExpression.getFormula(); + tinyFormulaPane.getUITextField().setText(formula); + } + + @Override + public FormulaSortExpression updateBean() { + String formula = tinyFormulaPane.getUITextField().getText(); + return new FormulaSortExpression(formula); + } + + public boolean needSortArea() { + return false; + } + +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/expressionpane/SortExpressionPane.java b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/SortExpressionPane.java new file mode 100644 index 000000000..69af8464c --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/expressionpane/SortExpressionPane.java @@ -0,0 +1,23 @@ +package com.fr.design.sort.expressionpane; + +import com.fr.report.core.sort.sortexpression.SortExpression; + +import javax.swing.*; + + +public abstract class SortExpressionPane extends JPanel { + + public abstract String getSortName(); + + public abstract void populateBean(T sortExpression); + + public abstract T updateBean(); + + public boolean needSortArea() { + return true; + } + + public boolean needSortRule() { + return true; + } +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/header/HeaderAreaPane.java b/designer-realize/src/main/java/com/fr/design/sort/header/HeaderAreaPane.java new file mode 100644 index 000000000..92f7aaf2e --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/header/HeaderAreaPane.java @@ -0,0 +1,149 @@ +package com.fr.design.sort.header; + +import com.fr.design.event.UIObserverListener; +import com.fr.design.gui.icombobox.UIComboBox; +import com.fr.design.gui.ilable.UILabel; +import com.fr.design.mainframe.ElementCasePane; +import com.fr.design.sort.common.AbstractSortPane; +import com.fr.design.sort.common.SortColumnRowPane; +import com.fr.stable.ColumnRow; + +import javax.swing.*; +import java.awt.*; +import java.awt.event.ItemEvent; +import java.awt.event.ItemListener; + + +public class HeaderAreaPane extends JPanel { + protected int headerAreaPaneWidth; + protected int headerAreaPaneRightWidth; + + AreaJLayeredPane areaJLayeredPane; + + HeaderAreaPane(int headerAreaPaneWidth, int headerAreaPaneRightWidth) { + this.headerAreaPaneWidth = headerAreaPaneWidth; + this.headerAreaPaneRightWidth = headerAreaPaneRightWidth; + this.setLayout(new FlowLayout(FlowLayout.LEFT, 0, 0)); + initComponents(); + } + + void initComponents() { + initUILabel(); + initLayeredPane(); + } + + + void initUILabel() { + UILabel uiLabel = new UILabel("表头区域", SwingConstants.LEFT); + this.add(uiLabel); + this.add(AbstractSortPane.createIntervalUILabel()); + } + + void initLayeredPane() { + areaJLayeredPane = new AreaJLayeredPane(); + this.add(areaJLayeredPane); + } + + + public void populateBean(ColumnRow columnRow) { + areaJLayeredPane.populateBean(columnRow); + } + + public ColumnRow updateBean() { + return areaJLayeredPane.updateBean(); + } + + class AreaJLayeredPane extends JPanel { + SortColumnRowPane columnRowPane; + JLayeredPane jLayeredPane; + UIComboBox uiComboBox; + + AreaJLayeredPane() { + this.setLayout(new FlowLayout(FlowLayout.LEFT, 0, 0)); + initComponents(); + } + + private void initComponents() { + initUIComboBox(); + initJLayeredPane(); + } + + + void initUIComboBox() { + uiComboBox = new UIComboBox(new String[]{"无", "自定义"}); + uiComboBox.setSize(new Dimension(headerAreaPaneRightWidth, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + uiComboBox.addItemListener(new ItemListener() { + @Override + public void itemStateChanged(ItemEvent e) { + setSortColumnRowPaneShow(uiComboBox.getSelectedIndex() == 1); + } + }); + } + + void setSortColumnRowPaneShow(boolean show) { + if (show) { + jLayeredPane.setLayer(columnRowPane, JLayeredPane.POPUP_LAYER); + jLayeredPane.setLayer(uiComboBox, JLayeredPane.MODAL_LAYER); + } else { + jLayeredPane.setLayer(uiComboBox, JLayeredPane.POPUP_LAYER); + jLayeredPane.setLayer(columnRowPane, JLayeredPane.MODAL_LAYER); + } + refresh(); + } + + void initJLayeredPane() { + jLayeredPane = new JLayeredPane(); + columnRowPane = new SortColumnRowPane(headerAreaPaneRightWidth - 18, AbstractSortPane.PANE_COMPONENT_HEIGHT); + jLayeredPane.setPreferredSize(new Dimension(headerAreaPaneRightWidth, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + jLayeredPane.add(columnRowPane, JLayeredPane.MODAL_LAYER); + jLayeredPane.add(uiComboBox, JLayeredPane.POPUP_LAYER); + this.add(jLayeredPane); + } + + public void populateBean(ColumnRow columnRow) { + if (columnRow != null && columnRow.getRow() != -1 && columnRow.getColumn() != -1) { + columnRowPane.populateBean(columnRow); + uiComboBox.setSelectedIndex(1); + } else { + uiComboBox.setSelectedIndex(0); + } + setSortColumnRowPaneShow(uiComboBox.getSelectedIndex() == 1); + } + + public ColumnRow updateBean() { + if (uiComboBox.getSelectedIndex() == 0) { + return null; + } else { + return columnRowPane.updateBean(); + } + } + + public void addListener(UIObserverListener uiObserverListener) { + columnRowPane.addListener(uiObserverListener); + uiComboBox.registerChangeListener(uiObserverListener); + } + + + public void removeListener(UIObserverListener uiObserverListener) { + columnRowPane.removeListener(uiObserverListener); + uiComboBox.removeChangeListener(); + } + + public void refresh() { + validate(); + repaint(); + revalidate(); + } + + } + + public void addListener(UIObserverListener uiObserverListener) { + areaJLayeredPane.addListener(uiObserverListener); + } + + + public void removeListener(UIObserverListener uiObserverListener) { + areaJLayeredPane.removeListener(uiObserverListener); + } + +} \ No newline at end of file diff --git a/designer-realize/src/main/java/com/fr/design/sort/header/HeaderSettingPane.java b/designer-realize/src/main/java/com/fr/design/sort/header/HeaderSettingPane.java new file mode 100644 index 000000000..4cf2229c8 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/header/HeaderSettingPane.java @@ -0,0 +1,91 @@ +package com.fr.design.sort.header; + +import com.fr.design.event.UIObserverListener; +import com.fr.design.gui.icheckbox.UICheckBox; +import com.fr.design.gui.ilable.UILabel; +import com.fr.design.sort.common.AbstractSortPane; +import com.fr.report.core.sort.header.SortHeader; + +import javax.swing.*; +import javax.swing.event.ChangeEvent; +import javax.swing.event.ChangeListener; +import java.awt.*; + +public class HeaderSettingPane extends JPanel { + protected int headerSettingPaneWidth; + protected int headerSettingPaneRightWidth; + HeaderSortRulePane headerSortRulePane; + UICheckBox uiCheckBox; + + HeaderSettingPane(int headerSettingPaneWidth, int headerSettingPaneRightWidth) { + this.headerSettingPaneWidth = headerSettingPaneWidth; + this.headerSettingPaneRightWidth = headerSettingPaneRightWidth; + this.setLayout(new BoxLayout(this, BoxLayout.Y_AXIS)); + initComponents(); + } + + void initComponents() { + initUILabel(); + initHeaderSortRulePane(); + } + + void initUILabel() { + JPanel jPanel = new JPanel(new FlowLayout(FlowLayout.LEFT, 0, 2)); + UILabel uiLabel = new UILabel("表头设置"); + UILabel emptyUILabel = new UILabel(); + emptyUILabel.setPreferredSize(new Dimension(10, 10)); + + uiCheckBox = new UICheckBox("用户点击排列顺序"); + uiCheckBox.setPreferredSize(new Dimension(headerSettingPaneRightWidth - 10, AbstractSortPane.PANE_COMPONENT_HEIGHT)); + uiCheckBox.addChangeListener(new ChangeListener() { + @Override + public void stateChanged(ChangeEvent e) { + headerSortRulePane.setVisible(uiCheckBox.isSelected()); + } + }); + jPanel.add(uiLabel); + jPanel.add(emptyUILabel); + jPanel.add(uiCheckBox); + this.add(jPanel); + } + + void initHeaderSortRulePane() { + headerSortRulePane = new HeaderSortRulePane(); + this.add(headerSortRulePane); + headerSortRulePane.setVisible(false); + } + + protected void refresh() { + validate(); + repaint(); + revalidate(); + } + + public void populateBean(SortHeader.SortItem[] sortItems) { + if (sortItems == null) { + uiCheckBox.setSelected(false); + } else { + uiCheckBox.setSelected(true); + } + headerSortRulePane.populateBean(sortItems); + } + + public SortHeader.SortItem[] updateBean() { + if (uiCheckBox.isSelected()) { + return headerSortRulePane.updateBean(); + } else { + return null; + } + } + + public void addListener(UIObserverListener uiObserverListener) { + uiCheckBox.registerChangeListener(uiObserverListener); + headerSortRulePane.addListener(uiObserverListener); + } + + + public void removeListener(UIObserverListener uiObserverListener) { + uiCheckBox.removeChangeListener(); + headerSortRulePane.removeListener(uiObserverListener); + } +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/header/HeaderSortRulePane.java b/designer-realize/src/main/java/com/fr/design/sort/header/HeaderSortRulePane.java new file mode 100644 index 000000000..55db383b2 --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/header/HeaderSortRulePane.java @@ -0,0 +1,256 @@ +package com.fr.design.sort.header; + +import com.fr.base.svg.SVGIcon; +import com.fr.base.svg.SVGTranscoder; +import com.fr.design.event.UIObserverListener; +import com.fr.design.gui.icheckbox.UICheckBox; +import com.fr.design.gui.ilable.UILabel; +import com.fr.design.layout.TableLayoutHelper; +import com.fr.design.mainframe.theme.edit.ui.ColorListPane; +import com.fr.general.IOUtils; +import com.fr.report.core.sort.header.SortHeader; +import com.fr.report.core.sort.common.SortRule; +import org.apache.batik.transcoder.TranscoderInput; + +import javax.swing.*; +import javax.swing.event.ChangeEvent; +import javax.swing.event.ChangeListener; +import java.awt.*; +import java.awt.image.BufferedImage; +import java.io.ByteArrayInputStream; +import java.io.InputStream; +import java.util.ArrayList; + +public class HeaderSortRulePane extends JPanel { + + + private static final String ASC_ICON_TEMPLATE_PATH = "/com/fr/design/images/sort/asc.svg"; + private static final String DES_ICON_TEMPLATE_PATH = "/com/fr/design/images/sort/des.svg"; + private static final String NOSORT_ICON_TEMPLATE_PATH = "/com/fr/design/images/sort/nosort.svg"; + IconButton ascIconButton; + IconButton desIconButton; + IconButton nosortIconButton; + UICheckBox ascUICheckBox; + UICheckBox desUICheckBox; + UICheckBox nosortUICheckBox; + + + HeaderSortRulePane() { + initComponents(); + initState(); + this.setBorder(BorderFactory.createEmptyBorder(0, 15, 0, 15)); + } + + void initComponents() { + this.setLayout(new BorderLayout()); + initUILabel(); + initSortRuleItem(); + this.setPreferredSize(new Dimension(160, 160)); + } + + void initUILabel() { + UILabel uiLabel = new UILabel("排序依据:", SwingConstants.LEFT); + this.add(uiLabel, BorderLayout.NORTH); + } + + void initSortRuleItem() { + Component[][] components = new Component[][]{ + new Component[]{ascUICheckBox = new UICheckBox("升序"), ascIconButton = new IconButton(ASC_ICON_TEMPLATE_PATH)}, + new Component[]{desUICheckBox = new UICheckBox("降序"), desIconButton = new IconButton(DES_ICON_TEMPLATE_PATH)}, + new Component[]{nosortUICheckBox = new UICheckBox("不排序"), nosortIconButton = new IconButton(NOSORT_ICON_TEMPLATE_PATH)}, + }; + double[] rowSize = {24, 24, 24}; + double[] columnSize = {80, 30}; + JPanel sortRuleItem = TableLayoutHelper.createCommonTableLayoutPane(components, rowSize, columnSize, 0); + this.add(sortRuleItem, BorderLayout.CENTER); + } + + void initState() { + ascUICheckBox.setSelected(false); + desUICheckBox.setSelected(false); + nosortUICheckBox.setSelected(false); + ascIconButton.refreshIconLabelColor(new Color(33, 33, 34)); + desIconButton.refreshIconLabelColor(new Color(33, 33, 34)); + nosortIconButton.refreshIconLabelColor(new Color(33, 33, 34)); + } + + + class IconButton extends JPanel { + JLayeredPane jLayeredPane; + String iconTemplatePath; + UILabel iconLabel; + ColorListPane.ColorButton colorButton; + Color color; + BufferedImage bufferedImage; + UIObserverListener uiObserverListener; + + IconButton(String iconTemplatePath) { + this.iconTemplatePath = iconTemplatePath; + initComponents(); + } + + void initComponents() { + jLayeredPane = new JLayeredPane(); + iconLabel = getIconLabel(iconTemplatePath); + + + UILabel emptyUiLabel = new UILabel(); + emptyUiLabel.setSize(16, 16); + emptyUiLabel.setOpaque(true); + emptyUiLabel.setBackground(Color.WHITE); + iconLabel.setSize(16, 16); + colorButton = new ColorListPane.ColorButton(Color.CYAN); + colorButton.setSize(16, 16); + colorButton.addChangeListener(new ChangeListener() { + @Override + public void stateChanged(ChangeEvent e) { + color = colorButton.getSelectObject(); + refreshIconLabelColor(color); + if (uiObserverListener != null) { + uiObserverListener.doChange(); + } + } + }); + jLayeredPane.setPreferredSize(new Dimension(16, 16)); + + jLayeredPane.add(iconLabel, JLayeredPane.POPUP_LAYER); + jLayeredPane.add(emptyUiLabel, JLayeredPane.MODAL_LAYER); + jLayeredPane.add(colorButton, JLayeredPane.PALETTE_LAYER); + this.add(jLayeredPane); + } + + void refreshIconLabelColor(Color color) { + Icon icon = getIcon(iconTemplatePath, color); + refreshIconLabel(icon); + } + + void refreshIconLabel(Icon icon) { + if (icon != null) { + iconLabel.removeAll(); + iconLabel.setIcon(icon); + iconLabel.repaint(); + } + } + + UILabel getIconLabel(String iconPath) { + return getIconLabel(iconPath, new Color(33, 33, 34)); + } + + UILabel getIconLabel(String iconPath, Color color) { + Icon svgIcon = getIcon(iconPath, color); + return new UILabel(svgIcon); + } + + Icon getIcon(String iconPath, Color color) { + try { + InputStream inputStream = IOUtils.getResourceAsStream(iconPath, HeaderSortRulePane.class); + String svgText = getSvgText(inputStream); + svgText = svgText.replaceAll("\\{fillColor\\}", shiftColor(color)); + InputStream svgInputStream = new ByteArrayInputStream(svgText.getBytes()); + TranscoderInput input = new TranscoderInput(svgInputStream); + bufferedImage = SVGTranscoder.createImage(1.0, input).getImage(); + SVGIcon svgIcon = new SVGIcon(bufferedImage); + return svgIcon; + } catch (Exception e) { + + } + return null; + + } + + String shiftColor(Color color) { + StringBuilder stringBuilder = new StringBuilder(); + stringBuilder.append(shiftValue(color.getRed())); + stringBuilder.append(shiftValue(color.getGreen())); + stringBuilder.append(shiftValue(color.getBlue())); + return stringBuilder.toString(); + } + + String shiftValue(int value) { + int resultValue = (int) ((((float) value) / 255) * 99); + if (resultValue < 10) { + return "0" + resultValue; + } else { + return "" + resultValue; + } + } + + private String getSvgText(InputStream inputStream) throws Exception { + StringBuffer stringBuffer = new StringBuffer(); + byte[] b = new byte[1024]; + for (int n; (n = inputStream.read(b)) != -1; ) { + stringBuffer.append(new String(b, 0, n)); + } + return stringBuffer.toString(); + } + + public void addListener(UIObserverListener uiObserverListener) { + this.uiObserverListener = uiObserverListener; + } + + + public void removeListener(UIObserverListener uiObserverListener) { + this.uiObserverListener = null; + } + } + + + public void populateBean(SortHeader.SortItem[] sortItems) { + initState(); + if (sortItems != null) { + for (SortHeader.SortItem sortItem : sortItems) { + SortRule sortRule = sortItem.getSortRule(); + BufferedImage bufferedImage = sortItem.getBufferedImage(); + Icon icon = null; + if (bufferedImage != null) { + icon = new SVGIcon(bufferedImage); + } + if (sortRule == SortRule.ASC) { + ascIconButton.refreshIconLabel(icon); + ascUICheckBox.setSelected(true); + } else if (sortRule == SortRule.DES) { + desIconButton.refreshIconLabel(icon); + desUICheckBox.setSelected(true); + } else if (sortRule == SortRule.NO_SORT) { + nosortIconButton.refreshIconLabel(icon); + nosortUICheckBox.setSelected(true); + } + + } + } + } + + public SortHeader.SortItem[] updateBean() { + java.util.List items = new ArrayList<>(); + if (ascUICheckBox.isSelected()) { + items.add(new SortHeader.SortItem(SortRule.ASC, ascIconButton.bufferedImage)); + } + if (desUICheckBox.isSelected()) { + items.add(new SortHeader.SortItem(SortRule.DES, desIconButton.bufferedImage)); + } + if (nosortUICheckBox.isSelected()) { + items.add(new SortHeader.SortItem(SortRule.NO_SORT, nosortIconButton.bufferedImage)); + } + SortHeader.SortItem[] resultItems = new SortHeader.SortItem[items.size()]; + return items.toArray(resultItems); + } + + public void addListener(UIObserverListener uiObserverListener) { + ascIconButton.addListener(uiObserverListener); + desIconButton.addListener(uiObserverListener); + nosortIconButton.addListener(uiObserverListener); + ascUICheckBox.registerChangeListener(uiObserverListener); + desUICheckBox.registerChangeListener(uiObserverListener); + nosortUICheckBox.registerChangeListener(uiObserverListener); + } + + + public void removeListener(UIObserverListener uiObserverListener) { + ascIconButton.removeListener(uiObserverListener); + desIconButton.removeListener(uiObserverListener); + nosortIconButton.removeListener(uiObserverListener); + ascUICheckBox.removeChangeListener(); + desUICheckBox.removeChangeListener(); + nosortUICheckBox.removeChangeListener(); + } +} diff --git a/designer-realize/src/main/java/com/fr/design/sort/header/SortHeaderPane.java b/designer-realize/src/main/java/com/fr/design/sort/header/SortHeaderPane.java new file mode 100644 index 000000000..d82c2483c --- /dev/null +++ b/designer-realize/src/main/java/com/fr/design/sort/header/SortHeaderPane.java @@ -0,0 +1,74 @@ +package com.fr.design.sort.header; + +import com.fr.design.event.UIObserverListener; +import com.fr.report.core.sort.header.SortHeader; +import com.fr.stable.ColumnRow; + +import javax.swing.*; + +public class SortHeaderPane extends JPanel { + int sortHeaderPaneWidth; + int sortHeaderPaneRightWidth; + SortHeader sortHeader; + HeaderAreaPane headerAreaPane; + HeaderSettingPane headerSettingPane; + + public SortHeaderPane(int sortHeaderPaneWidth, int sortHeaderPaneRightWidth) { + this.sortHeaderPaneWidth = sortHeaderPaneWidth; + this.sortHeaderPaneRightWidth = sortHeaderPaneRightWidth; + this.setLayout(new BoxLayout(this, BoxLayout.Y_AXIS)); + initHeaderArea(); + initHeaderSetting(); + this.setBorder(BorderFactory.createEmptyBorder(10, 0, 0, 0)); + } + + + void initHeaderArea() { + this.headerAreaPane = new HeaderAreaPane(sortHeaderPaneWidth, sortHeaderPaneRightWidth); + this.add(headerAreaPane); + } + + void initHeaderSetting() { + this.headerSettingPane = new HeaderSettingPane(sortHeaderPaneWidth, sortHeaderPaneRightWidth); + this.add(headerSettingPane); + } + + + public void populateBean(SortHeader sortHeader, String defaultHeaderArea) { + this.sortHeader = sortHeader; + ColumnRow columnRow = null; + SortHeader.SortItem[] sortItems = null; + String sortArea = defaultHeaderArea; + if (sortHeader != null) { + sortArea = sortHeader.getSortArea(); + sortItems = sortHeader.getSortItems(); + } + columnRow = ColumnRow.valueOf(sortArea); + + headerAreaPane.populateBean(columnRow); + headerSettingPane.populateBean(sortItems); + } + + public SortHeader updateBean() { + ColumnRow columnRow = headerAreaPane.updateBean(); + SortHeader.SortItem[] items = headerSettingPane.updateBean(); + String sortArea = null; + if (columnRow != null) { + sortArea = columnRow.toString(); + } + SortHeader sortHeader = new SortHeader(sortArea, items); + return sortHeader; + } + + public void addListener(UIObserverListener uiObserverListener) { + headerAreaPane.addListener(uiObserverListener); + headerSettingPane.addListener(uiObserverListener); + } + + + public void removeListener(UIObserverListener uiObserverListener) { + headerAreaPane.removeListener(uiObserverListener); + headerSettingPane.removeListener(uiObserverListener); + } +} + diff --git a/designer-realize/src/main/java/com/fr/quickeditor/cellquick/CellDSColumnEditor.java b/designer-realize/src/main/java/com/fr/quickeditor/cellquick/CellDSColumnEditor.java index 0ede5114f..3d82ebb31 100644 --- a/designer-realize/src/main/java/com/fr/quickeditor/cellquick/CellDSColumnEditor.java +++ b/designer-realize/src/main/java/com/fr/quickeditor/cellquick/CellDSColumnEditor.java @@ -11,6 +11,7 @@ import com.fr.design.dscolumn.DSColumnAdvancedPane; import com.fr.design.dscolumn.ResultSetGroupDockingPane; import com.fr.design.dscolumn.SelectedDataColumnPane; import com.fr.design.event.UIObserverListener; +import com.fr.design.foldablepane.UIExpandablePane; import com.fr.design.formula.CustomVariableResolver; import com.fr.design.formula.FormulaFactory; import com.fr.design.formula.UIFormula; @@ -31,6 +32,7 @@ import com.fr.design.layout.FRGUIPaneFactory; import com.fr.design.layout.TableLayout; import com.fr.design.layout.TableLayoutHelper; import com.fr.design.mainframe.cell.AbstractDSCellEditorPane; +import com.fr.design.sort.celldscolumn.CellDSColumnSortPane; import com.fr.design.utils.gui.UIComponentUtils; import com.fr.design.widget.FRWidgetFactory; import com.fr.general.IOUtils; @@ -221,6 +223,7 @@ public class CellDSColumnEditor extends CellQuickEditor { */ private UIButton conditionUIButton; + /** * 分组设置监听器 */ @@ -373,6 +376,8 @@ public class CellDSColumnEditor extends CellQuickEditor { * 补充空白数据数目面板 可隐藏 */ private JPanel multiPane; + + private CellDSColumnSortPane cellDSColumnSortPane; /*pane end*/ @@ -449,6 +454,14 @@ public class CellDSColumnEditor extends CellQuickEditor { fireTargetModified(); } }; + + private UIObserverListener cellDSColumnSortPaneChangeListener = new UIObserverListener() { + @Override + public void doChange() { + cellDSColumnSortPane.updateBean(cellElement); + fireTargetModified(); + } + }; /*listeners end*/ @@ -480,6 +493,7 @@ public class CellDSColumnEditor extends CellQuickEditor { updateExtendConfig(); //更新补充空白设置 updateMultipleConfig(); + cellDSColumnSortPane.updateBean(cellElement); } } @@ -524,6 +538,9 @@ public class CellDSColumnEditor extends CellQuickEditor { useMultiNumCheckBox.setSelected(true); multiNumSpinner.setValue(cellExpandAttr.getMultipleNumber()); } + if (cellDSColumnSortPane != null) { + cellDSColumnSortPane.populateBean(cellElement); + } this.checkButtonEnabled(); enableListener(); } @@ -578,6 +595,7 @@ public class CellDSColumnEditor extends CellQuickEditor { */ @Override protected JPanel createContentPane() { + JPanel contentPane = new JPanel(new BorderLayout()); this.setLayout(FRGUIPaneFactory.createBorderLayout()); //结果集排序 @@ -630,8 +648,13 @@ public class CellDSColumnEditor extends CellQuickEditor { double[] rowSize = new double[components.length]; Arrays.fill(rowSize, P); double[] columnSize = {F}; + JPanel advancePropertyPane = TableLayoutHelper.createGapTableLayoutPane(components, rowSize, columnSize, HGAP, VGAP); + contentPane.add(advancePropertyPane, BorderLayout.NORTH); + UIExpandablePane sortUIExpandablePane = + new UIExpandablePane("扩展后排序", 223, 24, cellDSColumnSortPane = new CellDSColumnSortPane()); - return TableLayoutHelper.createGapTableLayoutPane(components, rowSize, columnSize, HGAP, VGAP); + contentPane.add(sortUIExpandablePane, BorderLayout.CENTER); + return contentPane; } public void enableListener() { @@ -643,6 +666,9 @@ public class CellDSColumnEditor extends CellQuickEditor { veCheckBox.addChangeListener(veCheckBoxChangeListener); useMultiNumCheckBox.addActionListener(useMultiNumCheckBoxChangeListener); multiNumSpinner.addChangeListener(multiNumSpinnerChangeListener); + if (cellDSColumnSortPane != null) { + cellDSColumnSortPane.addListener(cellDSColumnSortPaneChangeListener); + } } public void disableListener() { @@ -653,6 +679,9 @@ public class CellDSColumnEditor extends CellQuickEditor { veCheckBox.removeChangeListener(veCheckBoxChangeListener); useMultiNumCheckBox.removeActionListener(useMultiNumCheckBoxChangeListener); multiNumSpinner.removeChangeListener(multiNumSpinnerChangeListener); + if (cellDSColumnSortPane != null) { + cellDSColumnSortPane.removeListener(cellDSColumnSortPaneChangeListener); + } }