张世豪
4 小时以前 100f4dcea20a32663a07e91525de111f7515eb79
src/chuankou/Sendmsg.java
@@ -2,6 +2,15 @@
import java.text.SimpleDateFormat;
import java.util.Date;
import javax.swing.SwingWorker;
import chushihua.lunxun;
import dialog.Charulog;
import dialog.Dingshidialog;
import dialog.Errlog;
import publicway.OpenDoor;
import xitongshezhi.SystemDebugDialog;
/**
 * 串口消息发送工具类
 * 提供高性能的串口消息发送功能,适合高频调用
@@ -11,11 +20,83 @@
    private static volatile SerialPortService serialService = null;
    private static volatile boolean isPortOpen = false;
    
    // 调试模式开关
    private static final boolean DEBUG_MODE = false;
    // 改为非final,支持动态控制
    private static boolean DEBUG_MODE = false;
    
    // 日期格式化
    private static final SimpleDateFormat timeFormat = new SimpleDateFormat("HH:mm:ss.SSS");
    /**发卡服务器控制打开某个柜门调用指令
     * @param int slotId柜门编号1-60
     * @param int type 1是服务器发卡,2是管理员发卡*/
    public static boolean opendoorzhiling(int slotId,int type) {
       lunxun.setSendChaxunzhiling(false);//暂停查询指令
       // 调用OpenDoor生成开门指令
       String command = OpenDoor.openOneDoor(slotId, type);
       boolean sendResult = Sendmsg.sendMessage(command);
       String mes=command+";type"+type+"控制打开"+slotId+"柜门";
       Charulog.logOperation(mes);
       if (lunxun.DEBUG_ENABLED) {
            SystemDebugDialog.appendAsciiData(mes);
        }
       lunxun.setSendChaxunzhiling(true);//开始查询指令
      return sendResult;
    }
    /**
     * 打开全部卡槽的公用静态方法
     * @param type 操作类型:1-服务器发卡,2-管理员发卡
     */
    public static void openAllSlots(int type) {
       lunxun.setSendChaxunzhiling(false);//暂停查询指令
        // 使用SwingWorker在后台执行,避免阻塞UI
        SwingWorker<Void, Void> worker = new SwingWorker<Void, Void>() {
            @Override
            protected Void doInBackground() throws Exception {
                // 遍历所有卡槽(1-60)
                for (int slotId = 1; slotId <= 60; slotId++) {
                    try {
                        // 生成开门指令
                        String command = OpenDoor.openOneDoor(slotId, type);
                        // 发送串口指令
                        boolean sent = Sendmsg.sendMessage(command);
                        if (!sent) {
                            Errlog.logOperation("发送指令到卡槽 " + slotId + " 失败");
                        }
                        // 间隔100ms
                        Thread.sleep(100);
                    } catch (Exception e) {
                        Errlog.logOperation("处理卡槽 " + slotId + " 时发生错误: " + e.getMessage());
                        e.printStackTrace();
                    }
                }
                return null;
            }
            @Override
            protected void done() {
                // 可选:完成后可以添加回调处理
                System.out.println("全部卡槽开门指令发送完成");
                String types="管理员";
                if(type==1) {
                   types="服务器指令";
                }
                String message=types+"已将全部卡槽已经打开请取卡";
                Dingshidialog.showTimedDialog(null,5,message);
                Charulog.logOperation(message);
            }
        };
        worker.execute();
        lunxun.setSendChaxunzhiling(true);//开始查询指令
    }
    
    /**
     * 设置串口服务实例
@@ -35,48 +116,65 @@
    }
    
    /**
     * 发送消息到串口
     * @param message 要发送的HEX格式消息
     * @return 发送成功返回true,失败返回false
     * 发送消息到串口(带重试机制)
     */
    public static boolean sendMessage(String message) {
        if (!isPortOpen || serialService == null) {
            if (DEBUG_MODE) {
                System.err.println("[" + getCurrentTime() + "] 串口未打开,无法发送数据");
            }
            Errlog.logOperation("[" + getCurrentTime() + "] 串口未打开,无法发送数据");
            return false;
        }
        
        if (message == null || message.trim().isEmpty()) {
            if (DEBUG_MODE) {
                System.err.println("[" + getCurrentTime() + "] 发送数据为空");
            }
            Errlog.logOperation("[" + getCurrentTime() + "] 发送数据为空");
            return false;
        }
        
        String text = message.trim();
        int retryCount = 0;
        final int MAX_RETRY = 2;
        
        try {
            // HEX格式发送
            byte[] data = hexStringToByteArray(text);
            if (data != null && serialService.send(data)) {
                // 高频调用时避免频繁的日志输出,只在调试时记录
                if (DEBUG_MODE) {
                    System.out.println("[" + getCurrentTime() + "] 发送: " + text.toUpperCase());
        while (retryCount <= MAX_RETRY) {
            try {
                byte[] data = hexStringToByteArray(text);
                if (data == null) {
                    Errlog.logOperation("[" + getCurrentTime() + "] HEX转换失败,数据: " + text);
                    return false;
                }
                return true;
            } else {
                if (DEBUG_MODE) {
                    System.err.println("[" + getCurrentTime() + "] 数据发送失败");
                boolean sendResult = serialService.send(data);
                if (sendResult) {
                    if (DEBUG_MODE) {
                        System.out.println("[" + getCurrentTime() + "] 发送成功: " + text.toUpperCase());
                    }
                    return true;
                } else {
                    retryCount++;
                    if (retryCount <= MAX_RETRY) {
                        Errlog.logOperation("[" + getCurrentTime() + "] 发送失败,正在重试 (" + retryCount + "/" + MAX_RETRY + ")");
                        try {
                            Thread.sleep(50); // 重试前等待
                        } catch (InterruptedException e) {
                            Thread.currentThread().interrupt();
                            break;
                        }
                    } else {
                        Errlog.logOperation("[" + getCurrentTime() + "] 串口发送失败,指令: " + text.toUpperCase());
                        Errlog.logOperation("[" + getCurrentTime() + "] 串口状态 - 打开: " + isPortOpen + ", 服务: " + (serialService != null));
                        if (serialService != null) {
                            Errlog.logOperation("[" + getCurrentTime() + "] 串口服务状态 - 是否打开: " + serialService.isOpen());
                        }
                        return false;
                    }
                }
            } catch (Exception e) {
                Errlog.logOperation("[" + getCurrentTime() + "] 发送异常,指令: " + text.toUpperCase());
                e.printStackTrace();
                return false;
            }
        } catch (Exception e) {
            if (DEBUG_MODE) {
                System.err.println("[" + getCurrentTime() + "] 数据格式错误: " + e.getMessage());
            }
            return false;
        }
        return false;
    }
    
    /**
@@ -84,7 +182,11 @@
     * @return 串口打开状态
     */
    public static boolean isPortOpen() {
        return isPortOpen && serialService != null;
        boolean open = isPortOpen && serialService != null;
        if (!open && DEBUG_MODE) {
            Errlog.logOperation("[" + getCurrentTime() + "] 串口状态检查: 未打开");
        }
        return open;
    }
    
    /**
@@ -100,7 +202,7 @@
        s = s.replaceAll("\\s+", ""); // 移除空格
        int len = s.length();
        if (len % 2 != 0) {
            throw new IllegalArgumentException("HEX字符串长度必须为偶数");
            throw new IllegalArgumentException("HEX字符串长度必须为偶数,当前长度: " + len + ", 数据: " + s);
        }
        
        byte[] data = new byte[len / 2];
@@ -109,7 +211,7 @@
            int low = Character.digit(s.charAt(i + 1), 16);
            
            if (high == -1 || low == -1) {
                throw new IllegalArgumentException("无效的HEX字符: " + s.charAt(i) + s.charAt(i + 1));
                throw new IllegalArgumentException("无效的HEX字符: '" + s.charAt(i) + s.charAt(i + 1) + "' 在位置 " + i + "-" + (i+1) + ", 完整数据: " + s);
            }
            
            data[i / 2] = (byte) ((high << 4) + low);
@@ -144,12 +246,25 @@
    
    /**
     * 启用调试模式
     * 注意:这会修改静态final变量,实际项目中不建议这样做
     * 这里只是演示,实际应该通过配置文件控制
     */
    public static void enableDebugMode() {
        // 在实际项目中,应该使用可配置的方式而不是修改final变量
        // 这里只是示意,实际使用时需要重新设计
        System.out.println("调试模式已启用");
        DEBUG_MODE = true;
        System.out.println("[" + getCurrentTime() + "] Sendmsg调试模式已启用");
    }
    /**
     * 禁用调试模式
     */
    public static void disableDebugMode() {
        DEBUG_MODE = false;
        System.out.println("[" + getCurrentTime() + "] Sendmsg调试模式已禁用");
    }
    /**
     * 设置调试模式
     */
    public static void setDebugMode(boolean debug) {
        DEBUG_MODE = debug;
        System.out.println("[" + getCurrentTime() + "] Sendmsg调试模式: " + (debug ? "启用" : "禁用"));
    }
}