Implement cooldown on frontend

Also make cooldown time dependent on mates.json
This commit is contained in:
Thomas Wade 2018-10-06 21:08:57 +09:30
parent 7eeaaa58c7
commit 08f83d9adf
5 changed files with 109 additions and 9 deletions

View File

@ -16,7 +16,10 @@
<body> <body>
<div class="container" ng-controller="mates"> <div class="container" ng-controller="mates">
<div class="above">Loky has</div> <div class="above">Loky has</div>
<div class="count" ng-click="countClick()">{{mates}}</div> <div class="count" ng-disabled="cooldown" ng-click="countClick()">
{{mates}}<br/>
<div class="timeRemainingBar" ng-style="countdownStyle"></div>
</div>
<div class="below">mates</div> <div class="below">mates</div>
</div> </div>
</body> </body>

View File

@ -1 +1 @@
{"mates":0,"lastUpdate":0} {"mates":0,"lastUpdate":0,"cooldown":60}

View File

@ -1,13 +1,23 @@
var app = angular.module("app", []); var app = angular.module("app", []);
app.controller("mates", ["$scope", "$http", function($scope, $http) app.controller("mates", ["$scope", "$http", "$interval", function($scope, $http, $interval)
{ {
$scope.mates = 0; $scope.mates = 0;
$scope.animation = undefined;
$scope.countdownStyle =
{
width: '0%'
};
$scope.cooldown = false;
$http.get("/mates") $http.get("/mates")
.then((r) => .then((r) =>
{ {
$scope.mates = angular.fromJson(r.data).mates; var json = angular.fromJson(r.data);
$scope.mates = json.mates;
animateCountdown($scope, $interval, json.lastUpdate, json.cooldown);
}); });
$scope.countClick = () => $scope.countClick = () =>
@ -15,7 +25,73 @@ app.controller("mates", ["$scope", "$http", function($scope, $http)
$http.post("/mates") $http.post("/mates")
.then((r) => .then((r) =>
{ {
$scope.mates = angular.fromJson(r.data).mates; var json = angular.fromJson(r.data);
})
} // Check if this was sent to early
if (json.error || r.status != 200) return;
$scope.mates = json.mates;
animateCountdown($scope, $interval, json.lastUpdate, json.cooldown);
});
};
}]); }]);
function animateCountdown($scope, $interval, lastUpdate, cooldown)
{
var lastUpdateDate = new Date(lastUpdate)
var difference = timeSince(lastUpdateDate);
// Check if there is a cooldown in progress
if (difference < cooldown)
{
// Make sure there is no animation in progress before proceeding
if (angular.isDefined($scope.animation)) return;
// Run callback immediately as an interval workaround
cooldownIntervalCallback($scope, $interval, lastUpdateDate, cooldown);
// Set the interval
$scope.animation = $interval(() =>
{
cooldownIntervalCallback($scope, $interval, lastUpdateDate, cooldown);
}, 1000);
}
}
function cooldownIntervalCallback($scope, $interval, lastUpdateDate, cooldown)
{
var difference = timeSince(lastUpdateDate);
if (difference >= cooldown)
{
// Cancel the interval if it exists and clear it
if (angular.isDefined($scope.animation)) $interval.cancel($scope.animation);
$scope.animation = undefined;
// Reset the countdown bar
$scope.countdownStyle =
{
width: '0%'
};
// Reset the cooldown flag
$scope.cooldown = false;
}
else
{
// Set the style based on the remaining percent
$scope.countdownStyle =
{
width: ((cooldown - difference) / cooldown) * 100 + '%'
};
// Set the cooldown flag
$scope.cooldown = true;
}
}
function timeSince(date)
{
return Math.ceil((new Date().getTime() - date.getTime()) / 1000);
}

View File

@ -39,7 +39,7 @@ app.post('/mates', function(rq, rs)
var data = fs.readFileSync('./mates.json'); var data = fs.readFileSync('./mates.json');
var json = JSON.parse(data); var json = JSON.parse(data);
var cooldownSecs = 60; var cooldownSecs = json.cooldown;
var currentTime = new Date().getTime(); var currentTime = new Date().getTime();
var timeSinceLast = (currentTime - json.lastUpdate) / 1000; var timeSinceLast = (currentTime - json.lastUpdate) / 1000;

View File

@ -42,7 +42,28 @@ body
vertical-align: middle; vertical-align: middle;
} }
.count:hover .count:hover:not(.count[disabled])
{ {
color: green; color: green;
} }
.count[disabled]
{
color: #0009;
}
.timeRemainingBar
{
position: relative;
bottom: 10px;
height: 5px;
margin-right: auto;
margin-left: auto;
transition-timing-function: linear;
transition-duration: 1s;
transition-property: width;
background-color: #0009;
}