๐Ÿฅค [JS] Webucks Project(1)

luneahยท2021๋…„ 11์›” 22์ผ
0

Webucks Project

๋ชฉ๋ก ๋ณด๊ธฐ
1/10
post-thumbnail

[Mini Project] WeBucks-JS

[Mission 1~3] ๊ตฌํ˜„ (ํ•„์ˆ˜ ๊ตฌํ˜„ ์‚ฌํ•ญ)
โœจ ๊ตฌํ˜„ ๊ธฐ๊ฐ„ : 11/22~26

[Mission 1] ๋กœ๊ทธ์ธ ํŽ˜์ด์ง€ ๋ ˆ์ด์•„์›ƒ ๊ตฌํ˜„

  1. ๋กœ๊ณ ๋Š” ์•„๋ž˜ ๋‘˜ ์ค‘ ํ•˜๋‚˜์˜ ์กฐ๊ฑด์„ ๋งŒ์กฑ์‹œ์ผœ์ฃผ์„ธ์š”.
    • img ํƒœ๊ทธ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋กœ๊ณ ๋ฅผ ์ด๋ฏธ์ง€ ํŒŒ์ผ๋กœ ์ œ์ž‘
    • ํŠน์ • ํฐํŠธ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋กœ๊ณ ๋ฅผ ๋งŒ๋“ค์–ด์•ผ ํ•ฉ๋‹ˆ๋‹ค.(๊ธฐ๋ณธ ํฐํŠธ๊ฐ€ ์•„๋‹ˆ๋ผ ๊ตฌ๊ธ€ ํฐํŠธ์— ์žˆ๋Š” ์›ํ•˜์‹œ๋Š” ๋‹ค๋ฅธ ํฐํŠธ๋ฅผ ์‚ฌ์šฉํ•ด๋„ ๋ฌด๊ด€ํ•ฉ๋‹ˆ๋‹ค)
  2. ๋‹ค์Œ ์š”๊ตฌ์‚ฌํ•ญ์— ๋งž๊ฒŒ HTML์„ ์ž‘์„ฑํ•ด์ฃผ์„ธ์š”.
    • HTML์„ ์ž‘์„ฑํ• ๋•Œ๋Š”, ํ•ญ์ƒ ๋””์ž์ธ๋œ ํ™”๋ฉด์„ ๋ณด๋ฉด์„œ ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.
    • ์•„๋ž˜ ์ด๋ฏธ์ง€๋ฅผ ๋ณด๊ณ  ๋ ˆ์ด์•„์›ƒ์„ ์™„์„ฑํ•ด์ฃผ์„ธ์š”.
    • ๋กœ๊ทธ์ธ ๋ฐ•์Šค ์ „์ฒด๋ฅผ ๊ฐ์‹ธ๊ณ  ์žˆ๋Š” div ํ˜น์€ section ํƒœ๊ทธ๊ฐ€ ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.
    • form ํƒœ๊ทธ๋ฅผ ํ™œ์šฉํ•ด์ฃผ์„ธ์š”.
    • input ํƒœ๊ทธ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์•„์ด๋””, ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ์ž…๋ ฅํ•˜๋Š” ์ฐฝ์„ ๊ตฌํ˜„ํ•ด์ฃผ์„ธ์š”.
      • input์˜ ํƒ€์ž…์€ ๊ฐ๊ฐ text ํ˜น์€ password์ž…๋‹ˆ๋‹ค.
      • input์˜ ์†์„ฑ์œผ๋กœ placeholder๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ํ•ด๋‹น ์†์„ฑ์„ ์‚ฌ์šฉํ•˜์—ฌ "์ „ํ™”๋ฒˆํ˜ธ, ์‚ฌ์šฉ์ž ์ด๋ฆ„ ๋˜๋Š” ์ด๋ฉ”์ผ" ๋“ฑ์˜ ๊ฐ’์„ ๋„ฃ์–ด์ฃผ์‹œ๋ฉด ๋ฉ๋‹ˆ๋‹ค.
    • ๋กœ๊ทธ์ธ ๋ฒ„ํŠผ์€ button ํƒœ๊ทธ๋ฅผ ์‚ฌ์šฉํ•ด์ฃผ์„ธ์š”.

[ Result ]
- display: flex ์†์„ฑ ํ™œ์šฉํ•˜์—ฌ body, div, form ์ •๋ ฌ

๐Ÿ’ก Tip!

  1. opacity ์†์„ฑ์„ ํ™œ์šฉํ•˜๋ฉด ๊ฐ™์€ ์ƒ‰์ƒ์ด๋”๋ผ๋„ ํˆฌ๋ช…๋„๋ฅผ ์กฐ์ •ํ•˜์—ฌ ๋ณด์—ฌ์ค€๋‹ค.
