package shiyan11_1zz;
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.MouseEvent;
import java.awt.event.MouseListener;
import java.io.File;
import javax.swing.*;
public class ScientificCalculatorPanel extends JPanel implements ActionListener{
private JPanel leftPanel = new JPanel(new BorderLayout()); // 左侧面板
private JTextField processText = new JTextField(); // 用于显示计算过程的文本字段
private JTextField resultText = new JTextField("0"); // 用于显示计算结果的文本字段
private String resultStr = "0";
private String[] buttonExpr = { "CE", "C", "←", "÷", "7", "8", "9", "×", "4", "5", "6", "-", "1", "2", "3", "+",
"+/-", "0", ".", "=" }; // 按钮表达式数组
private RoundedButton[] buttons = new RoundedButton[buttonExpr.length]; // 按钮数组
private JPanel buttonPanel = new JPanel(new GridLayout(5, 4, 10, 10));
private JPanel rightPanel = new JPanel(new BorderLayout()); // 右侧面板
private JButton logDelButton = new RoundedButton("清空"); // 日志清空按钮
private JTextArea logRecord = new JTextArea("尚无历史记录"); // 日志记录文本区域
private String command = ""; // 当前操作命令
private String lastCommand = "";
private StringBuilder equation = new StringBuilder();
private StringBuilder logRecordText = new StringBuilder();
public ScientificCalculatorPanel() {
setLayout(new BorderLayout()); // 设置面板的布局管理器
setPreferredSize(new Dimension(1200, 800)); // 设置面板的首选大小
// 初始化左侧面板
leftPanel.setPreferredSize(new Dimension(850, 800)); // 设置左侧面板的大小
// 设置处理文本字段的属性
processText.setEditable(false); // 设置文本字段不可编辑
processText.setFont(new Font("黑体", Font.PLAIN, 25)); // 设置字体
processText.setHorizontalAlignment(JTextField.RIGHT); // 设置文本对齐方式为右对齐
processText.setBorder(BorderFactory.createMatteBorder(25, 3, 0, 3, new Color(181, 181, 181))); // 设置边框
processText.setBackground(new Color(181, 181, 181)); // 设置背景色
processText.setPreferredSize(new Dimension(850, 150)); // 设置首选大小
// 设置结果文本字段的属性
resultText.setEditable(false); // 设置文本字段不可编辑
resultText.setFont(new Font("黑体", Font.BOLD, 55)); // 设置字体为黑体加粗,大小为55
resultText.setHorizontalAlignment(JTextField.RIGHT); // 设置文本对齐方式为右对齐
resultText.setBorder(BorderFactory.createMatteBorder(0, 3, 5, 3, new Color(181, 181, 181))); // 设置边框
resultText.setBackground(new Color(181, 181, 181)); // 设置背景色
resultText.setPreferredSize(new Dimension(850, 50)); // 设置首选大小
// 初始化按钮面板,设置布局和边框
buttonPanel.setPreferredSize(new Dimension(850, 600));
buttonPanel.setBorder(BorderFactory.createMatteBorder(5, 3, 5, 3, new Color(181, 181, 181)));
for (int i = 0; i < buttonExpr.length; i++) {
buttons[i] = new RoundedButton(buttonExpr[i]);
buttons[i].setFont(new Font("Arial", Font.BOLD, 40));
buttons[i].setForeground(Color.BLACK);
if ("9876543210.=".contains(buttonExpr[i])) {
buttons[i].setBackground(Color.white);
if("=".equals(buttonExpr[i])) {
buttons[i].setBackground(new Color(126, 192, 238));
}
} else {
buttons[i].setBackground(new Color(232, 232, 232));
if("+/-".equals(buttonExpr[i])) {
buttons[i].setBackground(Color.white);
}
}
buttons[i].addActionListener(this);
buttons[i].addMouseListener(new ButtonMouseListener());
buttonPanel.add(buttons[i]);
}
// 将各个子面板添加到主面板
leftPanel.add(processText, BorderLayout.NORTH); // 将处理文本字段添加到左侧面板的北部
leftPanel.add(resultText, BorderLayout.CENTER); // 将结果文本字段添加到左侧面板的中部
leftPanel.add(buttonPanel, BorderLayout.SOUTH); // 将按钮面板添加到左侧面板的南部
add(leftPanel, BorderLayout.CENTER); // 将左侧面板添加到主面板的中心
// 初始化右侧面板
rightPanel.setPreferredSize(new Dimension(350, 800)); // 设置右侧面板的大小
JScrollPane rhtPanel = new JScrollPane(); // 右侧面板中的滚动面板
rhtPanel.setViewportView(logRecord); // 将日志记录文本区域设置为滚动面板的视图
rhtPanel.setBorder(null); // 设置滚动面板无边框
rightPanel.add(rhtPanel, BorderLayout.CENTER); // 将滚动面板添加到右侧面板的中心
logDelButton.setBackground(new Color(232, 232, 232)); // 设置日志清空按钮的背景色
logDelButton.setFont(new Font("黑体", Font.PLAIN, 25)); // 设置日志清空按钮的字体
logDelButton.setHorizontalAlignment(SwingConstants.CENTER); // 设置日志清空按钮的对齐方式为右对齐
logDelButton.addActionListener(e -> {
logRecordText = new StringBuilder("尚无历史记录");
logRecord.setText(logRecordText.toString());
}); // 为日志清空按钮添加事件监听
rightPanel.add(logDelButton, BorderLayout.NORTH); // 将日志清空按钮添加到右侧面板的南部
logRecord.setEditable(false); // 设置文本字段不可编辑
logRecord.setFont(new Font("黑体", Font.PLAIN, 20));
add(rightPanel, BorderLayout.EAST); // 将右侧面板添加到主面板的东部
addKeyListener(new ButtonKeyListener());
setFocusable(true);
SwingUtilities.invokeLater(new Runnable() {
public void run() {
requestFocusInWindow();
}
});
}
@Override
public void actionPerformed(ActionEvent e) {
command = e.getActionCommand();
if(lastCommand.equals("=")) {
logRecordText.append(equation.toString() + resultStr + "\n");
logRecord.setText(logRecordText.toString());
equation = new StringBuilder();
}
if(ScientificTools.isNumber(command)) {
if(resultStr.equals("0") || resultStr.length()==0) {
resultStr = command;
}else if(ScientificTools.isNumber(resultStr) || lastCommand.equals("←")){
resultStr += command;
}
}else if(command.equals(".")) {
if(ScientificTools.isNumber(resultStr) && !resultStr.contains(".")) {
resultStr += command;
}
}else if(command.equals("+/-")) {
if(ScientificTools.isNumber(resultStr)){
resultStr = "(-" + resultStr + ")";
}
}else if(ScientificTools.isOperationalSymbol(command)) {
equation.append(resultStr + command);
resultStr = "0";
}else if(command.equals("=")) {
try {
equation.append(resultStr);
resultStr = ScientificTools.calculate(equation.toString());
equation.append(command);
} catch (Exception e1) {
// TODO Auto-generated catch block
resultStr = "输入有误,请检查输入";
}
}else if(command.equals("C")) {
resultStr = "0";
equation = new StringBuilder();
}else if(command.equals("CE")) {
resultStr = "0";
}else if(command.equals("←")) {
try {
resultStr = equation.toString() + resultStr;
resultStr = resultStr.substring(0, resultStr.length() - 1);
equation = new StringBuilder(resultStr);
resultStr = "";
} catch (Exception e1) {
// TODO Auto-generated catch block
resultStr = "已经没有了别删了";
}
}
processText.setText(equation.toString());
lastCommand = command;
resultText.setText(resultStr);
}
class ButtonKeyListener implements KeyListener {
@Override
public void keyTyped(KeyEvent e) {
// 此方法可以根据需要保持空白
}
@Override
public void keyPressed(KeyEvent e) {
char keyChar = e.