이번 회차 교육에서는 플렉스 박스와 웹 페이지 클론 코딩 위주로 진행한다.

0. CSS 레이아웃

레이아웃(layout)이란? '구성 요소를 공간에 효과적으로 배열하는 일, 또는 기술'을 뜻한다.

CSS 레이아웃은 웹 요소를 올바른 장소에 배치하는 기술이다.
CSS 레이아웃 기술은 형제 요소들을 가지런히 정렬할 수 있게 해주며, 요소가 컨테이너 내부에서 어떤 위치에 놓이게 될지 결정할 수 있다. (색상, 크기, 위치)

  • 대표적인 CSS 레이아웃 기술들
    - 일반적인 문서 흐름
    - display 속성
    - "플렉스 박스"
    - 그리드 레이아웃
    - float 속성
    - position 속성
    - 기타 등등...
    (출처: CSS 레이아웃 입문서, MDN)

1. 플렉스 박스 레이아웃

01. 플렉스 박스(flexbox)

플렉스 박스란, 행 또는 열을 주축으로 설정하여 웹 요소를 배치 및 정렬하는 1차원 레이아웃 방식을 말한다.

플렉스 박스 방식에서 요소의 배치와 정렬은 " 플렉스 컨테이너와 플렉스 아이템 간의 상호작용 "을 통해 결정된다.

  • 플렉스 컨테이너: 개발자가 플렉스 박스 방식으로 레이아웃을 결정(지정)할 요소

  • 플렉스 아이템: 플렉스 컨테이너 내부에서 플렉스 박스 방식으로 배치되는 (자식) 요소


02. 플렉스 박스 방식

1. display: flex;

기본적으로 flex로 지정이 된 컨테이너는 블록 레벨 요소이며, 그 안에 있는 요소들의 배치 및 정렬이 플렉스 박스 방식으로 이루어진다.

2. display: inline-flex;

플렉스 컨테이너가 인라인 레벨 요소이길 원한다면 이렇게 사용하면 된다.


03. 중요 개념 - 축⭐

플렉스 박스 방식은 두개의 축을 기반으로 동작한다.
그 중 하나의 축을 주축삼아 요소를 배치하는데 주축의 기본값은 가로 방향(왼쪽 → 오른쪽)이다.
세로 방향(위 → 아래)은 교차축이다.

[flexbox 관련 속성들]

  • flex-direction
  • flex-wrap
  • justify-content
  • align-items
  • align-self
  • align-content
  • flex-grow
  • flex-shrink
  • flex-basis
  • order
  • flex

각 속성별 설명은 아래와 같다.
(각 속성별 사용 가능한 모든 속성값을 명시하지 않았으며, 대표적으로 자주 사용되는 속성값 위주로 명시했다.)


04. flex-direction

플렉스 컨테이너의 주축을 결정하는 속성이다.
행은 가로 축을, 열은 세로 축을 주축으로 한다.

  • row (기본값)
    : 주축은 행이고 방향은 콘텐츠 방향과 동일

  • row-reverse
    : 주축은 행이고 방향은 콘텐츠 방향과 반대

  • colume
    : 주축은 열이고 방향은 콘텐츠 방향과 동일

  • column-reverse
    : 주축은 열이고 방향은 콘텐츠 방향과 반대


05. flex-wrap

플렉스 아이템들이 강제로 한줄에 배치되게 할 것인지 (이렇게 되면 폭이 좁아질때 자식 요소들을 강제로 쭈그려트린다.),
또는 가능한 영역 내에서 벗어나지 않고 여러행으로 나누어 표현할 것인지 결정하는 속성이다.

  • nowrap (기본값)
    : 공간이 부족하더라도 요소를 한줄에 배치

  • wrap
    : 공간 크기에 따라 요소가 여러 행에 걸쳐 배치

  • wrap-reverse
    : wrap과 동일하나 요소가 나영되는 시작점과 끝점이 반대

위 flex-direction과 flex-wrap을 한번에 지정할 수 있는 속성값은 "flex-flow" 이다.


06. justify-content

