첫 클론 프로젝트 Danstagram★
먼저 clone을 하기에 앞서 내가 이 프로젝트에서 무엇을 얻어갈 것인가에 대한 리스트 업을 했다.
✅ 우선 순위
- html - 시멘틱 구성 : 왜? 그 위치, 그 태그를 사용했는지 고민하며 작성하기
- css - flex속성 능숙하게 사용하기
- css- float:left에 대한 의존도 줄이기
☓☓ 우선 순위 아닌 것 (= 시선 뺐기지 말 것 제발..)
- 반응형 욕구
- "똑.같.이"의 구현의 집착 (픽셀 크기 , 폰트 스타일 등)
common - css
@import url('https://fonts.googleapis.com/css2?family=Lobster&display=swap');
*{
box-sizing:border-box;
margin:0;
padding:0;
}
body{
background:#fafafa;
}
ol, ul {
list-style:none;
}
p, span, div, a{
font-family: sans-serif;
}
button{
border:none;
}
a{
color:#000;
text-decoration:none;
}
button{
background: none;
cursor: pointer;
}
h1{
color:#262626;
font-family:'Lobster', cursive;
font-weight:100;
line-height: 1;
}
input, textarea{
outline:none;
}
아직 reset시트까지 나눌 규모가 아니라는 판단에 common 스타일시트에 다 작성했다.
다 손으로 직접 타이핑하기.
:: Refactoring 세션에서 guide 듣고 발등에 불 떨어짐
처음에 왼쪽 처럼 작성했다가 가독성이 떨어진다고 해서 세로로 다 고쳤다. 두 번 작업하는 거라 은근 시간이 걸려서, 그때 그때 한 섹션씩 수정하기로했다.
알아서 정렬해주는 툴도 있었지만, 손에 익숙하게 하고 싶어 번거로워도 하나씩 직접 수정해나갔다.
🌈 Login Page
✔️ html
<!DOCTYPE html>
<html lang="ko">
<head>
<!--META-->
<meta charset="UTF-8"/>
<mata http-equiv="X-UA-Compatible" content="IE=edge"/>
<meta name="viewport" content="width=device-width, initial-scale=1.0"/>
<!--TITLE-->
<title>Danstagram | Login</title>
<!--FAVICON-->
<link rel="shortcut icon" href="./favicon.ico" type="image/x-icon"/>
<!--CSS-->
<link rel="stylesheet" href="./style/common.css"/>
<link rel="stylesheet" href="./style/login.css"/>
</head>
<body>
<main class="container">
<h1>Danstagram</h1>
<!--LOGIN FORM-->
<form id="loginForm" class="login_wrap">
<input id="userId" type="text" placeholder="전화번호, 사용자 이름 또는 이메일"/>
<input id="userPw" type="password" placeholder="비밀번호"/>
<button id="btnLogin" type="submit">로그인</button>
</form>
<!--//LOGIN FORM-->
<a href="#n" class="lost_pw">비밀번호를 잊으셨나요?</a>
</main>
<script type="text/javascript" src="./js/login.js"></script>
</body>
</html>
button의 type=submit 속성에 대해 정확히 알게됐다.
지금까지 기분에 따라 a태그와 button을 기분에 따라 사용해왔는데😅 둘의 태생의 이유가 달랐다.
- <a>는 herf속성을 사용하는만큼 "페이지 간의 이동", "페이지 내의 다른 영역으로 이동"같은 hyperlink적 기능에 사용되어야 적합함.
- <button>은 UI의 조작. 또는 기능 구현, 데이터 전송에 사용됨.
- 팝업 창 띄우기, 클릭 시 요소에 효과를 주는 것, input내용 내용을 전송하는 기능.
- type의 default값은 submit이다. (submit : form내용 전송)
- submit을 위해 사용하지 않고 UI로써의 기능만을 담당할 때 는 type=button임을 명시해야함.
✔️ css
/**************************
LOGIN PAGE - LAYOUT
**************************/
html, body{
width: 100%;
height: 100%;
}
body{
display: flex;
justify-content: center;
align-items: center;
background: #fafafa;
}
.container{
display: flex;
flex-direction: column;
padding: 3em 2em;
background: #fff;
border: 1px solid #e8e8e8;
text-align: center;
}
h1{
margin-bottom: 40px;
font-size: 3.5em;
}
/**************************
LOGIN FORM
**************************/
form.login_wrap{
display: flex;
flex-direction: column;
}
.login_wrap input{
height: 45px;
padding: 0 20px;
margin-bottom: 10px;
color: #000;
background: #fafafa;
border-radius: 5px;
border: 1px solid #f1f1f1;
font-size: 1em;
}
.login_wrap input:focus{
border:1px solid #d6d6d6;
}
.login_wrap button{
height: 40px;
margin: 23px 0;
color: #fff;
background: #c4e1fb;
border-radius: 5px;
font-size: 1.2em;
line-height: 1;
text-align: center;
transition: all 0.3s;
cursor: default;
}
.login_wrap button.active{
background: #52adff;
cursor: pointer;
}
.lost_pw{
margin-top: 70px;
color: #3c5588;
}
🌈 Main Page
<!DOCTYPE html>
<html lang="ko">
<head>
<!--META-->
<meta charset="UTF-8"/>
<meta http-equiv="X-UA-Compatible" content="IE=edge"/>
<meta name="viewport" content="width=device-width, initial-scale=1.0"/>
<!--TITLE-->
<title>Danstagram | My feeds</title>
<!--FAVICON-->
<link rel="shortcut icon" href="./favicon.ico" type="image/x-icon"/>
<!--CSS-->
<link rel="stylesheet" href="./style/common.css"/>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.8.2/css/all.min.css"/>
<link rel="stylesheet" href="./style/main.css"/>
</head>
<body>
<!--HEADER-->
<header>
<div class="wrap">
<a href="#n" class="logo"><h1>Danstagram</h1></a>
<div class="search">
<input type="text" placeholder="검색"/>
<button><i class="fas fa-search"></i></button>
</div>
<nav class="gnb">
<ul>
<li class="research"><a href="#">탐색</a></li>
<li class="like"><a href="#">좋아요</a></li>
<li class="mypage"><a href="#">my profile</a></li>
</ul>
</nav>
</div>
</header>
<!--//HEADER-->
<!---MAIN--->
<main class="container wrap">
<aside>
<!--my profile-->
<div class="my_profile">
<a href="#n" class="profile_img">
<img alt="User profile image" class="round_img" src="./images/dan.jpg"/>
</a>
<span class="my_id">
<a href="#n" class="txt_id">My ID</a>
<p>My Nickname</p>
</span>
</div>
<!--WIDGET - story-->
<article class="widget stories">
<div class="widget_ttl">
<span>스토리</span>
<a href="#n">모두 보기</a>
</div>
<section class="list_story">
<div class="story">
<a href="#n" class="follower_img">
<img alt="follower profile image" class="round_img" src="./images/cat_01.png" />
</a>
<span class="user_id">
<a href="#n" class="txt_id">Fallowing ID</a>
<p>3h ago</p>
</span>
</div>
<div class="story">
<a href="#n" class="follower_img">
<img alt="follower profile image" class="round_img" src="./images/cat_02.png" />
</a>
<span class="user_id">
<a href="#n" class="txt_id">Fallowing ID</a>
<p>3h ago</p>
</span>
</div>
<div class="story">
<a href="#n" class="follower_img">
<img alt="follower profile image" class="round_img" src="./images/cat_03.png" />
</a>
<span class="user_id">
<a href="#n" class="txt_id">Fallowing ID</a>
<p>3h ago</p>
</span>
</div>
<div class="story">
<a href="#n" class="follower_img">
<img alt="follower profile image" class="round_img" src="./images/cat_04.png" />
</a>
<span class="user_id">
<a href="#n" class="txt_id">Fallowing ID</a>
<p>3h ago</p>
</span>
</div>
</section>
</article>
<!--//WIDGET - story-->
<!--WIDGET - recommend-->
<article class="widget recommends">
<div class="widget_ttl">
<span>회원님을 위한 추천</span>
<a href="#n">모두 보기</a>
</div>
<section class="list_recommend">
<div class="recommend">
<a href="#n" class="recommend_img">
<img alt="follower profile image" class="round_img" src="./images/dog_01.png" />
</a>
<span class="user_id">
<a href="#n" class="txt_id">recommender ID</a>
<p>follwor list</p>
</span>
<button type="button">팔로우</button>
</div>
<div class="recommend">
<a href="#n" class="recommend_img">
<img alt="follower profile image" class="round_img" src="./images/dog_02.png" />
</a>
<span class="user_id">
<a href="#n" class="txt_id">recommender ID</a>
<p>follwor list</p>
</span>
<button type="button">팔로우</button>
</div>
<div class="recommend">
<a href="#n" class="recommend_img">
<img alt="follower profile image" class="round_img" src="./images/dog_03.png" />
</a>
<span class="user_id">
<a href="#n" class="txt_id">recommender ID</a>
<p>follwor list</p>
</span>
<button type="button">팔로우</button>
</div>
</section>
</article>
<!--//WIDGET - recommend-->
<!--menu-->
<nav class="menu">
<ul>
<li><a href="#n">westagram 정보</a></li>
<li><a href="#n">지원</a></li>
<li><a href="#n">홍보센터</a></li>
<li><a href="#n">API</a></li>
<li><a href="#n">채용 정보</a></li>
<li><a href="#n">개인정보처리방침</a></li>
<li><a href="#n">약관</a></li>
<li><a href="#n">디렉터리</a></li>
<li><a href="#n">프로필</a></li>
<li><a href="#n">해시태그</a></li>
<li><a href="#n">언어</a></li>
</ul>
</nav>
<p class="copyright">©. 2021 WESTAGRAM</p>
</aside>
<!--FEED BOARD-->
<div class="feed_board">
<!--FEED COMPONENT-->
<article class="feed">
<!--top-->
<div class="new_poster">
<a href="#n" class="poster_img">
<img alt="follower profile image" class="round_img" src="./images/fallowing.png" />
</a>
<a href="#n" class="poster_id txt_id">Following ID</a>
<button><i class="fas fa-ellipsis-h"></i>옵션 더보기</button>
</div>
<!--content-->
<section class="feed_imgs">
<img alt="햄스터 사진" src="./images/cute_01.png" />
<div class="interactions">
<div class="my_emotion">
<button type="button"><i class="far fa-heart"></i>like</button></span>
<button type="button"><i class="far fa-comment"></i>write_comment</button></span>
<button type="button"><i class="far fa-paper-plane"></i>send_DM</button></span>
</div>
<div class="pagnation"></div>
<button type="button" class="bookmark"><i class="far fa-bookmark"></i>bookmark</button>
</div>
<p>
<a href="#n" class="like_user">
<img alt="like user image" class="round_img" src="./images/cat_01.png" />
<span class="txt_id">강당당</span>
</a>
님
<a href="#n" class="like_num txt_id">외 10명</a>
이 좋아합니다
</p>
</section>
<!--feed text-->
<section class="feed_txt">
<a href="#n" class="txt_id">User ID</a>
<span>건방진 고양이. 나의 찍찍 펀치를 받아라. <br/> 건방진 고양이. 나의 찍찍 펀치를 받아라. 건방진 고양이. 나의 찍찍 펀치를 받아라. 건방진 고양이. 나의 찍찍 펀치를 받아라. 건방진 고양이. 나의 찍찍 펀치를 받아라.</span>
<a href="#n" class="more">더보기</a>
</section>
<!--comment-->
<div class="comments">
<div id="listComment" class="list_comment">
<p class="txt_comment">
<span>
<a href="#n" class="txt_id">follow ID</a>
<span>나는 냥냥</span>
</span>
<button id="delete" type="button">X</button>
</p>
</div>
<form id="post" class="post_comment">
<textarea id="newComment" type="in" placeholder="댓글 달기..."></textarea>
<button id="btnPost" type="submit">게시</button>
</form>
</div>
</article>
</div>
<!--//FEED BOARD-->
</main>
<!---//MAIN--->
<script type="text/javascript" src="./js/main.js"></script>
</body>
</html>
main.html의 경우도 리팩토링을 한 번 거쳤지만, 아직 더 수정할 여지가 있다.
우선 레이아웃을 잡으면서 "instagram"은 어떤 서비스 인가? 에 대해 먼저 생각했다.
- 글 보다 이미지, 비디오 등의 콘텐츠 등 시각적 요소에 집중하며 성장한 서비스
- 릴스, 스토리 같은 short 영상 제작과 공유에 힘주고 있는 서비스
- 시각적인 부분의 강점으로 성장한 서비스에서 시각적 요소 없이도 좋은 사이트가 되기 위해선 어떻게 구성해야하나?
제공 받은 이미지는 예전 버전이지만, 현재 레이아웃과 번갈아보여 작업했다.
(건방지지만) 내 의견과는 다른 구성이 눈에 보여서 내 방식대로 작성한 후 그 이유를 기록해 두려고 한다.
👩🏻🦱 header
현재 인스타그램에서는 상단의 로고는 <div> 태그로 되어있고, "logo + search bar + menu"를 감싸는 태그가 <nav>로 되어있다.
하지만 나는 로고는 이 사이트의 가장 중요한 "제목"에 해당하는 분이고 '내가 지금 어느 사이트에 와있는가?'를 가장 분명하게 보여줘하는 요소라고 생각한다.
그래서 <h1>태그를 사용해 이 사이트의 유일무이한 제목의 역할을 줘야한다고 봤다.
오른쪽 상단의 "탐색하기, 좋아요 리스트 보기, 마이페이지"와 같이 다른 페이지로의 이동할 수 있는 리스트에는 <nav>가 적합하다고 생각한다.
그리고 <h1>, search bar, <nav>로 이 사이트가 구성하고자하는 요소들을 <header>로 묶어줬다.
+ 2022.12.08 변경된 생각 추가 👇
기획에 따라 <h1>역할이 "사이트 자체"를 기준으로 할 지, "해당 페이지의 주제(제목)"을 기준으로 할 지 달라진다.
특시 게시판형에서는 사이트이름보다 해당 게시글의 주제가 해당 게시물의 주제가 되듯이.
예를 들어 신문기사를 확인하는 페이지에서의 <h1>은 그 기사의 제목이지, "OO일보"같은게 아니라는 생각이다.
이 블로그만 봐도 게시글의 제목이 <h1>으로 잡힌다. (블로그명 역시 h1으로 잡힌다....)
h1의 역할을 상기하며 작업해야겠다.
💪 aside
이 페이지에서 눈에 딱! 들어와하는 요소는 feed의 사진이다.
이러헌 시각적 구성상 feed영역이 먼저(왼쪽부터) 노출되어있으니 먼저 작성해야한다고 생각했다.
하지만 'feed영역을 먼저 작성 하는 건 좋다'는 것엔 동의 해도 오른쪽의 '내 프로필, 스토리, 추천친구'가 밑에 작성되어야한다'는 것엔 동의할 수 없었다.
instagram은 모바일 기반의 서비스이고 모바일에서는 '스토리' 영역은 feed보다 상단에 배치 되는 요소다.
그리고 피드는 스크롤을 하면 할 수록 계속 다른 피드를 로드하는 구조라 '스토리'와 '추천친구' 등을 아래 붙여버리면 거의 못찾는 요소가 되어 버릴 것이다.
특히 '스토리'는 instagram의 두 번째 정체성이라고 해도 과언이 아니라고 생각하기에 feed영역 아래 위치할 요소라는 것에 동의 할 수 없었다.
(2021년 9월인 지금은 '스토리' 영역이 feed영역 위에 있음.)
이런 이유로 <aside>를 위로 작성하고 <footer>에 대한 고심을 하게 되는데...
🤦🏻♀️
'회사 정보, 개인정보 처리방침 등의 페이지 링크와 copyright문구는 보통 <footer>에 넣었는데.'
'<footer>태그를 중간에 넣은 적이 있던가?'
'일단 하단에 작성한 뒤 position으로 분리해서 위치를 올려잡아야 하나?' 하는 갈등
그냥 aside를 밑으로 내려버려?(괜히 복잡하게 생각하는 건가) 하는 생각까지 갔다가 나열된 링크를 하나하나 들어가보니, '이 사이트에 있음직한 페이지'나열들일 뿐이라는 생각이들었다. 그래서 <nav>로 처리했다.
🧥 article
각 feed는 하나의 독립적인 페이지로도 가능한 존재라고 생각해 <article>을 선택했다.
그리고 사진영역과 텍스트 영역을 <section>으로 나눴다.
하나의 <section>안에 넣어도 될 것같긴한데, 요즘 사진과 텍스트가 그리 종속적인 구성으로 사용되고 있진 않는 거같아 분리해보기로 했다.
✔️ css
/**************************
MAIN PAGE - COMMON
**************************/
.wrap{
width:935px;
margin:0 auto;
}
.round_img{
border-radius:50%;
}
.txt_id{
font-weight:bold;
}
/**************************
HEADER
**************************/
header{
position: fixed;
width: 100%;
background: #fff;
border-bottom: 1px solid #e8e8e8;
}
header .wrap{
display: flex;
align-items: center;
height: 100%;
padding: 15px 0;
}
header a.logo{
height: 20px;
background: url('../images/logo.png') 0 center / contain no-repeat;
}
header .logo h1{
height:100%;
margin-left:35px;
padding-left:15px;
border-left:1px solid #262626;
font-size:25px;
line-height:15px;
font-weight:100;
}
.search{
display: flex;
flex: 3.5;
padding: 0 5px;
margin: 0 15%;
background: #fafafa;
border: 1px solid #e8e8e8;
text-align: center;
}
.search input[type=text]{
position: relative;
flex: 9;
height: 25px;
background: none;
border: none;
}
.search button{
flex: 1;
color: #999;
}
.gnb{
flex: 1.5;
}
.gnb ul{
display: flex;
}
.gnb ul li{
position: relative;
flex: 2.5;
font-size: 0;
width: 25px;
height: 25px;
background-position: center center;
background-size: contain;
background-repeat: no-repeat;
}
.gnb ul li:before{
content: "";
position: absolute;
bottom: -7px;
left: 50%;
margin-left: -1.5px;
width: 4px;
height: 4px;
background: #e04141;
border-radius: 4px;
}
.gnb ul li.research{
background-image: url('https://s3.ap-northeast-2.amazonaws.com/cdn.wecode.co.kr/bearu/explore.png');
}
.gnb ul li.like{
background-image: url('https://s3.ap-northeast-2.amazonaws.com/cdn.wecode.co.kr/bearu/heart.png');
}
.gnb ul li.mypage{
background-image: url('https://s3.ap-northeast-2.amazonaws.com/cdn.wecode.co.kr/bearu/profile.png');
}
.gnb ul li.mypage:before{
display: none;
}
.gnb ul li a{
display: block;
height: 100%;
}
/**************************
MAIN LAYOUT
**************************/
main.wrap{
display: flex;
flex-direction: row-reverse;
padding: 80px 0 100px;
}
/**************************
ASIDE
**************************/
aside{
flex: 3.5;
}
/* my profile */
.my_profile{
display: flex;
align-items: center;
margin-bottom: 10px;
}
.my_profile a.profile_img{
flex:2;
}
.my_profile a.profile_img img{
width: 55px;
height: 55px;
}
.my_profile .my_id{
flex: 8;
}
.my_profile .my_id p{
color: #999;
}
/* WIDGET - common */
.widget{
background: #fff;
border: 1px solid #e8e8e8;
border-radius: 5px;
padding: 20px;
margin-bottom: 15px;
}
.widget_ttl{
display: flex;
justify-content: space-between;
margin-bottom: 10px;
font-size: 0.8em;
}
.widget_ttl span{
color: #999;
}
.widget .txt_id:hover{
text-decoration: underline;
}
/* WIDGET - story */
.stories{
padding-bottom: 0;
}
.list_story{
height: 200px;
overflow-y: scroll;
}
.list_story::-webkit-scrollbar{
width: 0;
}
.story{
display: flex;
align-items: center;
margin-bottom: 10px;
}
.story a.follower_img{
flex: 2;
}
.story a.follower_img img{
width: 45px;
height: 45px;
}
.story .user_id{
flex: 8;
}
.story .user_id p{
color: #999;
}
/* WIDGET - recommend*/
.recommends{
padding-bottom:5px;
}
.recommend{
display: flex;
align-items: center;
margin-bottom: 10px;
}
.recommend a.recommend_img{
flex: 2;
}
.recommend a.recommend_img img{
width: 45px;
height: 45px;
}
.recommend .user_id{
flex: 6;
}
.recommend .user_id p{
color: #999;
}
.recommend button{
flex: 2;
color: #0095f6;
font-size: 0.8em;
font-weight: 500;
}
/*menu*/
.menu ul li{
position: relative;
display: inline-block;
line-height: 1.5;
padding-right: 12px;
}
.menu ul li:before{
content: "";
position: absolute;
top: 50%;
right: 7px;
width: 2px;
height: 2px;
margin-top: -1px;
background: #b9b9b9;
}
.menu ul li a{
color: #999;
font-size: 0.8em;
}
.copyright{
color: #999;
font-size: 0.8em;
padding-top: 20px;
}
/**************************
FEED BOARD
**************************/
div.feed_board{
flex: 6.5;
margin-right: 15px;
}
/* FEED - common */
.feed{
background: #fff;
border: 1px solid #e8e8e8;
}
/* FEED - top */
.new_poster{
display: flex;
align-items: center;
padding: 10px 20px;
}
.new_poster .poster_img{
flex:1;
}
.new_poster .poster_img img{
width:45px;
height:45px;
}
.new_poster .poster_id{
flex: 18;
margin-left: 10px;
}
.new_poster button{
flex: 1;
font-size: 0;
text-align: right;
}
.new_poster button .fas{
flex: 0.4;
font-size: 12px;
}
/* FEED - content */
.feed_imgs img,
.feed_imgs video{
width: 100%;
}
.interactions{
display: flex;
align-items: center;
height: 50px;
padding: 0 10px;
}
.interactions button{
flex: 3;
margin: 0 10px;
font-size: 0;
}
.interactions button.bookmark{
flex: 1;
}
.interactions button .far{
font-size: 20px;
color: #676767;
}
.interactions .my_emotion{
display: flex;
flex: 2;
}
.pagnation{
flex:25;
}
.like_user img{
width: 25px;
height: 25px;
}
.feed_imgs p{
display: flex;
align-items: center;
padding: 10px 20px;
}
.feed_imgs p .like_user{
display: flex;
align-items: center;
}
.feed_imgs p .txt_id{
margin-left: 10px;
}
/* FEED - feed text */
.feed_txt{
padding: 0 20px;
}
.feed_txt .txt_id{
margin-right: 5px;
}
.feed_txt .more{
color: #999;
}
/*comments*/
.comments{
padding: 10px 20px;
}
.list_comment{
margin-bottom: 10px;
}
.txt_comment{
display:flex;
margin-bottom: 5px;
}
.txt_comment > span{
flex:9.8;
}
.txt_comment > span .txt_id{
margin-right: 10px;
}
.txt_comment > span span{
width: 100%;
}
.txt_comment button{
flex: 0.2;
color: #ddd;
}
.txt_comment button:hover{
color: #777;
}
.post_comment{
display: flex;
align-content: center;
padding: 20px 0 10px;
border-top: 1px solid #e8e8e8;
}
.post_comment textarea{
flex: 9;
height: 30px;
border: none;
resize: none;
}
.post_comment textarea::-webkit-scrollbar{
width: 0;
}
.post_comment button{
flex: 1;
color: #0095f6;
}
'D.evelop > Clone Projects' 카테고리의 다른 글
[Team project] 🍿MEGAFOX 🎞 - 회고 (0) | 2021.10.31 |
---|---|
[Team project] 🍿MEGAFOX 🎞 - 초기세팅 (0) | 2021.10.18 |
[Team project] ⚾️BBADDA 💢 - 회고 (0) | 2021.10.18 |
[clone project]Danstagram - js (Main page) (0) | 2021.09.13 |
[clone project]Danstagram - js (Login page) (0) | 2021.09.12 |
댓글