⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 controlclass.~pas

📁 求是科技出版的《Delphi串口通信工程开发实例导航》所有的源代码。是一本很好的书。拿出来与大家共享。
💻 ~PAS
📖 第 1 页 / 共 4 页
字号:
end;

function TCardReader.CardNo_SoftToHard(ACardNoSoft: string): TCardNoHard;
var
    mCard: integer;
    mResult : TCardNoHard;
    mStr : string;
begin
    if Length(ACardNoSoft) <> 8 then
    begin
        raise Exception.Create('卡号的位数不正确!');
    end;

    try
        //=============卡号的编码方式==================
        //mCard := StrToInt(ACardNoSoft);
        //mStr := Copy(ACardNoSoft,1,2);
        mResult.N1 := Copy(ACardNoSoft,1,2);
        mResult.N2 := Copy(ACardNoSoft,3,2);
        mResult.N3 := Copy(ACardNoSoft,5,2);
        mResult.N4 := Copy(ACardNoSoft,7,2);
    except
        mResult.N1 := '00';
        mResult.N2 := '00';
        mResult.N3 := '00';
        mResult.N4 := '00';
    end;
    Result := mResult;
end;

constructor TCardReader.Create(Address: string; APortNo: integer);
begin
    //SetAddress(Address);
    FPortNo := APortNo;

    FMSComm := TMSComm.Create(nil);
    OpenPort();

    //========================
    //TCommand.Create();
    TBottomMsg.Create();
end;

constructor TCardReader.Create(APortNo: integer);
begin
    FPortNo := APortNo;

    FMSComm := TMSComm.Create(nil);
    OpenPort();

    FCommand := TBottomMsg.Create();
end;

destructor TCardReader.Destroy;
begin
    if FMSComm.PortOpen then FMSComm.PortOpen:= False;
    FMSComm.Free;
    //========================
    FCommand.Free;
    FBottomMsg.Free;

    inherited;

end;

procedure TCardReader.OpenPort;
begin
    FMSComm.InputMode := 1; //comInputModeBinary;
    FMSComm.CommPort := FPortNo;
    FMSComm.Settings := '9600,n,8,1';
    //open the port
    if not FMSComm.PortOpen then FMSComm.PortOpen:= True;

end;

function TCardReader.ReadCard(var ACardUse: TCardUse): integer;
var
    mCounter : integer;
    mCommand : TCommand;
    mBottomMsg : TBottomMsg;
    mBuf: array of byte;
    Year,Month,Day,Hour,Min,Sec: word;
begin
    mCommand := TCommand.Create('B3B3B3 02 FD 14 XX');
    mBottomMsg := TBottomMsg.Create();
    //通信次数计数器
    mCounter := 0 ;
    while mCounter < TRY_TIMES do
    begin
        //输出上位机报文
        FMSComm.Output := mCommand.FBuffer;
        //等待读卡机响应
        Sleep(WAIT_TIME);
        //检查上传报文长度
        if FMSComm.InBufferCount >= 10 then
        begin
            //将OLE变量付值给树组
            SetLength(mBuf,FMSComm.InBufferCount);
            //读取上传报文
            mBuf := FMSComm.Input;
            //设置下位机应答信息类分析
            mBottomMsg.SetBuffer(mBuf);
            //分析应答数据
            if mBottomMsg.GetPosStr(4) = '07' then break;
        end;
        Inc(mCounter);
    end;
    //放弃通信
    if mCounter >= TRY_TIMES then
    begin
        Result := -1 ;
    end
    //场内没有卡
    else if mBottomMsg.GetPosStr(7) = '12' then
    begin
       Result := -2;
    end
    else begin
        ACardUse.Card := mBottomMsg.GetPosStr(8)
                        +mBottomMsg.GetPosStr(9)
                        +mBottomMsg.GetPosStr(10)
                        +mBottomMsg.GetPosStr(11);
    end;

    mCommand.Free;
    mBottomMsg.Free;
end;

