Skip to content

Commit

Permalink
init project with basic features
Browse files Browse the repository at this point in the history
  • Loading branch information
joshua1988 committed Apr 2, 2020
1 parent f44a4ae commit 5988e02
Show file tree
Hide file tree
Showing 3 changed files with 544 additions and 0 deletions.
258 changes: 258 additions & 0 deletions project/app.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,258 @@
// utils
function $(selector) {
return document.querySelector(selector);
}
function getUnixTimestamp(date) {
return new Date(date).getTime();
}

// DOM
const confirmedTotal = $('.confirmed-total');
const deathsTotal = $('.deaths');
const recoveredTotal = $('.recovered');
const lastUpdatedTime = $('.last-updated-time');
const rankList = $('.rank-list');
const deathsList = $('.deaths-list');
const recoveredList = $('.recovered-list');
const deathSpinner = createSpinnerElement('deaths-spinner');
const recoveredSpinner = createSpinnerElement('recovered-spinner');

function createSpinnerElement(id) {
const wrapperDiv = document.createElement('div');
wrapperDiv.setAttribute('id', id);
wrapperDiv.setAttribute(
'class',
'spinner-wrapper flex justify-center align-center',
);
const spinnerDiv = document.createElement('div');
spinnerDiv.setAttribute('class', 'ripple-spinner');
spinnerDiv.appendChild(document.createElement('div'));
spinnerDiv.appendChild(document.createElement('div'));
wrapperDiv.appendChild(spinnerDiv);
return wrapperDiv;
}

// state
let isDeathLoading = false;
let isRecoveredLoading = false;

// api
function fetchCovidSummary() {
const url = 'https://api.covid19api.com/summary';
return axios.get(url);
}

function fetchCountryInfo(countryCode, status) {
// params: confirmed, recovered, deaths
const url = `https://api.covid19api.com/country/${countryCode}/status/${status}`;
return axios.get(url);
}

// methods
function startApp() {
setupData();
initEvents();
}

// events
function initEvents() {
rankList.addEventListener('click', handleListClick);
}

async function handleListClick(event) {
let selectedId;
if (
event.target instanceof HTMLParagraphElement ||
event.target instanceof HTMLSpanElement
) {
selectedId = event.target.parentElement.id;
}
if (event.target instanceof HTMLLIElement) {
selectedId = event.target.id;
}
if (isDeathLoading) {
return;
}
clearDeathList();
clearRecoveredList();
startLoadingAnimation();
isDeathLoading = true;
const { data: deathResponse } = await fetchCountryInfo(selectedId, 'deaths');
const { data: recoveredResponse } = await fetchCountryInfo(
selectedId,
'recovered',
);
const { data: confirmedResponse } = await fetchCountryInfo(
selectedId,
'confirmed',
);
console.log(confirmedResponse);
endLoadingAnimation();
setDeathsList(deathResponse);
setTotalDeathsByCountry(deathResponse);
setRecoveredList(recoveredResponse);
setTotalRecoveredByCountry(recoveredResponse);
setChartData(confirmedResponse);
isDeathLoading = false;
// console.log(data);
}

function setDeathsList(data) {
const sorted = data.sort(
(a, b) => getUnixTimestamp(b.Date) - getUnixTimestamp(a.Date),
);
sorted.forEach(value => {
const li = document.createElement('li');
li.setAttribute('class', 'list-item-b flex align-center');
const span = document.createElement('span');
span.textContent = value.Cases;
span.setAttribute('class', 'deaths');
const p = document.createElement('p');
p.textContent = new Date(value.Date).toLocaleDateString().slice(0, -1);
li.appendChild(span);
li.appendChild(p);
deathsList.appendChild(li);
});
}

function clearDeathList() {
deathsList.innerHTML = null;
}

function setTotalDeathsByCountry(data) {
deathsTotal.innerText = data[0].Cases;
}

function setRecoveredList(data) {
const sorted = data.sort(
(a, b) => getUnixTimestamp(b.Date) - getUnixTimestamp(a.Date),
);
sorted.forEach(value => {
const li = document.createElement('li');
li.setAttribute('class', 'list-item-b flex align-center');
const span = document.createElement('span');
span.textContent = value.Cases;
span.setAttribute('class', 'recovered');
const p = document.createElement('p');
p.textContent = new Date(value.Date).toLocaleDateString().slice(0, -1);
li.appendChild(span);
li.appendChild(p);
recoveredList.appendChild(li);
});
}

function clearRecoveredList() {
recoveredList.innerHTML = null;
}

function setTotalRecoveredByCountry(data) {
recoveredTotal.innerText = data[0].Cases;
}

function startLoadingAnimation() {
deathsList.appendChild(deathSpinner);
recoveredList.appendChild(recoveredSpinner);
}

function endLoadingAnimation() {
deathsList.removeChild(deathSpinner);
recoveredList.removeChild(recoveredSpinner);
}

//
async function setupData() {
const { data } = await fetchCovidSummary();
console.log(data);
setTotalConfirmedNumber(data);
setTotalDeathsByWorld(data);
setTotalRecoveredByWorld(data);
setCountryRanksByConfirmedCases(data);
setLastUpdatedTimestamp(data);
// renderChart();
}

function renderChart(data, labels) {
var ctx = $('#lineChart').getContext('2d');
const defaultLabel = [
'January',
'February',
'March',
'April',
'May',
'June',
'July',
];
const defaultData = [0, 10, 5, 2, 20, 30, 45];
Chart.defaults.global.defaultFontColor = '#f5eaea';
Chart.defaults.global.defaultFontFamily = 'Exo 2';
var chart = new Chart(ctx, {
type: 'line',
data: {
labels,
datasets: [
{
label: 'Confirmed for the last two weeks',
backgroundColor: '#feb72b',
borderColor: '#feb72b',
data,
},
],
},
options: {},
});
}

function setChartData(data) {
const chartData = data.slice(-14).map(value => value.Cases);
const chartLabel = data
.slice(-14)
.map(value => new Date(value.Date).toLocaleDateString().slice(5, -1));
renderChart(chartData, chartLabel);
}

function setTotalConfirmedNumber(data) {
confirmedTotal.innerText = data.Countries.reduce(
(total, current) => (total += current.TotalConfirmed),
0,
);
}

function setTotalDeathsByWorld(data) {
deathsTotal.innerText = data.Countries.reduce(
(total, current) => (total += current.TotalDeaths),
0,
);
}

function setTotalRecoveredByWorld(data) {
recoveredTotal.innerText = data.Countries.reduce(
(total, current) => (total += current.TotalRecovered),
0,
);
}

function setCountryRanksByConfirmedCases(data) {
const sorted = data.Countries.sort(
(a, b) => b.TotalConfirmed - a.TotalConfirmed,
);
sorted.forEach(value => {
const li = document.createElement('li');
li.setAttribute('class', 'list-item flex align-center');
li.setAttribute('id', value.Slug);
const span = document.createElement('span');
span.textContent = value.TotalConfirmed;
span.setAttribute('class', 'cases');
const p = document.createElement('p');
p.setAttribute('class', 'country');
p.textContent = value.Country;
li.appendChild(span);
li.appendChild(p);
rankList.appendChild(li);
});
}

function setLastUpdatedTimestamp(data) {
lastUpdatedTime.innerText = new Date(data.Date).toLocaleString();
}

startApp();
59 changes: 59 additions & 0 deletions project/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>코로나 세계 현황</title>
<link
href="https://fonts.googleapis.com/css?family=Exo+2&display=swap"
rel="stylesheet"
/>
<link rel="stylesheet" href="./main.css" />
</head>
<body>
<header class="flex justify-center">
<h1>코로나 세계 현황판</h1>
</header>
<main class="flex">
<div class="left-panel flex column">
<div class="total-board">
<p>Total Confirmed</p>
<span class="confirmed-total"></span>
</div>
<div class="country-ranks">
<p>Confirmed Cases by Country</p>
<ol class="rank-list"></ol>
</div>
<p class="last-updated-time flex justify-center align-center"></p>
</div>
<div class="right-panel">
<div class="summary-wrapper flex">
<div class="deaths-container">
<h3 class="summary-title">Total Deaths</h3>
<p class="total deaths">0</p>
<div class="list-wrapper">
<ol class="deaths-list"></ol>
</div>
</div>
<div class="recovered-container">
<h3 class="summary-title">Total Recovered</h3>
<p class="total recovered">0</p>
<div class="list-wrapper">
<ol class="recovered-list"></ol>
</div>
</div>
</div>
<div class="chart-container">
<canvas
id="lineChart"
class="corona-chart"
style="width: 100%; height: 356px; background-color: #5b5656;"
></canvas>
</div>
</div>
</main>
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/chart.js@2.8.0"></script>
<script src="./app.js"></script>
</body>
</html>
Loading

0 comments on commit 5988e02

Please sign in to comment.