플렉스 아이템들이 플렉스 박스 주축을 따라 배치될 때, 요소 사이의 공간을 분배하는 방식을 결정한다.

  • flex-start
    : 주축의 시작점으로부터 끝점을 향해 배치

  • flex-end
    : 주축의 끝점으로부터 시작점을 향해 배치

  • center
    : 주축의 중심부에 배치

  • space-between
    : 주축에서 일정한 간격을 둔 채 양끝 정렬 배치

  • space-around
    : 모든 요소가 동일한 여백을 갖도록 배치

  • space-evenly
    : 모든 요소 사이의 간격을 동일하게 유지해 배치


07. align-items

플렉스 컨테이너의 교차축 위에서 플렉스 아이템들이 어떤 식으로 정렬될 것인지를 결정한다.

  • stretch
    : 플렉스 아이템이 교차축 길이에 맞춰 늘어남.
    하지만, 너비나 높이가 우선이다.

  • flex-start
    : 교차축의 시작점으로부터 끝점을 향해 배치

  • flex-end
    : 교차축의 끝점으로부터 시작점을 향해 배치

  • center
    : 교차축의 중심부에 배치


08. align-self

각각의 플렉스 아이템이 교차축에서 어떤 식으로 정렬될 것인지를 스스로 결정한다. (자식 요소에 작서하는 속성)

  • 속성값은 align-items와 동일하다.

09. align-content

교차축 위에서 justify-content와 동일하게 사용할 수 있는 속성이다.
다음 두 조건이 만족되면서 여유 공간이 있을 때만 동작할 수 있다.

  1. flex-wrap의 값이 wrap으로 지정되어 있을 때
  2. 아이템을 배치하기 위해 필요한 공간보다 플렉스 컨테이너가 더 클 때

10. flex-grow & flex-shrink & flex-basis

  • flex-grow (기본값: 0)
    : 플렉스 아이템이 기본 크기보다 더 커질 수 있는지를 결정하고, 플렉스 컨테이너 내부에서 할당받을 수 있는 공간을 상대적으로 정의할 수 있는 속성이다.

  • flex-shrink (기본값: 1)
    : 플렉스 아이템이 기본 크기보다 더 작아질 수 있는지를 결정하고, 플렉스 컨테이너 내부에서 할당받을 수 있는 공간을 상대적으로 정의할 수 있는 속성이다.

  • flex-basis
    : 플렉스 아이템의 초기 크기를 지정하는 속성이다.

이 속성값들은 자식 요소에 지정하는 속성들이다. 정수로 정하며 해당 숫자의 상대값으로 정해진다. (like z-index)

이 세가지 속성값의 단축 속성이 "flex" 이다.


11. order

플렉스 아이템의 배치 순서를 설정할 수 있으며, 지정한 숫자에 맞춰 오름차순으로 배치가 진행된다. 코드에 영향을 끼치는 것이 아닌, 보여지는 순서에만 영향을 준다.

  • 정수 : 같은 값이면 코드 상의 순서대로 배치

2. 플렉스 실습

플렉스 아이템은 플렉스 컨테이너로서의 역할은 하지 않는다.
플렉스 아이템도 플렉스 컨테이너로서의 역할을 하고 싶다면 display: flex; 속성을 정해줘야한다!!

ex)
<ul></ul> 가 플렉스 컨테이너라면 안에 있는 <li></li>는 플렉스 아이템이다.
하지만, <li></li> 안에 있는 <p></p>들은 플렉스 아이템이 아니다.
<li></li>도 플렉스 컨테이너의 역할을 하고 싶다면, <li></li>에도 플렉스 속성을 줘야한다.


3. 클론코딩

당근마켓🥕 - 알바 구인 페이지를 클론 코딩 해보려고 한다.

https://www.daangn.com/kr/jobs/

각 요소들을 모듈별로 나눠서 배치할 것이다.

구성은

  1. 헤더
  2. 대문 이미지 (정보 section)
  3. main part (모듈화 디자인)
  4. 중간 중간 배너
  5. footer

이렇게 5가지가 필요하다.

Copy page 제목은 내가 고구마를 좋아해서 "고구마 마켓"으로 정했다! 🍠

