标签 WinInet 下的文章

wininet源代码获取例子 update2

#include <windows.h>
#include <wininet.h>
#include <process.h>
#include "resource.h"
#pragma comment(lib, "wininet")
#define ID_URLEDITBOX 1
#define ID_GETBUTTON 2
#define ID_SHOWEDITBOX 3
#define WEBSOURCE_SIZE (1024*1024*sizeof(char))

static HWND hwndUrlEdt,hwndGetBtn,hwndShowEdt;

LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM) ;
int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance,
PSTR szCmdLine, int iCmdShow)
{
static TCHAR szAppName[] = TEXT ("BtnLook") ;
HWND hwnd ;
MSG msg ;
WNDCLASS wndclass ;
wndclass.style = CS_HREDRAW | CS_VREDRAW ;
wndclass.lpfnWndProc = WndProc ;
wndclass.cbClsExtra = 0 ;
wndclass.cbWndExtra = 0 ;
wndclass.hInstance = hInstance ;
wndclass.hIcon = LoadIcon (NULL, MAKEINTRESOURCE(IDI_MYICON)) ;
wndclass.hCursor = LoadCursor (NULL, IDC_ARROW) ;
wndclass.hbrBackground = (HBRUSH) GetStockObject (WHITE_BRUSH) ;
wndclass.lpszMenuName = NULL ;
wndclass.lpszClassName = szAppName ;

if (!RegisterClass (&wndclass))
{
MessageBox (NULL, TEXT ("This program requires Windows NT!"),
szAppName, MB_ICONERROR) ;
return 0 ;
}

hwnd = CreateWindow (szAppName, TEXT ("WinINet源代码获取"),
WS_OVERLAPPED | WS_SYSMENU | WS_BORDER | WS_MINIMIZEBOX,GetSystemMetrics(SM_CXSCREEN)/4,GetSystemMetrics(SM_CYSCREEN)/4,650,350,
NULL, NULL, hInstance, NULL) ;
ShowWindow (hwnd, iCmdShow) ;
UpdateWindow (hwnd) ;

while (GetMessage (&msg, NULL, 0, 0))
{
TranslateMessage (&msg) ;
DispatchMessage (&msg) ;
}
return msg.wParam ;
}
void Thread1 (PVOID pvoid)
{
HINTERNET hConnect,hSession;
char *szBuffer = malloc(WEBSOURCE_SIZE);
wchar_t *wszBuffer = (wchar_t *)malloc(WEBSOURCE_SIZE);
TCHAR szStr[100];
DWORD dwSize=0;
DWORD dwDownloaded;
int len;
if(szBuffer == NULL)
{
MessageBox(hwndGetBtn,TEXT("error"),TEXT("Error"),MB_ICONHAND);
}
GetWindowText(hwndUrlEdt,szStr,sizeof(szStr)/sizeof(TCHAR));
hSession = InternetOpen(TEXT("testWinINet"), PRE_CONFIG_INTERNET_ACCESS, NULL, INTERNET_INVALID_PORT_NUMBER, 0);
hConnect = InternetOpenUrl(hSession,szStr,NULL,0,INTERNET_FLAG_DONT_CACHE,0);
ZeroMemory(szBuffer,WEBSOURCE_SIZE);
while (InternetReadFile(hConnect,szBuffer,WEBSOURCE_SIZE,&dwDownloaded))
{
if (0==dwDownloaded) break;
szBuffer[dwDownloaded]=0;
}
len=MultiByteToWideChar(CP_UTF8,0,szBuffer,-1,NULL,0);
MultiByteToWideChar(CP_UTF8,0,szBuffer,-1,wszBuffer,sizeof(wszBuffer));

SetWindowText(hwndShowEdt,szBuffer);

//释放内存
free(szBuffer);
szBuffer=NULL;
//按钮状态
SetWindowText(hwndGetBtn,TEXT("GO"));
EnableWindow (hwndGetBtn, TRUE) ;

_endthread () ;
}
LRESULT CALLBACK WndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
static HICON hIcon;
HINSTANCE hInstance;
HFONT font;
static int cxClient,cyClient;
font = CreateFont(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, "microsoft yahei");
switch (message)
{
case WM_CREATE:
//loadicon
//hInstance = ((LPCREATESTRUCT) lParam)->hInstance ;
//hIcon = LoadIcon (hInstance, MAKEINTRESOURCE (NULL)) ;
//child window
hwndUrlEdt = CreateWindow (TEXT ("EDIT"), NULL,
WS_CHILD | WS_VISIBLE | WS_BORDER | ES_LEFT | ES_AUTOHSCROLL ,
20,20,500,25, hwnd, (HMENU)ID_URLEDITBOX,
((LPCREATESTRUCT) lParam) -> hInstance, NULL) ;

hwndGetBtn = CreateWindow (TEXT ("BUTTON"), TEXT("GO"),
WS_CHILD | WS_VISIBLE | BS_DEFPUSHBUTTON ,
530,20,100,25, hwnd, (HMENU)ID_GETBUTTON,
((LPCREATESTRUCT) lParam) -> hInstance, NULL) ;

hwndShowEdt = CreateWindow (TEXT ("EDIT"), TEXT(""),
WS_CHILD | WS_VISIBLE | WS_BORDER | WS_HSCROLL | WS_VSCROLL | ES_AUTOHSCROLL | ES_AUTOVSCROLL | ES_MULTILINE ,
20,60,600,250, hwnd, (HMENU)ID_SHOWEDITBOX,
((LPCREATESTRUCT) lParam) -> hInstance, NULL) ;

SendMessage(hwndUrlEdt,WM_SETFONT,(WPARAM)font,TRUE);
SendMessage(hwndGetBtn,WM_SETFONT,(WPARAM)font,TRUE);
SendMessage(hwndShowEdt,WM_SETFONT,(WPARAM)font,TRUE);

return 0;
case WM_SIZE:
cyClient = LOWORD(lParam);
cxClient = LOWORD(lParam);
return 0;
case WM_COMMAND:
if(LOWORD(wParam) == ID_GETBUTTON)
{
//按钮状态
SetWindowText(hwndGetBtn,TEXT("下载中..."));
EnableWindow (hwndGetBtn, FALSE) ;
_beginthread (Thread1, 0, NULL) ;
}
return 0;
case WM_DESTROY:
DeleteObject(font);
PostQuitMessage(0);
return 0;
}
return DefWindowProc (hwnd, message, wParam, lParam) ;
}

存储源代码的变量使用malloc申请内存空间就可以摆脱1MB栈大小的限制(char *szBuffer = malloc(WEBSOURCE_SIZE);),点击按钮后可以先EnableWindow (hwndGetBtn, FALSE) ;把按钮变灰,避免重复点击。

字体通过
font = CreateFont(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, "microsoft yahei");
SendMessage(hwndUrlEdt,WM_SETFONT,(WPARAM)font,TRUE);
修改。

最后的字符集问题,核心函数是MultiByteToWideChar,搞了1天,utf-8网页还是乱码。下载了一个数年前使用的明小子用delphi写的注入工具domain web旁注工具,版本已经更新到了3.6,结果提交表单到一个utf-8网页也是乱码,我现在终于知道底层处理编码是多么蛋疼的一件事情。

wininet源代码获取例子 update:使用多线程,修正点击按钮后卡住的问题

#include <windows.h>
#include <wininet.h>
#include <process.h>
#pragma comment(lib, "wininet")

#define ID_URLEDITBOX 1
#define ID_GETBUTTON 2
#define ID_SHOWEDITBOX 3
static HWND hwndUrlEdt,hwndGetBtn,hwndShowEdt;

LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM) ;
int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance,
PSTR szCmdLine, int iCmdShow)
{
static TCHAR szAppName[] = TEXT ("BtnLook") ;
HWND hwnd ;
MSG msg ;
WNDCLASS wndclass ;

wndclass.style = CS_HREDRAW | CS_VREDRAW ;
wndclass.lpfnWndProc = WndProc ;
wndclass.cbClsExtra = 0 ;
wndclass.cbWndExtra = 0 ;
wndclass.hInstance = hInstance ;
wndclass.hIcon = LoadIcon (NULL, IDI_APPLICATION) ;
wndclass.hCursor = LoadCursor (NULL, IDC_ARROW) ;
wndclass.hbrBackground = (HBRUSH) GetStockObject (WHITE_BRUSH) ;
wndclass.lpszMenuName = NULL ;
wndclass.lpszClassName = szAppName ;

if (!RegisterClass (&wndclass))
{
MessageBox (NULL, TEXT ("This program requires Windows NT!"),
szAppName, MB_ICONERROR) ;
return 0 ;
}

hwnd = CreateWindow (szAppName, TEXT ("WinINet源代码获取"),
WS_OVERLAPPEDWINDOW,
GetSystemMetrics (SM_CXSCREEN) / 4, GetSystemMetrics (SM_CYSCREEN) / 4,
GetSystemMetrics (SM_CXSCREEN) / 2, GetSystemMetrics (SM_CYSCREEN) / 2,
NULL, NULL, hInstance, NULL) ;

ShowWindow (hwnd, iCmdShow) ;
UpdateWindow (hwnd) ;

while (GetMessage (&msg, NULL, 0, 0))
{
TranslateMessage (&msg) ;
DispatchMessage (&msg) ;
}
return msg.wParam ;
}
void Thread1 (PVOID pvoid)
{
HINTERNET hConnect,hRequest,hSession;
LPTSTR lpszHost;
char szBuffer[1024*1024/10];
TCHAR szStr[100];
DWORD dwSize=0;
DWORD dwDownloaded;
GetWindowText(hwndUrlEdt,szStr,sizeof(szStr)/sizeof(TCHAR));
hSession = InternetOpen(TEXT("testWinINet"), PRE_CONFIG_INTERNET_ACCESS, NULL, INTERNET_INVALID_PORT_NUMBER, 0);
hConnect = InternetOpenUrl(hSession,szStr,NULL,0,INTERNET_FLAG_DONT_CACHE,0);
ZeroMemory(szBuffer,sizeof(szBuffer));
while (InternetReadFile(hConnect,szBuffer,sizeof(szBuffer),&dwDownloaded))
{
if (0==dwDownloaded) break;
szBuffer[dwDownloaded]=0;
}
SetWindowText(hwndShowEdt,szBuffer);
ZeroMemory(szBuffer,sizeof(szBuffer));
_endthread () ;
}
LRESULT CALLBACK WndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
switch (message)
{
case WM_CREATE:
hwndUrlEdt = CreateWindow (TEXT ("EDIT"), NULL,
WS_CHILD | WS_VISIBLE | WS_BORDER | ES_LEFT | ES_AUTOHSCROLL ,
20,20,500,20, hwnd, (HMENU)ID_URLEDITBOX,
((LPCREATESTRUCT) lParam) -> hInstance, NULL) ;

hwndGetBtn = CreateWindow (TEXT ("BUTTON"), TEXT("GO"),
WS_CHILD | WS_VISIBLE | BS_DEFPUSHBUTTON ,
530,20,30,20, hwnd, (HMENU)ID_GETBUTTON,
((LPCREATESTRUCT) lParam) -> hInstance, NULL) ;

hwndShowEdt = CreateWindow (TEXT ("EDIT"), TEXT(""),
WS_CHILD | WS_VISIBLE | WS_BORDER | WS_HSCROLL | WS_VSCROLL | ES_AUTOHSCROLL | ES_AUTOVSCROLL | ES_MULTILINE ,
20,60,600,250, hwnd, (HMENU)ID_SHOWEDITBOX,
((LPCREATESTRUCT) lParam) -> hInstance, NULL) ;

return 0;
case WM_COMMAND:
if(LOWORD(wParam) == ID_GETBUTTON)
{
_beginthread (Thread1, 0, NULL) ;
}
return 0;
}
return DefWindowProc (hwnd, message, wParam, lParam) ;
}

