Skip to content

Commit 78f3b1f

Browse files
authored
Merge branch 'dev' into feat/#97/filter-control
2 parents 5a03904 + 276da86 commit 78f3b1f

31 files changed

Lines changed: 445 additions & 132 deletions

File tree

package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
"react": "^19.1.0",
2525
"react-dom": "^19.1.0",
2626
"react-router": "^7.6.3",
27+
"react-textarea-autosize": "^8.5.9",
2728
"swiper": "^11.2.10",
2829
"zustand": "^5.0.6"
2930
},

panda.config.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ import { defineConfig } from '@pandacss/dev';
33
const PANDA_CSS_CONSTANTS = {
44
NAVIGATOR_HEIGHT: { value: '97px' },
55
HOME_HEADER_HEIGHT: { value: '52px' },
6-
DETAIL_PAGE_NAVIGATOR_HEIGHT: { value: '6.75rem' },
6+
DETAIL_PAGE_NAVIGATOR_HEIGHT: { value: '6.375rem' },
77
MAX_WIDTH: { value: '700px' },
88
CHAT_ROOM_FOOTER_HEIGHT: { value: '102px' },
99
CHAT_MAX_WIDTH: { value: '270px' },

src/common/components/Button/index.tsx

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,17 @@
11
import type { HTMLAttributes, PropsWithChildren } from 'react';
2+
import { cx } from '@styled-system/css';
3+
24
import * as s from './style.css';
35

46
interface Props extends PropsWithChildren {
57
mode?: 'main' | 'default' | 'back' | 'disabled';
68
onClick?: () => void;
79
style?: HTMLAttributes<HTMLDivElement>['style'];
10+
className?: string;
811
}
9-
const Btn = ({ children, mode = 'default', onClick, style }: Props) => {
12+
const Btn = ({ children, mode = 'default', onClick, style, className }: Props) => {
1013
return (
11-
<div className={s.Button({ mode })} style={style} onClick={onClick}>
14+
<div className={cx(s.Button({ mode }), className)} style={style} onClick={onClick}>
1215
{children}
1316
</div>
1417
);

src/common/components/ItemTokenList/index.tsx

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,9 @@ interface Props {
1919
quality?: Quality;
2020
size: Size;
2121
};
22-
showAll?: boolean;
22+
showCount?: number;
2323
}
24-
const ItemTokenList = ({ itemInfo, showAll = true }: Props) => {
24+
const ItemTokenList = ({ itemInfo, showCount }: Props) => {
2525
const tags: TagType[] = [
2626
...(itemInfo.transactionTypes || []),
2727
...(itemInfo.productTypes || []),
@@ -30,7 +30,8 @@ const ItemTokenList = ({ itemInfo, showAll = true }: Props) => {
3030
...(itemInfo.color ? [itemInfo.color] : []),
3131
...(itemInfo.tradeMethods || []),
3232
];
33-
const showTags = showAll ? tags : tags.slice(0, 4);
33+
const showAll = showCount === undefined;
34+
const showTags = showAll ? tags : tags.slice(0, showCount);
3435
const noneShownCount = tags.length - showTags.length;
3536

3637
return (

src/common/utils/getImageUrl.ts

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,10 @@
1+
const prefixUrl = import.meta.env.VITE_IMAGE_PREFIX_URL || '';
2+
13
const getImageUrl = (imageUrl: string) => {
24
if (imageUrl.startsWith('http')) {
35
return imageUrl;
46
}
5-
const prefixUrl = import.meta.env.VITE_IMAGE_PREFIX_URL || '';
6-
if (!prefixUrl) {
7-
throw new Error('VITE_IMAGE_PREFIX_URL is not defined or is empty.');
8-
}
7+
98
return `${prefixUrl}/${imageUrl}`;
109
};
1110

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
// 채팅방 들어갔을 때 오는 값
2+
import client from '@/common/utils/client';
3+
import { useMutation } from '@tanstack/react-query';
4+
5+
const postChatRoom = async ({ chatRoomId }: { chatRoomId: number }) => {
6+
const res = await client.post(`/api/v1/chatroom/${chatRoomId}/enter`, null, {
7+
params: { pageSize: 5 },
8+
});
9+
10+
console.log(res.data.message);
11+
12+
return res;
13+
};
14+
15+
export const usePostChatRoom = () =>
16+
useMutation({
17+
mutationFn: postChatRoom,
18+
});
Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
import Btn from '@/common/components/Button';
2+
3+
import * as s from './style.css';
4+
import type { TransactionType } from '@/libs/types/item';
5+
import type { ItemInfoInterface } from '@/features/detail/types';
6+
7+
interface PickButtonProps {
8+
type: TransactionType;
9+
index: number;
10+
salePrice: number;
11+
deposit: number;
12+
rentalFee: number;
13+
}
14+
const PickButton = ({ type, index, salePrice, deposit, rentalFee }: PickButtonProps) => {
15+
const color = index === 0 ? 'red' : 'blue';
16+
const label = type === 'RENTAL' ? '대여' : '구매';
17+
const priceText =
18+
type === 'RENTAL'
19+
? `대여료+보증금 ${(deposit + rentalFee).toLocaleString()}원`
20+
: `판매가 ${salePrice.toLocaleString()}원`;
21+
22+
const handlePickClick = () => {
23+
alert(`${type} 선택`);
24+
};
25+
26+
return (
27+
<button className={s.PickButton({ color })} onClick={handlePickClick} aria-label={`${label}, ${priceText}`}>
28+
<span>{label}</span>
29+
<p>{priceText}</p>
30+
</button>
31+
);
32+
};
33+
34+
interface Props {
35+
itemInfo: ItemInfoInterface;
36+
}
37+
const BottomActions = ({ itemInfo }: Props) => {
38+
const { transactionTypes, mine, salePrice, deposit, rentalFee } = itemInfo;
39+
40+
// TODO: 실제 액션 추가
41+
const handleChatClick = () => {
42+
alert('채팅 연결');
43+
};
44+
45+
return (
46+
<div className={s.Container}>
47+
<Btn className={s.ChatButton({ isMine: mine })} onClick={handleChatClick}>
48+
<span className="mgc_chat_2_fill" />
49+
{mine && <p>채팅</p>}
50+
</Btn>
51+
{!mine && (
52+
<div className={s.PickButtonContainer}>
53+
{transactionTypes.map((type, index) => {
54+
return (
55+
<PickButton
56+
key={type}
57+
type={type}
58+
index={index}
59+
salePrice={salePrice}
60+
deposit={deposit}
61+
rentalFee={rentalFee}
62+
/>
63+
);
64+
})}
65+
</div>
66+
)}
67+
</div>
68+
);
69+
};
70+
export default BottomActions;
Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,76 @@
1+
import { css, cva } from '@styled-system/css';
2+
3+
export const Container = css({
4+
position: 'fixed',
5+
bottom: '0',
6+
left: '0',
7+
right: '0',
8+
height: 'DETAIL_PAGE_NAVIGATOR_HEIGHT',
9+
display: 'flex',
10+
gap: '0.87rem',
11+
px: '1rem',
12+
pt: '0.625rem',
13+
bg: 'linear-gradient(180deg, rgba(28, 28, 30, 0.00) 0%, #1C1C1E 8.82%)',
14+
roundedTop: '0.625rem',
15+
});
16+
17+
export const ChatButton = cva({
18+
base: {
19+
flexShrink: 0,
20+
height: '3.125rem',
21+
},
22+
variants: {
23+
isMine: {
24+
true: {
25+
width: 'full',
26+
},
27+
false: {
28+
width: '3.125rem',
29+
},
30+
},
31+
},
32+
});
33+
34+
export const PickButtonContainer = css({
35+
flexGrow: 1,
36+
display: 'flex',
37+
alignItems: 'center',
38+
gap: '0.87rem',
39+
height: '3.125rem',
40+
});
41+
42+
export const PickButton = cva({
43+
base: {
44+
flexGrow: 1,
45+
flexBasis: 0,
46+
flexDir: 'column',
47+
gap: '0.25rem',
48+
height: 'full',
49+
overflow: 'hidden',
50+
rounded: '0.375rem',
51+
'& > span': {
52+
color: '80',
53+
fontSize: '1rem',
54+
fontWeight: 500,
55+
lineHeight: 'normal',
56+
letterSpacing: '-0.04rem',
57+
},
58+
'& > p': {
59+
color: '100',
60+
fontSize: '0.75rem',
61+
fontWeight: 600,
62+
lineHeight: 'normal',
63+
letterSpacing: '-0.03rem',
64+
},
65+
},
66+
variants: {
67+
color: {
68+
red: {
69+
bgColor: 'main',
70+
},
71+
blue: {
72+
bgColor: '#3978FF',
73+
},
74+
},
75+
},
76+
});

src/features/home/components/ItemCard/PriceToken/index.tsx

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -7,14 +7,16 @@ interface Props {
77
const PriceToken = ({ price, deposit }: Props) => {
88
const isRental = deposit !== undefined;
99
return (
10-
<div className={s.PriceItem}>
11-
<label>{isRental ? '대여' : '판매'}</label>
12-
<p>{price.toLocaleString()}</p>
10+
<div className={s.Wrapper}>
11+
<div className={s.PriceItem}>
12+
<label>{isRental ? '대여료' : '판매가'}</label>
13+
<p>{price.toLocaleString()}</p>
14+
</div>
1315
{isRental && (
14-
<p>
16+
<div className={s.PriceItem}>
1517
<label>보증금</label>
16-
{deposit.toLocaleString()}
17-
</p>
18+
<p>{deposit.toLocaleString()}</p>
19+
</div>
1820
)}
1921
</div>
2022
);
Lines changed: 15 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,27 @@
11
import { css } from '@styled-system/css';
22

3-
export const PriceItem = css({
3+
export const Wrapper = css({
44
display: 'flex',
55
alignItems: 'center',
6-
gap: '0.375rem',
6+
gap: '0.875rem',
7+
height: '1.375rem',
8+
});
9+
10+
export const PriceItem = css({
11+
display: 'flex',
12+
alignItems: 'baseline',
13+
gap: '0.25rem',
14+
lineHeight: 1.4,
715
'& > label': {
8-
padding: '0.125rem 0.25rem',
9-
display: 'flex',
10-
alignItems: 'center',
11-
justifyContent: 'center',
12-
rounded: '0.25rem',
13-
bgColor: 'systemGray4',
1416
color: '54',
15-
fontSize: '0.625rem',
17+
fontSize: '0.75rem',
1618
fontWeight: 500,
17-
lineHeight: 1.4,
18-
letterSpacing: '-0.025rem',
19-
flexShrink: 0,
19+
letterSpacing: '-0.03rem',
2020
},
21-
'& p': {
21+
'& > p': {
2222
color: '100',
23-
fontSize: '1rem',
23+
fontSize: '0.875rem',
2424
fontWeight: 600,
25-
lineHeight: 1.4,
26-
letterSpacing: '-0.04rem',
27-
display: 'flex',
28-
gap: '0.375rem',
29-
alignItems: 'baseline',
30-
'& > label': {
31-
color: '54',
32-
fontSize: '0.875rem',
33-
fontWeight: 500,
34-
letterSpacing: '-0.035rem',
35-
},
25+
letterSpacing: '-0.035rem',
3626
},
3727
});

0 commit comments

Comments
 (0)