<시작 전 사전 setting>

  1. 홈 화면 파일(index.html) 만들기.

  2. 모듈 5가지 만들기. (.css)

    • 헤더(header)
    • info
    • notice (main part)
    • banner
    • footer
  3. html 파일에 5가지 css 파일 <link>하기.

  4. 전체적으로 들어가는 몇가지 스타일은 html에서 <style>로 작성 예정.

이제부터 아래 설명하는 부분들은 모두 "고구마 마켓🍠🏪" 에 들어갈 기술들이다~!


4. 고구마 마켓🍠 헤더 만들기

1단계. HTML Mark-up!

<!DOCTYPE html>
<html lang="ko">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>🍠우리 동네에서 찾는 고구마 마켓🏪</title>
    <style> /*전체 기본 sestting*/
        *{
            box-sizing: border-box;
        }
        html{
            font-size: 16px;
        }
        body{
            margin: 0;
        }
        .flex{
            display: flex;
        }
    </style>
    <link href="SP_header.css" rel="stylesheet">
    <link href="SP_info.css" rel="stylesheet">
    <link href="SP_notice.css" rel="stylesheet">
    <link href="SP_banner.css" rel="stylesheet">
    <link href="SP_footer.css" rel="stylesheet">
</head>
<body>
    <div class="container">
        <header class="header">
            <div class="header-content flex"> <!--flex container될 예정-->
                <div class="header-content__logo">🍠고구마</div>
                <nav class="header-content__nav flex">
                    <ul>
                        <li>중고거래</li>
                        <li>동네업체</li>
                        <li class="active">알바</li>
                        <li>부동산 직거래</li>
                        <li>중고차 직거래</li>
                    </ul>
                </nav>
                <div class="header-content__input flex">
                    <span class="icon glass">
                        <input type="button" value="&#128269;"> <!--페이지 폭이 줄어들었을 때 나타날 아이콘-->
                    </span>
                    <span>
                        <input type="text" class="search" placeholder="물품이나 동네를 검색해보세요">
                    </span>
                    <span class="icon menu"> 
                        <input type="button" value="&#9776;"> <!--페이지 폭이 줄어들었을 때 나타날 아이콘-->
                    </span>
                    <span>
                        <input type="button" class="chat" value="채팅하기">
                    </span>
                </div>
            </div>
        </header>
    </div>
</body>
</html>

이렇게 작성하면 아직은 엉성하지만

요렇게 된다!


2단계. Header CSS 작성!

  1. 헤더는 스크롤을 내려도 상단에 고정되어 있어야한다.
    position을 잡고 디자인 작업을 진행할 것이다.
  • z-index를 큰 숫자로 잡아놔야 다른 content보다 앞에 보일 수 있다...! (내가 이전에 작업한 copy page에서 이게 어려웠는데 알게 되었다. 💫)
  1. html 안에서 기본 글자 크기를 16px로 잡아놨기 때문에 1rem = 16px로 작성될 것이다.

  2. max-width 속성을 이용해서 페이지 양 옆 여백을 만들어줬다.

    max-width: 75rem; 
    /* 웹 페이지 폭이 75rem이 넘으면 양 옆에 여백이 자동으로 만들어진다. */

<최종 작성된 CSS Code>

