package dell_system;
|
import com.fazecast.jSerialComm.SerialPort;
|
import Dell55aa.Dell55AA12HighPerf;
|
import Dell55aa.Dell55AA12HighPerf.ParseResult;
|
import javax.swing.*;
|
import javax.swing.border.TitledBorder;
|
import javax.swing.event.PopupMenuEvent;
|
import javax.swing.event.PopupMenuListener;
|
import java.awt.*;
|
import java.awt.event.WindowAdapter;
|
import java.awt.event.WindowEvent;
|
import java.io.PrintWriter;
|
import java.text.SimpleDateFormat;
|
import java.util.Date;
|
import java.util.ResourceBundle;
|
|
public class SerialCommPanel extends JPanel {
|
|
private static final long serialVersionUID = 1L;
|
private final ResourceBundle messages;
|
private final SerialPortService serialService = new SerialPortService();
|
|
// ÐÂÔö×Ö¶Î
|
private int packetCounter = 0;
|
private JLabel lblParseStatus;
|
private JCheckBox chkEnableParsing;
|
private JLabel lblPacketCount; // ÐÂÔö£ºÊý¾Ý°ü¼ÆÊý±êÇ©
|
|
// UI ×é¼þ
|
private JComboBox<String> cbPorts;
|
private JComboBox<String> cbBaudRate;
|
private JCheckBox chkHexDisplay;
|
private JCheckBox chkTimestamp;
|
private JCheckBox chkAppendNewline;
|
private JCheckBox chkHexSend;
|
private JCheckBox chkTimedSend;
|
private JTextField txtInterval;
|
private JButton btnOpenSerial;
|
private JButton btnStart;
|
private JButton btnPause;
|
private JButton btnClear;
|
private JTextField txtSendData;
|
private JButton btnSend;
|
private JTextArea txtRawData;
|
private JTextArea txtParsedData;
|
private JScrollPane rawScrollPane;
|
private JScrollPane parsedScrollPane;
|
|
private final SimpleDateFormat sdf = new SimpleDateFormat("HH:mm:ss.SSS");
|
|
public SerialCommPanel(ResourceBundle messages) {
|
this.messages = messages;
|
initUI();
|
}
|
|
/* ================= UI ³õʼ»¯ ================= */
|
private void initUI() {
|
setLayout(new GridBagLayout());
|
GridBagConstraints gbc = new GridBagConstraints();
|
gbc.insets = new Insets(5, 10, 5, 10);
|
gbc.anchor = GridBagConstraints.WEST;
|
gbc.fill = GridBagConstraints.HORIZONTAL;
|
setBackground(new Color(240, 245, 249));
|
|
/* ===== ´®¿ÚÑ¡ÔñºÍ²¨ÌØÂÊ ===== */
|
gbc.gridx = 0;
|
gbc.gridy = 0;
|
gbc.gridwidth = 1;
|
gbc.weightx = 0.3;
|
JPanel portPanel = new JPanel(new BorderLayout(5, 0));
|
portPanel.setBackground(new Color(240, 245, 249));
|
JLabel lblPort = new JLabel(messages.getString("SERIAL_PORT"));
|
lblPort.setFont(new Font("ËÎÌå", Font.BOLD, 12));
|
portPanel.add(lblPort, BorderLayout.WEST);
|
|
cbPorts = new JComboBox<>();
|
cbPorts.setBackground(new Color(200, 255, 200));
|
scanSerialPorts();
|
cbPorts.addPopupMenuListener(new PopupMenuListener() {
|
@Override
|
public void popupMenuWillBecomeVisible(PopupMenuEvent e) {
|
scanSerialPorts();
|
}
|
|
@Override
|
public void popupMenuWillBecomeInvisible(PopupMenuEvent e) {
|
}
|
|
@Override
|
public void popupMenuCanceled(PopupMenuEvent e) {
|
}
|
});
|
portPanel.add(cbPorts, BorderLayout.CENTER);
|
add(portPanel, gbc);
|
|
gbc.gridx++;
|
JPanel baudPanel = new JPanel(new BorderLayout(5, 0));
|
baudPanel.setBackground(new Color(240, 245, 249));
|
JLabel lblBaud = new JLabel(messages.getString("BAUD_RATE"));
|
lblBaud.setFont(new Font("ËÎÌå", Font.BOLD, 12));
|
baudPanel.add(lblBaud, BorderLayout.WEST);
|
|
cbBaudRate = new JComboBox<>(new String[]{
|
"19200", "38400", "57600", "115200",
|
"230400", "460800", "921600"
|
});
|
cbBaudRate.setBackground(new Color(255, 200, 255));
|
cbBaudRate.setSelectedItem("115200");
|
baudPanel.add(cbBaudRate, BorderLayout.CENTER);
|
add(baudPanel, gbc);
|
|
gbc.gridx++;
|
btnOpenSerial = createStyledButton(messages.getString("OPEN_SERIAL"), new Color(70, 130, 180));
|
btnOpenSerial.addActionListener(e -> toggleSerialPort());
|
add(btnOpenSerial, gbc);
|
|
/* ===== ÔʼÊý¾ÝÏÔÊ¾ÇøÓò ===== */
|
gbc.gridx = 0;
|
gbc.gridy++;
|
gbc.gridwidth = 3;
|
gbc.weighty = 0.5;
|
gbc.fill = GridBagConstraints.BOTH;
|
txtRawData = new JTextArea();
|
txtRawData.setFont(new Font("Monospaced", Font.PLAIN, 12));
|
txtRawData.setEditable(false);
|
txtRawData.setBackground(new Color(255, 200, 200));
|
txtRawData.setLineWrap(true);
|
txtRawData.setWrapStyleWord(false);
|
rawScrollPane = new JScrollPane(txtRawData);
|
rawScrollPane.setBorder(BorderFactory.createTitledBorder(
|
BorderFactory.createLineBorder(Color.DARK_GRAY),
|
messages.getString("RAW_DATA_WINDOW"),
|
TitledBorder.LEFT, TitledBorder.TOP,
|
new Font("ËÎÌå", Font.BOLD, 12), Color.BLACK));
|
add(rawScrollPane, gbc);
|
|
/* ===== ½âÎöÊý¾ÝÏÔÊ¾ÇøÓò ===== */
|
gbc.gridy++;
|
txtParsedData = new JTextArea();
|
txtParsedData.setFont(new Font("Monospaced", Font.PLAIN, 12));
|
txtParsedData.setEditable(false);
|
txtParsedData.setBackground(new Color(255, 255, 200));
|
txtParsedData.setLineWrap(true);
|
txtParsedData.setWrapStyleWord(false);
|
parsedScrollPane = new JScrollPane(txtParsedData);
|
parsedScrollPane.setBorder(BorderFactory.createTitledBorder(
|
BorderFactory.createLineBorder(Color.DARK_GRAY),
|
messages.getString("PARSED_DATA_WINDOW"),
|
TitledBorder.LEFT, TitledBorder.TOP,
|
new Font("ËÎÌå", Font.BOLD, 12), Color.BLACK));
|
add(parsedScrollPane, gbc);
|
|
/* ===== Ϊ½âÎö´°¿ÚÌí¼ÓÓÒ¼ü²Ëµ¥ ===== */
|
JPopupMenu parsedPopup = new JPopupMenu();
|
JMenuItem clearItem = new JMenuItem(messages.getString("CLEAR"));
|
JMenuItem exportItem = new JMenuItem(messages.getString("EXPORT"));
|
|
clearItem.addActionListener(e -> txtParsedData.setText(""));
|
exportItem.addActionListener(e -> exportParsedData());
|
|
parsedPopup.add(clearItem);
|
parsedPopup.add(exportItem);
|
txtParsedData.setComponentPopupMenu(parsedPopup);
|
|
/* ===== ¿ØÖƺÍÏÔʾѡÏî ===== */
|
gbc.gridy++;
|
gbc.weighty = 0;
|
gbc.fill = GridBagConstraints.HORIZONTAL;
|
JPanel controlPanel = new JPanel(new BorderLayout(10, 0));
|
controlPanel.setBackground(new Color(240, 245, 249));
|
|
// ×ó²à¿ØÖư´Å¥
|
JPanel buttonPanel = new JPanel(new FlowLayout(FlowLayout.LEFT, 10, 5));
|
buttonPanel.setBackground(new Color(240, 245, 249));
|
|
btnStart = createStyledButton(messages.getString("START"), new Color(70, 130, 180));
|
btnPause = createStyledButton(messages.getString("PAUSE"), new Color(218, 165, 32));
|
btnClear = createStyledButton(messages.getString("CLEAR"), new Color(205, 92, 92));
|
|
btnStart.setEnabled(true);
|
btnPause.setEnabled(false);
|
|
btnStart.addActionListener(e -> startCapture());
|
btnPause.addActionListener(e -> pauseCapture());
|
btnClear.addActionListener(e -> clearDisplay());
|
|
buttonPanel.add(btnStart);
|
buttonPanel.add(btnPause);
|
buttonPanel.add(btnClear);
|
|
// ÐÂÔö£ºÊý¾Ý°ü¼ÆÊý±êÇ©
|
lblPacketCount = new JLabel(String.format(messages.getString("packet.count.format"), 0));
|
lblPacketCount.setFont(new Font("ËÎÌå", Font.BOLD, 12));
|
lblPacketCount.setForeground(new Color(0, 100, 0)); // ÉîÂÌÉ«
|
buttonPanel.add(lblPacketCount);
|
|
controlPanel.add(buttonPanel, BorderLayout.WEST);
|
|
// ÓÒ²àÏÔʾѡÏî
|
JPanel checkboxPanel = new JPanel(new FlowLayout(FlowLayout.LEFT, 10, 5));
|
checkboxPanel.setBackground(new Color(240, 245, 249));
|
|
chkHexDisplay = createStyledCheckbox(messages.getString("HEX_DISPLAY"));
|
chkTimestamp = createStyledCheckbox(messages.getString("TIMESTAMP"));
|
chkAppendNewline = createStyledCheckbox(messages.getString("APPEND_NEWLINE"));
|
chkHexSend = createStyledCheckbox(messages.getString("HEX_SEND"));
|
chkTimedSend = createStyledCheckbox(messages.getString("TIMED_SEND"));
|
chkHexDisplay.setSelected(true);
|
chkTimestamp.setSelected(true);
|
chkAppendNewline.setSelected(true);
|
|
txtInterval = new JTextField("1000", 5);
|
txtInterval.setEnabled(false);
|
txtInterval.setFont(new Font("ËÎÌå", Font.PLAIN, 12));
|
txtInterval.setBackground(Color.WHITE);
|
chkTimedSend.addActionListener(e -> txtInterval.setEnabled(chkTimedSend.isSelected()));
|
|
// ÐÂÔö½âÎö¿ØÖÆÑ¡Ïî
|
chkEnableParsing = createStyledCheckbox(messages.getString("ENABLE_PARSING"));
|
chkEnableParsing.setSelected(true);
|
|
// ɾ³ý½âÎöÆ÷ÏÂÀ¿ò¼°Æä±êÇ©
|
checkboxPanel.add(chkHexDisplay);
|
checkboxPanel.add(chkTimestamp);
|
checkboxPanel.add(chkAppendNewline);
|
checkboxPanel.add(chkHexSend);
|
checkboxPanel.add(chkTimedSend);
|
checkboxPanel.add(new JLabel(messages.getString("INTERVAL_MS")));
|
checkboxPanel.add(txtInterval);
|
checkboxPanel.add(chkEnableParsing);
|
controlPanel.add(checkboxPanel, BorderLayout.EAST);
|
|
// ÐÂÔö½âÎö״ָ̬ʾÆ÷
|
JPanel statusPanel = new JPanel(new FlowLayout(FlowLayout.RIGHT));
|
statusPanel.setBackground(new Color(240, 245, 249));
|
lblParseStatus = new JLabel(messages.getString("parser.ready"));
|
lblParseStatus.setFont(new Font("ËÎÌå", Font.PLAIN, 12));
|
lblParseStatus.setForeground(Color.BLUE);
|
statusPanel.add(lblParseStatus);
|
controlPanel.add(statusPanel, BorderLayout.CENTER);
|
|
add(controlPanel, gbc);
|
|
/* ===== ·¢ËÍÇøÓò ===== */
|
gbc.gridy++;
|
JPanel sendPanel = new JPanel(new BorderLayout(10, 5));
|
sendPanel.setBackground(new Color(240, 245, 249));
|
|
txtSendData = new JTextField();
|
txtSendData.setBackground(new Color(200, 200, 255));
|
txtSendData.setFont(new Font("ËÎÌå", Font.PLAIN, 12));
|
|
btnSend = createStyledButton(messages.getString("SEND"), new Color(60, 179, 113));
|
btnSend.addActionListener(e -> sendData());
|
|
sendPanel.add(new JLabel(messages.getString("SEND_DATA")), BorderLayout.WEST);
|
sendPanel.add(txtSendData, BorderLayout.CENTER);
|
sendPanel.add(btnSend, BorderLayout.EAST);
|
add(sendPanel, gbc);
|
|
addNotify();
|
}
|
|
/* ================= ɨÃè´®¿ÚÁбí ================= */
|
private void scanSerialPorts() {
|
cbPorts.removeAllItems();
|
SerialPort[] ports = SerialPort.getCommPorts();
|
if (ports.length == 0) {
|
cbPorts.addItem("No port found");
|
cbPorts.setEnabled(false);
|
return;
|
}
|
for (SerialPort p : ports) {
|
String item = p.getSystemPortName();
|
String desc = p.getPortDescription();
|
if (desc != null && !desc.trim().isEmpty()) {
|
item += " (" + desc + ")";
|
}
|
cbPorts.addItem(item);
|
}
|
cbPorts.setEnabled(true);
|
}
|
|
/* ================= ´ò¿ª/¹Ø±Õ´®¿Ú ================= */
|
private void toggleSerialPort() {
|
if (serialService.isOpen()) {
|
serialService.close();
|
btnOpenSerial.setText(messages.getString("OPEN_SERIAL"));
|
btnStart.setEnabled(true);
|
btnPause.setEnabled(false);
|
} else {
|
String selected = (String) cbPorts.getSelectedItem();
|
if (selected == null || selected.startsWith("No port")) {
|
JOptionPane.showMessageDialog(this,
|
messages.getString("SELECT_PORT_ERROR"),
|
messages.getString("ERROR"), JOptionPane.ERROR_MESSAGE);
|
return;
|
}
|
String portName = selected.split(" ")[0];
|
int baud = Integer.parseInt((String) cbBaudRate.getSelectedItem());
|
if (serialService.open(portName, baud)) {
|
btnOpenSerial.setText(messages.getString("CLOSE_SERIAL"));
|
startCapture();
|
} else {
|
JOptionPane.showMessageDialog(this,
|
messages.getString("OPEN_PORT_ERROR"),
|
messages.getString("ERROR"), JOptionPane.ERROR_MESSAGE);
|
}
|
}
|
}
|
|
/* ================= Êý¾Ý½ÓÊÕ¿ØÖÆ ================= */
|
private void startCapture() {
|
if (!serialService.isOpen()) return;
|
serialService.startCapture(this::appendRawData);
|
btnStart.setEnabled(false);
|
btnPause.setEnabled(true);
|
}
|
|
private void pauseCapture() {
|
serialService.setPaused(!serialService.isPaused());
|
btnPause.setText(serialService.isPaused()
|
? messages.getString("RESUME")
|
: messages.getString("PAUSE"));
|
}
|
|
/* ================= ½âÎöÊý¾ÝÏÔʾ ================= */
|
private void appendParsedData(byte[] data) {
|
if (!chkEnableParsing.isSelected()) return;
|
|
SwingUtilities.invokeLater(() -> {
|
packetCounter++;
|
lblPacketCount.setText(String.format(messages.getString("packet.count.format"), packetCounter)); // ¸üмÆÊý±êÇ©
|
|
try {
|
// ½«×Ö½ÚÊý¾Ýת»»ÎªÊ®Áù½øÖÆ×Ö·û´®
|
String hexData = bytesToHex(data).toUpperCase();
|
// ʹÓÃDell55AA12HighPerf½âÎö
|
ParseResult result = Dell55AA12HighPerf.parse(hexData);
|
|
if (result != null) {
|
// ¹¹½¨×´Ì¬×Ö·û´®
|
String buttonStatus = result.sosButtonPressed ? messages.getString("yes") : messages.getString("no");
|
String staticStatus = result.isStatic ? messages.getString("yes") : messages.getString("no");
|
String sleepStatus = result.isSleeping ? messages.getString("yes") : messages.getString("no");
|
String vibrationStatus = (result.vibrationState == 1) ? messages.getString("on") : messages.getString("off");
|
String uwbStatus = result.tagRemoved ? messages.getString("off") : messages.getString("on");
|
|
// ¹¹½¨»ùÕ¾ÐÅÏ¢
|
StringBuilder anchorIds = new StringBuilder();
|
StringBuilder distances = new StringBuilder();
|
StringBuilder anchorPowers = new StringBuilder();
|
|
for (int i = 0; i < result.anchorCount; i++) {
|
if (i > 0) {
|
anchorIds.append(",");
|
distances.append(",");
|
anchorPowers.append(",");
|
}
|
anchorIds.append(result.anchorIds[i]);
|
distances.append(result.distances[i]);
|
anchorPowers.append(result.anchorPowers[i]);
|
}
|
|
// ¸ñʽ»¯Êä³ö
|
StringBuilder parsedOutput = new StringBuilder();
|
|
// Ìí¼Óʱ¼ä´Á£¨Èç¹û¹´Ñ¡£©
|
if (chkTimestamp.isSelected()) {
|
parsedOutput.append("[").append(sdf.format(new Date())).append("]\n");
|
}
|
|
parsedOutput.append(String.format(
|
"%s: %d\n%s: %d\n%s: %d%%\n%s: %s[%s], %s[%s], %s[%s], %s[%s], %s[%s]\n%s: %d\n%s: %d\n%s: (%s)\n%s: (%s)\n%s: (%s)\n\n",
|
messages.getString("label.id"), result.tagId,
|
messages.getString("label.sequence"), result.sequenceNum,
|
messages.getString("label.power"), result.power,
|
messages.getString("label.status"),
|
messages.getString("status.button"), buttonStatus,
|
messages.getString("status.static"), staticStatus,
|
messages.getString("status.sleeping"), sleepStatus,
|
messages.getString("status.vibration"), vibrationStatus,
|
messages.getString("status.uwb_switch"), uwbStatus,
|
messages.getString("label.tag_height"), result.tagHeight,
|
messages.getString("label.anchor_count"), result.anchorCount,
|
messages.getString("label.anchor_ids"), anchorIds.toString(),
|
messages.getString("label.distances"), distances.toString(),
|
messages.getString("label.anchor_powers"), anchorPowers.toString()
|
));
|
|
txtParsedData.append(parsedOutput.toString());
|
txtParsedData.setCaretPosition(txtParsedData.getDocument().getLength());
|
lblParseStatus.setText(String.format("%s (Packets: %d)", messages.getString("parser.ready"), packetCounter));
|
} else {
|
StringBuilder invalidMsg = new StringBuilder();
|
// Ìí¼Óʱ¼ä´Á£¨Èç¹û¹´Ñ¡£©
|
if (chkTimestamp.isSelected()) {
|
|
invalidMsg.append("[").append(sdf.format(new Date())).append("]\n");
|
}
|
invalidMsg.append(String.format("[Packet #%d] Not a valid 55AA12 packet\n\n", packetCounter));
|
|
txtParsedData.append(invalidMsg.toString());
|
lblParseStatus.setText(String.format("Parser: Invalid (Packets: %d)", packetCounter));
|
}
|
} catch (Exception e) {
|
StringBuilder errorMsg = new StringBuilder();
|
// Ìí¼Óʱ¼ä´Á£¨Èç¹û¹´Ñ¡£©
|
if (chkTimestamp.isSelected()) {
|
errorMsg.append("[").append(sdf.format(new Date())).append("]\n");
|
}
|
errorMsg.append(String.format("[Packet #%d] Parse error: %s\n\n",
|
packetCounter, e.getMessage()));
|
|
txtParsedData.append(errorMsg.toString());
|
lblParseStatus.setText(String.format("Parser: Error (Packets: %d)", packetCounter));
|
}
|
});
|
}
|
|
/* ================= UI ¸üР================= */
|
private void appendRawData(byte[] bytes) {
|
SwingUtilities.invokeLater(() -> {
|
StringBuilder sb = new StringBuilder();
|
|
if (chkTimestamp.isSelected()) {
|
sb.append("[").append(sdf.format(new Date())).append("] ");
|
}
|
|
if (chkHexDisplay.isSelected()) {
|
for (byte b : bytes) {
|
sb.append(String.format("%02X ", b));
|
}
|
} else {
|
for (byte b : bytes) {
|
if (b != 0) sb.append((char) b);
|
}
|
}
|
|
sb.append("\n");
|
txtRawData.append(sb.toString());
|
txtRawData.setCaretPosition(txtRawData.getDocument().getLength());
|
|
// ´¥·¢½âÎö
|
appendParsedData(bytes);
|
});
|
}
|
|
private void sendData() {
|
String data = txtSendData.getText().trim();
|
if (data.isEmpty()) {
|
JOptionPane.showMessageDialog(this,
|
messages.getString("EMPTY_SEND_DATA"),
|
messages.getString("WARNING"), JOptionPane.WARNING_MESSAGE);
|
return;
|
}
|
|
byte[] sendBytes;
|
|
if (chkHexSend.isSelected()) {
|
try {
|
sendBytes = hexStringToBytes(data);
|
if (sendBytes == null) {
|
throw new IllegalArgumentException("HEX¸ñʽ´íÎó");
|
}
|
} catch (Exception ex) {
|
JOptionPane.showMessageDialog(this,
|
"HEX¸ñʽ´íÎó£¬ÇëÊäÈëÓÐЧµÄÊ®Áù½øÖÆÊý¾Ý£¨È磺01 0A FF£©",
|
"¸ñʽ´íÎó", JOptionPane.ERROR_MESSAGE);
|
return;
|
}
|
} else {
|
sendBytes = data.getBytes();
|
if (chkAppendNewline.isSelected()) {
|
String newline = "\r\n";
|
byte[] newlineBytes = newline.getBytes();
|
byte[] combined = new byte[sendBytes.length + newlineBytes.length];
|
System.arraycopy(sendBytes, 0, combined, 0, sendBytes.length);
|
System.arraycopy(newlineBytes, 0, combined, sendBytes.length, newlineBytes.length);
|
sendBytes = combined;
|
}
|
}
|
|
if (!serialService.send(sendBytes)) {
|
JOptionPane.showMessageDialog(this,
|
messages.getString("SEND_ERROR"),
|
messages.getString("ERROR"), JOptionPane.ERROR_MESSAGE);
|
}
|
}
|
|
/* ================= µ¼³ö½âÎöÊý¾Ý ================= */
|
private void exportParsedData() {
|
JFileChooser fileChooser = new JFileChooser();
|
fileChooser.setDialogTitle(messages.getString("EXPORT_PARSED_DATA"));
|
if (fileChooser.showSaveDialog(this) == JFileChooser.APPROVE_OPTION) {
|
try (PrintWriter writer = new PrintWriter(fileChooser.getSelectedFile())) {
|
writer.write(txtParsedData.getText());
|
JOptionPane.showMessageDialog(this,
|
messages.getString("EXPORT_SUCCESS"),
|
messages.getString("INFO"), JOptionPane.INFORMATION_MESSAGE);
|
} catch (Exception ex) {
|
JOptionPane.showMessageDialog(this,
|
messages.getString("EXPORT_FAILED") + ": " + ex.getMessage(),
|
messages.getString("ERROR"), JOptionPane.ERROR_MESSAGE);
|
}
|
}
|
}
|
|
/* ================= ¸¨Öú·½·¨ ================= */
|
private byte[] hexStringToBytes(String hexString) {
|
if (hexString == null || hexString.trim().isEmpty()) {
|
return null;
|
}
|
|
hexString = hexString.replaceAll("\\s+", "");
|
|
if (hexString.length() % 2 != 0) {
|
return null;
|
}
|
|
try {
|
byte[] result = new byte[hexString.length() / 2];
|
for (int i = 0; i < result.length; i++) {
|
int index = i * 2;
|
String byteStr = hexString.substring(index, index + 2);
|
result[i] = (byte) Integer.parseInt(byteStr, 16);
|
}
|
return result;
|
} catch (NumberFormatException e) {
|
return null;
|
}
|
}
|
|
private JButton createStyledButton(String text, Color bg) {
|
JButton b = new JButton(text);
|
b.setFont(new Font("ËÎÌå", Font.BOLD, 12));
|
b.setBackground(bg);
|
b.setForeground(Color.WHITE);
|
b.setFocusPainted(false);
|
b.setBorder(BorderFactory.createCompoundBorder(
|
BorderFactory.createLineBorder(bg.darker(), 1),
|
BorderFactory.createEmptyBorder(5, 15, 5, 15)));
|
return b;
|
}
|
|
private JCheckBox createStyledCheckbox(String text) {
|
JCheckBox c = new JCheckBox(text);
|
c.setFont(new Font("ËÎÌå", Font.PLAIN, 12));
|
c.setBackground(new Color(240, 245, 249));
|
c.setForeground(new Color(70, 70, 70));
|
return c;
|
}
|
|
/* ================= ´°¿Ú¹Ø±Õ´¦Àí ================= */
|
@Override
|
public void addNotify() {
|
super.addNotify();
|
java.awt.Window w = SwingUtilities.getWindowAncestor(this);
|
if (w != null) {
|
w.addWindowListener(new WindowAdapter() {
|
@Override
|
public void windowClosing(WindowEvent e) {
|
serialService.close();
|
}
|
});
|
}
|
}
|
|
// ÐÂÔö¸¨Öú·½·¨£º×Ö½ÚÊý×éתʮÁù½øÖÆ×Ö·û´®
|
private String bytesToHex(byte[] bytes) {
|
StringBuilder sb = new StringBuilder();
|
for (byte b : bytes) {
|
sb.append(String.format("%02X", b));
|
}
|
return sb.toString();
|
}
|
|
// ÐÞ¸ÄclearDisplay·½·¨
|
private void clearDisplay() {
|
txtRawData.setText("");
|
txtParsedData.setText("");
|
packetCounter = 0;
|
lblPacketCount.setText(String.format(messages.getString("packet.count.format"), 0));
|
lblParseStatus.setText(messages.getString("parser.ready"));
|
}
|
}
|