button {
  background-color: #0096f6;
  opacity: 0.5; 	/* ํˆฌ๋ช…๋„ 50% */
}

button.active {
  background-color: #0096f6;
  opacity: 1; 		/* ํˆฌ๋ช…๋„ 0% */
}
  1. a ํƒœ๊ทธ๋ฅผ ์ ์šฉํ•˜๋ฉด ๋ฐ‘์ค„์ด ์ƒ๊ธฐ๋Š”๋ฐ ์ด๋ฅผ ์ง€์›Œ์ฃผ๋Š” css ์„ค์ •์ด๋‹ค.
a {
 text-decoration-line: none;
}


[Mission 2] ๋กœ๊ทธ์ธ ํŽ˜์ด์ง€ ๊ธฐ๋Šฅ ๊ตฌํ˜„

  1. id์— @๊ฐ€ ํฌํ•จ๋˜๊ณ , password๊ฐ€ 8์ž ์ด์ƒ์ด ๋˜๋ฉด ๋ฒ„ํŠผ์ด ํ™œ์„ฑํ™” ๋˜๋„๋ก ํ•ด์ฃผ์„ธ์š”.
    • ์›๋ž˜ ์—ฐํ•œ ํŒŒ๋ž€์ƒ‰์ด์—ˆ๋‹ค๊ฐ€ ํ™œ์„ฑํ™” ๋˜๋ฉด ๋ฐ๊ณ  ์ง„ํ•œ ํŒŒ๋ž€์ƒ‰์œผ๋กœ ๋ณ€๊ฒฝ
  2. id, password๊ฐ€ ์กฐ๊ฑด์— ๋งž์„ ๋•Œ ๋กœ๊ทธ์ธ ๋ฒ„ํŠผ์„ ๋ˆ„๋ฅด๋ฉด list ํŽ˜์ด์ง€๋กœ ์ด๋™ํ•ด์•ผ ํ•ฉ๋‹ˆ๋‹ค.

[ login.html ]

<form class="loginBox">
    <input class="id" type="text" placeholder="์ „ํ™”๋ฒˆํ˜ธ, ์‚ฌ์šฉ์ž ์ด๋ฆ„ ๋˜๋Š” ์ด๋ฉ”์ผ">
    <input class="pw" type="password" placeholder="๋น„๋ฐ€๋ฒˆํ˜ธ">
    <button class="loginBtn">๋กœ๊ทธ์ธ</button>
</form>

[ login.css ]

button.active {
  background-color: #0096f6;
  opacity: 1;
  cursor: pointer;
  font-weight: bold;
}

[ login.js ]

  • ์‚ผํ•ญ ์—ฐ์‚ฐ์ž ์‚ฌ์šฉ
    • id์— '@' ํฌํ•จ, pw ๊ธธ์ด 8๊ธ€์ž ์ด์ƒ : active ์ถ”๊ฐ€, onclick ์ด๋ฒคํŠธ ํ™œ์„ฑํ™”
    • ์•„๋‹Œ ๊ฒฝ์šฐ : active ์‚ญ์ œ, onclick ์ด๋ฒคํŠธ ๋น„ํ™œ์„ฑํ™” โ†’ ์ž…๋ ฅํ–ˆ๋‹ค ์ง€์› ์„ ๋•Œ๋„ ๋น„ํ™œ์„ฑํ™”๋กœ ๋งŒ๋“ค์–ด์คŒ.
const loginBox = document.querySelector('.loginBox');
const loginBtn = document.querySelector('.loginBtn');

loginBox.onkeyup = function () {
    let userId = document.querySelector('.id').value;
    let userPw = document.querySelector('.pw').value;
    ((userId.includes('@')) && (userPw.length >= 8))
    ? (loginBtn.classList.add('active'), loginBtn.onclick = moveList) : (loginBtn.classList.remove('active'), loginBtn.onclick=null);
};

function moveList(e) {
    e.preventDefault();
    window.location.href = "list.html";
}

[ Result ]

โญ๏ธ Struggle Point : ์กฐ๊ฑด์— ๋งž๊ฒŒ ์ž…๋ ฅํ–ˆ๋‹ค ์ง€์› ์„ ๋•Œ๋„ ํ™œ์„ฑํ™” ์ƒํƒœ์ธ ๋ฒ„ํŠผ

