WinAPI window doesn't appear
And I can't figure out why. My code:
#include <windows.h>
#include <commctrl.h>
#include <cstdio>
#include <stdarg.h>
#include <string>
#include <cmath>
#include <vector>
#include "resources.hpp"
using std::string;
using std::vector;
struct undostruct{
/* add later */};
char buffer[2048];
HWND statusbar;
HINSTANCE hinst;
vector<undostruct> undo;
void show_error(const char* format,...){
va_list args;
va_start(args,format);
vsprintf(buffer,format,args);
va_end(args);
MessageBox(NULL,buffer,"ERROR",MB_OK);}
HWND create_tooltip(HWND parent,char* tip,unsigned uid,unsigned extraflags=0){
HWND tt=CreateWindowEx(WS_EX_TOPMOST,TOOLTIPS_CLASS,NULL,WS_POPUP|TTS_NOPREFIX|TTS_ALWAYSTIP,0,0,0,0,parent,NULL,NULL,NULL);
SetWindowPos(tt,HWND_TOPMOST,0,0,0,0,SWP_NOMOVE|SWP_NOSIZE|SWP_NOACTIVATE);
TOOLINFO ti;
ti.cbSize=sizeof(TOOLINFO);
ti.uFlags=TTF_SUBCLASS|extraflags;
ti.hwnd=parent;
ti.hinst=NULL;
ti.uId=uid;
ti.lpszText=tip;
GetClientRect(parent,&ti.rect);
SendMessage(tt,TTM_ADDTOOL,0,(LPARAM)(LPTOOLINFO)&ti);
return tt;}
LRESULT CALLBACK WndProc(HWND,UINT,WPARAM,LPARAM);
class Font{
private:
HFONT hfont;
public:
Font(const char* fname){
hfont=CreateFont(0,0,0,0,FW_NORMAL,false,false,false,DEFAULT_CHARSET,OUT_DEFAULT_PRECIS,CLIP_DEFAULT_PRECIS,DEFAULT_QUALITY,DEFAULT_PITCH,fname);}
~Font(){
DeleteObject(hfont);}
operator HFONT(){
return hfont;}}courier("Courier New");
bool get_filename(char* fname,int len,HWND hwnd,bool save){
OPENFILENAME ofn;
ZeroMemory(&ofn,sizeof(OPENFILENAME));
ofn.lStructSize=sizeof(OPENFILENAME);
ofn.hwndOwner=hwnd;
ofn.lpstrFilter="Text Files (*.txt)\0*.txt\0All Files (*.*)\0*.*\0\0";
ofn.lpstrFile=fname;
ofn.nMaxFile=len;
ofn.lpstrTitle="Text Editor";
ofn.Flags=OFN_FILEMUSTEXIST|OFN_HIDEREADONLY;
if(save){
return GetSaveFileName(&ofn);}
else{
return GetOpenFileName(&ofn);}}
int WINAPI WinMain(HINSTANCE hprev,HINSTANCE hInst,LPSTR cmdline,int cmdshow){
WNDCLASSEX wcex;
//HACCEL haccel=LoadAccelerators(hInst,MAKEINTRESOURCE(ACCELS));
HWND hwnd;
MSG msg;
hinst=hInst;
//Register the window
wcex.cbSize=sizeof(WNDCLASSEX);
wcex.style=CS_HREDRAW|CS_VREDRAW;
wcex.lpfnWndProc=WndProc;
wcex.cbClsExtra=0;
wcex.cbWndExtra=0;
wcex.hInstance=hinst;
wcex.hIcon=NULL;
wcex.hCursor=NULL;
wcex.hbrBackground=(HBRUSH)(COLOR_WINDOW+1);
wcex.lpszMenuName=MAKEINTRESOURCE(MAINMENU);
wcex.lpszClassName="ImageEditor";
wcex.hIconSm=NULL;
if(!RegisterClassEx(&wcex)){
show_error("Error %i: Failed to register the window.",GetLastError());
return -1;}
//Create the window
hwnd=CreateWindow("ImageEditor","Image Editor",WS_VISIBLE|WS_OVERLAPPEDWINDOW,CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,NULL,NULL,hinst,NULL);
if(!hwnd){
show_error("Error %i: Failed to create the window.",GetLastError());
return -2;}
//Show/Update the window
ShowWindow(hwnd,cmdshow);
UpdateWindow(hwnd);
//Initialize common controls
/*INITCOMMONCONTROLSEX iccex;
i开发者_StackOverflowccex.dwICC=ICC_WIN95_CLASSES;
iccex.dwSize=sizeof(INITCOMMONCONTROLSEX);
InitCommonControlsEx(&iccex);*/
//Go into the main program loop
while(GetMessage(&msg,NULL,0,0)){
//if(!TranslateAccelerator(hwnd,haccel,&msg)){
TranslateMessage(&msg);
DispatchMessage(&msg);}//}
return msg.wParam;}
LRESULT CALLBACK WndProc(HWND hwnd,UINT msg,WPARAM wparam,LPARAM lparam){
static int sizes[]={260,330,420,520};
switch(msg){
case WM_CREATE:
statusbar=CreateWindow(STATUSCLASSNAME,"",WS_CHILD|WS_BORDER|WS_VISIBLE,-100,-100,10,10,hwnd,NULL,hinst,NULL);
if(!statusbar){
show_error("Error %i: Failed to create the statusbar.",GetLastError());}
//Description|Characters|Size|Lines|Line|Column
SendMessage(statusbar,SB_SETPARTS,sizeof(sizes),(LPARAM)sizes);
break;
case WM_QUIT:
DestroyWindow(hwnd);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
case WM_COMMAND:
//switch(LOWORD(wparam)){}
//break;
default:
return DefWindowProc(hwnd,msg,wparam,lparam);}
return 0;}
Also, my compiler doesn't recognize INITCOMMONCONTROLSEX when it should, which is commented out near the end of WinMain.
The most likely bug in this code is that you need to run InitCommonControls BEFORE creating a window. And forget that InitCommonControlsEx() code, you'll be better with a plain old InitCommonControls.
Remember to check every function's return value and use GetLastError().
Also, you're trying to reinvent the wheel and instead of rolling out your own window creating procedure I suggest you to take a look at how others do it, or even use WTL, it's not that difficult.
精彩评论