Skip to content

Commit bab5ba8

Browse files
authored
Merge pull request #123 from MUIT-UMC/114/refactor-디테일-수정
예매절차 디테일
2 parents eba5c2e + 2295715 commit bab5ba8

5 files changed

Lines changed: 104 additions & 64 deletions

File tree

src/components/buy/Step1.jsx

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import React, { useState, useEffect } from "react";
2-
import { useNavigate } from "react-router-dom";
2+
import {useLocation, useNavigate } from "react-router-dom";
33
import styled from "styled-components";
44
import { useParams } from 'react-router-dom';
55

@@ -30,6 +30,10 @@ const Step1 = () => {
3030
setPeopleCount(event.target.value);
3131
};
3232

33+
const handleNextStep = () => {
34+
navigate("./step2", { state: { peopleCount,ticketInfo, } }); // 인원 정보 전달
35+
};
36+
3337
return (
3438
<Container>
3539
<LeftSection>
@@ -60,7 +64,7 @@ const Step1 = () => {
6064
</TicketRow>
6165
</TicketDetails>
6266
</Info>
63-
<Button onClick={() => navigate("./step2")}>예약하기</Button>
67+
<Button onClick={handleNextStep}>예약하기</Button>
6468
</RightSection>
6569
</Container>
6670
);

src/components/buy/Step2.jsx

Lines changed: 43 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -7,13 +7,16 @@ import { useParams } from 'react-router-dom';
77
import useCustomFetch from "../../hooks/useCustomFetch";
88
//const token = import.meta.env.VITE_APP_ACCESS_TOKEN;
99
const token = localStorage.getItem("accessToken");
10-
10+
import { useLocation } from "react-router-dom";
1111

1212
// Step2 - 할인 선택
1313
const Step2 = () => {
1414

1515
const {amateurId} = useParams();
1616
const navigate = useNavigate();
17+
const location = useLocation();
18+
const peopleCount = location.state?.peopleCount || 1;
19+
const [selectedTicketId, setSelectedTicketId] = useState("1");
1720

1821
const url = `/tickets/${amateurId}/ticketInfo`;
1922
const { data, error, loading } = useCustomFetch(url, {
@@ -27,6 +30,26 @@ const Step2 = () => {
2730

2831
const ticketInfo = data.result;
2932

33+
34+
// 🎯 선택된 티켓 정보 찾기
35+
const selectedTicket = ticketInfo.tickets.find(ticket => ticket.amateurTicketId === selectedTicketId);
36+
const ticketPrice = selectedTicket ? selectedTicket.price : 0;
37+
38+
// 🎯 할인 선택 핸들러
39+
const handleDiscountChange = (event) => {
40+
setSelectedTicketId(event.target.value);
41+
};
42+
const handleNextStep = () => {
43+
navigate('../step3', {
44+
state: {
45+
peopleCount,
46+
selectedTicketId,
47+
ticketInfo,
48+
},
49+
});
50+
};
51+
52+
3053
return (
3154
<Container>
3255
<Sidebar>
@@ -44,13 +67,25 @@ const Step2 = () => {
4467
<DiscountTitle>할인 선택</DiscountTitle>
4568
<Options>
4669
<Option>
47-
<RadioButton type="radio" name="discount" defaultChecked /> 할인 없음
70+
<RadioButton type="radio"
71+
name="discount"
72+
value="1"
73+
checked={selectedTicketId === "1"}
74+
onChange={handleDiscountChange} /> 할인 없음
4875
</Option>
4976
<Option>
50-
<RadioButton type="radio" name="discount" /> 홍대생 할인
77+
<RadioButton type="radio"
78+
name="discount"
79+
value="2"
80+
checked={selectedTicketId === "2"}
81+
onChange={handleDiscountChange} /> 홍대생 할인
5182
</Option>
5283
<Option>
53-
<RadioButton type="radio" name="discount" /> 지인 할인
84+
<RadioButton type="radio"
85+
name="discount"
86+
value="2"
87+
checked={selectedTicketId === "2"}
88+
onChange={handleDiscountChange} /> 지인 할인
5489
</Option>
5590
</Options>
5691
</DiscountBox>
@@ -62,25 +97,21 @@ const Step2 = () => {
6297
</Row>
6398
<Row>
6499
<Label>인원</Label>
65-
<Value>1</Value>
100+
<Value>{peopleCount}</Value>
66101
</Row>
67102
<Row>
68103
<Label>티켓 금액</Label>
69-
<Value>{ticketInfo.tickets.price}</Value>
70-
</Row>
71-
<Row>
72-
<Label>할인</Label>
73-
<Value active>0원</Value>
104+
<Value>{ticketPrice.toLocaleString()}</Value>
74105
</Row>
75106
<Row>
76107
<Label>배송료</Label>
77108
<Value>-</Value>
78109
</Row>
79110
<TotalRow>
80111
<TotalLabel>총 결제 금액</TotalLabel>
81-
<TotalValue>{ticketInfo.tickets.price}</TotalValue>
112+
<TotalValue>{(ticketPrice * peopleCount).toLocaleString()}</TotalValue>
82113
</TotalRow>
83-
<Button onClick={() => navigate('../step3')} active>다음</Button> {/* 이전 페이지로 이동 */}
114+
<Button onClick={handleNextStep} active>다음</Button> {/* 이전 페이지로 이동 */}
84115
<Button onClick={() => navigate('..')}>이전</Button> {/* 다음 페이지로 이동 */}
85116
</Summary>
86117
</Content>

src/components/buy/Step3.jsx

Lines changed: 26 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -7,12 +7,15 @@ import { useParams } from 'react-router-dom';
77
import useCustomFetch from "../../hooks/useCustomFetch";
88
//const token = import.meta.env.VITE_APP_ACCESS_TOKEN;
99
const token = localStorage.getItem("accessToken");
10+
import { useLocation } from "react-router-dom";
1011

1112

1213
// Step3 - 배송 선택 및 주문자 확인
1314
const Step3 = () => {
1415
const {amateurId} = useParams();
1516
const navigate = useNavigate();
17+
const location = useLocation();
18+
const { peopleCount = 1, selectedTicketId = '1' } = location.state || {};
1619

1720
const url = `/tickets/${amateurId}/ticketInfo`;
1821
const { data, error, loading } = useCustomFetch(url, {
@@ -27,6 +30,25 @@ const Step3 = () => {
2730

2831
const ticketInfo = data.result;
2932
const memberInfo = data.result.reserveConfirmMemberDTO;
33+
34+
// 선택된 티켓 정보 찾기
35+
const selectedTicket = ticketInfo.tickets.find(
36+
(ticket) => ticket.amateurTicketId === selectedTicketId
37+
);
38+
const ticketPrice = selectedTicket ? selectedTicket.price : 0;
39+
// 총 결제 금액 계산
40+
const totalAmount = ticketPrice * peopleCount;
41+
42+
const handleNextStep = () => {
43+
navigate('../step4', {
44+
state: {
45+
peopleCount,
46+
selectedTicketId,
47+
ticketInfo,
48+
},
49+
});
50+
};
51+
3052

3153
return (
3254
<Container>
@@ -40,7 +62,6 @@ const Step3 = () => {
4062
<LeftContent>
4163
<Title>{ticketInfo.name}</Title>
4264
<Subtitle>{ticketInfo.place}</Subtitle>
43-
<DateRange>{ticketInfo.schedule}</DateRange>
4465
<DiscountBox>
4566
<DiscountTitle>티켓 수령 방법</DiscountTitle>
4667
<Options>
@@ -75,25 +96,21 @@ const Step3 = () => {
7596
</Row>
7697
<Row>
7798
<Label>인원</Label>
78-
<Value>1</Value>
99+
<Value>{peopleCount}</Value>
79100
</Row>
80101
<Row>
81102
<Label>티켓 금액</Label>
82-
<Value>{ticketInfo.tickets.price}</Value>
83-
</Row>
84-
<Row>
85-
<Label>할인</Label>
86-
<Value active>-3000원</Value>
103+
<Value>{ticketPrice.toLocaleString()}</Value>
87104
</Row>
88105
<Row>
89106
<Label>배송료</Label>
90107
<Value>0원 (현장수령)</Value>
91108
</Row>
92109
<TotalRow>
93110
<TotalLabel>총 결제 금액</TotalLabel>
94-
<TotalValue>{ticketInfo.tickets.price}</TotalValue>
111+
<TotalValue>{totalAmount.toLocaleString()}</TotalValue>
95112
</TotalRow>
96-
<Button onClick={() => navigate('../step4')} active>다음</Button> {/* 이전 페이지로 이동 */}
113+
<Button onClick={handleNextStep} active>다음</Button> {/* 이전 페이지로 이동 */}
97114
<Button onClick={() => navigate('../step2')}>이전</Button> {/* 다음 페이지로 이동 */}
98115
</Summary>
99116
</Content>

src/components/buy/Step4.jsx

Lines changed: 22 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import React, { useState } from "react";
22
import styled from "styled-components";
3-
import { useNavigate, useParams } from 'react-router-dom';
3+
import { useLocation, useNavigate, useParams } from 'react-router-dom';
44

55

66
// const token = import.meta.env.VITE_APP_ACCESS_TOKEN;
@@ -10,10 +10,10 @@ const Step4 = () => {
1010
const navigate = useNavigate();
1111
const { amateurId } = useParams();
1212
const [accountName, setAccountName] = useState("");
13-
const [quantity] = useState(1);
1413
const [isSubmitting, setIsSubmitting] = useState(false);
15-
16-
const isButtonActive = accountName.trim().length > 0;
14+
const isButtonActive = accountName.trim().length > 0;
15+
const location = useLocation();
16+
const { peopleCount, selectedTicketId,ticketInfo } = location.state || {};
1717

1818
const handleSubmit = async () => {
1919
if (!isButtonActive || isSubmitting) return;
@@ -31,7 +31,7 @@ const Step4 = () => {
3131
},
3232
body: JSON.stringify({
3333
accountName,
34-
quantity: 1,
34+
quantity: peopleCount,
3535
}),
3636
});
3737

@@ -50,6 +50,13 @@ const Step4 = () => {
5050
setIsSubmitting(false);
5151
}
5252
};
53+
// 선택된 티켓 정보 찾기
54+
const selectedTicket = ticketInfo.tickets.find(
55+
(ticket) => ticket.amateurTicketId === selectedTicketId
56+
);
57+
const ticketPrice = selectedTicket ? selectedTicket.price : 0;
58+
// 총 결제 금액 계산
59+
const totalAmount = ticketPrice * peopleCount;
5360

5461
return (
5562
<Container>
@@ -61,9 +68,8 @@ const Step4 = () => {
6168
</Sidebar>
6269
<Content>
6370
<LeftContent>
64-
<Title>실종</Title>
65-
<Subtitle>홍익대학교 학생회관 3층 소극장</Subtitle>
66-
<DateRange>2024.10.03~2024.10.05</DateRange>
71+
<Title>{ticketInfo.name}</Title>
72+
<Subtitle>{ticketInfo.place}</Subtitle>
6773
<DiscountBox>
6874
<DiscountTitle>결제수단</DiscountTitle>
6975
<Options>
@@ -84,29 +90,26 @@ const Step4 = () => {
8490
<Summary>
8591
<Row>
8692
<Label>일시</Label>
87-
<Value>2024.10.03 (목) 19:00</Value>
93+
<Value>{ticketInfo.schedule}</Value>
8894
</Row>
8995
<Row>
9096
<Label>인원</Label>
91-
<Value>1</Value>
97+
<Value>{peopleCount}</Value>
9298
</Row>
9399
<Row>
94100
<Label>티켓 금액</Label>
95-
<Value>10,000원</Value>
96-
</Row>
97-
<Row>
98-
<Label>할인</Label>
99-
<Value $active>-3000원</Value>
101+
<Value>{ticketPrice.toLocaleString()}</Value>
100102
</Row>
101103
<Row>
102104
<Label>배송료</Label>
103105
<Value>0원 (현장수령)</Value>
104106
</Row>
105107
<TotalRow>
106108
<TotalLabel>총 결제 금액</TotalLabel>
107-
<TotalValue>7,000원</TotalValue>
109+
<TotalValue>{totalAmount.toLocaleString()}</TotalValue>
108110
</TotalRow>
109-
<Button onClick={handleSubmit} $active={isButtonActive && !isSubmitting} disabled={isSubmitting}>
111+
<Button
112+
onClick={handleSubmit} >
110113
{isSubmitting ? '결제 처리 중...' : '다음'}
111114
</Button>
112115
<PreButton onClick={() => navigate('../step3')}>이전</PreButton>
@@ -196,18 +199,6 @@ line-height: 25px; /* 156.25% */
196199
margin-bottom: 3px;
197200
`;
198201

199-
const DateRange = styled.div`
200-
color: #919191;
201-
202-
/* Body-tiny-md */
203-
font-family: Inter;
204-
font-size: 14px;
205-
font-style: normal;
206-
font-weight: 500;
207-
line-height: 18px; /* 128.571% */
208-
margin-bottom: 20px;
209-
`;
210-
211202
const DiscountBox = styled.div`
212203
display: flex;
213204
width: 376px;
@@ -378,8 +369,8 @@ line-height: normal;
378369

379370
const Button = styled.button`
380371
border-radius: 3px;
381-
border: 1px solid ${({ active }) => (active ? "#A00000" : "#919191")};
382-
background: ${({ active }) => (active ? "#A00000" : "#919191")};
372+
border: 1px solid ;
373+
background: #A00000;
383374
display: flex;
384375
width: 400px;
385376
height: 40px;

src/pages/small-theater/SmallDetail.jsx

Lines changed: 7 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -40,22 +40,19 @@ function SmallDetail() {
4040

4141
const imageUrls = musical.notice.imgUrls;
4242
const poster = musical.posterImgUrl
43-
const detailImg=DetailImg;
4443
const details = [
4544
{ label: "장소", value: musical.place},
4645
{ label: "공연 기간", value: musical.schedule },
4746
{ label: "공연 시간", value: musical.runtime },
4847
{ label: "관람 연령", value:musical.age },
4948
{ label: "출연", value: musical.starring },
50-
{ label: "가격", value: <Price>
51-
<div className="item">
52-
<div className="type">일반예매</div>
53-
<div className="price">10,000원</div>
54-
</div>
55-
<div className="item">
56-
<div className="type">지인, 홍대생 할인</div>
57-
<div className="price">7,000원</div>
58-
</div>
49+
{ label: "가격", value: <Price>
50+
{musical.tickets.map((ticket, index) => (
51+
<div className="item" key={index}>
52+
<div className="type">{ticket.ticketName}</div>
53+
<div className="price">{ticket.price}</div>
54+
</div>
55+
))}
5956
</Price> }, // 가격 상세 구현 필요
6057
{ label: "티켓 수", value: "200매 (표가 없을 시 구매 불가)" },
6158
];

0 commit comments

Comments
 (0)