์ฃผ์–ด์ง„ ์กฐ๊ฑด์— ๋งž๊ฒŒ ์ž…๋ ฅํ–ˆ์„ ๋•Œ ๋กœ๊ทธ์ธ ๋ฒ„ํŠผ ํ™œ์„ฑํ™” ๋๊ณ  ๋ฆฌ์ŠคํŠธ ํŽ˜์ด์ง€๋กœ ๋„˜์–ด๊ฐ„๋‹ค. ๊ทธ๋Ÿฌ๋‚˜ ์กฐ๊ฑด์— ๋งž๊ฒŒ ์ž…๋ ฅํ–ˆ๋‹ค ์ง€์› ์„ ๋•Œ๋„ ๋ฆฌ์ŠคํŠธ ํŽ˜์ด์ง€๋กœ ๋„˜์–ด๊ฐ€๋Š” ํ˜„์ƒ์ด ๋ฐœ์ƒํ–ˆ๊ณ  ์ด๋ฅผ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•ด ํ•ด๋‹น ์ด๋ฒคํŠธ์ธ onclick์„ null๋กœ ์„ค์ •ํ•˜์—ฌ ํด๋ฆญํ–ˆ์„ ๋•Œ ๋ฐœ์ƒํ•˜๋Š” ํ•จ์ˆ˜๋ฅผ ํ•ด์ œํ•ด์คฌ๋‹ค.



[Mission 3] ์ปคํ”ผ ๋ฆฌ์ŠคํŠธ ํŽ˜์ด์ง€ ๋ ˆ์ด์•„์›ƒ ๊ตฌํ˜„

  1. HTML, CSS๋กœ๋งŒ ์•„๋ž˜ ์Šคํƒ€๋ฒ…์Šค ๋ฆฌ์ŠคํŠธ ํŽ˜์ด์ง€๋ฅผ ๊ตฌํ˜„ํ•ด์ฃผ์„ธ์š”.
  2. ์‹ค์ œ ํŽ˜์ด์ง€๊ฐ€ ์•„๋‹ˆ๋ผ ์•„๋ž˜ ์ด๋ฏธ์ง€์— ์žˆ๋Š” ๋ถ€๋ถ„๋งŒ ๊ตฌํ˜„ํ•ด์ฃผ์„ธ์š”.
  3. ์ฝœ๋“œ ๋ธŒ๋ฃจ ์ปคํ”ผ, ๋ธŒ๋ฃจ๋“œ ์ปคํ”ผ ๋‘ ์ข…๋ฅ˜์— ๋Œ€ํ•ด์„œ ๋งŒ๋“ค์–ด์ฃผ์„ธ์š”.
    • ์ปคํ”ผ ์‚ฌ์ง„๊ณผ ์ด๋ฆ„์€ ๋ชจ๋‘ ๋‹ค๋ฅด๊ฒŒ ํ•ด์ฃผ์„ธ์š”.
    • ๋ฐ˜์‘ํ˜•์„ ๊ณ ๋ คํ•˜์ง€ ์•Š์œผ์…”๋„ ๊ดœ์ฐฎ์Šต๋‹ˆ๋‹ค.
    • ๋ฐ˜์‘ํ˜•์„ ๊ณ ๋ คํ•˜์‹ ๋‹ค๋ฉด ์ปคํ”ผ ๋ฆฌ์ŠคํŠธ๋Š” flex-wrap ํ˜น์€ grid๋ฅผ ํ™œ์šฉํ•ด์ฃผ์„ธ์š”.
  4. ์ปคํ”ผ ์ด๋ฏธ์ง€์— ๋งˆ์šฐ์Šค๋ฅผ ํ˜ธ๋ฒ„ํ–ˆ์„ ๋•Œ ์ด๋ฏธ์ง€๋ฅผ ํ™•๋Œ€ํ•ด์ฃผ์„ธ์š”.
    • ์ด ํšจ๊ณผ๋Š” ์‹ค์ œ ์Šคํƒ€๋ฒ…์Šค ํŽ˜์ด์ง€๋ฅผ ์ฐธ๊ณ ํ•ด์ฃผ์„ธ์š”!

[list.html]

<div class="wrapper">
    <div class="img">
        <div class="scale"><img src="img/coffee.jpg" alt="ํ† ํ”ผ๋„› ์ฝœ๋“œ ๋ธŒ๋ฃจ"></div>
        <p>ํ† ํ”ผ๋„› ์ฝœ๋“œ ๋ธŒ๋ฃจ &nbsp;<i class="far fa-heart"></i></p>
    </div>
    <div class="img">
        <div class="scale"><img src="img/coffee1.jpg" alt="๋‚˜์ดํŠธ๋กœ ๋ฐ”๋‹๋ผ ํฌ๋ฆผ"></div>
        <p>๋‚˜์ดํŠธ๋กœ ๋ฐ”๋‹๋ผ ํฌ๋ฆผ &nbsp;<i class="far fa-heart"></i></p>
    </div>
    <div class="img">
        <div class="scale"><img src="img/coffee2.jpg" alt="๋‚˜์ดํŠธ๋กœ ์ฝœ๋“œ ๋ธŒ๋ฃจ"></div>
        <p>๋‚˜์ดํŠธ๋กœ ์ฝœ๋“œ ๋ธŒ๋ฃจ &nbsp;<i class="far fa-heart"></i></p>
    </div>
    <div class="img">
        <div class="scale"><img src="img/coffee3.jpg" alt="๋Œ์ฒด ์ฝœ๋“œ ๋ธŒ๋ฃจ"></div>
        <p>๋Œ์ฒด ์ฝœ๋“œ ๋ธŒ๋ฃจ &nbsp;<i class="far fa-heart"></i></p>
    </div>