多加入了#include ,project setting->code generation设置为multithreaded,HWND的声明放到了全局范围,便于Thread1()的访问。_beginthread (Thread1, 0, NULL) ;进入线程,_endthread ()结束线程 ;

visual studio的debug窗口在点击一次“GO”按钮后,会弹出消息:
The thread 0xDA4 has exited with code 0 (0x0).
The thread 0xE1C has exited with code 0 (0x0).
The thread 0xCC0 has exited with code 0 (0x0).
The thread 0xB90 has exited with code 0 (0x0).
The thread 0xBF8 has exited with code 0 (0x0).
The thread 0xF14 has exited with code 0 (0x0).
The thread 0xA58 has exited with code 0 (0x0).
The thread 0xDA8 has exited with code 0 (0x0).
当一个线程还没有结束的时候,可以多次重复点击“GO”按钮,新建新的线程。

wininet源代码获取例子

wininet源代码获取例子

#include <windows.h>
#include <wininet.h>
#pragma comment(lib, "wininet")

#define ID_URLEDITBOX 1
#define ID_GETBUTTON 2
#define ID_SHOWEDITBOX 3
LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM) ;
int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance,
PSTR szCmdLine, int iCmdShow)
{
static TCHAR szAppName[] = TEXT ("BtnLook") ;
HWND hwnd ;
MSG msg ;
WNDCLASS wndclass ;

wndclass.style = CS_HREDRAW | CS_VREDRAW ;
wndclass.lpfnWndProc = WndProc ;
wndclass.cbClsExtra = 0 ;
wndclass.cbWndExtra = 0 ;
wndclass.hInstance = hInstance ;
wndclass.hIcon = LoadIcon (NULL, IDI_APPLICATION) ;
wndclass.hCursor = LoadCursor (NULL, IDC_ARROW) ;
wndclass.hbrBackground = (HBRUSH) GetStockObject (WHITE_BRUSH) ;
wndclass.lpszMenuName = NULL ;
wndclass.lpszClassName = szAppName ;

if (!RegisterClass (&wndclass))
{
MessageBox (NULL, TEXT ("This program requires Windows NT!"),
szAppName, MB_ICONERROR) ;
return 0 ;
}

hwnd = CreateWindow (szAppName, TEXT ("WinINet源代码获取"),
WS_OVERLAPPEDWINDOW,
GetSystemMetrics (SM_CXSCREEN) / 4, GetSystemMetrics (SM_CYSCREEN) / 4,
GetSystemMetrics (SM_CXSCREEN) / 2, GetSystemMetrics (SM_CYSCREEN) / 2,
NULL, NULL, hInstance, NULL) ;

ShowWindow (hwnd, iCmdShow) ;
UpdateWindow (hwnd) ;

while (GetMessage (&msg, NULL, 0, 0))
{
TranslateMessage (&msg) ;
DispatchMessage (&msg) ;
}
return msg.wParam ;
}