/* 상단 고정 */
header.header{  
    position: fixed;
    top: 0;
    width: 100%;
    z-index: 999;
    background-color: #FFFFFF;
    color: #000000;
}
/* header 배치 */
.header-content{  
    width: 100%;
    max-width: 85rem;
    height: 4rem; /* 64px */
    padding: 0.75rem 1rem;
    margin: auto;

    justify-content: space-between;
}
/* header 내부 배치 */
.header-content__logo{
    color: #C8386B;
    font-size: 2rem;
    font-weight: 900;

    height: 1rem;
    width: 12rem;
    margin-right: 20px;
    line-height: 40px;
}
.header-content__nav{
    align-items: center;
    padding: 0 2.5rem 0 0;
    flex-grow: 1;
    color: #505050;
}
.header-content__nav ul{
    padding: 0;
    margin: 0;
    list-style: none;
}
.header-content__nav li{
    display: inline-block;
    margin-right: 2rem;
    font-size: 1.2rem;
    font-weight: 900;
}
.header-content__nav ul li.active{
    color: #C8386B;
}
/* 우측 flex 콘테이너 */
.header-content__input{
    justify-content: center;
    align-items: center;
}
.header-content__input .search{
    width: 18rem;
    height: 2.5rem;
    padding: 0.5rem 0.75rem;
    background-color: #F2F2F2;
    border: none;
    border-radius: 0.5rem;
    font-size: 1rem;
}
.header-content__input .chat{
    line-height: 1.3;
    font-size: 1rem;
    margin: 0 0.5rem;
    padding: 0.5rem 1rem;
    background-color: #FFFFFF;
    border: 0.5px solid #F2F2F2;
    border-radius: 0.25rem;
    font-weight: 600;
}
/* 우측 아이콘 2개의 미디어 쿼리 */
.header-content__input .icon{
    display: none;
}
.header-content__input input{
    margin-right: 1rem;
    border: none;
    padding: 0;
    font-size: 1.5rem;
    background-color: transparent;
}
@media screen and (max-width: 1340px) {
    .header-content__input .search{
        display: none;
    }    
    .header-content__input .glass{
        display: block;
    }
}
@media screen and (max-width: 1084px) {
    .header-content__input .chat, .header-content__nav{
        display: none;
    }    
    .header-content__input .menu{
        display: block;
    }
}

[결과 ⭐]


5. 고구마 마켓🍠 대문 이미지 info 만들기

1단계. HTML Mark-up 추가.

실제 이미지는 넣지 않고 글자와 배경에만 치중해서 넣을 것이다.

</header> 다음으로

<main class="main">
    <section class="info">
        <div class="info__text">
            <h1>우리 동네에서 찾는<br>고구마알바</h1>
            <p>걸어서 10분 거리의<br>동네 알바들 여기 다 있어요.</p>
            <input type="button" value="공고 올리기">
        </div>
    </section>
</main>

코드를 넣어주었고,

info 부분 공통 스타일을 <style>에서 아래 내용을 추가해 주었다.

.main{
    padding: 4rem 0 5rem;
}

2단계. Info CSS 작성!

.info{
    width: 100%;
    height: 20rem;
    background-color: #FFCAD5;
}
.info__text{
    max-width: 50rem;
    margin: auto;
    padding: 3rem 1rem 0;
}
.info__text h1{
    margin: 0;
    font-size: 1.9rem;
    line-height: 3rem;
}
.info__text p{
    margin: 1rem 0.5rem 0 0;
    font-size: 1.1rem;
    line-height: 1.5rem;
}
.info__text input{
    margin: 1.3rem 0px;
    width: 6rem;
    height: 2rem;
    border: none;
    background-color: #FF7E9D;
    color: #FFFFFF;
    border-radius: 0.3rem;
}
@media screen and (max-width: 1065px) {
    .info{
        height: 18rem;
    }
    .info__text{
        padding: 1.3rem 1rem;
    }
    .info__text h1{
        font-size: 1.5rem;
        line-height: 1.7rem;
    }
    .info__text p{
        display: none;
    }
}

[결과 ⭐]


6. 고구마 마켓🍠 항목 추가하기

이부분은 같은 항목들의 반복이기 때문에 html에서 항목 넣는 부분 보다 css 코드가 더 중요했다.

1단계. HTML Mark-up 추가.

<main> 태그 안에 info <section> 그 아래에 들어갈 항목들이다.

<section class="notice">
    <h2 class="notice__title">인기 고구마알바</h2>
    <div class="notice__container flex">
        <article class="notice__item flex">
            <div class="notice__thumb"></div>
            <div class="notice__content">
                <div class="notice__content__title">고구마마켓 고객센터 단기계약직 모집! (한달 계약직)</div>
                <div class="notice__content__address">주식회사 고구마서비스 ・ 서울특별시 성북구 종암동</div>
                <div class="notice__content__pay">월급 3,000,000</div>
            </div>
        </article>
    </div>
