MFC图片缩放近邻算法、插值算法的实现

server/2024/9/24 10:20:16/

1、图片缩放最近邻算法函数声明

/// srcWight 原图像宽度

/// srcHeight 原图像高度

/// destWight 目标图像宽度

/// destHeight 目标图像高度

/// srcBytesPerPixel 原始图像一个像素所占字节数

/// srcBytesPerLine 原始图像一行像素所占字节数

/// destBytesPerLine 目标图像一行像素所占字节数

/// srcData 原始图像数据

/// destData 目标像素数据


 

    void NearValueCalculate(int srcWight,int srcHeight,int destWight,int destHeight,int srcBytesPerPixel,int srcBytesPerLine, int destBytesPerLine, std::vector<BYTE> &srcData,std::vector<BYTE> &destData)

2、图片缩放最近邻算法函数定义

void NearValueCalculate(int srcWight,int srcHeight,int destWight,int destHeight,int srcBytesPerPixel,int srcBytesPerLine, int destBytesPerLine, std::vector<BYTE> &srcData,std::vector<BYTE> &destData)
{for (int y = 0; y < destHeight; y++){for (int x = 0; x < destWight; x++){int srcX = x * srcWight / destWight;int srcY = y * srcHeight / destHeight;for (int i = 0; i < srcBytesPerPixel; i++){destData[y * destBytesPerLine + x * srcBytesPerPixel + i] =srcData[srcY * srcBytesPerLine + srcX * srcBytesPerPixel + i];}}}
}

3、图片缩放插值算法函数声明

/// srcWight 原图像宽度

/// srcHeight 原图像高度

/// destWight 目标图像宽度

/// destHeight 目标图像高度

/// srcBytesPerPixel 原始图像一个像素所占字节数

/// srcBytesPerLine 原始图像一行像素所占字节数

/// destBytesPerLine 目标图像一行像素所占字节数

/// srcData 原始图像数据

/// destData 目标像素数据

void InsertValueCalculate(int srcWight,int srcHeight,int destWight,int destHeight,int srcBytesPerPixel,int srcBytesPerLine, int destBytesPerLine, std::vector<BYTE> &srcData,std::vector<BYTE> &destData);

4、图片缩放插值算法函数定义