LRESULT CALLBACK WndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
static HWND hwndUrlEdt,hwndGetBtn,hwndShowEdt;
HINTERNET hConnect,hRequest,hSession;
LPTSTR lpszHost;
char szBuffer[1024*1024/10];
TCHAR szStr[100];
DWORD dwSize=0;
DWORD dwDownloaded;
static LPCTSTR pAcceptType[] = { TEXT("Accept: */*"), NULL };

switch (message)
{
case WM_CREATE:
hwndUrlEdt = CreateWindow (TEXT ("EDIT"), NULL,
WS_CHILD | WS_VISIBLE | WS_BORDER | ES_LEFT | ES_AUTOHSCROLL ,
20,20,500,20, hwnd, (HMENU)ID_URLEDITBOX,
((LPCREATESTRUCT) lParam) -> hInstance, NULL) ;

hwndGetBtn = CreateWindow (TEXT ("BUTTON"), TEXT("GO"),
WS_CHILD | WS_VISIBLE | BS_DEFPUSHBUTTON ,
530,20,30,20, hwnd, (HMENU)ID_GETBUTTON,
((LPCREATESTRUCT) lParam) -> hInstance, NULL) ;

hwndShowEdt = CreateWindow (TEXT ("EDIT"), TEXT(""),
WS_CHILD | WS_VISIBLE | WS_BORDER | WS_HSCROLL | WS_VSCROLL | ES_AUTOHSCROLL | ES_AUTOVSCROLL | ES_MULTILINE ,
20,60,600,250, hwnd, (HMENU)ID_SHOWEDITBOX,
((LPCREATESTRUCT) lParam) -> hInstance, NULL) ;

return 0;
case WM_COMMAND:
if(LOWORD(wParam) == ID_GETBUTTON)
{
GetWindowText(hwndUrlEdt,szStr,sizeof(szStr)/sizeof(TCHAR));
hSession = InternetOpen(TEXT("testWinINet"), PRE_CONFIG_INTERNET_ACCESS, NULL, INTERNET_INVALID_PORT_NUMBER, 0);
hConnect = InternetOpenUrl(hSession,szStr,NULL,0,INTERNET_FLAG_DONT_CACHE,0);
ZeroMemory(szBuffer,sizeof(szBuffer));
while (InternetReadFile(hConnect,szBuffer,sizeof(szBuffer),&dwDownloaded))
{
if (0==dwDownloaded) break;
szBuffer[dwDownloaded]=0;
}
SetWindowText(hwndShowEdt,szBuffer);
ZeroMemory(szBuffer,sizeof(szBuffer));
}
return 0;
}
return DefWindowProc (hwnd, message, wParam, lParam) ;
}

程序缺点很多,1是点击“GO”之后,获取源代码的时候会卡住,因为没有用多线程,
2,存储源代码的内存空间受到了限制,csdn上面的人说受vc编译器堆栈大小的限制,超出了就stack overflow了。目前我只能使用临时文件存储的方法来解决。
3是子窗口都是使用代码写的,所以字体都是默认的fixedsys"system",中文字体十分难看。
4是字符串如果不是gb2312和纯英文的,其他字符串全部乱码,如上图就是一个最好的例证。

说了这么多缺点,说出来以后“深造”后再修正吧。嘎嘎~~