</section>

이건 나중에 원하는 만큼 복사해서 붙여넣으면 된다! (<article></article>까지 내용)

이미지 부분은 색으로 대체할거기 때문에 <div class="notice__thumb"></div> 이부분에 내용이 없다!


2단계. 항목 CSS 작성!

웹 사이즈 768px에서 바뀌는게 많은 이유는 테블릿 pc 기준으로 반응형 웹을 만들때 768px 사이즈를 기준으로 잡은 것이 많아서 그렇다!

.notice{
    max-width: 50rem; /*info__text와 동일한 너비*/
    margin: auto;
}
.notice__title{
    font-size: 1.6rem;
    margin: 3.75rem 0 1.5rem;
    line-height: 1.5;
}
.notice__container{
    justify-content: space-between;
    flex-wrap: wrap; /* 플렉스 아이템들이 여러줄로도 배치될 수 있게 했다.*/
}
.notice__item{
    padding: 1.25rem 0;
    flex-basis: 48%;
}
.notice__thumb{
    min-width: 6.7rem;
    min-height: 7.5rem;
    background-color: #CC47AD;
    border-radius: 0.5rem;
}
.notice__content{
    margin-left: 1rem;
}
.notice__content__title{
    line-height: 1.32;
    font-size: 1.125rem;
}
.notice__content__address{
    line-height: 1.4;
    font-size: 0.875rem;
    color: #aeaeae;
}
.notice__content__pay{
    font-weight: 700;
}
@media screen and (max-width: 768px) {
    .notice{
        padding: 0 1rem 1.25rem;
    }    
    .notice__title{
        font-weight: 700;
        line-height: 1.3;
        font-size: 1.25rem;
        margin: 2.5rem 0 1.5rem;
    }
    .notice__container{
        display: block;
    }
}

[결과 ⭐]


7. 고구마 마켓🍠 배너 만들기

1단계. HTML Mark-up 추가.

배너는 공고들 중간에 들어가기 때문에 이 html code 삽입 위치는 <div class="notice__container flex"></div> 이후로 해주면 된다.

<div class="banner flex">
    <div class="banner__text">고구마알바 이용방법이 궁금하다면<br>지금 바로 알아보세요!</div>
    <button class="banner__button">이용방법 알아보기</button>
</div>

이것도 구인공고 항목과 동일하게 같은 것을 반복해서 쓰는 경우로 복사 붙여넣기 하면 된다.☆

복붙할때는 <h2 class="notice__title">인기 고구마알바</h2> 사이 항목들을 복붙하면 된다.


2단계. Banner CSS 작성!

.banner{
    justify-content: space-between;
    align-items: center;
    background-color: #E2F2CB;
    margin: 2.5rem 0;
    padding: 1.8rem 1.5rem 1.8rem 9rem;
    border-radius: 0.5rem;
}
.banner__text{
    line-height: 1.3;
    font-size: 1.25rem;
    font-weight: 900;
}
.banner__button{
    margin: 0;
    padding: 0.5rem 0.625rem;
    line-height: 1.4;
    font-size: 0.9rem;
    background-color: #FF7E9D;
    color: #FFFFFF;
    font-weight: 700;
    border: none;
    border-radius: 0.3rem;
}
@media screen and (max-width: 768px) {
    .banner{
        display: block;
        padding: 1.5rem 1rem;
    }
    .banner__text{
        line-height: 1.3;
        font-size: 1rem;
        font-weight: 700;
    }
    .banner__button{
        margin: 0.75rem 0 0;
        font-size: 0.7rem;
    }
}

[결과 ⭐]


8. 고구마 마켓🍠 푸터 만들기

1단계. HTML Mark-up 추가.

이 부분은 <main></main> 파트 이후에 <footer></footer>로 넣어주면 된다.