function TCardReader.ReadComplexCard(var ACardUse: TComplexCardUse): integer;
var
    mCounter : integer;
    mCommand : TCommand;
    mBottomMsg : TBottomMsg;
    mBuf: array of byte;
    Year1,Year2,Month,Day,Hour,Min,Sec: word;
begin
    mCommand := TCommand.Create('B3B3B3 03 FC 0A 04 XX');
    mBottomMsg := TBottomMsg.Create();

    //mCommand.ParamByPos(1,FAddr1);//地址
    //mCommand.ParamByPos(2,FAddr2);//地址

    mCounter := 0 ;
    while mCounter < TRY_TIMES do
    begin
        FMSComm.Output := mCommand.FBuffer;
        Sleep(WAIT_TIME);
        if FMSComm.InBufferCount >= 8 then
        begin
            //将OLE变量付值给树组
            SetLength(mBuf,FMSComm.InBufferCount);
            mBuf := FMSComm.Input;
            mBottomMsg.SetBuffer(mBuf);
            //分析应答数据
            if mBottomMsg.GetPosStr(7) = '00' then break;
        end;
        Inc(mCounter);
    end;
    //放弃通信
    if mCounter >= TRY_TIMES then
    begin
        Result := -1 ;
        Exit;
    end
    else begin
        ACardUse.MainClass := mBottomMsg.GetPosStr(8+1);
        ACardUse.SlaveClass := mBottomMsg.GetPosStr(8+2);

    end;
    mCommand.Free;
    mBottomMsg.Free;

    //==================第五区
    mCommand := TCommand.Create('B3B3B3 03 FC 0A 05 XX');
    mBottomMsg := TBottomMsg.Create();
    mCounter := 0 ;
    while mCounter < TRY_TIMES do
    begin
        FMSComm.Output := mCommand.FBuffer;
        Sleep(WAIT_TIME);
        if FMSComm.InBufferCount >= 8 then
        begin
            //将OLE变量付值给树组
            SetLength(mBuf,FMSComm.InBufferCount);
            mBuf := FMSComm.Input;
            mBottomMsg.SetBuffer(mBuf);
            //分析应答数据
            if mBottomMsg.GetPosStr(7) = '00' then break;
        end;
        Inc(mCounter);
    end;
    //放弃通信
    if mCounter >= TRY_TIMES then
    begin
        Result := -1 ;
        Exit;
    end
    else begin
        ACardUse.EnterAddr1  := mBottomMsg.GetPosStr(8+1);
        ACardUse.EnterAddr2  := mBottomMsg.GetPosStr(8+2);
        ACardUse.LeaveAddr1  := mBottomMsg.GetPosStr(8+3);
        ACardUse.LeaveAddr2  := mBottomMsg.GetPosStr(8+4);

    end;

    mCommand.Free;
    mBottomMsg.Free;

    //===============第六区

    mCommand := TCommand.Create('B3B3B3 03 FC 0A 06 XX');
    mBottomMsg := TBottomMsg.Create();
    mCounter := 0 ;
    while mCounter < TRY_TIMES do
    begin
        FMSComm.Output := mCommand.FBuffer;
        Sleep(WAIT_TIME);
        if FMSComm.InBufferCount >= 8 then
        begin
            //将OLE变量付值给树组
            SetLength(mBuf,FMSComm.InBufferCount);
            mBuf := FMSComm.Input;
            mBottomMsg.SetBuffer(mBuf);
            //分析应答数据
            if mBottomMsg.GetPosStr(7) = '00' then break;
        end;
        Inc(mCounter);
    end;
    //放弃通信
    if mCounter >= TRY_TIMES then
    begin
        Result := -1 ;
        Exit;
    end
    else begin
        ACardUse.Card  := mBottomMsg.GetPosStr(8+1)
                         +mBottomMsg.GetPosStr(8+2)
                         +mBottomMsg.GetPosStr(8+3)
                         +mBottomMsg.GetPosStr(8+4);

    end;

    mCommand.Free;
    mBottomMsg.Free;


    //===============第七区

    mCommand := TCommand.Create('B3B3B3 03 FC 0A 07 XX');
    mBottomMsg := TBottomMsg.Create();
    mCounter := 0 ;
    while mCounter < TRY_TIMES do
    begin
        FMSComm.Output := mCommand.FBuffer;
        Sleep(WAIT_TIME);
        if FMSComm.InBufferCount >= 17 then
        begin
            //将OLE变量付值给树组
            SetLength(mBuf,FMSComm.InBufferCount);
            mBuf := FMSComm.Input;
            mBottomMsg.SetBuffer(mBuf);
            //分析应答数据
            if mBottomMsg.GetPosStr(7) = '00' then break;
        end;
        Inc(mCounter);
    end;
    //放弃通信
    if mCounter >= TRY_TIMES then
    begin
        Result := -1 ;
        Exit;
    end
    else begin
        try
               //解析时间
         Year1 := StrToInt(mBottomMsg.GetPosStr(9));
        Year2 := StrToInt(mBottomMsg.GetPosStr(10));
        Month := StrToInt(mBottomMsg.GetPosStr(11));
        Day := StrToInt(mBottomMsg.GetPosStr(12));
        Hour := StrToInt(mBottomMsg.GetPosStr(13));
        Min := StrToInt(mBottomMsg.GetPosStr(14));
        Sec := StrToInt(mBottomMsg.GetPosStr(15));
        ACardUse.EnterTime := EncodeDate(Year1*100+Year2,Month,Day)
                           + EncodeTime(Hour,Min,Sec,0);//微秒为零
        except
            ACardUse.EnterTime := 0;
            Result := -1;
        end;

    end;

    mCommand.Free;
    mBottomMsg.Free;


    //===============第八区
    
