Implementing Simple Programs Using JS

Clock

<h2 id="clock">00:00</h2>

위의 clock을 구현하기 위해 JavaScript에서 제공하는 setTimeout과 setInterval 함수에 대해서 알아야한다.

function sayHello(){
    console.log("hello");
}
//1000ms 마다 sayHello 실행
setInterval(sayHello,1000);
//500ms 이후에 sayHello 함수 실행
setTimeout(sayHello,500);

setInterval를 하게 되면 첫번째 인자로 전달된 콜백함수를, 두번째 인자로 전달된 시간값에 따라 계속해서 반복해서 실행하게 된다.

setTimeout를 이용하면 첫번째 인자로 전달된 콜백함수를, 두번째 인자로 전달된 시간값 만큼 기다린 후 한번만 실행한다

따라서 시계를 구현하기 위해 1초마다 h2 tag의 값을 바꿔주는 setInterval 함수를 이용한다.

const clock=document.querySelector("h2#clock");

function getClock(){
    const date=new Date();
    const hours=String(date.getHours()).padStart(2,"0");
    const minutes=String(date.getMinutes()).padStart(2,"0");
    const seconds=String(date.getSeconds()).padStart(2,"0");
    const date_String=`${hours}:${minutes}:${seconds}`
    //console.log(date_String);
    clock.innerText=date_String;
}
//초기에 한번 실행해서 시계를 표시하고
getClock();
//매초마다 시계 최신화
setInterval(getClock,1000);

Quotes

    <div id="quote">
        <span></span>
        <span></span>
    </div>
const quotes=[
    {
        quote:"The purpose of our lives is to be happy.",
        author:"Dalai Lama"
    },
    ...
]

const quote= document.querySelector("div#quote span:first-child");
const author=document.querySelector("div#quote span:last-child");

randomIndex=Math.floor(Math.random()*quotes.length);

const todayQuote=quotes[Math.floor(Math.random()*quotes.length)];

quote.innerText=todayQuote.quote;
author.innerText=todayQuote.author;

위와 같이 Math의 random function을 이용해서 인덱스를 무작위로 선택할 수 있도록 한다.

Background Image

const images=["img1.jpg","img2.jpg","img3.jpg"];
const chosenImage=images[Math.floor(Math.random()*images.length)];

const bgImage=document.createElement("img");
bgImage.src=`img/${chosenImage}`;

document.body.appendChild(bgImage);

background image 구현 부분 또한 quote 부분과 매우 유사하다. 여기서 다루고 있는 중요한 부분은 javascript을 이용해서 html element을 만들고 이를 배치하는 부분이다.

html_element=document.createElement(tagname)
document.appendChild(html_element=)

위와 같이 createElement 함수를 이용해서 원하는 tag의 html을 만들 수 있고, 이를 appendChild을 이용해서 기존의 html에 추가한다.

TO DO LIST

    <form id="todo-form">
        <input type="text" required placeholder="Write a To Do and press Enter "/>
    </form>
    <ul id="todo-list"></ul>
const toDoForm=document.getElementById("todo-form");
const toDoList=document.getElementById("todo-list");
const toDoInput=toDoForm.querySelector("input");
let toDos=[];
const TODOS_KEY="todos"

Adding to Local Storage

function saveToDos(){
    localStorage.setItem(TODOS_KEY,JSON.stringify(toDos));
}

Local Storage에 저장할때에는 javascript list 형태 그대로 저장하기 위해 JSON 형태로 변환해주는 JSON.stringify function을 활용

Adding TO DO

Adding Html list element


function paintToDo(newToDoObj){
    const li=document.createElement("li");
    li.id=newToDoObj.id;
    const span=document.createElement("span");
    span.innerText=newToDoObj.text;
    const button=document.createElement("button");
    button.innerText="X";

    button.addEventListener("click",deleteToDo);

    li.appendChild(span);
    li.appendChild(button);
    toDoList.appendChild(li);
}

각각의 to do list을 생성할 떄, span,button tag를 만들어서 이를 ul tag에 추가시켜준다.

Event Handler

function handleToDoSubmit(event){
    event.preventDefault();
    const newToDo=toDoInput.value;
    toDoInput.value="";
    const newToDoObj={text:newToDo,id:Date.now()};
    toDos.push(newToDoObj);
    paintToDo(newToDoObj);
    saveToDos();
}
//만약 이미 local storage에 저장되어 있는 to do list가 이미 있는 경우, localStorage로 부터 기존의 내용들을 받아온다.
const savedToDos=localStorage.getItem(TODOS_KEY);
if(savedToDos){
    const parsedToDos=JSON.parse(savedToDos);
    toDos=parsedToDos;
    parsedToDos.forEach(paintToDo)
    
}

toDoForm.addEventListener("submit",handleToDoSubmit);

매번 to do 가 입력되면 실행되는 event handler이다. 나중에 to do list를 개별적으로 삭제할 수 있도록 하기 위해 미리 ID를 부여하는데, 이때 Date.now를 통해 1/1000 ms 단위의 시간값을 활용

localStorage에 JSON 형태로 저장되어있는 data를 의미있는 Javascript object으로 변환하기 JSON.parse를 이용한다.

Deleting TO DO

function deleteToDo(event){
    const li=event.target.parentElement;
    toDos=toDos.filter((item) => item.id !== parseInt(li.id));
    li.remove();
    saveToDos();
}

알다시피, event handler에는 javascript에서 기본적으로 event에 대한 정보를 인자로 전달해준다. 따라서 이를 이용해서 쉽게 어떤 html element에서 event를 발생시켰는지 확인가능하다.

javascript에서는 filter함수가 존재하는데, 각각의 리스트의 원소에 대해 filter함수에 정의된 함수값을 검증해서 TRUE이면 남기고, FALSE 인경우 리스트에서 제거한다.

Weather

    <div id="weather">
        <span></span>
        <span></span>
    </div>

Geolocation

console.log(navigator.geolocation.getCurrentPosition(onGeoOk,onGeoError))

위와 같이 onGeok 콜백이 실행되면, 사용자의 위도,경도값을 알아낼 수 있다. –> 이를

javascript에서는 아래와 같은 geolocation과 같은 내장 객체가 존재하는데 이는 현재 사용자의 위치를 알고자 할때 사용할 수 있다. geolocationd의 getCurrentPosition에 전달해야하는 인자는, 위치를 받아오는 것에 성공했을때의 콜백함수와 위치를 받아오는 것에 실패했을 때의 콜백함수이다. 또한 기본적으로 성공했을 때의 콜백함수에는 javascript에서 위치에 대한 정보를 객체형태로 전달해서 실행한다.

API

const API_KEY="";

function onGeoOk(position){
    const lat=position.coords.latitude;
    const lng=position.coords.longitude;
    console.log("you live in ",lat,lng);
    const url=`https://api.openweathermap.org/data/2.5/weather?lat=${lat}&lon=${lng}&appid=${API_KEY}&units=metric`
    
    fetch(url)
        .then(response => response.json())
        .then(data => { 
            const weather=document.querySelector("#weather span:first-child");
            const city=document.querySelector("#weather span:last-child");

            city.innerText=data.name;
            weather.innerText=`${data.weather[0].main}/${data.main.temp}`;
        })

    }

function onGeoError(){
    alert("Can't find you")
}
`https://api.openweathermap.org/data/2.5/weather?lat=${lat}&lon=${lng}&appid=${API_KEY}&units=metric`

사용자의 위도,경도값을 이용해서 날씨를 알아내기 위해 API를 활용한다. 위와 같이 위도,경도,api_key를 전달하면 아래와 같이 날씨에 관한 object가 반환된다.

{
    "coord": {
        "lon": 139,
        "lat": 35
    },
    "weather": [
        {
            "id": 804,
            "main": "Clouds",
            "description": "overcast clouds",
            "icon": "04d"
        }
    ],
    "base": "stations",
    "main": {
        "temp": 21.65,
        "feels_like": 22.14,
        "temp_min": 21.65,
        "temp_max": 21.65,
        "pressure": 1009,
        "humidity": 87,
        "sea_level": 1009,
        "grnd_level": 982
    },
    "visibility": 10000,
    "wind": {
        "speed": 0.76,
        "deg": 218,
        "gust": 2.01
    },
    "clouds": {
        "all": 100
    },
    "dt": 1653551893,
    "sys": {
        "type": 1,
        "id": 8070,
        "country": "JP",
        "sunrise": 1653507246,
        "sunset": 1653558493
    },
    "timezone": 32400,
    "id": 1851632,
    "name": "Shuzenji",
    "cod": 200
}

Final Result

References

link: nomadcoders

댓글남기기