|
|
请使用QQ关联注册PLM之家,学习更多关于内容,更多精彩原创视频供你学习!
您需要 登录 才可以下载或查看,没有账号?注册
x
本帖最后由 15757753770 于 2016-12-11 15:09 编辑
8 G% s0 g% m; Y d q& \) c9 t/ m: k+ I
7 D, x$ H |# u. v以下内容转载来的 部分亲测 部分未测试
# E: ^3 V5 O4 p0 v+ H! @7 y+ q# R) S8 E7 y
/ T5 e2 F# Z0 k, r. R& s* C3 ~; s% q- [5 {
VB调用C DLL时的参数传递6 H* r- e+ J4 k5 v' n9 b* s& u* H- i
6 A* M+ E; J2 z M! j
函数在C中的原型,参数类型和传递方式 对应关系 1 ? ]& A' U! V6 q2 K. \
! h: M4 c" z: j9 ]. z) R W
% |$ I. o- o. n
# _. {# |' H! OC DLL 原型 VB声明 VB调用$ U* C% y$ Q H6 O6 A5 y% v6 D
5 e, c ]; o5 y# ]USHORT a ByVal a as long Call func(…,a,…)7 ]4 Q0 q2 }7 V, n2 l- |
5 J7 z1 y3 G* }% g+ P' dint a ByVal a as long Call func(…,a,…)
$ L9 \4 x" F5 @/ s0 R/ F# \
B9 a& |+ K; a2 P8 M, b% k9 Y! klong a ByRef a as long Call func(…,byval a,…)
9 t3 E3 { P2 |, m3 g( H# H; c: D
int *pa ByRef pa as long Call func(…,pa,…), `9 M2 t* _% Q J/ I! m+ B
0 k2 f5 |. D+ k& u ^3 |* `* W
long *pa ByVal pa as long Call func(…,varptr(pa),…) <---------(1), Z: b9 S: X5 P3 ^
) {- @( }& `9 v3 Q! t
LPSTR lpStr ByVal lpStr as string Call func(…,lpStr,…)+ P( c: u- B1 t( r6 M0 ?
3 X* g, v3 B" B- V% f# b* ^
char *pstr ByVal pstr as string Call func(…,pstr,…) <---------(2)3 M3 R1 u/ f' k3 }5 W9 A, x
7 ]$ [; j7 o }3 J( Q) Owchar *pstr ByRef pstr as string Call func(…,byval pstr,…)% d3 B- ^' M: M' C2 c* q
! k% D$ \' n8 {, v' h
struct tagX *p ByRef p as tagX Call func(…,ptag,…) <---------(3)
$ d7 O0 r9 m. f2 \4 B, I% E7 U7 ]% h; _
HANDLE h ByVal h as long Call func(…,h,…) <---------(4) ( a, E. q$ l, _7 `3 p
9 c. w+ U+ T1 |3 ?/ v6 s
备注
' b" `1 h; c S+ k" [4 f2 a0 a4 p# s& ?1 g3 T6 H2 _% J
1)不推荐使用此方式
+ O9 |3 q1 h; i# h, Y6 d, i; g x! E; n& p. Y& ^
2)如果DLL要求一个字符串缓冲区,一定要在调用前初始化字串,即dim t as string * 50
2 v+ D' r% j3 {$ P. U+ z
8 _) U2 g) x4 E7 K- |3)用户定义子类型必须用ByRef方式传递, 9 v, r! _" c5 B# I
6 X3 q: |7 f( n4 [8 b4)任何内核对象的句柄(process, thread, module, file, filemapping, semaphore等)和大多数GDI对象的句柄都能用此方式传递。 0 ]3 s5 }- N8 _, o- a' {
3 G8 g f4 t, c/ V. |% h
1 F0 b' h0 ?5 {9 r; F( @" Z. M' |1 C: M+ a8 T! E6 e
* u/ I' [4 C; g2 e0 P) b
, f$ C0 P5 ?/ ]! M+ ^ X( {; b3 ~7 g* ~/ B D" D/ t
8 W2 x8 M% X0 M+ X) s0 B' |数组传递
/ ~8 Z- Q9 H1 q4 m7 q! Z! h" O$ v8 ]- c
数组传递值用ByRef
( M4 u+ Y0 R; j
; S5 E# P1 q8 D VB地址到VC的传递,只需要将数组第一个值得地址作为ByVal参数传递过去就可以。
7 o* c- \1 i2 @: I6 W* b `: }: d
3 |. m" c s6 e c/ a/ K, Z+ g& _* q+ ~! J, r
5 D. U* G& s( x8 y% J: g/ e VC中的数组的第一个的元素的地址传递到VB,只需要通过API函数CopyMemory就可以将整个数组拷贝到VB数组中。' j2 b+ U! X9 ?2 X6 a3 x" s
$ P5 _3 A) o* x5 A, N, ~+ a5 @4 T: M5 T
0 l0 D) X5 A6 `5 o( m0 H5 |
4 i9 p* k1 g7 g& _7 p
9 @# z$ [7 N. j+ e5 R) udll函数直接返回字符串$ \, U' T1 r2 Q0 g8 ~! s: V u
+ z5 D% s9 h+ @7 l& `3 j' t& _0 X: Q4 O
) Y% c) I( ~0 v9 m5 o0 _! _
VB下的字符串格式和VC中的char有些不同的
, Z+ O% o4 {/ h+ M, ^1 {0 Q; x
& x6 q& B! L n" @ 直接返回char *是不行的,VB不支持这种做法。正如你在资料中看到,大多数都是在VB中先给字符串分配空间,再传递给VC,在DLL中可以修改字符串,但不能超过VB中分配的空间。如果你希望直接返回字符串,必须使用BSTR类型,这实际上就是VB中的字符串所使用的类型。下面是一个简单的例子:
- P. l8 p8 F# P( G7 j( h+ d
2 S# m, f, l! |
% O" S, M. t* y
, A9 T+ ~. w0 w8 m EXTERN_C BSTR WINAPI RetStr() ?, ]) F9 [3 h) W3 W
: r/ Y4 u5 l0 V { 0 `4 U4 I( ], @# M: \/ L6 u
5 s2 z4 o; k3 \) g; y( ?
char *str = "1234567890";
! Q( c) G( X! V; p- N$ o) q0 D; P8 I0 P8 d+ y' I) ^' R
return SysAllocString((BSTR)str);
+ j6 [- e* Z! \) X- C9 v% o' L: D: p# ~7 E4 z; a& F9 k- q+ h6 v
}
2 C( Z4 }: S7 ]7 c, `) A+ k, R; h' d! P) H; N7 h5 D
或者参考一下VB下调用GeTComputerName的方法.
. B: o7 Z0 a8 t7 _6 m0 F: d9 K2 D9 k! P- y- B" n
( N0 L& {1 M! N. M5 d
! o: Q+ K1 k O( Y: S
; x: F6 C& k+ F2 L: Y7 E9 a, r1 n
6 z" X3 @! R4 h# r
VC++与VB数据类型对应关系
! ~/ i* h5 x/ V, c1 p
$ X3 e! @' X k TVC++ VB/ i/ E( O* l' ^4 M
short Integer- p# F" `/ Z* p/ w+ V6 i
int Long
3 n7 {0 f& b8 H2 _long Long
9 V! h" F# k) A0 gUNIT Long
# R6 K; D9 S4 B* b/ DULONG Long" v, C% H5 E: p: u( }. A# A6 w
WORD DWORDLong
: Z: Z$ ~/ z5 {9 F5 v: v: ^WPARAM LPARAMLong9 h5 C2 T, o6 n8 C
WMSG UMSGLong/ |" k6 }9 U1 Q: `7 o
HRESULT Long
4 A( Q- I& T3 A5 {4 u! m; lBOOL Boolean- t4 u& a/ m$ u- ?; l( l% f
COLORREF Long' W7 ~5 z3 k+ i0 i, U# w
HWND,HDC,HBRUSH,HKEY,等等 Long% V! `. Q9 K% r' e6 }7 M3 v; A
LPSTR LPCSTRString4 r: D5 n2 _" Y+ H$ g
LPWSTR,OLECHARBSTR String
# F2 [+ U5 a" V4 A: F. ~LPTSTR String
) q6 }$ y" [6 W; \& F+ _VARIANT_BOOL Boolean2 J* A5 W/ U5 L s9 t8 ^
unsignedchar Byte
+ `" a5 T3 s! q, c! ?8 w. m- JBYTE Byte
0 L$ F) C7 m) S. @+ R; z' v; R( rVARIANTVariant
0 u! d* @3 D; i. e3 U% h(任何以*或**结尾的数据类型) Long
2 \% n& a/ ?/ I! C: y: B) v
. S' n, i' l# D
. f/ _4 H5 }+ B, j) Ac中的数据类型 VB中的声明 结果
" l B2 s3 O6 ~, F
2 k- Z6 o t3 cATOM ByVal variable As Integer 结果为Integer 类型的表达式
" G1 c! y4 n4 I `, z% KBOOL ByVal variable As Boolean 结果为 Long 类型的表达式
2 P3 x/ D8 X) Q" WBYTE ByVal variable As Byte 结果为 Byte 类型的表达式
! \; [# r7 ]8 BCHAR ByVal variable As Byte 结果为 Byte 类型的表达式 5 `+ a2 U7 z6 ~) k
COLORREF ByVal variable As Long 结果为 Long 类型的表达式 9 ~2 v# h9 C6 c, q% m
DWORD ByVal variable As Long 结果为 Long 类型的表达式
5 a7 E+ |/ o8 a UHWND, HDC, HMENU ByVal variable As Long 结果为 Long 类型的表达式等Windows 句柄 9 L6 X2 Y r5 i4 X9 ~$ J/ @0 m
INT, UINT ByVal variable As Long 结果为 Long 类型的表达式
" d' S" z# k$ z: A' qLONG ByVal variable As Long 结果为 Long 类型的表达式
8 `; F! [( v& Z7 A& M' Y" sLPARAM ByVal variable As Long 结果为 Long 类型的表达式
/ ?" `* T% o3 ^) Z- ^LPDWORD variable As Long 结果为 Long 类型的表达式 " J# p- S* d" p" T5 E) j
LPINT, LPUINT variable As Long 结果为 Long 类型的表达式 1 N2 H( `% p: x1 i
LPRECT variable As type 自定义类型的任意变量
1 k. z; L& G$ v; U8 NLPSTR, LPCSTR ByVal variable As String 结果为 String 类型的表达式 - J% u' t! c/ F( e, m
LPVOID variable As Any 任何变量(在传递字符串的时候使用ByVal)
' z4 Q1 ]4 p- Z4 n7 \8 E! p9 F6 ^LPWORD variable As Integer 结果为Integer 类型的表达式
$ L, {0 W, a5 pLRESULT ByVal variable As Long 结果为 Long 类型的表达式 & X0 ^: T$ C5 o3 e G' l
NULL As Any 或 ByVal Nothing 或 ByVal variable As Long ByVal 0& 或 VBNullString SHORT ByVal variable As Integer 结果为Integer 类型的表达式 8 O) F3 j6 g4 @* _
VOID Sub procedure 不可用
* U) U" q# O" m/ r* h: EWORD ByVal variable As Integer 结果为Integer 类型的表达式
& s* e2 F" u! q* [8 C6 ^5 tWPARAM ByVal variable As Long' ^- a" v) W% R& |/ o
" ?: W( Y8 L+ `$ K' x Y" y
|
|