Introduction
Think that you have a Microsoft Excel application (VBA) and you have to use timer functionality there. There is no such native control in Excel called "Timer". What will you do? Also think that you are in a situation where you are unable to use a "Form" where you can "put" a timer control. But still you need a timer functionality that will work exactly like the timer control. It'll fire an event in a timely fashioned and can start and stop, etc. If you're in such a situation, the article below is for you.
Background
I have seen many articles on the Internet that resolve timer functionality without a timer control using a set of complicated Win32 APIs. The codes are very risky to use and your application can crash anytime. Also in most of the cases, there is no event firing option like the timer control has. In this article, I have shown a very simple way to implement timer functionality without a timer control just using a single Win32 API. It is a single class AxtiveX DLL project.
Using the Code
The main tricky way of this application is using a Win32API named "GetTickCount
". The GetTickCount
function retrieves the number of milliseconds that have elapsed since Windows was started. Using this API, you can code an ActiveX DLL that will serve you the need of a timer. I have named the project TimerLib
and it has only a single class named TimerEx.cls. See the code below:
Option Explicit
Private Declare Function GetTickCount Lib "kernel32" () As Long
Private mblnEnabled As Boolean
Private mlngInterval As Long
Private mstrTag As String
Private mlngTickCount As Long
Private mtypIntervalType As IntervalData
Public Event OnTimer()
Public Type IntervalData
MilliSecond As Long
Second As Long
Minute As Long
Hour As Long
End Type
Public Property Get Enabled() As Boolean
Enabled = mblnEnabled
End Property
Public Property Let Enabled(blnEnabled As Boolean)
mblnEnabled = blnEnabled
If blnEnabled Then
mlngTickCount = GetTickCount
Call TimerLoop
End If
End Property
Public Property Get Interval() As Long
Interval = mlngInterval
End Property
Public Property Let Interval(lngInterval As Long)
mlngInterval = lngInterval
End Property
Public Property Get IntervalInfo() As IntervalData
IntervalInfo = mtypIntervalType
End Property
Public Property Let IntervalInfo(typIntervalType As IntervalData)
mtypIntervalType = typIntervalType
mlngInterval = mtypIntervalType.MilliSecond + typIntervalType.Second * 1000 + _
typIntervalType.Minute * 60 * 1000 + typIntervalType.Hour * 60 * 60 * 1000
End Property
Public Property Get Tag() As String
Tag = mstrTag
End Property
Public Property Let Tag(strTag As String)
mstrTag = strTag
End Property
Private Sub TimerLoop()
Do While Not mblnEnabled = False
If GetTickCount - mlngTickCount >= mlngInterval Then
RaiseEvent OnTimer
mlngTickCount = GetTickCount
ElseIf GetTickCount = 0 Then
mlngTickCount = 0
ElseIf GetTickCount < mlngTickCount Then
mlngTickCount = 0
End If
DoEvents
Loop
End Sub
How to Use the Library
You can use this library from any COM compatible high level language. In the sample code, I have taken a standard VB6 EXE application that has two buttons in the form named "cmdEnableTimer
" and "cmdDisableTimer
". I have taken the reference of the timer library from the Project>References. and used the TimerEx
class using...
WithEvents
... Keyword so that the timer event can be tracked. In my library, the timer event is OnTimer
. See the code below:
Option Explicit
Private WithEvents myTimer As TimerEx
Private mlngTick As Long
Private myIntervalInfo As IntervalData
Private Sub cmdDisableTimer_Click()
myTimer.Enabled = False
End Sub
Private Sub cmdEnableTimer_Click()
myTimer.Enabled = True
End Sub
Private Sub Form_Load()
myIntervalInfo.Second = 5
Set myTimer = New TimerLib.TimerEx
myTimer.IntervalInfo = myIntervalInfo
End Sub
Private Sub Form_Unload(Cancel As Integer)
myTimer.Enabled = False
Set myTimer = Nothing
End Sub
Private Sub myTimer_OnTimer()
mlngTick = mlngTick + 1
Me.Caption = mlngTick
End Sub
Points of Interest
You can use the TimerLib
from any COM compatible language. And you'll see from the code that here I extended the Interval
property of the VB6 timer control from conventional milliseconds to Second / Minute and even in Hour. Hope you'll enjoy using this code.
History
- 14th September, 2008: Initial post