</div>

[list.css]

  • ์ „์ฒด๋ฅผ ๊ฐ์‹ธ๋Š” div์— flex-wrap ์†์„ฑ ์ด์šฉํ•ด ๋ฉ”๋‰ด ์ •๋ ฌ
  • transform: scale() ์ด์šฉํ•ด ์ด๋ฏธ์ง€ ํ™•๋Œ€
    • ํ™•๋Œ€๋˜์–ด ํŠ€์–ด๋‚˜๊ฐ€๋Š” ๋ถ€๋ถ„ overflow: hidden์œผ๋กœ ์ˆจ๊ฒจ์ฃผ๊ธฐ
    • ๋ถ€๋“œ๋Ÿฝ๊ฒŒ ํ™•๋Œ€/์ถ•์†Œ ์‹œํ‚ค๊ธฐ ์œ„ํ•ด transition: all ease-in-out ์ฃผ๊ธฐ
.wrapper {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  padding: 0px 20%;
  text-align: center;
}

.scale {
  height: 200px;
  width: 200px;
  overflow: hidden;
}

.scale img {
  height: 100%;
  width: 100%;
  object-fit: cover;
  transform: scale(1);
  transition: all 0.5s ease-in-out;
}

.scale img:hover {
  cursor: pointer;
  transform: scale(1.1);
  transition: all 0.5s ease-in-out;
}

[ Result ]

  • ์ „์ฒด ๋ ˆ์ด์•„์›ƒ

  • ์ด๋ฏธ์ง€์— ๋งˆ์šฐ์Šค ํ˜ธ๋ฒ„ ์‹œ : ์ด๋ฏธ์ง€ ํ™•๋Œ€

โญ๏ธ Struggle Point 1 : ์ด๋ฏธ์ง€ ๋ฐฐ์น˜ ์‹œ ์ด๋ฏธ์ง€ ๊ฐ„ ๊ฐ„๊ฒฉ ์กฐ์ •

flex-wrap: wrap ์†์„ฑ๋งŒ์œผ๋กœ๋Š” ์ด๋ฏธ์ง€๊ฐ€ ๋ชจ๋‘ ๋ถ™์–ด์žˆ๊ฒŒ ๋˜๋ฏ€๋กœ justify-content: space-between์œผ๋กœ ๊ฐ„๊ฒฉ ์กฐ์ •, ๋˜ํ•œ padding ์ด์šฉํ•ด ์ „์ฒด์ ์ธ ์ด๋ฏธ์ง€์˜ ์œ„์น˜๋ฅผ ์กฐ์ •ํ•ด์ฃผ์—ˆ๋‹ค.

โญ๏ธ Struggle Point 2 : ์ด๋ฏธ์ง€ ํ™•๋Œ€์‹œ ํŠ€์–ด๋‚˜๊ฐ€๋Š” ๋ถ€๋ถ„ ๋ฐœ์ƒ

์ด๋ฏธ์ง€์— ๋งˆ์šฐ์Šค๋ฅผ ํ˜ธ๋ฒ„ํ–ˆ์„ ๋•Œ ํ™•๋Œ€ํ•˜๋Š” ์• ๋‹ˆ๋ฉ”์ด์…˜์€ ๊ตฌํ˜„ํ•˜์˜€์œผ๋‚˜ ์›๋ž˜ ์‚ฌ์ง„ ํฌ๊ธฐ์—์„œ ๋ฒ—์–ด๋‚˜ ๊ธ€์”จ ๋ถ€๋ถ„์„ ์นจ๋ฒ”ํ•˜๊ฒŒ ๋˜์–ด ์ด๋ฅผ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•ด overflow: hidden์„ ์ฃผ์–ด ํŠ€์–ด๋‚˜๊ฐ€๋Š” ๋ถ€๋ถ„์„ ๊ฐ€๋ ค์ฃผ์—ˆ๋‹ค.

profile
ํ•˜๋Š˜์ด์˜ ๊ฐœ๋ฐœ ์ผ๊ธฐ

0๊ฐœ์˜ ๋Œ“๊ธ€