[C con Clase] Duda con winapi
Rubén Blanco Fernández
darkmalka en hotmail.com
Dom Oct 21 14:56:59 CEST 2018
Buenas,
Estoy aprendiendo a usar winapi con el curso de cconclase y es realmente bueno.
Se me a presentado un problema que no tengo claro como gestionarlo. Estoy acostumbrado a programar en consola y cuando quieres hacer un bucle que tarde su tiempo, simplemente hay que esperar a que termine.
El caso es que si activo un bucle con WM_COMAND, la aplicación se cuelga hasta que el bucle finalice.
Como tendría que hacer para ejecutar un bucle/funcion que tarde 10 minutos por ejemplo sin que deje de responder la aplicación? El ejemplo 4 del curso es perfecto para mostrar lo que yo he hecho (está marcado en rojo).
Para solucionarlo he pensado en activar un boleano con WM_COMAND y después ejecutar el bucle en otro sitio, e incluso segmentar el bucle para que valla funcionando poco a poco, pero creo esto simplemente camufla el problema. No se si hay una solución más obvia para esto.
Muchas gracias por vuestro tiempo.
Un saludo
#include <windows.h>
#include <stdio.h>
#include "main.h"
/* Declaración del procedimiento de ventana */
LRESULT CALLBACK WindowProcedure (HWND, UINT, WPARAM, LPARAM);
BOOL CALLBACK DlgProc(HWND, UINT, WPARAM, LPARAM);
BOOL CALLBACK DlgProc2(HWND, UINT, WPARAM, LPARAM);
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 = "Menu";
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_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 */
"Ejemplo 004", /* 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 */
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 msg, WPARAM wParam, LPARAM lParam)
{
static HINSTANCE hInstance;
static int veces;
switch (msg) /* manipulador del mensaje */
{
case WM_CREATE:
hInstance = ((LPCREATESTRUCT)lParam)->hInstance;
return 0;
break;
case WM_COMMAND:
switch(LOWORD(wParam)) {
case CM_DIALOGO2:
//bucle
DialogBoxParam(hInstance, "DialogoPrueba", hwnd, DlgProc2, veces);
break;
}
break;
case WM_DESTROY:
PostQuitMessage(0); /* envía un mensaje WM_QUIT a la cola de mensajes */
break;
default: /* para los mensajes de los que no nos ocupamos */
return DefWindowProc(hwnd, msg, wParam, lParam);
}
return 0;
}
BOOL CALLBACK DlgProc2(HWND hDlg, UINT msg, WPARAM wParam, LPARAM lParam)
{
char texto[25];
switch (msg) /* manipulador del mensaje */
{
case WM_INITDIALOG:
sprintf(texto, "Veces invocado: %d", (int)lParam);
SetWindowText(GetDlgItem(hDlg, TEXTO), texto);
return TRUE;
case WM_COMMAND:
EndDialog(hDlg, FALSE);
return TRUE;
}
return FALSE;
}
------------ próxima parte ------------
Se ha borrado un adjunto en formato HTML...
URL: <http://listas.conclase.net/pipermail/cconclase_listas.conclase.net/attachments/20181021/c8182385/attachment.html>
Más información sobre la lista de distribución Cconclase