Jump to content

Recommended Posts

Posted

Yes, I did search the forums :)

I found a few scripts which can do this. The first that I came across was this one:

http://www.autoitscript.com/forum/index.php?showtopic=16039

But I find if you check too often it causes quite a bit of CPU load, and I do want this script to be accurate.

The second was this: http://www.autoitscript.com/forum/index.php?showtopic=4361

Very clean, but unfortunately the windows I tired typing in report a static caret position regardless of the true position.

On doing a little bit of googling, I found this seems to be a reliable way of finding idle time on NT systems:

http://msdn.microsoft.com/library/default....stinputinfo.asp

But I have no idea how to use DLLCalls. Can anyone lend me a hand? A general note to developers, it'd be great if there was an easy way to detect system idle time via an AutoIt command.

Posted (edited)

Thanks for the pointers w0uter, I'm hoping I have in fact made progress thanks to it! Never thought I'd understand DLLCalls :)

I'm still looking for a little bit of advice though.

My test code:

$struct = DllStructCreate ( "uint;dword" );
DllStructSetData ( $struct, 1, 8 );

while ( 1 )
    Sleep(2000)

    DllCall ( "user32.dll", "int", "GetLastInputInfo", "ptr", DllStructGetPtr( $struct ) )
    ConsoleWrite ( "Data:" & DllStructGetData($struct,2) & @LF)
WEnd

The returned data:

Data:60270406
Data:60270406
Data:60276906
Data:60278484
Data:60279890
Data:60279890
Data:60279890
Data:60279890
Data:60288953
Data:60290968
Data:60292921
Data:60293843
Data:60293843
Data:60298921
Data:60299671
Data:60303000
Data:60304921
Data:60307000
Data:60309000

Unless I've done something wrong I assume this must be a relative time to something, as I assumed it more to be based on a starting point of 0. That's something I can work out okay, I really just want to know if my code is okay because.. if the system has been running a long time I assume the number could become greater than the max value int can hold.

If it's all okay, I'm going to turn it into a function and stick it into the UDF forum I guess.. Seems a very efficient way of getting idle time on 2k/XP and created 0 CPU load even running with a sleep(200). Kinda surprised no-one else has looked into this way :mellow:

Edit:

Ah, silly me. On re-reading the documentation I somehow overlooked the obvious at the top: The GetLastInputInfo function retrieves the time of the last input event. I'm still unsure what the chances of a number greater than what the int can hold is, and what would happen. I'm not very mathamatical :)

Edited by Suxen
Posted

Maybe something like?

#include <Date.au3>
HotKeySet("{Esc}", "_Terminate")

Local $last_active = 0, $iHours, $iMins, $iSecs
$not_idle = _CheckIdle($last_active, 1)
while (1)
    Sleep(200)
    $not_idle = _CheckIdle($last_active)
    _TicksToTime($not_idle, $iHours, $iMins, $iSecs)
    If $iHours Or $iMins Or $iSecs Then
        ConsoleWrite("Was Idle for: Hours: " & $iHours & " Minutes: " & $iMins & " Seconds: " & $iSecs & @LF)
    EndIf
WEnd

Func _CheckIdle(ByRef $last_active, $start = 0)
    $struct = DllStructCreate("uint;dword");
    DllStructSetData($struct, 1, DllStructGetSize($struct));
    If $start Then
        DllCall("user32.dll", "int", "GetLastInputInfo", "ptr", DllStructGetPtr($struct))
        $last_active = DllStructGetData($struct, 2)
        Return $last_active
    Else
        DllCall("user32.dll", "int", "GetLastInputInfo", "ptr", DllStructGetPtr($struct))
        If $last_active <> DllStructGetData($struct, 2) Then
            Local $save = $last_active
            $last_active = DllStructGetData($struct, 2)
            Return $last_active - $save
        EndIf
    EndIf
EndFunc  ;==>_CheckIdle

Func _Terminate()
    Exit
EndFunc  ;==>_Terminate

SciTE for AutoItDirections for Submitting Standard UDFs

 

Don't argue with an idiot; people watching may not be able to tell the difference.

 

Posted (edited)

You guys are geniuses, thanks! :mellow:

Would be cool to release this as a UDF, but as it's not my work and such, I'm going to leave it to the more talented! Absolutely perfectly what I was after! :)

EDIT: Although, one more question though :) What'd be the easiest way to return the time as seconds only? Just iMins * 60 and iHours * 60 * 60? Can't decide if I want purely seconds or properly formatted for what I'm after yet. But again I say, awesome :o

Edited by Suxen
Posted (edited)

You guys are geniuses, thanks! :mellow:

Would be cool to release this as a UDF, but as it's not my work and such, I'm going to leave it to the more talented! Absolutely perfectly what I was after! :)

EDIT: Although, one more question though :) What'd be the easiest way to return the time as seconds only? Just iMins * 60 and iHours * 60 * 60? Can't decide if I want purely seconds or properly formatted for what I'm after yet. But again I say, awesome :o

should be something like

If $iHours Or $iMins Or $iSecs Then
        ConsoleWrite((($iHours * 60) * 60) + ($iMins * 60) + $iSecs & @LF)
        ConsoleWrite("Was Idle for: Hours: " & $iHours & " Minutes: " & $iMins & " Seconds: " & $iSecs & @LF)
    EndIf
Edited by gafrost

SciTE for AutoItDirections for Submitting Standard UDFs

 

Don't argue with an idiot; people watching may not be able to tell the difference.

 

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...