注册 登录
编程论坛 VFP论坛

VFP封装结构类型示例(二)

吹水佬 发布于 2022-03-26 22:52, 1506 次点击
     
前一贴:VFP封装结构类型示例 https://bbs.bccn.net/thread-508553-1-1.html
   
前一贴以 PARAFORMAT2 结构简单探讨了一下VFP封装结构类型的问题,引起不少FOX友的关注和热烈讨论。
   
现在继续探讨VFP封装结构类型的问题:结构体的嵌套。

1、在结构体中包含其他结构体类型。
2、在结构体中包含指向其他结构体的指针。

先看看下面两个结构 NMHDR 和 OFNOTIFYA 的原形
程序代码:

typedef struct _nmhdr {
  HWND hwndFrom;
  UINT idFrom;
  UINT code;
} NMHDR;

typedef struct _OFNOTIFYA {
  NMHDR           hdr;
  LPOPENFILENAMEA lpOFN;
  LPSTR           pszFile;
} OFNOTIFYA

OFNOTIFYA 结构体成员 hdr 是一个 NMHDR 结构体;成员 lpOFN 是一个指向 OPENFILENAMEA 结构体的指针。
  NMHDR 结构类
程序代码:

DEFINE CLASS NMHDR as STRUCT_CLASS
    PROCEDURE init
        DIMENSION this.aSTRUCT[3,4]
        this.stInit(1,  "hwndFrom", "I",4)    && 有符号整数
        this.stInit(2,  "idFrom",   "U",4)    && 无符号整数
        this.stInit(3,  "code",     "U",4)
        STRUCT_CLASS::init
    ENDPROC
ENDDEFINE

  OFNOTIFYA 结构类可以有两种形式

  形式一、直接将 NMHDR 与 OFNOTIFYA 的成员名合并,变成简单的结构体
程序代码:

DEFINE CLASS OFNOTIFYA as STRUCT_CLASS
    PROCEDURE init
        DIMENSION this.aSTRUCT[5,4]
        * NMHDR 结构
        this.stInit(1,  "hwndFrom", "I",4)
        this.stInit(2,  "idFrom",   "U",4)
        this.stInit(3,  "code",     "U",4)
        
        this.stInit(4,  "lpOFN",    "U",4)    && OPENFILENAMEA 结构指针
        this.stInit(5,  "pszFile",  "U",4)
        STRUCT_CLASS::init
    ENDPROC
ENDDEFINE

  形式二、将 NMHDR 以字符串形式来表达 OFNOTIFYA 的 hdr 成员
程序代码:

DEFINE CLASS OFNOTIFYA as STRUCT_CLASS
    PROCEDURE init
        DIMENSION this.aSTRUCT[3,4]
        this.stInit(1,  "hdr",     "C",12)   && NMHDR 结构
        this.stInit(2,  "lpOFN",   "U",4)    && OPENFILENAMEA 结构指针
        this.stInit(3,  "pszFile", "U",4)
        STRUCT_CLASS::init
    ENDPROC
ENDDEFINE

  以形式二简单的操作示例
程序代码:

cDefPath = ADDBS(JUSTPATH(SYS(16)))
SET DEFAULT TO (cDefPath)

#INCLUDE apiFuns.h
SET PROCEDURE TO apiFuns.prg, StructClass.prg ADDITIVE
LoadApi()

nm = CREATEOBJECT("NMHDR")
of = CREATEOBJECT("OFNOTIFYA")
op = CREATEOBJECT("OPENFILENAMEA")

op.setValue("lStructSize", op.size)
of.setValue("lpOFN", op.addr)

nm.setValue("code", 123, of.getMemberAddr("hdr"))
? "OFNOTIFYA.hdr.code", nm.getValue("code", of.getMemberAddr("hdr"))
? "OFNOTIFYA.hdr.code", C2UINT(sys(2600, of.addr+8, 4))  && 验证一下

SET PROCEDURE TO
CLEAR ALL
RETURN

相关代码打包
只有本站会员才能查看附件,请 登录




[此贴子已经被作者于2022-3-26 23:00编辑过]

4 回复
#2
schtg2022-03-27 06:31
@吹版,认真学习
只有本站会员才能查看附件,请 登录

请继续,谢谢!

[此贴子已经被作者于2022-3-27 06:38编辑过]

#3
吹水佬2022-03-27 09:55
回复 2楼 schtg
多谢!
STRUCT_CLASS 类读写字符串的地方最好修改一下

FUNCTION getValue(cName, ptr) 的:

  CASE this.aSTRUCT[n,2]=="C"   
    RETURN val
改为
  CASE this.aSTRUCT[n,2]=="C"
    RETURN RTRIM(val)

FUNCTION setValue(cName, val, ptr) 的:

  CASE this.aSTRUCT[n,2]=="C" AND VARTYPE(val)=="C"
    val = LEFT(val, nSize)
    nSize = LEN(val)
    RETURN SYS(2600, ptr, nSize, val)
改为:
  CASE this.aSTRUCT[n,2]=="C" AND VARTYPE(val)=="C"
    val = PADR(val, nSize, " ")
    RETURN SYS(2600, ptr, nSize, val)

#4
antony5212022-03-27 10:13
回复 楼主 吹水佬
干得漂亮。就需要这样的老师!
#5
schtg2022-03-27 10:22
回复 3楼 吹水佬
非常感谢,学到了很多有用的!
1