ストップウォッチを作ってみる[Visualforce]
概要

Visualforceでストップウォッチを作成します。
スタートの時間とストップの時間の差分を計算します。
ミリ秒単位で計測します。
ソースコード
Stopwatch.vfp
<apex:page docType="html-5.0" LightningStylesheets="true">
<html lang="ja">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>ストップウォッチ</title>
<apex:slds />
</head>
<body>
<div class="slds-align_absolute-center">
<div class="slds-size_2-of-3">
<apex:pageBlock >
<div class="slds-grid slds-einstein-header slds-card__header">
<header class="slds-media slds-media_center slds-has-flexi-truncate">
<div class="slds-grid slds-grid_vertical-align-center slds-size_3-of-4 slds-medium-size_2-of-3">
<h1 class="slds-truncate" title="ストップウォッチ">
<span class="slds-text-heading_large">ストップウォッチ</span>
</h1>
</div>
<div class="slds-einstein-header__figure slds-size_1-of-4 slds-medium-size_1-of-3"></div>
</header>
</div>
<div class="slds-align_absolute-center">
<div class="slds-m-top_large">
<header class="slds-col slds-size_1-of-1 slds-align_absolute-center" >
<div class="curentTime slds-text-heading_large">00:00:000</div>
</header>
<main class="slds-align_absolute-center">
<div class="slds-button-group slds-m-vertical_medium" role="group">
<button id="start" class="slds-button slds-button_neutral slds-text-heading_medium slds-p-around_small">スタート</button>
<button id="stop" class="slds-button slds-button_neutral slds-text-heading_medium slds-p-around_small" disabled="true">ストップ</button>
<button id="reset" class="slds-button slds-button_text-destructive slds-text-heading_medium slds-p-around_small">リセット</button>
</div>
</main>
</div>
</div>
</apex:pageBlock>
</div>
</div>
<apex:include pageName="StopwatchJs"/>
</body>
</html>
</apex:page>
Stopwatch.Js
<apex:page >
<script>
const stopwatchButton = document.querySelectorAll('.slds-button'),
startButton = document.querySelector('#start'),
stopButton = document.querySelector('#stop'),
curentTimeText = document.querySelector('.curentTime');
let startTime, // 計測開始時刻
timeToAdd = 0, // 経過時間
measuringTime = 0, // 計測時間
timerId; // clearTimeout用のID
stopwatchButton.forEach(function (button) {
button.addEventListener('click', event => {
let clickedButtonId = event.currentTarget.id;
if(clickedButtonId === 'start') {
// 計測開始
this.startTimmer();
} else if(clickedButtonId === 'stop') {
// 計測終了
this.stopTimmer();
} else {
// 計測リセット
this.resetTimmer();
}
})
})
// 計測開始
function startTimmer() {
startButton.disabled = true;
stopButton.disabled = false;
startTime = Date.now();
// 10ミリ秒毎に計測する
countUp();
}
// 計測終了
function stopTimmer() {
startButton.disabled = false;
stopButton.disabled = true;
clearTimeout(timerId);
timeToAdd += Date.now() - startTime; // 経過時間を記録
}
// 計測リセット
function resetTimmer() {
startButton.disabled = false;
stopButton.disabled = true;
clearTimeout(timerId);
measuringTime = 0;
timeToAdd = 0;
// 計測時間を分に変換して表示する
updateTimeText();
}
// 計測時間を分に変換して表示する
function updateTimeText(){
let min = Math.floor(measuringTime / 60000); // 分
let sec = Math.floor(measuringTime % 60000 / 1000); // 秒
let ms = measuringTime % 1000; // ミリ秒
// 桁数を固定
min = ('0' + min).slice(-2);
sec = ('0' + sec).slice(-2);
ms = ('00' + ms).slice(-3);
// 計測時間を表示
curentTimeText.textContent = min + ':' + sec + ':' + ms;
}
// 10ミリ秒毎に計測する
function countUp(){
timerId = setTimeout(function(){
measuringTime = Date.now() - startTime + timeToAdd;
// 計測時間を分に変換して表示する
updateTimeText()
// 10ミリ秒毎に計測する
countUp();
},10);
}
</script>
</apex:page>

