package FLXCheckInController import ( "fmt" "io" "reflect" "time" log "github.com/sirupsen/logrus" ) type FlxCheckInCmdReader struct { BufferMaxLength int SerialPort *io.ReadWriteCloser tmpRecDataBuffer []byte IsRunning bool //记录最后一次接收数据时间 dtLastRecivedDateTime time.Time InvokeOnBusinessDataReviceData func([]byte) OnConnectStatusHandler func(time.Time) } func (para *FlxCheckInCmdReader) InitPara(serialPortt *io.ReadWriteCloser) { defer func() { if r := recover(); r != nil { log.Error("InitPara:", r) } }() fmt.Println("初始化串口驱动参数 ") para.SerialPort = serialPortt // Make sure to close it later. // defer port.Close() // // Write 4 bytes to the port. // b := []byte{0x00, 0x01, 0x02, 0x03} // n, err := port.Write(b) // port.Read() // if err != nil { // fmt.Println("port.Write: %v", err) // } // fmt.Println("Wrote", n, "bytes.") } // /// 接收到业务数据后触发事件 // public event BusinessDataReciveEventHandler OnBusinessDataReciveEventHandler; // /// 读串口数据时发生的日志信息 // public event DataReciveLogHandler OnDataReciveLogHandler; // /// // /// 判断串口设备的连接状态事件 // /// // public event DataReciveHandler OnConnectStatusHandler; func (para *FlxCheckInCmdReader) InvokeOnDataReciveLogHandler(logMessage string) { defer func() { if r := recover(); r != nil { log.Error("InvokeOnDataReciveLogHandler:", r) } }() // if OnDataReciveLogHandler != nil { // OnDataReciveLogHandler(logMessage) // } fmt.Println("串口消息:" + logMessage) } func (para *FlxCheckInCmdReader) InvokeOnConnectStatusHandler(dtLastRecived time.Time) { defer func() { if r := recover(); r != nil { log.Error("InvokeOnConnectStatusHandler:", r) } }() para.OnConnectStatusHandler(dtLastRecived) } func (para *FlxCheckInCmdReader) ProcessRecvBuff(RecvBuffer []byte) { defer func() { if r := recover(); r != nil { log.Error("ProcessRecvBuff:", r) } }() var PackLen int = 0 var PackBuff []byte var startIndex int = 0 var curIndex int = 0 for curIndex < len(RecvBuffer) { //应该判断7E 06 或02 if RecvBuffer[curIndex] == CMD_HEAD { if startIndex != curIndex && (curIndex-startIndex) >= 5 { PackLen = curIndex + 1 - startIndex PackBuff = make([]byte, PackLen) PackBuff = RecvBuffer[startIndex : startIndex+PackLen] para.InvokeOnBusinessDataReviceData(PackBuff) //外发事件。 startIndex = curIndex + 1 } } curIndex++ } if startIndex != curIndex { para.tmpRecDataBuffer = append(para.tmpRecDataBuffer, RecvBuffer[curIndex:]...) } } func (para *FlxCheckInCmdReader) TimerCallbackHandler() { defer func() { if r := recover(); r != nil { log.Error("TimerCallbackHandler:", r) } }() var waitReadPackLen int = 0 //待读的字节长度 // var length int = 0 //放入缓冲区的长度。 for para.IsRunning { reciveData := make([]byte, 51200) clen, err := (*(para.SerialPort)).Read(reciveData) if err != nil { fmt.Println(err) if err == io.EOF { // time.Sleep(2000) // para.IsRunning = false // go para.CloseDevice() // go para.TimerCallbackHandler() return } continue } if clen >= DataPacketMinLength { waitReadPackLen = clen if waitReadPackLen == 0 { fmt.Println(err) } data := make([]byte, waitReadPackLen) data = reciveData[:waitReadPackLen] //当前包接收长度 加上 上次接收半包的长度 recvBuffer := make([]byte, len(para.tmpRecDataBuffer)+waitReadPackLen) //从端口读取数据的缓冲区 //上次如果为半包 if len(para.tmpRecDataBuffer) > 0 { recvBuffer = insertToSlice(0, para.tmpRecDataBuffer, recvBuffer) // id = PersonIDs[j] } recvBuffer = insertToSlice(len(para.tmpRecDataBuffer), data, recvBuffer) para.tmpRecDataBuffer = para.tmpRecDataBuffer[0:0] // recvBuffer = append(para.tmpRecDataBuffer, data...) //读取当前包的数据 //Array.Copy(data, 0, recvBuffer, index, waitReadPackLen) //读来的数据先零时放入这个缓冲区 para.ProcessRecvBuff(recvBuffer) para.dtLastRecivedDateTime = time.Now() } else { para.tmpRecDataBuffer = append(para.tmpRecDataBuffer, reciveData[:clen]...) } } } func (para *FlxCheckInCmdReader) Start() bool { defer func() { if r := recover(); r != nil { log.Error("Start:", r) } }() // id = PersonIDs[j] //此处 para.IsRunning 如不设置,则程序无法接收签到门信息 para.IsRunning = true fmt.Println("中控机接收开启") go para.TimerCallbackHandler() return true } func (para *FlxCheckInCmdReader) Stop() bool { defer func() { if r := recover(); r != nil { log.Error("Stop:", r) } }() para.IsRunning = false return true } func (para *FlxCheckInCmdReader) ReadResponseData() []byte { defer func() { if r := recover(); r != nil { log.Error("ReadResponseData:", r) } }() if para.SerialPort == nil { return nil } reciveData := make([]byte, 51200) clen, err := (*(para.SerialPort)).Read(reciveData) if err != nil { fmt.Println("串口报错消息:" + err.Error()) return nil } if clen <= 0 { return nil } // data := make([]byte, clen) data := reciveData[:clen] return data } // 截取字符串 start 起点下标 length 需要截取的长度 func Substr(str string, start int, length int) string { defer func() { if r := recover(); r != nil { log.Error("Substr:", r) } }() rs := []rune(str) rl := len(rs) end := 0 if start < 0 { start = rl - 1 + start } end = start + length if start > end { start, end = end, start } if start < 0 { start = 0 } if start > rl { start = rl } if end < 0 { end = 0 } if end > rl { end = rl } return string(rs[start:end]) } // insertSlice 插入 func insertSlice(index int, newstr []byte, src []byte) (ns []byte) { defer func() { if r := recover(); r != nil { log.Error("insertSlice:", r) } }() ns = append(ns, src[:index]...) // 切片后加..., 相当于拆包成单个元素 ns = append(ns, newstr...) ns = append(ns, src[index+len(newstr):]...) return } func insertToSlice(index int, newstr []byte, src []byte) (ns []byte) { defer func() { if r := recover(); r != nil { log.Error("insertToSlice:", r) } }() ns = append(ns, src[:index]...) // 切片后加..., 相当于拆包成单个元素 ns = append(ns, newstr...) ns = append(ns, src[index:]...) return } func Contain(obj interface{}, target interface{}) bool { defer func() { if r := recover(); r != nil { log.Error("Contain:", r) } }() targetValue := reflect.ValueOf(target) switch reflect.TypeOf(target).Kind() { case reflect.Slice, reflect.Array: for i := 0; i < targetValue.Len(); i++ { if targetValue.Index(i).Interface() == obj { return true } } case reflect.Map: if targetValue.MapIndex(reflect.ValueOf(obj)).IsValid() { return true } } return false } // RemoveElementToint32 移除数组内的指定元素 func RemoveElementStrings(list []string, value string) []string { defer func() { if r := recover(); r != nil { log.Error("RemoveElementStrings:", r) } }() var result = make([]string, 0) index := 0 endIndex := len(list) - 1 for i, s := range list { if s == value { result = append(result, list[index:i]...) index = i + 1 } else if i == endIndex { result = append(result, list[index:endIndex+1]...) } } return result }