void InsertValueCalculate(int srcWight,int srcHeight,int destWight,int destHeight,int srcBytesPerPixel,int srcBytesPerLine, int destBytesPerLine, std::vector<BYTE> &srcData,std::vector<BYTE> &destData)
{for (int hnum = 0; hnum < destHeight; hnum++){for (int wnum = 0; wnum < destWight; wnum++){double d_original_img_hnum = 1.0 * hnum * srcHeight / destHeight;double d_original_img_wnum = 1.0 * wnum * srcWight / destWight;int i_original_img_hnum = d_original_img_hnum;int i_original_img_wnum = d_original_img_wnum;double distance_to_a_x = d_original_img_wnum - i_original_img_wnum;//在原图像中与a点的水平距离  double distance_to_a_y = d_original_img_hnum - i_original_img_hnum;//在原图像中与a点的垂直距离  int original_point_a = i_original_img_hnum * destBytesPerLine + i_original_img_wnum * srcBytesPerPixel;//数组位置偏移量,对应于图像的各像素点RGB的起点,相当于点A    int original_point_b = i_original_img_hnum * destBytesPerLine + (i_original_img_wnum + 1) * srcBytesPerPixel;//数组位置偏移量,对应于图像的各像素点RGB的起点,相当于点B  int original_point_c = (i_original_img_hnum + 1)*destBytesPerLine + i_original_img_wnum * srcBytesPerPixel;//数组位置偏移量,对应于图像的各像素点RGB的起点,相当于点C   int original_point_d = (i_original_img_hnum + 1)*destBytesPerLine + (i_original_img_wnum + 1) * srcBytesPerPixel;//数组位置偏移量,对应于图像的各像素点RGB的起点,相当于点D   if (i_original_img_hnum +1== destHeight - 1){original_point_c = original_point_a;original_point_d = original_point_b;}if (i_original_img_wnum +1== destWight - 1){original_point_b = original_point_a;original_point_d = original_point_c;}int pixel_point = hnum * srcBytesPerLine + wnum * srcBytesPerPixel;//映射尺度变换图像数组位置偏移量  for(int i = 0; i < srcBytesPerPixel; i++){destData[pixel_point + i] =srcData[original_point_a + i] * (1 - distance_to_a_x) * (1 - distance_to_a_y) +srcData[original_point_b + i] * distance_to_a_x * (1 - distance_to_a_y) +srcData[original_point_c + i] * distance_to_a_y * (1 - distance_to_a_x) +srcData[original_point_c + i] * distance_to_a_y * distance_to_a_x;}}}
}

5、图片缩放调用函数声明

static HBITMAP BitmapResize(HDC hdc, HBITMAP hBmpSrc, int calculateType = 0);

6、图片缩放调用函数定义

HBITMAP BitmapResize(HDC hdc, HBITMAP hBmpSrc,int calculateType)
{// 获取源位图的信息BITMAP bmpSrc;GetObject(hBmpSrc, sizeof(BITMAP), &bmpSrc);int newWidth = bmpSrc.bmWidth;int newHeight = (int)(1.0 * bmpSrc.bmHeight / SCALE_FACTOR);// 创建目标位图HBITMAP hBmpDest = CreateCompatibleBitmap(hdc, newWidth, newHeight);// 获取源位图和目标位图的数据int srcWidth = bmpSrc.bmWidth;int srcHeight = bmpSrc.bmHeight;int srcBytesPerPixel = bmpSrc.bmBitsPixel / 8; //一个像素占字节数int srcBytesPerLine = ((srcWidth * srcBytesPerPixel + (srcBytesPerPixel - 1)) / srcBytesPerPixel) * srcBytesPerPixel;//原始图像一行像素所占字节数int destBytesPerLine = ((newWidth * srcBytesPerPixel + (srcBytesPerPixel - 1)) / srcBytesPerPixel) * srcBytesPerPixel;//目标图像一行像素所占字节数std::vector<BYTE> srcData(srcBytesPerLine * srcHeight);//存储原始图像数据std::vector<BYTE> destData(destBytesPerLine * newHeight);//存储目标像素数据GetBitmapBits(hBmpSrc, srcData.size(), srcData.data());switch (calculateType){case 0:InsertValueCalculate(srcWidth,srcHeight,newWidth,newHeight,srcBytesPerPixel,srcBytesPerLine,destBytesPerLine,srcData,destData);break;case 1:NearValueCalculate(srcWidth,srcHeight,newWidth,newHeight,srcBytesPerPixel,srcBytesPerLine,destBytesPerLine,srcData,destData);break;default:break;}// 设置目标位图的数据SetBitmapBits(hBmpDest, destData.size(), destData.data());return hBmpDest;
}

7、调用实例

#define NEW_WIDTH 800
#define NEW_HEIGHT 480
#define SCALE_FACTOR 1.25 //图片缩放系数HBITMAP hBitmap;
HDC hdc = GetDC()->GetSafeHdc();;
CStatic* picSetDlgBack;
RECT rect;
int y,height;//缩放窗体
this->MoveWindow(0,0,NEW_WIDTH,NEW_HEIGHT);
//缩放图片
picSetDlgBack = (CStatic *)GetDlgItem(IDC_STATIC);//获取控件指针
picSetDlgBack->GetWindowRect(&rect);
ScreenToClient(&rect);
y = (int)1.0 * rect.top / SCALE_FACTOR;
height = (int)(1.0 * (rect.bottom - rect.top)/SCALE_FACTOR);
picSetDlgBack->MoveWindow(rect.left,y,rect.right - rect.left,height);
hBitmap = ::LoadBitmap(AfxGetInstanceHandle(),MAKEINTRESOURCE(IDB_INITBKG_T));
hBitmap2 = BitmapResize(hdc,hBitmap);
picSetDlgBack->SetBitmap(hBitmap2);

技术交流请加群:996775415


http://www.ppmy.cn/server/103844.html

相关文章

【ARM+Codesys 客户案例 】 基于RK3568/A40i/STM32+CODESYS在工厂自动化中的应用:铆接机

应用&#xff1a;铆接机&#xff1a; 连接、压入和焊接工艺中&#xff0c;铆接机的加工过程控制 Berghof向德国Wener Krayer公司提供铆接机的显控一体控制器&#xff0c;该控制器有强大的I/O扩展功能。使用该控制器&#xff0c;可以显著减少铆接过程中的失误率或次品率。其体积…

leetcode滑动窗口问题

想成功先发疯&#xff0c;不顾一切向前冲。 第一种 定长滑动窗口 . - 力扣&#xff08;LeetCode&#xff09;1456.定长子串中的元音的最大数目. - 力扣&#xff08;LeetCode&#xff09; No.1 定长滑窗套路 我总结成三步&#xff1a;入-更新-出。 1. 入&#xff1a;下标为…

学习记录第二十八天

有名管道&#xff08;FIFO&#xff09; 在Linux系统中&#xff0c;有名管道是一种特殊类型的文件&#xff0c;它允许不相关的进程之间进行通信。有名管道在文件系统中有一个具体的路径和名称&#xff0c;因此它们可以被多个进程共同访问。有名管道的特点包括持久性、多进程访问…

『Z-Workshop』 The Graph workshop mini hackathon活动

Community Meetup In Hangzhou ZJUBCA 2024 求是 创新 概述 / OVERVIEW The Graph作为一个去中心化的查询协议&#xff0c;为区块链数据的索引和查询提供了强大的支持。我们希望通过这场黑客松&#xff0c;激发大家对区块链技术更深层次的探索和应用&#xff0c;共同推动这一…

WPS宏实现表格合并功能

把文件夹中N个表格Sheet1页的数据合并成一个新的表格 function 合并表格() { //合并文件为C盘下面名为test的文件夹 var folderPath "C:\\test"; var fileName Dir(folderPath "\\*.*"); if(fileName ""){ ale…

知识改变命运 数据结构【链表面试题】

1. 删除链表中等于给定值 val 的所有节点。 OJ链接 public ListNode removeElements(ListNode head, int val) {if (headnull) {return null;}ListNode curhead.next;ListNode prehead;while(cur!null) {if(cur.valval) {pre.nextcur.next;curcur.next;}else {precur;curcur.ne…

学习之appium的简单使用

使用之前需要先安装一下依赖 1、安装jdk&#xff1a;暂时为整理笔记以后补充 2、安装nodejs:https://blog.csdn.net/qq_42792477/article/details/141363957?spm1001.2014.3001.5501 3、安装SDk&#xff08;安卓篇&#xff09;&#xff1a;https://blog.csdn.net/qq_42792477…

esbuild中的Data URL Loader:轻松将文件嵌入为Base64编码的数据URL

在前端项目中&#xff0c;经常需要将图片、字体、音频或其他文件直接嵌入到JavaScript代码中&#xff0c;以便在运行时能够立即使用&#xff0c;而无需额外的HTTP请求。为了实现这一需求&#xff0c;esbuild提供了Data URL Loader这一功能强大的工具。它能够在构建时将文件加载…