Browse Source

Merge branch 'feature/x' of ssh://code.fineres.com:7999/~roger.chen/design into feature/x

feature/x
roger 2 years ago
parent
commit
ac7525b436
  1. 41
      designer-base/src/main/java/com/fr/design/actions/help/alphafine/AlphaFineConfigManager.java
  2. 166
      designer-base/src/main/java/com/fr/design/actions/help/alphafine/AlphaFineConfigPane.java
  3. 4
      designer-base/src/main/java/com/fr/design/components/tooltip/ModernToolTip.java
  4. 5
      designer-base/src/main/java/com/fr/design/data/BasicTableDataTreePane.java
  5. 33
      designer-base/src/main/java/com/fr/design/data/DesignTableDataManager.java
  6. 3
      designer-base/src/main/java/com/fr/design/data/datapane/TableDataPaneListPane.java
  7. 8
      designer-base/src/main/java/com/fr/design/data/datapane/TableDataSourceOP.java
  8. 2
      designer-base/src/main/java/com/fr/design/data/datapane/TableDataTree.java
  9. 3
      designer-base/src/main/java/com/fr/design/data/datapane/TableDataTreePane.java
  10. 72
      designer-base/src/main/java/com/fr/design/data/datapane/preview/PreviewTablePane.java
  11. 6
      designer-base/src/main/java/com/fr/design/data/tabledata/tabledatapane/ProcedureDataPane.java
  12. 37
      designer-base/src/main/java/com/fr/design/data/tabledata/wrapper/MultiResultTableDataNameWrapper.java
  13. 73
      designer-base/src/main/java/com/fr/design/data/tabledata/wrapper/MultiResultTableDataWrapper.java
  14. 2
      designer-base/src/main/java/com/fr/design/data/tabledata/wrapper/StoreProcedureDataWrapper.java
  15. 15
      designer-base/src/main/java/com/fr/design/deeplink/DeepLinkCore.java
  16. 9
      designer-base/src/main/java/com/fr/design/file/HistoryTemplateListCache.java
  17. 8
      designer-base/src/main/java/com/fr/design/layout/FRGUIPaneFactory.java
  18. 8
      designer-base/src/main/java/com/fr/design/mainframe/CenterRegionContainerPane.java
  19. 2
      designer-base/src/main/java/com/fr/design/mainframe/theme/utils/DefaultThemedTemplateCellElementCase.java
  20. 32
      designer-base/src/main/java/com/fr/design/utils/ColorUtils.java
  21. 16
      designer-base/src/main/java/com/fr/design/utils/DesignUtils.java
  22. 15
      designer-base/src/main/java/com/fr/start/BaseDesigner.java
  23. 2
      designer-base/src/main/java/com/fr/start/common/DesignerOpenEmptyPanel.java
  24. 16
      designer-base/src/main/java/com/fr/start/common/DesignerStartupContext.java
  25. 30
      designer-base/src/main/java/com/fr/start/common/DesignerStartupUtil.java
  26. 1
      designer-base/src/main/java/com/fr/startup/metric/DesignerMetrics.java
  27. 198
      designer-base/src/main/java/com/fr/startup/metric/DesignerStartupPageStatistic.java
  28. 12
      designer-base/src/main/java/com/fr/startup/ui/StartupPageConstants.java
  29. 3
      designer-base/src/main/java/com/fr/startup/ui/StartupPageModel.java
  30. 46
      designer-base/src/main/java/com/fr/startup/ui/StartupPageUtil.java
  31. 49
      designer-base/src/main/java/com/fr/startup/ui/StartupPageWindow.java
  32. 145
      designer-base/src/main/java/com/fr/startup/ui/StartupPageWorkspacePanel.java
  33. BIN
      designer-base/src/main/resources/com/fr/design/startup/startup_page_background.jpg
  34. 21
      designer-base/src/test/java/com/fr/startup/ui/StartupPageUtilTest.java
  35. 16
      designer-form/src/main/java/com/fr/design/designer/creator/cardlayout/XWCardTagLayout.java
  36. 8
      designer-realize/src/main/java/com/fr/design/actions/server/WidgetManagerAction.java
  37. 4
      designer-realize/src/main/java/com/fr/design/deeplink/FileOpen4MacDeepLink.java
  38. 2
      designer-realize/src/main/java/com/fr/design/mainframe/ElementCasePaneDelegate.java
  39. 22
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/AlphaFineConstants.java
  40. 18
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/CellType.java
  41. 29
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/action/StartUseAction.java
  42. 303
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/AlphaFineFrame.java
  43. 16
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/ProductNewsList.java
  44. 74
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/RecommendSearchPane.java
  45. 74
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/TemplateResourceImagePanel.java
  46. 225
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/TemplateResourcePageGridPane.java
  47. 122
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/TemplateResourcePanel.java
  48. 47
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/model/ProductNews.java
  49. 191
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/model/TemplateResource.java
  50. 208
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/model/TemplateResourceDetail.java
  51. 196
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/preview/TemplateResourceDetailPane.java
  52. 158
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/preview/TemplateShopPane.java
  53. 109
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/search/TemplateResourceSearchWorkerManager.java
  54. 178
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/search/helper/FineMarketClientHelper.java
  55. 68
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/search/manager/impl/ProductNewsSearchManager.java
  56. 100
      designer-realize/src/main/java/com/fr/design/mainframe/alphafine/search/manager/impl/TemplateResourceSearchManager.java
  57. 11
      designer-realize/src/main/java/com/fr/start/MainDesigner.java
  58. 5
      designer-realize/src/main/java/com/fr/start/module/optimized/DesignerStartupPageActivator.java
  59. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/bottom.svg
  60. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/bottom_disable.svg
  61. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/config.svg
  62. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/down.svg
  63. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/down_disable.svg
  64. BIN
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/local_template1.png
  65. BIN
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/local_template2.png
  66. BIN
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/local_template3.png
  67. BIN
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/local_template4.png
  68. BIN
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/more.png
  69. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/next.svg
  70. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/prev.svg
  71. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/top.svg
  72. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/top_disable.svg
  73. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/up.svg
  74. 3
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/up_disable.svg
  75. 110
      designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/template_resource/local_templates.json

41
designer-base/src/main/java/com/fr/design/actions/help/alphafine/AlphaFineConfigManager.java

