Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 21 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
.playwright-mcp/

# IDE - Cursor/VSCode
.vscode/
.cursor/
*.code-workspace
.idea/

# OS
.DS_Store
Thumbs.db
desktop.ini

# Logs
*.log
npm-debug.log*

# Temp files
*.tmp
*.temp
~*
238 changes: 238 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,238 @@
# 판다마켓

중고거래 플랫폼
배포: [https://sprint.boolean.kr/](https://sprint.boolean.kr/)
Github Pages: [https://cobool.github.io/21-Sprint-Mission/](https://cobool.github.io/21-Sprint-Mission/)


---

## 개요
스프린트 21기 프론트엔드 미션.
HTML/CSS로 구성된 정적 중고거래 플랫폼 **“판다마켓”** 제작.

---

## 파일 구조

```
assets/
css/
- base.css 기본 스타일 (변수 등)
- common.css 공통 컴포넌트 (container, sr-only)
- font.css ROKAFSans 폰트
- form.css 로그인/회원가입 폼 스타일
- reset.css Meyer's Reset
- style.css 메인 페이지 스타일
fonts/ ROKAFSans woff
images/ 이미지
icons/ 소셜 로그인 아이콘
js/
- form.js 폼 검증 및 이벤트 처리
- script.js 주요 로직
utility/
- validation.js 폼 검증 유틸리티 함수

pages/
- faq.html FAQ 페이지
- items.html 상품 리스트 페이지
- login.html 로그인 페이지
- privacy.html 개인정보처리방침 페이지
- signup.html 회원가입 페이지

index.html 메인 랜딩 페이지
```

---

## HTML

### index.html

```
header - sticky 헤더, 로고 + 로그인
main
- 배너 (히어로)
- 기능 소개 3개 (Hot / Search / Register)
- 배너
footer - 링크, SNS
```

- 배너는 grid로 텍스트/이미지 2컬럼 구성
- 기능 카드 비율: 이미지 55%, 텍스트 45%
- Search 섹션만 reverse 처리 (좌우 반전)
- Hero 이미지는 CSS 배경으로 처리
- Features 이미지는 `<img>` 태그 사용

### login.html / signup.html

```
header - 폼 헤더, 로고
form
- 이메일 입력
- 비밀번호 입력 (토글 버튼 포함)
- 간편 로그인
footer - 회원가입/로그인 링크
```

- 비밀번호 토글 버튼용 `form-block__input-wrapper` 추가
- 로고 위 상단 여백 변수로 관리

---

## CSS

### 구조

```
base.css → 기본 변수, reset, font (@import)
common.css → 공통 컴포넌트 (container, sr-only)
style.css → 메인 페이지 스타일
form.css → 로그인/회원가입 폼 스타일
reset.css → Meyer's Reset
font.css → ROKAFSans 폰트
```

### 변수

```css
--max-width: 1140px

--color-blue: #3692FF
--color-blue-light: #E6F2FF
--color-white: #FFFFFF

--color-banner-bg: #CFE5FF
--color-footer-bg: #111827

--color-gray-50 ~ 900: 그레이 스케일

--spacing-form-header-top: 60px
--spacing-form-gap: 24px
```

- CSS 변수로 색상 시스템 통일 관리
- Max-width 1140px 제한
- 폰트: Pretendard Variable (CDN) + ROKAFSans (로고, 폰트 파일)
- 레이아웃: flexbox
- Mobile First 접근 방식
- BEM 네이밍 컨벤션 사용

### 페이지별 헤더 분리

- 메인: `.page-header` (sticky)
- 폼: `.form-header` (중앙 정렬)

---

## 현재 상태
- **완성:** index.html, login.html, signup.html
- **부분 완성:** items.html, faq.html, privacy.html (템플릿)
- **JS:** 폼 검증 로직 및 비밀번호 보기/숨기기 기능 완성

---

## TODO

### HTML/CSS
- [x] `login.html`: 로그인 폼 구현
- [x] `signup.html`: 회원가입 폼 구현
- [x] CSS 구조 개선 (common.css 분리)
- [x] 페이지별 헤더 네이밍 분리 (page-header, form-header)
- [x] CSS 변수 확대 (색상, 간격)
- [x] 비밀번호 토글 버튼 구조 개선 (wrapper 적용)
- [ ] `items.html`: 상품 리스트 페이지 구성
- [ ] `faq.html`: 자주 묻는 질문 콘텐츠 작성
- [ ] `privacy.html`: 개인정보처리방침 콘텐츠 작성

### JavaScript
- [x] 폼 검증 로직 완성
- [x] 비밀번호 보기/숨기기 기능 구현

### 반응형
- [x] **반응형 디자인 적용 완료** (PC 1200px+, Tablet 768px~1199px, Mobile 375px~767px)

---

## 체크리스트

### [기본]
- [x] 랜딩 페이지의 url path는 루트('/')로 설정
- [x] title은 **"판다마켓"** 으로 설정
- [x] Global Navigation Bar가 sticky(최상단 고정) 처리
- [x] Palette의 color 값을 CSS 변수로 등록하고 사용
- [x] 클릭 가능한 요소에 `cursor: pointer` 설정
- [x] "판다마켓" 클릭 시 루트 페이지(`/`)로 이동 및 새로고침
- [x] "로그인" 버튼 클릭 시 로그인 페이지(`/login`)로 이동
- [x] "회원 가입" 버튼 클릭 시 회원가입 페이지(`/signup`)로 이동
- [x] "구경하러가기" 버튼 클릭 시 `/items`로 이동
- [x] "Privacy Policy", "FAQ" 클릭 시 각각 `/privacy`, `/faq`로 이동
- [x] SNS 아이콘(Google, Kakao, Facebook, Instagram, Twitter, YouTube) 클릭 시 각각의 페이지로 새 창 이동

### [로그인/회원가입]
- [x] 로그인 페이지, 회원가입 페이지 로고 위 상단 여백 동일
- [x] 비밀번호 input 요소 오른쪽에 눈모양 아이콘 추가
- [x] 비밀번호 토글 버튼 정렬 최적화 (wrapper 적용)
- [x] 비밀번호 보기/숨기기 기능 구현

### [반응형]
- [x] **반응형 디자인 적용 완료** (PC 1200px+, Tablet 768px~1199px, Mobile 375px~767px)
- PC/Tablet/Mobile 분기 처리
- "판다마켓" 로고와 "로그인" 버튼 간격 반응형 조정
- 요소 간 간격, 크기, 폰트 크기 등 유동적 변환

### [SEO/메타]
- [x] 메타 태그 설정 (제목: "판다 마켓", 설명: "일상의 모든 물건을 거래해보세요")

### [심화]
- [x] 브라우저 크기에 따라 모든 크기 관련 값이 유동적으로 변환
- [x] CSS 변수를 통한 스타일 시스템 구축
- [x] BEM 네이밍 컨벤션 적용
- [x] 구조적 HTML (시맨틱 태그 사용)

---

## 주요 개선 사항

### 1. CSS 구조 개선
- `common.css` 추가로 공통 컴포넌트 분리
- `base.css`에서 reset, font import 처리
- 파일별 역할 명확화

### 2. 페이지별 헤더 분리
- 메인: `.page-header` (sticky positioning)
- 폼: `.form-header` (중앙 정렬)
- 중복 방지 및 유지보수성 향상

### 3. CSS 변수 확대
- 색상: `--color-blue`, `--color-blue-light`, `--color-white`
- 간격: `--spacing-form-header-top`, `--spacing-form-gap`
- 하드코딩 색상 제거

### 4. 비밀번호 토글 구조
- `.form-block__input-wrapper` 추가
- 버튼 정확한 중앙 정렬
- 베스트 프랙티스 적용

### 5. 폼 검증 로직 리팩토링

#### 변경 전 (이전 버전)
- `config` 객체 기반 검증 시스템
- `form.dataset.type`으로 login/signup 구분
- 각 필드별 `validator` 함수와 `isInvalid` 플래그로 상태 관리
- `validation.js`의 함수들(`validateEmail`, `validatePassword` 등) 직접 사용
- 필드별 개별 메시지 관리 (`messages.email.required`, `messages.email.invalid` 등)
- 에러 클래스: `form-block__group--error`

#### 변경 후 (현재 버전)
- **선언적 검증 시스템**: `data-validate` 속성 기반
- HTML에서 `data-validate="required|email|max:50"` 형태로 검증 규칙 선언
- `rules` 객체로 규칙 기반 검증 (required, email, min, max, match)
- `validateInput()` 함수로 각 input을 독립적으로 검증
- **규칙별 통합 메시지**: 함수 지원으로 동적 메시지 생성
- **개선된 상태 관리**: `invalid`/`valid` 클래스로 시각적 피드백
- **버튼 상태 관리**: `updateButtonState()` 함수로 모든 필드 검증 후 버튼 활성화/비활성화
- 반복 코드 제거 및 헬퍼 함수 활용
- 실시간 검증 및 버튼 활성화/비활성화 처리
- 비밀번호 보기/숨기기 토글 기능 구현
- null 안전성 체크 및 에러 처리 개선
41 changes: 41 additions & 0 deletions assets/css/base.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
/*
==============================
기본 초기화 및 공통 변수
모든 페이지에서 사용하는 기본 설정만 포함
==============================
*/
@import url("./reset.css");
@import url("./font.css");

html,
body {
width: 100%;
height: 100%;
font-family: "Pretendard Variable", sans-serif;
}

:root {
--color-banner-bg: #CFE5FF;
--color-footer-bg: #111827;

--color-blue: #3692FF;
--color-blue-light: #E6F2FF;

--color-white: #FFFFFF;

--color-gray-50: #F9FAFB;
--color-gray-100: #F3F4F6;
--color-gray-200: #E5E7EB;
--color-gray-300: #D1D5DB;
--color-gray-400: #9CA3AF;
--color-gray-500: #6B7280;
--color-gray-600: #4B5563;
--color-gray-700: #374151;
--color-gray-800: #1F2937;
--color-gray-900: #111827;

--max-width: 1140px;

--spacing-form-header-top: 60px;
--spacing-form-gap: 24px;
}
53 changes: 53 additions & 0 deletions assets/css/common.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
/*
==============================
공통 컴포넌트
모든 페이지에서 공통으로 사용하는 컴포넌트 스타일
==============================
*/

/*
==============================
레이아웃 스타일
==============================
*/
.container {
width: 100%;
margin: 0 auto;
padding: 0 16px;
max-width: var(--max-width);
}

/*
==============================
미디어 쿼리
==============================
*/
@media (min-width: 768px) {
.container {
padding: 0 24px;
}
}

@media (min-width: 1200px) {
.container {
padding: 0 10px;
}
}

/*
==============================
공통 유틸리티 스타일
==============================
*/
.sr-only {
position: absolute;
width: 1px;
height: 1px;
margin: -1px;
border: 0;
padding: 0;
white-space: nowrap;
clip-path: inset(100%);
clip: rect(0 0 0 0);
}

11 changes: 11 additions & 0 deletions assets/css/font.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
@font-face {
font-family: 'ROKAFSans';
font-weight: 400;
src: url('../fonts/ROKAFSansMedium.woff') format('woff');
}

@font-face {
font-family: 'ROKAFSans';
font-weight: 700;
src: url('../fonts/ROKAFSansBold.woff') format('woff');
}
Loading