請教大大高手門,如何將unit1中的陣列傳到unit2中的func,算完再傳回結果 |
答題得分者是:hagar
|
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
小弟寫一支程式如下
unit1:
利用VB MSCOMM元件做RS232通信,協定是MODBUS RTU,
送出一陣列值為
0.Function 03
1.Starting Address Hi 00
2.Starting Address Lo 6B
3.No. of Registers Hi 00
4.No. of Registers Lo 02 將陣列位址[0~4]值傳至unit2中的crc 函式,算完會傳回一個word的數值
5.CRC Hi xx
6.CRC Lo xx
將整個陣列傳至MSCOMM後
而傳回植為
0.Function 03
1.Byte Count 06
2.Register value Hi (108) 02
3.Register value Lo (108) 2B
4.Register value Hi (109) 00
5.Register value Lo (109) 00
須將陣列位址[2~5]傳至UNIT2中的HexToFloat函數,然後傳回一個Single型態的值
unit2: interface type
pSingle = ^TSingle ;
TSingle = record
Case Integer Of
0: (AsSingle:Single);
1: (FirstHi,FirstLo,SecondHi,SecondLo:Byte);
End; function CRC16(CRCData: array of Byte; Datalen: Integer):Word; implementation function HexToFloat(aryData: array of Byte; Datalen: Integer):Single;
Var
p : PSingle;
S : Single ;
begin
S := 23 ;
P := @S ; // 讓P 指向S 的位址(使用同一塊記憶體)
// 或是 P.AsSingle := 23 ; // 可以不用S 變數,只用P來操作亦可。 // 逐個Byte 轉成16進位字串
P.FirstHi := aryData[2];
P.FirstLo := aryData[3];
P.SecondHi := aryData[4];
P.SecondLo := aryData[5]; end; function CRC16(CRCData: array of Byte; Datalen: Integer):Word;
var
CRC16Lo: Byte;
CRC16Hi: Byte;
SaveLo:Byte;
SaveHi:Byte;
GLo:Byte;
GHi:Byte;
i:Integer;
Flag:Integer;
begin
CRC16Lo:=$ff;
CRC16Hi:=$ff;
GLo:=$01;
GHi:=$a0;
for i:=0 to Datalen -1 do
begin
CRC16Lo:=CRC16Lo xor CRCData[i];
for Flag :=0 to 7 do
begin
SaveLo:=CRC16Lo;
SaveHi:=CRC16Hi;
CRC16Hi:=CRC16Hi shr 1;
CRC16Lo:=CRC16Lo shr 1;
if (SaveHi and $01) = $01 then
CRC16Lo:=CRC16Lo or $80;
if (SaveLo and $01) = $01 then
begin
CRC16Hi:=CRC16Hi xor GHi;
CRC16Lo:=CRC16Lo xor GLo;
end;
end;
end;
CRC16 := CRC16Lo * 256 CRC16Hi;
end;
end. 程式傳遞參數總是有問題,不知錯在那裡,煩請各為高手大大指導小弟,感恩萬分
|
Chance36
版主 ![]() ![]() ![]() ![]() ![]() ![]() 發表:31 回覆:1033 積分:792 註冊:2002-12-31 發送簡訊給我 |
wychen57 你好
程式傳遞參數總是有問題? 是那個函數有問題,你也沒說明,到底是什麼問題呢?底下僅針對貼上的程式內容,發現的問題說明如下: 1.function HexToFloat()要在宣告區先行宣告,才可讓別的元呼叫到 2.function HexToFloat()的 Datalen: Integer 這個好像沒必要 3.function HexToFloat()程式內容修改如下 function CRC16(CRCData: array of Byte):Word; function HexToFloat(aryData: array of Byte):Single; implementation function HexToFloat(aryData: array of Byte):Single; Var p : PSingle; begin // S := 23 ; P := @Result ; // 讓P 指向S 的位址(使用同一塊記憶體) // 或是 P.AsSingle := 23 ; // 可以不用S 變數,只用P來操作亦可。 // 逐個Byte 轉成16進位字串 P.FirstHi := aryData[2]; P.FirstLo := aryData[3]; P.SecondHi := aryData[4]; P.SecondLo := aryData[5]; end; PS:至於CRC16()除了運算部份之外程式架構,基本上沒有錯,只是DataLen參數 應該拿掉改由Length(CRCData)取得或用Low(CRCData) To High(CrcData)的方式 處理比較靈活。 function CRC16(CRCData: array of Byte):Word; var CRC16Lo: Byte; CRC16Hi: Byte; SaveLo:Byte; SaveHi:Byte; GLo:Byte; GHi:Byte; i:Integer; Flag:Integer; begin CRC16Lo:=$ff; CRC16Hi:=$ff; GLo:=$01; GHi:=$a0; for i:=Low(CRCData) to High(CRCData) do begin CRC16Lo:=CRC16Lo xor CRCData[i]; for Flag :=0 to 7 do begin SaveLo:=CRC16Lo; SaveHi:=CRC16Hi; CRC16Hi:=CRC16Hi shr 1; CRC16Lo:=CRC16Lo shr 1; if (SaveHi and $01) = $01 then CRC16Lo:=CRC16Lo or $80; if (SaveLo and $01) = $01 then begin CRC16Hi:=CRC16Hi xor GHi; CRC16Lo:=CRC16Lo xor GLo; end; end; end; CRC16 := CRC16Lo * 256 CRC16Hi; end;_______________________________________ 深藍的魚,祝您好運..........連連 發表人 - chance36 於 2004/08/03 01:08:18 |
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
引言: wychen57 你好chance36大大您好,小弟程式寫得不好,你可能看不懂我的程式需求,crc16是要把陣列中特定長度的資料做crc運算並傳回呼叫者,而HEXTOFLOAT是把陣列中特定位置開始連續4BYTE轉成FLOAT資料(IEEE754格式),故兩者皆需指定需轉換之陣列長度或起始位置,而小弟就是不知怎麼寫才對,而且之前的問題就是陣列在這兩函數與主FORM之間傳遞失敗,每次傳回都傳錯誤資料(可能是傳值或傳址呼叫用錯了),煩請大大指點指點。程式傳遞參數總是有問題? 是那個函數有問題,你也沒說明,到底是什麼問題呢?底下僅針對貼上的程式內容,發現的問題說明如下: 1.function HexToFloat()要在宣告區先行宣告,才可讓別的元呼叫到 2.function HexToFloat()的 Datalen: Integer 這個好像沒必要 3.function HexToFloat()程式內容修改如下 function CRC16(CRCData: array of Byte):Word; function HexToFloat(aryData: array of Byte):Single; implementation function HexToFloat(aryData: array of Byte):Single; Var p : PSingle; begin // S := 23 ; P := @Result ; // 讓P 指向S 的位址(使用同一塊記憶體) // 或是 P.AsSingle := 23 ; // 可以不用S 變數,只用P來操作亦可。 // 逐個Byte 轉成16進位字串 P.FirstHi := aryData[2]; P.FirstLo := aryData[3]; P.SecondHi := aryData[4]; P.SecondLo := aryData[5]; end; PS:至於CRC16()除了運算部份之外程式架構,基本上沒有錯,只是DataLen參數 應該拿掉改由Length(CRCData)取得或用Low(CRCData) To High(CrcData)的方式 處理比較靈活。 function CRC16(CRCData: array of Byte):Word; var CRC16Lo: Byte; CRC16Hi: Byte; SaveLo:Byte; SaveHi:Byte; GLo:Byte; GHi:Byte; i:Integer; Flag:Integer; begin CRC16Lo:=$ff; CRC16Hi:=$ff; GLo:=$01; GHi:=$a0; for i:=Low(CRCData) to High(CRCData) do begin CRC16Lo:=CRC16Lo xor CRCData[i]; for Flag :=0 to 7 do begin SaveLo:=CRC16Lo; SaveHi:=CRC16Hi; CRC16Hi:=CRC16Hi shr 1; CRC16Lo:=CRC16Lo shr 1; if (SaveHi and $01) = $01 then CRC16Lo:=CRC16Lo or $80; if (SaveLo and $01) = $01 then begin CRC16Hi:=CRC16Hi xor GHi; CRC16Lo:=CRC16Lo xor GLo; end; end; end; CRC16 := CRC16Lo * 256 CRC16Hi; end;_______________________________________ 深藍的魚,祝您好運..........連連 發表人 - chance36 於 2004/08/03 01:08:18 |
Chance36
版主 ![]() ![]() ![]() ![]() ![]() ![]() 發表:31 回覆:1033 積分:792 註冊:2002-12-31 發送簡訊給我 |
|
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
引言: wychen57 你好 可以描述一下,你想像中的狀況嗎? 怎麼呼叫? 傳什麼參數進去? 希望傳回什麼樣的資料回來呢? _______________________________________ 深藍的魚,祝您好運..........連連inbyte[0..1024],outbyte[0..7] as byte outbyte[0~7]=01,03,03,00,00,02,XX,yy crcdata=crc16(outbyte,5); xx= crcdata->Hibyte yy= crcdata->Lowbyte MSCOMM.Output=OutByte//將outbyte經mscomm送至設備 inbyte=MSCOMM.Input inbyte[3]開始為資料區,每4byte為一組,meter_val=HexToFloat(inbyte,i) i為要轉換之起始位置,現在問題就出在不論inbye->hextofloat or outbyte-->crc16,傳過去的都不是陣列元素的值,而是很奇怪的數值,所以始終無法算出正確數值,不知是我函數定義有問題還是傳遞的寫法有問題,大大能告訴我嗎,謝謝 |
Chance36
版主 ![]() ![]() ![]() ![]() ![]() ![]() 發表:31 回覆:1033 積分:792 註冊:2002-12-31 發送簡訊給我 |
wychen57 你好
參考下列程式,看符不符合需求? type pSingle = ^TSingle ; TSingle = record Case Integer Of 0: (AsSingle:Single); 1: (FirstHi,FirstLo,SecondHi,SecondLo:Byte); End; TForm1 = class(TForm) BitBtn1: TBitBtn; procedure BitBtn1Click(Sender: TObject); private { Private declarations } public { Public declarations } end; // 宣告位置在兒,別的單元才可以呼叫得到 // 或是將這兩函式放到獨立公用函式的單元檔中 function CRC16(CRCData: array of Byte; Datalen: Integer):Word; function HexToFloat(aryData: array of Byte; Datalen: Integer):Single; var Form1: TForm1; implementation {$R *.DFM} function HexToFloat(aryData: array of Byte; Datalen: Integer):Single; Var p : PSingle; begin P := @Result ; P.FirstHi := aryData[Datalen]; P.FirstLo := aryData[Datalen 1]; P.SecondHi := aryData[Datalen 2]; P.SecondLo := aryData[Datalen 3]; end; function CRC16(CRCData: array of Byte; Datalen: Integer):Word; var CRC16Lo: Byte; CRC16Hi: Byte; SaveLo:Byte; SaveHi:Byte; GLo:Byte; GHi:Byte; i:Integer; Flag:Integer; begin CRC16Lo:=$ff; CRC16Hi:=$ff; GLo:=$01; GHi:=$a0; for i:=0 to Datalen -1 do begin CRC16Lo:=CRC16Lo xor CRCData[i]; for Flag :=0 to 7 do begin SaveLo:=CRC16Lo; SaveHi:=CRC16Hi; CRC16Hi:=CRC16Hi shr 1; CRC16Lo:=CRC16Lo shr 1; if (SaveHi and $01) = $01 then CRC16Lo:=CRC16Lo or $80; if (SaveLo and $01) = $01 then begin CRC16Hi:=CRC16Hi xor GHi; CRC16Lo:=CRC16Lo xor GLo; end; end; end; CRC16 := CRC16Lo * 256 CRC16Hi; end; procedure TForm1.BitBtn1Click(Sender: TObject); Var inbyte : Array[0..1024] Of Byte; outbyte: Array[0..7] Of byte; xx,yy : Byte ; crcData : Word ; meter_val : Single ; begin outbyte[0] := 01; outbyte[1] := 03; outbyte[2] := 03; outbyte[3] := 00; outbyte[4] := 00; outbyte[5] := 02; CrcData := crc16( outbyte , 6 ); // 算出CRC值後再寫入到outbyte[6..7] outbyte[6] := Trunc(crcData/256) ; outbyte[7] := (crcData Mod 256); // ShowMessage(IntToStr(Integer(crcdata))); InByte[3] := $00; InByte[4] := $00; InByte[5] := $2b; InByte[6] := $43; InByte[7] := $00; InByte[8] := $00; InByte[9] := $2c; InByte[10] := $43; // 以上是假設資料,你應該改成這樣 MSCOMM.Output=OutByte;//將outbyte經mscomm送至設備 inbyte=MSCOMM.Input; meter_val := HexToFloat(InByte, 3); ShowMessage(FloatToStr(meter_val)); meter_val := HexToFloat(InByte, 7); ShowMessage(FloatToStr(meter_val)); end; end._______________________________________ 深藍的魚,祝您好運..........連連 |
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
chance36大大你好
小弟照您的程式宣告依然無法跨unit呼叫,煩請大大再指導一下,感恩。mainform與unitfunc宣告如下
unitFunc:
unit UnitFunc; interface
type
pSingle = ^TSingle ;
TSingle = record
Case Integer Of
0: (AsSingle:Single);
1: (FirstHi,FirstLo,SecondHi,SecondLo:Byte);
End;
public
function CRC16(CRCData: array of Byte; Datalen: Integer):Word;
function HexToFloat(aryData: array of Byte; Datalen: Integer):Single;
End; implementation
MainForm宣告如下
unit Main; interface uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, OleCtrls, MSCommLib_TLB, UnitFunc; type
TfrmMain = class(TForm)
Edit1: TEdit;
Edit2: TEdit;
btnSend: TButton;
btnRecive: TButton;
MSComm: TMSComm;
Edit3: TEdit;
Edit4: TEdit;
Edit5: TEdit;
Edit6: TEdit;
procedure FormCreate(Sender: TObject); private
{ Private declarations }
public
{ Public declarations }
end; var
frmMain: TfrmMain; implementation // uses UnitFunc; {$R *.dfm}
|
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
CrcData := crc16( outbyte , 6 );
^^^^^出現"undeclared identifier crc16" // 算出CRC值後再寫入到outbyte[6..7]
outbyte[6] := Trunc(crcData/256) ;
outbyte[7] := (crcData Mod 256);
// ShowMessage(IntToStr(Integer(crcdata))); MSCOMM.Output=OutByte;//將outbyte經mscomm送至設備
^^^^^^^^^^^^^^^^^^^^^^^^^^^出現"Incompatible 'OleVariant' and 'array'"
inbyte=MSCOMM.Input;[/green]
^^^^^^^^^^^^^^^^^^^^^^^^^^^出現"Incompatible 'OleVariant' and 'array'"
|
Chance36
版主 ![]() ![]() ![]() ![]() ![]() ![]() 發表:31 回覆:1033 積分:792 註冊:2002-12-31 發送簡訊給我 |
CrcData := crc16( outbyte , 6 );
^^^^^出現"undeclared identifier crc16"
unit UnitFunc; interface type pSingle = ^TSingle ; TSingle = record Case Integer Of 0: (AsSingle:Single); 1: (FirstHi,FirstLo,SecondHi,SecondLo:Byte); End; //public <============== 移除 function CRC16(CRCData: array of Byte; Datalen: Integer):Word; function HexToFloat(aryData: array of Byte; Datalen: Integer):Single; //End; <============== 移除 implementationMSCOMM.Output=OutByte;//將outbyte經mscomm送至設備 ^^^^^^^^^^^^^^^^^^^^^^^^^^^出現"Incompatible 'OleVariant' and 'array'" inbyte=MSCOMM.Input; ^^^^^^^^^^^^^^^^^^^^^^^^^^^出現"Incompatible 'OleVariant' and 'array'" MSCOMM.output的型態為'OleVariant'而outbyte為Array Of Byte兩者不相容 一般通訊API皆以PChar為參數型態,所以outbyte及inByte應該改成PChar型態看看。(MSCOMM我並沒用過,實際要怎麼使用我也不清楚) [/green] _______________________________________ 深藍的魚,祝您好運..........連連 |
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
MSCOMM.output的型態為'OleVariant'而outbyte為Array Of Byte兩者不相容
一般通訊API皆以PChar為參數型態,所以outbyte及inByte應該改成PChar型態看看。(MSCOMM我並沒用過,實際要怎麼使用我也不清楚)
那請問要如何定義,pchar跟array要怎麼轉換,或pchar要怎麼巷array一樣可以逐bytpe塞資料(如outbyte),或如何取單一byte資料(如inbyte),不然crc16跟hectofloat就無法使用啦,而且剛把程式改成如下所示
var
pInByte : pchar;
pOutByte : pchar;
pOutByte := @OutByte;
MSCOMM.Output := pOutByte;//將outbyte經mscomm送至設備
出現"incompatible 'OleVariant' and 'PAnsiChar'"喔
|
hagar
版主 ![]() ![]() ![]() ![]() ![]() ![]() 發表:143 回覆:4056 積分:4445 註冊:2002-04-14 發送簡訊給我 |
引言: CrcData := crc16( outbyte , 6 ); ^^^^^出現"undeclared identifier crc16"關於 OleVariant 與 Array of Byte 的部份, 也許這篇幫得上忙: http://delphi.ktop.com.tw/topic.php?TOPIC_ID=35466 -- 向 KTop 的弟兄們致敬!unit UnitFunc; interface type pSingle = ^TSingle ; TSingle = record Case Integer Of 0: (AsSingle:Single); 1: (FirstHi,FirstLo,SecondHi,SecondLo:Byte); End; //public <============== 移除 function CRC16(CRCData: array of Byte; Datalen: Integer):Word; function HexToFloat(aryData: array of Byte; Datalen: Integer):Single; //End; <============== 移除 implementationMSCOMM.Output=OutByte;//將outbyte經mscomm送至設備 ^^^^^^^^^^^^^^^^^^^^^^^^^^^出現"Incompatible 'OleVariant' and 'array'" inbyte=MSCOMM.Input; ^^^^^^^^^^^^^^^^^^^^^^^^^^^出現"Incompatible 'OleVariant' and 'array'" MSCOMM.output的型態為'OleVariant'而outbyte為Array Of Byte兩者不相容 一般通訊API皆以PChar為參數型態,所以outbyte及inByte應該改成PChar型態看看。(MSCOMM我並沒用過,實際要怎麼使用我也不清楚) [/green] _______________________________________ 深藍的魚,祝您好運..........連連 ![]() |
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
|
hagar
版主 ![]() ![]() ![]() ![]() ![]() ![]() 發表:143 回覆:4056 積分:4445 註冊:2002-04-14 發送簡訊給我 |
參考這篇試試: http://groups.google.com/groups?hl=zh-TW&lr=&ie=UTF-8&th=44fc6498863d55a7&rnum=33
type TArrayOfByte = array of Byte; procedure VariantToArrayOfByte(const V: OleVariant; out A: TArrayOfByte); var L: Integer; P: Pointer; begin Assert(VarType(V) = varByte or varArray); Assert(VarArrayDimCount(V) = 1); L := VarArrayHighBound(V, 1) - VarArrayLowBound(V, 1) 1; SetLength(A, L); P := VarArrayLock(V); try Move(P^, Pointer(A)^, L); finally VarArrayUnlock(V); end; end; //The complementary procedure would be: procedure ArrayOfByteToVariant(const A: TArrayOfByte; out V: OleVariant); var L: Integer; P: Pointer; begin L := Length(A); V := VarArrayCreate([0, L - 1], varByte); P := VarArrayLock(V); try Move(Pointer(A)^, P^, L); finally VarArrayUnlock(V); end; end;-- 向 KTop 的弟兄們致敬! ![]() |
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
hagar大大你好,小弟還是將完整程式碼貼出給站上高手大大看好了,小弟的程式區分主表單跟程序單元(MainForm & UnitProg),所有副程式皆放在unitprog中
主表單如下
unit Main; interface uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, OleCtrls, MSCommLib_TLB, UnitFunc; type
TArrayOfByte = array of byte;
TfrmMain = class(TForm)
Edit1: TEdit;
Edit2: TEdit;
btnSend: TButton;
btnRecive: TButton;
MSComm: TMSComm;
Edit3: TEdit;
Edit4: TEdit;
Edit5: TEdit;
Edit6: TEdit;
Button1: TButton;
procedure FormCreate(Sender: TObject);
procedure Button1Click(Sender: TObject);
procedure VariantToArrayOfByte(const V: OleVariant;out A: TArrayOfByte);
// [Error] Main.pas(24): Unsatisfied forward or external declaration: 'TfrmMain.VariantToArrayOfByte'
procedure ArrayOfByteToVariant(const A: TArrayOfByte;out V: OleVariant);
// [Error] Main.pas(25): Unsatisfied forward or external declaration: 'TfrmMain.ArrayOfByteToVariant'
private
{ Private declarations }
public
{ Public declarations }
end; var
frmMain: TfrmMain; implementation // uses UnitFunc; {$R *.dfm} procedure VariantToArrayOfByte(const V: OleVariant;out A: TArrayOfByte); var
L: Integer;
P: Pointer; begin
Assert(VarType(V) = varByte or varArray);
Assert(VarArrayDimCount(V) = 1); L := VarArrayHighBound(V, 1) - VarArrayLowBound(V, 1) 1; SetLength(A, L);
P := VarArrayLock(V);
try
Move(P^, Pointer(A)^, L);
finally
VarArrayUnlock(V);
end;
end; //The complementary procedure would be: procedure ArrayOfByteToVariant(const A: TArrayOfByte;out V: OleVariant); var
L: Integer;
P: Pointer; begin
L := Length(A);
V := VarArrayCreate([0, L - 1], varByte); P := VarArrayLock(V);
try
Move(Pointer(A)^, P^, L);
finally
VarArrayUnlock(V);
end;
end; procedure TfrmMain.FormCreate(Sender: TObject);
var
lblary : array Of Pointer;
//a: array[0..7] of Byte;
//b: array[0..1] of Byte;
OutByte: Array[0..10] Of Byte ;
inbyte : Array[0..1024] Of Byte;
crcData : Word ;
StrByte : OleVariant;
Meter_Val : Single ;
begin
mscomm.CommPort:=1;
mscomm.Settings:= '9600,n,8,1';
mscomm.InputMode:=1;
mscomm.PortOpen:= true;
SetLength(lblary, 6);
lblary[0]:= Edit1;
lblary[1]:= Edit2;
lblary[2]:= Edit3;
lblary[3]:= Edit4;
lblary[4]:= Edit5;
lblary[5]:= Edit6;
//TButton(oa[1]).Caption := 'xxxxx'; outbyte[0] := $01;
outbyte[1] := $03;
outbyte[2] := $00;
outbyte[3] := $1A;
outbyte[4] := $00;
outbyte[5] := $02;
CrcData := crc16( outbyte , 6 );
// 算出CRC值後再寫入到outbyte[6..7]
outbyte[6] := Trunc(crcData/256) ;
outbyte[7] := (crcData Mod 256);
edit3.Text:= IntToStr(outbyte[6]);
edit4.Text:= IntToStr(outbyte[7]); InByte[3] := $00;
InByte[4] := $00;
InByte[5] := $2b;
InByte[6] := $43; InByte[7] := $00;
InByte[8] := $00;
InByte[9] := $2c;
InByte[10] := $43;
// 以上是假設資料,你應該改成這樣
ArrayOfByteToVariant(OutByte,StrByte);//將outbyte經mscomm送至設備
//出現 [Error] Main.pas(131): Incompatible types: 'Array' and 'TArrayOfByte'
MSCOMM.Output := StrByte;
StrByte := MSCOMM.Input;
VariantToArrayOfByte(StrByte,InByte);
// [Error] Main.pas(134): Types of actual and formal var parameters must be identical
meter_val := HexToFloat(InByte, 3);
edit1.Text:= FloatToStr(meter_val);
//ShowMessage(FloatToStr(meter_val)); meter_val := HexToFloat(InByte, 7);
edit2.Text:= FloatToStr(meter_val);
//ShowMessage(FloatToStr(meter_val)); end;
procedure TfrmMain.Button1Click(Sender: TObject);
begin
mscomm.PortOpen:=false;
close;
end; end.
程序單元如下
unit UnitFunc; interface
uses SysUtils, Variants;
type
pSingle = ^TSingle ;
TSingle = record
Case Integer Of
0: (AsSingle:Single);
1: (FirstHi,FirstLo,SecondHi,SecondLo:Byte);
End;
function CRC16(CRCData: array of Byte; Datalen: Integer):Word;
function HexToFloat(aryData: array of Byte; Datalen: Integer):Single;
function Str(ArrayData: array of Byte):string;
implementation function HexToFloat(aryData: array of Byte; Datalen: Integer):Single;
Var
p : PSingle;
begin
P := @Result;
P.FirstHi := aryData[Datalen];
P.FirstLo := aryData[Datalen 1];
P.SecondHi := aryData[Datalen 2];
P.SecondLo := aryData[Datalen 3]; end; function CRC16(CRCData: array of Byte; Datalen: Integer):Word;
var
CRC16Lo: Byte;
CRC16Hi: Byte;
SaveLo:Byte;
SaveHi:Byte;
GLo:Byte;
GHi:Byte;
i:Integer;
Flag:Integer;
begin
CRC16Lo:=$ff;
CRC16Hi:=$ff;
GLo:=$01;
GHi:=$a0;
for i:=0 to Datalen -1 do
begin
CRC16Lo:=CRC16Lo xor CRCData[i];
for Flag :=0 to 7 do
begin
SaveLo:=CRC16Lo;
SaveHi:=CRC16Hi;
CRC16Hi:=CRC16Hi shr 1;
CRC16Lo:=CRC16Lo shr 1;
if (SaveHi and $01) = $01 then
CRC16Lo:=CRC16Lo or $80;
if (SaveLo and $01) = $01 then
begin
CRC16Hi:=CRC16Hi xor GHi;
CRC16Lo:=CRC16Lo xor GLo;
end; end; end;
CRC16 := CRC16Lo * 256 CRC16Hi;
end; function Str(ArrayData: array of Byte):String;
var
i: Integer;
Str: string;
begin
Str := '';
for i := Low(ArrayData) to High(ArrayData) do
Str := Str IntToStr(ArrayData[i]); end; end.
其中VariantToArrayOfByte & ArrayOfByteToVariant要改成function
我需要的是類似
mscomm.output :=ArrayOfByteToVariant(OutByte);
StrByte := mscomm.input;
InByte := VariantToArrayOfByte(StrByte);
大大您能了解我的問題嗎,煩請不吝指導,感恩萬分
|
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
|
hagar
版主 ![]() ![]() ![]() ![]() ![]() ![]() 發表:143 回覆:4056 積分:4445 註冊:2002-04-14 發送簡訊給我 |
您要的是這樣?
type TArrayOfByte = array of Byte; function VariantToArrayOfByte(const V: OleVariant): TArrayOfByte; var L: Integer; P: Pointer; begin Assert(VarType(V) = varByte or varArray); Assert(VarArrayDimCount(V) = 1); L := VarArrayHighBound(V, 1) - VarArrayLowBound(V, 1) 1; SetLength(Result, L); P := VarArrayLock(V); try Move(P^, Pointer(Result)^, L); finally VarArrayUnlock(V); end; end; function ArrayOfByteToVariant(const A: TArrayOfByte): OleVariant; var L: Integer; P: Pointer; begin L := Length(A); Result := VarArrayCreate([0, L - 1], varByte); P := VarArrayLock(Result); try Move(Pointer(A)^, P^, L); finally VarArrayUnlock(Result); end; end;-- ![]() |
wychen57
一般會員 ![]() ![]() 發表:32 回覆:77 積分:21 註冊:2003-10-04 發送簡訊給我 |
|
hagar
版主 ![]() ![]() ![]() ![]() ![]() ![]() 發表:143 回覆:4056 積分:4445 註冊:2002-04-14 發送簡訊給我 |
|
neopasia
一般會員 ![]() ![]() 發表:0 回覆:1 積分:0 註冊:2004-12-21 發送簡訊給我 |
本站聲明 |
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。 2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。 3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇! |