
ě´ě  ęłľëśěě ě´ě´ě
đ ěě  ë˛íź í´ëŚ ě ëĄěťŹ ě¤í 댏ě§ě ě ěĽë todos í¨ęť ěě í기
í´ëŚí todoę° ëŹ´ěě¸ě§ ěŚ, ěě í´ěź í  todoę° ëŹ´ěě¸ě§ ě ě ěëëĄ todos ë°°ě´ě ěě íë¤. ěëë todos í
ě¤í¸ë§ todos ë°°ě´ě push í´ě¤Źě§ë§, todos í
ě¤í¸ëĽź ęł ě ě idě í¨ęť newTodoObjectě ë´ě todos ë°°ě´ě push í´ěŁźěë¤. ęł ě ě idë ë°ëŚŹě´ëĽź ë°ííë Date.now()뼟 ě´ěŠí´ ë§ë¤ěë¤.
í늴ě to do list뼟 íěí기 ěí´ li ěě뼟 ë§ë¤ ë ꡸ ěěě id ę°ěźëĄ todo ě¤ë¸ě í¸ě id뼟 ëŁě´ěŁźěë¤. ě´ë todo ě¤ë¸ě í¸ě idë ěŤěě¸ ë°ëŠ´, li í꡸ě idë 돸ěě´ě´ë¤.
ěě  ë˛íźě í´ëŚí´ í늴ěě í´ëš to do list뼟 ěě í  ë, ě´íě ěëĄęł ěš¨ě í´ë ěŹě í ěě í to do listë í늴ě ëł´ě´ě§ ěëëĄ, ëĄěťŹ ě¤í ëŚŹě§ěěë to do list뼟 ěě íęł ě íë¤. li ěěë§ë¤ ě¤ě í´ě¤ id ę°ęłź array.filter()뼟 ě´ěŠí´ todos ë°°ě´ě ě
ë°ě´í¸í´ě¤ í, ě´ëĽź ë°íěźëĄ saveToDos() í¨ě뼟 ě¤íí´ ëĄěťŹ ě¤í ëŚŹě§ë ě
ë°ě´í¸í´ě¤ë¤.
const toDoForm = document.querySelector('#todo-form');
const toDoInput = toDoForm.querySelector('input');
const toDoList = document.querySelector('#todo-list');
const TODOS_KEY = 'todos';
let todos = [];
function saveToDos() {
  localStorage.setItem(TODOS_KEY, JSON.stringify(todos));
}
function deleteToDo(event) {
  const li = event.target.parentNode;
  li.remove();
  todos = todos.filter(todo => todo.id!== parseInt(li.id)); // todos ë°°ě´ ě
ë°ě´í¸ í
  saveToDos(); // ě´ëĽź ë°íěźëĄ ëĄěťŹ ě¤í ëŚŹě§ë ě
ë°ě´í¸ í´ě¤ěź íë¤ !
}
function paintToDo(newToDo) {
  const li = document.createElement('li');
  li.id = newToDo.id; // li ěěě id ę° ëśěŹ
  const span = document.createElement('span');
  span.innerText = newToDo.text;
  const delBtn = document.createElement('button');
  delBtn.innerText = 'â';
  delBtn.addEventListener('click', deleteToDo);
  li.appendChild(span);
  li.appendChild(delBtn);
  toDoList.appendChild(li);
}
function onToDoSubmit(event) {
  event.preventDefault();
  const newToDo = toDoInput.value;
  toDoInput.value = '';
  const newToDoObject = { text: newToDo, id: Date.now() };
  todos.push(newToDoObject); // ęł ě ě id ę°ęłź todo í
ě¤í¸ëĽź 모ë ë´ęł  ěë ě¤ë¸ě í¸ëĽź todos ë°°ě´ě push
  paintToDo(newToDoObject);
  saveToDos();
}
toDoForm.addEventListener('submit', onToDoSubmit);
const savedToDos = localStorage.getItem(TODOS_KEY);
if (savedToDos) {
  const parsedToDos = JSON.parse(savedToDos);
  todos = parsedToDos;
  parsedToDos.forEach(todo => paintToDo(todo));
}
navigator.geoloction.getCurrentPosition() ëŠěë뼟 ě´ěŠí´ ěŹěŠěě íěŹ ěěš(ěëě 경ë)뼟 ë°ěěŹ ě ěë¤.đĄ navigator.geoloction.getCurrentPosition(ěąęłľ ě ě˝ë°ą í¨ě, ě¤í¨ ě ě˝ë°ą í¨ě)
ě¸ěëĄ ë¤ě´ę°ë ě˝ë°ą í¨ěë¤ě
ěěš ě ëł´ ę°ě˛´ëĽź ě ěźí ě¸ěëĄ ë°ëë¤
function onGeoOk(position) { // position : ěěš ě ëł´ ę°ě˛´
  const lat = position.coords.latitude;
  const lon = position.coords.longitude;
}
function onGeoError() {
  alert("Can't find you. No weather for you.");
}
navigator.geolocation.getCurrentPosition(onGeoOk, onGeoError);
đĄ ë ě¨ ě 보뼟 ěë ¤ěŁźë API
http://openweathermap.org(ä¸ Current weather data)ěě city name, geographic coordinates ëąě íľí´ í´ëš ě§ěě ë ě¨ëĽź ě ě ěë¤.
ex.
ě§ëŚŹ ě˘í뼟 ě´ěŠí´ ë ě¨ ě 보뼟 ěťě´ě¤ë ë°Šë˛https://api.openweathermap.org/data/2.5/weather?lat=${lat}&lon=${lon}&appid=${API_KEY}&units=metric
ě urlě ěëě 경ë ě 보뼟 ě ë Ľí늴, í´ëš urlě´ ë ě¨ ě 보뼟 ěëľíë¤. (units=metric ěľě ě ěśę°í늴, íě¨ ě¨ë뼟 ěě¨ ě¨ëëĄ ě¸Ąě  ë¨ě뼟 ë°ężě¤ë¤.)
[TIL] 210920 3.fetch API ëśëś ě°¸ęł
fetch()뼟 ě´ěŠí´ ě urlě ëśëĽ´ëëĄ íë¤. ě ëëĄ ëśëŹěëě§ë ę°ë°ě ë꾏ě ë¤í¸ěíŹ íěě íě¸í´ëłź ě ěë¤.const API_KEY = 'ec0fa8b152f1731f40ff6e8e9a1e9328';
const url = `https://api.openweathermap.org/data/2.5/weather?lat=${lat}&lon=${lon}&appid=${API_KEY}&units=metric`;
fetch(url);
<div id="weather">
  <span></span>
  <span></span>
</div>
const API_KEY = 'ec0fa8b152f1731f40ff6e8e9a1e9328';
function onGeoOk(position) {
  const lat = position.coords.latitude;
  const lon = position.coords.longitude;
  const url = `https://api.openweathermap.org/data/2.5/weather?lat=${lat}&lon=${lon}&appid=${API_KEY}&units=metric`;
  fetch(url).then(response => response.json()).then(data => {
    const weather = document.querySelector('#weather span:first-child');
    const name = document.querySelector('#weather span:last-child');
    weather.innerText = `${data.weather[0].main} / ${data.main.temp}â`;
    name.innerText = data.name;
  });
}
function onGeoError() {
  alert("Can't find you. No weather for you.");
}
navigator.geolocation.getCurrentPosition(onGeoOk, onGeoError);