<footer class="footer">
    <div class="footer__container">
        <section class="footer__menu">
            <div class="footer__apps">
                <div class="footer__appdown">고구마마켓 앱 다운로드</div>
                <div class="footer__appbtn flx">
                    <button>App Store</button>
                    <button>Google Play</button>
                </div>
            </div>
            <nav class="footer__nav flex">
                <ul>
                    <li>중고거래</li>
                    <li>동네업체</li>
                    <li>고구마알바</li>
                    <li>부동산 직거래</li>
                    <li>중고차 직거래</li>
                </ul>
                <ul>
                    <li>고구마비즈니스</li>
                    <li>채팅하기</li>
                </ul>
                <ul>
                    <li>자주 묻는 질문</li>
                    <li>회사 소개</li>
                    <li>인재 채용</li>
                </ul>
            </nav>
        </section>
    	<section class="footer__plus">
        	<div class="footer_intro">
            	<p><strong>대표</strong> 김민정 | <strong>사업자번호</strong> 123-45-00678
                <br><strong>직업정보제공사업 신고번호</strong> 2023-서울성북-0515
                <br><strong>주소</strong> 서울특별시 성북구 종암로 108 3층
                <br><strong>전화</strong> 1588-5959 | <strong>고객문의</strong> cs@spservice.com</p>
            </div>
			<nav class="footer__q">
        		<ul class="footer__q1 flex">
            		<li>제휴 문의</li>
                	<li>광고 문의</li>
                	<li>PR 문의</li>
                	<li>IR 문의</li>
            	</ul>
            	<ul class="footer__q2 flex">
            		<li>이용약관</li>
                	<li>개인정보처리방침</li>
                	<li>위치기반서비스 이용약관</li>
                	<li>이용자보호 비전과 계획</li>
                	<li>청소년보호정책</li>
            	</ul>
        	</nav>
    	</section>
	</div>
</footer>

.footer{
    color: #505050;
    border-top: 1px solid #b6b6b6;
    padding: 0 1rem;
}
.footer__container{
    max-width: 50rem;
    margin: auto;
}
.footer__menu{
    padding: 3rem 0;
}
.footer__apps{
    float: right;
}
.footer__appdown{
    font-size: 0.875rem;
    font-weight: 700;
    line-height: 1.4;
    margin: 0 0 0.5rem 0;
}
.footer__appbtn{
    width: 18.75rem;
    justify-content: space-between;
}
.footer__appbtn button{
    width: 45%;
    height: 2.75rem;
    padding: 0;
    border: none;
    border-radius: 8px;
    font-size: 1rem;
    font-weight: 700;
}
.footer__nav ul{
    display: flex;
    flex-direction: column;
    list-style-type: none;
    width: 33%;
    margin: 0;
    padding: 0;
    line-height: 1.4;
    font-size: 0.85rem;
}
.footer__nav ul:nth-child(3){
    margin-right: 15%;
}
.footer__nav ul li{
    margin-bottom: 1rem;
}
@media screen and (max-width: 768px) {
    .footer__apps{
        float: none;
        display: flex;
        margin-bottom: 1.25rem;
    }
    .footer__appbtn{
        display: none;
    }
}

.footer__plus{
    border-top: 1px solid #b6b6b6;
    padding: 1rem 0;
    font-size: 0.9rem;
}
.footer__plus ul{
    display: flex;
    flex-direction: row;
    list-style-type: none;
    margin: 1rem 0;
    padding: 0;
    line-height: 1.4;
    font-size: 0.85rem;
    font-weight: 700;
}
.footer__plus li{
    padding-right: 1rem;
}

[결과 ⭐]


[HTML, CSS 후기]

어떻게 보면 front-end 개발의 꽃이라고 볼 수 있는 HTML과 CSS를 배웠는데 정말이지 배우는건 쉽지만 하나하나 적용하면서 넣는 것은 인고의 시간이었다,,,ㅎㅎㅎ

혼자서 유튜브 페이지 카피를 한적이 있는데 (이것도 나중에 보여줄 예정★) 그때도 반나절을 투자하며 힘들게 했지만

이렇게 모듈화를 하는 것, animation과 media를 넣어서 반응형 창으로까지 만들진 않아서
나중에 시간이 된다면 그렇게 수정해보고 싶다 ㅎㅎㅎ

(아래 사진은 한거 미리보기 ☆)


[참고 자료]

profile
백엔드 코린이😁

0개의 댓글