标题:用GDI+绘制的图像生成StdPicture对象
只看楼主
eepcvfp
Rank: 2
等 级:论坛游民
帖 子:166
专家分:15
注 册:2013-8-12
结帖率:87.5%
已结贴  问题点数:20 回复次数:10 
用GDI+绘制的图像生成StdPicture对象
各位高手:
      用GDI+绘制的图像如何才能直接从内存中生成一个StdPicture对象呢?

因为我用GDI+绘制的图像要导入到一个第三方控件中,而这个第三方控件支持导入StdPicture对象,我想把GDI+绘制好的图像不经存储,直接从内存中生成一个StdPicture对象,这样可以提高效率,如何才能做到?


关于“StdPicture对象”,我在VFP9的帮助中找不到任何信息,所以向大家求助。
搜索更多相关主题的帖子: GDI 绘制 图像 生成 对象 
2018-02-02 20:52
吹水佬
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:432
帖 子:10064
专家分:41463
注 册:2014-5-20
得分:10 
这个第三方控件是什么
2018-02-03 05:13
eepcvfp
Rank: 2
等 级:论坛游民
帖 子:166
专家分:15
注 册:2013-8-12
得分:0 
回复 2楼 吹水佬
谢谢 吹版!!

是这样的,我需要在FlexCell控件的单元格内放入图片,使用了thisform.FlexCell.Images.AddPicture(Picture, Key)方法。

该方法的参数如下:
Picture:一个StdPicture对象。
Key:字符串表达式,用于指定图片的键,调用Cell对象的SetImage()方法时需要用到此值。需要注意的是,图片组中不能有重复的键。

图片文件是用GDI+自绘的,我以前用的方法是将自绘图像存储为图片,然后用thisform.FlexCell.Images.Add(FilePath, Key)方法添加图片,但这种方法需要先将自绘图像保存为磁盘文件,如果要添加大量的图片,无疑会影响效率,所以,现在我在研究如何将GDI+绘制的图像,不经保存,直接在内存中生成 StdPicture对象,再添加到FlexCell控件的单元格内。

请问,在VFP9.0中,利用 _gdiplus.vcx 类自绘图像如何生成 StdPicture对象? VFP9.0的帮助文件中找不到关于 StdPicture对象 的信息。


[此贴子已经被作者于2018-2-3 14:04编辑过]

2018-02-03 14:00
吹水佬
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:432
帖 子:10064
专家分:41463
注 册:2014-5-20
得分:0 
没用过FlexCell控件不好说
看看有无类似VFP image控件的PictureVal属性,可以直接使用图片数据。
PS:如果FlexCell控件是免费的,可否给测试一下。
2018-02-04 07:51
eepcvfp
Rank: 2
等 级:论坛游民
帖 子:166
专家分:15
注 册:2013-8-12
得分:0 
测试了以下代码:
LOCAL oPic
m.oPic = LoadPicture(SYS(5) + SYS(2003) + '\aa.bmp')
Thisform.Image1.PictureVal = m.oPic

我发现:LoadPicture()函数导入图像,就能得到一个供 Image1.PictureVal 属性所需要的“图像对象”。

所以,我的问题可以简化为:用GDI+绘制的图像如何不经存储,直接在内存中生成 Image1.PictureVal 属性所需要的“图像对象”?

测试项目如下:
测试项目.rar (83.52 KB)


[此贴子已经被作者于2018-2-4 13:23编辑过]

2018-02-04 13:22
吹水佬
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:432
帖 子:10064
专家分:41463
注 册:2014-5-20
得分:0 
VFP的LoadPicture()函数返回的好象是IPicture接口对象。
如果不使用LoadPicture()来获取IPicture接口对象,就是要自己创建引用一个IPicture接口对象(oPic),然后处理oPic的相关数据。
可以参考IPicture接口编程的相关资料,看看有什么搞头。

