Thread: Problems with standard WIN32 Code

  1. #1
    Registered User
    Join Date
    Aug 2004
    Posts
    9

    Problems with standard WIN32 Code

    Code:
    /*
    
    Questions go here:
    
    1. is a reference another word for handle?
    2. research TCHAR datatype.
    3. Difference between WNDCLASSEX and WNDCLASS?
       WNDCLASSEX is the newer one. There are more differences but for our purposes
       lets assume that the newer one is the "better one". 
    */
    
    //always necessary to include windows.h for making windowed programs
    
    #include <windows.h>
    #include "stdafx.h"
    #include <stdio.h>
    
    //function prototypes
    
    ATOM produceAndregisterClass();
    
    int createAndShowWindow();
    
    LRESULT CALLBACK WindowProcedure
        (HWND hwnd, unsigned int message, WPARAM wParam, LPARAM lParam);
    
    //global variables follow
    
    HINSTANCE hinst; //a reference to the application instance
    
    HWND mainWindow; //this reference will eventually point to the main Window,
    				 //once instantiated
    
    TCHAR className[] = "myWindow"; //the name of the "class" which we will register
    
    /* Main Steps 
    
    1. Define a window "class". Populate a WND Class Ex structure.
    2. Register the window class. Pass the WNDCLASSEX struct pointer to RegisterClassEx.
    3. Provide a windows procedure. This is the function which will deal with the user's
       interaction with the window.
    4. Create and show the window.
    5. Put application into a "message loop". 
    
    */
    
    //entry point into a windowed application is main 
    
    int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
    {
    
    	printf("in main function");
    
    	if ( produceAndregisterClass() == 0 )
    		return -1; //producing and registering class did not work for whatever reason
    				   //thus we will exit early.
    
    	if ( createAndShowWindow () == 0 )
    		return -1; //again, something went wrong so exit early.
    
    	//message loop goes here
    
    	BOOL bRet;
    
    	MSG msg;
    
    	while( (bRet = GetMessage( &msg, NULL, 0, 0 )) != 0)
    	{ 
    		if (bRet == -1)
    		{
            return -1;
    		}
        else
        {
            TranslateMessage(&msg); 
            DispatchMessage(&msg); 
        }
    }
    
    	
    	return 0;
    }
    
    ATOM produceAndregisterClass()
    {
    
    	//first let us populate a WNDCLASSEX struct. 
    	//this struct contains all the details of windows we will display
    
    	WNDCLASSEX windowClass;
    
    	//set the size. when dealing with WNDCLASSEX structures, the RHS of the
    	//code is always the same when setting the cbSize member
    
    	windowClass.cbSize = sizeof(WNDCLASSEX); 
    
    	//a style helps determine the window's behavior. these are enumerated
    	//at the MSDN website.
    	//it is my understanding that using the | operator allows you to specify a combination of styles
    	//I've set it to redraw the window whenever the height or width is adjusted.
    	
    	windowClass.style = CS_HREDRAW | CS_VREDRAW;
    
    	//pointer to the programmer defined window procedure to deal with the user interaction with window
    
    	windowClass.lpfnWndProc = (WNDPROC) WindowProcedure; 
    
    	//number of extra bytes to allocate to structure. i'm saying 0 because this is a simple window,
    	//although it remains to be seen exactly how you work how much more you need if the window was
    	//"complex".
    
    	windowClass.cbClsExtra = 0;
    
    	//assign the reference to the application instance
    
    	windowClass.hInstance = hinst;
    
    	//assignment of an icon. NULL means system provides default.
    
    	windowClass.hIcon = 0;
    
    	//assignment of cursor. NULL means default.
    
    	windowClass.hCursor = 0;
    
    	//background colour assignment, this can be a handle to a data type called HBRUSH or
    	//alternatively it can be a specified colour (if the latter must cast to HBRUSH).
    	//always must add 1 to chosen colour.
    
    	windowClass.hbrBackground = (HBRUSH) (COLOR_WINDOW + 1);
    
    	//this should be a string pointing to a resource that specifies a menu. 
    	//but a NULL value means no menu, which is what we want for this simple window.
    
    	windowClass.lpszMenuName = 0;
    
    	//assign the class name (which we've stored in a global variable)
    
    	windowClass.lpszClassName = className;
    
        //i guess this icon member is for the icon your app should have when it is listed
    	//in a directory. don't really know but its not that important. we'll just use NULL.
    
    	windowClass.hIconSm = 0; 
    
    	//The structure is filled and now we must register it.
    
    	return RegisterClassEx(&windowClass);
    }
    
    //call this function to create and display window only after registering the class.
    
    int createAndShowWindow()
    {
    
    mainWindow = CreateWindowEx(
    							WS_EX_APPWINDOW,//window behavior
    							className, 
    							"Test Window", //title bar string
    							WS_CAPTION, //style
    							CW_USEDEFAULT, //x position
    							CW_USEDEFAULT, //y position
    							CW_USEDEFAULT, //width
    							CW_USEDEFAULT, //height
    							0, //handle to parent window, but there is no parent so...?
    							0, //menu handle. null means use the one specified in class
    							hinst, //handle instance
    							0 //lparam value...not really sure what its for
    							);
    
    if ( !mainWindow ) return 0;
    
    else return 1;
    
    }
    
    //this function always has this signature and it deals with the user interaction
    //messages are passed from the operating system to this function which processes 
    //the messages
    
    LRESULT CALLBACK WindowProcedure
        (HWND hwnd, unsigned int message, WPARAM wParam, LPARAM lParam)
    
    {
    
    //the window will do nothing, except vanish when we ask it to
    //if there is a message we have not dealt with in the case statement
    //we use the defaultwindowprocedure called DefWindowPoc.
    
    	switch (message)
        {
            case WM_DESTROY:
                PostQuitMessage (0);
                return 0;
    
        }
        return DefWindowProc (hwnd, message, wParam, lParam );
    
    }
    i'm using visual c++ 6.0 and i have made sure i chose win32 project (Not console app).

    when i run the executable nothing at all happens. not even the very first line of the main function which is
    Code:
    printf("in main function");
    i must be doing something trivial but for the life of me i can't see what.

    any help would be appreciated. thanks.

  2. #2
    erstwhile
    Join Date
    Jan 2002
    Posts
    2,227
    Some compilers create a console in addition to a 'window' (eg. borland) unless you specify otherwise. If msvc6 is capable of this then I don't know what compiler switch(es) enable it. Accordingly, the output of printf or other functions that use stdin,stdout or stderr will not normally be available to a windows application generated by msvc6.

    What you can do, however, is step through the code with the debugger and check the return values of your 'produceAndregisterClass' and 'createAndShowWindow' functions to ensure that both window registration and window creation are occurring.

    You might also want to ensure your window will actually be visible after it's been created either by giving it the WS_VISIBLE window style or by the more traditional approach of:
    Code:
    ShowWindow(mainWindow,nCmdShow);
    UpdateWindow(hwnd);
    after a successful return from CreateWindow or CreateWindowEx.

    You might also want to compare your code with the code that msvc6 will optionally auto-generate for you when you create a win32 exe application.

    BTW, this question should have been directed to the windows board.
    CProgramming FAQ
    Caution: this person may be a carrier of the misinformation virus.

  3. #3
    Registered User
    Join Date
    Aug 2004
    Posts
    9
    Quote Originally Posted by Ken Fitlike
    Some compilers create a console in addition to a 'window' (eg. borland) unless you specify otherwise. If msvc6 is capable of this then I don't know what compiler switch(es) enable it. Accordingly, the output of printf or other functions that use stdin,stdout or stderr will not normally be available to a windows application generated by msvc6.

    What you can do, however, is step through the code with the debugger and check the return values of your 'produceAndregisterClass' and 'createAndShowWindow' functions to ensure that both window registration and window creation are occurring.

    You might also want to ensure your window will actually be visible after it's been created either by giving it the WS_VISIBLE window style or by the more traditional approach of:
    Code:
    ShowWindow(mainWindow,nCmdShow);
    UpdateWindow(hwnd);
    after a successful return from CreateWindow or CreateWindowEx.

    You might also want to compare your code with the code that msvc6 will optionally auto-generate for you when you create a win32 exe application.

    BTW, this question should have been directed to the windows board.

    thank you for your suggestions, i will give them a try.

    sorry about posting this in the wrong forum!

  4. #4
    Registered User
    Join Date
    Aug 2004
    Posts
    9
    i added in the show and update lines then ran the debugger. after pressing "go", i immediately got the following info

    Loaded 'C:\WINDOWS\SYSTEM\ADVAPI32.DLL', no matching symbolic information found.
    Loaded 'C:\WINDOWS\SYSTEM\GDI32.DLL', no matching symbolic information found.
    Loaded 'C:\WINDOWS\SYSTEM\KERNEL32.DLL', no matching symbolic information found.
    Loaded 'C:\WINDOWS\SYSTEM\USER32.DLL', no matching symbolic information found.
    Loaded 'C:\Program Files\AIM95\idlemon.dll', no matching symbolic information found.
    Loaded 'C:\Program Files\WinPortrait\winphook.dll', no matching symbolic information found.
    The thread 0xED263F31 has exited with code -1 (0xFFFFFFFF).
    The program 'C:\WaveSim\WinTest\Debug\WinTest.exe' has exited with code -1 (0xFFFFFFFF).

    i'm not really sure what any of that means.

    i also checked the template code given by visual c++ -- that worked ok and though I think I saw some differences I couldn't quite work out why my code failed to work.

  5. #5
    erstwhile
    Join Date
    Jan 2002
    Posts
    2,227
    Rebuild your application as 'Debug' (change the project configuration from 'Release' to 'Debug' with the configuration manager which I think you can get from either the 'project' or 'build' menu).
    Last edited by Ken Fitlike; 08-23-2004 at 02:39 PM.
    CProgramming FAQ
    Caution: this person may be a carrier of the misinformation virus.

  6. #6
    Yes, my avatar is stolen anonytmouse's Avatar
    Join Date
    Dec 2002
    Posts
    2,544
    Code:
    HINSTANCE hinst; //a reference to the application instance
    As far as I can see, hinst remains 0 throughout your program. Is that a problem?
    --
    It is a good idea to always zero out a structure before use. This means, that if you forget to assign a value to one of the structure members, as you have done, it will remain zero and it may work.
    Code:
    	WNDCLASSEX windowClass = { 0 };

  7. #7
    Registered User
    Join Date
    Aug 2004
    Posts
    9
    Quote Originally Posted by anonytmouse
    Code:
    HINSTANCE hinst; //a reference to the application instance
    As far as I can see, hinst remains 0 throughout your program. Is that a problem?
    --
    It is a good idea to always zero out a structure before use. This means, that if you forget to assign a value to one of the structure members, as you have done, it will remain zero and it may work.
    Code:
    	WNDCLASSEX windowClass = { 0 };

    hi, yes i've changed the code now so that in the main function the first thing i do is assign the global hinst variable to the hinstance parameter passed to the main function. i.e.

    Code:
    int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
    {
    
    	hinst = hInstance;
    
    ....
    }
    and then i proceed to produce and register the window class. the effect is still the same though.

    the "createAndShowWindow" function returns the value 0, which my program interprets as failure and exits early. i have inferred this by commenting out the call to createAndShowWindow in main and observing that program remains in an infinite loop (the message loop that is executed immediately after the createAndShowWindow).

    but for the life of me I can't see exactly what is wrong with the code in that function.

    edit: you mention i have forgotten to assign a value to one of the member's of the windowClass strut..which one?

    second edit: yes it works! i had forgotten to give a value to "cbWndExtra". damn...that had me puzzled for an entire day. programming is fun but when it gets like that you almost want to throw the monitor out the window.

    any, thanks people!
    Last edited by BruceLeroy; 08-24-2004 at 09:42 AM.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Win32 API GUI problems
    By Cha0sBG in forum Windows Programming
    Replies: 7
    Last Post: 06-05-2009, 04:35 PM
  2. Problems with code
    By hollyjaye in forum C Programming
    Replies: 11
    Last Post: 03-29-2007, 05:42 AM
  3. lcc win32 compiler download problems
    By GanglyLamb in forum A Brief History of Cprogramming.com
    Replies: 5
    Last Post: 08-01-2004, 07:39 PM
  4. Using standard C fscanf function with win32 save dialog
    By korbitz in forum Windows Programming
    Replies: 1
    Last Post: 04-08-2004, 03:31 PM
  5. More Array code problems
    By Masa in forum C++ Programming
    Replies: 1
    Last Post: 04-08-2004, 02:04 AM