[C con Clase] Como trabaja InsertarMenu en WIN API 32

Luis Gutierrez Gomez gutierrezgl en hotmail.com
Jue Dic 22 18:12:51 CET 2011



Tengo el siguiente programa:

 

#include <windows.h>

#define CM_PRUEBA   100
#define CM_SALIR    101
#define CM_SOLUCION    102

/*  Declaración del procedimiento de ventana  */
LRESULT CALLBACK WindowProcedure (HWND, UINT, WPARAM, LPARAM);
void InsertarMenu( HWND );

int WINAPI WinMain (HINSTANCE hThisInstance,
                    HINSTANCE hPrevInstance,
                    LPSTR lpszArgument,
                    int nFunsterStil)
{
    HWND hwnd;               /* Manipulador de ventana */
    MSG mensaje;             /* Mensajes recibidos por la aplicación */
    WNDCLASSEX wincl;        /* Estructura de datos para la clase de ventana */

    /* Estructura de la ventana */
    wincl.hInstance = hThisInstance;
    wincl.lpszClassName = "NUESTRA_CLASE";
    wincl.lpfnWndProc = WindowProcedure;      /* Esta función es invocada por Windows */
    wincl.style = CS_DBLCLKS;                 /* Captura los doble-clicks */
    wincl.cbSize = sizeof (WNDCLASSEX);

    /* Usar icono y puntero por defector */
    wincl.hIcon = LoadIcon (NULL, IDI_APPLICATION);
    wincl.hIconSm = LoadIcon (NULL, IDI_APPLICATION);
    wincl.hCursor = LoadCursor (NULL, IDC_ARROW);
    wincl.lpszMenuName = NULL;                 /* Sin menú */
    wincl.cbClsExtra = 0;                      /* Sin información adicional para la */
    wincl.cbWndExtra = 0;                      /* clase o la ventana */
    /* Usar el color de fondo por defecto para la ventana */
    wincl.hbrBackground = GetSysColorBrush (COLOR_ACTIVEBORDER+1);/*(COLOR_BACKGROUND);

    /* Registrar la clase de ventana, si falla, salir del programa */
    if(!RegisterClassEx(&wincl)) return 0;

    /* La clase está registrada, crear la ventana */
    hwnd = CreateWindowEx(
           0,                   /* Posibilidades de variación */
           "NUESTRA_CLASE",     /* Nombre de la clase */
           "Ejemplo001",       /* Texto del título */
           WS_OVERLAPPEDWINDOW, /* Tipo por defecto */
           CW_USEDEFAULT,       /* Windows decide la posición */
           CW_USEDEFAULT,       /* donde se coloca la ventana */
           544,                 /* Ancho */
           375,                 /* Alto en pixels */
           HWND_DESKTOP,        /* La ventana es hija del escritorio */
           NULL,                /* Sin menú */
           hThisInstance,       /* Manipulador de instancia */
           NULL                 /* No hay datos de creación de ventana */
    );

    /* Mostrar la ventana */

    /*ACA ESTA LA CONSULTA: Si en este punto una sola vez se inserta el Menu con InsertarMenu()

, y luego se pasa esta parte y se llega

al bucle WHILE y se supone que el programa permanece alli esperando un "mensaje", que en este caso el mensaje posible

es WM_DESTROY. Cuando yo ejecuto el programa, me aparece la ventana con el menú "Principal"y cuando le doy click

al menú me aparece el menu desplegado, ¿ Como hace el programa para ejecutar la orden de desplegar el menú, si se supone

que en ese momento el programa esta en WHILE, y alli no se colocó ninguna otra opción de mensaje ( para que abra el Menú ) ?*/


    InsertarMenu(hwnd);
    ShowWindow(hwnd, SW_SHOWDEFAULT);

    /* Bucle de mensajes, se ejecuta hasta que haya error o GetMessage devuelva FALSE */
    

 

while(TRUE == GetMessage(&mensaje, NULL, 0, 0))
    {
        /* Traducir mensajes de teclas virtuales a mensajes de caracteres */
        TranslateMessage(&mensaje);
        /* Enviar mensaje al procedimiento de ventana */
        DispatchMessage(&mensaje);
    }

    /* Salir con valor de retorno */
    return mensaje.wParam;
}


/*  Esta función es invocada por la función DispatchMessage()  */
LRESULT CALLBACK WindowProcedure (HWND hwnd, UINT mensaje, WPARAM wParam, LPARAM lParam)
{
    switch (mensaje)                  /* manipulador de mensaje */
    {
        case WM_DESTROY:
            PostQuitMessage (0);       /* Envía el mensaje WM_QUIT a la cola de mensajes */
            break;
        default:                      /* Mensajes que no queremos manejar */
            return DefWindowProc (hwnd, mensaje, wParam, lParam);
    }

    return 0;
}

void InsertarMenu (HWND hwnd)
{

    HMENU hMenu1, hMenu2;

    hMenu1 = CreateMenu();/*Manipulador de la barra de menu */
    hMenu2 = CreateMenu();/*Manipulador para el primer menu pop-up */
    AppendMenu( hMenu2, MF_STRING, CM_SOLUCION, "&Solucion"); /* 1° Item */
    AppendMenu( hMenu2, MF_STRING, CM_PRUEBA, "&Prueba"); /* 1° Item */
    AppendMenu( hMenu2, MF_SEPARATOR, 0, NULL); /* 2° Item (separador) */
    AppendMenu( hMenu2, MF_STRING, CM_SALIR, "&Salir"); /* 3° item Insercion del menu pop_up*/
    AppendMenu( hMenu1, MF_STRING | MF_POPUP, (UINT)hMenu2, "&Principal");
    SetMenu ( hwnd, hMenu1 ); /* Asigna el menu a la ventana hWnd */
}

 

Gracias por su respuesta

Cordiales Saludos

 

Luis 		 	   		  



Más información sobre la lista de distribución Cconclase