2018-02-04 16:49
吹水佬
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:432
帖 子:10064
专家分:41463
注 册:2014-5-20
得分:0 
VFP的Image1.PictureVal也可以用字符串格式,也就是位图文件的字符串影像,可以按位图格式将数据写入字符串,但这只是适用于VFP的Image控件。
2018-02-04 16:52
吹水佬
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:版主
威 望:432
帖 子:10064
专家分:41463
注 册:2014-5-20
得分:0 
简单写个获取IPicture接口对象的示例
重点谈接口部份,省略内存图片数据编辑部份,直接将图片文件读入内存。
主要调用:
GlobalAlloc()分配内存
CreateStreamOnHGlobal()获取IStream接口
OleLoadPicture(IPicture)获取IPicture接口
**
** test.prg
**
DECLARE LONG CreateFile IN Kernel32 STRING@, LONG, LONG, LONG, LONG, LONG, LONG
DECLARE LONG GetFileSize IN Kernel32 LONG, LONG@
DECLARE LONG ReadFile IN Kernel32 LONG, LONG, LONG, LONG@, LONG
DECLARE LONG CloseHandle IN Kernel32 LONG

DECLARE LONG GlobalAlloc IN Kernel32 LONG, LONG
DECLARE LONG GlobalLock IN Kernel32 LONG
DECLARE LONG GlobalUnlock IN Kernel32 LONG
DECLARE LONG GlobalFree IN Kernel32 LONG

DECLARE LONG CreateStreamOnHGlobal IN Ole32 LONG, LONG, STRING@
DECLARE LONG OleLoadPicture IN OleAut32 LONG, LONG, LONG, STRING@, STRING@

LOCAL hFile
    ** HANDLE hFile=CreateFile(szImagePath, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL)
hFile = CreateFile("C:\temp\test.bmp", 0x80000000, 1, 0, 3, 0x80, 0)

IF (hFIle == -1)
    RETURN
ENDIF
LOCAL nHSize, nLSize, nFileSize
nHSize = 0
nLSize = GetFileSize(hFile, @nHSize)
nFileSize = nHSize * 0x100000000 + nLSize
LOCAL hImageMemory, pImageMemory
hImageMemory = GlobalAlloc(0x42, nFileSize) && GMEM_MOVEABLE | GMEM_ZEROINIT
pImageMemory = GlobalLock(hImageMemory)
LOCAL nReadSize
nReadSize = 0
ReadFile(hFile, pImageMemory, nFileSize, @nReadSize, 0)
GlobalUnlock(hImageMemory)
CloseHandle(hFile)
LOCAL pIStream
pIStream = REPLICATE(0h00, 4)
CreateStreamOnHGlobal(hImageMemory, 0, @pIStream)
    *IID_IPicture is defined as 7BF80980-BF32-101A-8BBB-00AA00300CAB
LOCAL IID_IPicture, pIPicture
IID_IPicture = 0h8009F87B32BF1A108BBB00AA00300CAB
pIPicture = REPLICATE(0h00, 4)
OleLoadPicture(CTOBIN(pIStream,"4RS"), 0, 0, @IID_IPicture, @pIPicture)
oIPicture = SYS(3096, CTOBIN(pIPicture,"4RS"))
_screen.AddObject("Image1", "image")
_screen.Image1.width = 300
_screen.Image1.height = 200
_screen.Image1.PictureVal = oIPicture
_screen.Image1.Visible = .T.
MESSAGEBOX("结束......")
_screen.RemoveObject("Image1")
GlobalFree(hImageMemory)
CLEAR ALL
2018-02-05 11:11
schtg
Rank: 11Rank: 11Rank: 11Rank: 11
来 自:https://t.me/pump_upp
等 级:贵宾
威 望:67
帖 子:1355
专家分:2534
注 册:2012-2-29
得分:10 
@吹版,谢谢!
2018-02-05 13:33
eepcvfp
Rank: 2
等 级:论坛游民
帖 子:166
专家分:15
注 册:2013-8-12
得分:0 
谢谢 吹版!

您的代码示范了获取IPicture接口对象,但是从存盘文件创建的,怎么把用GDI+绘制的图像生成IPicture接口对象呢?

我先研究一下您的代码。

再次感谢!!!
2018-02-05 20:35



参与讨论请移步原网站贴子:https://bbs.bccn.net/thread-484603-1-1.html




关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.215129 second(s), 8 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved