• Welcome to Valhalla Legends Archive.
 

SetTimer()?

Started by Eli_1, February 07, 2004, 11:13 PM

Previous topic - Next topic

Eli_1

I remember using SetTimer with VB but I don't know how to do it with C++. I tryed researching it for about an hour but everything I found uses CWnd:: which wasn't working for me. if anyone knows how I can use the SetTimer() and KillTimer() APIs with c++ please tell me.

Adron

You were previously making a console app - so I just wanted to warn you that SetTimer and KillTimer aren't the best for console apps.

From MSDN:
Quote

UINT_PTR SetTimer(
 HWND hWnd,              // handle to window
 UINT_PTR nIDEvent,      // timer identifier
 UINT uElapse,           // time-out value
 TIMERPROC lpTimerFunc   // timer procedure
);


You have two choices:

* Call SetTimer with the handle to your window, an (nonzero) identifier of your choice and the timeout value, then write a handler for WM_TIMER in your WindowProc. You will get that message when the timeout elapses.

* Call SetTimer with the pointer to a function you've written and the timeout value. You still need to be processing window messages or it won't work. Your function will be called when the timeout elapses.

In both cases, unused arguments should be zero.

To abort the timer, you call KillTimer with your window + identifier in the first case, or with the return value from the SetTimer call in the second case.

Eli_1

Quote from: Adron on February 08, 2004, 05:16 AM
* Call SetTimer with the handle to your window, an (nonzero) identifier of your choice and the timeout value, then write a handler for WM_TIMER in your WindowProc. You will get that message when the timeout elapses.

Here's the code I have for the timer.

#include <windows.h> // for windowproc??
#include <winuser.h> // same??
#include <iostream.h>
#include <stdlib.h>

HWND hwnd;
// WNDCLASSEX wc;
int my_timer;

int main() {
   bool nostop=true;
   char input[256];
   
   hwnd=GetForegroundWindow();

   // wc.lpfnWndProc = WindowProc;
   my_timer=SetTimer(hwnd, 1, 1000, NULL);
   cout << "Timer created. hWnd->" << hwnd << "\n";
   while (nostop==true) { continue; }
   KillTimer(hwnd,my_timer);
   return 0;
}

LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) {
   cout << "Timer! - uMsg->" << uMsg << "\n";
}

Output:

Timer created! hWnd->00000A70

The problem is WindowProc is never being called? any ideas?

iago

Like Adron said, you have to be processing messages for it to work.  In a console ap, you generally dont process messages, so it might be a lot trickier.

On a side note, that "continue;" in your code was completely unnecessary.  When it gets to the end up a loop, it will continue anyway.  A sleep(0) might be better there
This'll make an interesting test for broken AV:
QuoteX5O!P%@AP[4\PZX54(P^)7CC)7}$EICAR-STANDARD-ANTIVIRUS-TEST-FILE!$H+H*


Maddox

Quote from: Eli_1 on February 08, 2004, 12:02 PM
The problem is WindowProc is never being called? any ideas?

The reason is this is happening is because you've left the lpTimerFunc argument NULL and your TIMERPROC function's declaration is incorrect.

Try this

// this should changed in main()
my_timer=SetTimer(hwnd, 1, 1000, MyTimer);


// timer proc
VOID CALLBACK MyTimer(HWND hwnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime)
{
    cout << "Timer! - uMsg->" << uMsg << "\n";
}


Hope that helps.
asdf.

Eli_1

#5
Quote
error C2664: 'SetTimer' : cannot convert parameter 4 from 'void (struct HWND__ *,unsigned int,unsigned long,unsigned long)' to 'void (__stdcall *)(struct HWND__ *,unsigned int,unsigned int,un
signed long)'
       None of the functions with this name in scope match the target type
Error executing cl.exe.

Here's some of the code I'm using

//prototypes
VOID CALLBACK TimProc(HWND hwnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime);


my_timer=SetTimer(hwnd,1,int_input,TimProc);



VOID CALLBACK TimProc(HWND hwnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime)
{
   cout << "Timer! - uMsg->" << uMsg << "\n";
}

iago

Read the error message for this one:
Quote
error C2664: 'SetTimer' : cannot convert parameter 4 from
'void (struct HWND__ *,unsigned int,unsigned long,unsigned long)'
to
'void (__stdcall *)(struct HWND__ *,unsigned int,unsigned int,unsigned long)'

Seems pretty obvious to me.
This'll make an interesting test for broken AV:
QuoteX5O!P%@AP[4\PZX54(P^)7CC)7}$EICAR-STANDARD-ANTIVIRUS-TEST-FILE!$H+H*


Eli_1

what's __stdcall*?  ???

MrRaza

MSDN explains this all for you.

iago

Declare your function with _stdcall there.

void __stdcall myFunc(.....);

or, if it has to be a pointer, it's either
void *__stdcall myFunc(.....);
or
void __stdcall *myFunc(.....);
I'm not sure which is right, but I'm sure Skywing or Kp or somebody else will clear that up, or you can just try both.
This'll make an interesting test for broken AV:
QuoteX5O!P%@AP[4\PZX54(P^)7CC)7}$EICAR-STANDARD-ANTIVIRUS-TEST-FILE!$H+H*


Kp

#10
Quote from: iago on February 08, 2004, 07:59 PM
Declare your function with _stdcall there.

void __stdcall myFunc(.....);

or, if it has to be a pointer, it's either
void *__stdcall myFunc(.....);
or
void __stdcall *myFunc(.....);
I'm not sure which is right, but I'm sure Skywing or Kp or somebody else will clear that up, or you can just try both.

The compiler should've picked up on that part automatically.  If it didn't, then he should use &TimProc as the parameter to SetTimer (use an & to explicitly take its address).  Regardless, he needs to add _stdcall to the function declaration (as you mentioned).  I'm actually rather surprised to see that error, since iirc CALLBACK is aliased to _stdcall.
[19:20:23] (BotNet) <[vL]Kp> Any idiot can make a bot with CSB, and many do!

Adron

Quote from: Maddox on February 08, 2004, 02:16 PM
Quote from: Eli_1 on February 08, 2004, 12:02 PM
The problem is WindowProc is never being called? any ideas?

The reason is this is happening is because you've left the lpTimerFunc argument NULL and your TIMERPROC function's declaration is incorrect.


Like I said before, even with a timerproc, you have to process window messages. So it will never work as long as the program consists of an endless while loop doing nothing special. Making the while loop something like:


 MSG msg;
 while(GetMessage(&msg, 0, 0, 0) == TRUE)
    DispatchMessage(&msg);


should help things. In addition to that you should use either the timerproc way, or actually make a window for your windowproc.

Zakath

That error is puzzling. Kp was right about CALLBACK. See the MSVS tooltip when CALLBACK is pointed at?

Quote from: iago on February 02, 2005, 03:07 PM
Yes, you can't have everybody...contributing to the main source repository.  That would be stupid and create chaos.

Opensource projects...would be dumb.

dxoigmn

#13
Quote from: Zakath on February 09, 2004, 09:41 AM
That error is puzzling. Kp was right about CALLBACK. See the MSVS tooltip when CALLBACK is pointed at?



Your answer lies in the declaration of the arguments.  Notice how he declares the type of idEvent to UINT_PTR, it should be UINT.  Even though MSDN documents it as UINT_PTR for TimerProc Function, in their Using Timers example it uses the UINT convention and this is the way it is specified in WinUser.h:

WINUSERAPI
UINT
WINAPI
SetTimer(
   HWND hWnd ,
   UINT nIDEvent,
   UINT uElapse,
   TIMERPROC lpTimerFunc);