Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

6mn12j 박민주 #1

Open
wants to merge 15 commits into
base: main
Choose a base branch
from
Open
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
22 changes: 22 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
"react-router-dom": "^6.4.2",
"react-scripts": "5.0.1",
"styled-components": "^5.3.6",
"styled-reset": "^4.4.2",
"web-vitals": "^2.1.4"
},
"scripts": {
Expand Down
6 changes: 6 additions & 0 deletions public/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,12 @@
<head>
<meta charset="utf-8" />
<link rel="icon" href="%PUBLIC_URL%/favicon.ico" />
<link rel="preconnect" href="https://fonts.googleapis.com" />
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
<link
href="https://fonts.googleapis.com/css2?family=Inter:wght@200&display=swap"
rel="stylesheet"
/>
<meta name="viewport" content="width=device-width, initial-scale=1" />
<meta name="theme-color" content="#000000" />
<meta name="description" content="Web site created using create-react-app" />
Expand Down
5 changes: 0 additions & 5 deletions src/App.js

This file was deleted.

14 changes: 14 additions & 0 deletions src/App.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import Providers from "./context/Providers";
import AppRouter from "./routes/AppRouter";
import GlobalStyle from "./styles/globalStyles";

function App() {
return (
<Providers>
<GlobalStyle />
<AppRouter />
</Providers>
);
}

export default App;
70 changes: 70 additions & 0 deletions src/api/carAPI.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
import { CAR_API_URL, CAR_FUELTYPE, CAR_SEGMENT } from "./constant";
import { createInstance } from "./createInstance";

const BASE_URL = "https://preonboarding.platdev.net/api";

class carAPI {
#API;
#instance;
#fuelType;
#segment;

constructor() {
this.#instance = createInstance({
url: BASE_URL,
config: {
timeout: 3000,
},
});
this.#API = CAR_API_URL;
this.#fuelType = CAR_FUELTYPE;
this.#segment = CAR_SEGMENT;
}

getAllCar() {
return this.#instance.get(this.#API.cars);
}

getFuelTypeSegmentCars({ fuelType, segment }) {
return this.#instance.get(this.#API.cars, {
params: {
fuelType,
segment,
},
});
}

getFuelTypeCars({ fuleType }) {
return this.#instance.get(this.#API.cars, {
params: {
fuleType,
},
});
}

async getSegmentCars({ segment }) {
return this.#instance.get(this.#API.cars, {
params: {
segment,
},
});
}

async getSmallCars() {
return this.getSegmentCars({ segment: this.#segment.small });
}

async getMediumCars() {
return this.getSegmentCars({ segment: this.#segment.medium });
}

async getLargeCars() {
return this.getSegmentCars({ segment: this.#segment.large });
}

async getSuvCars() {
return this.getSegmentCars({ segment: this.#segment.suv });
}
}

export default new carAPI();
16 changes: 16 additions & 0 deletions src/api/constant.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
export const CAR_API_URL = {
cars: "/cars",
};

export const CAR_FUELTYPE = {
gasiline: "gasoline",
hybrid: "hybrid",
ev: "ev",
};

export const CAR_SEGMENT = {
small: "C",
medium: "D",
large: "E",
suv: "SUV",
};
8 changes: 8 additions & 0 deletions src/api/createInstance.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import axios from "axios";

export const createInstance = ({ url, config }) => {
return axios.create({
baseURL: url,
...config,
});
};
Binary file added src/assets/icons/iconBack.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
23 changes: 23 additions & 0 deletions src/components/CarDetail/CarAdditionalProducts.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import React from "react";
import { formatAmout } from "../../utils/formatAmount";
import DetailInfo from "../common/DetailInfo";
import SubHeader from "../common/SubHeader";

const CarAdditionalProducts = ({ additionalProducts }) => {
return (
<div>
<SubHeader title="추가상품" />
<div>
{additionalProducts &&
additionalProducts.map((element) => {
const { name, amount } = element;
return (
<DetailInfo key={name} name={name} description={`월 ${formatAmout(amount)} 원`} />
);
})}
</div>
</div>
);
};

export default CarAdditionalProducts;
55 changes: 55 additions & 0 deletions src/components/CarDetail/CarDetail.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
import React from "react";
import styled from "styled-components";
import { useLocation } from "../../../node_modules/react-router-dom/dist/index";
import CarAdditionalProducts from "./CarAdditionalProducts";
import CarInfo from "./CarInfo";
import CarInsurance from "./CarInsurance";
import CarMainDetail from "./CarMainDetail";

const CarDetail = () => {
const {
state: {
state: {
startDate,
amount,
attribute: { brand, name, segment, fuelType, imageUrl },
insurance,
additionalProducts,
},
},
} = useLocation();

return (
<div>
<S.CarImg>
<img alt={name} src={imageUrl} />
</S.CarImg>
<S.Detail>
<CarMainDetail name={name} brand={brand} amount={amount} />
<CarInfo segment={segment} fuelType={fuelType} startDate={startDate} />
<CarInsurance insurance={insurance} />
<CarAdditionalProducts additionalProducts={additionalProducts} />
</S.Detail>
</div>
);
};

const S = {
CarImg: styled.div`
width: 100%;
min-height: 20rem;
display: flex;
justify-content: center;
position: relative;
background-color: ${({ theme }) => theme.color.gray};
img {
max-width: 200px;
width: 100%;
}
`,
Detail: styled.div`
display: flex;
flex-direction: column;
`,
};
export default CarDetail;
35 changes: 35 additions & 0 deletions src/components/CarDetail/CarDetailHeader.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import styled from "styled-components";
import { useNavigate } from "../../../node_modules/react-router-dom/dist/index";
import icon from "../../assets/icons/iconBack.png";
const CarDetailHeader = () => {
const navigate = useNavigate();
return (
<S.Header>
<S.BackButon onClick={() => navigate(-1)}>
<img src={icon} alt="back_button" />
</S.BackButon>
<h1>차량상세</h1>
</S.Header>
);
};

const S = {
Header: styled.div`
padding: 2rem 15rem;
text-align: center;
position: relative;
h1 {
min-width: 6.4rem;
max-height: 6rem;
font-weight: 700;
font-size: 17px;
line-height: 21px;
color: ${({ theme }) => theme.black};
}
`,
BackButon: styled.button`
position: absolute;
left: 5%;
`,
};
export default CarDetailHeader;
27 changes: 27 additions & 0 deletions src/components/CarDetail/CarInfo.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import React from "react";
import styled from "styled-components";
import DetailInfo from "../common/DetailInfo";
import SubHeader from "../common/SubHeader";

//TODO: utls로 분리
const day = ["월", "화", "수", "목", "금", "토", "일"];
const startDateFormat = (stringDate) => {
const date = new Date(stringDate);
return `${date.getMonth() + 1} 월 ${date.getDate()}일 (${day[date.getDay()]}) 부터 `;
};

const CarInfo = ({ segment, fuelType, startDate }) => {
return (
<S.CarInfo>
<SubHeader title="차량정보" />
<DetailInfo name="차종" description={segment} />
<DetailInfo name="연료" description={fuelType} />
<DetailInfo name="이용가능일" description={startDateFormat(startDate)} />
</S.CarInfo>
);
};

const S = {
CarInfo: styled.div``,
};
export default CarInfo;
20 changes: 20 additions & 0 deletions src/components/CarDetail/CarInsurance.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
import React from "react";
import DetailInfo from "../common/DetailInfo";
import SubHeader from "../common/SubHeader";

const CarInsurance = ({ insurance }) => {
return (
<div>
<SubHeader title="보험" />
<div>
{insurance &&
insurance.map((element) => {
const { name, description } = element;
return <DetailInfo key={name} name={name} description={description} />;
})}
</div>
</div>
);
};

export default CarInsurance;
45 changes: 45 additions & 0 deletions src/components/CarDetail/CarMainDetail.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
import React from "react";
import styled from "styled-components";
import { formatAmout } from "../../utils/formatAmount";

const CarMainDetail = ({ brand, name, amount }) => {
return (
<S.MainDetail>
<strong>{brand}</strong>
<strong>{name}</strong>
<S.AmountContainer>
<p>월 {formatAmout(amount)} 원</p>
</S.AmountContainer>
</S.MainDetail>
);
};

const S = {
MainDetail: styled.div`
display: flex;
flex-direction: column;
gap: 0.2rem;
font-size: inherit;
padding: 2rem;
strong {
font-weight: 700;
font-size: 1.4rem;
}
> :first-child {
font-size: 2rem;
}

> :nth-child(2) {
font-size: 2.4rem;
margin-bottom: 0.8rem;
}
`,

AmountContainer: styled.span`
text-align: right;
font-weight: 400;
font-size: 1.7rem;
`,
};

export default CarMainDetail;
Loading