OpenCV打开的图片如何与TBitmap相互转换?

ooolinux 2017-09-07 08:58:04
OpenCV打开的图片在内存中如何与TBitmap相互转换,以便用TImage显示?
...全文
1492 16 打赏 收藏 转发到动态 举报
写回复
用AI写文章
16 条回复
切换为时间正序
请发表友善的回复…
发表回复
  • 打赏
  • 举报
回复
还有人在关注这个问题吗,同遇到这个问题啊
ooolinux 2017-09-20
  • 打赏
  • 举报
回复
@DelphiGuy 我浏览器出问题引用点不了了 Delphi版人气好一些~
  • 打赏
  • 举报
回复
原来你发在Delphi版,我还以为是CB版呢。
  • 打赏
  • 举报
回复
如果opencv中Mat的内部存储结构可以和Tbitmap的内部存储结构对等的话(假设如此),可以: Mat src = imread("xxx"); src.convertTo(src, 某种格式); TBitmap *bmp = new TBitmap; bmp->Width = src.cols; bmp->Height = src.rows; bmp->PixelFormat = 某种格式; memcpy(bmp->ScanLine[0], src.ptr, src.cols * src.elemSize); 没有测试,可能需要cast某些类型,也可能需要循环每次复制一行,因为不清楚Mat的内部存储结构能否和BITMAP的每行像素字节数对齐到32位匹配。
ooolinux 2017-09-19
  • 打赏
  • 举报
回复
@lvjun 我浏览器出问题引用点不了了 比如24位图像,不知道有没有实际的代码?
lvjun 2017-09-19
  • 打赏
  • 举报
回复
......一行数据,无非是一个个点的数据的组合,而一个点是3个或者4个字节(24和32位RGB)的组合而已,所谓的互换,无非就是两个字节内容换一下就可以了。如果一定要到代码,就是用pbyte或者pansichar对应到图像数据或者scanline,例如第一个点就j m := p[0]; p[0] := p[2]; p[2] := m;就可以了,24位是有对齐的问题,scanline好像是按4字节对齐的吧。
ooolinux 2017-09-15
  • 打赏
  • 举报
回复
@DelphiGuy 我浏览器出问题引用点不了了 写到文件再打开,不如在内存中操作速度快~
  • 打赏
  • 举报
回复
opencv里用imwrite写到一个bitmap文件再打开最简单了。
ooolinux 2017-09-14
  • 打赏
  • 举报
回复
@lvjun 我浏览器出问题引用点不了了 如何要RB互换,CV的图像数据就不能直接拷贝给ScanLine了?RB互换有函数吗? 如果原来图像就是24位的,那要考虑对齐问题吗?
lvjun 2017-09-14
  • 打赏
  • 举报
回复
windows的bitmap好像是按BGRA的顺序存放的,而有些技术规范是按RGBA方式存储的,如果转换的两边不同,就要把RB通道换一下,直白点就是把一个像素占用的四个字节中的第一个和第三个换一下就可以了(是不是一样的,,查下资料,或者运行看一下颜色对不对就知道了。)。关于对齐 ,,你使用32位模式,就没有对齐 问题的。速度也快,访问方式也简单,就只是一个点比24位多一个字节,
ooolinux 2017-09-12
  • 打赏
  • 举报
回复
引用 5 楼 lvjun 的回复:
应该是都可以的,首先图像格式最好用32位或者24位图像格式,CV是可以转换的。其次ScanLine就是存储的图像中一行行的数据,所以只要将CV只的数据,按行的方式(如第一行是指针开始位置,第二行是开始位置加上图像宽度*4或者3,以此循环),复制到ScanLine就可以了。如果是FMX的话,可以用map、unmap的方式做,需要注意的一是图像是格式是否一致,否则要RB互换,二是坐标体系,bitmap好像是从左下开始的,VC好像是从左上吧,数据直接move就可以了。
CV的图像数据和ScanLine数据,R、G、B还是B、G、R顺序是一致的吗?每像素行图像数据末尾不知道有没有对齐填充? RB互换是什么意思?
lvjun 2017-09-12
  • 打赏
  • 举报
回复
应该是都可以的,首先图像格式最好用32位或者24位图像格式,CV是可以转换的。其次ScanLine就是存储的图像中一行行的数据,所以只要将CV只的数据,按行的方式(如第一行是指针开始位置,第二行是开始位置加上图像宽度*4或者3,以此循环),复制到ScanLine就可以了。如果是FMX的话,可以用map、unmap的方式做,需要注意的一是图像是格式是否一致,否则要RB互换,二是坐标体系,bitmap好像是从左下开始的,VC好像是从左上吧,数据直接move就可以了。
ooolinux 2017-09-08
  • 打赏
  • 举报
回复
引用 3 楼 summergo123321 的回复:
data 是一个数据存储区指针而已,怎么转?你自己不填充没别的办法,而且C++还要注意 ,cv::Mat 如果定义成局部变量(不是new出来的),,data的内存是自动释放的。
我说的转的意思是包含数据复制,data的数据可以转换成ScanLine吗?
mk_lucifer 2017-09-08
  • 打赏
  • 举报
回复
data 是一个数据存储区指针而已,怎么转?你自己不填充没别的办法,而且C++还要注意 ,cv::Mat 如果定义成局部变量(不是new出来的),,data的内存是自动释放的。
ooolinux 2017-09-08
  • 打赏
  • 举报
回复
引用 1 楼 summergo123321 的回复:
不能转换,自己根据 cv::Mat 中的数据填充一张位图即可, 比如一个简单的方法,cv::Mat(C++) 或者IplImage(C语言)中,直接获取他的type,col,row,还有data属性,然后delphi通过这些参数直接创建一个位图填充像素即可。
是填充TBitmap的Pixels[x][y]吗?可以把data转成ScanLine吗?
mk_lucifer 2017-09-08
  • 打赏
  • 举报
回复
不能转换,自己根据 cv::Mat 中的数据填充一张位图即可, 比如一个简单的方法,cv::Mat(C++) 或者IplImage(C语言)中,直接获取他的type,col,row,还有data属性,然后delphi通过这些参数直接创建一个位图填充像素即可。

1,183

社区成员

发帖
与我相关
我的任务
社区描述
Delphi GAME,图形处理/多媒体
社区管理员
  • GAME,图形处理/多媒体社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