转自http://blog.csdn.net/wallimn/article/details/3068643
/************************************************************/
VC IPicture
显示网络图片 显示远程图片 显示URL指定的图片
通过HTTP下载显示图片 显示网上广告图片
上面是我罗列的关键字,我找这个文章换了好几种关键字写法,才找到,
为了方便它人,我把关键字全部写上。
/************************************************************/
文章很不错,正好解决了我的问题。感谢作者。这是个用SDK(没有使用MFC)开发的程序。
如果对SDK开发方式不是很熟,只看ShowPic函数就以了。
- #include <windows.h> // Windows SDK 要用到的
- #include <commdlg.h> // 打开文件的窗口要包含这个头文件
-
- //用到了 IPicture 接口,要包含下面两个 头文件
- #include <ocidl.h>
- #include <olectl.h>
-
- // 声明窗口函数的原型
- LRESULT CALLBACK MainWndProc (HWND, UINT, WPARAM, LPARAM);
-
- // 声明显示图片的函数原型
- HRESULT ShowPic(char *lpstrFile,HWND hWnd) ;
-
- //图片文件名
- char lpstrFile[MAX_PATH]="";
-
-
- int WINAPI WinMain (HINSTANCE hThisInstance,
- HINSTANCE hPrevInstance,
- LPSTR lpszArgument,
- int nFunsterStil)
-
- {
- // 窗口类名
- char szClassName[ ] = "ShowPicture";
-
- WNDCLASSEX windclass;
-
- //用描述主窗口的参数填充 WNDCLASSEX 结构
- windclass.cbSize = sizeof(windclass); //结构大小
- windclass.hInstance = hThisInstance; //实例句酚
- windclass.lpszClassName = szClassName;
- windclass.lpfnWndProc = MainWndProc; //窗口函数指针
- windclass.style = CS_DBLCLKS; //捕获双击事件
- windclass.cbSize = sizeof (WNDCLASSEX);
-
- windclass.hIcon = LoadIcon (NULL, IDI_APPLICATION); //使用预定义图标
- windclass.hIconSm = LoadIcon (NULL, IDI_APPLICATION); //使用预定义类的小图标
- windclass.hCursor = LoadCursor (NULL, IDC_ARROW); //使用预定义光标
- windclass.lpszMenuName = NULL; //不指定主菜单
- windclass.cbClsExtra = 0; //没有额外的类内存
- windclass.cbWndExtra = 0; //没有额外的窗口内存
-
- windclass.hbrBackground = (HBRUSH) COLOR_BACKGROUND; //使用预定义背景画刷
-
- //注册这个窗口类,如果失败直接退出程序
- if (!RegisterClassEx (&windclass))
- return 0;
-
- //创建主窗口
- HWND hWnd = CreateWindowEx (
- 0, //dwExStyle, 扩展样式
- szClassName, //lpClassName, 类名
- "显示图片 -- 鼠标双击浏览图片文件 -- Author:Unmi", //lpWindowName, 标题
- WS_OVERLAPPEDWINDOW, //dwStyle, 窗口风格
- CW_USEDEFAULT, //X, 初始 X 坐标
- CW_USEDEFAULT, //Y, 初始 YX 坐标
- 640, //nWidth, 宽度
- 480, //nHeight, 高度
- HWND_DESKTOP, //hWndParent, 父窗口句柄
- NULL, //hMenu, 菜单句柄
- hThisInstance, //hInstance, 程序实例句柄
- NULL //lpParam, 用户数据
- );
-
- //显示窗口,刷新窗口客户区
- ShowWindow (hWnd, nFunsterStil);
-
- // 从消息队列中取出消息,交给窗口函数处理
- // 直到 GetMessage 取出的消息是 WM_QUIT,即FALSE,则结束消息循环
- MSG messages;
- while (GetMessage (&messages, NULL, 0, 0))
- {
- //转换键盘消息,把虚拟键转换为字符消息
- TranslateMessage(&messages);
-
- //将消息发送到相应的窗口函数
- DispatchMessage(&messages);
- }
-
- // GetMessage 返回 FALSE,程序结束 PostQuitMessage() 发出这一消息
- return messages.wParam;
- }
-
-
- // 窗口函数,消息由 DispatchMessage 派发
- LRESULT CALLBACK MainWndProc (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
- {
- switch (message) //处理消息
- {
- case WM_DESTROY:
- //向消息队列投递一个 WM_QUIT 消息,促使 GetMessage 函数返回0,结束消息循环
- PostQuitMessage (0);
- break;
- case WM_LBUTTONDBLCLK:
- {
- OPENFILENAME file = {0};
- file.lStructSize = sizeof(file);
- file.lpstrTitle = "请选择一个图片文件";
- file.lpstrFile = lpstrFile;
- file.nMaxFile = MAX_PATH;
- file.lpstrFilter = "Pictures(*.jpg,*.gif,*.bmp)/0*.jpg;*.gif;*.bmp/0/0";
- if(::GetOpenFileName(&file))
- {
- //清除原来的图像
- HDC hdc=GetDC(hWnd);
- RECT rect;
- ::GetWindowRect(hWnd,&rect);
- ::FillRect(hdc,&rect,(HBRUSH) COLOR_BACKGROUND);
-
- ::SendMessage(hWnd,WM_PAINT,NULL,NULL);
- }
- }
- break;
- case WM_PAINT:
- ShowPic(lpstrFile,hWnd);
- break;
- default:
-
- //将我们不处理的消息交给系统 做默认处理
- return DefWindowProc (hWnd, message, wParam, lParam);
- }
-
- return 0;
- }
- // 显示图片, lpstrImgUrl 为图片URL地址,hWnd 为窗口句柄
- HRESULT Utils::ShowPic(char *lpstrImgUrl,HWND hWnd)
- {
- HDC hDC_Temp=GetDC(hWnd);
-
- IPicture *pPic;
- IStream *pStm;
-
- BOOL bResult;
-
- DWORD dwFileSize,dwByteRead;
-
- //读取网页上图片文件,实际是个CHttpFile指针
- CInternetSession session("HttpClient");
- CFile* httpFile = (CFile*)session.OpenURL(lpstrImgUrl);
-
- if (httpFile!=INVALID_HANDLE_VALUE)
- {
- dwFileSize= httpFile->GetLength();//获取文件字节数
-
- if (dwFileSize==0xFFFFFFFF)
- return E_FAIL;
- }
- else
- {
- return E_FAIL;
- }
-
-
- //分配全局存储空间
- HGLOBAL hGlobal = GlobalAlloc(GMEM_MOVEABLE, dwFileSize);
- LPVOID pvData = NULL;
-
- if (hGlobal == NULL)
- return E_FAIL;
-
- if ((pvData = GlobalLock(hGlobal)) == NULL)//锁定分配内存块
- return E_FAIL;
-
- //把文件读入内存缓冲区
- dwByteRead = httpFile->Read(pvData,dwFileSize);
-
- GlobalUnlock(hGlobal);
-
- CreateStreamOnHGlobal(hGlobal, TRUE, &pStm);
-
- //装入图形文件
- bResult=OleLoadPicture(pStm,dwFileSize,TRUE,IID_IPicture,(LPVOID*)&pPic);
-
- if(FAILED(bResult))
- return E_FAIL;
-
- OLE_XSIZE_HIMETRIC hmWidth; //图片的真实宽度, 单位为英寸
- OLE_YSIZE_HIMETRIC hmHeight; //图片的真实高度, 单位为英寸
- pPic->get_Width(&hmWidth);
- pPic->get_Height(&hmHeight);
-
- //转换hmWidth和hmHeight为pixels距离,1英寸=25.4毫米
- int nWidth = MulDiv(hmWidth,GetDeviceCaps(hDC_Temp,LOGPIXELSX),2540);
- int nHeight = MulDiv(hmHeight,GetDeviceCaps(hDC_Temp,LOGPIXELSY),2540);
-
- //将图形输出到屏幕上(有点像BitBlt)
- bResult=pPic->Render(hDC_Temp,0,0,nWidth,nHeight,
- 0,hmHeight,hmWidth,-hmHeight,NULL);
-
- pPic->Release();
-
- httpFile->Close();//关闭打开的文件
-
- if (SUCCEEDED(bResult))
- {
- return S_OK;
- }
- else
- {
- return E_FAIL;
- }
- }
补充说明:
原文的程序是使用SDK方式开发的,可能会有些人不习惯,我使用MFC方式验证调试了一下,效果还不错。如需要源码的,请到http://wallimn.ys168.com(我的网络硬盘)下载。
我的程序是个很简单的程序,没有考虑重绘、图片大小的处理等问题,仅体现编程思想及方法。