@ -10,18 +10,16 @@ import com.fr.stable.xml.XMLPrintWriter;
import com.fr.stable.xml.XMLReadable;
import com.fr.stable.xml.XMLable;
import com.fr.stable.xml.XMLableReader;
import java.util.Arrays;
import java.util.HashSet;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Set;
import java.util.Stack;
import org.jetbrains.annotations.NotNull;
import javax.swing.*;
import javax.swing.KeyStroke;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.Set;
import java.util.Stack;
/**
* AlphaFine配置类
@ -54,13 +52,17 @@ public class AlphaFineConfigManager implements XMLable {
*/
private boolean containRecommend = true;
/**
* 设置
* 功能
*/
private boolean containAction = true;
/**
* 帮助文档
*/
private boolean containDocument = true;
/**
* 我的模板
* */
private boolean containMyTemplate = true;
/**
* 模板
*/
@ -70,7 +72,7 @@ public class AlphaFineConfigManager implements XMLable {
*/
private boolean containFileContent;
/**
* 应用中心
* 插件中心
*/
private boolean containPlugin = true;
/**
@ -95,6 +97,11 @@ public class AlphaFineConfigManager implements XMLable {
*/
private boolean productDynamics = true;
/**
* 模板商城是否展示
* */
private boolean showTemplateShop = true;
private Map<String, String> actionSearchTextCache = new HashMap<>(8);
private String cacheBuildNO;
@ -326,6 +333,14 @@ public class AlphaFineConfigManager implements XMLable {
this.containDocument = containDocument;
}
public void setContainMyTemplate(boolean containMyTemplate) {
this.containMyTemplate = containMyTemplate;
}
public boolean isContainMyTemplate() {
return containMyTemplate;
}
public boolean isContainTemplate() {
return containTemplate;
}
@ -446,6 +461,14 @@ public class AlphaFineConfigManager implements XMLable {
return productDynamics && FRContext.isChineseEnv();
}
public boolean hasTemplateShop() {
return showTemplateShop && FRContext.isChineseEnv();
}
public void setShowTemplateShop(boolean showTemplateShop) {
this.showTemplateShop = showTemplateShop;
}
public void setProductDynamics(boolean productDynamics) {
this.productDynamics = productDynamics;
}

166
designer-base/src/main/java/com/fr/design/actions/help/alphafine/AlphaFineConfigPane.java

@ -1,17 +1,29 @@
package com.fr.design.actions.help.alphafine;
import com.fr.base.FRContext;
import com.fr.base.svg.IconUtils;
import com.fr.design.DesignerEnvManager;
import com.fr.design.dialog.BasicPane;
import com.fr.design.gui.icheckbox.UICheckBox;
import com.fr.design.gui.ilable.UILabel;
import com.fr.design.gui.imenu.UIPopupMenu;
import com.fr.design.gui.itextfield.UITextField;
import com.fr.design.i18n.Toolkit;
import com.fr.design.layout.FRGUIPaneFactory;
import com.fr.design.layout.TableLayoutHelper;
import com.fr.design.utils.gui.GUICoreUtils;
import com.fr.log.FineLoggerFactory;
import javax.swing.*;
import java.awt.*;
import javax.swing.BorderFactory;
import javax.swing.JButton;
import javax.swing.JPanel;
import javax.swing.KeyStroke;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Insets;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyAdapter;
@ -25,14 +37,22 @@ import java.awt.event.MouseEvent;
public class AlphaFineConfigPane extends BasicPane {
private static final String TYPE = "pressed";
private static final String DISPLAY_TYPE = "+";
private static final Color LABEL_TEXT = new Color(0x919193);
private static final double COLUMN_GAP = 180;
private static final double ROW_GAP = 25;
private static final double COLUMN_WIDTH = 150;
private static final double ROW_HEIGHT = 25;
private KeyStroke shortCutKeyStore = null;
private UICheckBox enabledCheckbox, searchOnlineCheckbox, needSegmentationCheckbox, needIntelligentCustomerService, productDynamicsCheckbox, containActionCheckbox, containDocumentCheckbox, containTemplateCheckbox, containPluginCheckbox, containFileContentCheckbox;
private UICheckBox enabledCheckbox, searchOnlineCheckbox, needSegmentationCheckbox;
private UICheckBox productDynamicsCheckbox, containTemplateShopCheckbox, containDocumentCheckbox,
containPluginCheckbox, containActionCheckbox, containMyTemplateCheckbox;
private UITextField shortcutsField;
// 搜索范围-我的模板,相关组件
private JPanel containMyTemplatePane;
private JButton myTemplateSearchConfigButton;
private UIPopupMenu myTemplateSearchMenu;
private UICheckBox containTemplateNameSearchCheckbox, containFileContentSearchCheckbox;
public AlphaFineConfigPane() {
this.initComponents();
}
@ -45,15 +65,6 @@ public class AlphaFineConfigPane extends BasicPane {
createSearchConfigPane(contentPane);
this.setLayout(FRGUIPaneFactory.createBorderLayout());
this.add(contentPane, BorderLayout.NORTH);
}
private Component[][] initSearchRangeComponents() {
Component[][] components = new Component[][]{
new Component[]{productDynamicsCheckbox, containActionCheckbox, containDocumentCheckbox},
new Component[]{containTemplateCheckbox, containPluginCheckbox, containFileContentCheckbox},
};
return components;
}
private Component[][] initOnlineComponents() {
@ -63,24 +74,99 @@ public class AlphaFineConfigPane extends BasicPane {
return components;
}
// 搜索范围
private void createSearchConfigPane(JPanel contentPane) {
double[] rowSize = {ROW_GAP, ROW_GAP, ROW_GAP};
double[] columnSize = {COLUMN_GAP, COLUMN_GAP, COLUMN_GAP};
double[] rowSize = {ROW_HEIGHT, ROW_HEIGHT, ROW_HEIGHT};
double[] columnSize = {COLUMN_WIDTH, COLUMN_WIDTH, COLUMN_WIDTH};
JPanel northPane = FRGUIPaneFactory.createTitledBorderPane(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_AlphaFine_Search_Range"));
productDynamicsCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_AlphaFine_Product_Dynamics"));
containActionCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_Set"));
productDynamicsCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_AlphaFine_Product_News"));
containActionCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_Function"));
containPluginCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_Plugin_Addon"));
containDocumentCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_Community_Help"));
containTemplateCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_Templates"));
containFileContentCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Templates_Content"));
needIntelligentCustomerService = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_AlphaFine_Intelligent_Customer_Service"));
containMyTemplateCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_My_Templates"));
containFileContentSearchCheckbox = new UICheckBox(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Templates_Content"));
containTemplateShopCheckbox = new UICheckBox(Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Shop"));
containMyTemplateCheckbox = new UICheckBox(Toolkit.i18nText("Fine-Design_Report_My_Templates"));
JPanel searchConfigPane = TableLayoutHelper.createTableLayoutPane(initSearchRangeComponents(), rowSize, columnSize);
northPane.add(searchConfigPane);
contentPane.add(northPane);
}
private Component[][] initSearchRangeComponents() {
// 我的模板checkbox设置,点击后
initMyTemplateSearchPane();
Component[][] components = new Component[][]{
new Component[]{productDynamicsCheckbox, containTemplateShopCheckbox, containDocumentCheckbox},
new Component[]{containPluginCheckbox, containActionCheckbox, containMyTemplatePane},
};
for (int i = 0; i < components.length; i++) {
for (int j = 0; j < components[i].length; j++) {
if (components[i][j] instanceof UICheckBox) {
UICheckBox box = (UICheckBox) components[i][j];
}
}
}
return components;
}
/**
* 搜索范围中的复选框有无选中的
* */
private boolean hasSelectedSearchRangeCheckBox() {
return productDynamicsCheckbox.isSelected() || containTemplateShopCheckbox.isSelected() || containDocumentCheckbox.isSelected()
|| containPluginCheckbox.isSelected() || containActionCheckbox.isSelected() || containMyTemplateCheckbox.isSelected();
}
// 搜索范围-我的模板
private void initMyTemplateSearchPane() {
containMyTemplatePane = new JPanel(new FlowLayout(FlowLayout.LEFT,4,5));
containMyTemplateCheckbox.setBorder(BorderFactory.createEmptyBorder());
containMyTemplateCheckbox.addActionListener(
new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
if (containMyTemplateCheckbox.isSelected()) {
myTemplateSearchConfigButton.setVisible(true);
} else {
myTemplateSearchConfigButton.setVisible(false);
}
}
}
);
myTemplateSearchConfigButton = new JButton();
myTemplateSearchConfigButton.setBorder(BorderFactory.createEmptyBorder());
myTemplateSearchConfigButton.setMargin(new Insets(0,0,0,0));
myTemplateSearchConfigButton.setIcon(IconUtils.readIcon("/com/fr/design/mainframe/alphafine/images/config.svg"));
myTemplateSearchMenu = new UIPopupMenu();
containTemplateNameSearchCheckbox = new UICheckBox(Toolkit.i18nText("Fine-Design_AlphaFine_Config_Name_Search"));
containFileContentSearchCheckbox = new UICheckBox(Toolkit.i18nText("Fine-Design_AlphaFine_Config_Content_Search"));
containTemplateNameSearchCheckbox.setSelected(true);
containTemplateNameSearchCheckbox.setEnabled(false);
containTemplateNameSearchCheckbox.setBackground(null);
containFileContentSearchCheckbox.setBackground(null);
myTemplateSearchMenu.add(containTemplateNameSearchCheckbox);
myTemplateSearchMenu.add(containFileContentSearchCheckbox);
myTemplateSearchConfigButton.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
super.mouseClicked(e);
GUICoreUtils.showPopupMenu(myTemplateSearchMenu, containMyTemplatePane, containMyTemplateCheckbox.getWidth(), containMyTemplatePane.getY());
}
@Override
public void mouseMoved(MouseEvent e) {
super.mouseMoved(e);
myTemplateSearchMenu.setVisible(false);
}
});
containMyTemplatePane.add("containMyTemplateCheckbox", containMyTemplateCheckbox);
containMyTemplatePane.add("myTemplateSearchConfigButton", myTemplateSearchConfigButton);
}
private void createShortcutsPane(JPanel contentPane) {
JPanel northPane = FRGUIPaneFactory.createTitledBorderPane(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_AlphaFine_Shortcut_Config"));
shortcutsField = new UITextField();
@ -91,7 +177,7 @@ public class AlphaFineConfigPane extends BasicPane {
northPane.add(new UILabel(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Open") + ":"));
northPane.add(shortcutsField);
UILabel label = new UILabel(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_AlphaFine_SetShortcuts"));
label.setForeground(Color.RED);
label.setForeground(LABEL_TEXT);
northPane.add(label);
contentPane.add(northPane);
}
@ -130,21 +216,21 @@ public class AlphaFineConfigPane extends BasicPane {
productDynamicsCheckbox.setEnabled(false);
containPluginCheckbox.setEnabled(false);
containDocumentCheckbox.setEnabled(false);
needIntelligentCustomerService.setEnabled(false);
containTemplateShopCheckbox.setEnabled(false);
productDynamicsCheckbox.setSelected(false);
containPluginCheckbox.setSelected(false);
containDocumentCheckbox.setSelected(false);
needIntelligentCustomerService.setSelected(false);
containTemplateShopCheckbox.setSelected(false);
} else {
productDynamicsCheckbox.setEnabled(true);
containPluginCheckbox.setEnabled(true);
containDocumentCheckbox.setEnabled(true);
needIntelligentCustomerService.setEnabled(true);
containTemplateShopCheckbox.setEnabled(true);
}
}
});
double[] rowSize = {ROW_GAP};
double[] columnSize = {COLUMN_GAP, COLUMN_GAP, COLUMN_GAP};
double[] rowSize = {ROW_HEIGHT};
double[] columnSize = {COLUMN_WIDTH, COLUMN_WIDTH, COLUMN_WIDTH};
JPanel onlinePane = TableLayoutHelper.createTableLayoutPane(initOnlineComponents(), rowSize, columnSize);
northPane.add(onlinePane);
contentPane.add(northPane);
@ -172,8 +258,10 @@ public class AlphaFineConfigPane extends BasicPane {
this.searchOnlineCheckbox.setSelected(enabled4Locale);
this.containActionCheckbox.setSelected(alphaFineConfigManager.isContainAction());
this.containTemplateCheckbox.setSelected(alphaFineConfigManager.isContainTemplate());
this.containFileContentCheckbox.setSelected(alphaFineConfigManager.isContainFileContent());
this.containMyTemplateCheckbox.setSelected(alphaFineConfigManager.isContainMyTemplate());
this.myTemplateSearchConfigButton.setVisible(alphaFineConfigManager.isContainMyTemplate());
this.containFileContentSearchCheckbox.setSelected(alphaFineConfigManager.isContainFileContent());
this.containDocumentCheckbox.setSelected(alphaFineConfigManager.isContainDocument() && enabled4Locale);
this.containDocumentCheckbox.setEnabled(enabled4Locale);
@ -184,13 +272,13 @@ public class AlphaFineConfigPane extends BasicPane {
this.productDynamicsCheckbox.setSelected(alphaFineConfigManager.isProductDynamics() && enabled4Locale);
this.productDynamicsCheckbox.setEnabled(enabled4Locale);
this.containTemplateShopCheckbox.setSelected(alphaFineConfigManager.hasTemplateShop() && enabled4Locale);
this.containTemplateShopCheckbox.setEnabled(enabled4Locale);
this.shortcutsField.setText(AlphaFineShortCutUtil.getDisplayShortCut(alphaFineConfigManager.getShortcuts()));
this.needSegmentationCheckbox.setSelected(alphaFineConfigManager.isNeedSegmentationCheckbox());
this.needIntelligentCustomerService.setSelected(alphaFineConfigManager.isNeedIntelligentCustomerService() && enabled4Locale);
this.needIntelligentCustomerService.setEnabled(enabled4Locale);
shortCutKeyStore = convert2KeyStroke(alphaFineConfigManager.getShortcuts());
}
@ -201,12 +289,12 @@ public class AlphaFineConfigPane extends BasicPane {
alphaFineConfigManager.setContainAction(this.containActionCheckbox.isSelected());
alphaFineConfigManager.setContainDocument(this.containDocumentCheckbox.isSelected());
alphaFineConfigManager.setProductDynamics(this.productDynamicsCheckbox.isSelected());
alphaFineConfigManager.setShowTemplateShop(this.containTemplateShopCheckbox.isSelected());
alphaFineConfigManager.setEnabled(this.enabledCheckbox.isSelected());
alphaFineConfigManager.setSearchOnLine(this.searchOnlineCheckbox.isSelected());
alphaFineConfigManager.setContainTemplate(this.containTemplateCheckbox.isSelected());
alphaFineConfigManager.setContainFileContent(this.containFileContentCheckbox.isSelected());
alphaFineConfigManager.setContainMyTemplate(this.containMyTemplateCheckbox.isSelected());
alphaFineConfigManager.setContainFileContent(this.containFileContentSearchCheckbox.isSelected());
alphaFineConfigManager.setNeedSegmentationCheckbox(this.needSegmentationCheckbox.isSelected());
alphaFineConfigManager.setNeedIntelligentCustomerService(this.needIntelligentCustomerService.isSelected());
alphaFineConfigManager.setShortcuts(shortCutKeyStore != null ? shortCutKeyStore.toString().replace(TYPE, DISPLAY_TYPE) : this.shortcutsField.getText());
designerEnvManager.setAlphaFineConfigManager(alphaFineConfigManager);
try {
@ -233,10 +321,10 @@ public class AlphaFineConfigPane extends BasicPane {
}
public UICheckBox getIsContainFileContentCheckbox() {
return containFileContentCheckbox;
return containFileContentSearchCheckbox;
}
public void setIsContainFileContentCheckbox(UICheckBox isContainFileContentCheckbox) {
this.containFileContentCheckbox = isContainFileContentCheckbox;
this.containFileContentSearchCheckbox = isContainFileContentCheckbox;
}
}

4
designer-base/src/main/java/com/fr/design/components/tooltip/ModernToolTip.java

@ -12,11 +12,9 @@ import javax.swing.plaf.ToolTipUI;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.FontMetrics;
import java.awt.GradientPaint;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.geom.GeneralPath;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.StringReader;
@ -52,7 +50,7 @@ public class ModernToolTip extends UIToolTip {
Graphics2D g2 = (Graphics2D) g;
g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2.setColor(new Color(51, 51, 52, (int) Math.round(0.7 * 255)));
g2.fillRoundRect(0, 0, width, height, 0, 0);
g2.fillRoundRect(0, 0, width, height, 4, 4);
g2.setColor(Color.WHITE);
if (strs != null) {

5
designer-base/src/main/java/com/fr/design/data/BasicTableDataTreePane.java

@ -4,7 +4,6 @@ import com.fr.base.BaseUtils;
import com.fr.base.TableData;
import com.fr.data.MultiResultTableData;
import com.fr.data.TableDataSource;
import com.fr.data.api.StoreProcedureAssist;
import com.fr.design.DesignModelAdapter;
import com.fr.design.actions.UpdateAction;
import com.fr.design.data.datapane.TableDataCreatorProducer;
@ -184,7 +183,7 @@ public abstract class BasicTableDataTreePane extends DockingView implements Resp
private boolean isIncludeUnderline(String name) {
return ComparatorUtils.equals(name.indexOf(StoreProcedureAssist.GROUP_MARKER), -1) ? false : true;
return ComparatorUtils.equals(name.indexOf(MultiResultTableData.GROUP_MARKER), -1) ? false : true;
}
public abstract void addDataPane(final AbstractTableDataPane<?> uPanel, String paneName);
@ -445,7 +444,7 @@ public abstract class BasicTableDataTreePane extends DockingView implements Resp
((MultiResultTableData<?>) (((TableDataWrapper) data).getTableData())).resetDataModelList();
if (data instanceof MultiResultTableDataWrapper) {
MultiResultTableDataWrapper oldSdw = ((MultiResultTableDataWrapper) data);
MultiResultTableDataWrapper newSdw = new MultiResultTableDataWrapper((MultiResultTableData<?>) oldSdw.getTableData(), oldSdw.getTableDataName(), oldSdw.getTableDataName());
MultiResultTableDataWrapper newSdw = new MultiResultTableDataWrapper((MultiResultTableData<?>) oldSdw.getTableData(), oldSdw.getTableDataName(), oldSdw.getDataModelName());
newSdw.previewData(MultiResultTableDataWrapper.PREVIEW_ONE);
} else {
MultiResultTableData<?> tableData = (MultiResultTableData<?>) ((TableDataWrapper) data).getTableData();

33
designer-base/src/main/java/com/fr/design/data/DesignTableDataManager.java

@ -9,8 +9,10 @@ import com.fr.data.TableDataSourceTailor;
import com.fr.data.core.DataCoreXmlUtils;
import com.fr.data.impl.EmbeddedTableData;
import com.fr.data.impl.NameDataModel;
import com.fr.data.impl.storeproc.ProcedureDataModel;
import com.fr.data.impl.storeproc.StoreProcedure;
import com.fr.data.impl.storeproc.StoreProcedureConstants;
import com.fr.data.impl.storeproc.StoreProcedureHelper;
import com.fr.data.operator.DataOperator;
import com.fr.design.DesignModelAdapter;
import com.fr.design.data.datapane.preview.PreviewTablePane;
@ -322,9 +324,8 @@ public abstract class DesignTableDataManager {
public static java.util.Map<String, TableDataWrapper> getAllDataSetIncludingProcedure(java.util.Map<String, TableDataWrapper> resMap) {
java.util.LinkedHashMap<String, TableDataWrapper> dsMap = new java.util.LinkedHashMap<String, TableDataWrapper>();
Iterator<Entry<String, TableDataWrapper>> entryIt = resMap.entrySet().iterator();
while (entryIt.hasNext()) {
String key = entryIt.next().getKey();
for (Entry<String, TableDataWrapper> entry : resMap.entrySet()) {
String key = entry.getKey();
TableDataWrapper tableDataWrapper = resMap.get(key);
if (tableDataWrapper.getTableData() instanceof MultiResultTableData) {
MultiResultTableData<?> tableData = (MultiResultTableData<?>) tableDataWrapper.getTableData();
@ -333,9 +334,10 @@ public abstract class DesignTableDataManager {
TableDataWrapper tdw = new MultiResultTableDataNameWrapper(name + "_Table", tableData);
boolean hasSchemaOrResult = false;
// 存储过程的特殊处理,还有其它名称
if (tableData instanceof StoreProcedure) {
StoreProcedure storeProcedure = (StoreProcedure) tableData;
StoreProcedureParameter[] parameters = StoreProcedure.getSortPara(storeProcedure.getParameters());
StoreProcedureParameter[] parameters = StoreProcedureHelper.getSortPara(storeProcedure.getParameters());
for (StoreProcedureParameter parameter : parameters) {
if (parameter.getSchema() != StoreProcedureConstants.IN) {
@ -345,20 +347,21 @@ public abstract class DesignTableDataManager {
hasSchemaOrResult = true;
}
}
} else {
for (NameDataModel nameDataModel : tableData.getDataModelList()) {
String dmName = name + "_" + nameDataModel.getName();
dsMap.put(nameDataModel.getName(), new MultiResultTableDataWrapper(tableData, name, dmName, false));
} /*else {
// TODO getDataModelList是空的
for (String n : tableData.getResultNames()) {
String dmName = name + "_" + n;
dsMap.put(n, new MultiResultTableDataWrapper(tableData, name, dmName, false));
}
}
}*/
if (!resultNames.isEmpty()) {
hasSchemaOrResult = true;
for (int i = 0; i < resultNames.size(); i++) {
String parameterName = name + "_" + resultNames.get(i);
TableDataWrapper newTwd = new MultiResultTableDataWrapper(tableData, name, parameterName, false);
dsMap.put(parameterName, newTwd);
for (String resultName : resultNames) {
String dmName = name + "_" + resultName;
TableDataWrapper newTwd = new MultiResultTableDataWrapper(tableData, name, dmName, false);
dsMap.put(dmName, newTwd);
}
}
@ -621,8 +624,8 @@ public abstract class DesignTableDataManager {
XMLPrintWriter writer = XMLPrintWriter.create(out);
// 把storeProcedure写成xml文件到out
DataCoreXmlUtils.writeXMLStoreProcedure(writer, storeProcedure, null);
if (storeProcedure.getDataModelSize() > 0 && !storeProcedure.isFirstExpand()) {
return storeProcedure.creatLazyDataModel();
if (storeProcedure.getDataModelList().size() > 0 && !storeProcedure.isFirstExpand()) {
return storeProcedure.getDataModelList().toArray(new ProcedureDataModel[0]);
}
ParameterProvider[] inParameters = DataOperator.getInstance().getStoreProcedureParameters(storeProcedure);

3
designer-base/src/main/java/com/fr/design/data/datapane/TableDataPaneListPane.java

@ -5,7 +5,6 @@ import com.fr.base.TableDataBean;
import com.fr.config.RemoteConfigEvent;
import com.fr.data.MultiResultTableData;
import com.fr.data.TableDataSource;
import com.fr.data.api.StoreProcedureAssist;
import com.fr.design.data.BasicTableDataUtils;
import com.fr.design.data.DesignTableDataManager;
import com.fr.design.dialog.FineJOptionPane;
@ -137,7 +136,7 @@ public class TableDataPaneListPane extends JListControlPane implements TableData
}
private boolean isIncludeUnderline(String name) {
return name.contains(StoreProcedureAssist.GROUP_MARKER);
return name.contains(MultiResultTableData.GROUP_MARKER);
}
/**

8
designer-base/src/main/java/com/fr/design/data/datapane/TableDataSourceOP.java

@ -4,9 +4,9 @@ import com.fr.base.StoreProcedureParameter;
import com.fr.base.TableData;
import com.fr.data.MultiResultTableData;
import com.fr.data.TableDataSource;
import com.fr.data.impl.NameDataModel;
import com.fr.data.impl.storeproc.StoreProcedure;
import com.fr.data.impl.storeproc.StoreProcedureConstants;
import com.fr.data.impl.storeproc.StoreProcedureHelper;
import com.fr.design.DesignModelAdapter;
import com.fr.design.data.DesignTableDataManager;
import com.fr.design.data.tabledata.wrapper.MultiResultTableDataNameWrapper;
@ -203,7 +203,7 @@ public class TableDataSourceOP implements UserObjectOP<TableDataWrapper> {
if (tableData instanceof StoreProcedure) {
StoreProcedure storeProcedure = (StoreProcedure) tableData;
StoreProcedureParameter[] parameters = StoreProcedure.getSortPara(storeProcedure.getParameters());
StoreProcedureParameter[] parameters = StoreProcedureHelper.getSortPara(storeProcedure.getParameters());
for (StoreProcedureParameter parameter : parameters) {
if (parameter.getSchema() != StoreProcedureConstants.IN) {
if (!nodeName.contains(parameter.getName())) {
@ -217,7 +217,7 @@ public class TableDataSourceOP implements UserObjectOP<TableDataWrapper> {
}
}
}
} else {
} /*else {
if (tableData.getDataModelList().size() > 1) {
for (NameDataModel nameDataModel : tableData.getDataModelList()) {
if (!nodeName.contains(nameDataModel.getName())) {
@ -231,7 +231,7 @@ public class TableDataSourceOP implements UserObjectOP<TableDataWrapper> {
}
}
}
}
}*/
if (!resultNames.isEmpty()) {

2
designer-base/src/main/java/com/fr/design/data/datapane/TableDataTree.java

@ -379,7 +379,7 @@ public class TableDataTree extends UserObjectRefreshJTree<TableDataSourceOP> {
return false;
}
Object userObject = treeNode.getUserObject();
if (userObject instanceof NameObject && ((NameObject) userObject).getObject() instanceof AbstractTableDataWrapper) {
if (userObject instanceof NameObject && ((NameObject) userObject).getObject() instanceof TableDataWrapper) {
return true;
}
return false;

3
designer-base/src/main/java/com/fr/design/data/datapane/TableDataTreePane.java

@ -3,7 +3,6 @@ package com.fr.design.data.datapane;
import com.fr.base.TableData;
import com.fr.data.MultiResultTableData;
import com.fr.data.TableDataSource;
import com.fr.data.api.StoreProcedureAssist;
import com.fr.data.impl.DBTableData;
import com.fr.data.impl.TableDataSourceDependent;
import com.fr.design.DesignModelAdapter;
@ -522,7 +521,7 @@ public class TableDataTreePane extends BasicTableDataTreePane {
private boolean isIncludeUnderline(String name) {
return !ComparatorUtils.equals(name.indexOf(StoreProcedureAssist.GROUP_MARKER), -1);
return !ComparatorUtils.equals(name.indexOf(MultiResultTableData.GROUP_MARKER), -1);
}
@Override

72
designer-base/src/main/java/com/fr/design/data/datapane/preview/PreviewTablePane.java

@ -8,7 +8,6 @@ import com.fr.base.TableData;
import com.fr.data.TableDataSource;
import com.fr.data.impl.DBTableData;
import com.fr.data.impl.EmbeddedTableData;
import com.fr.data.impl.NameDataModel;
import com.fr.data.operator.DataOperator;
import com.fr.design.DesignerEnvManager;
@ -65,7 +64,7 @@ import java.util.concurrent.CancellationException;
*/
public class PreviewTablePane extends BasicPane {
private TableData tableData;
private NameDataModel dataModel;
private DataModel dataModel;
private UINumberField maxPreviewNumberField;
private UINumberField currentRowsField;
private JTable preveiwTable;
@ -156,7 +155,7 @@ public class PreviewTablePane extends BasicPane {
try {
populate(tableData);
if (dataModel != null) {
populateStoreDataSQL();
setRowsLimitTableModel();
}
} catch (Exception e1) {
}
@ -426,6 +425,7 @@ public class PreviewTablePane extends BasicPane {
*
* @param storeProcedureDataModel storeProcedureDataModel
*/
@Deprecated
public static void previewStoreData(NameDataModel storeProcedureDataModel) {
previewStoreData(storeProcedureDataModel, -1, -1);
}
@ -437,13 +437,30 @@ public class PreviewTablePane extends BasicPane {
* @param keyIndex 实际值
* @param valueIndex 显示值
*/
@Deprecated
public static void previewStoreData(final NameDataModel storeProcedureDataModel, final int keyIndex, final int valueIndex) {
previewDataModel(storeProcedureDataModel, keyIndex, valueIndex);
}
public static void previewDataModel(DataModel dataModel) {
previewDataModel(dataModel, -1, -1);
}
/**
* 直接预览数据集的结果集
*
* @param dataModel 结果集
* @param keyIndex
* @param valueIndex
*/
public static void previewDataModel(final DataModel dataModel, final int keyIndex, final int valueIndex) {
final PreviewTablePane previewTablePane = new PreviewTablePane();
previewTablePane.dataModel = storeProcedureDataModel;
previewTablePane.dataModel = dataModel;
previewTablePane.setBorder(BorderFactory.createTitledBorder(Toolkit.i18nText("Fine-Design_Basic_Data")));
try {
previewTablePane.populateStoreDataSQL();
previewTablePane.setRowsLimitTableModel();
previewTablePane.resetPreviewTableColumnColor();
if (keyIndex > -1) {
@ -460,27 +477,28 @@ public class PreviewTablePane extends BasicPane {
previewTablePane.showWindow(new JFrame()).setVisible(true);
}
/**
* 直接预览存储过程的所有返回数据集没有实际值和显示值
*
* @param storeProcedureDataModels storeProcedureDataModels
*/
public static void previewStoreDataWithAllDs(NameDataModel[] storeProcedureDataModels) {
UITabbedPane tabPreviewpane = new UITabbedPane();
int tableSize = storeProcedureDataModels.length;
for (int i = 0; i < tableSize; i++) {
public static void previewMultiDataModels(NameDataModel[] nameDataModels) {
// tab窗口
UITabbedPane tabbedPane = new UITabbedPane();
for (NameDataModel nameDataModel : nameDataModels) {
// 单个结果集的展示面板
PreviewTablePane previewTablePane = new PreviewTablePane();
previewTablePane.dataModel = storeProcedureDataModels[i];
previewTablePane.dataModel = nameDataModel;
// 数据
previewTablePane.setBorder(BorderFactory.createTitledBorder(Toolkit.i18nText("Fine-Design_Basic_Data")));
try {
previewTablePane.populateStoreDataSQL();
// 带行数限制的数据集结果预览对象
previewTablePane.setRowsLimitTableModel();
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
tabPreviewpane.addTab(storeProcedureDataModels[i].getName(), previewTablePane);
tabbedPane.addTab(nameDataModel.getName(), previewTablePane);
}
BasicPane prieviewPane = new BasicPane() {
// 包含整个tab的容器窗口
BasicPane previewPane = new BasicPane() {
@Override
protected String title4PopupWindow() {
@ -488,12 +506,22 @@ public class PreviewTablePane extends BasicPane {
}
};
prieviewPane.setLayout(FRGUIPaneFactory.createBorderLayout());
prieviewPane.add(tabPreviewpane, BorderLayout.CENTER);
prieviewPane.showWindow(new JFrame()).setVisible(true);
previewPane.setLayout(FRGUIPaneFactory.createBorderLayout());
previewPane.add(tabbedPane, BorderLayout.CENTER);
previewPane.showWindow(new JFrame()).setVisible(true);
}
/**
* 直接预览存储过程的所有返回数据集没有实际值和显示值
*
* @param storeProcedureDataModels storeProcedureDataModels
*/
@Deprecated
public static void previewStoreDataWithAllDs(NameDataModel[] storeProcedureDataModels) {
previewMultiDataModels(storeProcedureDataModels);
}
private void populateStoreDataSQL() throws Exception {
private void setRowsLimitTableModel() throws Exception {
PreviewTableModel previewModel;
try {
previewModel = new PreviewTableModel(dataModel, (int) maxPreviewNumberField.getValue());

6
designer-base/src/main/java/com/fr/design/data/tabledata/tabledatapane/ProcedureDataPane.java

@ -289,16 +289,16 @@ public class ProcedureDataPane extends AbstractTableDataPane<StoreProcedure> imp
@Override
protected Void doInBackground() throws Exception {
DesignTableDataManager.setThreadLocal(DesignTableDataManager.NO_PARAMETER);
sp.setCalculating(true);
// sp.setCalculating(true);
ProcedureDataModel[] dataModels = (ProcedureDataModel[]) DesignTableDataManager.createLazyDataModel(sp, false);
sp.refreshDataModelListAndResultNames(dataModels);
//sp.refreshDataModelListAndResultNames(dataModels);
return null;
}
@Override
public void done() {
DesignTableDataManager.setThreadLocal(DesignTableDataManager.NO_PARAMETER);
sp.setCalculating(false);
// sp.setCalculating(false);
doAfterProcudureDone();
fireDSChanged();
TableDataTreePane.getInstance(DesignModelAdapter.getCurrentModelAdapter());

37
designer-base/src/main/java/com/fr/design/data/tabledata/wrapper/MultiResultTableDataNameWrapper.java

@ -1,6 +1,5 @@
package com.fr.design.data.tabledata.wrapper;
import com.fr.base.BaseUtils;
import com.fr.base.TableData;
import com.fr.data.MultiResultTableData;
import com.fr.data.impl.NameDataModel;
@ -9,6 +8,7 @@ import com.fr.design.data.datapane.TableDataCreatorProducer;
import com.fr.design.data.datapane.TableDataNameObjectCreator;
import com.fr.design.data.datapane.preview.PreviewTablePane;
import com.fr.design.gui.itree.refreshabletree.ExpandMutableTreeNode;
import com.fr.general.IOUtils;
import com.fr.log.FineLoggerFactory;
import com.fr.workspace.WorkContext;
@ -29,15 +29,15 @@ public final class MultiResultTableDataNameWrapper implements TableDataWrapper {
private NameDataModel dataModel;
private final String name;
private final MultiResultTableData<?> tableData;
private List<String> columnNameList;
private List<String> childrenList;
/**
* @param name 存储过程本身名字
* @param storeProcedure 存储过程
* @param name 数据集名字
* @param tableData 数据集
*/
public MultiResultTableDataNameWrapper(String name, MultiResultTableData<?> storeProcedure) {
public MultiResultTableDataNameWrapper(String name, MultiResultTableData<?> tableData) {
this.name = name;
this.tableData = storeProcedure;
this.tableData = tableData;
}
/**
@ -46,6 +46,7 @@ public final class MultiResultTableDataNameWrapper implements TableDataWrapper {
* @return 子节点
*/
public ExpandMutableTreeNode[] load() {
// 生成多数据集结果子节点
List<String> namelist = calculateColumnNameList();
ExpandMutableTreeNode[] res = new ExpandMutableTreeNode[namelist.size()];
for (int i = 0; i < res.length; i++) {
@ -67,17 +68,17 @@ public final class MultiResultTableDataNameWrapper implements TableDataWrapper {
@Override
public Icon getIcon() {
// TODO
for (TableDataNameObjectCreator creator : TableDataCreatorProducer.getInstance().createReportTableDataCreator()) {
if (creator.createObject().getClass() == this.tableData.getClass()) {
return BaseUtils.readIcon(creator.getIconPath());
if (creator.createObject().getClass().isAssignableFrom(this.tableData.getClass())) {
return IOUtils.readIcon(creator.getIconPath());
}
}
return BaseUtils.readIcon("/com/fr/design/images/data/multi.png");
return IOUtils.readIcon("/com/fr/design/images/data/multi.png");
}
private void createResult(boolean needLoadingBar) {
try {
// todo 啥意思?
dataModel = DesignTableDataManager.createLazyDataModel(tableData, needLoadingBar)[0];
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
@ -92,14 +93,14 @@ public final class MultiResultTableDataNameWrapper implements TableDataWrapper {
* @return 字段
*/
public List<String> calculateColumnNameList() {
if (columnNameList != null) {
return columnNameList;
if (childrenList != null) {
return childrenList;
}
columnNameList = new ArrayList<String>();
childrenList = new ArrayList<>();
if (!WorkContext.getCurrent().isLocal()) {
try {
createResult(false);
columnNameList = Arrays.asList(dataModel.getColumnNames());
childrenList = Arrays.asList(dataModel.getColumnNames());
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
@ -109,10 +110,10 @@ public final class MultiResultTableDataNameWrapper implements TableDataWrapper {
createResult(false);
}
if (dataModel != null) {
columnNameList = Arrays.asList(dataModel.getColumnNames());
childrenList = Arrays.asList(dataModel.getColumnNames());
}
}
return columnNameList;
return childrenList;
}
/**
@ -122,7 +123,7 @@ public final class MultiResultTableDataNameWrapper implements TableDataWrapper {
if (dataModel == null) {
createResult(true);
}
PreviewTablePane.previewStoreData(dataModel);
PreviewTablePane.previewDataModel(dataModel);
}
@ -136,7 +137,7 @@ public final class MultiResultTableDataNameWrapper implements TableDataWrapper {
if (dataModel == null) {
createResult(true);
}
PreviewTablePane.previewStoreData(dataModel, keyIndex, valueIndex);
PreviewTablePane.previewDataModel(dataModel, keyIndex, valueIndex);
}
/**

73
designer-base/src/main/java/com/fr/design/data/tabledata/wrapper/MultiResultTableDataWrapper.java

@ -1,6 +1,5 @@
package com.fr.design.data.tabledata.wrapper;
import com.fr.base.BaseUtils;
import com.fr.base.TableData;
import com.fr.data.MultiResultTableData;
import com.fr.data.impl.NameDataModel;
@ -16,6 +15,7 @@ import com.fr.design.gui.itree.refreshabletree.ExpandMutableTreeNode;
import com.fr.design.i18n.Toolkit;
import com.fr.design.mainframe.DesignerContext;
import com.fr.general.ComparatorUtils;
import com.fr.general.IOUtils;
import com.fr.log.FineLoggerFactory;
import javax.swing.Icon;
@ -40,7 +40,7 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
public static AutoProgressBar loadingBar;
private NameDataModel dataModel;
private final String dsName;
private final String dataModelName;
private final String tableDataName;
private final MultiResultTableData<?> tableData;
private List<String> columnNameList;
@ -49,29 +49,45 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
private SwingWorker<?, ?> worker;
private int previewModel;
public MultiResultTableDataWrapper(MultiResultTableData<?> tableData, String tableDataName, String dsName) {
this(null, tableData, tableDataName, dsName, true);
/**
* @param tableData 数据集
* @param tableDataName 数据集名称
* @param dataModelName 数据集的一个结果的名称全限定名称
*/
public MultiResultTableDataWrapper(MultiResultTableData<?> tableData, String tableDataName, String dataModelName) {
this(null, tableData, tableDataName, dataModelName, true);
}
public MultiResultTableDataWrapper(MultiResultTableData<?> tableData, String tableDataName, String dsName, boolean needLoad) {
this(null, tableData, tableDataName, dsName, needLoad);
/**
* @param tableData 数据集
* @param tableDataName 数据集名称
* @param dataModelName 数据集的一个结果的名称全限定名称
* @param needLoad 是否需要加载
*/
public MultiResultTableDataWrapper(MultiResultTableData<?> tableData, String tableDataName, String dataModelName, boolean needLoad) {
this(null, tableData, tableDataName, dataModelName, needLoad);
}
public MultiResultTableDataWrapper(Component component, MultiResultTableData<?> tableData, String tableDataName, String dsName) {
this(component, tableData, tableDataName, dsName, true);
/**
* @param component 父容器
* @param tableData 数据集
* @param tableDataName 数据集名称
* @param dataModelName 数据集的一个结果的名称全限定名称
*/
public MultiResultTableDataWrapper(Component component, MultiResultTableData<?> tableData, String tableDataName, String dataModelName) {
this(component, tableData, tableDataName, dataModelName, true);
}
/**
* @param component loadingBar的父弹框如果不设置父弹框的话可能出现loadingBar隐藏在一个弹框后的情况
* @param tableData 存储过程
* @param tableDataName 存储过程的名字(某些情况下可以为空)
* @param dsName 存储过程一个返回数据集的名字
* @param tableData 多结果数据集
* @param tableDataName 多结果数据集的名字(某些情况下可以为空)
* @param dataModelName 多结果数据集一个返回数据集的名字
* @param needLoad 是否要加载
**/
public MultiResultTableDataWrapper(Component component, MultiResultTableData<?> tableData, String tableDataName, String dsName, boolean needLoad) {
this.dsName = dsName;
public MultiResultTableDataWrapper(Component component, MultiResultTableData<?> tableData, String tableDataName, String dataModelName, boolean needLoad) {
this.dataModelName = dataModelName;
this.tableData = tableData;
this.tableData.setCalculating(false);
this.tableDataName = tableDataName;
if (component == null) {
component = new JFrame();
@ -133,10 +149,11 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
private void createResults(boolean needLoadingBar) throws Exception {
this.dataModel = null;
dataModels = DesignTableDataManager.createLazyDataModel(tableData, needLoadingBar);
if (dataModels != null && dataModels.length != 0) {
for (NameDataModel dataModel : dataModels) {
if (ComparatorUtils.equals(this.dsName, tableDataName + "_" + dataModel.getName())) {
if (ComparatorUtils.equals(this.dataModelName, tableDataName + MultiResultTableData.GROUP_MARKER + dataModel.getName())) {
this.dataModel = dataModel;
break;
}
@ -147,11 +164,11 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
@Override
public Icon getIcon() {
for (TableDataNameObjectCreator creator : TableDataCreatorProducer.getInstance().createReportTableDataCreator()) {
if (creator.createObject().getClass() == this.tableData.getClass()) {
return BaseUtils.readIcon(creator.getIconPath());
if (creator.createObject().getClass().isAssignableFrom(this.tableData.getClass())) {
return IOUtils.readIcon(creator.getIconPath());
}
}
return BaseUtils.readIcon("/com/fr/design/images/data/multi.png");
return IOUtils.readIcon("/com/fr/design/images/data/multi.png");
}
/**
@ -179,6 +196,8 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
loadingBar.close();
PreviewTablePane.resetPreviewTable();
connectionBar.start();
// 存储过程需要先测试一下连接
if (tableData instanceof StoreProcedure) {
boolean status = DataOperator.getInstance().testConnection(((StoreProcedure) getTableData()).getDatabaseConnection());
if (!status) {
@ -189,6 +208,8 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
connectionBar.close();
tableData.resetDataModelList();
// 获取结果
createResults(true);
return null;
}
@ -200,7 +221,7 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
loadingBar.close();
switch (previewModel) {
case MultiResultTableDataWrapper.PREVIEW_ALL:
PreviewTablePane.previewStoreDataWithAllDs(dataModels);
PreviewTablePane.previewMultiDataModels(dataModels);
break;
case MultiResultTableDataWrapper.PREVIEW_ONE:
previewData();
@ -246,12 +267,12 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
*/
@Override
public void previewData(final int keyIndex, final int valueIndex) {
PreviewTablePane.previewStoreData(dataModel, keyIndex, valueIndex);
PreviewTablePane.previewDataModel(dataModel, keyIndex, valueIndex);
}
/**
* 预览返回的所有数据集只有在编辑存储过程时才用到
* 预览返回的所有数据集只有在编辑多结果数据集时才用到
*/
public void previewAllTable() {
if (dataModel == null) {
@ -261,12 +282,16 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
return;
}
}
PreviewTablePane.previewStoreDataWithAllDs(dataModels);
PreviewTablePane.previewMultiDataModels(dataModels);
}
@Override
public String getTableDataName() {
return dsName;
return tableDataName;
}
public String getDataModelName() {
return dataModelName;
}
@Override
@ -287,7 +312,7 @@ public final class MultiResultTableDataWrapper implements TableDataWrapper {
@Override
public boolean equals(Object obj) {
return obj instanceof MultiResultTableDataWrapper
&& ComparatorUtils.equals(this.dsName, ((MultiResultTableDataWrapper) obj).getTableDataName())
&& ComparatorUtils.equals(this.dataModelName, ((MultiResultTableDataWrapper) obj).getTableDataName())
&& ComparatorUtils.equals(this.tableData, ((MultiResultTableDataWrapper) obj).getTableData())
&& ComparatorUtils.equals(this.tableDataName, ((MultiResultTableDataWrapper) obj).getTableDataName());

2
designer-base/src/main/java/com/fr/design/data/tabledata/wrapper/StoreProcedureDataWrapper.java

@ -76,7 +76,7 @@ public final class StoreProcedureDataWrapper implements TableDataWrapper {
public StoreProcedureDataWrapper(Component component, StoreProcedure storeProcedure, String storeprocedureName, String dsName, boolean needLoad) {
this.dsName = dsName;
this.storeProcedure = storeProcedure;
this.storeProcedure.setCalculating(false);
/*this.storeProcedure.setCalculating(false);*/
this.storeprocedureName = storeprocedureName;
if (component == null) {
component = new JFrame();

15
designer-base/src/main/java/com/fr/design/deeplink/DeepLinkCore.java

@ -10,6 +10,7 @@ import com.fr.event.Null;
import com.fr.log.FineLoggerFactory;
import com.fr.stable.StringUtils;
import com.fr.stable.os.OperatingSystem;
import com.fr.start.common.DesignerStartupContext;
import com.fr.third.org.apache.http.NameValuePair;
import com.fr.web.URLUtils;
@ -131,7 +132,19 @@ public class DeepLinkCore {
}
private boolean canConsumePendingURL() {
return StringUtils.isNotEmpty(this.pendingURL) && isDesignerStartupCompleted;
return StringUtils.isNotEmpty(this.pendingURL) && isAvailableConsumingTime();
}
/**
* 是否是可用的消耗时机
* 满足任一即可
* 1-设计器已经启动
* 2-出在设计器启动页页面
*
* @return /
*/
private boolean isAvailableConsumingTime() {
return isDesignerStartupCompleted || DesignerStartupContext.getInstance().isOnWaiting();
}
private void consumePendingURL() {

9
designer-base/src/main/java/com/fr/design/file/HistoryTemplateListCache.java

@ -97,8 +97,13 @@ public class HistoryTemplateListCache implements CallbackEvent {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
}
/**
* 需要使用 {@link JTemplate#isValid(JTemplate)} 来判断空
*
* @return 当前正在编辑的模板
*/
@Nullable
public JTemplate<?, ?> getCurrentEditingTemplate() {
return this.editingTemplate;

8
designer-base/src/main/java/com/fr/design/layout/FRGUIPaneFactory.java

@ -153,7 +153,7 @@ public class FRGUIPaneFactory {
}
public static LayoutManager createCenterLayout(JComponent centerBody) {
return createCenterLayout(centerBody, 0.3d);
return createCenterLayout(centerBody, 0.5d, 0.3d);
}
/**
@ -162,7 +162,7 @@ public class FRGUIPaneFactory {
* @param centerBody 中心组件
* @return 布局方式
*/
public static LayoutManager createCenterLayout(JComponent centerBody, double factor) {
public static LayoutManager createCenterLayout(JComponent centerBody, double factorX, double factorY) {
return new LayoutManager() {
@ -188,8 +188,8 @@ public class FRGUIPaneFactory {
// 这个时候大小是不确定的
int bodyWidth = centerBody.getPreferredSize().width;
int bodyHeight = centerBody.getPreferredSize().height;
int labelX = (width - bodyWidth) / 2;
int labelY = (int) ((height - bodyHeight) * factor);
int labelX = (int) ((width - bodyWidth) * factorX);
int labelY = (int) ((height - bodyHeight) * factorY);
centerBody.setBounds(labelX, labelY, bodyWidth, bodyHeight);
}

8
designer-base/src/main/java/com/fr/design/mainframe/CenterRegionContainerPane.java

@ -156,7 +156,7 @@ public class CenterRegionContainerPane extends JPanel {
private void addExtraButtons() {
JTemplate<?, ?> jt = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate();
if (jt == null) {
if (!JTemplate.isValid(jt)) {
return;
}
@ -172,7 +172,7 @@ public class CenterRegionContainerPane extends JPanel {
private void addCheckButton() {
JTemplate<?, ?> jt = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate();
if (jt == null) {
if (!JTemplate.isValid(jt)) {
return;
}
combineUp.addSeparator(new Dimension(2, 16));
@ -185,7 +185,7 @@ public class CenterRegionContainerPane extends JPanel {
private void addShareButton() {
JTemplate<?, ?> jt = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate();
if (jt == null) {
if (!JTemplate.isValid(jt)) {
return;
}
@ -205,7 +205,7 @@ public class CenterRegionContainerPane extends JPanel {
protected void checkCombineUp(boolean flag, ArrayList<String> al) {
//Yvan: 检查当前是否为WORK_SHEET状态,因为只有WORK_SHEET中含有格式刷组件,此时是不需要进行checkComponentsByNames的
JTemplate<?, ?> jTemplate = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate();
if (jTemplate != null) {
if (JTemplate.isValid(jTemplate)) {
// 第一个条件满足后还需要添加一重判断,判断是编辑报表块还是参数面板,编辑报表块时则直接return
if (jTemplate.getMenuState() == DesignState.WORK_SHEET && !jTemplate.isUpMode()) {
return;

2
designer-base/src/main/java/com/fr/design/mainframe/theme/utils/DefaultThemedTemplateCellElementCase.java

@ -33,7 +33,7 @@ public class DefaultThemedTemplateCellElementCase {
private static DefaultTemplateCellElement themingCellElement(DefaultTemplateCellElement cellElement) {
JTemplate<?,?> template = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate();
if (template != null) {
if (JTemplate.isValid(template)) {
TemplateTheme theme = template.getTemplateTheme();
ThemedCellStyle themedCellStyle = theme.getCellStyleList().getUse4Default();
if (themedCellStyle != null) {

32
designer-base/src/main/java/com/fr/design/utils/ColorUtils.java

@ -27,6 +27,38 @@ public class ColorUtils {
}
}
}
/**
* 递归的同步颜色如何组件的背景颜色等于默认颜色的话变更为 replaceColor
*
* @param component 组件
* @param replaceColor 替换颜色
* @param defaultColor 默认颜色
*/
public static void syncBackgroundIfAbsent(Component component, Color replaceColor, Color defaultColor) {
if (component.getBackground() != defaultColor) {
return;
}
component.setBackground(replaceColor);
if (component instanceof Container) {
Container container = (Container) component;
Component[] components = container.getComponents();
if (components != null) {
Arrays.stream(components).forEach((e) -> syncBackgroundIfAbsent(e, replaceColor, defaultColor));
}
}
}
/**
* 使背景透明
*
* @param component 组件
*/
public static void transparentBackground(Component component) {
syncBackgroundIfAbsent(component, new Color(0,0,0,0), ThemeUtils.BACK_COLOR);
}
public static boolean isDarkColor(Color color) {
if(color == null) {

16
designer-base/src/main/java/com/fr/design/utils/DesignUtils.java

@ -25,7 +25,7 @@ import com.fr.stable.StringUtils;
import com.fr.stable.os.OperatingSystem;
import com.fr.start.ServerStarter;
import com.fr.start.common.DesignerStartupContext;
import com.fr.startup.ui.StartupPageModel;
import com.fr.start.common.DesignerStartupUtil;
import com.fr.value.NotNullLazyValue;
import com.fr.workspace.WorkContext;
import org.jetbrains.annotations.NotNull;
@ -48,7 +48,6 @@ import java.net.URI;
import java.nio.charset.StandardCharsets;
import java.util.Enumeration;
import java.util.Locale;
import java.util.Optional;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
@ -216,18 +215,9 @@ public class DesignUtils {
@Override
public void run() {
DesignerStartupContext context = DesignerStartupContext.getInstance();
// 如果在启动页展示中
if (context.isOnWaiting()) {
FileFILE fileFILE = new FileFILE(f);
// 设置上一次启动模板为
DesignerEnvManager.getEnvManager().setLastOpenFile(fileFILE.getPath());
StartupPageModel model = context.getStartupPageModel();
Optional.ofNullable(model)
.ifPresent((e) -> {
// 执行上一次模板的启动
Runnable openLastTemplateRunnable = e.getOpenLastTemplateRunnable();
openLastTemplateRunnable.run();
});
if (DesignerStartupUtil.openTemplateIfOnWaiting(f)) {
return;
}
// 如果是在启动中

15
designer-base/src/main/java/com/fr/start/BaseDesigner.java

@ -35,6 +35,7 @@ import com.fr.start.common.DesignerStartupContext;
import com.fr.start.common.DesignerStartupUtil;
import com.fr.start.event.LazyStartupEvent;
import com.fr.workspace.base.WorkspaceStatus;
import org.jetbrains.annotations.Nullable;
import java.awt.Window;
import java.lang.reflect.Method;
@ -126,7 +127,7 @@ public abstract class BaseDesigner extends ToolBarMenuDock {
if (args != null && args.length > 0) {
file = DesignerStartupUtil.convertArgs2FILE(args);
} else {
file = FILEFactory.createFILE(FILEFactory.ENV_PREFIX + DesignerEnvManager.getEnvManager().getLastOpenFile());
file = getLastOpenFile();
}
DesignerFrame df = DesignerContext.getDesignerFrame();
isException = openFile(df, isException, file);
@ -141,7 +142,17 @@ public abstract class BaseDesigner extends ToolBarMenuDock {
}
}
}
@Nullable
private FILE getLastOpenFile() {
FILE file = DesignerStartupContext.getInstance().getStartingTemplateFile();
if (file == null) {
file = FILEFactory.createFILE(FILEFactory.ENV_PREFIX + DesignerEnvManager.getEnvManager().getLastOpenFile());
}
return file;
}
private boolean openFile(final DesignerFrame df, boolean isException, FILE file) {
AtomicBoolean isExWrapper = new AtomicBoolean(isException);

2
designer-base/src/main/java/com/fr/start/common/DesignerOpenEmptyPanel.java

@ -70,7 +70,7 @@ public class DesignerOpenEmptyPanel extends JPanel {
this.body.add(createIcon, BorderLayout.NORTH);
this.body.add(createButtonPanel, BorderLayout.SOUTH);
setLayout(FRGUIPaneFactory.createCenterLayout(this.body, 0.4d));
setLayout(FRGUIPaneFactory.createCenterLayout(this.body, 0.4d, 0.4d));
ColorUtils.syncBackground(this, Color.WHITE);

16
designer-base/src/main/java/com/fr/start/common/DesignerStartupContext.java

@ -3,6 +3,7 @@ package com.fr.start.common;
import com.fr.design.DesignerEnvManager;
import com.fr.design.env.DesignerWorkspaceInfo;
import com.fr.design.env.DesignerWorkspaceType;
import com.fr.file.FileFILE;
import com.fr.start.module.StartupArgs;
import com.fr.startup.metric.DesignerMetrics;
import com.fr.startup.ui.StartupPageModel;
@ -64,6 +65,11 @@ public class DesignerStartupContext {
*/
private boolean createNew;
/**
* 启动的模板
*/
private FileFILE startingTemplateFile;
/**
* 时间记录
*/
@ -72,7 +78,7 @@ public class DesignerStartupContext {
public static DesignerStartupContext getInstance() {
return StartupContextHolder.INSTANCE;
}
private static class StartupContextHolder {
private static final DesignerStartupContext INSTANCE = new DesignerStartupContext();
}
@ -87,6 +93,14 @@ public class DesignerStartupContext {
/* 启动模式 */
public FileFILE getStartingTemplateFile() {
return startingTemplateFile;
}
public void setStartingTemplateFile(FileFILE startingTemplateFile) {
this.startingTemplateFile = startingTemplateFile;
}
/**
* 展示启动页
* 1. 判断当前的工作目录数量

30
designer-base/src/main/java/com/fr/start/common/DesignerStartupUtil.java

@ -6,16 +6,44 @@ import com.fr.file.FILE;
import com.fr.file.FILEFactory;
import com.fr.file.FileFILE;
import com.fr.general.ComparatorUtils;
import com.fr.startup.ui.StartupPageModel;
import org.jetbrains.annotations.Nullable;
import java.io.File;
import java.util.Optional;
/**
* created by Harrison on 2022/07/09
**/
public class DesignerStartupUtil {
@Nullable
/**
* 如果是在启动页中
*
* @param file 文件
* @return 成功/失败
*/
public static boolean openTemplateIfOnWaiting(File file) {
DesignerStartupContext context = DesignerStartupContext.getInstance();
// 如果在启动页展示中
if (context.isOnWaiting()) {
FileFILE fileFILE = new FileFILE(file);
// 设置上一次启动模板为当前模板
DesignerStartupContext.getInstance().setStartingTemplateFile(fileFILE);
StartupPageModel model = context.getStartupPageModel();
Optional.ofNullable(model)
.ifPresent((e) -> {
// 执行上一次模板的启动
Runnable openLastTemplateRunnable = e.getOpenLastTemplateRunnable();
openLastTemplateRunnable.run();
});
return true;
}
return false;
}
@Nullable
public static FILE convertArgs2FILE(String[] args) {
// p:需要打开这个报表文件,这个代码不能删除.

1
designer-base/src/main/java/com/fr/startup/metric/DesignerMetrics.java

@ -19,4 +19,5 @@ public class DesignerMetrics {
public DesignerStartupPageStatistic getStatistic() {
return statistic;
}
}

198
designer-base/src/main/java/com/fr/startup/metric/DesignerStartupPageStatistic.java

@ -1,5 +1,13 @@
package com.fr.startup.metric;
import com.fr.stable.StringUtils;
import com.fr.start.common.DesignerStartupContext;
import com.fr.startup.ui.StartupPageModel;
import com.fr.startup.ui.StartupWorkspaceBean;
import java.util.ArrayDeque;
import java.util.Deque;
/**
* 设计器启动页使用数据
*
@ -7,65 +15,185 @@ package com.fr.startup.metric;
**/
public class DesignerStartupPageStatistic {
private final Deque<Operation> operations = new ArrayDeque<>();
/**
* operate0-双击工作目录进入 点击蓝色箭头进入1-切换其他工作目录2-点击展开全部3-点击工作目录中的模版直接打开 直接点击蓝色箭头进入
* {@link OperationType} 的注释
*/
private int operate;
public void recordOpenEmptyTemplate() {
Operation operation = OperationType.DO_OPEN_EMPTY_TEMPLATE.create();
StartupPageModel pageModel = DesignerStartupContext.getInstance().getStartupPageModel();
operation.setWorkspace(pageModel.getSelectWorkspaceInfo().getName());
operation.setWorkspaceNum(pageModel.getWorkspaceInfos().size());
pushOperation(operation);
}
/**
* workplace工作目录名称当operate为 0或1时记录
* {@link OperationType} 的注释
*/
private String workspace;
public void recordSwitchWorkspace(StartupWorkspaceBean lastWorkspaceInfo, StartupWorkspaceBean currentWorkspace) {
if (lastWorkspaceInfo != null && StringUtils.equals(lastWorkspaceInfo.getName(), currentWorkspace.getName())) {
return;
}
Operation operation = OperationType.DO_SWITCH_WORKSPACE.create();
StartupPageModel pageModel = DesignerStartupContext.getInstance().getStartupPageModel();
operation.setWorkspace(currentWorkspace.getName());
operation.setWorkspaceNum(pageModel.getWorkspaceInfos().size());
pushOperation(operation);
}
/**
* workplaceNumber工作目录的个数当operate为 0或1或2或3时记录
* {@link OperationType} 的注释
*/
private String workspaceNum;
public void recordShowAllAction() {
Operation operation = OperationType.DO_SHOW_ALL_ACTION.create();
StartupPageModel pageModel = DesignerStartupContext.getInstance().getStartupPageModel();
operation.setWorkspaceNum(pageModel.getWorkspaceInfos().size());
pushOperation(operation);
}
/**
* template模板名称当operate为 3时记录
* {@link OperationType} 的注释
*/
private String template;
public void recordOpenLastTemplate(String lastOpenFile) {
public DesignerStartupPageStatistic(int operate, String workspace, String workspaceNum, String template) {
this.operate = operate;
this.workspace = workspace;
this.workspaceNum = workspaceNum;
this.template = template;
Operation operation = OperationType.DO_OPEN_LAST_TEMPLATE_ACTION.create();
StartupPageModel pageModel = DesignerStartupContext.getInstance().getStartupPageModel();
operation.setWorkspaceNum(pageModel.getWorkspaceInfos().size());
operation.setTemplate(lastOpenFile);
pushOperation(operation);
}
public DesignerStartupPageStatistic() {
}
/**
* 添加操作
*
* @param operation 操作
*/
public void pushOperation(Operation operation) {
public int getOperate() {
return operate;
this.operations.push(operation);
}
public void setOperate(int operate) {
this.operate = operate;
}
/**
* 获取操作
*
* @return 操作
*/
public Deque<Operation> getOperations() {
public String getWorkspace() {
return workspace;
return this.operations;
}
public void setWorkspace(String workspace) {
this.workspace = workspace;
}
public enum OperationType {
public String getWorkspaceNum() {
return workspaceNum;
}
/**
* 双击工作目录进入 点击蓝色箭头进入
*/
DO_OPEN_EMPTY_TEMPLATE(0),
public void setWorkspaceNum(String workspaceNum) {
this.workspaceNum = workspaceNum;
}
/**
* 切换其他工作目录
*/
DO_SWITCH_WORKSPACE(1),
/**
* 点击展开全部
*/
DO_SHOW_ALL_ACTION(2),
/**
* 点击工作目录中的模版直接打开 直接点击蓝色箭头进入
*/
DO_OPEN_LAST_TEMPLATE_ACTION(3);
private final int sign;
public String getTemplate() {
return template;
OperationType(int sign) {
this.sign = sign;
}
public int getSign() {
return sign;
}
public Operation create() {
Operation operation = new Operation();
operation.setOperateType(this);
return operation;
}
}
public void setTemplate(String template) {
this.template = template;
public static class Operation {
/**
* operate0-双击工作目录进入 点击蓝色箭头进入1-切换其他工作目录2-点击展开全部3-点击工作目录中的模版直接打开 直接点击蓝色箭头进入
*/
private int operate;
/**
* workplace工作目录名称当operate为 0或1时记录
*/
private String workspace;
/**
* workplaceNumber工作目录的个数当operate为 0或1或2或3时记录
*/
private int workspaceNum;
/**
* template模板名称当operate为 3时记录
*/
private String template;
public Operation(int operate, String workspace, int workspaceNum, String template) {
this.operate = operate;
this.workspace = workspace;
this.workspaceNum = workspaceNum;
this.template = template;
}
public Operation() {
}
public int getOperate() {
return operate;
}
public void setOperateType(OperationType operateType) {
this.operate = operateType.getSign();
}
public void setOperate(int operate) {
this.operate = operate;
}
public String getWorkspace() {
return workspace;
}
public void setWorkspace(String workspace) {
this.workspace = workspace;
}
public int getWorkspaceNum() {
return workspaceNum;
}
public void setWorkspaceNum(int workspaceNum) {
this.workspaceNum = workspaceNum;
}
public String getTemplate() {
return template;
}
public void setTemplate(String template) {
this.template = template;
}
}
}

12
designer-base/src/main/java/com/fr/startup/ui/StartupPageConstants.java

@ -1,5 +1,7 @@
package com.fr.startup.ui;
import java.awt.Color;
/**
* created by Harrison on 2022/07/07
**/
@ -14,4 +16,14 @@ public class StartupPageConstants {
* 内容宽度
*/
public static final int CONTENT_WIDTH = 850;
/**
* 边框的颜色
*/
public static final Color BORDER_COLOR = Color.WHITE;
/**
* 透明的颜色
*/
public static final Color TRANSPARENT_COLOR = new Color(0, 0, 0, 0);
}

3
designer-base/src/main/java/com/fr/startup/ui/StartupPageModel.java

@ -45,7 +45,8 @@ public class StartupPageModel {
DesignerWorkspaceInfo workspaceInfo = envManager.getWorkspaceInfo(e);
if (workspaceInfo.getType() == DesignerWorkspaceType.Remote) {
WorkspaceConnectionInfo connection = workspaceInfo.getConnection();
return new StartupWorkspaceBean(e, connection.getUrl(), workspaceInfo.getType());
String remoteAddress = StartupPageUtil.getRemoteAddress(connection.getUrl());
return new StartupWorkspaceBean(e, remoteAddress, workspaceInfo.getType());
} else {
return new StartupWorkspaceBean(e, workspaceInfo.getPath(), workspaceInfo.getType());
}

46
designer-base/src/main/java/com/fr/startup/ui/StartupPageUtil.java

@ -2,14 +2,22 @@ package com.fr.startup.ui;
import com.fr.base.svg.SVGIcon;
import com.fr.design.env.DesignerWorkspaceType;
import com.fr.log.FineLoggerFactory;
import com.fr.stable.StringUtils;
import javax.swing.Icon;
import javax.swing.JComponent;
import javax.swing.JRootPane;
import java.net.URL;
/**
* created by Harrison on 2022/07/11
**/
public class StartupPageUtil {
public static final int INVALID_PORT = -1;
public static final String COLON = ":";
/**
* 获取最近区域的 ICON
*
@ -37,4 +45,42 @@ public class StartupPageUtil {
}
return SVGIcon.readSVGIcon("/com/fr/design/startup/remote_server_background_28.svg", 28, 28);
}
/**
* 返回 ip : port
*
* @param urlStr 完整的 url 例如 https://localhost:3090/xxx
* @return localhost:3090
*/
public static String getRemoteAddress(String urlStr) {
try {
if (StringUtils.isEmpty(urlStr)) {
return StringUtils.EMPTY;
}
URL url = new URL(urlStr);
String host = url.getHost();
int port = url.getPort();
if (port == INVALID_PORT) {
return host;
}
return host + COLON + port;
} catch (Exception e) {
FineLoggerFactory.getLogger().debug(e.getMessage(), e);
return urlStr;
}
}
/**
* 透明的背景需要从根节点重绘
*
* @param component 组件
*/
public static void repaintAll(JComponent component) {
JRootPane rootPane = component.getRootPane();
if (rootPane != null) {
rootPane.repaint();
}
}
}

49
designer-base/src/main/java/com/fr/startup/ui/StartupPageWindow.java

@ -11,12 +11,15 @@ import com.fr.design.layout.FRGUIPaneFactory;
import com.fr.design.layout.VerticalFlowLayout;
import com.fr.design.ui.util.UIUtil;
import com.fr.design.utils.ColorUtils;
import com.fr.design.utils.gui.GUICoreUtils;
import com.fr.design.utils.ThemeUtils;
import com.fr.exit.DesignerExiter;
import com.fr.general.GeneralUtils;
import com.fr.general.IOUtils;
import com.fr.log.FineLoggerFactory;
import com.fr.stable.ProductConstants;
import com.fr.stable.collections.CollectionUtils;
import com.fr.start.common.DesignerStartupContext;
import com.fr.startup.metric.DesignerMetrics;
import org.jetbrains.annotations.NotNull;
import javax.swing.BorderFactory;
@ -44,6 +47,7 @@ import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.awt.image.BufferedImage;
import java.util.List;
import java.util.Map;
@ -68,7 +72,7 @@ public class StartupPageWindow extends JFrame {
private static final int TITLE_FONT_SIZE = 24;
private static final int ITEM_VERTICAL_GAP = 5;
private static final Dimension SCREEN_SIZE = new Dimension(1600, 820);
private static final Dimension SCREEN_SIZE = java.awt.Toolkit.getDefaultToolkit().getScreenSize();
private StartupPageWorkspacePanel workspacePanel;
@ -96,6 +100,7 @@ public class StartupPageWindow extends JFrame {
setLayout(new BorderLayout());
this.body = FRGUIPaneFactory.createBorderLayout_S_Pane();
this.body.setBackground(new Color(0, 0, 0, 0));
// Header
UILabel label = new UILabel(Toolkit.i18nText("Fine-Design_Startup_Page_Select_Workspace"));
Font font = label.getFont();
@ -105,6 +110,7 @@ public class StartupPageWindow extends JFrame {
LayoutManager centerFlowLayout = FRGUIPaneFactory.createCenterFlowLayout();
headerPanel.setLayout(centerFlowLayout);
headerPanel.add(label);
headerPanel.setBackground(new Color(0, 0, 0, 0));
this.body.add(headerPanel, BorderLayout.NORTH);
// Workspace-description
@ -126,7 +132,14 @@ public class StartupPageWindow extends JFrame {
this.recentOpenPanel = generateRecentOpenPanel(pageModel);
this.body.add(recentOpenPanel, BorderLayout.SOUTH);
this.contentPane = new JPanel();
this.contentPane = new JPanel() {
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
BufferedImage image = IOUtils.readImage("com/fr/design/startup/startup_page_background.jpg");
g.drawImage(image, 0, 0, SCREEN_SIZE.width, SCREEN_SIZE.height, this);
}
};
this.contentPane.setLayout(getCenterLayout(body));
this.contentPane.add(this.body, BorderLayout.CENTER);
this.contentPane.setPreferredSize(this.body.getPreferredSize());
@ -147,7 +160,14 @@ public class StartupPageWindow extends JFrame {
validate();
revalidate();
GUICoreUtils.centerWindow(this);
setFullScreen();
}
private void setFullScreen() {
Dimension screenSize = java.awt.Toolkit.getDefaultToolkit().getScreenSize();
this.setLocation(0, 0);
this.setSize(screenSize.width, screenSize.height);
}
private void addDefaultListeners() {
@ -296,6 +316,7 @@ public class StartupPageWindow extends JFrame {
recentOpenWrapperPanel.setBorder(new EmptyBorder(0, 0, 0, 20));
recentOpenWrapperPanel.add(recentOpenPanel, BorderLayout.CENTER);
ColorUtils.syncBackgroundIfAbsent(recentOpenWrapperPanel, new Color(0,0,0,0), ThemeUtils.BACK_COLOR);
return recentOpenWrapperPanel;
}
@ -324,17 +345,18 @@ public class StartupPageWindow extends JFrame {
@Override
public void mouseEntered(MouseEvent e) {
recentFileLabel.setForeground(HOVER_COLOR);
StartupPageUtil.repaintAll(recentOpenGroupPanel);
}
@Override
public void mouseExited(MouseEvent e) {
recentFileLabel.setForeground(recentFileLabelForeground);
StartupPageUtil.repaintAll(recentOpenGroupPanel);
}
@Override
public void mouseClicked(MouseEvent e) {
DesignerEnvManager.getEnvManager().setLastOpenFile(recentFile);
pageModel.getOpenLastTemplateRunnable().run();
doOpenLastTemplateAction(recentFile, pageModel);
}
});
Dimension preferredSize = recentItemPanel.getPreferredSize();
@ -357,8 +379,10 @@ public class StartupPageWindow extends JFrame {
}
private StartupPageWorkspacePanel generateWorkspacePanel(StartupPageModel pageModel) {
return new StartupPageWorkspacePanel(pageModel);
StartupPageWorkspacePanel startupPageWorkspacePanel = new StartupPageWorkspacePanel(pageModel);
ColorUtils.syncBackgroundIfAbsent(startupPageWorkspacePanel, new Color(0, 0, 0, 0), ThemeUtils.BACK_COLOR);
return startupPageWorkspacePanel;
}
protected LayoutManager getCenterLayout(JComponent centerBody) {
@ -366,4 +390,13 @@ public class StartupPageWindow extends JFrame {
return FRGUIPaneFactory.createCenterLayout(centerBody);
}
private void doOpenLastTemplateAction(String recentFile, StartupPageModel pageModel) {
DesignerEnvManager.getEnvManager().setLastOpenFile(recentFile);
pageModel.getOpenLastTemplateRunnable().run();
DesignerMetrics designerMetrics = DesignerStartupContext.getInstance().getDesignerMetrics();
designerMetrics.getStatistic().recordOpenLastTemplate(recentFile);
}
}

145
designer-base/src/main/java/com/fr/startup/ui/StartupPageWorkspacePanel.java

@ -7,6 +7,8 @@ import com.fr.design.gui.ilable.UILabel;
import com.fr.design.i18n.Toolkit;
import com.fr.design.layout.FRGUIPaneFactory;
import com.fr.design.utils.ColorUtils;
import com.fr.start.common.DesignerStartupContext;
import com.fr.startup.metric.DesignerMetrics;
import com.fr.third.guava.collect.Lists;
import org.jetbrains.annotations.NotNull;
@ -89,6 +91,7 @@ public class StartupPageWorkspacePanel extends JPanel {
public StartupPageWorkspacePanel(StartupPageModel pageModel) {
this.setLayout(new BorderLayout(0, 0));
this.setBorder(new EmptyBorder(15, 0, 20, 0));
this.pageModel = pageModel;
@ -127,8 +130,12 @@ public class StartupPageWorkspacePanel extends JPanel {
private JComponent generateUnLimitContentPanel(List<List<StartupWorkspaceBean>> partitions) {
JPanel workspaceDescWrapper = new JPanel();
workspaceDescWrapper.setLayout(new BorderLayout(0, 0));
workspaceDescWrapper.setBorder(new EmptyBorder(0, 0, 0, 0));
JPanel workspaceDescPanel = new JPanel();
workspaceDescPanel.setLayout(new GridLayout(partitions.size(), 1, 0, ITEM_VERTICAL_GAP));
workspaceDescPanel.setLayout(new GridLayout(partitions.size(), 1, 0, 0));
for (List<StartupWorkspaceBean> partition : partitions) {
JPanel partitionPanel = generatePartitionPanel(partition);
workspaceDescPanel.add(partitionPanel);
@ -139,14 +146,18 @@ public class StartupPageWorkspacePanel extends JPanel {
UIScrollPane scrollPane = new UIScrollPane(workspaceDescPanel, ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED, ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);
scrollPane.setBorder(new EmptyBorder(10, 0, 0, 0));
scrollPane.setPreferredSize(new Dimension(CONTENT_WIDTH, SCROLL_HEIGHT));
return scrollPane;
workspaceDescWrapper.add(scrollPane, BorderLayout.CENTER);
return workspaceDescWrapper;
}
return workspaceDescPanel;
workspaceDescWrapper.add(workspaceDescPanel, BorderLayout.CENTER);
ColorUtils.transparentBackground(workspaceDescWrapper);
return workspaceDescWrapper;
}
private JPanel generateLimitContentPanel(List<List<StartupWorkspaceBean>> partitions) {
JPanel workspaceDescPanel = FRGUIPaneFactory.createVerticalFlowLayout_Pane(true, FlowLayout.LEFT, 0, ITEM_VERTICAL_GAP);
JPanel workspaceDescPanel = FRGUIPaneFactory.createVerticalFlowLayout_Pane(true, FlowLayout.LEFT, 0, 0);
int limit = 2;
for (int i = 0; i < partitions.size(); i++) {
if (i >= limit) {
@ -157,22 +168,38 @@ public class StartupPageWorkspacePanel extends JPanel {
JPanel partitionPanel = generatePartitionPanel(partition);
workspaceDescPanel.add(partitionPanel);
}
ColorUtils.transparentBackground(workspaceDescPanel);
return workspaceDescPanel;
}
@NotNull
private JPanel generateTailPanel() {
AtomicReference<Color> hoverBackColorRef = new AtomicReference<>();
JPanel tailPanel = new JPanel();
{
tailPanel.setLayout(new FlowLayout(FlowLayout.RIGHT));
tailPanel.setBorder(new EmptyBorder(0, 0, 0, 20));
JPanel showAllPanel = new JPanel();
JPanel showAllPanel = new JPanel() {
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
if (hoverBackColorRef.get() != null) {
g.setColor(hoverBackColorRef.get());
Dimension preferredSize = getPreferredSize();
g.fillRoundRect(0, 0, preferredSize.width, preferredSize.height, 5, 5);
}
}
};
showAllPanel.setLayout(new BorderLayout(5, 0));
showAllPanel.setBorder(new EmptyBorder(5, 5, 5, 5));
UILabel fontLabel = new UILabel(Toolkit.i18nText("Fine-Design_Startup_Page_Expand_All"));
fontLabel.setForeground(HOVER_COLOR);
showAllPanel.setBackground(new Color(0, 0, 0, 0));
showAllPanel.add(fontLabel, BorderLayout.WEST);
UILabel iconLabel = new UILabel(IconUtils.readIcon("/com/fr/design/startup/show_more.svg"));
@ -183,28 +210,21 @@ public class StartupPageWorkspacePanel extends JPanel {
showAllPanel.addMouseListener(new MouseAdapter() {
@Override
public void mouseEntered(MouseEvent e) {
Color hoverColor = new Color(217, 235, 254);
showAllPanel.setBackground(hoverColor);
Color hoverBackColor = new Color(217, 235, 254);
hoverBackColorRef.set(hoverBackColor);
repaintAll();
}
@Override
public void mouseExited(MouseEvent e) {
hoverBackColorRef.set(null);
ColorUtils.syncBackground(showAllPanel, showAllBackground);
repaintAll();
}
@Override
public void mousePressed(MouseEvent e) {
if (showMore) {
fontLabel.setText(Toolkit.i18nText("Fine-Design_Startup_Page_Collapse_Workspace"));
iconLabel.setIcon(IconUtils.readIcon("/com/fr/design/startup/show_less.svg"));
showMoreContent();
showMore = !showMore;
} else {
fontLabel.setText(Toolkit.i18nText("Fine-Design_Startup_Page_Expand_All"));
iconLabel.setIcon(IconUtils.readIcon("/com/fr/design/startup/show_more.svg"));
showLessContent();
showMore = !showMore;
}
doShowAllAction(fontLabel, iconLabel);
}
});
tailPanel.add(showAllPanel);
@ -217,7 +237,11 @@ public class StartupPageWorkspacePanel extends JPanel {
@NotNull
private JPanel generatePartitionPanel(List<StartupWorkspaceBean> partition) {
JPanel partitionPanel = FRGUIPaneFactory.createBoxFlowInnerContainer_S_Pane(0, 20, 0);;
JPanel partitionPanelWrapper = new JPanel();
partitionPanelWrapper.setBorder(new EmptyBorder(10,0,10,0));
partitionPanelWrapper.setLayout(new BorderLayout());
JPanel partitionPanel = FRGUIPaneFactory.createBoxFlowInnerContainer_S_Pane(0, 20, 0);
partitionPanel.setName("partitionPanel");
for (StartupWorkspaceBean workspaceInfo : partition) {
@ -233,7 +257,9 @@ public class StartupPageWorkspacePanel extends JPanel {
Dimension preferredSize = partitionPanel.getPreferredSize();
partitionPanel.setPreferredSize(new Dimension(CONTENT_WIDTH, (int) preferredSize.getHeight()));
}
return partitionPanel;
partitionPanelWrapper.add(partitionPanel, BorderLayout.CENTER);
return partitionPanelWrapper;
}
private void layoutSelectWorkspacePanel(StartupWorkspaceBean workspaceInfo, JPanel workspaceItemDesc) {
@ -298,8 +324,8 @@ public class StartupPageWorkspacePanel extends JPanel {
int roundOffset = 15;
// 画一个圆角
int fixRoundWidth = getWidth() - rectOffset;
int fixRoundHeight = getHeight() - BORDER_THIN * 2;
g2d.drawRoundRect(BORDER_THIN, BORDER_THIN, fixRoundWidth, fixRoundHeight, ARC_DIAMETER, ARC_DIAMETER);
int fixRoundHeight = getHeight() - BORDER_THIN;
g2d.drawRoundRect(strokeOffset, strokeOffset, fixRoundWidth, fixRoundHeight, ARC_DIAMETER, ARC_DIAMETER);
g2d.setColor(backColor);
@ -313,9 +339,9 @@ public class StartupPageWorkspacePanel extends JPanel {
g2d.fillRect(fixedX, BORDER_THIN, coverWidth, coverHeight);
g2d.setColor(borderColor);
g2d.drawLine(getWidth() / 2, BORDER_THIN, getWidth(), BORDER_THIN);
g2d.drawLine(getWidth() / 2, getHeight() - BORDER_THIN, getWidth(), getHeight() - BORDER_THIN);
g2d.drawLine(getWidth() - strokeOffset, BORDER_THIN, getWidth() - strokeOffset, getHeight() - BORDER_THIN);
g2d.drawLine(getWidth() / 2, strokeOffset, getWidth(), strokeOffset);
g2d.drawLine(getWidth() / 2, getHeight() - strokeOffset, getWidth(), getHeight() - strokeOffset);
g2d.drawLine(getWidth() - strokeOffset, strokeOffset, getWidth() - strokeOffset, getHeight() - strokeOffset);
}
}
};
@ -366,7 +392,7 @@ public class StartupPageWorkspacePanel extends JPanel {
borderColorRef.set(hoverColor);
nameLabel.setForeground(hoverColor);
pathLabel.setForeground(hoverColor );
selectWorkspacePanel.getParent().repaint();
repaintAll();
}
@Override
@ -374,7 +400,7 @@ public class StartupPageWorkspacePanel extends JPanel {
borderColorRef.set(Color.WHITE);
nameLabel.setForeground(nameForeground);
pathLabel.setForeground(pathColor);
selectWorkspacePanel.getParent().repaint();
repaintAll();
}
@Override
@ -382,13 +408,10 @@ public class StartupPageWorkspacePanel extends JPanel {
int clickCount = e.getClickCount();
if (clickCount == DOUBLE_CLICK_COUNT) {
pageModel.setSelectWorkspaceInfo(workspaceInfo);
openEmptyTemplateRunnable.run();
doOpenEmptyTemplate(workspaceInfo);
return;
}
// selectWorkspaceRunnable
pageModel.setSelectWorkspaceInfo(workspaceInfo);
selectWorkspaceRunnable.run();
doSwitchWorkspace(workspaceInfo);
}
};
@ -415,7 +438,7 @@ public class StartupPageWorkspacePanel extends JPanel {
@Override
public void mousePressed(MouseEvent e) {
openEmptyTemplateRunnable.run();
doOpenEmptyTemplate(workspaceInfo);
}
});
descPanel.add(arrowLabel, BorderLayout.EAST);
@ -462,16 +485,15 @@ public class StartupPageWorkspacePanel extends JPanel {
int borderOffset = BORDER_THIN * 2;
// 画画的笔触需要调整一下
//g2d.drawRoundRect(strokeOffset, strokeOffset, getWidth() - rectOffset, getHeight() - BORDER_THIN, 0, 0);
g2d.drawRoundRect(BORDER_THIN, BORDER_THIN, getWidth() - borderOffset, getHeight() - borderOffset, ARC_DIAMETER, ARC_DIAMETER);
g2d.drawRoundRect(strokeOffset, strokeOffset, getWidth() - borderOffset, getHeight() - BORDER_THIN, ARC_DIAMETER, ARC_DIAMETER);
g2d.setColor(backColor);
int fillWidth = 15;
g2d.fillRect(0, 0, fillWidth, getHeight());
g2d.setColor(borderColor);
g2d.drawLine(BORDER_THIN, BORDER_THIN, fillWidth, BORDER_THIN);
g2d.drawLine(BORDER_THIN, getHeight() - BORDER_THIN, fillWidth, getHeight() - BORDER_THIN);
g2d.drawLine(BORDER_THIN, BORDER_THIN, BORDER_THIN, getHeight() - BORDER_THIN);
g2d.drawLine(strokeOffset, strokeOffset, fillWidth, strokeOffset);
g2d.drawLine(strokeOffset, getHeight() - strokeOffset, fillWidth, getHeight() - strokeOffset);
g2d.drawLine(strokeOffset, strokeOffset, strokeOffset, getHeight() - strokeOffset);
}
}
@ -488,15 +510,15 @@ public class StartupPageWorkspacePanel extends JPanel {
@Override
public void mouseEntered(MouseEvent e) {
borderColorRef.set(HOVER_COLOR);
selectAndCreatePanel.getParent().repaint();
label.setIcon(IconUtils.readIcon("/com/fr/design/standard/system/add_hover.svg"));
repaintAll();
}
@Override
public void mouseExited(MouseEvent e) {
borderColorRef.set(null);
selectAndCreatePanel.getParent().repaint();
label.setIcon(IconUtils.readIcon("/com/fr/design/standard/system/add.svg"));
repaintAll();
}
@Override
public void mousePressed(MouseEvent e) {
@ -515,4 +537,47 @@ public class StartupPageWorkspacePanel extends JPanel {
this.selectWorkspaceRunnable = selectWorkspaceRunnable;
}
private void doOpenEmptyTemplate(StartupWorkspaceBean workspaceInfo) {
pageModel.setSelectWorkspaceInfo(workspaceInfo);
openEmptyTemplateRunnable.run();
DesignerMetrics designerMetrics = DesignerStartupContext.getInstance().getDesignerMetrics();
designerMetrics.getStatistic().recordOpenEmptyTemplate();
}
private void doSwitchWorkspace(StartupWorkspaceBean workspaceInfo) {
StartupWorkspaceBean lastWorkspaceInfo = pageModel.getSelectWorkspaceInfo();
// selectWorkspaceRunnable
pageModel.setSelectWorkspaceInfo(workspaceInfo);
selectWorkspaceRunnable.run();
DesignerMetrics designerMetrics = DesignerStartupContext.getInstance().getDesignerMetrics();
designerMetrics.getStatistic().recordSwitchWorkspace(lastWorkspaceInfo, workspaceInfo);
}
private void doShowAllAction(UILabel fontLabel, UILabel iconLabel) {
if (showMore) {
fontLabel.setText(Toolkit.i18nText("Fine-Design_Startup_Page_Collapse_Workspace"));
iconLabel.setIcon(IconUtils.readIcon("/com/fr/design/startup/show_less.svg"));
showMoreContent();
showMore = !showMore;
} else {
fontLabel.setText(Toolkit.i18nText("Fine-Design_Startup_Page_Expand_All"));
iconLabel.setIcon(IconUtils.readIcon("/com/fr/design/startup/show_more.svg"));
showLessContent();
showMore = !showMore;
}
DesignerMetrics designerMetrics = DesignerStartupContext.getInstance().getDesignerMetrics();
designerMetrics.getStatistic().recordShowAllAction();
repaintAll();
}
private void repaintAll() {
this.getRootPane().repaint();
}
}

BIN
designer-base/src/main/resources/com/fr/design/startup/startup_page_background.jpg

Binary file not shown.

After

Width:  |  Height:  |  Size: 197 KiB

21
designer-base/src/test/java/com/fr/startup/ui/StartupPageUtilTest.java

@ -0,0 +1,21 @@
package com.fr.startup.ui;
import org.junit.Assert;
import org.junit.Test;
import static org.junit.Assert.*;
public class StartupPageUtilTest {
@Test
public void testGetRemoteAddress() throws Exception {
String remoteAddress = StartupPageUtil.getRemoteAddress("https://localhost:9090/webroot");
Assert.assertEquals("localhost:9090", remoteAddress);
String remoteAddress1 = StartupPageUtil.getRemoteAddress("https://localhost/webroot");
Assert.assertEquals("localhost", remoteAddress1);
String remoteAddress2 = StartupPageUtil.getRemoteAddress(null);
Assert.assertEquals("", remoteAddress2);
}
}

16
designer-form/src/main/java/com/fr/design/designer/creator/cardlayout/XWCardTagLayout.java

@ -35,6 +35,7 @@ import com.fr.general.act.BorderPacker;
import com.fr.general.ComparatorUtils;
import com.fr.general.FRFont;
import com.fr.general.cardtag.DefaultTemplateStyle;
import com.fr.stable.StringUtils;
import javax.swing.border.Border;
import java.awt.*;
@ -132,14 +133,16 @@ public class XWCardTagLayout extends XWHorizontalBoxLayout {
}
int index = this.cardLayout.toData().getWidgetCount();
//新加一个card
String widgetName = tagName + getTabNameIndex();
//新加一个card,命名规则是tabxy,x为tablayout中tab的index,y为模板中tablayout 的index
String widgetName = tagName + getTabNameIndex() + getCardLayoutSuffix(cardLayout.toData().getWidgetName(), cardLayout.createDefaultName());
WTabFitLayout fitLayout = new WTabFitLayout(widgetName, tabFitIndex, currentCard);
fitLayout.setTabNameIndex(getTabNameIndex());
XWTabFitLayout tabFitLayout = new XWTabFitLayout(fitLayout, new Dimension());
FormDesigner formDesigner = WidgetPropertyPane.getInstance().getEditingFormDesigner();
ModelUtil.renameWidgetName(formDesigner.getTarget(), tabFitLayout);
if (formDesigner.getTarget().isNameExist(widgetName)) {
ModelUtil.renameWidgetName(formDesigner.getTarget(), tabFitLayout);
}
WCardTagLayout layout = (WCardTagLayout) this.toData();
if(!ComparatorUtils.equals(layout.getTemplateStyle().getStyle(), DefaultTemplateStyle.DEFAULT_TEMPLATE_STYLE)){
@ -154,6 +157,13 @@ public class XWCardTagLayout extends XWHorizontalBoxLayout {
cardLayout.showCard();
}
private String getCardLayoutSuffix(String cardLayoutName, String defaultName){
if (StringUtils.isEmpty(cardLayoutName) || StringUtils.isEmpty(defaultName) || !cardLayoutName.contains(defaultName)){
return StringUtils.EMPTY;
}
return cardLayoutName.substring(defaultName.length());
}
@Override
protected String getIconName() {

8
designer-realize/src/main/java/com/fr/design/actions/server/WidgetManagerAction.java

@ -1,16 +1,15 @@
package com.fr.design.actions.server;
import com.fr.base.svg.IconUtils;
import com.fr.design.DesignModelAdapter;
import com.fr.design.actions.UpdateAction;
import com.fr.design.dialog.BasicDialog;
import com.fr.design.dialog.DialogActionAdapter;
import com.fr.design.mainframe.DesignerContext;
import com.fr.design.mainframe.DesignerFrame;
import com.fr.design.mainframe.JTemplate;
import com.fr.design.menu.MenuKeySet;
import com.fr.design.webattr.WidgetManagerPane;
import com.fr.form.ui.WidgetInfoConfig;
import com.fr.transaction.CallBackAdaptor;
import com.fr.transaction.Configurations;
import com.fr.transaction.WorkerFacade;
@ -61,7 +60,10 @@ public class WidgetManagerAction extends UpdateAction {
if (model != null) {
model.widgetConfigChanged();
}
designerFrame.getSelectedJTemplate().refreshToolArea();
JTemplate<?, ?> jt = designerFrame.getSelectedJTemplate();
if (JTemplate.isValid(jt)) {
jt.refreshToolArea();
}
}
}));
}

4
designer-realize/src/main/java/com/fr/design/deeplink/FileOpen4MacDeepLink.java

@ -4,6 +4,7 @@ import com.fr.design.mainframe.DesignerContext;
import com.fr.file.FileFILE;
import com.fr.stable.StringUtils;
import com.fr.stable.os.OperatingSystem;
import com.fr.start.common.DesignerStartupUtil;
import java.io.File;
import java.util.Map;
@ -23,6 +24,9 @@ public class FileOpen4MacDeepLink extends DeepLink {
public void run(String url, String host, String path, Map<String, Object> params) {
File file = new File(url);
if (file.exists()) {
if (DesignerStartupUtil.openTemplateIfOnWaiting(file)) {
return;
}
DesignerContext.getDesignerFrame().openTemplate(new FileFILE(file));
}
}

2
designer-realize/src/main/java/com/fr/design/mainframe/ElementCasePaneDelegate.java

@ -86,7 +86,7 @@ public class ElementCasePaneDelegate extends ElementCasePane<WorkSheet> {
QuickEditorRegion.getInstance().populate(getCurrentEditor());
JTemplate editingTemplate = HistoryTemplateListPane.getInstance().getCurrentEditingTemplate();
// 模板初始化完成后,才能初始化超级链接面板
if (editingTemplate != null && !editingTemplate.isUpMode()) {
if (JTemplate.isValid(editingTemplate) && !editingTemplate.isUpMode()) {
Selection editingSelection = getSelection();
// 获取超级链接面板并刷新显示
HyperlinkGroupPane hyperlinkGroupPane = editingTemplate.getHyperLinkPane(HyperlinkGroupPaneActionImpl.getInstance());

22
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/AlphaFineConstants.java

@ -5,8 +5,9 @@ import com.fr.base.svg.IconUtils;
import com.fr.design.i18n.Toolkit;
import com.fr.design.utils.DesignUtils;
import com.fr.general.CloudCenter;
import com.fr.general.IOUtils;
import javax.swing.Icon;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
@ -14,7 +15,6 @@ import java.util.ArrayList;
import java.util.Arrays;
import java.util.LinkedHashSet;
import java.util.Set;
import javax.swing.Icon;
/**
@ -81,6 +81,8 @@ public class AlphaFineConstants {
public static final Color WHITE = new Color(0xf9f9f9);
public static final Color LABEL_SELECTED = new Color(0x419bf9);
public static final Color GRAY = new Color(0xd2d2d2);
public static final Color LIGHT_GRAY = new Color(0xcccccc);
@ -154,9 +156,21 @@ public class AlphaFineConstants {
public static final String ALPHA_PREVIEW = CloudCenter.getInstance().acquireUrlByKind("af.preview");
public static final String ALPHA_CID = CloudCenter.getInstance().acquireUrlByKind("af.cid", "https://cid.fanruan.com/api/nav/alphafine");
public static final String ALPHA_CID = CloudCenter.getInstance().acquireUrlByKind("af.cid.new");
public static final String ALPHA_CID_USER_GROUP_INFO = CloudCenter.getInstance().acquireUrlByKind("af.cid.user.group.info");
public static final String SEARCH_BY_ID = "?id=";
private static final String QUICK_START_URL = CloudCenter.getInstance().acquireUrlByKind("af.help.quick.start");
private static final String REPORT_LEARNING_PATH = CloudCenter.getInstance().acquireUrlByKind("af.help.report.learning.path");
private static final String PARAMETER_LEARNING_PATH = CloudCenter.getInstance().acquireUrlByKind("af.help.param.learning.path");
private static final String FILL_LEARNING_PATH = CloudCenter.getInstance().acquireUrlByKind("af.help.fill.learning.path");
private static final String API_SUMMARY = CloudCenter.getInstance().acquireUrlByKind("af.help.api.summary");
private static final String MONTHLY_DOCUMENT = CloudCenter.getInstance().acquireUrlByKind("af.help.monthly.document");
private static final String DEFAULT_RECOMMEND = "[ { \"name\":\"快速入门指南\", \"link\":\"https://help.fanruan.com/finereport/doc-view-1335.html?source=3\" }, { \"name\":\"报表应用学习路径\", \"link\":\"https://help.fanruan.com/finereport/doc-view-1336.html?source=3\" }, { \"name\":\"参数应用学习路径\", \"link\":\"https://help.fanruan.com/finereport/doc-view-4219.html?source=3\" }, { \"name\":\"填报学习路径\", \"link\":\"https://help.fanruan.com/finereport/doc-view-4103.html?source=3\" }, { \"name\":\"API接口汇总\", \"link\":\"https://help.fanruan.com/finereport/doc-view-4327.html?source=3\" }, { \"name\":\"文档月刊\", \"link\":\"https://help.fanruan.com/finereport/doc-view-4613.html?source=3\" } ]";
private static final String DEFAULT_RECOMMEND = "[ { \"name\":\"快速入门指南\", \"link\":\"" + QUICK_START_URL + "\" }, { \"name\":\"报表应用学习路径\", \"link\":\"" + REPORT_LEARNING_PATH + "\" }, { \"name\":\"参数应用学习路径\", \"link\":\"" + PARAMETER_LEARNING_PATH + "\" }, { \"name\":\"填报学习路径\", \"link\":\"" + FILL_LEARNING_PATH + "\" }, { \"name\":\"API接口汇总\", \"link\":\"" + API_SUMMARY + "\" }, { \"name\":\"文档月刊\", \"link\":\"" + MONTHLY_DOCUMENT + "\" } ]";
public static final String ALPHA_HELP_RECOMMEND = CloudCenter.getInstance().acquireUrlByKind("af.recommend", DEFAULT_RECOMMEND);

18
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/CellType.java

@ -17,7 +17,8 @@ public enum CellType {
RECOMMEND_ROBOT(8),
BOTTOM(9),
ROBOT(10),
PRODUCT_NEWS(11, "productNews", "productNewsResult", true);
PRODUCT_NEWS(11, "productNews", "productNewsResult", true, false),
TEMPLATE_SHOP(12, "templateShop", "templateShop", false, true);
private int typeValue;
@ -35,11 +36,19 @@ public enum CellType {
private boolean needNetWork = true;
CellType(int type, String flagStr4None, String flagStr4Result, boolean needNetWork) {
private boolean canLocalSearch = false;
CellType(int type, String flagStr4None, String flagStr4Result, boolean needNetWork, boolean canLocalSearch) {
this.typeValue = type;
this.flagStr4None = flagStr4None;
this.flagStr4Result = flagStr4Result;
this.needNetWork = needNetWork;
this.canLocalSearch = canLocalSearch;
}
CellType(int type, String flagStr4None, String flagStr4Result, boolean needNetWork) {
this(type, flagStr4None, flagStr4Result, needNetWork, false);
}
CellType(int type) {
@ -75,5 +84,8 @@ public enum CellType {
public boolean isNeedNetWork() {
return needNetWork;
}
}
public boolean isCanLocalSearch() {
return canLocalSearch;
}
}

29
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/action/StartUseAction.java

@ -0,0 +1,29 @@
package com.fr.design.mainframe.alphafine.action;
import com.fr.design.mainframe.alphafine.model.TemplateResourceDetail;
import com.fr.design.mainframe.alphafine.search.helper.FineMarketClientHelper;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
/**
* alphaFine - 模板资源 - 二级界面 - 开始使用按钮的绑定事件
*
* 点击后跳转至帆软市场下载对应模板资源
*
* TODO:可以参考mini组件商城的下载@ComponentsPackageInstallation#install
* */
public class StartUseAction implements ActionListener {
TemplateResourceDetail resourceDetail;
public StartUseAction(TemplateResourceDetail detail) {
this.resourceDetail = detail;
}
@Override
public void actionPerformed(ActionEvent e) {
FineMarketClientHelper.getInstance().openBrowserAndDownload(resourceDetail.getRoot());
}
}

303
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/AlphaFineFrame.java

@ -22,20 +22,34 @@ import com.fr.design.mainframe.alphafine.preview.NoResultPane;
import com.fr.design.mainframe.alphafine.preview.NoResultWithLinkPane;
import com.fr.design.mainframe.alphafine.preview.SearchLoadingPane;
import com.fr.design.mainframe.alphafine.preview.SimpleRightSearchResultPane;
import com.fr.design.mainframe.alphafine.preview.TemplateShopPane;
import com.fr.design.mainframe.alphafine.question.QuestionWindow;
import com.fr.design.mainframe.alphafine.search.ProductNewsSearchWorkerManager;
import com.fr.design.mainframe.alphafine.search.SearchTextBean;
import com.fr.design.mainframe.alphafine.search.SearchWorkerManager;
import com.fr.design.mainframe.alphafine.search.TemplateResourceSearchWorkerManager;
import com.fr.design.mainframe.alphafine.search.manager.impl.ActionSearchManager;
import com.fr.design.mainframe.alphafine.search.manager.impl.DocumentSearchManager;
import com.fr.design.mainframe.alphafine.search.manager.impl.FileSearchManager;
import com.fr.design.mainframe.alphafine.search.manager.impl.PluginSearchManager;
import com.fr.design.mainframe.alphafine.search.manager.impl.ProductNewsSearchManager;
import com.fr.design.mainframe.alphafine.search.manager.impl.SegmentationManager;
import com.fr.design.mainframe.alphafine.search.manager.impl.TemplateResourceSearchManager;
import com.fr.design.utils.DesignUtils;
import com.fr.design.utils.gui.GUICoreUtils;
import com.fr.general.ComparatorUtils;
import com.fr.stable.StringUtils;
import javax.swing.BorderFactory;
import javax.swing.Icon;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JPopupMenu;
import javax.swing.SwingConstants;
import javax.swing.Timer;
import javax.swing.event.PopupMenuEvent;
import javax.swing.event.PopupMenuListener;
import java.awt.BorderLayout;
import java.awt.CardLayout;
import java.awt.Color;
@ -62,16 +76,6 @@ import java.util.List;
import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.swing.BorderFactory;
import javax.swing.Icon;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JPopupMenu;
import javax.swing.SwingConstants;
import javax.swing.Timer;
import javax.swing.event.PopupMenuEvent;
import javax.swing.event.PopupMenuListener;
/**
* @author hades
@ -98,7 +102,7 @@ public class AlphaFineFrame extends JFrame {
private static final String PLACE_HOLDER = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_AlphaFine");
private static final String SETTING = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_Set");
private static final String FUNCTION = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_Function");
private static final String NO_RESULT = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_No_Result");
@ -110,7 +114,7 @@ public class AlphaFineFrame extends JFrame {
private static final String GO_FORUM = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_AlphaFine_Go_Forum");
private static final String TEMPLATES = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_Templates");
private static final String MY_TEMPLATES = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_My_Templates");
public static final String PRODUCT_NEWS = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_AlphaFine_Product_News");
@ -122,7 +126,7 @@ public class AlphaFineFrame extends JFrame {
private static final String NO_SEARCH_RESULT = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_AlphaFine_NO_Result");
private static final String PRODUCT_DYNAMICS = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_AlphaFine_Product_Dynamics");
private static final String TEMPLATE_SHOP = com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Shop");
private static final Image SEARCH_IMAGE = SVGLoader.load("/com/fr/design/mainframe/alphafine/images/search.svg");
@ -152,7 +156,19 @@ public class AlphaFineFrame extends JFrame {
private JPanel tabPane;
private CellType selectedType;
private JPanel labelPane;
private JPanel labelContentPane;
private JPanel labelEastPane;
private JPanel labelWestPane;
private UILabel tabLabel;
private UILabel readLabel;
private SelectedLabel selectedTab;
private String beforeSearchStr = StringUtils.EMPTY;
@ -168,15 +184,38 @@ public class AlphaFineFrame extends JFrame {
private ProductNewsSearchWorkerManager productNewsSearchWorkerManager;
private TemplateResourceSearchWorkerManager templateResourceSearchWorkerManager;
public AlphaFineFrame() {
this.setTitle(AlphaFineConstants.TITLE);
//去掉边框
setUndecorated(true);
setSize(AlphaFineConstants.FIELD_SIZE);
setSize(AlphaFineConstants.FULL_SIZE);
initComponents();
centerWindow(this);
initSearchManager();
}
public void showResult(String flag) {
cardLayout.show(resultPane, flag);
}
public void addResult(JPanel panel, String flag) {
resultPane.add(panel, flag);
}
public void removeSearchResultPane(JPanel panel) {
resultPane.remove(panel);
}
public String getSearchText() {
return searchTextField.getText();
}
public CellType getSelectedType() {
return selectedTab.getCellType();
}
private void initSearchManager() {
this.productNewsSearchWorkerManager = new ProductNewsSearchWorkerManager(
@ -213,20 +252,26 @@ public class AlphaFineFrame extends JFrame {
new LoadingRightSearchResultPane()
);
this.templateResourceSearchWorkerManager = new TemplateResourceSearchWorkerManager(
CellType.TEMPLATE_SHOP,
searchTextBean -> {
return TemplateResourceSearchManager.getInstance().getSearchResult(searchTextBean.getSearchText());
},
this
);
}
/**
* 初始化全部组件
*/
private void initComponents() {
add(createTopPane(), BorderLayout.NORTH);
initSearchTextField();
add(createSearchPane(), BorderLayout.CENTER);
add(createShowPane(), BorderLayout.SOUTH);
this.getContentPane().setBackground(Color.WHITE);
this.setIconImage(SEARCH_IMAGE);
this.setSize(AlphaFineConstants.FULL_SIZE);
this.setIconImage(SEARCH_IMAGE); // 应用图标
}
private JPanel createTopPane() {
@ -289,7 +334,6 @@ public class AlphaFineFrame extends JFrame {
}
};
private JPopupMenu createTipPop() {
JPanel panel = new JPanel(new BorderLayout());
String toolTip = AlphaFineShortCutUtil.getDisplayShortCut(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Report_AlphaFine_Short_Cut", DesignerEnvManager.getEnvManager().getAlphaFineConfigManager().getShortcuts()));
@ -372,29 +416,39 @@ public class AlphaFineFrame extends JFrame {
return searchPane;
}
/**
* showPane,内容展示区分为三个小区tab区label区内容区
* */
private JPanel createShowPane() {
JPanel showPane = new JPanel(new BorderLayout());
// 内容区,card layout
resultPane.add(new DefaultProductNewsPane(), CellType.PRODUCT_NEWS.getFlagStr4None());
resultPane.add(new NoResultWithLinkPane(GO_FORUM, AlphaFineConstants.NO_RESULT_ICON), CellType.NO_RESULT.getFlagStr4None());
resultPane.add(new NoResultPane(SEARCH_TERM, AlphaFineConstants.NO_RESULT_ICON), CellType.ACTION.getFlagStr4None());
resultPane.add(new NoResultPane(SEARCH_TERM, AlphaFineConstants.NO_RESULT_ICON), CellType.FILE.getFlagStr4None());
resultPane.add(new NoResultPane(SEARCH_TERM, AlphaFineConstants.NO_RESULT_ICON), CellType.PLUGIN.getFlagStr4None());
resultPane.add(new HelpDocumentNoResultPane(SEARCH_TERM, AlphaFineConstants.NO_RESULT_ICON), CellType.DOCUMENT.getFlagStr4None());
resultPane.add(TemplateShopPane.getInstance(), CellType.TEMPLATE_SHOP.getFlagStr4None());
resultPane.add(new NetWorkFailedPane(this::reSearch), AlphaFineConstants.NETWORK_ERROR);
JPanel labelPane = new JPanel(new BorderLayout());
// label区,border layout
labelPane = new JPanel(new BorderLayout());
labelPane.setBorder(BorderFactory.createEmptyBorder(0, 20, 0, 20));
labelPane.setBackground(Color.WHITE);
JPanel labelContentPane = new JPanel(new BorderLayout());
UILabel tabLabel = new UILabel(PRODUCT_DYNAMICS);
labelContentPane = new JPanel(new BorderLayout());
tabLabel = new UILabel(PRODUCT_NEWS);
tabLabel.setForeground(AlphaFineConstants.FOREGROUND_COLOR_6);
tabLabel.setBorder(BorderFactory.createEmptyBorder(0, 10, 0, 0));
tabLabel.setPreferredSize(new Dimension(100, 30));
JPanel westPane = new JPanel(new FlowLayout(FlowLayout.LEFT, 0, 0));
westPane.add(tabLabel);
labelContentPane.add(westPane, BorderLayout.WEST);
JPanel eastPane = new JPanel(new FlowLayout(FlowLayout.RIGHT, 0, 0));
UILabel readLabel = new UILabel(ONE_CLICK_READ);
tabLabel.setPreferredSize(new Dimension(60, 30));
tabLabel.setForeground(AlphaFineConstants.LABEL_SELECTED);
labelWestPane = new JPanel(new FlowLayout(FlowLayout.LEFT, 0, 0));
labelWestPane.add(tabLabel);
labelContentPane.add(labelWestPane, BorderLayout.WEST);
labelEastPane = new JPanel(new FlowLayout(FlowLayout.RIGHT, 0, 0));
// 一键已读
readLabel = new UILabel(ONE_CLICK_READ);
readLabel.setHorizontalAlignment(SwingConstants.RIGHT);
readLabel.setBorder(BorderFactory.createEmptyBorder(0, 0, 0, 10));;
readLabel.setPreferredSize(new Dimension(100, 30));
@ -406,24 +460,30 @@ public class AlphaFineFrame extends JFrame {
showPane.repaint();
}
});
eastPane.add(readLabel);
labelContentPane.add(eastPane, BorderLayout.EAST);
labelEastPane.add(readLabel);
labelContentPane.add(labelEastPane, BorderLayout.EAST);
labelContentPane.setBackground(new Color(245, 245, 247));
labelPane.add(labelContentPane);
labelPane.setPreferredSize(new Dimension(AlphaFineConstants.FULL_SIZE.width, 30));
// tab区 flow layout
tabPane = new JPanel(new FlowLayout(FlowLayout.LEFT, 20, 10));
tabPane.setBackground(Color.WHITE);
List<SelectedLabel> selectedLabelList = createSelectedLabelList();
selectedType = selectedLabelList.get(0).getCellType();
// 第一个tab 非产品动态
if (selectedType != CellType.PRODUCT_NEWS) {
tabLabel.setText(selectedLabelList.get(0).getText());
selectedTab = null;
for (SelectedLabel label : selectedLabelList) {
if (label.isSelected()) {
selectedTab = label;
break;
}
}
if (this.selectedTab.getCellType() != CellType.PRODUCT_NEWS) {
tabLabel.setText(this.selectedTab.getText());
readLabel.setVisible(false);
}
for (SelectedLabel selectedLabel : selectedLabelList) {
selectedLabel.addMouseListener(createMouseListener(selectedLabelList, selectedLabel, tabPane, tabLabel, readLabel));
tabPane.add(selectedLabel);
for (SelectedLabel label : selectedLabelList) {
label.addMouseListener(createMouseListener(selectedLabelList, label, tabPane, tabLabel, readLabel));
tabPane.add(label);
}
showPane.add(tabPane, BorderLayout.NORTH);
showPane.add(labelPane, BorderLayout.CENTER);
@ -431,46 +491,47 @@ public class AlphaFineFrame extends JFrame {
return showPane;
}
public JPanel getLabelWestPane() {
return labelWestPane;
}
public UILabel getTabLabel() {
return tabLabel;
}
private MouseAdapter createMouseListener(List<SelectedLabel> selectedLabelList, SelectedLabel selectedLabel,
JPanel tabPane, UILabel tabLabel, UILabel readLabel) {
return new MouseAdapter() {
@Override
public void mousePressed(MouseEvent e) {
// tab栏里的label全设置为没选中,并设置颜色为灰色
for (SelectedLabel label : selectedLabelList) {
label.setSelected(false);
label.setForeground(AlphaFineConstants.FOREGROUND_COLOR_8);
}
// 选中
selectedLabel.setSelected(true);
AlphaFineFrame.this.selectedTab = selectedLabel;
// 处理产品动态 tab与下方文字展示不一致
if (ComparatorUtils.equals(selectedLabel.getText().trim(), PRODUCT_NEWS)) {
tabLabel.setText(PRODUCT_DYNAMICS);
tabLabel.setText(PRODUCT_NEWS);
} else {
tabLabel.setText(selectedLabel.getText());
}
// 刷新westlabelpane
refreshLabelPane();
// 将已读设置不可见
readLabel.setVisible(false);
// tab栏重新绘制
tabPane.repaint();
switch (selectedLabel.getCellType()) {
case PRODUCT_NEWS:
readLabel.setVisible(true);
switchType(CellType.PRODUCT_NEWS);
break;
case ACTION:
currentSearchWorkerManager = settingSearchWorkerManager;
switchType(CellType.ACTION);
break;
case FILE:
currentSearchWorkerManager = fileSearchWorkerManager;
switchType(CellType.FILE);
break;
case DOCUMENT:
currentSearchWorkerManager = documentWorkerManager;
switchType(CellType.DOCUMENT);
break;
case PLUGIN:
currentSearchWorkerManager = pluginSearchWorkerManager;
switchType(CellType.PLUGIN);
break;
}
// 选中事件
switchTab(selectedLabel.getCellType(), readLabel);
if (currentSearchWorkerManager != null) {
AlphaFineList alphaFineList = currentSearchWorkerManager.getSearchResultList();
if (alphaFineList != null) {
@ -494,17 +555,51 @@ public class AlphaFineFrame extends JFrame {
};
}
// 方便记埋点
private void switchTab(CellType cellType, UILabel readLabel) {
switch (cellType) {
case PRODUCT_NEWS:
readLabel.setVisible(true);
switchType(CellType.PRODUCT_NEWS);
break;
case ACTION:
currentSearchWorkerManager = settingSearchWorkerManager;
switchType(CellType.ACTION);
break;
case FILE:
currentSearchWorkerManager = fileSearchWorkerManager;
switchType(CellType.FILE);
break;
case DOCUMENT:
currentSearchWorkerManager = documentWorkerManager;
switchType(CellType.DOCUMENT);
break;
case PLUGIN:
currentSearchWorkerManager = pluginSearchWorkerManager;
switchType(CellType.PLUGIN);
break;
case TEMPLATE_SHOP:
TemplateShopPane.getInstance().showPagePane();
switchType(CellType.TEMPLATE_SHOP);
break;
}
}
private void refreshLabelPane() {
labelWestPane.removeAll();
labelWestPane.add(tabLabel);
}
private List<SelectedLabel> createSelectedLabelList() {
List<SelectedLabel> selectedLabelList = new ArrayList<>();
AlphaFineConfigManager alphaFineConfigManager = DesignerEnvManager.getEnvManager().getAlphaFineConfigManager();
if (alphaFineConfigManager.isProductDynamics()) {
selectedLabelList.add(new SelectedLabel(PRODUCT_NEWS, CellType.PRODUCT_NEWS, true));
selectedLabelList.add(new SelectedLabel(PRODUCT_NEWS, CellType.PRODUCT_NEWS));
}
if (alphaFineConfigManager.isContainAction()) {
selectedLabelList.add(new SelectedLabel(SETTING, CellType.ACTION));
}
if (alphaFineConfigManager.isContainFileContent() || alphaFineConfigManager.isContainTemplate()) {
selectedLabelList.add(new SelectedLabel(TEMPLATES, CellType.FILE));
// 默认选中模板商城
if (alphaFineConfigManager.hasTemplateShop()) {
selectedLabelList.add(new SelectedLabel(TEMPLATE_SHOP, CellType.TEMPLATE_SHOP, true));
}
if (alphaFineConfigManager.isContainDocument()) {
selectedLabelList.add(new SelectedLabel(HELP, CellType.DOCUMENT));
@ -512,6 +607,19 @@ public class AlphaFineFrame extends JFrame {
if (alphaFineConfigManager.isContainPlugin()) {
selectedLabelList.add(new SelectedLabel(PLUGIN, CellType.PLUGIN));
}
if (alphaFineConfigManager.isContainAction()) {
selectedLabelList.add(new SelectedLabel(FUNCTION, CellType.ACTION));
}
if (alphaFineConfigManager.isContainMyTemplate()) {
selectedLabelList.add(new SelectedLabel(MY_TEMPLATES, CellType.FILE));
}
// 如果不展示模板商城,则list中第一个被选中
if (!alphaFineConfigManager.hasTemplateShop() && !selectedLabelList.isEmpty()) {
selectedLabelList.get(0).setSelected(true);
}
return selectedLabelList;
}
@ -524,7 +632,6 @@ public class AlphaFineFrame extends JFrame {
}
private void switchType(CellType cellType) {
this.selectedType = cellType;
if (StringUtils.isEmpty(searchTextField.getText())) {
cardLayout.show(resultPane, cellType.getFlagStr4None());
} else {
@ -541,8 +648,7 @@ public class AlphaFineFrame extends JFrame {
if (checkNetworkError()) {
return;
}
cardLayout.show(resultPane, cellType.getFlagStr4Result());
showResult(cellType.getFlagStr4Result());
checkSearchResult();
}
@ -550,23 +656,23 @@ public class AlphaFineFrame extends JFrame {
private boolean checkNetworkError() {
boolean networkError;
if (selectedType == CellType.PRODUCT_NEWS) {
if (selectedTab.getCellType() == CellType.PRODUCT_NEWS) {
networkError = productNewsSearchWorkerManager.isNetWorkError();
} else {
networkError = currentSearchWorkerManager.isNetWorkError();
}
cardLayout.show(resultPane, AlphaFineConstants.NETWORK_ERROR);
showResult(AlphaFineConstants.NETWORK_ERROR);
return networkError;
}
private boolean checkSearchLoading() {
boolean searchOver;
if (selectedType == CellType.PRODUCT_NEWS) {
if (selectedTab.getCellType() == CellType.PRODUCT_NEWS) {
searchOver = productNewsSearchWorkerManager.isSearchOver();
} else {
searchOver = currentSearchWorkerManager.isSearchOver();
}
cardLayout.show(resultPane, AlphaFineConstants.LOADING);
showResult(AlphaFineConstants.LOADING);
return searchOver;
}
@ -587,14 +693,14 @@ public class AlphaFineFrame extends JFrame {
searchResultList.requestFocus();
}
boolean hasSearchResult = true;
if (selectedType == CellType.PRODUCT_NEWS) {
if (selectedTab.getCellType() == CellType.PRODUCT_NEWS) {
hasSearchResult = productNewsSearchWorkerManager.hasSearchResult();
} else {
hasSearchResult = currentSearchWorkerManager.hasSearchResult();
}
if (!hasSearchResult) {
cardLayout.show(resultPane, CellType.NO_RESULT.getFlagStr4None());
showResult(CellType.NO_RESULT.getFlagStr4None());
}
}
@ -608,7 +714,6 @@ public class AlphaFineFrame extends JFrame {
searchTextField.setBorder(null);
}
private void initTextFieldListener() {
searchTextField.addKeyListener(new KeyAdapter() {
@Override
@ -659,20 +764,24 @@ public class AlphaFineFrame extends JFrame {
}
/**
* 控制搜索tip框弹出收起
* 不断地刷新tab页并防止tab页显示错误
* */
private void startSearchTextFieldTimer() {
Timer timer = new Timer(TIMER_DELAY, e -> {
// 坑 isShowing返回false 即使textField有内容 getText返回的也是空
if (searchTextField.isShowing() && StringUtils.isEmpty(searchTextField.getText())) {
SearchTooltipPopup.getInstance().hide();
clearLabel.setVisible(false);
switchType(selectedType);
switchType(selectedTab.getCellType());
TemplateShopPane.getInstance().quitSearchResultPane();
beforeSearchStr = StringUtils.EMPTY;
} else if (searchTextField.hasFocus()) {
clearLabel.setVisible(true);
SearchTooltipPopup.getInstance().show(searchTextFieldWrapperPane);
}
tabPane.repaint();
});
timer.start();
}
@ -751,21 +860,8 @@ public class AlphaFineFrame extends JFrame {
}
}
public void showResult(String flag) {
cardLayout.show(resultPane, flag);
}
public void addResult(JPanel panel, String flag) {
resultPane.add(panel, flag);
}
public void removeSearchResultPane(JPanel panel) {
resultPane.remove(panel);
}
private void doSearch(String text) {
refreshLabelPane();
initSearchLoadingPane();
SearchTextBean searchTextBean = generateSearchTextBean(text);
this.productNewsSearchWorkerManager.doSearch(searchTextBean);
@ -773,6 +869,7 @@ public class AlphaFineFrame extends JFrame {
this.fileSearchWorkerManager.doSearch(searchTextBean);
this.documentWorkerManager.doSearch(searchTextBean);
this.pluginSearchWorkerManager.doSearch(searchTextBean);
this.templateResourceSearchWorkerManager.doSearch(searchTextBean);
}
private SearchTextBean generateSearchTextBean(String searchText) {
@ -806,25 +903,15 @@ public class AlphaFineFrame extends JFrame {
this.pluginSearchWorkerManager.doSearch(searchTextBean);
}
/**
* 所有tab页搜索通用的加载panel
* */
private void initSearchLoadingPane() {
if (searchLoadingPane == null) {
searchLoadingPane = new SearchLoadingPane();
}
resultPane.add(searchLoadingPane, AlphaFineConstants.LOADING);
cardLayout.show(resultPane, AlphaFineConstants.LOADING);
}
public String getSearchText() {
return searchTextField.getText();
}
public CellType getSelectedType() {
return selectedType;
}
public void setStoreText(String storeText) {
this.storeText = storeText;
showResult(AlphaFineConstants.LOADING);
}
/**
@ -839,6 +926,9 @@ public class AlphaFineFrame extends JFrame {
return storeText;
}
public void setStoreText(String storeText) {
this.storeText = storeText;
}
/**
* 去除特殊字符空格等
@ -894,6 +984,7 @@ public class AlphaFineFrame extends JFrame {
@Override
public void setVisible(boolean b) {
super.setVisible(b);
switchTab(selectedTab.getCellType(), readLabel);
QuestionWindow.getInstance().setVisible(!b);
if (!b) {
AlphaFineHelper.resetAlphaFineDialog();

16
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/ProductNewsList.java

@ -5,18 +5,15 @@ import com.fr.design.mainframe.alphafine.AlphaFineConstants;
import com.fr.design.mainframe.alphafine.AlphaFineHelper;
import com.fr.design.mainframe.alphafine.model.ProductNews;
import com.fr.design.utils.BrowseUtils;
import com.fr.log.FineLoggerFactory;
import javax.swing.DefaultListModel;
import javax.swing.JList;
import javax.swing.ListModel;
import java.awt.Cursor;
import java.awt.Desktop;
import java.awt.Point;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionAdapter;
import java.net.URI;
import javax.swing.DefaultListModel;
import javax.swing.JList;
import javax.swing.ListModel;
/**
* @author hades
@ -64,11 +61,16 @@ public class ProductNewsList extends JList<ProductNews> {
private void dealWithClick() {
ProductNews productNews = getSelectedValue();
BrowseUtils.browser(productNews.getUrl());
openNewsInBrowser(productNews.getUrl());
DesignerEnvManager.getEnvManager().getAlphaFineConfigManager().getReadSet().add(productNews.getId());
AlphaFineHelper.getAlphaFineDialog().repaint();
}
// 方便埋点
private void openNewsInBrowser(String url) {
BrowseUtils.browser(url);
}
public int getHoverIndex() {
return hoverIndex;
}

74
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/RecommendSearchPane.java

@ -0,0 +1,74 @@
package com.fr.design.mainframe.alphafine.component;
import com.fr.design.i18n.Toolkit;
import com.fr.design.mainframe.alphafine.AlphaFineHelper;
import com.fr.design.mainframe.alphafine.model.TemplateResource;
import javax.swing.BorderFactory;
import javax.swing.JLabel;
import javax.swing.JPanel;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.FlowLayout;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.List;
public class RecommendSearchPane extends TemplateResourcePanel {
private static final Color BORDER_WHITE = new Color(0xe8e8e9);
private static final Color RECOMMEND_SEARCH_KEY_BLUE = new Color(0x419bf9);
public RecommendSearchPane(TemplateResource templateResource) {
super();
setTemplateResource(templateResource);
initComponent();
this.setLayout(new BorderLayout());
this.setBorder(BorderFactory.createLineBorder(BORDER_WHITE, 1));
this.add(getNorthPane(), BorderLayout.NORTH);
this.add(getSouthPane(), BorderLayout.SOUTH);
}
private void initComponent() {
createNorthPane();
createSouthPane();
}
private void createSouthPane() {
setSouthPane(new JPanel(new FlowLayout(FlowLayout.LEFT)));
JPanel southPane = getSouthPane();
southPane.setBackground(Color.WHITE);
JLabel recommend = new JLabel(Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Resource_Recommend_For_You"));
southPane.add(recommend);
List<String> searchKeys = getTemplateResource().getRecommendSearchKey();
for (String key : searchKeys) {
JLabel keyLabel = new SearchKeyLabel(key);
southPane.add(keyLabel);
}
}
class SearchKeyLabel extends JLabel {
String searchKey;
SearchKeyLabel(String searchKey) {
this.searchKey = searchKey;
setText(searchKey);
setBackground(Color.WHITE);
setForeground(RECOMMEND_SEARCH_KEY_BLUE);
addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
AlphaFineHelper.getAlphaFineDialog().fireSearch(searchKey);
}
});
}
}
}

74
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/TemplateResourceImagePanel.java

@ -0,0 +1,74 @@
package com.fr.design.mainframe.alphafine.component;
import com.fr.base.GraphHelper;
import com.fr.design.mainframe.alphafine.model.TemplateResource;
import com.fr.third.jodd.util.StringUtil;
import javax.swing.JPanel;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.RenderingHints;
public class TemplateResourceImagePanel extends JPanel {
private static final int BACKGROUND_HEIGHT = 20;
private static final Color BACKGROUND_COLOR = new Color(116, 181, 249);
private static final Color COVER_COLOR = new Color(116, 181, 249, 26);
private TemplateResource templateResource;
private int width = 200;
private int height = 100;
public TemplateResourceImagePanel(TemplateResource templateResource) {
this.templateResource = templateResource;
}
public TemplateResourceImagePanel(TemplateResource templateResource, int width, int height) {
this(templateResource);
this.width = width;
this.height = height;
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2 = (Graphics2D) g;
g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
Color defaultColor = g2.getColor();
Image image = templateResource.getImage();
if (image != null) {
g2.drawImage(templateResource.getImage(), 0, 0, getWidth(), getHeight(), this);
} else {
g2.setColor(COVER_COLOR);
g2.fillRect(0, 0, getWidth(), getHeight());
}
String tagName = templateResource.getType().getName();
if (!StringUtil.isEmpty(tagName)) {
g2.setColor(BACKGROUND_COLOR);
g2.fillRect(0, getHeight() - BACKGROUND_HEIGHT, getWidth(), BACKGROUND_HEIGHT);
g2.setColor(Color.WHITE);
int x = (getWidth() - GraphHelper.getWidth(tagName, g2.getFont())) / 2;
g2.drawString(tagName, x, getHeight() - 5);
}
g2.setColor(defaultColor);
}
@Override
public Dimension getPreferredSize() {
return new Dimension(width, height);
}
}

225
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/TemplateResourcePageGridPane.java

@ -0,0 +1,225 @@
package com.fr.design.mainframe.alphafine.component;
import com.fr.base.svg.IconUtils;
import com.fr.design.gui.icontainer.UIScrollPane;
import com.fr.design.layout.TableLayoutHelper;
import com.fr.design.mainframe.alphafine.model.TemplateResource;
import javax.swing.BorderFactory;
import javax.swing.JButton;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;
import java.awt.BorderLayout;
import java.awt.CardLayout;
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Label;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
/**
* 卡片布局每个卡片里塞了scrollpanel
* */
public class TemplateResourcePageGridPane extends JPanel {
private List<TemplateResource> data;
private CardLayout cardLayout;
private List<Page> pages;
private int totalPage;
List<UIScrollPane> scrollPanes = new ArrayList<>();
private static final int PAGE_MAX_SIZE = 12;
private static final int TABLE_MAX_ROW_COUNT = 4;
private static final int TABLE_COL_COUNT = 3;
private static final int TABLE_VGAP = 15;
private static final int TABLE_HGAP = 15;
private static final int RESOURCE_WIDTH = 197;
private static final int RESOURCE_HEIGHT = 128;
public TemplateResourcePageGridPane(List<TemplateResource> templateResourceList) {
this.data = templateResourceList;
totalPage = (int) Math.ceil((double)data.size() / PAGE_MAX_SIZE);
createPages();
initComponents();
this.setBackground(Color.WHITE);
this.setBorder(BorderFactory.createEmptyBorder(10, 20, 0, 20));
switchPage(1);
}
private void initComponents() {
cardLayout = new CardLayout();
this.setLayout(cardLayout);
this.setBackground(Color.WHITE);
for (int i = 0; i < pages.size(); i++) {
UIScrollPane scrollPane = new UIScrollPane(pages.get(i));
scrollPanes.add(scrollPane);
this.add(scrollPane, String.valueOf(i + 1));
}
}
/**
* 构建分页将资源切分到每一页并在每一页尾部添加分页按钮
* */
private void createPages() {
int dataCnt = data.size();
List<TemplateResource>[] slice = new ArrayList[totalPage];
for (int i = 0; i < dataCnt; i++) {
int index = i / PAGE_MAX_SIZE;
if (slice[index] == null) {
slice[index] = new ArrayList<>();
}
slice[index].add(data.get(i));
}
pages = new ArrayList<>();
for (int i = 0; i < totalPage; i++) {
pages.add(new Page(slice[i], i + 1));
}
}
private void switchPage(int pageNumber) {
if (pageNumber < 1 || pageNumber > this.totalPage) {
return;
}
cardLayout.show(TemplateResourcePageGridPane.this, String.valueOf(pageNumber));
scrollPanes.get(pageNumber - 1).getVerticalScrollBar().setValue(0);
// 坑,切换页面会刷新失败,需要手动滚动一下才能刷新
scrollPanes.get(pageNumber - 1).getVerticalScrollBar().setValue(1);
scrollPanes.get(pageNumber - 1).getVerticalScrollBar().setValue(0);
}
/**
* 分页panelborderlayout布局north为信息页south为分页按钮区
* */
private class Page extends JPanel {
List<TemplateResource> pageData;
Component[][] comps;
JPanel contentPane;
JPanel pageButtonPane;
JButton prev, next;
JTextField pageNumberField;
JLabel pageCnt;
int pageNumber;
Page(List<TemplateResource> pageData, int pageNumber) {
super();
this.pageData = pageData;
this.pageNumber = pageNumber;
initComponents();
this.setLayout(new BorderLayout());
this.add(contentPane, BorderLayout.NORTH);
if (totalPage > 1) {
this.add(pageButtonPane, BorderLayout.SOUTH);
}
this.setBackground(Color.WHITE);
}
private void initComponents() {
createContentPane();
createPageButtonPane();
}
void createContentPane() {
int dataCnt = pageData.size();
int rowCnt = (int) Math.ceil((double)dataCnt / 3);
double[] rowHeight = new double[rowCnt];
double[] colWidth = new double[TABLE_COL_COUNT];
Arrays.fill(rowHeight, RESOURCE_HEIGHT);
Arrays.fill(colWidth, RESOURCE_WIDTH);
comps = new Component[rowCnt][TABLE_COL_COUNT];
for (int i = 0; i < rowCnt; i++) {
for (int j = 0; j < TABLE_COL_COUNT; j++) {
int which = i * 3 + j;
if (which >= dataCnt) {
Label empty = new Label();
empty.setPreferredSize(new Dimension(RESOURCE_WIDTH, RESOURCE_HEIGHT));
empty.setVisible(false);
comps[i][j] = empty;
} else {
TemplateResourcePanel resource = TemplateResourcePanel.create(pageData.get(which));
resource.setPreferredSize(new Dimension(RESOURCE_WIDTH, RESOURCE_HEIGHT));
comps[i][j] = resource;
}
}
}
contentPane = TableLayoutHelper.createGapTableLayoutPane(comps, rowHeight, colWidth, TABLE_HGAP, TABLE_VGAP);
contentPane.setBackground(Color.WHITE);
}
void createPageButtonPane() {
prev = new JButton(IconUtils.readIcon("/com/fr/design/mainframe/alphafine/images/prev.svg"));
next = new JButton(IconUtils.readIcon("/com/fr/design/mainframe/alphafine/images/next.svg"));
pageNumberField = new JTextField((int) Math.log10(totalPage) + 1);
pageNumberField.setText(String.valueOf(this.pageNumber));
pageCnt = new JLabel("/ " + totalPage);
pageButtonPane = new JPanel(new FlowLayout(FlowLayout.RIGHT));
pageButtonPane.add(prev);
pageButtonPane.add(pageNumberField);
pageButtonPane.add(pageCnt);
pageButtonPane.add(next);
addPageAction();
}
// 添加翻页按钮事件
void addPageAction() {
addPrevPageAction();
addNextPageAction();
addGotoPageAction();
}
void addPrevPageAction() {
prev.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
super.mouseClicked(e);
if (pageNumber > 1) {
switchPage(pageNumber - 1);
}
}
});
};
void addNextPageAction() {
next.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
super.mouseClicked(e);
if (pageNumber < totalPage) {
switchPage(pageNumber + 1);
}
}
});
}
void addGotoPageAction() {
pageNumberField.addKeyListener(new KeyAdapter() {
@Override
public void keyPressed(KeyEvent e) {
super.keyPressed(e);
String numb = pageNumberField.getText();
if (numb != null && !numb.equals(pageNumber)) {
if (e.getKeyCode() == KeyEvent.VK_ENTER) {
switchPage(Integer.parseInt(numb));
}
}
}
});
}
}
}

122
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/component/TemplateResourcePanel.java

@ -0,0 +1,122 @@
package com.fr.design.mainframe.alphafine.component;
import com.fr.design.i18n.Toolkit;
import com.fr.design.mainframe.alphafine.model.TemplateResource;
import com.fr.design.mainframe.alphafine.preview.TemplateShopPane;
import com.fr.design.utils.BrowseUtils;
import com.fr.log.FineLoggerFactory;
import javax.swing.BorderFactory;
import javax.swing.JLabel;
import javax.swing.JPanel;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
public class TemplateResourcePanel extends JPanel {
private JPanel northPane;
private JPanel southPane;
private TemplateResource templateResource;
private static final Color PANEL_BORDER_COLOR = new Color(0xe8e8e9);
private static final Color DEMO_LABEL_FOREGROUND = new Color(0x419bf9);
protected TemplateResourcePanel() {
}
protected TemplateResourcePanel(TemplateResource templateResource) {
this.templateResource = templateResource;
initComponent();
this.setLayout(new BorderLayout());
this.setBorder(BorderFactory.createLineBorder(PANEL_BORDER_COLOR, 1));
this.add(northPane, BorderLayout.NORTH);
this.add(southPane, BorderLayout.SOUTH);
addAction();
}
private void addAction() {
this.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
super.mouseClicked(e);
TemplateShopPane.getInstance().searchAndShowDetailPane(templateResource);
}
});
}
public static TemplateResourcePanel create(TemplateResource templateResource) {
if (TemplateResource.Type.RECOMMEND_SEARCH.equals(templateResource.getType())) {
return new RecommendSearchPane(templateResource);
} else {
return new TemplateResourcePanel(templateResource);
}
}
public JPanel getNorthPane() {
return northPane;
}
public JPanel getSouthPane() {
return southPane;
}
public TemplateResource getTemplateResource() {
return templateResource;
}
public void setNorthPane(JPanel northPane) {
this.northPane = northPane;
}
public void setSouthPane(JPanel southPane) {
this.southPane = southPane;
}
public void setTemplateResource(TemplateResource templateResource) {
this.templateResource = templateResource;
}
private void initComponent() {
createNorthPane();
createSouthPane();
}
protected void createNorthPane() {
northPane = new TemplateResourceImagePanel(templateResource);
}
private void createSouthPane() {
JLabel nameLabel = new JLabel(templateResource.getName());
nameLabel.setBackground(Color.WHITE);
nameLabel.setBorder(BorderFactory.createEmptyBorder());
JLabel demoLabel = new JLabel();
if (templateResource.hasDemoUrl()) {
demoLabel.setText(Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Resource_Demo"));
demoLabel.setForeground(DEMO_LABEL_FOREGROUND);
demoLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
try {
BrowseUtils.browser(templateResource.getDemoUrl());
} catch (Exception ex) {
FineLoggerFactory.getLogger().error(ex, ex.getMessage());
}
}
});
}
southPane = new JPanel(new BorderLayout());
southPane.setBackground(Color.WHITE);
southPane.add(nameLabel, BorderLayout.WEST);
southPane.add(demoLabel, BorderLayout.EAST);
}
@Override
public Dimension getPreferredSize() {
return new Dimension(180, 90);
}
}

47
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/model/ProductNews.java

@ -1,8 +1,12 @@
package com.fr.design.mainframe.alphafine.model;
import com.fr.design.i18n.Toolkit;
import java.awt.Image;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
/**
* 产品动态
@ -17,7 +21,9 @@ public class ProductNews {
private String title;
private Tag tag;
private Target target;
// 推送对象,对象为 list<用户组id>
private List<String> target;
private Status status;
private String url;
@ -26,6 +32,8 @@ public class ProductNews {
private Date pushDate;
public static final String ALL_USER_TARGET = "0";
/**
* 创建cid的用户
*/
@ -58,11 +66,11 @@ public class ProductNews {
return this;
}
public Target getTarget() {
public List<String> getTarget() {
return target;
}
public ProductNews setTarget(Target target) {
public ProductNews setTarget(List<String> target) {
this.target = target;
return this;
}
@ -172,29 +180,18 @@ public class ProductNews {
}
}
public enum Target {
ALL_USER(0);
private final int code;
Target(int code) {
this.code = code;
}
public int getCode() {
return code;
}
public static Target parseCode(int code) {
for (Target target : values()) {
if (target.code == code) {
return target;
}
}
throw new IllegalArgumentException();
/**
* 将接口中的target字段转换一下
* 原始数据是字符串例如"1,2,3,4"
* 转换为 List<int>{1,2,3,4}
* */
public static List<String> ParseTarget(String s) {
List<String> list = new ArrayList<>();
if (s != null) {
String[] targets = s.split(",");
list.addAll(Arrays.asList(targets));
}
return list;
}
}

191
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/model/TemplateResource.java

@ -0,0 +1,191 @@
package com.fr.design.mainframe.alphafine.model;
import com.fr.design.i18n.Toolkit;
import com.fr.design.mainframe.alphafine.search.manager.impl.TemplateResourceSearchManager;
import com.fr.general.IOUtils;
import com.fr.json.JSONArray;
import com.fr.json.JSONObject;
import com.fr.third.jodd.util.StringUtil;
import java.awt.Image;
import java.util.ArrayList;
import java.util.List;
/**
* 模板资源数据
*/
public class TemplateResource {
/***
* 模板资源类型模板解决方案推荐搜索
*/
public enum Type {
SINGLE_TEMPLATE(Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Resource_Single_Template")),
SCENARIO_SOLUTION(Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Resource_Scenario_Solution")),
RECOMMEND_SEARCH;
private String name;
Type() {
}
Type(String name) {
this.name = name;
}
public String getName() {
return name;
}
}
// 模板资源搜索接口返回值字段名
public static final String ID = "id";
public static final String UUID = "uuid";
public static final String NAME = "name";
public static final String IMAGE_URL = "pic";
public static final String DEMO_URL = "demoUrl";
public static final String PKG_SIZE = "pkgsize";
private static final String RECOMMEND_SEARCH_IMG_URL = "com/fr/design/mainframe/alphafine/images/more.png";
// 模板资源属性
private String id;
private String uuid;
private Type type;
private String imageUrl;
private Image image;
private String name;
private String demoUrl;
private int pkgSize;
private List<String> recommendSearchKey;
public static List<TemplateResource> createByJson(JSONArray jsonArray) {
List<TemplateResource> list = new ArrayList<>();
if (jsonArray != null) {
for (int i = jsonArray.length() - 1; i >= 0; i--) {
list.add(createByJson(jsonArray.getJSONObject(i)));
}
}
return list;
}
public static TemplateResource createByJson(JSONObject jsonObject) {
TemplateResource templateResource = new TemplateResource().setId(jsonObject.getString(ID)).setUuid(jsonObject.getString(UUID)).setName(jsonObject.getString(NAME))
.setDemoUrl(jsonObject.getString(DEMO_URL)).setPkgSize(jsonObject.getInt(PKG_SIZE));
int pkgSize = templateResource.getPkgSize();
if (pkgSize == 0) {
templateResource.type = Type.SINGLE_TEMPLATE;
} else {
templateResource.type = Type.SCENARIO_SOLUTION;
}
templateResource.setImageUrl(parseUrl(jsonObject));
templateResource.setImage(IOUtils.readImage(templateResource.imageUrl));
return templateResource;
}
/**
* 商城接口传过来的图片url是特殊格式需要特殊处理下
* */
static String parseUrl(JSONObject jsonObject) {
String imgUrl = jsonObject.getString(IMAGE_URL);
int index = imgUrl.indexOf(",");
if (index != -1) {
imgUrl = imgUrl.substring(0, imgUrl.indexOf(","));
}
return imgUrl;
}
public static TemplateResource getRecommendSearch() {
TemplateResource recommend = new TemplateResource();
recommend.setType(Type.RECOMMEND_SEARCH);
recommend.setImageUrl(RECOMMEND_SEARCH_IMG_URL);
recommend.setImage(IOUtils.readImage(RECOMMEND_SEARCH_IMG_URL));
recommend.setRecommendSearchKey(TemplateResourceSearchManager.getInstance().getRecommendSearchKeys());
return recommend;
}
public Type getType() {
return type;
}
public void setType(Type type) {
this.type = type;
}
public List<String> getRecommendSearchKey() {
return recommendSearchKey;
}
public void setRecommendSearchKey(List<String> recommendSearchKey) {
this.recommendSearchKey = recommendSearchKey;
}
public TemplateResource setImage(Image image) {
this.image = image;
return this;
}
public Image getImage() {
return image;
}
public TemplateResource setImageUrl(String imageUrl) {
this.imageUrl = imageUrl;
return this;
}
public String getName() {
return name;
}
public TemplateResource setName(String name) {
this.name = name;
return this;
}
public String getDemoUrl() {
return demoUrl;
}
public boolean hasDemoUrl() {
return !StringUtil.isEmpty(demoUrl);
}
public TemplateResource setDemoUrl(String demoUrl) {
this.demoUrl = demoUrl;
return this;
}
public int getPkgSize() {
return pkgSize;
}
public TemplateResource setPkgSize(int pkgSize) {
this.pkgSize = pkgSize;
return this;
}
public String getId() {
return id;
}
public TemplateResource setId(String id) {
this.id = id;
return this;
}
public String getUuid() {
return uuid;
}
public TemplateResource setUuid(String uuid) {
this.uuid = uuid;
return this;
}
}

208
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/model/TemplateResourceDetail.java

@ -0,0 +1,208 @@
package com.fr.design.mainframe.alphafine.model;
import com.fr.design.mainframe.alphafine.search.helper.FineMarketClientHelper;
import com.fr.design.mainframe.alphafine.search.manager.impl.TemplateResourceSearchManager;
import com.fr.json.JSONArray;
import com.fr.json.JSONObject;
import com.fr.log.FineLoggerFactory;
import com.fr.stable.StringUtils;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
* 模板资源详细数据
*/
public class TemplateResourceDetail {
// 与对应的模板资源关联
private final TemplateResource root;
private String info;
private String vendor;
private List<String> detailInfo;
private String[] tagsId;
private List<String> tagsName;
private double price;
private String parentPkgName;
private String resourceUrl;
public static final String ID = "id";
public static final String INFO = "description";
public static final String VENDOR = "vendor";
public static final String DETAIL_INFO = "text";
public static final String TAGS_ID = "cid";
public static final String PRICE = "price";
public static final String NAME = "name";
public static final String PARENT_NAME = "parentName";
public static final String TAGS_NAME = "tagsName";
public static final String URL = "url";
public TemplateResourceDetail(TemplateResource resource) {
this.root = resource;
}
public String getVendor() {
return vendor;
}
public void setVendor(String vendor) {
this.vendor = vendor;
}
public TemplateResource getRoot() {
return root;
}
public String getInfo() {
return info;
}
public void setInfo(String info) {
this.info = info;
}
public List<String> getDetailInfo() {
return detailInfo;
}
public void setDetailInfo(List<String> detailInfo) {
this.detailInfo = detailInfo;
}
public String[] getTagsId() {
return tagsId;
}
public void setTagsId(String[] tagsId) {
this.tagsId = tagsId;
}
public List<String> getTagsName() {
return tagsName;
}
public void setTagsName(List<String> tagsName) {
this.tagsName = tagsName;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
public String getParentPkgName() {
return parentPkgName;
}
public void setParentPkgName(String parentPkgName) {
if (StringUtils.isEmpty(parentPkgName)) {
this.parentPkgName = "";
} else {
this.parentPkgName = parentPkgName;
}
}
public String getResourceUrl() {
return resourceUrl;
}
public void setResourceUrl(String resourceUrl) {
this.resourceUrl = resourceUrl;
}
public static TemplateResourceDetail createByTemplateResource(TemplateResource root) {
return Builder.buildByResource(root);
}
public static TemplateResourceDetail createFromEmbedResource(TemplateResource root) {
return Builder.buildFromEmbedResource(root);
}
static class Builder {
static FineMarketClientHelper helper = FineMarketClientHelper.getInstance();
static TemplateResourceDetail buildFromEmbedResource(TemplateResource templateResource) {
TemplateResourceDetail detail = new TemplateResourceDetail(templateResource);
String resourceId = templateResource.getId();
JSONArray embedResources = TemplateResourceSearchManager.getInstance().getEmbedResourceJSONArray();
for (int i = 0; i < embedResources.length(); i++) {
JSONObject resource = embedResources.getJSONObject(i);
if (resourceId.equals(resource.getString(ID))) {
detail.setInfo(resource.getString(INFO));
detail.setDetailInfo(parseDetailInfo(resource.getString(DETAIL_INFO)));
detail.setVendor(resource.getString(VENDOR));
detail.setPrice(resource.getDouble(PRICE));
detail.setResourceUrl(resource.getString(URL));
detail.setParentPkgName(resource.getString(PARENT_NAME));
detail.setTagsName(Arrays.asList(resource.getString(TAGS_NAME).split(",")));
break;
}
}
return detail;
}
static TemplateResourceDetail buildByResource(TemplateResource templateResource) {
TemplateResourceDetail detail = new TemplateResourceDetail(templateResource);
String resourceId = templateResource.getId();
// 获取模板详情页的信息一共需要三次请求
try {
// 1请求详细信息
JSONObject info = helper.getTemplateInfoById(resourceId);
detail.setInfo(info.getString(INFO));
detail.setDetailInfo(parseDetailInfo(info.getString(DETAIL_INFO)));
detail.setVendor(info.getString(VENDOR));
detail.setTagsId(info.getString(TAGS_ID).split(","));
detail.setPrice(info.getDouble(PRICE));
detail.setResourceUrl(helper.getTemplateUrlById(templateResource.getId()));
// 2请求所属模板包信息
JSONObject parentPkginfo = helper.getTemplateParentPackageByTemplateId(resourceId);
if (parentPkginfo != null) {
detail.setParentPkgName(parentPkginfo.getString(NAME));
}
// 3请求标签信息
detail.setTagsName(helper.getTemplateTagsByTemplateTagIds(detail.getTagsId()));
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e, e.getMessage());
}
return detail;
}
/**
* 这里做下数据转换
* 原始数据是html标签写的如下
* "<ol style="list-style-type: decimal;" class=" list-paddingleft-2"><li><p>该模板需用10.0及以上版本设计器预览<br/></p></li><li><p>该模板为库存场景解决方案的部分内容,全部内容可下载<a href="https://market.fanruan.com/template/20000733" target="_self">库存场景解决方案</a>查看</p></li><li><p>为保障模板预览效果,建议安装<a href="https://help.fanruan.com/finereport10.0/doc-view-3665.html" target="_self">新自适应插件</a>(FR11.0版本插件已内置,无需手动安装),有使用需求或疑问,请联系帆软技术支持咨询<br/></p></li></ol>",
*
* 转换的后的数据 是原始数据中所有<p></p>标签内的包括标签的字符串List<String>,如上字符串会转为如下
* List [<p>该模板需用10.0及以上版本设计器预览<br/></p>,
* <p>该模板为库存场景解决方案的部分内容全部内容可下载<a href="https://market.fanruan.com/template/20000733" target="_self">库存场景解决方案</a>查看</p>,
* <p>为保障模板预览效果建议安装<a href="https://help.fanruan.com/finereport10.0/doc-view-3665.html" target="_self">新自适应插件</a>FR11.0版本插件已内置无需手动安装有使用需求或疑问请联系帆软技术支持咨询<br/></p>
* ]
* */
static final Pattern htmlPattern = Pattern.compile("<p>(.+?)</p>");
static List<String> parseDetailInfo(String htmlDetailInfo) {
List<String> infos = new ArrayList<>();
Matcher matcher = htmlPattern.matcher(htmlDetailInfo);
while (matcher.find()) {
infos.add(matcher.group());
}
return infos;
}
}
}

196
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/preview/TemplateResourceDetailPane.java

@ -0,0 +1,196 @@
package com.fr.design.mainframe.alphafine.preview;
import com.fr.design.gui.ibutton.UIButton;
import com.fr.design.gui.icontainer.UIScrollPane;
import com.fr.design.i18n.Toolkit;
import com.fr.design.mainframe.alphafine.action.StartUseAction;
import com.fr.design.mainframe.alphafine.component.TemplateResourceImagePanel;
import com.fr.design.mainframe.alphafine.model.TemplateResourceDetail;
import com.fr.design.utils.BrowseUtils;
import javax.swing.BorderFactory;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.SwingConstants;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.List;
public class TemplateResourceDetailPane extends JPanel {
private TemplateResourceDetail data;
private TemplateResourceImagePanel imagePane;
private JPanel contentPane;
private UIScrollPane infoScrollPane;
private JPanel operatePane;
private UIScrollPane detailInfoPane;
private static final int IMAGE_HEIGHT = 170;
private static final int IMAGE_WIDTH= 310;
private static final int SCROLL_PANE_WIDTH = 320;
private static final int SCROLL_PANE_HEIGHT = 150;
private static final int CONTENT_PANE_WIDTH = 320;
private static final int CONTENT_PANE_HEIGHT = 180;
private static final int DETAIL_PANE_HEIGHT = 110;
private static final int TEXT_SCROLL_PANE_HEIGHT = 500;
private static final int PANE_WIDTH = 640;
private static final String GOTO_DETAIL = Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Detail_GOTO_DETAIL");
private static final String START_USE = Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Detail_START_USE");
private static final String VENDOR = Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Detail_Vendor");
private static final String TAGS = Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Detail_Tags");
private static final String PARENT_PACKAGE = Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Detail_Parent_Package");
private static final String DETAIL_INFO = Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Detail_Info");
private static final String FREE = Toolkit.i18nText("Fine-Design_Report_AlphaFine_Template_Detail_Price_Free");
private static final String SPACE = " ";
private static final String LF = "<br>";
private static final String RMB = "¥";
private static final Color INFO_PANE_BACKGROUND = new Color(0xf9f9f9);
private static final Color INFO_PANE_FOREGROUND = new Color(0x5b5b5c);
public TemplateResourceDetailPane(TemplateResourceDetail detail) {
this.data = detail;
initComponent();
this.setLayout(new FlowLayout(FlowLayout.LEFT));
this.setBorder(BorderFactory.createEmptyBorder(10,20,0,20));
this.add(imagePane);
this.add(contentPane);
this.add(detailInfoPane);
this.setBackground(Color.WHITE);
}
public void refresh() {
}
private void initComponent() {
createImagePane();
createContentPane();
createDetailInfoPane();
}
private void createContentPane() {
createInfoScrollPane();
createOperatePane();
contentPane = new JPanel();
contentPane.setLayout(new FlowLayout(FlowLayout.LEFT));
contentPane.setPreferredSize(new Dimension(CONTENT_PANE_WIDTH, CONTENT_PANE_HEIGHT));
contentPane.add(infoScrollPane);
contentPane.add(operatePane);
contentPane.setBackground(Color.WHITE);
}
private void createOperatePane() {
operatePane = new JPanel(new FlowLayout(FlowLayout.LEFT));
JLabel emptyLabel = new JLabel();
emptyLabel.setPreferredSize(new Dimension(140, 25));
JLabel priceLabel = new JLabel();
priceLabel.setForeground(Color.RED);
if (data.getPrice() == 0) {
priceLabel.setText(FREE);
} else {
priceLabel.setText(RMB + SPACE + data.getPrice());
}
operatePane.add(createLinkLabel());
operatePane.add(emptyLabel);
operatePane.add(priceLabel);
operatePane.add(createStartUseButton());
operatePane.setBackground(Color.WHITE);
}
JLabel createLinkLabel() {
JLabel linkLabel = new JLabel(GOTO_DETAIL);
linkLabel.setBackground(Color.WHITE);
linkLabel.setForeground(Color.BLUE);
linkLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
super.mouseClicked(e);
openResourceUrl(data.getResourceUrl());
}
});
return linkLabel;
}
// 方便埋点
void openResourceUrl(String url) {
BrowseUtils.browser(url);
}
UIButton createStartUseButton() {
UIButton starUseButton = new UIButton(START_USE);
starUseButton.addActionListener(new StartUseAction(data));
return starUseButton;
}
private void createInfoScrollPane() {
JLabel content = new JLabel();
content.setHorizontalAlignment(SwingConstants.LEFT);
content.setVerticalAlignment(SwingConstants.TOP);
StringBuilder sb = new StringBuilder();
sb.append("<html><body><p>");
sb.append(VENDOR + data.getVendor() + LF);
List<String> tags = data.getTagsName();
sb.append(TAGS);
for (String tag : tags) {
sb.append(tag + SPACE);
}
sb.append(LF);
sb.append(PARENT_PACKAGE + data.getParentPkgName() + LF);
sb.append(data.getInfo());
sb.append("</p></body></html>");
content.setText(sb.toString());
content.setBackground(INFO_PANE_BACKGROUND);
content.setForeground(INFO_PANE_FOREGROUND);
content.setPreferredSize(new Dimension(SCROLL_PANE_WIDTH - 10, TEXT_SCROLL_PANE_HEIGHT));
infoScrollPane = new UIScrollPane(content);
infoScrollPane.setPreferredSize(new Dimension(SCROLL_PANE_WIDTH, SCROLL_PANE_HEIGHT - 25));
infoScrollPane.setBorder(BorderFactory.createEmptyBorder(0,0,0,0));
}
private void createImagePane() {
imagePane = new TemplateResourceImagePanel(data.getRoot(), IMAGE_WIDTH, IMAGE_HEIGHT);
}
private void createDetailInfoPane() {
JLabel content = new JLabel();
content.setHorizontalAlignment(SwingConstants.LEFT);
content.setVerticalAlignment(SwingConstants.TOP);
StringBuilder sb = new StringBuilder();
sb.append("<html><body><p>");
sb.append(DETAIL_INFO + LF);
List<String> detailInfos = data.getDetailInfo();
for (String info : detailInfos) {
sb.append(info);
}
sb.append("</p></body></html>");
content.setText(sb.toString());
content.setPreferredSize(new Dimension(PANE_WIDTH - 20, TEXT_SCROLL_PANE_HEIGHT));
content.setBackground(Color.WHITE);
detailInfoPane = new UIScrollPane(content);
detailInfoPane.setPreferredSize(new Dimension(PANE_WIDTH, DETAIL_PANE_HEIGHT));
detailInfoPane.setBackground(Color.WHITE);
detailInfoPane.setBorder(BorderFactory.createEmptyBorder(0,0,0,0));
}
}

158
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/preview/TemplateShopPane.java

@ -0,0 +1,158 @@
package com.fr.design.mainframe.alphafine.preview;
import com.fr.design.gui.ilable.UILabel;
import com.fr.design.mainframe.alphafine.AlphaFineConstants;
import com.fr.design.mainframe.alphafine.AlphaFineHelper;
import com.fr.design.mainframe.alphafine.component.TemplateResourcePageGridPane;
import com.fr.design.mainframe.alphafine.model.TemplateResource;
import com.fr.design.mainframe.alphafine.model.TemplateResourceDetail;
import com.fr.design.mainframe.alphafine.search.manager.impl.TemplateResourceSearchManager;
import com.fr.log.FineLoggerFactory;
import com.fr.third.apache.logging.log4j.util.Strings;
import javax.swing.JPanel;
import javax.swing.SwingWorker;
import java.awt.CardLayout;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.List;
public class TemplateShopPane extends JPanel {
private static final TemplateShopPane INSTANCE = new TemplateShopPane();
public static TemplateShopPane getInstance() {
return INSTANCE;
}
// public 方便埋点
public static final String DEFAULT_PAGE_PANEL = "defaultPagePane";
public static final String PAGE_PANEL = "pagePane";
public static final String DETAIL_PANEL = "detailPane";
public static final String LOADING_PANEL = "loadingPane";
private String currentCard = Strings.EMPTY;
private static final String SLASH = "/";
private CardLayout cardLayout = new CardLayout();
private JPanel defaultPagePane;
private JPanel pagePane;
private JPanel detailPane;
private JPanel loadingPane;
private TemplateShopPane() {
setLayout(cardLayout);
initComponents();
this.add(defaultPagePane, DEFAULT_PAGE_PANEL);
this.add(loadingPane, LOADING_PANEL);
this.setPreferredSize(AlphaFineConstants.PREVIEW_SIZE);
switchCard(DEFAULT_PAGE_PANEL);
}
private void switchCard(String flag) {
cardLayout.show(this, flag);
currentCard = flag;
}
private void initComponents() {
defaultPagePane = createDefaultResourcePane();
loadingPane = createLoadingPane();
}
public void refreshPagePane(List<TemplateResource> resourceList) {
pagePane = createContentPane(resourceList);
this.add(pagePane, PAGE_PANEL);
switchCard(PAGE_PANEL);
}
public void quitSearchResultPane() {
if (currentCard.equals(PAGE_PANEL)) {
switchCard(DEFAULT_PAGE_PANEL);
}
}
public void showPagePane() {
switchCard(PAGE_PANEL);
}
// 打开二级页面,显示详细信息
public void searchAndShowDetailPane(TemplateResource resource) {
changeLabel(resource.getName());
switchCard(LOADING_PANEL);
new SwingWorker<TemplateResourceDetail, Void>() {
@Override
protected TemplateResourceDetail doInBackground(){
// 搜搜
TemplateResourceDetail detail = TemplateResourceSearchManager.getInstance().getDetailSearchResult(resource);
return detail;
}
@Override
protected void done() {
TemplateResourceDetail detail = null;
try {
detail = get();
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e, e.getMessage());
}
// detailpane初始化
detailPane = new TemplateResourceDetailPane(detail);
// 切换
INSTANCE.add(detailPane, DETAIL_PANEL);
switchCard(DETAIL_PANEL);
}
}.execute();
}
private void changeLabel(String resourceName) {
JPanel labelNamePane = AlphaFineHelper.getAlphaFineDialog().getLabelWestPane();
UILabel tabLabel = AlphaFineHelper.getAlphaFineDialog().getTabLabel();
tabLabel.setForeground(AlphaFineConstants.DARK_GRAY);
UILabel slash = new UILabel(SLASH);
slash.setForeground(AlphaFineConstants.DARK_GRAY);
UILabel resourceLabel = new UILabel(resourceName);
resourceLabel.setForeground(AlphaFineConstants.LABEL_SELECTED);
labelNamePane.add(slash);
labelNamePane.add(resourceLabel);
tabLabel.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
super.mouseClicked(e);
switchCard(PAGE_PANEL);
tabLabel.setForeground(AlphaFineConstants.LABEL_SELECTED);
labelNamePane.remove(slash);
labelNamePane.remove(resourceLabel);
}
});
}
// 方便埋点,勿删
public String getCurrentCard() {
return currentCard;
}
private JPanel createContentPane(List<TemplateResource> templateResources) {
return new TemplateResourcePageGridPane(templateResources);
}
private JPanel createDefaultResourcePane() {
return createContentPane(TemplateResourceSearchManager.getInstance().getDefaultResourceList());
}
private JPanel createLoadingPane() {
return new SearchLoadingPane();
}
}

109
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/search/TemplateResourceSearchWorkerManager.java

@ -0,0 +1,109 @@
package com.fr.design.mainframe.alphafine.search;
import com.fr.design.mainframe.alphafine.AlphaFineConstants;
import com.fr.design.mainframe.alphafine.AlphaFineHelper;
import com.fr.design.mainframe.alphafine.CellType;
import com.fr.design.mainframe.alphafine.component.AlphaFineFrame;
import com.fr.design.mainframe.alphafine.model.TemplateResource;
import com.fr.design.mainframe.alphafine.preview.TemplateShopPane;
import com.fr.log.FineLoggerFactory;
import javax.swing.SwingWorker;
import java.util.List;
import java.util.function.Function;
public class TemplateResourceSearchWorkerManager implements SearchManager {
private final CellType cellType;
private SwingWorker<List<TemplateResource>, Void> searchWorker;
private Function<SearchTextBean, List<TemplateResource>> searchFunction;
private AlphaFineFrame alphaFineFrame;
private volatile boolean searchResult = true;
private volatile boolean searchOver = false;
private volatile boolean networkError = false;
public TemplateResourceSearchWorkerManager(CellType cellType, Function<SearchTextBean, List<TemplateResource>> searchFunction, AlphaFineFrame alphaFineFrame) {
this.cellType = cellType;
this.searchFunction = searchFunction;
this.alphaFineFrame = alphaFineFrame;
}
@Override
public void doSearch(SearchTextBean searchTextBean) {
checkSearchWork();
searchOver = false;
networkError = false;
this.searchWorker = new SwingWorker<List<TemplateResource>, Void>() {
@Override
protected List<TemplateResource> doInBackground() {
List<TemplateResource> list;
if (!AlphaFineHelper.isNetworkOk() && cellType.isNeedNetWork()) {
networkError = true;
FineLoggerFactory.getLogger().warn("alphaFine network error");
}
list = searchFunction.apply(searchTextBean);
return list;
}
@Override
protected void done() {
searchOver = true;
if (!isCancelled()) {
try {
List<TemplateResource> list = get();
searchResult = !list.isEmpty();
showResult(list);
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e.getMessage(), e);
}
}
}
};
this.searchWorker.execute();
}
void showResult(List<TemplateResource> list) {
if (networkError && !searchResult) {
alphaFineFrame.showResult(AlphaFineConstants.NETWORK_ERROR);
return;
}
if (alphaFineFrame.getSelectedType() == cellType) {
if (!searchResult) {
alphaFineFrame.showResult(CellType.NO_RESULT.getFlagStr4None());
} else {
TemplateShopPane.getInstance().refreshPagePane(list);
AlphaFineHelper.getAlphaFineDialog().showResult(cellType.getFlagStr4None());
}
}
}
@Override
public boolean hasSearchResult() {
return searchResult;
}
@Override
public boolean isSearchOver() {
return searchOver;
}
private void checkSearchWork() {
if (this.searchWorker != null && !this.searchWorker.isDone()) {
this.searchWorker.cancel(true);
this.searchWorker = null;
}
}
@Override
public boolean isNetWorkError() {
return networkError;
}
}

178
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/search/helper/FineMarketClientHelper.java

@ -0,0 +1,178 @@
package com.fr.design.mainframe.alphafine.search.helper;
import com.fr.design.mainframe.alphafine.model.TemplateResource;
import com.fr.design.utils.BrowseUtils;
import com.fr.general.CloudCenter;
import com.fr.general.http.HttpToolbox;
import com.fr.json.JSONArray;
import com.fr.json.JSONObject;
import org.jetbrains.annotations.Nullable;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class FineMarketClientHelper {
private static final FineMarketClientHelper INSTANCE = new FineMarketClientHelper();
public static FineMarketClientHelper getInstance() {
return INSTANCE;
}
public static final String FINE_MARKET_TEMPLATE_INFO = CloudCenter.getInstance().acquireUrlByKind("market.template.info");
public static final String FINE_MARKET_TEMPLATE_URL = CloudCenter.getInstance().acquireUrlByKind("market.template.url");
public static final String LOGIN_FINE_CLUB_AND_REDIRECT_SHOP = CloudCenter.getInstance().acquireUrlByKind("af.login.redirect.market");
public static final String FILE_DOWNLOAD = "file/";
public static final String PACKAGE_DOWNLOAD = "package/download/";
public static final String TEMPLATES_PARENT_PACKAGE = "parent/";
public static final String TEMPLATES_TAGS = "filter";
public static final String NAME_SEARCH = "?searchKeyword=";
public static final String RESPONSE_STATE = "state";
public static final String RESPONSE_SUCCESS = "ok";
public static final String RESPONSE_RESULT = "result";
public static final String TAGS_KEY = "key";
public static final String TAGS_ITEMS = "items";
public static final String TAG_NAME = "name";
public static final String TAG_ID = "id";
// 缓存下所有tag标签
private Map<String, String> tags;
/**
* 获取模板资源的下载链接
* */
public String getResourceDownloadUrl(TemplateResource templateResource) {
if (TemplateResource.Type.SCENARIO_SOLUTION.equals(templateResource.getType())) {
return getPackageDownloadUrl(templateResource.getId());
} else {
return getFileDownLoadUrl(templateResource.getId());
}
}
public void openBrowserAndDownload(TemplateResource templateResource) {
String url = LOGIN_FINE_CLUB_AND_REDIRECT_SHOP;
if (TemplateResource.Type.SCENARIO_SOLUTION.equals(templateResource.getType())) {
url += getPackageDownloadUrl(templateResource.getId());
} else {
url += getFileDownLoadUrl(templateResource.getId());
}
BrowseUtils.browser(url);
}
/**
* 暂时没有package的下载接口需要用户在浏览器点击下载
* */
private String getPackageDownloadUrl(String id) {
return getTemplateUrlById(id);
}
/**
* 打开浏览器下载单一模板
* */
private String getFileDownLoadUrl(String id) {
return FINE_MARKET_TEMPLATE_INFO + FILE_DOWNLOAD + id;
}
/**
* 获取帆软市场模板资源页面链接
* */
public String getFineMarketTemplateUrl() {
return FINE_MARKET_TEMPLATE_URL;
}
public @Nullable JSONObject getTemplateInfoById(String id) throws IOException {
String url = FINE_MARKET_TEMPLATE_INFO + id;
String jsonString = HttpToolbox.get(url);
JSONObject jsonObject = new JSONObject(jsonString);
String responseState = (String) jsonObject.get(RESPONSE_STATE);
if (RESPONSE_SUCCESS.equals(responseState)) {
return jsonObject.getJSONObject(RESPONSE_RESULT);
} else {
return null;
}
}
public @Nullable JSONArray getTemplateInfoByName(String name) throws IOException {
String url = FINE_MARKET_TEMPLATE_INFO + NAME_SEARCH + name;
String jsonString = HttpToolbox.get(url);
JSONObject jsonObject = new JSONObject(jsonString);
String responseState = (String) jsonObject.get(RESPONSE_STATE);
if (RESPONSE_SUCCESS.equals(responseState)) {
return jsonObject.getJSONArray(RESPONSE_RESULT);
}
return null;
}
public String getTemplateUrlById(String id) {
return FINE_MARKET_TEMPLATE_URL + id;
}
public @Nullable JSONObject getTemplateParentPackageByTemplateId(String id) throws IOException {
String url = FINE_MARKET_TEMPLATE_INFO + TEMPLATES_PARENT_PACKAGE + id;
String jsonString = HttpToolbox.get(url);
JSONObject jsonObject = new JSONObject(jsonString);
String responseState = (String) jsonObject.get(RESPONSE_STATE);
if (RESPONSE_SUCCESS.equals(responseState)) {
JSONArray jsonArray = jsonObject.getJSONArray(RESPONSE_RESULT);
if (!jsonArray.isEmpty()) {
return jsonObject.getJSONArray(RESPONSE_RESULT).getJSONObject(0);
}
}
return null;
}
/**
* 根据模板资源的tagid获取tagName
* */
public List<String> getTemplateTagsByTemplateTagIds(String[] tagIds) throws IOException {
List<String> list = new ArrayList<>();
initTags();
if (tagIds != null) {
for (String tagId : tagIds) {
String tagName = tags.get(tagId);
if (tagName != null) {
list.add(tagName);
}
}
}
return list;
}
/**
* 请求帆软市场获取所有tag信息并构建tagid - tagname的map
* */
private void initTags() throws IOException {
tags = new HashMap<>();
String url = FINE_MARKET_TEMPLATE_INFO + TEMPLATES_TAGS;
String jsonString = HttpToolbox.get(url);
JSONObject jsonObject = new JSONObject(jsonString);
String responseState = (String) jsonObject.get(RESPONSE_STATE);
if (RESPONSE_SUCCESS.equals(responseState)) {
JSONArray resultArray = jsonObject.getJSONArray(RESPONSE_RESULT);
for (int i = 1; i < resultArray.size(); i++) {
JSONObject result = resultArray.getJSONObject(i);
String key = result.getString(TAGS_KEY);
key = key.substring(key.indexOf('@') + 1);
JSONArray items = result.getJSONArray(TAGS_ITEMS);
for (int j = 0; j < items.length(); j++) {
JSONObject item = items.getJSONObject(j);
String id = item.getString(TAG_ID);
String name = item.getString(TAG_NAME);
tags.put(key + '-' + id, name);
}
}
}
}
}

68
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/search/manager/impl/ProductNewsSearchManager.java

@ -1,6 +1,7 @@
package com.fr.design.mainframe.alphafine.search.manager.impl;
import com.fr.concurrent.NamedThreadFactory;
import com.fr.design.DesignerEnvManager;
import com.fr.design.mainframe.alphafine.AlphaFineConstants;
import com.fr.design.mainframe.alphafine.AlphaFineHelper;
import com.fr.design.mainframe.alphafine.model.ProductNews;
@ -12,17 +13,19 @@ import com.fr.json.JSONObject;
import com.fr.log.FineLoggerFactory;
import org.jetbrains.annotations.Nullable;
import javax.imageio.ImageIO;
import java.awt.Image;
import java.net.URL;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
import javax.imageio.ImageIO;
public class ProductNewsSearchManager {
@ -91,7 +94,7 @@ public class ProductNewsSearchManager {
setImage(getCoverImage(obj.getString("pic"))).
setUrl(obj.getString("url")).setTag(ProductNews.Tag.parseCode(obj.getInt("tag"))).
setStatus(ProductNews.Status.parseCode(obj.getInt("status"))).setTarget(
ProductNews.Target.parseCode(obj.getInt("target"))).
ProductNews.ParseTarget(obj.getString("target"))).
setCreator(obj.getInt("creator")).setPushDate(new Date(obj.getLong("push_time")));
Date currentDate = new Date(System.currentTimeMillis());
// 推送时间check
@ -100,9 +103,70 @@ public class ProductNewsSearchManager {
idSet.add(productNews.getId());
}
}
filterByDesignerId(productNewsList);
return productNewsList;
}
/**
* 将productNews根据设计器id进行过滤
* productNews有个target字段代表推送对象用户组检查设计器id是否在用户组中来进行过滤
* */
private List<ProductNews> filterByDesignerId(List<ProductNews> list) {
//设计器id
String designId = DesignerEnvManager.getEnvManager().getUUID();
HashMap<String, Set<String>> userGroupInfoCache = new HashMap<>();
//遍历资源,获取target下的所有用户组信息,检查是否包含设计器id
Iterator<ProductNews> iterator = list.iterator();
while (iterator.hasNext()) {
List<String> targets = iterator.next().getTarget();
boolean targetsContainDesignerId = false;
// 每条推送可能推送至多个用户组,需要逐一判断
for (String userGroupId : targets) {
// 没有记录的用户组信息需要请求一下
if (!userGroupInfoCache.containsKey(userGroupId)) {
userGroupInfoCache.put(userGroupId, searchUserGroupInfo(userGroupId));
}
// 判断设计器id是否在这个用户组中,在则退出判断,不在则继续
if (userGroupInfoCache.get(userGroupId).contains(designId) || userGroupId.equals(ProductNews.ALL_USER_TARGET)) {
targetsContainDesignerId = true;
break;
}
}
if (!targetsContainDesignerId) {
iterator.remove();
}
}
return list;
}
/**
* 根据用户组id查询用户组信息改用户组中的所有设计器id
* */
private Set<String> searchUserGroupInfo(String userGroupId) {
String url = AlphaFineConstants.ALPHA_CID_USER_GROUP_INFO + AlphaFineConstants.SEARCH_BY_ID + userGroupId;
Set<String> idSet = new HashSet<>();
try {
String jsonStr = HttpToolbox.get(url);
JSONObject jsonObject = new JSONObject(jsonStr);
JSONArray idArray = jsonObject.getJSONArray("data");
for (int i = 0; i < idArray.length(); i++) {
idSet.add(idArray.getJSONObject(i).getString("userid"));
}
} catch (Exception e) {
FineLoggerFactory.getLogger().error(e, e.getMessage());
}
return idSet;
}
public List<ProductNews> getCachedProductNewsList() {
return productNewsList;
}

100
designer-realize/src/main/java/com/fr/design/mainframe/alphafine/search/manager/impl/TemplateResourceSearchManager.java

@ -0,0 +1,100 @@
package com.fr.design.mainframe.alphafine.search.manager.impl;
import com.fr.design.mainframe.alphafine.AlphaFineHelper;
import com.fr.design.mainframe.alphafine.model.TemplateResource;
import com.fr.design.mainframe.alphafine.model.TemplateResourceDetail;
import com.fr.design.mainframe.alphafine.search.helper.FineMarketClientHelper;
import com.fr.general.CloudCenter;
import com.fr.general.IOUtils;
import com.fr.json.JSONArray;
import java.util.ArrayList;
import java.util.List;
public class TemplateResourceSearchManager {
private static final TemplateResourceSearchManager INSTANCE = new TemplateResourceSearchManager();
public static TemplateResourceSearchManager getInstance() {
return INSTANCE;
}
public static final String LOCAL_RESOURCE_URL = "/com/fr/design/mainframe/alphafine/template_resource/local_templates.json";
private static final FineMarketClientHelper helper = FineMarketClientHelper.getInstance();
/**
* 帆软市场暂时没有分页搜索接口先全量搜分页展示
* */
public List<TemplateResource> getSearchResult(String searchText) {
List<TemplateResource> resourceList = new ArrayList<>();
// 联网搜索
try {
JSONArray jsonArray = helper.getTemplateInfoByName(searchText);
if (jsonArray != null && !jsonArray.isEmpty()) {
resourceList.addAll(TemplateResource.createByJson(jsonArray));
}
} catch (Exception e) {
}
// 本地搜索
if (resourceList.isEmpty()) {
List<TemplateResource> localResource = getEmbedResourceList();
localResource.stream().forEach(resource->{
if (resource.getName().toLowerCase().contains(searchText)) {
resourceList.add(resource);
}
});
}
return resourceList;
}
/**
* 返回默认资源
* */
public List<TemplateResource> getDefaultResourceList() {
List<TemplateResource> resourceList = getEmbedResourceList();
// 添加推荐搜索卡片
resourceList.add(TemplateResource.getRecommendSearch());
return resourceList;
}
/**
* 返回内置资源
* */
public List<TemplateResource> getEmbedResourceList() {
List<TemplateResource> resourceList = new ArrayList<>();
JSONArray jsonArray = getEmbedResourceJSONArray();
for (int i = 0; i < jsonArray.size(); i++) {
resourceList.add(TemplateResource.createByJson(jsonArray.getJSONObject(i)));
}
return resourceList;
}
public JSONArray getEmbedResourceJSONArray() {
String jsonString = IOUtils.readResourceAsString(LOCAL_RESOURCE_URL);
return new JSONArray(jsonString);
}
public List<String> getRecommendSearchKeys() {
List<String> searchKey = new ArrayList<>();
String[] keys = CloudCenter.getInstance().acquireConf("alphafine.tempalte.recommend", "跑马灯,填报,地图").split(",");
for (String k : keys) {
searchKey.add(k);
}
return searchKey;
}
public TemplateResourceDetail getDetailSearchResult(TemplateResource resource) {
if (AlphaFineHelper.isNetworkOk()) {
return TemplateResourceDetail.createByTemplateResource(resource);
} else {
return TemplateResourceDetail.createFromEmbedResource(resource);
}
}
}

11
designer-realize/src/main/java/com/fr/start/MainDesigner.java

@ -240,8 +240,13 @@ public class MainDesigner extends BaseDesigner {
if (WorkContext.getCurrent().isRoot()) {
menuDef.addShortCut(
new ServerConfigManagerAction(),
new TemplateThemeManagerAction(),
new ServerConfigManagerAction()
);
JTemplate<?, ?> jt = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate();
if (JTemplate.isValid(jt)) {
menuDef.addShortCut(new TemplateThemeManagerAction());
}
menuDef.addShortCut(
new WidgetManagerAction()
);
menuDef.addShortCut(new ChartPreStyleAction(), new ChartEmptyDataStyleAction(),new ChartMapEditorAction());
@ -403,7 +408,7 @@ public class MainDesigner extends BaseDesigner {
@Override
protected void refreshLargeToolbarState() {
JTemplate<?, ?> jt = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate();
if (jt == null) {
if (!JTemplate.isValid(jt)) {
return;
}
saveButton.setEnabled(!jt.isSaved() && !DesignModeContext.isVcsMode() && jt.checkEnable());

5
designer-realize/src/main/java/com/fr/start/module/optimized/DesignerStartupPageActivator.java

@ -139,8 +139,9 @@ public class DesignerStartupPageActivator extends Activator {
}
private void recordStartupEnd(StopWatch stopWatch) {
DesignerMetrics designerMetrics = DesignerStartupContext.getInstance().getDesignerMetrics();
DesignerStartupContext context = DesignerStartupContext.getInstance();
DesignerMetrics designerMetrics = context.getDesignerMetrics();
DesignerStartupModel model = designerMetrics.getModel();
model.setStartingTime(stopWatch.getTime(TimeUnit.MILLISECONDS));
model.fill();

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/bottom.svg

@ -0,0 +1,3 @@
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M3.42701 7C3.31655 7 3.22701 7.08954 3.22701 7.2C3.22701 7.24679 3.24341 7.29209 3.27336 7.32804L7.84636 12.8156C7.91707 12.9005 8.04318 12.9119 8.12804 12.8412C8.13733 12.8335 8.1459 12.8249 8.15364 12.8156L12.7266 7.32804C12.7973 7.24318 12.7859 7.11707 12.701 7.04636C12.6651 7.0164 12.6198 7 12.573 7H9V2C9 1.44772 8.55228 1 8 1C7.44772 1 7 1.44772 7 2V7H3.42701ZM12.5 15C12.7761 15 13 14.7761 13 14.5C13 14.2239 12.7761 14 12.5 14H3.5C3.22386 14 3 14.2239 3 14.5C3 14.7761 3.22386 15 3.5 15H12.5Z" fill="#333334"/>
</svg>

After

Width:  |  Height:  |  Size: 672 B

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/bottom_disable.svg

@ -0,0 +1,3 @@
<svg width="16" height="16" viewBox="0 0 16 16" opacity=".7" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M3.42701 7C3.31655 7 3.22701 7.08954 3.22701 7.2C3.22701 7.24679 3.24341 7.29209 3.27336 7.32804L7.84636 12.8156C7.91707 12.9005 8.04318 12.9119 8.12804 12.8412C8.13733 12.8335 8.1459 12.8249 8.15364 12.8156L12.7266 7.32804C12.7973 7.24318 12.7859 7.11707 12.701 7.04636C12.6651 7.0164 12.6198 7 12.573 7H9V2C9 1.44772 8.55228 1 8 1C7.44772 1 7 1.44772 7 2V7H3.42701ZM12.5 15C12.7761 15 13 14.7761 13 14.5C13 14.2239 12.7761 14 12.5 14H3.5C3.22386 14 3 14.2239 3 14.5C3 14.7761 3.22386 15 3.5 15H12.5Z" fill="#333334"/>
</svg>

After

Width:  |  Height:  |  Size: 685 B

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/config.svg

@ -0,0 +1,3 @@
<svg width="15" height="15" viewBox="0 0 15 15" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M8 1C7.17157 1 6.5 1.67157 6.5 2.5V3.2289C6.21745 3.31765 5.9457 3.4308 5.68724 3.56589L5.1716 3.05025C4.58582 2.46447 3.63607 2.46447 3.05028 3.05025C2.4645 3.63604 2.4645 4.58579 3.05028 5.17157L3.56591 5.6872C3.43081 5.94567 3.31765 6.21743 3.2289 6.5H2.5C1.67157 6.5 1 7.17157 1 8C1 8.82843 1.67157 9.5 2.5 9.5H3.2289C3.31765 9.78256 3.43081 10.0543 3.5659 10.3128L3.05026 10.8284C2.46448 11.4142 2.46448 12.364 3.05026 12.9497C3.63605 13.5355 4.5858 13.5355 5.17159 12.9497L5.68722 12.4341C5.94569 12.5692 6.21744 12.6824 6.5 12.7711V13.5C6.5 14.3284 7.17157 15 8 15C8.82843 15 9.5 14.3284 9.5 13.5V12.7711C9.78257 12.6824 10.0543 12.5692 10.3128 12.4341L10.8285 12.9497C11.4142 13.5355 12.364 13.5355 12.9498 12.9497C13.5356 12.364 13.5356 11.4142 12.9498 10.8284L12.4341 10.3128C12.5692 10.0543 12.6824 9.78255 12.7711 9.5H13.5C14.3284 9.5 15 8.82843 15 8C15 7.17157 14.3284 6.5 13.5 6.5H12.7711C12.6824 6.21744 12.5692 5.94569 12.4341 5.68722L12.9498 5.17157C13.5355 4.58579 13.5355 3.63604 12.9498 3.05025C12.364 2.46447 11.4142 2.46447 10.8284 3.05025L10.3128 3.5659C10.0543 3.43081 9.78256 3.31765 9.5 3.2289V2.5C9.5 1.67157 8.82843 1 8 1ZM8 10C9.10457 10 10 9.10457 10 8C10 6.89543 9.10457 6 8 6C6.89543 6 6 6.89543 6 8C6 9.10457 6.89543 10 8 10Z" fill="#333334"/>
</svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/down.svg

@ -0,0 +1,3 @@
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M3.42705 9.1124C3.31659 9.1124 3.22705 9.20195 3.22705 9.31241C3.22705 9.35919 3.24345 9.4045 3.27341 9.44044L7.8464 14.928C7.91711 15.0129 8.04322 15.0244 8.12808 14.9536C8.13737 14.9459 8.14594 14.9373 8.15369 14.928L12.7267 9.44044C12.7974 9.35559 12.7859 9.22947 12.7011 9.15876C12.6651 9.12881 12.6198 9.1124 12.573 9.1124H9.00004V2.1124C9.00004 1.56012 8.55233 1.1124 8.00004 1.1124C7.44776 1.1124 7.00004 1.56012 7.00004 2.1124V9.1124H3.42705Z" fill="#333334"/>
</svg>

After

Width:  |  Height:  |  Size: 620 B

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/down_disable.svg

@ -0,0 +1,3 @@
<svg width="16" height="16" viewBox="0 0 16 16" opacity=".7" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M3.42705 9.1124C3.31659 9.1124 3.22705 9.20195 3.22705 9.31241C3.22705 9.35919 3.24345 9.4045 3.27341 9.44044L7.8464 14.928C7.91711 15.0129 8.04322 15.0244 8.12808 14.9536C8.13737 14.9459 8.14594 14.9373 8.15369 14.928L12.7267 9.44044C12.7974 9.35559 12.7859 9.22947 12.7011 9.15876C12.6651 9.12881 12.6198 9.1124 12.573 9.1124H9.00004V2.1124C9.00004 1.56012 8.55233 1.1124 8.00004 1.1124C7.44776 1.1124 7.00004 1.56012 7.00004 2.1124V9.1124H3.42705Z" fill="#333334"/>
</svg>

After

Width:  |  Height:  |  Size: 637 B

BIN
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/local_template1.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 424 KiB

BIN
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/local_template2.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 MiB

BIN
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/local_template3.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 206 KiB

BIN
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/local_template4.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 591 KiB

BIN
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/more.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.9 KiB

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/next.svg

@ -0,0 +1,3 @@
<svg width="6" height="10" viewBox="0 0 6 10" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M4.29289 5L0.646447 8.64645C0.451184 8.84171 0.451184 9.15829 0.646447 9.35355C0.841709 9.54882 1.15829 9.54882 1.35355 9.35355L5.35355 5.35355C5.54882 5.15829 5.54882 4.84171 5.35355 4.64645L1.35355 0.646447C1.15829 0.451184 0.841709 0.451184 0.646447 0.646447C0.451184 0.841709 0.451184 1.15829 0.646447 1.35355L4.29289 5Z" fill="#C2C2C2"/>
</svg>

After

Width:  |  Height:  |  Size: 453 B

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/prev.svg

@ -0,0 +1,3 @@
<svg width="6" height="10" viewBox="0 0 6 10" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M1.70711 5L5.35355 8.64645C5.54882 8.84171 5.54882 9.15829 5.35355 9.35355C5.15829 9.54882 4.84171 9.54882 4.64645 9.35355L0.646447 5.35355C0.451185 5.15829 0.451185 4.84171 0.646447 4.64645L4.64645 0.646447C4.84171 0.451184 5.15829 0.451184 5.35355 0.646447C5.54882 0.841709 5.54882 1.15829 5.35355 1.35355L1.70711 5Z" fill="#C2C2C2"/>
</svg>

After

Width:  |  Height:  |  Size: 447 B

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/top.svg

@ -0,0 +1,3 @@
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M3.42701 9C3.31655 9 3.22701 8.91046 3.22701 8.8C3.22701 8.75321 3.24341 8.70791 3.27336 8.67196L7.84636 3.18437C7.91707 3.09952 8.04318 3.08805 8.12804 3.15877C8.13733 3.16651 8.1459 3.17508 8.15364 3.18437L12.7266 8.67196C12.7973 8.75682 12.7859 8.88293 12.701 8.95364C12.6651 8.9836 12.6198 9 12.573 9H9V14C9 14.5523 8.55228 15 8 15C7.44772 15 7 14.5523 7 14V9H3.42701ZM12.5 1C12.7761 1 13 1.22386 13 1.5C13 1.77614 12.7761 2 12.5 2H3.5C3.22386 2 3 1.77614 3 1.5C3 1.22386 3.22386 1 3.5 1H12.5Z" fill="#333334"/>
</svg>

After

Width:  |  Height:  |  Size: 668 B

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/top_disable.svg

@ -0,0 +1,3 @@
<svg width="16" height="16" viewBox="0 0 16 16" opacity=".7" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M3.42701 9C3.31655 9 3.22701 8.91046 3.22701 8.8C3.22701 8.75321 3.24341 8.70791 3.27336 8.67196L7.84636 3.18437C7.91707 3.09952 8.04318 3.08805 8.12804 3.15877C8.13733 3.16651 8.1459 3.17508 8.15364 3.18437L12.7266 8.67196C12.7973 8.75682 12.7859 8.88293 12.701 8.95364C12.6651 8.9836 12.6198 9 12.573 9H9V14C9 14.5523 8.55228 15 8 15C7.44772 15 7 14.5523 7 14V9H3.42701ZM12.5 1C12.7761 1 13 1.22386 13 1.5C13 1.77614 12.7761 2 12.5 2H3.5C3.22386 2 3 1.77614 3 1.5C3 1.22386 3.22386 1 3.5 1H12.5Z" fill="#333334"/>
</svg>

After

Width:  |  Height:  |  Size: 684 B

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/up.svg

@ -0,0 +1,3 @@
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M3.42705 7C3.31659 7 3.22705 6.91046 3.22705 6.8C3.22705 6.75321 3.24345 6.7079 3.27341 6.67196L7.8464 1.18437C7.91711 1.09952 8.04322 1.08805 8.12808 1.15876C8.13737 1.16651 8.14594 1.17508 8.15369 1.18437L12.7267 6.67196C12.7974 6.75682 12.7859 6.88293 12.7011 6.95364C12.6651 6.9836 12.6198 7 12.573 7H9.00004V14C9.00004 14.5523 8.55233 15 8.00004 15C7.44776 15 7.00004 14.5523 7.00004 14V7H3.42705Z" fill="#333334"/>
</svg>

After

Width:  |  Height:  |  Size: 573 B

3
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/images/up_disable.svg

@ -0,0 +1,3 @@
<svg width="16" height="16" viewBox="0 0 16 16" opacity=".7" fill="none" xmlns="http://www.w3.org/2000/svg">
<path fill-rule="evenodd" clip-rule="evenodd" d="M3.42705 7C3.31659 7 3.22705 6.91046 3.22705 6.8C3.22705 6.75321 3.24345 6.7079 3.27341 6.67196L7.8464 1.18437C7.91711 1.09952 8.04322 1.08805 8.12808 1.15876C8.13737 1.16651 8.14594 1.17508 8.15369 1.18437L12.7267 6.67196C12.7974 6.75682 12.7859 6.88293 12.7011 6.95364C12.6651 6.9836 12.6198 7 12.573 7H9.00004V14C9.00004 14.5523 8.55233 15 8.00004 15C7.44776 15 7.00004 14.5523 7.00004 14V7H3.42705Z" fill="#333334"/>
</svg>

After

Width:  |  Height:  |  Size: 589 B

110
designer-realize/src/main/resources/com/fr/design/mainframe/alphafine/template_resource/local_templates.json

@ -0,0 +1,110 @@
[
{
"id": 20000770,
"name": "PDCA销售运营闭环管理方案",
"uuid": "7975ad73-9aea-4634-96f1-d33ec1b4283c",
"vendor": "Victoria.",
"sellerId": 202,
"cid": "industry-3,purpose-2,purpose-16,purpose-15",
"tag": null,
"pic": "com/fr/design/mainframe/alphafine/images/local_template1.png",
"price": 0,
"fileLoca": null,
"text": "<ol style=\"list-style-type: decimal;\" class=\" list-paddingleft-2\"><li><p>此方案共包括14张模板,其中12张可视化分析看板、1张分析报表以及1张填报表,需在10.0及以上版本设计器中预览;</p></li><li><p>了解方案详情,可移步-数据分析与可视化指南</p></li><li><p>如果您希望在线体验当前方案,可移步-<a href=\"https://demo.finereport.com/\" target=\"_self\">官方DEMO系统</a>:业务场景应用-&gt;营销管理<br/></p></li><li><p>如果您对此方案感兴趣,希望更加深入了解,可以填写此表单:<a href=\"https://t6ixa9nyl6.jiandaoyun.com/f/60dac9bd282e8e000796eac3\" target=\"_self\">方案需求录入</a>;后续会有帆软行业顾问将与您联系。<br/></p></li></ol>",
"description": "将PDCA循环嵌入销售运营管理的全流程中,从决策层、管理层与执行层三个层级,对目标制定、执行过程、复盘分析、问题跟踪进行全方位精细化管理。",
"updateTime": "2022-06-15T06:36:39.000Z",
"downloadTimes": 1152,
"state": 1,
"designVersion": "10.0",
"involvePlugins": null,
"uploadTime": "2022-06-15T06:36:39.000Z",
"style": null,
"link": "template",
"sellerName": "Victoria.",
"pluginName": [],
"pkgsize": 14,
"material": "方案附件.rar",
"tagsName": "制造加工,营销,组织,管理,经营汇报"
},
{
"id": 20000733,
"name": "库存场景解决方案",
"uuid": "43d1c14b-1a73-41e6-adcc-aaf2872bc8d4",
"vendor": "Victoria.",
"sellerId": 202,
"cid": "industry-3,purpose-5",
"tag": null,
"pic": "com/fr/design/mainframe/alphafine/images/local_template2.png",
"price": 0,
"fileLoca": null,
"text": "<p>当前库存管理面临的现状:库存成本劣势明显、库存周转差距较大。如果对此没有合理有效的解决方案,往往会导致企业库存越来越混乱,经营、资金、成本等问题丛生。</p><p>库存管理解决方案从:“盘”、“析”、“管”三个方向开展,彻底解决库存量大、结构复杂、管理混乱等常见问题</p>",
"description": "库存管理解决方案即从:“盘”、“析”、“管”三个方向开展,对导致库存管理问题的原因逐一击破。",
"updateTime": "2022-05-05T03:53:55.000Z",
"downloadTimes": 816,
"state": 1,
"designVersion": "10.0",
"involvePlugins": null,
"uploadTime": "2022-05-05T03:53:55.000Z",
"style": null,
"link": "template",
"sellerName": "Victoria.",
"pluginName": [],
"pkgsize": 11,
"material": "",
"tagsName":"制造加工,库存"
},
{
"id": 20000581,
"name": "采购场景解决方案",
"uuid": "7994b01f-5069-4554-83cf-9d3506e30767",
"vendor": "Victoria.",
"sellerId": 202,
"cid": "industry-3,purpose-3",
"tag": null,
"pic": "com/fr/design/mainframe/alphafine/images/local_template3.png",
"price": 0,
"fileLoca": null,
"text": "<p>采购场景方案具体细节可参考:<a href=\"https://help.fanruan.com/dvg/doc-view-151.html\" target=\"_self\">可视化指南-采购场景应用</a><br/></p>",
"description": "采购解决方案采用:“自上而下”的分析思路,针对采购相关的不同角色层级及其不同角度发数据分析需求,产出不同的内容",
"updateTime": "2022-03-10T03:50:17.000Z",
"downloadTimes": 2353,
"state": 1,
"designVersion": "10.0",
"involvePlugins": null,
"uploadTime": "2022-03-10T03:50:18.000Z",
"style": null,
"link": "template",
"sellerName": "Victoria.",
"pluginName": [],
"pkgsize": 6,
"material": "",
"tagsName": "制造加工,采购"
},
{
"id": 20000747,
"name": "费用预算系统解决方案",
"uuid": "0776533469c3401a8da78706856b6b02",
"vendor": "finereport",
"sellerId": 1,
"cid": "template_type-1,terminal-1,industry-13,purpose-1",
"tag": null,
"pic": "com/fr/design/mainframe/alphafine/images/local_template4.png",
"price": 0,
"fileLoca": "费用预算系统解决方案.zip",
"text": "<p>模板中使用了数据查询数据集,如果要在本地打开,需要在自己的数据库中建表,并修改数据连接。</p><p>1)建表语句见附件文件夹:SQL语句与表。</p><p><br>2)数据连接默认为 FRDemo,如果用户表所在的数据库连接不是 FRDemo,将模板中数据连接修改为用户默认的数据连接。</p><p><br>3)模板中 SQL 语句为 MYSQL 数据库,若用户使用中数据库语句不匹配,可对应修改为匹配的语句。</p><p><br>4)模板中有大量的超链接,用户存在本地后,预览时注意修改超链接。</p><p><br>5)费用预算系统的平台沿用人事管理系统的平台配置,如果要在本地体验效果,可先下载人事管理系统部署:</span><a href=\"https://help.fanruan.com/dvg/doc-view-6.html?source=0&from=demoshop\" target=\"_blank\" style=\"text-decoration: underline; color: rgb(28, 133, 231); font-family: arial, helvetica, sans-serif;\"><span style=\"font-family: arial, helvetica, sans-serif;\">人事管理系统</span></a><span style=\"font-family: arial, helvetica, sans-serif;\"><br></p><p>模板中图标等背景样式见背景附件。 如果数据替换麻烦,可直接使用内置数据集模板,但内置模板只提供了样式,控件、数据等不能联动。如何制作,可查看帮助文档:</span><a href=\"https://help.fanruan.com/dvg/doc-view-124.html?source=0&from=demoshop\" target=\"_blank\" style=\"text-decoration: underline; color: rgb(28, 133, 231); font-family: arial, helvetica, sans-serif;\"><span style=\"font-family: arial, helvetica, sans-serif;\">费用预算系统</span></a><span style=\"font-family: arial, helvetica, sans-serif;\"></p>",
"description": "费用预算系统是通过 FineReport 填报功能和平台功能结合实现的审批流程系统。能够在线采集数据,提供标准数据模板,解决不同部门、子公司之间数据不统一的问题,\n实现记录预算审批与更改的操作,审批与更改记录留痕等。\n详细内容可查看帮助文档:</span><a href=\"https://help.fanruan.com/dvg/doc-view-124.html?source=0&from=demoshop\" target=\"_blank\" style=\"text-decoration: underline; color: rgb(28, 133, 231); font-family: arial, helvetica, sans-serif;\"><span style=\"font-family: arial, helvetica, sans-serif;\">费用预算系统</span></a><span style=\"font-family: arial, helvetica, sans-serif;\">",
"updateTime": "2022-05-15T05:34:45.000Z",
"downloadTimes": 141,
"state": 1,
"designVersion": "10.0",
"involvePlugins": null,
"uploadTime": "2022-05-15T05:34:45.000Z",
"style": "简约清新",
"link": "template",
"sellerName": "finereport",
"pluginName": [],
"pkgsize": 1,
"material": null,
"tagsName": "IT互联网,财务"
}
]
Loading…
Cancel
Save