//如果没有交费,不读第八区
if (ACardUse.LeaveAddr1 <> 'FF') or (ACardUse.LeaveAddr2 <> 'FF') then
begin
    mCommand := TCommand.Create('B3B3B3 03 FC 0A 08 XX');
    mBottomMsg := TBottomMsg.Create();
    mCounter := 0 ;
    while mCounter < TRY_TIMES do
    begin
        FMSComm.Output := mCommand.FBuffer;
        Sleep(WAIT_TIME);
        if FMSComm.InBufferCount >= 17 then
        begin
            //将OLE变量付值给树组
            SetLength(mBuf,FMSComm.InBufferCount);
            mBuf := FMSComm.Input;
            mBottomMsg.SetBuffer(mBuf);
            //分析应答数据
            if mBottomMsg.GetPosStr(7) = '00' then break;
        end;
        Inc(mCounter);
    end;
    //放弃通信
    if mCounter >= TRY_TIMES then
    begin
        Result := -1 ;
        Exit;
    end
    else begin
        try
               //解析时间
        Year1 := StrToInt(mBottomMsg.GetPosStr(9));
        Year2 := StrToInt(mBottomMsg.GetPosStr(10));
        Month := StrToInt(mBottomMsg.GetPosStr(11));
        Day := StrToInt(mBottomMsg.GetPosStr(12));
        Hour := StrToInt(mBottomMsg.GetPosStr(13));
        Min := StrToInt(mBottomMsg.GetPosStr(14));
        Sec := StrToInt(mBottomMsg.GetPosStr(15));
        ACardUse.LeaveTime := EncodeDate(Year1*100+Year2,Month,Day)
                           + EncodeTime(Hour,Min,Sec,0);//微秒为零
        except
            ACardUse.LeaveTime := 0;
            Result := -1;
        end;

    end;

    mCommand.Free;
    mBottomMsg.Free;
end; //不读第八区

    Result := 1;

end;



procedure TCardReader.SetAddress(Address: string);
begin
    FAddr1 := Copy(Address,1,2);
    FAddr2 := Copy(Address,3,2);
end;

