えーー。。実際に使うなら、zap35 さんのように、OnTime で実行したマクロ
の中で再度 OnTime を登録する方が良いと思います。
この方式だと、OnTime で登録されるのは常に一つだから管理し易いです。
これに未実行の予約を破棄できる仕組みを組み込めばベストだと思います。
今更こんな事言うのは、#6 の大げさなコードを見て、「また、やっちまった...」
と反省しているからです。が、#6 をアップしてしまった以上、それなりに
まとめておきました。こちらは、一括登録方式です。
コードのままだと、午前10時~午後6時まで30分間隔で Macro1 を実行します。
変更点は、
・ブッククローズをトラップした
・進捗状況をステータスバーに表示するようにした
・その他しょうもないこと
です。
このままコピペで使えると思いますが、試される場合は、MACRO1 はご自分の
用途に合わせて適切に修正して下さい。
Option Explicit
Dim mcolTask As Collection
Sub 実行予約()
Dim i As Date
Dim strProcName As String
Dim datBigin As Date
Dim datEnd As Date
Dim datInterval As Date
Dim datTimeout As Date
Dim blnJustTime As Boolean
' Setting-------------------------------------------------------
datBigin = TimeValue("10:00:00") ' 開始時刻
datEnd = TimeValue("18:00:00") ' 終了時刻
datInterval = TimeValue("00:30:00") ' 実行間隔(少なくとも数秒以上で)
datTimeout = TimeValue("00:02:00") ' 実行待機タイムアウト
blnJustTime = True ' datInterval で丸めるか
strProcName = "MACRO1" ' 実行するマクロ名
'---------------------------------------------------------------
' 既に実行予約されているか確認
If mcolTask Is Nothing Then
' 日付シリアル値を加算
datBigin = datBigin + Date
datEnd = datEnd + Date
' 終了時刻が開始時刻より小さければ日をまたぐので補正
If datEnd < datBigin Then datEnd = datEnd + 1
' 現在時刻が既に終了時刻を過ぎている場合
If datEnd < Now() Then
MsgBox "終了時刻を過ぎているため予約できません。", vbCritical, "終了"
Exit Sub
End If
' 現在時刻が開始時刻を過ぎていれば補正
If datBigin < Now() Then
' 開始時刻を datInterval で指定された値で丸めるか
If blnJustTime Then
datBigin = Application.Floor(Now() + datInterval, datInterval)
Else
datBigin = Now() + datInterval
End If
End If
' 初期化
Set mcolTask = New Collection
' メイン部分
For i = datBigin To datEnd Step datInterval
' 後から取り消せるようにコレクションに退避
mcolTask.Add CStr(i) & "," & strProcName
' Application.Ontime で実行予約を行う
Application.OnTime EarliestTime:=i, _
Procedure:=strProcName, _
LatestTime:=i + datTimeout, _
Schedule:=True
Next i
Else
MsgBox "既に実行中です", vbInformation
End If
End Sub
Sub 未実行予約強制解除()
Dim i As Long
Dim vntS As Variant
On Error Resume Next
Application.StatusBar = "タスク破棄中... "
For i = 1 To mcolTask.Count
vntS = Split(mcolTask.Item(i), ",")
Application.OnTime CDate(vntS(0)), CStr(vntS(1)), Schedule:=False
Next i
Application.StatusBar = ""
Set mcolTask = Nothing
End Sub
' タスク管理用
Private Sub RemoveTask()
On Error Resume Next
mcolTask.Remove (1)
Application.StatusBar = "待機中のタスク... " & mcolTask.Count
DoEvents
Beep
If mcolTask.Count = 0 Then
Application.StatusBar = ""
Set mcolTask = Nothing
End If
End Sub
Sub Auto_Close()
Dim intRes As Integer
If Not mcolTask Is Nothing Then
intRes = MsgBox( _
Prompt:="待機中のタスクが " & mcolTask.Count & " 件あります。" & vbLf _
& "破棄して終了しますか?", _
Buttons:=vbOKCancel + vbDefaultButton2 + vbExclamation, _
Title:="問い合わせ")
If intRes = vbOK Then
Call 未実行予約強制解除
Else
' ブッククローズをキャンセル
Application.ExecuteExcel4Macro ("Halt(True)")
End If
End If
End Sub
' 呼び出すマクロ--> Application.Ontime のマクロ名と一致させて下さい
Sub MACRO1()
Dim lngRow As Long
With ThisWorkbook.Sheets("Sheet1")
lngRow = .Range("V65536").End(xlUp).Offset(1).Row
.Cells(lngRow, "V").Resize(1, 3).Value = .Range("Q12:S12").Value
.Cells(lngRow, "Y").Value = Now()
End With
' ご自分のマクロの最後に次の一行を追加しておいて下さい
Call RemoveTask
End Sub
投稿日時 - 2006-06-17 00:14:44