From 4df79d29b2886c8fca0b8f24d3440dad42fafaee Mon Sep 17 00:00:00 2001 From: Hoky <303455184@qq.com> Date: Wed, 18 Aug 2021 13:46:28 +0800 Subject: [PATCH 1/6] =?UTF-8?q?REPORT-54887=20=E5=85=AC=E5=BC=8F=E7=BC=96?= =?UTF-8?q?=E8=BE=91=E5=99=A8=E4=BC=98=E5=8C=96=E4=B8=80=E6=9C=9F=201.?= =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E4=BA=86=E5=85=AC=E5=BC=8F=E7=9A=84=E5=8F=82?= =?UTF-8?q?=E6=95=B0=E4=B8=AA=E6=95=B0=E5=92=8C=E5=8F=82=E6=95=B0=E7=B1=BB?= =?UTF-8?q?=E5=9E=8B=E7=9A=84=E6=A0=A1=E9=AA=8C=EF=BC=9B=202.=E6=B7=BB?= =?UTF-8?q?=E5=8A=A0=E4=BA=86=E5=AE=9E=E6=97=B6=E8=AE=A1=E7=AE=97=E7=9A=84?= =?UTF-8?q?=E5=8A=9F=E8=83=BD=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/fr/design/formula/FormulaPane.java | 218 +++++++++++++++--- 1 file changed, 191 insertions(+), 27 deletions(-) diff --git a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java index 8b68dcdbe..d2756c28f 100644 --- a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java +++ b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java @@ -2,32 +2,67 @@ package com.fr.design.formula; import com.fr.base.BaseFormula; import com.fr.base.BaseUtils; +import com.fr.base.Parameter; +import com.fr.base.ParameterMapNameSpace; +import com.fr.base.TableDataNameSpace; +import com.fr.data.TableDataSource; import com.fr.design.actions.UpdateAction; import com.fr.design.border.UIRoundedBorder; import com.fr.design.constants.UIConstants; import com.fr.design.dialog.BasicDialog; import com.fr.design.dialog.BasicPane; +import com.fr.design.dialog.DialogActionAdapter; import com.fr.design.dialog.FineJOptionPane; +import com.fr.design.file.HistoryTemplateListCache; import com.fr.design.gui.ibutton.UIButton; import com.fr.design.gui.icontainer.UIScrollPane; import com.fr.design.gui.ilable.UILabel; import com.fr.design.gui.ilist.QuickList; +import com.fr.design.gui.itableeditorpane.ParameterTableModel; +import com.fr.design.gui.itableeditorpane.UITableEditorPane; import com.fr.design.gui.itextarea.UITextArea; import com.fr.design.gui.itextfield.UITextField; import com.fr.design.gui.syntax.ui.rsyntaxtextarea.RSyntaxTextArea; import com.fr.design.gui.syntax.ui.rsyntaxtextarea.SyntaxConstants; +import com.fr.design.i18n.Toolkit; import com.fr.design.layout.FRGUIPaneFactory; import com.fr.design.mainframe.DesignerContext; +import com.fr.design.parameter.ParameterInputPane; import com.fr.design.utils.gui.GUICoreUtils; import com.fr.general.ComparatorUtils; import com.fr.log.FineLoggerFactory; +import com.fr.main.impl.WorkBook; import com.fr.parser.FRLexer; import com.fr.parser.FRParser; +import com.fr.report.core.namespace.SimpleCellValueNameSpace; +import com.fr.script.Calculator; +import com.fr.script.ScriptConstants; +import com.fr.script.checker.FunctionCheckerDispatcher; +import com.fr.script.checker.exception.FunctionCheckWrongException; +import com.fr.script.rules.FunctionParameterType; +import com.fr.script.rules.FunctionRule; import com.fr.stable.EncodeConstants; +import com.fr.stable.ParameterProvider; import com.fr.stable.StringUtils; +import com.fr.stable.UtilEvalError; +import com.fr.stable.script.ColumnRowRange; import com.fr.stable.script.Expression; - -import javax.swing.*; +import com.fr.stable.script.Node; +import com.fr.stable.script.Tiny; +import com.fr.stable.script.TinyHunter; + +import javax.swing.BorderFactory; +import javax.swing.DefaultListCellRenderer; +import javax.swing.DefaultListModel; +import javax.swing.Icon; +import javax.swing.JComponent; +import javax.swing.JFrame; +import javax.swing.JList; +import javax.swing.JOptionPane; +import javax.swing.JPanel; +import javax.swing.JPopupMenu; +import javax.swing.JTree; +import javax.swing.SwingUtilities; import javax.swing.event.ListSelectionEvent; import javax.swing.event.ListSelectionListener; import javax.swing.event.TreeSelectionEvent; @@ -37,7 +72,10 @@ import javax.swing.tree.DefaultTreeCellRenderer; import javax.swing.tree.DefaultTreeModel; import javax.swing.tree.MutableTreeNode; import javax.swing.tree.TreePath; -import java.awt.*; +import java.awt.BorderLayout; +import java.awt.Color; +import java.awt.Component; +import java.awt.Dimension; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.KeyAdapter; @@ -55,7 +93,11 @@ import java.io.StringReader; import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; +import java.util.HashMap; +import java.util.HashSet; import java.util.List; +import java.util.Map; +import java.util.Set; /** * 公式编辑面板 @@ -65,6 +107,8 @@ import java.util.List; */ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { + public static final String VALID_FORMULA = Toolkit.i18nText("Fine-Design_Basic_FormulaD_Valid_Formula"); + public static final String INVALID_FORMULA = Toolkit.i18nText("Fine-Design_Basic_FormulaD_Invalid_Formula"); private VariableTreeAndDescriptionArea variableTreeAndDescriptionArea; private RSyntaxTextArea formulaTextArea; private UITextField keyWordTextField = new UITextField(18); @@ -78,6 +122,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { private QuickList functionTypeList; private DefaultListModel functionNameModel; private JList functionNameList; + private UITableEditorPane editor4CalPane; public FormulaPane() { initComponents(); @@ -201,6 +246,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { private void initTextPane() { // text + JPanel textPane = FRGUIPaneFactory.createBorderLayout_S_Pane(); this.add(textPane, BorderLayout.CENTER); JPanel checkBoxandbuttonPane = FRGUIPaneFactory.createNormalFlowInnerContainer_S_Pane(); @@ -217,13 +263,19 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { UIButton checkValidButton = new UIButton(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaD_Check_Valid")); + UIButton calButton = new UIButton(Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Button")); checkValidButton.addActionListener(checkValidActionListener); + calButton.addActionListener(calculateActionListener); JPanel checkBoxPane = FRGUIPaneFactory.createNormalFlowInnerContainer_S_Pane(); checkBoxPane.setPreferredSize(new Dimension(450, 30)); checkBoxandbuttonPane.add(checkBoxPane, BorderLayout.WEST); checkBoxandbuttonPane.add(checkValidButton, BorderLayout.EAST); + checkBoxandbuttonPane.add(calButton, BorderLayout.EAST); extendCheckBoxPane(checkBoxPane); + + ParameterTableModel model = new ParameterTableModel(0); + editor4CalPane = new UITableEditorPane<>(model); } @@ -585,39 +637,150 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } // check valid - private ActionListener checkValidActionListener = new ActionListener() { + private final ActionListener checkValidActionListener = new ActionListener() { public void actionPerformed(ActionEvent evt) { // Execute Formula default cell element. String formulaText = formulaTextArea.getText().trim(); + String formulaValidMessage = getFormulaValidMessage(formulaText); + FineJOptionPane.showMessageDialog( + FormulaPane.this, + formulaValidMessage + ".", + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), + JOptionPane.INFORMATION_MESSAGE); + } + }; - if (formulaText != null && formulaText.length() > 0) { - StringReader in = new StringReader(formulaText); + private static String getFormulaValidMessage(String formulaText) { + StringReader in = new StringReader(formulaText); + + FRLexer lexer = new FRLexer(in); + FRParser parser = new FRParser(lexer); + + try { + Expression expression = parser.parse(); + Node node = expression.getConditionalExpression(); + return FunctionCheckerDispatcher.getInstance() + .getFunctionChecker(node) + .checkFunction(node) ? VALID_FORMULA : INVALID_FORMULA; + } catch (FunctionCheckWrongException ce) { + List rules = ce.getRules(); + String functionName = ce.getFunctionName(); + StringBuilder errorMsg = new StringBuilder(functionName + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Error_Tips") + ":"); + for (int i = 0; i < rules.size(); i++) { + errorMsg.append("("); + for (FunctionParameterType functionParameterType : rules.get(i).getParameterList()) { + errorMsg.append(getTypeString(functionParameterType)).append(","); + } + if (",".equals(errorMsg.charAt(errorMsg.length() - 1) + "")) { + errorMsg.deleteCharAt(errorMsg.length() - 1); + } + errorMsg.append(")"); + if (i != rules.size() - 1) { + errorMsg.append(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Or")); + } + } + return errorMsg.toString(); + } catch (Exception e) { + FineLoggerFactory.getLogger().error(e.getMessage(), e); + return INVALID_FORMULA; + // alex:继续往下面走,expression为null时告知不合法公式 + } + } + + private static String getTypeString(FunctionParameterType type) { + switch (type) { + case NUMBER: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Number"); + case STRING: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_String"); + case ANY: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Any"); + case DATE: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Date"); + case BOOLEAN: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Boolean"); + case ARRAY: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Array"); + } + return ""; + } - FRLexer lexer = new FRLexer(in); - FRParser parser = new FRParser(lexer); + private final ActionListener calculateActionListener = new ActionListener() { + @Override + public void actionPerformed(ActionEvent e) { + String formulaText = formulaTextArea.getText().trim(); + String messageTips = getFormulaValidMessage(formulaText).equals(VALID_FORMULA) ? " " : getFormulaValidMessage(formulaText) + "\n"; + Map paramsMap = setParamsIfExist(formulaText); + Calculator calculator = Calculator.createCalculator(); + ParameterMapNameSpace parameterMapNameSpace = ParameterMapNameSpace.create(paramsMap); + calculator.pushNameSpace(parameterMapNameSpace); + + WorkBook workBook = (WorkBook) HistoryTemplateListCache.getInstance().getCurrentEditingTemplate().getTarget(); + calculator.pushNameSpace(SimpleCellValueNameSpace.getInstance()); + TableDataSource tableDataSource = workBook.getReport(0).getTableDataSource(); + calculator.setAttribute(TableDataSource.KEY, tableDataSource); + calculator.pushNameSpace(TableDataNameSpace.getInstance()); + BaseFormula baseFormula = BaseFormula.createFormulaBuilder().build(formulaText); + try { + Object value = calculator.evalValue(baseFormula); + messageTips = messageTips + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Result") + ":" + value; + FineLoggerFactory.getLogger().info("value:{}", value); + } catch (UtilEvalError utilEvalError) { + FineLoggerFactory.getLogger().error("", utilEvalError); + } + FineJOptionPane.showMessageDialog( + FormulaPane.this, + messageTips, + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), + JOptionPane.INFORMATION_MESSAGE); - Expression expression = null; - try { - expression = parser.parse(); - } catch (Exception e) { - FineLoggerFactory.getLogger().error(e.getMessage(), e); - // alex:继续往下面走,expression为null时告知不合法公式 + } + }; + + private Map setParamsIfExist(String formulaText) { + Map parameterMap = new HashMap<>(); + try { + Expression expression = Calculator.createCalculator().parse(formulaText); + ParameterCellHunter parameterCellHunter = new ParameterCellHunter(); + expression.traversal4Tiny(parameterCellHunter); + Parameter[] parameters = parameterCellHunter.getParameterBooty(); + + if (parameters.length < 1 && editor4CalPane.update().size() < 1) { + return parameterMap; + } + ParameterInputPane pPane = new ParameterInputPane(parameters); + pPane.showSmallWindow(new JFrame(), new DialogActionAdapter() { + @Override + public void doOk() { + parameterMap.putAll(pPane.update()); } + }).setVisible(true); + } catch (Exception e) { + FineLoggerFactory.getLogger().error("", e); + } + + return parameterMap; + } + + private static class ParameterCellHunter extends TinyHunter { + + private final Set parameterList = new HashSet<>(); + + Parameter[] getParameterBooty() { - FineJOptionPane.showMessageDialog( - FormulaPane.this, - /* - * alex:仅仅只需要根据expression是否为null作合法性判断 - * 不需要eval - * TODO 但有个问题,有些函数的参数个数是有规定的,何以判别之 - */ - (expression != null ? com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaD_Valid_Formula") : com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaD_Invalid_Formula")) + ".", - com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), - JOptionPane.INFORMATION_MESSAGE); + return parameterList.toArray(new Parameter[0]); + } + + public void hunter4Tiny(Tiny tiny) { + String statement = tiny.getStatement(); + if (StringUtils.isNotBlank(statement) && statement.startsWith(ScriptConstants.DETAIL_TAG)) { + parameterList.add(new Parameter(statement.substring(1))); + } else if (tiny.getClass().equals(ColumnRowRange.class)) { + parameterList.add(new Parameter(tiny.toString())); } } - }; + } public class VariableTreeAndDescriptionArea extends JPanel { @@ -805,13 +968,13 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { public void valueChanged(TreeSelectionEvent e) { DefaultMutableTreeNode selectedTreeNode = (DefaultMutableTreeNode) variablesTree.getLastSelectedPathComponent(); Object selectedValue = selectedTreeNode.getUserObject(); - Object selectedParentValue = ((DefaultMutableTreeNode)selectedTreeNode.getParent()).getUserObject(); + Object selectedParentValue = ((DefaultMutableTreeNode) selectedTreeNode.getParent()).getUserObject(); if (selectedValue == null) { return; } - if (selectedValue instanceof TextUserObject) { + if (selectedValue instanceof TextUserObject) { //有公式说明的条件:1.属于TextUserObject 2.parent是系统参数 if (ComparatorUtils.equals(((TextFolderUserObject) selectedParentValue).getText(), com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaPane_Variables"))) { @@ -1010,6 +1173,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { /** * 把以关键词开头的和不以关键词开头的分别按照字母表顺序排序 + * * @param o1 待比较对象1 * @param o2 待比较对象2 * @return 比较结果,1表示 o1 > o2, -1表示 o1 < o2, 0表示 o1 = o2 From 2b43c7d0e67fb4c56fa0a69addc8b9994db65ee0 Mon Sep 17 00:00:00 2001 From: Hoky <303455184@qq.com> Date: Mon, 23 Aug 2021 17:46:01 +0800 Subject: [PATCH 2/6] =?UTF-8?q?REPORT-57892=20=E5=85=AC=E5=BC=8F=E7=BC=96?= =?UTF-8?q?=E8=BE=91=E5=99=A8=E4=BC=98=E5=8C=96=EF=BC=9A=E5=AE=9E=E6=97=B6?= =?UTF-8?q?=E8=AE=A1=E7=AE=97=E8=BF=94=E5=9B=9E=E7=BB=93=E6=9E=9C=E4=B8=BA?= =?UTF-8?q?=E6=97=A5=E6=9C=9F=E6=A0=BC=E5=BC=8F=E6=97=B6=E4=B8=8D=E6=AD=A3?= =?UTF-8?q?=E7=A1=AE=201.=E6=B7=BB=E5=8A=A0=E4=B8=80=E4=B8=AAobject2string?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/main/java/com/fr/design/formula/FormulaPane.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java index d2756c28f..7c4bde420 100644 --- a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java +++ b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java @@ -30,6 +30,7 @@ import com.fr.design.mainframe.DesignerContext; import com.fr.design.parameter.ParameterInputPane; import com.fr.design.utils.gui.GUICoreUtils; import com.fr.general.ComparatorUtils; +import com.fr.general.GeneralUtils; import com.fr.log.FineLoggerFactory; import com.fr.main.impl.WorkBook; import com.fr.parser.FRLexer; @@ -724,7 +725,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { BaseFormula baseFormula = BaseFormula.createFormulaBuilder().build(formulaText); try { Object value = calculator.evalValue(baseFormula); - messageTips = messageTips + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Result") + ":" + value; + messageTips = messageTips + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Result") + ":" + GeneralUtils.objectToString(value); FineLoggerFactory.getLogger().info("value:{}", value); } catch (UtilEvalError utilEvalError) { FineLoggerFactory.getLogger().error("", utilEvalError); From 76e92ae71bd15bbc946242034ec3c2a263cf2445 Mon Sep 17 00:00:00 2001 From: Hoky <303455184@qq.com> Date: Mon, 30 Aug 2021 16:30:32 +0800 Subject: [PATCH 3/6] =?UTF-8?q?REPORT-58124=20=E5=85=AC=E5=BC=8F=E7=BC=96?= =?UTF-8?q?=E8=BE=91=E5=99=A8=E4=BC=98=E5=8C=96=EF=BC=9A=E4=B8=8D=E6=94=AF?= =?UTF-8?q?=E6=8C=81=E5=AE=9E=E6=97=B6=E8=AE=A1=E7=AE=97=E7=9A=84=E5=8A=9F?= =?UTF-8?q?=E8=83=BD=E6=8F=90=E7=A4=BA=E5=A4=84=E7=90=86=201.=E4=BF=AE?= =?UTF-8?q?=E6=94=B9=E9=81=8D=E5=8E=86=E4=B8=8D=E6=94=AF=E6=8C=81=E5=85=AC?= =?UTF-8?q?=E5=BC=8F=E7=9A=84=E9=80=BB=E8=BE=91?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/fr/design/formula/FormulaPane.java | 136 ++++++++++++++---- .../formula/UnsupportedFormulaScanner.java | 49 +++++++ 2 files changed, 160 insertions(+), 25 deletions(-) create mode 100644 designer-base/src/main/java/com/fr/design/formula/UnsupportedFormulaScanner.java diff --git a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java index 7c4bde420..f836cd571 100644 --- a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java +++ b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java @@ -5,6 +5,7 @@ import com.fr.base.BaseUtils; import com.fr.base.Parameter; import com.fr.base.ParameterMapNameSpace; import com.fr.base.TableDataNameSpace; +import com.fr.base.io.IOFile; import com.fr.data.TableDataSource; import com.fr.design.actions.UpdateAction; import com.fr.design.border.UIRoundedBorder; @@ -27,22 +28,28 @@ import com.fr.design.gui.syntax.ui.rsyntaxtextarea.SyntaxConstants; import com.fr.design.i18n.Toolkit; import com.fr.design.layout.FRGUIPaneFactory; import com.fr.design.mainframe.DesignerContext; +import com.fr.design.mainframe.JTemplate; import com.fr.design.parameter.ParameterInputPane; import com.fr.design.utils.gui.GUICoreUtils; import com.fr.general.ComparatorUtils; -import com.fr.general.GeneralUtils; +import com.fr.general.FArray; import com.fr.log.FineLoggerFactory; -import com.fr.main.impl.WorkBook; +import com.fr.parser.ArrayExpression; +import com.fr.parser.BlockIntervalLiteral; +import com.fr.parser.ColumnRowRangeInPage; import com.fr.parser.FRLexer; import com.fr.parser.FRParser; +import com.fr.parser.SheetIntervalLiteral; import com.fr.report.core.namespace.SimpleCellValueNameSpace; import com.fr.script.Calculator; import com.fr.script.ScriptConstants; import com.fr.script.checker.FunctionCheckerDispatcher; +import com.fr.script.checker.exception.ConditionCheckWrongException; import com.fr.script.checker.exception.FunctionCheckWrongException; import com.fr.script.rules.FunctionParameterType; import com.fr.script.rules.FunctionRule; import com.fr.stable.EncodeConstants; +import com.fr.stable.EssentialUtils; import com.fr.stable.ParameterProvider; import com.fr.stable.StringUtils; import com.fr.stable.UtilEvalError; @@ -110,6 +117,8 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { public static final String VALID_FORMULA = Toolkit.i18nText("Fine-Design_Basic_FormulaD_Valid_Formula"); public static final String INVALID_FORMULA = Toolkit.i18nText("Fine-Design_Basic_FormulaD_Invalid_Formula"); + public static final int DEFUAL_FOMULA_LENGTH = 103; + public static final String ELLIPSIS = "..."; private VariableTreeAndDescriptionArea variableTreeAndDescriptionArea; private RSyntaxTextArea formulaTextArea; private UITextField keyWordTextField = new UITextField(18); @@ -664,12 +673,19 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { return FunctionCheckerDispatcher.getInstance() .getFunctionChecker(node) .checkFunction(node) ? VALID_FORMULA : INVALID_FORMULA; + } catch (ConditionCheckWrongException cce) { + String functionName = cce.getFunctionName(); + StringBuilder errorMsg = new StringBuilder(functionName + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Condition_Tips") + ":"); + return errorMsg.toString(); } catch (FunctionCheckWrongException ce) { List rules = ce.getRules(); String functionName = ce.getFunctionName(); StringBuilder errorMsg = new StringBuilder(functionName + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Error_Tips") + ":"); for (int i = 0; i < rules.size(); i++) { errorMsg.append("("); + if (rules.get(i).getParameterList().isEmpty()) { + errorMsg.append(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_No_Param")); + } for (FunctionParameterType functionParameterType : rules.get(i).getParameterList()) { errorMsg.append(getTypeString(functionParameterType)).append(","); } @@ -711,38 +727,77 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { @Override public void actionPerformed(ActionEvent e) { String formulaText = formulaTextArea.getText().trim(); - String messageTips = getFormulaValidMessage(formulaText).equals(VALID_FORMULA) ? " " : getFormulaValidMessage(formulaText) + "\n"; - Map paramsMap = setParamsIfExist(formulaText); - Calculator calculator = Calculator.createCalculator(); - ParameterMapNameSpace parameterMapNameSpace = ParameterMapNameSpace.create(paramsMap); - calculator.pushNameSpace(parameterMapNameSpace); - - WorkBook workBook = (WorkBook) HistoryTemplateListCache.getInstance().getCurrentEditingTemplate().getTarget(); - calculator.pushNameSpace(SimpleCellValueNameSpace.getInstance()); - TableDataSource tableDataSource = workBook.getReport(0).getTableDataSource(); - calculator.setAttribute(TableDataSource.KEY, tableDataSource); - calculator.pushNameSpace(TableDataNameSpace.getInstance()); - BaseFormula baseFormula = BaseFormula.createFormulaBuilder().build(formulaText); - try { - Object value = calculator.evalValue(baseFormula); - messageTips = messageTips + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Result") + ":" + GeneralUtils.objectToString(value); - FineLoggerFactory.getLogger().info("value:{}", value); - } catch (UtilEvalError utilEvalError) { - FineLoggerFactory.getLogger().error("", utilEvalError); + String formulaValidMessage = getFormulaValidMessage(formulaText); + String unSupportFormula = containsUnsupportedSimulationFormulas(formulaText); + if (unSupportFormula != null) { + FineJOptionPane.showMessageDialog( + FormulaPane.this, + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Unsupported_Formulas") + ":" + unSupportFormula, + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), + JOptionPane.INFORMATION_MESSAGE); + return; + } + String messageTips; + if (formulaValidMessage.equals(INVALID_FORMULA)) { + messageTips = INVALID_FORMULA; + } else { + messageTips = formulaValidMessage.equals(VALID_FORMULA) ? "" : formulaValidMessage + "\n"; + Map paramsMap = setParamsIfExist(formulaText); + Calculator calculator = Calculator.createCalculator(); + ParameterMapNameSpace parameterMapNameSpace = ParameterMapNameSpace.create(paramsMap); + calculator.pushNameSpace(parameterMapNameSpace); + + JTemplate currentEditingTemplate = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate(); + if (currentEditingTemplate != null) { + IOFile file = (IOFile) currentEditingTemplate.getTarget(); + calculator.setAttribute(TableDataSource.KEY, file); + calculator.pushNameSpace(TableDataNameSpace.getInstance()); + calculator.pushNameSpace(SimpleCellValueNameSpace.getInstance()); + } + + BaseFormula baseFormula = BaseFormula.createFormulaBuilder().build(formulaText); + try { + Object value = calculator.evalValue(baseFormula); + String objectToString = EssentialUtils.objectToString(value); + String result = objectToString.length() > DEFUAL_FOMULA_LENGTH ? + objectToString.substring(0, DEFUAL_FOMULA_LENGTH - ELLIPSIS.length()) + ELLIPSIS : objectToString; + messageTips = messageTips + + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Result") + ":" + result; + FineLoggerFactory.getLogger().info("value:{}", value); + } catch (UtilEvalError utilEvalError) { + FineLoggerFactory.getLogger().error("", utilEvalError); + } } FineJOptionPane.showMessageDialog( FormulaPane.this, messageTips, com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), JOptionPane.INFORMATION_MESSAGE); - } }; + private String containsUnsupportedSimulationFormulas(String formulaText) { + try { + Expression expression = Calculator.createCalculator().parse(formulaText); + UnsupportedFormulaScanner scanner = new UnsupportedFormulaScanner(); + if (!scanner.travelFormula(expression.getConditionalExpression())) { + return scanner.getUnSupportFormula(); + } + + UnsupportedSimulationFormulaHunter unsupportedSimulationFormulaHunter = new UnsupportedSimulationFormulaHunter(); + expression.traversal4Tiny(unsupportedSimulationFormulaHunter); + return unsupportedSimulationFormulaHunter.isSupported() ? null : unsupportedSimulationFormulaHunter.getUnSupportFormula(); + } catch (Exception e) { + FineLoggerFactory.getLogger().error("", e); + } + return null; + } + private Map setParamsIfExist(String formulaText) { Map parameterMap = new HashMap<>(); try { - Expression expression = Calculator.createCalculator().parse(formulaText); + Calculator calculator = Calculator.createCalculator(); + Expression expression = calculator.parse(formulaText); ParameterCellHunter parameterCellHunter = new ParameterCellHunter(); expression.traversal4Tiny(parameterCellHunter); Parameter[] parameters = parameterCellHunter.getParameterBooty(); @@ -757,10 +812,18 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { parameterMap.putAll(pPane.update()); } }).setVisible(true); + //过滤出数组参数,如:[1,2] + for (Map.Entry entry : parameterMap.entrySet()) { + if (entry.getValue().toString().startsWith("[") && entry.getValue().toString().endsWith("]")) { + Expression parse = calculator.parse(entry.getValue()); + ArrayExpression arrayExpression = (ArrayExpression) parse.getConditionalExpression(); + FArray fArray = new FArray<>(arrayExpression.getArrays()); + parameterMap.put(entry.getKey(), fArray); + } + } } catch (Exception e) { FineLoggerFactory.getLogger().error("", e); } - return parameterMap; } @@ -769,7 +832,6 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { private final Set parameterList = new HashSet<>(); Parameter[] getParameterBooty() { - return parameterList.toArray(new Parameter[0]); } @@ -777,12 +839,36 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { String statement = tiny.getStatement(); if (StringUtils.isNotBlank(statement) && statement.startsWith(ScriptConstants.DETAIL_TAG)) { parameterList.add(new Parameter(statement.substring(1))); - } else if (tiny.getClass().equals(ColumnRowRange.class)) { + } else if (tiny.getClass() == ColumnRowRange.class || + tiny.getClass() == SheetIntervalLiteral.class || tiny.getClass() == BlockIntervalLiteral.class) { parameterList.add(new Parameter(tiny.toString())); } } } + private static class UnsupportedSimulationFormulaHunter extends TinyHunter { + + + private boolean supported = true; + + private String unSupportFormula; + + public boolean isSupported() { + return supported; + } + + public String getUnSupportFormula() { + return unSupportFormula; + } + + public void hunter4Tiny(Tiny tiny) { + if (tiny.getClass() == ColumnRowRangeInPage.class) { + supported = false; + unSupportFormula = tiny.toString(); + } + } + } + public class VariableTreeAndDescriptionArea extends JPanel { private JTree variablesTree; diff --git a/designer-base/src/main/java/com/fr/design/formula/UnsupportedFormulaScanner.java b/designer-base/src/main/java/com/fr/design/formula/UnsupportedFormulaScanner.java new file mode 100644 index 000000000..343086af5 --- /dev/null +++ b/designer-base/src/main/java/com/fr/design/formula/UnsupportedFormulaScanner.java @@ -0,0 +1,49 @@ +package com.fr.design.formula; + +import com.fr.parser.BinaryExpression; +import com.fr.parser.FunctionCall; +import com.fr.stable.script.Node; + +import java.util.Arrays; + +/** + * @author Hoky + * @date 2021/8/30 + */ +public class UnsupportedFormulaScanner { + public final static String[] UNSUPPORTED_FORMULAS = new String[]{"PROPORTION", "TOIMAGE", + "WEBIMAGE", "SORT", "CROSSLAYERTOTAL", "CIRCULAR", "LAYERTOTAL", "MOM", "HIERARCHY", + "FILENAME", "FILESIZE", "FILETYPE", "TREELAYER", "GETUSERDEPARTMENTS", "GETUSERJOBTITLES"}; + + private String unSupportFormula = ""; + + public boolean travelFormula(Node node) { + if (node instanceof FunctionCall) { + if (isUnsupportedFomula(((FunctionCall) node).getName())) { + unSupportFormula = ((FunctionCall) node).getName(); + return false; + } else { + for (Node argument : ((FunctionCall) node).getArguments()) { + if (!travelFormula(argument)) { + return false; + } + } + } + } else if (node instanceof BinaryExpression) { + for (Node array : ((BinaryExpression) node).getNodes()) { + if (!travelFormula(array)) { + return false; + } + } + } + return true; + } + + public String getUnSupportFormula() { + return unSupportFormula; + } + + private static boolean isUnsupportedFomula(String formula) { + return Arrays.asList(UNSUPPORTED_FORMULAS).contains(formula.toUpperCase()); + } +} From b8ec812d9ef10c8874b1f39db41e237f5a33a55a Mon Sep 17 00:00:00 2001 From: Hoky <303455184@qq.com> Date: Mon, 30 Aug 2021 14:31:13 +0800 Subject: [PATCH 4/6] =?UTF-8?q?=E8=A7=A3=E5=86=B3=E5=86=B2=E7=AA=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/fr/design/formula/FormulaPane.java | 508 ++++-------------- 1 file changed, 97 insertions(+), 411 deletions(-) diff --git a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java index f836cd571..e7319b73f 100644 --- a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java +++ b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java @@ -2,69 +2,36 @@ package com.fr.design.formula; import com.fr.base.BaseFormula; import com.fr.base.BaseUtils; -import com.fr.base.Parameter; -import com.fr.base.ParameterMapNameSpace; -import com.fr.base.TableDataNameSpace; -import com.fr.base.io.IOFile; -import com.fr.data.TableDataSource; +import com.fr.base.FRContext; import com.fr.design.actions.UpdateAction; import com.fr.design.border.UIRoundedBorder; import com.fr.design.constants.UIConstants; import com.fr.design.dialog.BasicDialog; import com.fr.design.dialog.BasicPane; -import com.fr.design.dialog.DialogActionAdapter; -import com.fr.design.dialog.FineJOptionPane; -import com.fr.design.file.HistoryTemplateListCache; import com.fr.design.gui.ibutton.UIButton; import com.fr.design.gui.icontainer.UIScrollPane; import com.fr.design.gui.ilable.UILabel; import com.fr.design.gui.ilist.QuickList; -import com.fr.design.gui.itableeditorpane.ParameterTableModel; -import com.fr.design.gui.itableeditorpane.UITableEditorPane; import com.fr.design.gui.itextarea.UITextArea; import com.fr.design.gui.itextfield.UITextField; import com.fr.design.gui.syntax.ui.rsyntaxtextarea.RSyntaxTextArea; import com.fr.design.gui.syntax.ui.rsyntaxtextarea.SyntaxConstants; -import com.fr.design.i18n.Toolkit; import com.fr.design.layout.FRGUIPaneFactory; import com.fr.design.mainframe.DesignerContext; -import com.fr.design.mainframe.JTemplate; -import com.fr.design.parameter.ParameterInputPane; import com.fr.design.utils.gui.GUICoreUtils; -import com.fr.general.ComparatorUtils; -import com.fr.general.FArray; import com.fr.log.FineLoggerFactory; -import com.fr.parser.ArrayExpression; -import com.fr.parser.BlockIntervalLiteral; -import com.fr.parser.ColumnRowRangeInPage; import com.fr.parser.FRLexer; import com.fr.parser.FRParser; -import com.fr.parser.SheetIntervalLiteral; -import com.fr.report.core.namespace.SimpleCellValueNameSpace; -import com.fr.script.Calculator; -import com.fr.script.ScriptConstants; -import com.fr.script.checker.FunctionCheckerDispatcher; -import com.fr.script.checker.exception.ConditionCheckWrongException; -import com.fr.script.checker.exception.FunctionCheckWrongException; -import com.fr.script.rules.FunctionParameterType; -import com.fr.script.rules.FunctionRule; import com.fr.stable.EncodeConstants; -import com.fr.stable.EssentialUtils; -import com.fr.stable.ParameterProvider; +import com.fr.stable.ProductConstants; import com.fr.stable.StringUtils; -import com.fr.stable.UtilEvalError; -import com.fr.stable.script.ColumnRowRange; import com.fr.stable.script.Expression; -import com.fr.stable.script.Node; -import com.fr.stable.script.Tiny; -import com.fr.stable.script.TinyHunter; import javax.swing.BorderFactory; import javax.swing.DefaultListCellRenderer; import javax.swing.DefaultListModel; import javax.swing.Icon; import javax.swing.JComponent; -import javax.swing.JFrame; import javax.swing.JList; import javax.swing.JOptionPane; import javax.swing.JPanel; @@ -98,14 +65,7 @@ import java.io.InputStream; import java.io.InputStreamReader; import java.io.Reader; import java.io.StringReader; -import java.util.ArrayList; -import java.util.Collections; -import java.util.Comparator; -import java.util.HashMap; -import java.util.HashSet; -import java.util.List; -import java.util.Map; -import java.util.Set; +import java.util.Locale; /** * 公式编辑面板 @@ -115,24 +75,19 @@ import java.util.Set; */ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { - public static final String VALID_FORMULA = Toolkit.i18nText("Fine-Design_Basic_FormulaD_Valid_Formula"); - public static final String INVALID_FORMULA = Toolkit.i18nText("Fine-Design_Basic_FormulaD_Invalid_Formula"); - public static final int DEFUAL_FOMULA_LENGTH = 103; - public static final String ELLIPSIS = "..."; - private VariableTreeAndDescriptionArea variableTreeAndDescriptionArea; - private RSyntaxTextArea formulaTextArea; - private UITextField keyWordTextField = new UITextField(18); - private int currentPosition = 0; - private int beginPosition = 0; - private int insertPosition = 0; - private JList tipsList; + protected VariableTreeAndDescriptionArea variableTreeAndDescriptionArea; + protected RSyntaxTextArea formulaTextArea; + protected UITextField keyWordTextField = new UITextField(18); + protected int currentPosition = 0; + protected int beginPosition = 0; + protected int insertPosition = 0; + protected JList tipsList; protected DefaultListModel listModel = new DefaultListModel(); - private int ifHasBeenWriten = 0; - private DefaultListModel functionTypeListModel = new DefaultListModel(); - private QuickList functionTypeList; - private DefaultListModel functionNameModel; - private JList functionNameList; - private UITableEditorPane editor4CalPane; + protected int ifHasBeenWriten = 0; + protected DefaultListModel functionTypeListModel = new DefaultListModel(); + protected QuickList functionTypeList; + protected DefaultListModel functionNameModel; + protected JList functionNameList; public FormulaPane() { initComponents(); @@ -193,12 +148,10 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { keyWordTextField.addKeyListener(new KeyListener() { @Override public void keyTyped(KeyEvent e) { - //do nothing } @Override public void keyReleased(KeyEvent e) { - //do nothing } @Override @@ -243,20 +196,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { protected void initComponents() { this.setLayout(new BorderLayout(4, 4)); - - initTextPane(); - initTipsPane(); - initVariableTreeAndDescriptionArea(); - } - - private void initVariableTreeAndDescriptionArea() { - variableTreeAndDescriptionArea = new VariableTreeAndDescriptionArea(); - this.add(variableTreeAndDescriptionArea, BorderLayout.SOUTH); - } - - private void initTextPane() { // text - JPanel textPane = FRGUIPaneFactory.createBorderLayout_S_Pane(); this.add(textPane, BorderLayout.CENTER); JPanel checkBoxandbuttonPane = FRGUIPaneFactory.createNormalFlowInnerContainer_S_Pane(); @@ -271,29 +211,26 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { textPane.add(formulaTextAreaScrollPane, BorderLayout.CENTER); textPane.add(checkBoxandbuttonPane, BorderLayout.SOUTH); + initTipsPane(); UIButton checkValidButton = new UIButton(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaD_Check_Valid")); - UIButton calButton = new UIButton(Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Button")); checkValidButton.addActionListener(checkValidActionListener); - calButton.addActionListener(calculateActionListener); JPanel checkBoxPane = FRGUIPaneFactory.createNormalFlowInnerContainer_S_Pane(); checkBoxPane.setPreferredSize(new Dimension(450, 30)); checkBoxandbuttonPane.add(checkBoxPane, BorderLayout.WEST); checkBoxandbuttonPane.add(checkValidButton, BorderLayout.EAST); - checkBoxandbuttonPane.add(calButton, BorderLayout.EAST); extendCheckBoxPane(checkBoxPane); - - ParameterTableModel model = new ParameterTableModel(0); - editor4CalPane = new UITableEditorPane<>(model); + variableTreeAndDescriptionArea = new VariableTreeAndDescriptionArea(); + this.add(variableTreeAndDescriptionArea, BorderLayout.SOUTH); } protected void extendCheckBoxPane(JPanel checkBoxPane) { - // do nothing + } - private void configFormulaArea() { + protected void configFormulaArea() { formulaTextArea.setSyntaxEditingStyle(SyntaxConstants.SYNTAX_STYLE_FORMULA); formulaTextArea.setAnimateBracketMatching(true); formulaTextArea.setAntiAliasingEnabled(true); @@ -308,68 +245,43 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } public class DoubleClick extends MouseAdapter { - String singlePressContent; - - String doublePressContent; @Override - public void mousePressed(MouseEvent e) { + public void mouseClicked(MouseEvent e) { int index = tipsList.getSelectedIndex(); if (index != -1) { - if (e.getClickCount() == 1) { - singlePressContent = (String) listModel.getElementAt(index); - } else if (e.getClickCount() == 2) { - doublePressContent = (String) listModel.getElementAt(index); - } - } - } - - @Override - public void mouseReleased(MouseEvent e) { - int index = tipsList.getSelectedIndex(); - if (index != -1) { - if (e.getClickCount() == 1) { - if (ComparatorUtils.equals((String) listModel.getElementAt(index), singlePressContent)) { - singleClickActuator(singlePressContent); + String currentLineContent = (String) listModel.getElementAt(index); + if (e.getClickCount() == 2) { + if (ifHasBeenWriten == 0) { + formulaTextArea.setForeground(Color.black); + formulaTextArea.setText(""); } - } else if (e.getClickCount() == 2) { - if (ComparatorUtils.equals((String) listModel.getElementAt(index), doublePressContent)) { - doubleClickActuator(doublePressContent); + formulaTextArea.setForeground(Color.black); + currentPosition = formulaTextArea.getCaretPosition(); + String output = currentLineContent + "()"; + String textAll = formulaTextArea.getText(); + String textReplaced; + int position = 0; + if (insertPosition <= currentPosition) { + textReplaced = textAll.substring(0, insertPosition) + output + textAll.substring(currentPosition); + position = insertPosition + output.length() - 1; + } else { + textReplaced = textAll.substring(0, currentPosition) + output + textAll.substring(insertPosition); + position = currentPosition + output.length() - 1; } - } - } - } - - private void singleClickActuator(String currentLineContent) { - refreshDescriptionTextArea(currentLineContent); - formulaTextArea.requestFocusInWindow(); - fixFunctionNameList(); - } + formulaTextArea.setText(textReplaced); + formulaTextArea.requestFocusInWindow(); + formulaTextArea.setCaretPosition(position); + insertPosition = position; + ifHasBeenWriten = 1; + listModel.removeAllElements(); + } else if (e.getClickCount() == 1) { + refreshDescriptionTextArea(currentLineContent); - private void doubleClickActuator(String currentLineContent) { - if (ifHasBeenWriten == 0) { - formulaTextArea.setForeground(Color.black); - formulaTextArea.setText(""); - } - formulaTextArea.setForeground(Color.black); - currentPosition = formulaTextArea.getCaretPosition(); - String output = currentLineContent + "()"; - String textAll = formulaTextArea.getText(); - String textReplaced; - int position = 0; - if (insertPosition <= currentPosition) { - textReplaced = textAll.substring(0, insertPosition) + output + textAll.substring(currentPosition); - position = insertPosition + output.length() - 1; - } else { - textReplaced = textAll.substring(0, currentPosition) + output + textAll.substring(insertPosition); - position = currentPosition + output.length() - 1; + formulaTextArea.requestFocusInWindow(); + fixFunctionNameList(); + } } - formulaTextArea.setText(textReplaced); - formulaTextArea.requestFocusInWindow(); - formulaTextArea.setCaretPosition(position); - insertPosition = position; - ifHasBeenWriten = 1; - listModel.removeAllElements(); } } @@ -413,7 +325,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } } - private void fixFunctionNameList() { + protected void fixFunctionNameList() { if (tipsList.getSelectedValue() != null) { int signOfContinue = 1; int indexOfFunction = 0; @@ -446,7 +358,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } - private int getBeginPosition() { + protected int getBeginPosition() { int i = currentPosition; String textArea = formulaTextArea.getText(); for (; i > 0; i--) { @@ -461,7 +373,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { return i; } - private void firstStepToFindTips(int theBeginPosition) { + protected void firstStepToFindTips(int theBeginPosition) { String textArea = formulaTextArea.getText(); if (currentPosition > 0 && theBeginPosition < currentPosition) { @@ -491,7 +403,6 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { @Override public void keyTyped(KeyEvent e) { - // do nothing } protected void search(String keyWord, boolean findDescription) { @@ -501,19 +412,14 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { if (keyWord.length() != 0) { NameAndDescription[] descriptions = FunctionConstants.ALL.getDescriptions(); int lengthOfDes = descriptions.length; - List list = new ArrayList<>(); for (int i = 0; i < lengthOfDes; i++) { NameAndDescription and = descriptions[i]; String functionName = and.searchResult(keyWord, findDescription); if (StringUtils.isNotBlank(functionName)) { - list.add(functionName); + listModel.addElement(functionName); } } - Collections.sort(list, new SimilarComparator(keyWord)); - for (String name : list) { - listModel.addElement(name); - } if (!listModel.isEmpty()) { tipsList.setSelectedIndex(0); @@ -549,7 +455,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { /** * Apply text. */ - private void applyText(String text) { + public void applyText(String text) { if (text == null || text.length() <= 0) { return; } @@ -647,234 +553,45 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } // check valid - private final ActionListener checkValidActionListener = new ActionListener() { + protected ActionListener checkValidActionListener = new ActionListener() { public void actionPerformed(ActionEvent evt) { // Execute Formula default cell element. String formulaText = formulaTextArea.getText().trim(); - String formulaValidMessage = getFormulaValidMessage(formulaText); - FineJOptionPane.showMessageDialog( - FormulaPane.this, - formulaValidMessage + ".", - com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), - JOptionPane.INFORMATION_MESSAGE); - } - }; - private static String getFormulaValidMessage(String formulaText) { - StringReader in = new StringReader(formulaText); - - FRLexer lexer = new FRLexer(in); - FRParser parser = new FRParser(lexer); - - try { - Expression expression = parser.parse(); - Node node = expression.getConditionalExpression(); - return FunctionCheckerDispatcher.getInstance() - .getFunctionChecker(node) - .checkFunction(node) ? VALID_FORMULA : INVALID_FORMULA; - } catch (ConditionCheckWrongException cce) { - String functionName = cce.getFunctionName(); - StringBuilder errorMsg = new StringBuilder(functionName + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Condition_Tips") + ":"); - return errorMsg.toString(); - } catch (FunctionCheckWrongException ce) { - List rules = ce.getRules(); - String functionName = ce.getFunctionName(); - StringBuilder errorMsg = new StringBuilder(functionName + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Error_Tips") + ":"); - for (int i = 0; i < rules.size(); i++) { - errorMsg.append("("); - if (rules.get(i).getParameterList().isEmpty()) { - errorMsg.append(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_No_Param")); - } - for (FunctionParameterType functionParameterType : rules.get(i).getParameterList()) { - errorMsg.append(getTypeString(functionParameterType)).append(","); - } - if (",".equals(errorMsg.charAt(errorMsg.length() - 1) + "")) { - errorMsg.deleteCharAt(errorMsg.length() - 1); - } - errorMsg.append(")"); - if (i != rules.size() - 1) { - errorMsg.append(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Or")); - } - } - return errorMsg.toString(); - } catch (Exception e) { - FineLoggerFactory.getLogger().error(e.getMessage(), e); - return INVALID_FORMULA; - // alex:继续往下面走,expression为null时告知不合法公式 - } - } + if (formulaText != null && formulaText.length() > 0) { + StringReader in = new StringReader(formulaText); - private static String getTypeString(FunctionParameterType type) { - switch (type) { - case NUMBER: - return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Number"); - case STRING: - return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_String"); - case ANY: - return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Any"); - case DATE: - return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Date"); - case BOOLEAN: - return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Boolean"); - case ARRAY: - return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Array"); - } - return ""; - } - - private final ActionListener calculateActionListener = new ActionListener() { - @Override - public void actionPerformed(ActionEvent e) { - String formulaText = formulaTextArea.getText().trim(); - String formulaValidMessage = getFormulaValidMessage(formulaText); - String unSupportFormula = containsUnsupportedSimulationFormulas(formulaText); - if (unSupportFormula != null) { - FineJOptionPane.showMessageDialog( - FormulaPane.this, - com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Unsupported_Formulas") + ":" + unSupportFormula, - com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), - JOptionPane.INFORMATION_MESSAGE); - return; - } - String messageTips; - if (formulaValidMessage.equals(INVALID_FORMULA)) { - messageTips = INVALID_FORMULA; - } else { - messageTips = formulaValidMessage.equals(VALID_FORMULA) ? "" : formulaValidMessage + "\n"; - Map paramsMap = setParamsIfExist(formulaText); - Calculator calculator = Calculator.createCalculator(); - ParameterMapNameSpace parameterMapNameSpace = ParameterMapNameSpace.create(paramsMap); - calculator.pushNameSpace(parameterMapNameSpace); - - JTemplate currentEditingTemplate = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate(); - if (currentEditingTemplate != null) { - IOFile file = (IOFile) currentEditingTemplate.getTarget(); - calculator.setAttribute(TableDataSource.KEY, file); - calculator.pushNameSpace(TableDataNameSpace.getInstance()); - calculator.pushNameSpace(SimpleCellValueNameSpace.getInstance()); - } + FRLexer lexer = new FRLexer(in); + FRParser parser = new FRParser(lexer); - BaseFormula baseFormula = BaseFormula.createFormulaBuilder().build(formulaText); + Expression expression = null; try { - Object value = calculator.evalValue(baseFormula); - String objectToString = EssentialUtils.objectToString(value); - String result = objectToString.length() > DEFUAL_FOMULA_LENGTH ? - objectToString.substring(0, DEFUAL_FOMULA_LENGTH - ELLIPSIS.length()) + ELLIPSIS : objectToString; - messageTips = messageTips + - com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Result") + ":" + result; - FineLoggerFactory.getLogger().info("value:{}", value); - } catch (UtilEvalError utilEvalError) { - FineLoggerFactory.getLogger().error("", utilEvalError); - } - } - FineJOptionPane.showMessageDialog( - FormulaPane.this, - messageTips, - com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), - JOptionPane.INFORMATION_MESSAGE); - } - }; - - private String containsUnsupportedSimulationFormulas(String formulaText) { - try { - Expression expression = Calculator.createCalculator().parse(formulaText); - UnsupportedFormulaScanner scanner = new UnsupportedFormulaScanner(); - if (!scanner.travelFormula(expression.getConditionalExpression())) { - return scanner.getUnSupportFormula(); - } - - UnsupportedSimulationFormulaHunter unsupportedSimulationFormulaHunter = new UnsupportedSimulationFormulaHunter(); - expression.traversal4Tiny(unsupportedSimulationFormulaHunter); - return unsupportedSimulationFormulaHunter.isSupported() ? null : unsupportedSimulationFormulaHunter.getUnSupportFormula(); - } catch (Exception e) { - FineLoggerFactory.getLogger().error("", e); - } - return null; - } - - private Map setParamsIfExist(String formulaText) { - Map parameterMap = new HashMap<>(); - try { - Calculator calculator = Calculator.createCalculator(); - Expression expression = calculator.parse(formulaText); - ParameterCellHunter parameterCellHunter = new ParameterCellHunter(); - expression.traversal4Tiny(parameterCellHunter); - Parameter[] parameters = parameterCellHunter.getParameterBooty(); - - if (parameters.length < 1 && editor4CalPane.update().size() < 1) { - return parameterMap; - } - ParameterInputPane pPane = new ParameterInputPane(parameters); - pPane.showSmallWindow(new JFrame(), new DialogActionAdapter() { - @Override - public void doOk() { - parameterMap.putAll(pPane.update()); + expression = parser.parse(); + } catch (Exception e) { + FRContext.getLogger().error(e.getMessage(), e); + // alex:继续往下面走,expression为null时告知不合法公式 } - }).setVisible(true); - //过滤出数组参数,如:[1,2] - for (Map.Entry entry : parameterMap.entrySet()) { - if (entry.getValue().toString().startsWith("[") && entry.getValue().toString().endsWith("]")) { - Expression parse = calculator.parse(entry.getValue()); - ArrayExpression arrayExpression = (ArrayExpression) parse.getConditionalExpression(); - FArray fArray = new FArray<>(arrayExpression.getArrays()); - parameterMap.put(entry.getKey(), fArray); - } - } - } catch (Exception e) { - FineLoggerFactory.getLogger().error("", e); - } - return parameterMap; - } - - private static class ParameterCellHunter extends TinyHunter { - - private final Set parameterList = new HashSet<>(); - - Parameter[] getParameterBooty() { - return parameterList.toArray(new Parameter[0]); - } - - public void hunter4Tiny(Tiny tiny) { - String statement = tiny.getStatement(); - if (StringUtils.isNotBlank(statement) && statement.startsWith(ScriptConstants.DETAIL_TAG)) { - parameterList.add(new Parameter(statement.substring(1))); - } else if (tiny.getClass() == ColumnRowRange.class || - tiny.getClass() == SheetIntervalLiteral.class || tiny.getClass() == BlockIntervalLiteral.class) { - parameterList.add(new Parameter(tiny.toString())); - } - } - } - - private static class UnsupportedSimulationFormulaHunter extends TinyHunter { - - private boolean supported = true; - - private String unSupportFormula; - - public boolean isSupported() { - return supported; - } - - public String getUnSupportFormula() { - return unSupportFormula; - } - - public void hunter4Tiny(Tiny tiny) { - if (tiny.getClass() == ColumnRowRangeInPage.class) { - supported = false; - unSupportFormula = tiny.toString(); + JOptionPane.showMessageDialog( + FormulaPane.this, + /* + * alex:仅仅只需要根据expression是否为null作合法性判断 + * 不需要eval + * TODO 但有个问题,有些函数的参数个数是有规定的,何以判别之 + */ + (expression != null ? com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaD_Valid_Formula") : com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaD_Invalid_Formula")) + ".", ProductConstants.PRODUCT_NAME, + JOptionPane.INFORMATION_MESSAGE); } } - } + }; public class VariableTreeAndDescriptionArea extends JPanel { private JTree variablesTree; private UITextArea descriptionTextArea; - VariableTreeAndDescriptionArea() { + public VariableTreeAndDescriptionArea() { this.initComponents(); } @@ -1053,31 +770,31 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { private void initVariablesTreeSelectionListener() { variablesTree.addTreeSelectionListener(new TreeSelectionListener() { public void valueChanged(TreeSelectionEvent e) { - DefaultMutableTreeNode selectedTreeNode = (DefaultMutableTreeNode) variablesTree.getLastSelectedPathComponent(); - Object selectedValue = selectedTreeNode.getUserObject(); - Object selectedParentValue = ((DefaultMutableTreeNode) selectedTreeNode.getParent()).getUserObject(); - + Object selectedValue = ((DefaultMutableTreeNode) variablesTree.getLastSelectedPathComponent()).getUserObject(); if (selectedValue == null) { return; } - - if (selectedValue instanceof TextUserObject) { - //有公式说明的条件:1.属于TextUserObject 2.parent是系统参数 - if (ComparatorUtils.equals(((TextFolderUserObject) selectedParentValue).getText(), - com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaPane_Variables"))) { - descriptionTextArea.setText(com.fr.design.i18n.Toolkit.i18nText(FormulaConstants.getValueByKey(((TextUserObject) selectedValue).getText()))); + StringBuilder desBuf = new StringBuilder(); + try { + String path; + Locale locale = FRContext.getLocale(); + if (locale.equals(Locale.CHINA)) { + path = "/com/fr/design/insert/formula/variable/cn/"; } else { - descriptionTextArea.setText(StringUtils.EMPTY); + path = "/com/fr/design/insert/formula/variable/en/"; } - } else if (selectedValue instanceof TextFolderUserObject) { - descriptionTextArea.setText(StringUtils.EMPTY); + if (selectedValue instanceof TextUserObject) { + desBuf = getText((TextUserObject) selectedValue, path); + } + } catch (IOException exp) { + FineLoggerFactory.getLogger().error(exp.getMessage(), exp); } + descriptionTextArea.setText(desBuf.toString()); descriptionTextArea.moveCaretPosition(0); } }); } - private void initVariablesTree() { // vairable. variablesTree = new JTree(); @@ -1097,15 +814,13 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { private void initComponents() { this.setLayout(new BorderLayout(4, 4)); - initVariablesTree(); - initFunctionPane(); - } - - private void initFunctionPane() { + // Function JPanel functionPane = new JPanel(new BorderLayout(4, 4)); this.add(functionPane, BorderLayout.WEST); initFunctionTypeList(functionPane); initFunctionNameList(functionPane); + initVariablesTree(); + // 选择: functionTypeList.setSelectedIndex(0); } @@ -1250,42 +965,13 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } } - public static class SimilarComparator implements Comparator { - - private String searchKey; - - public SimilarComparator(String searchKey) { - this.searchKey = searchKey.toLowerCase(); - } - - /** - * 把以关键词开头的和不以关键词开头的分别按照字母表顺序排序 - * - * @param o1 待比较对象1 - * @param o2 待比较对象2 - * @return 比较结果,1表示 o1 > o2, -1表示 o1 < o2, 0表示 o1 = o2 - */ - @Override - public int compare(String o1, String o2) { - int result; - boolean o1StartWith = o1.toLowerCase().startsWith(searchKey); - boolean o2StartWith = o2.toLowerCase().startsWith(searchKey); - if (o1StartWith) { - result = o2StartWith ? o1.compareTo(o2) : -1; - } else { - result = o2StartWith ? 1 : o1.compareTo(o2); - } - return result; - } - } - public static class TextFolderUserObject { private String text; private Icon icon; private String[] subNodes = new String[0]; - TextFolderUserObject(String text, Icon icon, String[] subNodes) { + public TextFolderUserObject(String text, Icon icon, String[] subNodes) { this.text = text; this.icon = icon; this.subNodes = subNodes; @@ -1312,11 +998,11 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { public static class TextUserObject { - TextUserObject(String text) { + public TextUserObject(String text) { this(text, text); } - TextUserObject(String text, String displayText) { + public TextUserObject(String text, String displayText) { this.text = text; this.displayText = displayText; } @@ -1325,7 +1011,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { return this.text; } - String getDisplayText() { + public String getDisplayText() { return this.displayText; } @@ -1350,6 +1036,6 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { buffer.append("|"); buffer.append("\n"); } - FineLoggerFactory.getLogger().debug(buffer.toString()); + FRContext.getLogger().debug(buffer.toString()); } } From 6096a53577e8ca7e71b2e43f473a7fa0a0bde51a Mon Sep 17 00:00:00 2001 From: Hoky <303455184@qq.com> Date: Tue, 31 Aug 2021 14:06:50 +0800 Subject: [PATCH 5/6] =?UTF-8?q?=E8=A7=A3=E5=86=B3=E5=86=B2=E7=AA=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/fr/design/formula/FormulaPane.java | 507 ++++++++++++++---- 1 file changed, 410 insertions(+), 97 deletions(-) diff --git a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java index e7319b73f..582fcb8d1 100644 --- a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java +++ b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java @@ -2,36 +2,70 @@ package com.fr.design.formula; import com.fr.base.BaseFormula; import com.fr.base.BaseUtils; -import com.fr.base.FRContext; +import com.fr.base.Parameter; +import com.fr.base.ParameterMapNameSpace; +import com.fr.base.TableDataNameSpace; +import com.fr.base.io.IOFile; +import com.fr.data.TableDataSource; import com.fr.design.actions.UpdateAction; import com.fr.design.border.UIRoundedBorder; import com.fr.design.constants.UIConstants; import com.fr.design.dialog.BasicDialog; import com.fr.design.dialog.BasicPane; +import com.fr.design.dialog.DialogActionAdapter; +import com.fr.design.dialog.FineJOptionPane; +import com.fr.design.file.HistoryTemplateListCache; import com.fr.design.gui.ibutton.UIButton; import com.fr.design.gui.icontainer.UIScrollPane; import com.fr.design.gui.ilable.UILabel; import com.fr.design.gui.ilist.QuickList; +import com.fr.design.gui.itableeditorpane.ParameterTableModel; +import com.fr.design.gui.itableeditorpane.UITableEditorPane; import com.fr.design.gui.itextarea.UITextArea; import com.fr.design.gui.itextfield.UITextField; import com.fr.design.gui.syntax.ui.rsyntaxtextarea.RSyntaxTextArea; import com.fr.design.gui.syntax.ui.rsyntaxtextarea.SyntaxConstants; +import com.fr.design.i18n.Toolkit; import com.fr.design.layout.FRGUIPaneFactory; import com.fr.design.mainframe.DesignerContext; +import com.fr.design.mainframe.JTemplate; +import com.fr.design.parameter.ParameterInputPane; import com.fr.design.utils.gui.GUICoreUtils; +import com.fr.general.ComparatorUtils; +import com.fr.general.FArray; import com.fr.log.FineLoggerFactory; +import com.fr.parser.ArrayExpression; +import com.fr.parser.BlockIntervalLiteral; +import com.fr.parser.ColumnRowRangeInPage; import com.fr.parser.FRLexer; import com.fr.parser.FRParser; +import com.fr.parser.FunctionCall; +import com.fr.parser.SheetIntervalLiteral; +import com.fr.report.core.namespace.SimpleCellValueNameSpace; +import com.fr.script.Calculator; +import com.fr.script.ScriptConstants; +import com.fr.script.checker.FunctionCheckerDispatcher; +import com.fr.script.checker.exception.ConditionCheckWrongException; +import com.fr.script.checker.exception.FunctionCheckWrongException; +import com.fr.script.rules.FunctionParameterType; +import com.fr.script.rules.FunctionRule; import com.fr.stable.EncodeConstants; -import com.fr.stable.ProductConstants; +import com.fr.stable.EssentialUtils; +import com.fr.stable.ParameterProvider; import com.fr.stable.StringUtils; +import com.fr.stable.UtilEvalError; +import com.fr.stable.script.ColumnRowRange; import com.fr.stable.script.Expression; +import com.fr.stable.script.Node; +import com.fr.stable.script.Tiny; +import com.fr.stable.script.TinyHunter; import javax.swing.BorderFactory; import javax.swing.DefaultListCellRenderer; import javax.swing.DefaultListModel; import javax.swing.Icon; import javax.swing.JComponent; +import javax.swing.JFrame; import javax.swing.JList; import javax.swing.JOptionPane; import javax.swing.JPanel; @@ -65,7 +99,15 @@ import java.io.InputStream; import java.io.InputStreamReader; import java.io.Reader; import java.io.StringReader; -import java.util.Locale; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collections; +import java.util.Comparator; +import java.util.HashMap; +import java.util.HashSet; +import java.util.List; +import java.util.Map; +import java.util.Set; /** * 公式编辑面板 @@ -75,19 +117,24 @@ import java.util.Locale; */ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { - protected VariableTreeAndDescriptionArea variableTreeAndDescriptionArea; - protected RSyntaxTextArea formulaTextArea; - protected UITextField keyWordTextField = new UITextField(18); - protected int currentPosition = 0; - protected int beginPosition = 0; - protected int insertPosition = 0; - protected JList tipsList; + public static final String VALID_FORMULA = Toolkit.i18nText("Fine-Design_Basic_FormulaD_Valid_Formula"); + public static final String INVALID_FORMULA = Toolkit.i18nText("Fine-Design_Basic_FormulaD_Invalid_Formula"); + public static final int DEFUAL_FOMULA_LENGTH = 103; + public static final String ELLIPSIS = "..."; + private VariableTreeAndDescriptionArea variableTreeAndDescriptionArea; + private RSyntaxTextArea formulaTextArea; + private UITextField keyWordTextField = new UITextField(18); + private int currentPosition = 0; + private int beginPosition = 0; + private int insertPosition = 0; + private JList tipsList; protected DefaultListModel listModel = new DefaultListModel(); - protected int ifHasBeenWriten = 0; - protected DefaultListModel functionTypeListModel = new DefaultListModel(); - protected QuickList functionTypeList; - protected DefaultListModel functionNameModel; - protected JList functionNameList; + private int ifHasBeenWriten = 0; + private DefaultListModel functionTypeListModel = new DefaultListModel(); + private QuickList functionTypeList; + private DefaultListModel functionNameModel; + private JList functionNameList; + private UITableEditorPane editor4CalPane; public FormulaPane() { initComponents(); @@ -148,10 +195,12 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { keyWordTextField.addKeyListener(new KeyListener() { @Override public void keyTyped(KeyEvent e) { + //do nothing } @Override public void keyReleased(KeyEvent e) { + //do nothing } @Override @@ -196,7 +245,20 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { protected void initComponents() { this.setLayout(new BorderLayout(4, 4)); + + initTextPane(); + initTipsPane(); + initVariableTreeAndDescriptionArea(); + } + + private void initVariableTreeAndDescriptionArea() { + variableTreeAndDescriptionArea = new VariableTreeAndDescriptionArea(); + this.add(variableTreeAndDescriptionArea, BorderLayout.SOUTH); + } + + private void initTextPane() { // text + JPanel textPane = FRGUIPaneFactory.createBorderLayout_S_Pane(); this.add(textPane, BorderLayout.CENTER); JPanel checkBoxandbuttonPane = FRGUIPaneFactory.createNormalFlowInnerContainer_S_Pane(); @@ -211,26 +273,29 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { textPane.add(formulaTextAreaScrollPane, BorderLayout.CENTER); textPane.add(checkBoxandbuttonPane, BorderLayout.SOUTH); - initTipsPane(); UIButton checkValidButton = new UIButton(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaD_Check_Valid")); + UIButton calButton = new UIButton(Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Button")); checkValidButton.addActionListener(checkValidActionListener); + calButton.addActionListener(calculateActionListener); JPanel checkBoxPane = FRGUIPaneFactory.createNormalFlowInnerContainer_S_Pane(); checkBoxPane.setPreferredSize(new Dimension(450, 30)); checkBoxandbuttonPane.add(checkBoxPane, BorderLayout.WEST); checkBoxandbuttonPane.add(checkValidButton, BorderLayout.EAST); + checkBoxandbuttonPane.add(calButton, BorderLayout.EAST); extendCheckBoxPane(checkBoxPane); - variableTreeAndDescriptionArea = new VariableTreeAndDescriptionArea(); - this.add(variableTreeAndDescriptionArea, BorderLayout.SOUTH); + + ParameterTableModel model = new ParameterTableModel(0); + editor4CalPane = new UITableEditorPane<>(model); } protected void extendCheckBoxPane(JPanel checkBoxPane) { - + // do nothing } - protected void configFormulaArea() { + private void configFormulaArea() { formulaTextArea.setSyntaxEditingStyle(SyntaxConstants.SYNTAX_STYLE_FORMULA); formulaTextArea.setAnimateBracketMatching(true); formulaTextArea.setAntiAliasingEnabled(true); @@ -245,44 +310,69 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } public class DoubleClick extends MouseAdapter { + String singlePressContent; + + String doublePressContent; @Override - public void mouseClicked(MouseEvent e) { + public void mousePressed(MouseEvent e) { int index = tipsList.getSelectedIndex(); if (index != -1) { - String currentLineContent = (String) listModel.getElementAt(index); - if (e.getClickCount() == 2) { - if (ifHasBeenWriten == 0) { - formulaTextArea.setForeground(Color.black); - formulaTextArea.setText(""); + if (e.getClickCount() == 1) { + singlePressContent = (String) listModel.getElementAt(index); + } else if (e.getClickCount() == 2) { + doublePressContent = (String) listModel.getElementAt(index); + } + } + } + + @Override + public void mouseReleased(MouseEvent e) { + int index = tipsList.getSelectedIndex(); + if (index != -1) { + if (e.getClickCount() == 1) { + if (ComparatorUtils.equals((String) listModel.getElementAt(index), singlePressContent)) { + singleClickActuator(singlePressContent); } - formulaTextArea.setForeground(Color.black); - currentPosition = formulaTextArea.getCaretPosition(); - String output = currentLineContent + "()"; - String textAll = formulaTextArea.getText(); - String textReplaced; - int position = 0; - if (insertPosition <= currentPosition) { - textReplaced = textAll.substring(0, insertPosition) + output + textAll.substring(currentPosition); - position = insertPosition + output.length() - 1; - } else { - textReplaced = textAll.substring(0, currentPosition) + output + textAll.substring(insertPosition); - position = currentPosition + output.length() - 1; + } else if (e.getClickCount() == 2) { + if (ComparatorUtils.equals((String) listModel.getElementAt(index), doublePressContent)) { + doubleClickActuator(doublePressContent); } - formulaTextArea.setText(textReplaced); - formulaTextArea.requestFocusInWindow(); - formulaTextArea.setCaretPosition(position); - insertPosition = position; - ifHasBeenWriten = 1; - listModel.removeAllElements(); - } else if (e.getClickCount() == 1) { - refreshDescriptionTextArea(currentLineContent); - - formulaTextArea.requestFocusInWindow(); - fixFunctionNameList(); } } } + + private void singleClickActuator(String currentLineContent) { + refreshDescriptionTextArea(currentLineContent); + formulaTextArea.requestFocusInWindow(); + fixFunctionNameList(); + } + + private void doubleClickActuator(String currentLineContent) { + if (ifHasBeenWriten == 0) { + formulaTextArea.setForeground(Color.black); + formulaTextArea.setText(""); + } + formulaTextArea.setForeground(Color.black); + currentPosition = formulaTextArea.getCaretPosition(); + String output = currentLineContent + "()"; + String textAll = formulaTextArea.getText(); + String textReplaced; + int position = 0; + if (insertPosition <= currentPosition) { + textReplaced = textAll.substring(0, insertPosition) + output + textAll.substring(currentPosition); + position = insertPosition + output.length() - 1; + } else { + textReplaced = textAll.substring(0, currentPosition) + output + textAll.substring(insertPosition); + position = currentPosition + output.length() - 1; + } + formulaTextArea.setText(textReplaced); + formulaTextArea.requestFocusInWindow(); + formulaTextArea.setCaretPosition(position); + insertPosition = position; + ifHasBeenWriten = 1; + listModel.removeAllElements(); + } } @Override @@ -325,7 +415,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } } - protected void fixFunctionNameList() { + private void fixFunctionNameList() { if (tipsList.getSelectedValue() != null) { int signOfContinue = 1; int indexOfFunction = 0; @@ -358,7 +448,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } - protected int getBeginPosition() { + private int getBeginPosition() { int i = currentPosition; String textArea = formulaTextArea.getText(); for (; i > 0; i--) { @@ -373,7 +463,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { return i; } - protected void firstStepToFindTips(int theBeginPosition) { + private void firstStepToFindTips(int theBeginPosition) { String textArea = formulaTextArea.getText(); if (currentPosition > 0 && theBeginPosition < currentPosition) { @@ -403,6 +493,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { @Override public void keyTyped(KeyEvent e) { + // do nothing } protected void search(String keyWord, boolean findDescription) { @@ -412,14 +503,19 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { if (keyWord.length() != 0) { NameAndDescription[] descriptions = FunctionConstants.ALL.getDescriptions(); int lengthOfDes = descriptions.length; + List list = new ArrayList<>(); for (int i = 0; i < lengthOfDes; i++) { NameAndDescription and = descriptions[i]; String functionName = and.searchResult(keyWord, findDescription); if (StringUtils.isNotBlank(functionName)) { - listModel.addElement(functionName); + list.add(functionName); } } + Collections.sort(list, new SimilarComparator(keyWord)); + for (String name : list) { + listModel.addElement(name); + } if (!listModel.isEmpty()) { tipsList.setSelectedIndex(0); @@ -455,7 +551,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { /** * Apply text. */ - public void applyText(String text) { + private void applyText(String text) { if (text == null || text.length() <= 0) { return; } @@ -553,45 +649,231 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } // check valid - protected ActionListener checkValidActionListener = new ActionListener() { + private final ActionListener checkValidActionListener = new ActionListener() { public void actionPerformed(ActionEvent evt) { // Execute Formula default cell element. String formulaText = formulaTextArea.getText().trim(); + String formulaValidMessage = getFormulaValidMessage(formulaText); + FineJOptionPane.showMessageDialog( + FormulaPane.this, + formulaValidMessage + ".", + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), + JOptionPane.INFORMATION_MESSAGE); + } + }; - if (formulaText != null && formulaText.length() > 0) { - StringReader in = new StringReader(formulaText); - - FRLexer lexer = new FRLexer(in); - FRParser parser = new FRParser(lexer); - - Expression expression = null; - try { - expression = parser.parse(); - } catch (Exception e) { - FRContext.getLogger().error(e.getMessage(), e); - // alex:继续往下面走,expression为null时告知不合法公式 + private static String getFormulaValidMessage(String formulaText) { + StringReader in = new StringReader(formulaText); + + FRLexer lexer = new FRLexer(in); + FRParser parser = new FRParser(lexer); + + try { + Expression expression = parser.parse(); + Node node = expression.getConditionalExpression(); + return FunctionCheckerDispatcher.getInstance() + .getFunctionChecker(node) + .checkFunction(node) ? VALID_FORMULA : INVALID_FORMULA; + } catch (ConditionCheckWrongException cce) { + String functionName = cce.getFunctionName(); + StringBuilder errorMsg = new StringBuilder(functionName + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Condition_Tips") + ":"); + return errorMsg.toString(); + } catch (FunctionCheckWrongException ce) { + List rules = ce.getRules(); + String functionName = ce.getFunctionName(); + StringBuilder errorMsg = new StringBuilder(functionName + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Error_Tips") + ":"); + for (int i = 0; i < rules.size(); i++) { + errorMsg.append("("); + if (rules.get(i).getParameterList().isEmpty()) { + errorMsg.append(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_No_Param")); + } + for (FunctionParameterType functionParameterType : rules.get(i).getParameterList()) { + errorMsg.append(getTypeString(functionParameterType)).append(","); + } + if (",".equals(errorMsg.charAt(errorMsg.length() - 1) + "")) { + errorMsg.deleteCharAt(errorMsg.length() - 1); + } + errorMsg.append(")"); + if (i != rules.size() - 1) { + errorMsg.append(com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_Or")); } + } + return errorMsg.toString(); + } catch (Exception e) { + FineLoggerFactory.getLogger().error(e.getMessage(), e); + return INVALID_FORMULA; + // alex:继续往下面走,expression为null时告知不合法公式 + } + } - JOptionPane.showMessageDialog( + private static String getTypeString(FunctionParameterType type) { + switch (type) { + case NUMBER: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Number"); + case STRING: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_String"); + case ANY: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Any"); + case DATE: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Date"); + case BOOLEAN: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Boolean"); + case ARRAY: + return com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Check_ParamType_Array"); + } + return ""; + } + + private final ActionListener calculateActionListener = new ActionListener() { + @Override + public void actionPerformed(ActionEvent e) { + String formulaText = formulaTextArea.getText().trim(); + if (containsUnsupportedSimulationFormulas(formulaText)) { + FineJOptionPane.showMessageDialog( FormulaPane.this, - /* - * alex:仅仅只需要根据expression是否为null作合法性判断 - * 不需要eval - * TODO 但有个问题,有些函数的参数个数是有规定的,何以判别之 - */ - (expression != null ? com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaD_Valid_Formula") : com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaD_Invalid_Formula")) + ".", ProductConstants.PRODUCT_NAME, + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Unsupported_Formulas"), + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), JOptionPane.INFORMATION_MESSAGE); + return; + } + String formulaValidMessage = getFormulaValidMessage(formulaText); + String messageTips; + if (formulaValidMessage.equals(INVALID_FORMULA)) { + messageTips = INVALID_FORMULA; + } else { + messageTips = formulaValidMessage.equals(VALID_FORMULA) ? "" : formulaValidMessage + "\n"; + Map paramsMap = setParamsIfExist(formulaText); + Calculator calculator = Calculator.createCalculator(); + ParameterMapNameSpace parameterMapNameSpace = ParameterMapNameSpace.create(paramsMap); + calculator.pushNameSpace(parameterMapNameSpace); + + JTemplate currentEditingTemplate = HistoryTemplateListCache.getInstance().getCurrentEditingTemplate(); + if (currentEditingTemplate != null) { + IOFile file = (IOFile) currentEditingTemplate.getTarget(); + calculator.setAttribute(TableDataSource.KEY, file); + calculator.pushNameSpace(TableDataNameSpace.getInstance()); + calculator.pushNameSpace(SimpleCellValueNameSpace.getInstance()); + } + + BaseFormula baseFormula = BaseFormula.createFormulaBuilder().build(formulaText); + try { + Object value = calculator.evalValue(baseFormula); + String objectToString = EssentialUtils.objectToString(value); + String result = objectToString.length() > DEFUAL_FOMULA_LENGTH ? + objectToString.substring(0, DEFUAL_FOMULA_LENGTH - ELLIPSIS.length()) + ELLIPSIS : objectToString; + messageTips = messageTips + + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Cal_Result") + ":" + result; + FineLoggerFactory.getLogger().info("value:{}", value); + } catch (UtilEvalError utilEvalError) { + FineLoggerFactory.getLogger().error("", utilEvalError); + } } + FineJOptionPane.showMessageDialog( + FormulaPane.this, + messageTips, + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), + JOptionPane.INFORMATION_MESSAGE); } }; + private boolean containsUnsupportedSimulationFormulas(String formulaText) { + try { + Expression expression = Calculator.createCalculator().parse(formulaText); + String name = ((FunctionCall) expression.getConditionalExpression()).getName(); + if (UnsupportedSimulationFormulaHunter.isUnsupportedFomula(name)) { + return true; + } + UnsupportedSimulationFormulaHunter unsupportedSimulationFormulaHunter = new UnsupportedSimulationFormulaHunter(); + expression.traversal4Tiny(unsupportedSimulationFormulaHunter); + return !unsupportedSimulationFormulaHunter.isSupported(); + } catch (Exception e) { + FineLoggerFactory.getLogger().error("", e); + } + return true; + } + + private Map setParamsIfExist(String formulaText) { + Map parameterMap = new HashMap<>(); + try { + Calculator calculator = Calculator.createCalculator(); + Expression expression = calculator.parse(formulaText); + ParameterCellHunter parameterCellHunter = new ParameterCellHunter(); + expression.traversal4Tiny(parameterCellHunter); + Parameter[] parameters = parameterCellHunter.getParameterBooty(); + + if (parameters.length < 1 && editor4CalPane.update().size() < 1) { + return parameterMap; + } + ParameterInputPane pPane = new ParameterInputPane(parameters); + pPane.showSmallWindow(new JFrame(), new DialogActionAdapter() { + @Override + public void doOk() { + parameterMap.putAll(pPane.update()); + } + }).setVisible(true); + //过滤出数组参数,如:[1,2] + for (Map.Entry entry : parameterMap.entrySet()) { + if (entry.getValue().toString().startsWith("[") && entry.getValue().toString().startsWith("]")) { + Expression parse = calculator.parse(entry.getValue()); + ArrayExpression arrayExpression = (ArrayExpression) parse.getConditionalExpression(); + FArray fArray = new FArray<>(arrayExpression.getArrays()); + parameterMap.put(entry.getKey(), fArray); + } + } + } catch (Exception e) { + FineLoggerFactory.getLogger().error("", e); + } + return parameterMap; + } + + private static class ParameterCellHunter extends TinyHunter { + + private final Set parameterList = new HashSet<>(); + + Parameter[] getParameterBooty() { + return parameterList.toArray(new Parameter[0]); + } + + public void hunter4Tiny(Tiny tiny) { + String statement = tiny.getStatement(); + if (StringUtils.isNotBlank(statement) && statement.startsWith(ScriptConstants.DETAIL_TAG)) { + parameterList.add(new Parameter(statement.substring(1))); + } else if (tiny.getClass() == ColumnRowRange.class || tiny.getClass() == ColumnRowRangeInPage.class || + tiny.getClass() == SheetIntervalLiteral.class || tiny.getClass() == BlockIntervalLiteral.class) { + parameterList.add(new Parameter(tiny.toString())); + } + } + } + + private static class UnsupportedSimulationFormulaHunter extends TinyHunter { + public final static String[] UNSUPPORTED_FORMULAS = new String[]{"PROPORTION", "TOIMAGE", + "WEBIMAGE", "SORT", "CROSSLAYERTOTAL", "CIRCULAR", "LAYERTOTAL", "MOM", "HIERARCHY"}; + + private boolean supported = true; + + public boolean isSupported() { + return supported; + } + + public void hunter4Tiny(Tiny tiny) { + String statement = tiny.getStatement().toUpperCase(); + if (Arrays.asList(UNSUPPORTED_FORMULAS).contains(statement)) { + supported = false; + } + } + + public static boolean isUnsupportedFomula(String formula) { + return Arrays.asList(UNSUPPORTED_FORMULAS).contains(formula); + } + } + public class VariableTreeAndDescriptionArea extends JPanel { private JTree variablesTree; private UITextArea descriptionTextArea; - public VariableTreeAndDescriptionArea() { + VariableTreeAndDescriptionArea() { this.initComponents(); } @@ -770,31 +1052,31 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { private void initVariablesTreeSelectionListener() { variablesTree.addTreeSelectionListener(new TreeSelectionListener() { public void valueChanged(TreeSelectionEvent e) { - Object selectedValue = ((DefaultMutableTreeNode) variablesTree.getLastSelectedPathComponent()).getUserObject(); + DefaultMutableTreeNode selectedTreeNode = (DefaultMutableTreeNode) variablesTree.getLastSelectedPathComponent(); + Object selectedValue = selectedTreeNode.getUserObject(); + Object selectedParentValue = ((DefaultMutableTreeNode) selectedTreeNode.getParent()).getUserObject(); + if (selectedValue == null) { return; } - StringBuilder desBuf = new StringBuilder(); - try { - String path; - Locale locale = FRContext.getLocale(); - if (locale.equals(Locale.CHINA)) { - path = "/com/fr/design/insert/formula/variable/cn/"; + + if (selectedValue instanceof TextUserObject) { + //有公式说明的条件:1.属于TextUserObject 2.parent是系统参数 + if (ComparatorUtils.equals(((TextFolderUserObject) selectedParentValue).getText(), + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_FormulaPane_Variables"))) { + descriptionTextArea.setText(com.fr.design.i18n.Toolkit.i18nText(FormulaConstants.getValueByKey(((TextUserObject) selectedValue).getText()))); } else { - path = "/com/fr/design/insert/formula/variable/en/"; + descriptionTextArea.setText(StringUtils.EMPTY); } - if (selectedValue instanceof TextUserObject) { - desBuf = getText((TextUserObject) selectedValue, path); - } - } catch (IOException exp) { - FineLoggerFactory.getLogger().error(exp.getMessage(), exp); + } else if (selectedValue instanceof TextFolderUserObject) { + descriptionTextArea.setText(StringUtils.EMPTY); } - descriptionTextArea.setText(desBuf.toString()); descriptionTextArea.moveCaretPosition(0); } }); } + private void initVariablesTree() { // vairable. variablesTree = new JTree(); @@ -814,13 +1096,15 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { private void initComponents() { this.setLayout(new BorderLayout(4, 4)); - // Function + initVariablesTree(); + initFunctionPane(); + } + + private void initFunctionPane() { JPanel functionPane = new JPanel(new BorderLayout(4, 4)); this.add(functionPane, BorderLayout.WEST); initFunctionTypeList(functionPane); initFunctionNameList(functionPane); - initVariablesTree(); - // 选择: functionTypeList.setSelectedIndex(0); } @@ -965,13 +1249,42 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } } + public static class SimilarComparator implements Comparator { + + private String searchKey; + + public SimilarComparator(String searchKey) { + this.searchKey = searchKey.toLowerCase(); + } + + /** + * 把以关键词开头的和不以关键词开头的分别按照字母表顺序排序 + * + * @param o1 待比较对象1 + * @param o2 待比较对象2 + * @return 比较结果,1表示 o1 > o2, -1表示 o1 < o2, 0表示 o1 = o2 + */ + @Override + public int compare(String o1, String o2) { + int result; + boolean o1StartWith = o1.toLowerCase().startsWith(searchKey); + boolean o2StartWith = o2.toLowerCase().startsWith(searchKey); + if (o1StartWith) { + result = o2StartWith ? o1.compareTo(o2) : -1; + } else { + result = o2StartWith ? 1 : o1.compareTo(o2); + } + return result; + } + } + public static class TextFolderUserObject { private String text; private Icon icon; private String[] subNodes = new String[0]; - public TextFolderUserObject(String text, Icon icon, String[] subNodes) { + TextFolderUserObject(String text, Icon icon, String[] subNodes) { this.text = text; this.icon = icon; this.subNodes = subNodes; @@ -998,11 +1311,11 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { public static class TextUserObject { - public TextUserObject(String text) { + TextUserObject(String text) { this(text, text); } - public TextUserObject(String text, String displayText) { + TextUserObject(String text, String displayText) { this.text = text; this.displayText = displayText; } @@ -1011,7 +1324,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { return this.text; } - public String getDisplayText() { + String getDisplayText() { return this.displayText; } @@ -1036,6 +1349,6 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { buffer.append("|"); buffer.append("\n"); } - FRContext.getLogger().debug(buffer.toString()); + FineLoggerFactory.getLogger().debug(buffer.toString()); } } From bbf31153a7373ee3f329ca3ecc648fbaf25a5f0b Mon Sep 17 00:00:00 2001 From: Hoky <303455184@qq.com> Date: Tue, 31 Aug 2021 14:09:23 +0800 Subject: [PATCH 6/6] =?UTF-8?q?=E8=A7=A3=E5=86=B3=E5=86=B2=E7=AA=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/fr/design/formula/FormulaPane.java | 43 ++++++++++--------- 1 file changed, 22 insertions(+), 21 deletions(-) diff --git a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java index 582fcb8d1..f836cd571 100644 --- a/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java +++ b/designer-base/src/main/java/com/fr/design/formula/FormulaPane.java @@ -39,7 +39,6 @@ import com.fr.parser.BlockIntervalLiteral; import com.fr.parser.ColumnRowRangeInPage; import com.fr.parser.FRLexer; import com.fr.parser.FRParser; -import com.fr.parser.FunctionCall; import com.fr.parser.SheetIntervalLiteral; import com.fr.report.core.namespace.SimpleCellValueNameSpace; import com.fr.script.Calculator; @@ -100,7 +99,6 @@ import java.io.InputStreamReader; import java.io.Reader; import java.io.StringReader; import java.util.ArrayList; -import java.util.Arrays; import java.util.Collections; import java.util.Comparator; import java.util.HashMap; @@ -729,15 +727,16 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { @Override public void actionPerformed(ActionEvent e) { String formulaText = formulaTextArea.getText().trim(); - if (containsUnsupportedSimulationFormulas(formulaText)) { + String formulaValidMessage = getFormulaValidMessage(formulaText); + String unSupportFormula = containsUnsupportedSimulationFormulas(formulaText); + if (unSupportFormula != null) { FineJOptionPane.showMessageDialog( FormulaPane.this, - com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Unsupported_Formulas"), + com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Formula_Unsupported_Formulas") + ":" + unSupportFormula, com.fr.design.i18n.Toolkit.i18nText("Fine-Design_Basic_Tool_Tips"), JOptionPane.INFORMATION_MESSAGE); return; } - String formulaValidMessage = getFormulaValidMessage(formulaText); String messageTips; if (formulaValidMessage.equals(INVALID_FORMULA)) { messageTips = INVALID_FORMULA; @@ -777,20 +776,21 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } }; - private boolean containsUnsupportedSimulationFormulas(String formulaText) { + private String containsUnsupportedSimulationFormulas(String formulaText) { try { Expression expression = Calculator.createCalculator().parse(formulaText); - String name = ((FunctionCall) expression.getConditionalExpression()).getName(); - if (UnsupportedSimulationFormulaHunter.isUnsupportedFomula(name)) { - return true; + UnsupportedFormulaScanner scanner = new UnsupportedFormulaScanner(); + if (!scanner.travelFormula(expression.getConditionalExpression())) { + return scanner.getUnSupportFormula(); } + UnsupportedSimulationFormulaHunter unsupportedSimulationFormulaHunter = new UnsupportedSimulationFormulaHunter(); expression.traversal4Tiny(unsupportedSimulationFormulaHunter); - return !unsupportedSimulationFormulaHunter.isSupported(); + return unsupportedSimulationFormulaHunter.isSupported() ? null : unsupportedSimulationFormulaHunter.getUnSupportFormula(); } catch (Exception e) { FineLoggerFactory.getLogger().error("", e); } - return true; + return null; } private Map setParamsIfExist(String formulaText) { @@ -814,7 +814,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { }).setVisible(true); //过滤出数组参数,如:[1,2] for (Map.Entry entry : parameterMap.entrySet()) { - if (entry.getValue().toString().startsWith("[") && entry.getValue().toString().startsWith("]")) { + if (entry.getValue().toString().startsWith("[") && entry.getValue().toString().endsWith("]")) { Expression parse = calculator.parse(entry.getValue()); ArrayExpression arrayExpression = (ArrayExpression) parse.getConditionalExpression(); FArray fArray = new FArray<>(arrayExpression.getArrays()); @@ -839,7 +839,7 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { String statement = tiny.getStatement(); if (StringUtils.isNotBlank(statement) && statement.startsWith(ScriptConstants.DETAIL_TAG)) { parameterList.add(new Parameter(statement.substring(1))); - } else if (tiny.getClass() == ColumnRowRange.class || tiny.getClass() == ColumnRowRangeInPage.class || + } else if (tiny.getClass() == ColumnRowRange.class || tiny.getClass() == SheetIntervalLiteral.class || tiny.getClass() == BlockIntervalLiteral.class) { parameterList.add(new Parameter(tiny.toString())); } @@ -847,25 +847,26 @@ public class FormulaPane extends BasicPane implements KeyListener, UIFormula { } private static class UnsupportedSimulationFormulaHunter extends TinyHunter { - public final static String[] UNSUPPORTED_FORMULAS = new String[]{"PROPORTION", "TOIMAGE", - "WEBIMAGE", "SORT", "CROSSLAYERTOTAL", "CIRCULAR", "LAYERTOTAL", "MOM", "HIERARCHY"}; + private boolean supported = true; + private String unSupportFormula; + public boolean isSupported() { return supported; } + public String getUnSupportFormula() { + return unSupportFormula; + } + public void hunter4Tiny(Tiny tiny) { - String statement = tiny.getStatement().toUpperCase(); - if (Arrays.asList(UNSUPPORTED_FORMULAS).contains(statement)) { + if (tiny.getClass() == ColumnRowRangeInPage.class) { supported = false; + unSupportFormula = tiny.toString(); } } - - public static boolean isUnsupportedFomula(String formula) { - return Arrays.asList(UNSUPPORTED_FORMULAS).contains(formula); - } } public class VariableTreeAndDescriptionArea extends JPanel {