Skip to content

Instantly share code, notes, and snippets.

@kjirou
Last active December 21, 2015 16:39
Show Gist options
  • Save kjirou/6334597 to your computer and use it in GitHub Desktop.
Save kjirou/6334597 to your computer and use it in GitHub Desktop.
個別のインターバルを持つ複数のタスクを時間通りに起動させるための、Timerクラスの設計メモ
//
// Timerクラスからは以下を分離したい
//
// - setTimeout/clearTimeout の実行
// - new Date の実行
//
var timer = new Timer();
// タスクを登録。'タスクID', インターバル(ms), コールバック
timer.registerTask('task1', 100, function(){/* 個別処理 */});
timer.registerTask('task2', 150, function(){/* 個別処理 */});
timer.registerTask('task3', 200, function(){/* 個別処理 */});
var nextTick = function(){
// 登録タスクのインターバルを使って、次タスクを決めてその情報を返す
var nextTask = timer.getNextTask();
// 次のタスクまでのミリ秒数
var interval = nextTask[0];
// 次のタスクリスト、同時間にタスクが重なることもあるのでリスト
var tasks = nextTask[1];
setTimeout(function(){
// Timerデータ内の時計を進める
timer.advanceTime(interval);
// タスクを発火する
timer.emitTasks(tasks);
// 再帰
nextTick();
}, interval);
};
//
// 上記に以下の機能を加える
//
// - 割り込みによるsetTimeoutのキャンセル
// - その際に、消化した現実時間の分、Timer内で管理している時間も進める
//
// この段階で Timer 以外が膨らみ過ぎて、
// 分離してしまうと本体の意味もわけわからなくなるので、
// 同じ Timer クラス内に置かざるを得なくなった。
//
// ということで要望未達中。
//
var timerId = null;
var setTime = null;
var nextTick = function(){
var nextTask = timer.getNextTask();
var interval = nextTask[0];
var tasks = nextTask[1];
// setTimeoutした時間
setTime = (new Date()).getTime();
timerId = setTimeout(function(){
timer.advanceTime(interval);
timer.emitTasks(tasks);
nextTick();
}, interval);
};
// 割り込みタスク
someView.onClick = function(){
// setTimeout をキャンセル
clearTimeout(timerId);
// setTimeout 登録から経過した現実時間
var deltaTime = (new Date()).getTime() - setTime;
// 未発火ながらも消化した時間をTimerデータへ反映させる
timer.advanceTime(deltaTime);
};
//
// 更に以下の機能を加える
//
// - タスク内から割り込みしてタイマーを停止
//
var timerId = null;
var setTime = null;
var nextTick = function(){
var nextTask = timer.getNextTask();
var interval = nextTask[0];
var tasks = nextTask[1];
setTime = (new Date()).getTime();
timerId = setTimeout(function(){
timer.advanceTime(interval);
// tasks の各タスク内で、
// Timerの特定のメソッドを呼ぶと次のタイマーをキャンセルできる
// 実行すると、次の isRunning が false を返すようになる
timer.emitTasks(tasks);
if (timer.isRunning()) {
nextTick();
}
}, interval);
};
someView.onClick = function(){
clearTimeout(timerId);
var deltaTime = (new Date()).getTime() - setTime;
timer.advanceTime(deltaTime);
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment