|
|
|
package com.fr.solution.plugin.design.formula.ui;
|
|
|
|
|
|
|
|
import com.fr.base.BaseFormula;
|
|
|
|
import com.fr.base.BaseUtils;
|
|
|
|
import com.fr.base.FRContext;
|
|
|
|
import com.fr.base.Parameter;
|
|
|
|
import com.fr.base.ParameterHelper;
|
|
|
|
import com.fr.base.ParameterMapNameSpace;
|
|
|
|
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.file.HistoryTemplateListPane;
|
|
|
|
import com.fr.design.formula.FunctionConstants;
|
|
|
|
import com.fr.design.formula.FunctionGroup;
|
|
|
|
import com.fr.design.formula.NameAndDescription;
|
|
|
|
import com.fr.design.formula.UIFormula;
|
|
|
|
import com.fr.design.formula.VariableResolver;
|
|
|
|
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.itextarea.UITextArea;
|
|
|
|
import com.fr.design.gui.itextfield.UITextField;
|
|
|
|
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.GeneralUtils;
|
|
|
|
import com.fr.general.Inter;
|
|
|
|
import com.fr.report.core.namespace.SimpleCellValueNameSpace;
|
|
|
|
import com.fr.script.Calculator;
|
|
|
|
import com.fr.solution.plugin.design.formula.ui.evt.OperateListener;
|
|
|
|
import com.fr.solution.plugin.design.formula.ui.type.CategoryFormulaPane;
|
|
|
|
import com.fr.stable.ArrayUtils;
|
|
|
|
import com.fr.stable.EncodeConstants;
|
|
|
|
import com.fr.stable.StringUtils;
|
|
|
|
import com.fr.stable.UtilEvalError;
|
|
|
|
|
|
|
|
import javax.swing.*;
|
|
|
|
import javax.swing.event.ListSelectionEvent;
|
|
|
|
import javax.swing.event.ListSelectionListener;
|
|
|
|
import javax.swing.event.TreeSelectionEvent;
|
|
|
|
import javax.swing.event.TreeSelectionListener;
|
|
|
|
import javax.swing.tree.DefaultMutableTreeNode;
|
|
|
|
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.event.ActionEvent;
|
|
|
|
import java.awt.event.ActionListener;
|
|
|
|
import java.awt.event.KeyEvent;
|
|
|
|
import java.awt.event.KeyListener;
|
|
|
|
import java.awt.event.MouseAdapter;
|
|
|
|
import java.awt.event.MouseEvent;
|
|
|
|
import java.awt.event.MouseListener;
|
|
|
|
import java.io.BufferedReader;
|
|
|
|
import java.io.IOException;
|
|
|
|
import java.io.InputStream;
|
|
|
|
import java.io.InputStreamReader;
|
|
|
|
import java.io.Reader;
|
|
|
|
import java.io.StringReader;
|
|
|
|
import java.util.HashMap;
|
|
|
|
import java.util.Locale;
|
|
|
|
import java.util.Map;
|
|
|
|
|
|
|
|
/**
|
|
|
|
* 组合了普通公式和脚本公式的编辑器面板
|
|
|
|
*/
|
|
|
|
public class GroupFormulaPane extends BasicPane implements UIFormula, OperateListener {
|
|
|
|
|
|
|
|
private VariableTreeAndDescriptionArea variableTreeAndDescriptionArea;
|
|
|
|
|
|
|
|
private CategoryFormulaPane formulaPane;
|
|
|
|
|
|
|
|
private UITextField keyWordTextField = new UITextField(18);
|
|
|
|
|
|
|
|
private JList tipsList;
|
|
|
|
private DefaultListModel listModel = new DefaultListModel();
|
|
|
|
|
|
|
|
private DefaultListModel functionTypeListModel = new DefaultListModel();
|
|
|
|
private QuickList functionTypeList;
|
|
|
|
private DefaultListModel functionNameModel;
|
|
|
|
private JList functionNameList;
|
|
|
|
|
|
|
|
public GroupFormulaPane() {
|
|
|
|
initComponents();
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void initKeyWordTextFieldKeyListener() {
|
|
|
|
keyWordTextField.addKeyListener(new KeyListener() {
|
|
|
|
@Override
|
|
|
|
public void keyTyped(KeyEvent e) {
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void keyReleased(KeyEvent e) {
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void keyPressed(KeyEvent e) {
|
|
|
|
if (e.getKeyCode() == KeyEvent.VK_ENTER) {
|
|
|
|
String toFind = keyWordTextField.getText();
|
|
|
|
search(toFind, false);
|
|
|
|
fixFunctionNameList();
|
|
|
|
e.consume();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
protected void initComponents() {
|
|
|
|
this.setLayout(new BorderLayout(4, 4));
|
|
|
|
// text
|
|
|
|
JPanel textPane = FRGUIPaneFactory.createBorderLayout_S_Pane();
|
|
|
|
this.add(textPane, BorderLayout.CENTER);
|
|
|
|
JPanel checkBoxAndButtonPane = FRGUIPaneFactory.createNormalFlowInnerContainer_S_Pane();
|
|
|
|
UILabel formulaLabel = new UILabel(Inter.getLocText("FormulaD-Input_formula_in_the_text_area_below") + ":"
|
|
|
|
+ " ");
|
|
|
|
formulaLabel.setBorder(BorderFactory.createEmptyBorder(4, 4, 4, 4));
|
|
|
|
|
|
|
|
formulaPane = new CategoryFormulaPane();
|
|
|
|
formulaPane.setOperateListener(this);
|
|
|
|
|
|
|
|
textPane.add(formulaLabel, BorderLayout.NORTH);
|
|
|
|
textPane.add(formulaPane, BorderLayout.CENTER);
|
|
|
|
textPane.add(checkBoxAndButtonPane, BorderLayout.SOUTH);
|
|
|
|
|
|
|
|
initTipsPane();
|
|
|
|
|
|
|
|
UIButton checkValidButton = new UIButton(Inter.getLocText("FormulaD-Check_Valid"));
|
|
|
|
checkValidButton.addActionListener(checkValidActionListener);
|
|
|
|
|
|
|
|
UIButton calculateButton = new UIButton(Inter.getLocText("FR-Designer_Group_Formula_Calculate"));
|
|
|
|
calculateButton.addActionListener(calculateActionListener);
|
|
|
|
|
|
|
|
JPanel checkBoxPane = FRGUIPaneFactory.createNormalFlowInnerContainer_S_Pane();
|
|
|
|
checkBoxPane.setPreferredSize(new Dimension(450, 30));
|
|
|
|
checkBoxAndButtonPane.add(checkBoxPane, BorderLayout.WEST);
|
|
|
|
checkBoxAndButtonPane.add(GUICoreUtils.createFlowPane(checkValidButton, calculateButton), BorderLayout.EAST);
|
|
|
|
extendCheckBoxPane(checkBoxPane);
|
|
|
|
variableTreeAndDescriptionArea = new VariableTreeAndDescriptionArea();
|
|
|
|
this.add(variableTreeAndDescriptionArea, BorderLayout.SOUTH);
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initTipsPane() {
|
|
|
|
// tipsPane
|
|
|
|
JPanel tipsPane = new JPanel(new BorderLayout(4, 4));
|
|
|
|
this.add(tipsPane, BorderLayout.EAST);
|
|
|
|
|
|
|
|
JPanel searchPane = new JPanel(new BorderLayout(4, 4));
|
|
|
|
searchPane.add(keyWordTextField, BorderLayout.CENTER);
|
|
|
|
UIButton searchButton = new UIButton(Inter.getLocText("FR-Designer_FormulaPane_Search"));
|
|
|
|
searchPane.add(searchButton, BorderLayout.EAST);
|
|
|
|
tipsPane.add(searchPane, BorderLayout.NORTH);
|
|
|
|
initKeyWordTextFieldKeyListener();
|
|
|
|
tipsList = new JList(listModel);
|
|
|
|
tipsList.addMouseListener(new DoubleClick());
|
|
|
|
UIScrollPane tipsScrollPane = new UIScrollPane(tipsList);
|
|
|
|
tipsScrollPane.setPreferredSize(new Dimension(170, 75));
|
|
|
|
tipsScrollPane.setBorder(new UIRoundedBorder(UIConstants.LINE_COLOR, 1, UIConstants.ARC));
|
|
|
|
tipsPane.add(tipsScrollPane, BorderLayout.CENTER);
|
|
|
|
searchButton.addActionListener(new ActionListener() {
|
|
|
|
@Override
|
|
|
|
public void actionPerformed(ActionEvent e) {
|
|
|
|
String toFind = keyWordTextField.getText();
|
|
|
|
search(toFind, false);
|
|
|
|
formulaPane.onSearch();
|
|
|
|
fixFunctionNameList();
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
protected void extendCheckBoxPane(JPanel checkBoxPane) {
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void clearMathListModel() {
|
|
|
|
listModel.removeAllElements();
|
|
|
|
}
|
|
|
|
|
|
|
|
public class DoubleClick extends MouseAdapter {
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void mouseClicked(MouseEvent e) {
|
|
|
|
int index = tipsList.getSelectedIndex();
|
|
|
|
if (index != -1) {
|
|
|
|
String currentLineContent = (String) listModel.getElementAt(index);
|
|
|
|
if (e.getClickCount() == 2) {
|
|
|
|
formulaPane.onDoubleClick(currentLineContent);
|
|
|
|
listModel.removeAllElements();
|
|
|
|
} else if (e.getClickCount() == 1) {
|
|
|
|
refreshDescriptionTextArea(currentLineContent);
|
|
|
|
formulaPane.onSingleClick();
|
|
|
|
fixFunctionNameList();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
public void fixFunctionNameList() {
|
|
|
|
if (tipsList.getSelectedValue() != null) {
|
|
|
|
int signOfContinue = 1;
|
|
|
|
int indexOfFunction = 0;
|
|
|
|
for (int i = 0; i < functionTypeListModel.size(); i++) {
|
|
|
|
int signOfType = 0;
|
|
|
|
FunctionGroup functionType = (FunctionGroup) functionTypeListModel.getElementAt(i);
|
|
|
|
NameAndDescription[] nads = functionType.getDescriptions();
|
|
|
|
if (signOfContinue == 1) {
|
|
|
|
functionNameModel.removeAllElements();
|
|
|
|
String functionName = ((String) tipsList.getSelectedValue());
|
|
|
|
for (int k = 0; k < nads.length; k++) {
|
|
|
|
functionNameModel.addElement(nads[k]);
|
|
|
|
if (functionName.equals(nads[k].getName()))//若相等,找出显示的函数的index,setSelectedIndex()
|
|
|
|
{
|
|
|
|
signOfType = 1;
|
|
|
|
signOfContinue = 0;
|
|
|
|
indexOfFunction = k;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (signOfType == 1) {
|
|
|
|
functionTypeList.setSelectedIndex(i);
|
|
|
|
signOfType = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
functionNameList.setSelectedIndex(indexOfFunction);
|
|
|
|
functionNameList.ensureIndexIsVisible(indexOfFunction);
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
public void search(String keyWord, boolean findDescription) {
|
|
|
|
listModel.removeAllElements();
|
|
|
|
|
|
|
|
keyWord = removeAllSpace(keyWord);
|
|
|
|
if (keyWord.length() != 0) {
|
|
|
|
NameAndDescription[] descriptions = FunctionConstants.ALL.getDescriptions();
|
|
|
|
int lengthOfDes = descriptions.length;
|
|
|
|
for (int i = 0; i < lengthOfDes; i++) {
|
|
|
|
NameAndDescription and = descriptions[i];
|
|
|
|
|
|
|
|
String functionName = and.searchResult(keyWord, findDescription);
|
|
|
|
if (StringUtils.isNotBlank(functionName)) {
|
|
|
|
listModel.addElement(functionName);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (!listModel.isEmpty()) {
|
|
|
|
tipsList.setSelectedIndex(0);
|
|
|
|
refreshDescriptionTextArea((String) listModel.getElementAt(0));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
private void refreshDescriptionTextArea(String line) {
|
|
|
|
NameAndDescription[] descriptions = FunctionConstants.ALL.getDescriptions();
|
|
|
|
int length = descriptions.length;
|
|
|
|
for (int i = 0; i < length; i++) {
|
|
|
|
NameAndDescription function = descriptions[i];
|
|
|
|
String functionName = function.getName();
|
|
|
|
if (functionName.equals(line)) {
|
|
|
|
variableTreeAndDescriptionArea.descriptionTextArea.setText(function.getDesc());
|
|
|
|
variableTreeAndDescriptionArea.descriptionTextArea.moveCaretPosition(0);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
private String removeAllSpace(String toFind) {
|
|
|
|
|
|
|
|
int index = toFind.indexOf(" ");
|
|
|
|
while (index != -1) {
|
|
|
|
toFind = toFind.substring(0, index) + toFind.substring(index + 1);
|
|
|
|
index = toFind.indexOf(" ");
|
|
|
|
}
|
|
|
|
return toFind;
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
protected String title4PopupWindow() {
|
|
|
|
return Inter.getLocText("FormulaD-Formula_Definition");
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Populate
|
|
|
|
*/
|
|
|
|
public void populate(BaseFormula formula) {
|
|
|
|
this.populate(formula, VariableResolver.DEFAULT);
|
|
|
|
}
|
|
|
|
|
|
|
|
public void populate(BaseFormula formula, VariableResolver variableResolver) {
|
|
|
|
this.variableTreeAndDescriptionArea.populate(variableResolver);
|
|
|
|
formulaPane.populateBean(formula);
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* update
|
|
|
|
*/
|
|
|
|
public BaseFormula update() {
|
|
|
|
return formulaPane.updateBean();
|
|
|
|
}
|
|
|
|
|
|
|
|
protected ActionListener checkValidActionListener = new ActionListener() {
|
|
|
|
|
|
|
|
public void actionPerformed(ActionEvent evt) {
|
|
|
|
formulaPane.checkContentValid();
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
private ActionListener calculateActionListener = new ActionListener() {
|
|
|
|
@Override
|
|
|
|
public void actionPerformed(ActionEvent e) {
|
|
|
|
Calculator calculator = Calculator.createCalculator();
|
|
|
|
JTemplate<?, ?> template = HistoryTemplateListPane.getInstance().getCurrentEditingTemplate();
|
|
|
|
if (template != null) {
|
|
|
|
IOFile file = template.getTarget();
|
|
|
|
calculator.setAttribute(TableDataSource.class, file);
|
|
|
|
calculator.pushNameSpace(SimpleCellValueNameSpace.getInstance());
|
|
|
|
}
|
|
|
|
BaseFormula formula = GroupFormulaPane.this.update();
|
|
|
|
String message = calculate(formula, formulaPane.analyze4Parameters(calculator), calculator);
|
|
|
|
JOptionPane.showMessageDialog(DesignerContext.getDesignerFrame(), message);
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
private String calculate(BaseFormula formula, Parameter[] parameters, Calculator calculator) {
|
|
|
|
final Map<String, Object> parameterMap = new HashMap<String, Object>();
|
|
|
|
if (ArrayUtils.isNotEmpty(parameters)) {
|
|
|
|
final ParameterInputPane pPane = new ParameterInputPane(parameters);
|
|
|
|
pPane.showSmallWindow(DesignerContext.getDesignerFrame(), new DialogActionAdapter() {
|
|
|
|
@Override
|
|
|
|
public void doOk() {
|
|
|
|
parameterMap.putAll(pPane.update());
|
|
|
|
}
|
|
|
|
}).setVisible(true);
|
|
|
|
}
|
|
|
|
calculator.pushNameSpace(ParameterMapNameSpace.create(parameterMap));
|
|
|
|
String message;
|
|
|
|
try {
|
|
|
|
Object result = formula.evalValue(calculator);
|
|
|
|
message = Inter.getLocText("FR-Designer_Group_Formula_Result") + ":" + GeneralUtils.objectToString(result);
|
|
|
|
} catch (UtilEvalError utilEvalError) {
|
|
|
|
message = Inter.getLocText("FR-Designer_Group_Formula_Calculate_Error") + ":" + utilEvalError.getMessage();
|
|
|
|
}
|
|
|
|
return message;
|
|
|
|
}
|
|
|
|
|
|
|
|
public class VariableTreeAndDescriptionArea extends JPanel {
|
|
|
|
|
|
|
|
private JTree variablesTree;
|
|
|
|
private UITextArea descriptionTextArea;
|
|
|
|
|
|
|
|
public VariableTreeAndDescriptionArea() {
|
|
|
|
this.initComponents();
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initFunctionTypeList(JPanel functionPane) {
|
|
|
|
functionTypeList = new QuickList(functionTypeListModel);
|
|
|
|
UIScrollPane functionTypeScrollPane = new UIScrollPane(functionTypeList);
|
|
|
|
functionTypeScrollPane.setBorder(new UIRoundedBorder(UIConstants.LINE_COLOR, 1, UIConstants.ARC));
|
|
|
|
functionTypeScrollPane.setPreferredSize(new Dimension(140, 200));
|
|
|
|
functionPane.add(this.createNamePane(Inter.getLocText("FormulaD-Function_category") + ":", functionTypeScrollPane), BorderLayout.WEST);
|
|
|
|
initTypeListCellRenderer();
|
|
|
|
initGroupTypeModel();
|
|
|
|
initTypeListSelectionListener();
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initTypeListCellRenderer() {
|
|
|
|
functionTypeList.setCellRenderer(
|
|
|
|
new DefaultListCellRenderer() {
|
|
|
|
@Override
|
|
|
|
public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
|
|
|
|
super.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
|
|
|
|
if (value instanceof FunctionGroup) {
|
|
|
|
this.setText(((FunctionGroup) value).getGroupName());
|
|
|
|
}
|
|
|
|
return this;
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initTypeListSelectionListener() {
|
|
|
|
functionTypeList.addListSelectionListener(new ListSelectionListener() {
|
|
|
|
public void valueChanged(ListSelectionEvent evt) {
|
|
|
|
Object selectedValue = ((JList) evt.getSource()).getSelectedValue();
|
|
|
|
if (!(selectedValue instanceof FunctionGroup)) {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
NameAndDescription[] nads = ((FunctionGroup) selectedValue).getDescriptions();
|
|
|
|
functionNameModel = (DefaultListModel) functionNameList.getModel();
|
|
|
|
functionNameModel.clear();
|
|
|
|
for (NameAndDescription nad : nads) {
|
|
|
|
functionNameModel.addElement(nad);
|
|
|
|
}
|
|
|
|
if (functionNameModel.size() > 0) {
|
|
|
|
functionNameList.setSelectedIndex(0);
|
|
|
|
functionNameList.ensureIndexIsVisible(0);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initGroupTypeModel() {
|
|
|
|
functionTypeListModel.addElement(FunctionConstants.COMMON);
|
|
|
|
for (int i = 0; i < FunctionConstants.EMBFUNCTIONS.length; i++) {
|
|
|
|
functionTypeListModel.addElement(FunctionConstants.EMBFUNCTIONS[i]);
|
|
|
|
}
|
|
|
|
functionTypeListModel.addElement(FunctionConstants.ALL);
|
|
|
|
functionTypeListModel.addElement(FunctionConstants.CUSTOM);
|
|
|
|
functionTypeListModel.addElement(FunctionConstants.PLUGIN);
|
|
|
|
|
|
|
|
//hugh: 从函数分组插件中添加分组
|
|
|
|
FunctionConstants.addFunctionGroupFromPlugins(functionTypeListModel);
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initFunctionNameListCellRenderer() {
|
|
|
|
functionNameList.setCellRenderer(new DefaultListCellRenderer() {
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
|
|
|
|
super.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
|
|
|
|
if (value instanceof NameAndDescription) {
|
|
|
|
this.setText(((NameAndDescription) value).getName());
|
|
|
|
}
|
|
|
|
return this;
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initFunctionNameListSelectionListener() {
|
|
|
|
functionNameList.addListSelectionListener(new ListSelectionListener() {
|
|
|
|
|
|
|
|
public void valueChanged(ListSelectionEvent evt) {
|
|
|
|
Object selectedValue = functionNameList.getSelectedValue();
|
|
|
|
if (!(selectedValue instanceof NameAndDescription)) {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
String description = ((NameAndDescription) selectedValue).getDesc();
|
|
|
|
descriptionTextArea.setText(description);
|
|
|
|
setTextAreaText(description);
|
|
|
|
descriptionTextArea.moveCaretPosition(0);
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initFunctionNameListMouseListener() {
|
|
|
|
functionNameList.addMouseListener(new MouseAdapter() {
|
|
|
|
public void mouseClicked(MouseEvent evt) {
|
|
|
|
if (evt.getClickCount() >= 2) {
|
|
|
|
Object selectedValue = functionNameList.getSelectedValue();
|
|
|
|
if (!(selectedValue instanceof NameAndDescription)) {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
String insert = ((NameAndDescription) selectedValue).getName() + "()";
|
|
|
|
formulaPane.applyText(insert);
|
|
|
|
|
|
|
|
}
|
|
|
|
if (SwingUtilities.isRightMouseButton(evt)) {
|
|
|
|
JPopupMenu popupMenu = new JPopupMenu();
|
|
|
|
VariableTreeAndDescriptionArea.LookDetailAction lookDetailAction = new VariableTreeAndDescriptionArea.LookDetailAction();
|
|
|
|
popupMenu.add(lookDetailAction);
|
|
|
|
|
|
|
|
// peter: 只有弹出菜单有子菜单的时候,才需要弹出来.
|
|
|
|
GUICoreUtils.showPopupMenu(popupMenu, functionNameList, evt.getX() - 1, evt.getY() - 1);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initFunctionNameList(JPanel functionPane) {
|
|
|
|
functionNameList = new JList(new DefaultListModel());
|
|
|
|
UIScrollPane functionNameScrollPane = new UIScrollPane(functionNameList);
|
|
|
|
functionNameScrollPane.setPreferredSize(new Dimension(140, 200));
|
|
|
|
functionPane.add(
|
|
|
|
this.createNamePane(Inter.getLocText("FormulaD-Function_name") + ":", functionNameScrollPane),
|
|
|
|
BorderLayout.CENTER);
|
|
|
|
functionNameScrollPane.setBorder(new UIRoundedBorder(UIConstants.LINE_COLOR, 1, UIConstants.ARC));
|
|
|
|
initFunctionNameListCellRenderer();
|
|
|
|
initFunctionNameListSelectionListener();
|
|
|
|
initFunctionNameListMouseListener();
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initDescriptionTextArea() {
|
|
|
|
// Description
|
|
|
|
descriptionTextArea = new UITextArea(16, 27);
|
|
|
|
|
|
|
|
UIScrollPane desScrollPane = new UIScrollPane(descriptionTextArea);
|
|
|
|
desScrollPane.setBorder(null);
|
|
|
|
this.add(this.createNamePane(Inter.getLocText("FR-Designer_FormulaPane_Formula_Description") + ":", desScrollPane), BorderLayout.EAST);
|
|
|
|
descriptionTextArea.setBackground(Color.white);
|
|
|
|
descriptionTextArea.setLineWrap(true);
|
|
|
|
descriptionTextArea.setWrapStyleWord(true);
|
|
|
|
descriptionTextArea.setEditable(false);
|
|
|
|
descriptionTextArea.addMouseListener(new MouseAdapter() {
|
|
|
|
|
|
|
|
public void mouseClicked(MouseEvent evt) {
|
|
|
|
if (evt.getClickCount() >= 2) {
|
|
|
|
showPopupPane();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
});
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
private StringBuilder getText(TextUserObject selectedValue, String path) throws IOException {
|
|
|
|
Reader desReader;
|
|
|
|
StringBuilder desBuf = new StringBuilder();
|
|
|
|
InputStream desInputStream = BaseUtils.readResource(path + (selectedValue).displayText + ".txt");
|
|
|
|
if (desInputStream == null) {
|
|
|
|
String description = "";
|
|
|
|
desReader = new StringReader(description);
|
|
|
|
} else {
|
|
|
|
desReader = new InputStreamReader(desInputStream, EncodeConstants.ENCODING_UTF_8);
|
|
|
|
}
|
|
|
|
BufferedReader reader = new BufferedReader(desReader);
|
|
|
|
String lineText;
|
|
|
|
while ((lineText = reader.readLine()) != null) {
|
|
|
|
if (desBuf.length() > 0) {
|
|
|
|
desBuf.append('\n');
|
|
|
|
}
|
|
|
|
desBuf.append(lineText);
|
|
|
|
}
|
|
|
|
reader.close();
|
|
|
|
desReader.close();
|
|
|
|
return desBuf;
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initVariablesTreeSelectionListener() {
|
|
|
|
variablesTree.addTreeSelectionListener(new TreeSelectionListener() {
|
|
|
|
public void valueChanged(TreeSelectionEvent e) {
|
|
|
|
Object selectedValue = ((DefaultMutableTreeNode) variablesTree.getLastSelectedPathComponent()).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/";
|
|
|
|
} else {
|
|
|
|
path = "/com/fr/design/insert/formula/variable/en/";
|
|
|
|
}
|
|
|
|
if (selectedValue instanceof TextUserObject) {
|
|
|
|
desBuf = getText((TextUserObject) selectedValue, path);
|
|
|
|
}
|
|
|
|
} catch (IOException exp) {
|
|
|
|
FRContext.getLogger().error(exp.getMessage(), exp);
|
|
|
|
}
|
|
|
|
descriptionTextArea.setText(desBuf.toString());
|
|
|
|
descriptionTextArea.moveCaretPosition(0);
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initVariablesTree() {
|
|
|
|
// vairable.
|
|
|
|
variablesTree = new JTree();
|
|
|
|
UIScrollPane variablesTreePane = new UIScrollPane(variablesTree);
|
|
|
|
variablesTreePane.setBorder(new UIRoundedBorder(UIConstants.LINE_COLOR, 1, UIConstants.ARC));
|
|
|
|
this.add(this.createNamePane(
|
|
|
|
Inter.getLocText("FR-Designer_FormulaPane_Variables") + ":", variablesTreePane), BorderLayout.CENTER);
|
|
|
|
variablesTree.setRootVisible(false);
|
|
|
|
variablesTree.setShowsRootHandles(true);
|
|
|
|
variablesTree.addMouseListener(applyTextMouseListener);
|
|
|
|
variablesTree.setCellRenderer(applyTreeCellRenderer);
|
|
|
|
|
|
|
|
initDescriptionTextArea();
|
|
|
|
|
|
|
|
initVariablesTreeSelectionListener();
|
|
|
|
}
|
|
|
|
|
|
|
|
private void initComponents() {
|
|
|
|
this.setLayout(new BorderLayout(4, 4));
|
|
|
|
// Function
|
|
|
|
JPanel functionPane = new JPanel(new BorderLayout(4, 4));
|
|
|
|
this.add(functionPane, BorderLayout.WEST);
|
|
|
|
initFunctionTypeList(functionPane);
|
|
|
|
initFunctionNameList(functionPane);
|
|
|
|
initVariablesTree();
|
|
|
|
// 选择:
|
|
|
|
functionTypeList.setSelectedIndex(0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* 查看函数的详细信息
|
|
|
|
*/
|
|
|
|
private class LookDetailAction extends UpdateAction {
|
|
|
|
|
|
|
|
public LookDetailAction() {
|
|
|
|
this.setName(Inter.getLocText("FR-Designer_FormulaPane_Function_Detail"));
|
|
|
|
this.setMnemonic('L');
|
|
|
|
this.setSmallIcon(BaseUtils.readIcon("/com/fr/design/images/m_file/preview.png"));
|
|
|
|
}
|
|
|
|
|
|
|
|
// 弹出的窗口中显示函数的用法明细
|
|
|
|
public void actionPerformed(ActionEvent evt) {
|
|
|
|
showPopupPane();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
private void showPopupPane() {
|
|
|
|
BasicPane basicPane = new BasicPane() {
|
|
|
|
@Override
|
|
|
|
protected String title4PopupWindow() {
|
|
|
|
return Inter.getLocText("FR-Designer_FormulaPane_Function_Detail");
|
|
|
|
}
|
|
|
|
};
|
|
|
|
basicPane.setLayout(FRGUIPaneFactory.createBorderLayout());
|
|
|
|
UITextArea desArea = new UITextArea();
|
|
|
|
// desArea。setEnabled(false);
|
|
|
|
desArea.setText(this.getTextAreaText());
|
|
|
|
basicPane.add(new UIScrollPane(desArea), BorderLayout.CENTER);
|
|
|
|
BasicDialog dialog = basicPane.showWindow(DesignerContext.getDesignerFrame());
|
|
|
|
dialog.setVisible(true);
|
|
|
|
}
|
|
|
|
|
|
|
|
private String getTextAreaText() {
|
|
|
|
return this.descriptionTextArea.getText();
|
|
|
|
}
|
|
|
|
|
|
|
|
private void setTextAreaText(String text) {
|
|
|
|
this.descriptionTextArea.setText(text);
|
|
|
|
}
|
|
|
|
|
|
|
|
private JPanel createNamePane(String name, JComponent comp) {
|
|
|
|
JPanel namePane = new JPanel(new BorderLayout(4, 4));
|
|
|
|
namePane.add(new UILabel(name), BorderLayout.NORTH);
|
|
|
|
namePane.add(comp, BorderLayout.CENTER);
|
|
|
|
return namePane;
|
|
|
|
}
|
|
|
|
|
|
|
|
private MouseListener applyTextMouseListener = new MouseAdapter() {
|
|
|
|
|
|
|
|
public void mouseClicked(MouseEvent evt) {
|
|
|
|
if (evt.getClickCount() >= 2) {
|
|
|
|
Object source = evt.getSource();
|
|
|
|
if (source instanceof JTree) {
|
|
|
|
JTree tree = (JTree) source;
|
|
|
|
TreePath selectedTreePah = tree.getSelectionPath();
|
|
|
|
if (selectedTreePah != null) {
|
|
|
|
DefaultMutableTreeNode selectedTreeNode = (DefaultMutableTreeNode) selectedTreePah.getLastPathComponent();
|
|
|
|
Object userObject = selectedTreeNode.getUserObject();
|
|
|
|
if (userObject != null && userObject instanceof TextUserObject) {
|
|
|
|
formulaPane.applyText(((TextUserObject) userObject).getText());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
};
|
|
|
|
private DefaultTreeCellRenderer applyTreeCellRenderer = new DefaultTreeCellRenderer() {
|
|
|
|
|
|
|
|
public Component getTreeCellRendererComponent(JTree tree,
|
|
|
|
Object value, boolean selected, boolean expanded,
|
|
|
|
boolean leaf, int row, boolean hasFocus) {
|
|
|
|
super.getTreeCellRendererComponent(tree, value, selected,
|
|
|
|
expanded, leaf, row, hasFocus);
|
|
|
|
|
|
|
|
DefaultMutableTreeNode treeNode = (DefaultMutableTreeNode) value;
|
|
|
|
Object userObj = treeNode.getUserObject();
|
|
|
|
|
|
|
|
if (userObj instanceof TextUserObject) {
|
|
|
|
this.setIcon(null);
|
|
|
|
this.setText(((TextUserObject) userObj).getDisplayText());
|
|
|
|
} else if (userObj instanceof TextFolderUserObject) {
|
|
|
|
TextFolderUserObject textUserObject = (TextFolderUserObject) userObj;
|
|
|
|
if (leaf) {
|
|
|
|
this.setText(textUserObject.getText());
|
|
|
|
} else {
|
|
|
|
this.setText(textUserObject.getText() + " - ["
|
|
|
|
+ treeNode.getChildCount() + "]");
|
|
|
|
}
|
|
|
|
|
|
|
|
this.setIcon(textUserObject.getIcon());
|
|
|
|
}
|
|
|
|
|
|
|
|
return this;
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
public void populate(VariableResolver variableResolver) {
|
|
|
|
// varibale tree.
|
|
|
|
DefaultTreeModel variableModel = (DefaultTreeModel) variablesTree.getModel();
|
|
|
|
|
|
|
|
DefaultMutableTreeNode rootNode = (DefaultMutableTreeNode) variableModel.getRoot();
|
|
|
|
rootNode.removeAllChildren();
|
|
|
|
|
|
|
|
if (variableResolver.isBindCell()) {
|
|
|
|
// 加上当前值"$$$"
|
|
|
|
DefaultMutableTreeNode bindCellNode = new DefaultMutableTreeNode(new TextUserObject("$$$"));
|
|
|
|
rootNode.add(bindCellNode);
|
|
|
|
}
|
|
|
|
|
|
|
|
rootNode.add(new TextFolderUserObject(Inter.getLocText("FormulaD-Data_Fields"),
|
|
|
|
BaseUtils.readIcon("/com/fr/design/images/dialog/table.png"),
|
|
|
|
variableResolver.resolveColumnNames()).createMutableTreeNode());
|
|
|
|
|
|
|
|
// Set cutReport Variable
|
|
|
|
rootNode.add(new TextFolderUserObject(Inter.getLocText("FR-Designer_FormulaPane_Variables"),
|
|
|
|
BaseUtils.readIcon("/com/fr/design/images/dialog/variable.png"),
|
|
|
|
variableResolver.resolveCurReportVariables()).createMutableTreeNode());
|
|
|
|
|
|
|
|
rootNode.add(new TextFolderUserObject(Inter.getLocText(new String[]{"Datasource-Datasource", "Parameter"}),
|
|
|
|
BaseUtils.readIcon("/com/fr/design/images/dialog/parameter.gif"),
|
|
|
|
variableResolver.resolveTableDataParameterVariables()).createMutableTreeNode());
|
|
|
|
|
|
|
|
rootNode.add(new TextFolderUserObject(Inter.getLocText("ParameterD-Report_Parameter"),
|
|
|
|
BaseUtils.readIcon("/com/fr/design/images/m_report/p.gif"),
|
|
|
|
variableResolver.resolveReportParameterVariables()).createMutableTreeNode());
|
|
|
|
|
|
|
|
rootNode.add(new TextFolderUserObject(Inter.getLocText("M_Server-Global_Parameters"),
|
|
|
|
BaseUtils.readIcon("/com/fr/design/images/dialog/parameter.gif"),
|
|
|
|
variableResolver.resolveGlobalParameterVariables()).createMutableTreeNode());
|
|
|
|
|
|
|
|
variableModel.reload();
|
|
|
|
// Expand
|
|
|
|
for (int row = 0; row < this.variablesTree.getRowCount(); row++) {
|
|
|
|
this.variablesTree.expandRow(row);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
public static class TextFolderUserObject {
|
|
|
|
|
|
|
|
private String text;
|
|
|
|
private Icon icon;
|
|
|
|
private String[] subNodes = new String[0];
|
|
|
|
|
|
|
|
public TextFolderUserObject(String text, Icon icon, String[] subNodes) {
|
|
|
|
this.text = text;
|
|
|
|
this.icon = icon;
|
|
|
|
this.subNodes = subNodes;
|
|
|
|
}
|
|
|
|
|
|
|
|
public String getText() {
|
|
|
|
return this.text;
|
|
|
|
}
|
|
|
|
|
|
|
|
public Icon getIcon() {
|
|
|
|
return this.icon;
|
|
|
|
}
|
|
|
|
|
|
|
|
MutableTreeNode createMutableTreeNode() {
|
|
|
|
DefaultMutableTreeNode variableTreeNode = new DefaultMutableTreeNode(this);
|
|
|
|
|
|
|
|
for (String subNode : subNodes) {
|
|
|
|
variableTreeNode.add(new DefaultMutableTreeNode(new TextUserObject(subNode)));
|
|
|
|
}
|
|
|
|
|
|
|
|
return variableTreeNode;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
public static class TextUserObject {
|
|
|
|
|
|
|
|
public TextUserObject(String text) {
|
|
|
|
this(text, text);
|
|
|
|
}
|
|
|
|
|
|
|
|
public TextUserObject(String text, String displayText) {
|
|
|
|
this.text = text;
|
|
|
|
this.displayText = displayText;
|
|
|
|
}
|
|
|
|
|
|
|
|
public String getText() {
|
|
|
|
return this.text;
|
|
|
|
}
|
|
|
|
|
|
|
|
public String getDisplayText() {
|
|
|
|
return this.displayText;
|
|
|
|
}
|
|
|
|
|
|
|
|
private String text;
|
|
|
|
private String displayText;
|
|
|
|
}
|
|
|
|
}
|