function TCardReader.WriteArea(Area:integer;AContent: string): integer;
var
    mCounter : integer;
    mCommand : TCommand;
    mBottomMsg : TBottomMsg;
    mBuf: array of byte;
    mStr: string;
begin
    //检查写入内容长度
    Assert(Length(AContent)=16,'卡写入区非法。');
    //构造上位机报文
    mStr := 'B3B3B3 0b F4 0B ' + IntToHex(Area,2) + AContent + 'XX';
    mCommand := TCommand.Create(mStr);
    //构造下位机应答信息类,准备接收下位机消息
    mBottomMsg := TBottomMsg.Create();
    //通信次数计数器
    mCounter := 0 ;
    while mCounter < TRY_TIMES do
    begin
         //输出上位机报文
        FMSComm.Output := mCommand.FBuffer;
        //等待下位机响应
        Sleep(WAIT_TIME);
        if FMSComm.InBufferCount >= 8 then
        begin
            //将OLE变量付值给树组
            SetLength(mBuf,FMSComm.InBufferCount);
            //检查上传报文长度
            mBuf := FMSComm.Input;
            //读取上传报文
            mBottomMsg.SetBuffer(mBuf);
            //分析应答数据
            if mBottomMsg.GetPosStr(7) = '00' then break;
        end;
        Inc(mCounter);
    end;
    //放弃通信
    if mCounter >= TRY_TIMES then
    begin
        Result := -1 ;
        Exit;
    end
    else begin
        Result := 1; //
    end;
    mCommand.Free;
    mBottomMsg.Free;
end;

function TCardReader.WriteAddr(EnterAddr1,EnterAddr2,
                   LeaveAddr1,LeaveAddr2: string): integer;
var
    mCommand : TCardCommand ;
    mStr: string;
begin
    Assert(Length(EnterAddr1)=2,'卡写入离开地址错误。');
    Assert(Length(EnterAddr2)=2,'卡写入离开地址错误。');
    Assert(Length(LeaveAddr1)=2,'卡写入离开地址错误。');
    Assert(Length(LeaveAddr2)=2,'卡写入离开地址错误。');
    mStr := EnterAddr1 + EnterAddr2 + LeaveAddr1 + LeaveAddr2;
    mStr := mStr + '00 00 00 XX';
    mCommand := TCardCommand.Create(mStr);
    mStr := mCommand.GetStrBuffer();
    Result := WriteArea(5,mStr);
    mCommand.Free;
end;

function TCardReader.WriteLeaveTime(ADateTime: TDateTime): integer;
var
    Year1,Year2,Month,Day,Hour,Min,Sec: word;
    mStr: string;
    mCommand : TCommand;
begin
    DecodeDate(ADateTime,Year1,Month,Day);
    DecodeTime(ADateTime,Hour,Min,Sec,Year2);
    Year2 := Year1 mod 100;
    Year1 := Year1 div 100;
    mStr := IntToStr2(Year1)
           +IntToStr2(Year2)
           +IntToStr2(Month)
           +IntToStr2(Day)
           +IntToStr2(Hour)
           +IntToStr2(Min)
           +IntToStr2(Sec)
           +'XX';
    mCommand := TCardCommand.Create(mStr);
    Result := WriteArea(8,mCommand.GetStrBuffer());
    mCommand.Free;
end;


{ TCardCommand }

function TCardCommand.CalCheck: integer;
var
    mByte : byte ;
    i : integer;
    mStr : string;
begin
    //校验位已经付值
    if not IsBufferPosToken(FLen) then
    begin
        Result := 0;
        Exit;
    end;

    try
        mByte := $00;
        //从第六位开始计算校验位
        for i := 6 to FLen-1 do
        begin
            mByte := mByte xor StrToInt('$' + Copy(FStrBuffer,i*2-1,2));
        end;
        mStr := IntToHex(mByte,2);
        FStrBuffer[FLen*2-1] := mStr[1];
        FStrBuffer[FLen*2] := mStr[2];
    except
        Result := -1;
        Exit;
    end;

    Result := 1;
end;

end.

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -