VC drops Winmain (the operating principle of Windows program and the implementation of VC ++)

xiaoxiao2021-03-06  47

WinMain (the operating principle of Windows program, and the implementation process of VC )

The operating system passes the change of the input device to our application with a message mechanism, and the role played by the operating system is the nerve end.

APP

System call API

OS

Output input

Hardware

The operating system is an operating system because it controls the hardware device, which can control the sound card to make a sound, can control the graphics card to draw a window, but it is not what we care about, these are the compilation What you have to do. The operating system can also obtain information from the input device, for example, the operating system can feel the movement of the mouse, and can also know where the mouse moves. For example, the operating system can feel the pressing of the keyboard, and know which key is pressed, all of which indicate that the operating system and the input and output devices have a relationship, as for how the operating system controls the input device and how to put the input device. To get your hand, we don't have to care, these are things that the person who writes the operating system or the people who write drivers should do. Since the application is running on the operating system, what is our concern about the application and the operating system. Just as the robot is able to walk, but the robot is going to take a few steps, walk in, these is the robot doesn't care, it just said that I have the ability to walk, as for how to send it to it, if we ask the robot to Walk 5 steps, machine talents can complete walking operations. Also for the operating system, the operating system can control the sound card to make sound, but what kind of sound is made, is it wonderful or sad, and how the application tells the operating system, we are writing When the C language is called by calling the function, the operating system can do something, the operating system can perform a variety of functions, which provide these functions to the application in the form of functions, the application notifies the operating system by calling these functions What do you do, the various functions of the operating system correspond to the corresponding functions, and the collection of these functions is called API. If you control the function of the robot, we call the Robot API, like the function of operating our system like Java, we call the Java API, where the API is not related to the Windows API.

Each application has a queue, called a message queue, what is a queue? It is actually a buffer (which is a array of definitions. How big is the array, how big is the buffer), then you can save the number, others You can take it from the inside. Pick up, you are the number you first deposited. Just like the paging system of the table, a paging information is coming, and Miss said that the information will be handed over to the transmitter. If there are many paging requests in one second, the transmitter is likely I have been busy, in order not to lose information, we will prepare a big buffer, there are 100 laptome, let a paging request put one in this buffer, then taken from the transmitter from inside, always Put it first, put it in the inside, take it from the inside, although it may be some latency, but we guarantee that the request is not lost, this is also reflected in our operating system, we have implemented it. Close the window of the window, maybe the window did not shut down immediately, but after a while or closed the window, this is also the queue application, the queue is good to buy rice than the queue in the food hall, buy the rice first, first After buying a meal, I left, and the second at this time became the first, and moved in turn, this is the characteristics of the queue advanced first. Our message queue here is a message, describing this message to use structural (MSG) because a message contains information about some auxiliary instructions messages. Here, MSG is explained, each message is associated with the window (that is, a message must be received by a window), because the message has a goal, so that the message can reach the target window, and this target window It should have focus, such as starting two Notepad programs, when pressing the keyboard, the message can only reach the window with focus. The second parameter is an integer that identifies the message, and the third fourth parameter is supplemented with the message. If there is a keyboard message, which key is all in this information, which is included in these two parameters. The fifth parameter is the time to issue a message, and the last parameter is where the mouse is located. View the prototypes such as LPARAM with Go to Definition. To explain the handle, we have to contact your handle (Handle). In fact, the handle is a void *, we can use Go to Definition to view Handle, any Windows entity in Windows (such as windows, bitmaps, brushes, menus, etc.) to account for a piece of space in memory, this space should There is an address that in order to distinguish the address of the previous normal variable, we use Handle to identify the Windows entity, Handle saves the address of the Windows entity so that the Windows entity is operated, as in the future, which window we want to maximize , I must tell the operating system I have to operate the window, then I handed a handle to the operating system. What we saw hwnd, hmenu, Hbursh is actually Handle. Our program is to take a message from the message queue, and the message is taken out to provide the user with an MSG structure, and then processes the message.

When the message is handled, we call the Windows API function, such as closing the window exit program, when we point the shutdown button, I received WM_CLOSE, then call the Windows API function to destroy the window when this message is called, when the operating system I really report a message after destroying the window, I will return to wait for your answer - Wm_Destroy, this time we can do something, you can really quit the app, you can do something else, this process is like a Closed loop, constantly taking a message from the message queue, then your code calls the API function to respond according to the message, such a loop process, so someone describes the Windows program without tail. We must write a Windows program to first understand the C language, then we have to know what meanings for each message, you can't receive a keyboard to press the message to do the mouse movement process, such as others saying foot pain, you can't take a headache. Finally, when we receive a message to try to do something, we must know which API function can implement this feature. However, there are more than 3,000 API functions, we just know 20% is enough, because these 20% of the function can do 80%. Below we start writing a Windows program: First we have to generate a window, with this window user to make a series of operations. Like the production of cars, we have to do some preparations before generating a car. In fact, the production of cars is very easy, it is difficult to design the car. If you design the car, you can produce a batch production. Designing a car to specify the color of the car, the car's engine, chassis, gearbox, etc. Also generates a window, we must also design, such as what the window is background, what is the window of the window, what is the icon of the window, what is the window of the window. After designing, we can produce bulk according to the design drawings. The design of the window is accomplished by a structure: WNDCLASS, the first parameter is STYLE, and this parameter corresponds to only one bit of 1 (one corresponding binary of hexadecimal). What is the benefit of this? For example, the first bit is the maximum button, the second is the minimization button, the third is closed button, if we want the window to maximize and minimize buttons, we set the first and second digits to 1 And the third bit is 0, if we want to close the closing button, we will put the style parameter or the integer of the closed button.

Two parameters in Style are CS_HREDRAW and CS_VREDRAW, when we change the size of the window (minimize, maximize, overwate the same), the graphics card will re-give us the window drawn (the window is painted), at this time It turned out that the things painted on the window were rushed away. If you don't do this, our size of our window cannot change. Here we specify that two parameters are specified that the graphics card needs to be required when the window level and vertical direction changes. Dress the window, the graphics card will be redrawn with the background color of the window you define when the window is drawn. This is like we have to spray the car every time you go, if we don't specify that these two parameters are said that I don't re-paint, I can use it. Take a demo as an example in the window. Cbclsextra, CbWndextra is the two supplemental parameters, which is used when the parameters of the window are not enough.

Hicon is the handle of the icon, which can be loaded through the API function Loadicon, and makeintResource is a macro that converts an integer to string. Note that the string is an address that identifies the first address of a character array constant. Word is a Unsigned Short, DWORD is a unsigned long. If you need a custom icon, the first parameter should be Hinstance, the second parameter is makeintResource (IDi_ICON1). Edit the icon in the VC and save, # include "resource.h" Adds Script1.rc to the project. Hcursor is the handle of the mouse pointer. You can load it through the API function loadCursor. The IDC_HAND in CURSOR is defined in the header file of Win2000, to install Win2000 SDK.

HBRBACKGROUND is a handle of a window background brush, and NULL means no brush. Get it through the API function getStockObject. Note that the concept of a near pointer and a far pointer is to contact the product of the 16-bit operating system, which is used to identify the management scope of the pointer, and there is no meaning in the 32-bit operating system, we can find that they are defined. Empty. Here, the return value of GetStockObject is to convert. (Set an arbitrary color?) Hinstance is the handle of the application instance. I started, the application is installed in memory, becoming an instance (because the application can start multiple, we manage and distinguish each application instance handle), after the operating system wants to control My app, I must pass the handle of the application to the operating system. We call it instance handle. All of us should belong to an application instance, so we are here to specify an instance handle of the application. This instance handle is assigned to us by the operating system. The application has an inlet function, which is the main function in DOS. It is a WinMain function in Windows. We find that the application's instance handle is transmitted to us in the Winmain function. HPREVINSTANCE is an instance handle of the previous application. Through this parameter we can control one application can only start one copy. Of course, we are here because it is unable to implement a simple implementation of the program. (WinMain function is the operating system call, so the parameters of Winmain are assigned the operating system.) LPSZMenuname Note The menu is not a window. Use Spy to view. lpszclassname is the name of the window type. Such as Fukang 988.

After the window is designed, we have to register the window registerclass and register to produce this window, otherwise the operating system does not know what kind of window you want to produce. Then we call CREATEWINDOW to generate a window. There is a window style parameter, WS_OVERLAPPEDWINDOW is a packaging style. If you want to remove a feature, you will reject the descending style, then the result is in the same as the packaging style. WM_DISABLE is unavailable in the window. If we don't have ShowWindow, you can't see the window. At this time, we add a space in your code, then delete spaces, the compiler discovers that the code changes will help us recompile, then report a Fatal Error, because the application After the program is started, the new will not overwrite the original. Note that there is no window that does not mean that the program is not running, the window is a window, the program is a program. The window is just a small part generated by the program. So after creating a window, we have to display the windows in the memory, but if you specify WS_Visible in the style property, you don't have to use ShowWindow. There is often UpdateWindow on the book, but we can use it here.

With a window user, you can do anything, and we have to process these operations, calling getMessage to get the message. Here we define a structure: MSG to save these messages. The first parameter of GetMessage is an MSG address. If it is not the address, we can't get the message. The second parameter is a handle of a window, since the message is associated with one window. If we fill this parameter into NULL, it means to take all messages belonging to this application, including messages of all windows in the application. Third, the four parameters are the scope of the message to take (the message is an integer), this parameter can help you filter some messages. We have to handle the news after handling the news and handle it. When is a loop stop? When getMessage takes a WM_QUIT message, it will return 0, and only this message allows GetMessage to return 0, so the program can exit. It should be noted here that if the second parameter of GetMessage is filled with the handle of this window, it will not receive the WM_Quit message so that the program will not pass, because wm_quit is a special message, the message does not address any windows Union, belongs to the application. So our second parameter is to fill up to NULL. TranslateMessage is a function that converts WM_KEYDOWN and WM_KEYUP to WM_CHAR, because sometimes we want to react with which key is pressed, so we only need WM_CHAR to determine relatively simple. When these three messages exist, first take WM_CHAR, then take WM_KeyDown, and finally WM_Keyup. DispatchMessage is a function of dispatch and forwarding messages.

So our program is a function of processing messages. lpfnWndProc requires a pointer to a function, this function is a callback function: As long as the window receives the message, you will find this regular callback function to deal with. Just as we bought a car, in the instructions of the car, I specified the car's maintenance location. When your car went to these designated locations to repair. Introduce the Sprintf and Messagebox functions. Callback indicates that the call mode is called by the call mode of PASCAL (_stdcall, such as Delphi), otherwise it is called according to the C language call mode (_CDECL). This is mainly to solve a general problem. __stdcall and __cdecl are two different function call habits, define the transmission order of the parameters, stack clearance, etc. For more information on their details, see MSDN. Since the API functions of those variable parameters are except for the API function of variable parameters, it is __stdcall habits. Since the VC program default compilation option is __cdecl, call these __stdcall habits in VC , you must add the __stdcall modifier when declaring these functions, in order to use the __stdcall habit of the function of the function. We have such experiences, in the DLL written in Delphi (the default compilation option is __stdcall), when it is called in VC , it always causes the program to crash, plus __stdcall modification in the prototype declaration of the function. The problem is solved. The callback function must also be __stdcall call habits, here is identified by Callback, otherwise, in the NT4.0 environment, the program will crash, but Win98 and Win2000 have no phenomenon. Demonstration code, including the response to the drawing and load icon, the default Windows message processing. There is only one message queue in the system in the 16-bit system, so the system must wait until the current task can send the next message to the corresponding program. If a program falls into a dead loop or the system will not be able to operate Control. This multitasking system is also called a multi-tasking system. Windows3.x is this system. Each running program in the 32-bit system will have a message queue, so the system can be converted in multiple message queues without waiting for the current program to complete message processing. This multi-tasking system is called a predetermined multitasking system. Windows95 / NT is this system

Note: Do not use the definition of the Winmain function in the API Reference, because w in lpwstr lpcmdline represents a wide byte, that is, two bytes, it is no problem, but because we use pirated, here is a problem.

The 16-bit operating system and 32-bit operating system, their fundamental difference is that the 16-bit operating system only reads only two lattice data, and the 32-bit operating system can read 4 landsters is 4 bytes. Because each byte is 8-bit binary, 4 bytes are 32 bits, so the 32-bit operating system is called. Starting from Win98, all Windows operating systems are completely 32-bit (Windows95 is not a pure 32-bit operating system because there is a satisfactory speed and good compatibility with old 16-bit programs, its core itself It is a 16-bit and 32-bit mixing. And starting from 386, all CPUs are 32 bits, which means that the CPU handles 4 bytes of data. Therefore, in the program, you'd better try to define the variable as long plastic, because 32-bit variables are the fastest, and is the fastest. Unless you are using 286 computers, or DOS operating systems.

#include #include "resource.h" #include int x, y; lresult callback myproc (hwnd hwnd, // handle to window uint umsg, // message identifier wparam wparam, // First Message Parameter LParam LParam // Second Message Parameter) {Switch (UMSG) {Case WM_Close: IF (iDok == MessageBox (hwnd, "Do you really want to quit?", "System Tips", MB_OKCANCEL | MB_ICONInInformation)) {DestroyWindow (hwnd);} Break; Case WM_DESTROY: PostquitMessage (0); Break; Default: Return DefWindowProc (HWND, UMSG, WPARAM, LPARAM); Case WM_CHAR: {Char BUF [100]; sprintf (buf, "% d ", wParam); MessageBox (hwnd, buf," show ", mb_ok); break;} case wm_mousemove: {// Here, the case is to prevent the replica definition of BUF, the second is to solve similar Int X = loword (lparam); defined compiler paste the error. HDC HDC = GETDC (HWND); Char BUF [100]; Sprintf (BUF, "X =% D, Y =% D", X, Y); SetTextColor (HDC, RGB (255, 255)); Textout (HDC, 0 , BUF, STRLEN (BUF)); // InvalidateRect (HWND, NULL, TRUE); // PostMessage (hwnd, wm_paint, 0, 0); // SendMessage (hwnd, wm_paint, 0, 0); x = Loword (LPARAM); Y = HiWord (LPARAM); MEMSET (BUF, 0,100); Sprintf (buf, "x =% D, Y =% D", x, y); setTextColor (HDC, RGB (0, 0, 0, 0); TextOut (HDC, 0, 0, BUF, Strlen); ReleaseDC (HWnd, HDC); Break;}} Return 1;} int WinApi Winmain (Hinstance Hinstance, // Handle To Current Instance Hinstance Hprevinstance , // handle to previous instance lpstr lpcmdline, // command line int ncmdshow // show state) {WNDCLASS WNDCLASS; WNDCLASS.CBCLSEXTRA = NULL; WNDCLASS.CBWNDEXTRA = NULL;

wndclass.hbrBackground = (HBRUSH) GetStockObject (GRAY_BRUSH); //wndclass.hCursor=LoadCursor(NULL,IDC_HAND); wndclass.hCursor = LoadCursor (hInstance, MAKEINTRESOURCE (IDC_POINTER)); // wndclass.hIcon = LoadIcon (NULL, IDI_ERROR ); Wndclass.hicon = loading (Hinstance, MakeintResource (IDi_icon1));

wndclass.hInstance = hInstance; wndclass.lpfnWndProc = myproc; wndclass.lpszClassName = "mywnd"; wndclass.lpszMenuName = NULL; wndclass.style = CS_HREDRAW; RegisterClass (& wndclass); HWND hwnd = CreateWindow ( "mywnd", "window test" , WS_OVERLAPPEDWINDOW, 100,100,400,400, NULL, NULL, hInstance, NULL); ShowWindow (hwnd, SW_SHOW); MSG msg; while (GetMessage (& msg, NULL, NULL, NULL)) {TranslateMessage (& msg); DispatchMessage (& msg);} return 1;}

转载请注明原文地址:https://www.9cbs.com/read-79624.html

New Post(0)