[detail]구매 부분 수정

- 옵션 첫번째에 select추가.
 - 갯수부분 수정가능하도록 변경.
This commit is contained in:
junghoon86.park
2025-10-27 11:39:39 +09:00
parent 1a5b229dac
commit 33f628e81d
2 changed files with 110 additions and 62 deletions

View File

@@ -1,9 +1,18 @@
import React, { useCallback, useEffect, useMemo, useState } from 'react';
import React, {
useCallback,
useEffect,
useMemo,
useState,
} from 'react';
import { useDispatch, useSelector } from 'react-redux';
import {
useDispatch,
useSelector,
} from 'react-redux';
import Spotlight from '@enact/spotlight';
import SpotlightContainerDecorator from '@enact/spotlight/SpotlightContainerDecorator';
import SpotlightContainerDecorator
from '@enact/spotlight/SpotlightContainerDecorator';
import { addToCart } from '../../../actions/cartActions';
import { getMyInfoCheckoutInfo } from '../../../actions/checkoutActions';
@@ -14,9 +23,15 @@ import {
showError,
} from '../../../actions/commonActions';
import { getProductCouponSearch } from '../../../actions/couponActions';
import { sendLogPaymentEntry, sendLogTotalRecommend } from '../../../actions/logActions';
import {
sendLogPaymentEntry,
sendLogTotalRecommend,
} from '../../../actions/logActions';
import { pushPanel } from '../../../actions/panelActions';
import { getProductOption, getProductOptionId } from '../../../actions/productActions';
import {
getProductOption,
getProductOptionId,
} from '../../../actions/productActions';
import { clearAllToasts } from '../../../actions/toastActions';
import TButton from '../../../components/TButton/TButton';
import TPopUp from '../../../components/TPopUp/TPopUp';
@@ -49,15 +64,23 @@ const BuyOption = ({
const dispatch = useDispatch();
// Redux 상태 (props가 있으면 props 우선, 없으면 Redux에서)
const { userId, userNumber } = useSelector((state) => state.common.appStatus.loginUserData);
const { userId, userNumber } = useSelector(
(state) => state.common.appStatus.loginUserData
);
const reduxProductInfo = useSelector((state) => state.main.productData);
const productInfo = propsProductInfo || reduxProductInfo;
const productOptionInfos = useSelector((state) => state.product.prdtOptInfo);
const productData = useSelector((state) => state.main.productData);
const { partnerCoupon } = useSelector((state) => state.coupon.productCouponSearchData || {});
const { popupVisible, activePopup } = useSelector((state) => state.common.popup);
const { partnerCoupon } = useSelector(
(state) => state.coupon.productCouponSearchData || {}
);
const { popupVisible, activePopup } = useSelector(
(state) => state.common.popup
);
const nowMenu = useSelector((state) => state.common.menu.nowMenu);
const webOSVersion = useSelector((state) => state.common.appStatus.webOSVersion);
const webOSVersion = useSelector(
(state) => state.common.appStatus.webOSVersion
);
// 옵션 선택 상태 관리 (SingleOption과 동일한 구조)
const [selectedBtnOptIdx, setSelectedBtnOptIdx] = useState(0);
@@ -84,7 +107,8 @@ const BuyOption = ({
couponInfo = partnerCoupon[0];
}
const { catCd, catNm, patncNm, patnrId, prdtId, prdtNm, priceInfo } = productData;
const { catCd, catNm, patncNm, patnrId, prdtId, prdtNm, priceInfo } =
productData;
const { cpnSno, cpnTtl } = couponInfo || {};
const prodOptSno =
(productOptionInfos &&
@@ -120,7 +144,8 @@ const BuyOption = ({
couponInfo = partnerCoupon[0];
}
const { catCd, catNm, patncNm, patnrId, prdtId, prdtNm, priceInfo } = productInfo;
const { catCd, catNm, patncNm, patnrId, prdtId, prdtNm, priceInfo } =
productInfo;
const { cpnSno, cpnTtl } = couponInfo || {};
const prodOptSno =
(productOptionInfos &&
@@ -321,8 +346,10 @@ const BuyOption = ({
{
patnrId: selectedPatnrId,
prdtId: selectedPrdtId,
prodOptCdCval: selectedOptions?.prodOptCdCval || null,
prodQty: quantity,
prodOptCdCval: selectedOptions?.prodOptCdCval
? selectedOptions.prodOptCdCval
: null,
prodQty: String(quantity),
prodOptTpCdCval: productOptionInfos[0]?.prodOptTpCdCval,
},
],
@@ -433,9 +460,13 @@ const BuyOption = ({
const index = selected.selected;
console.log('[BuyOption] Second option selected:', index);
setSelectedOptionItemIndex(index);
setSelectedOptions(productOptionInfos[selectedBtnOptIdx]?.prdtOptDtl[index]);
setSelectedOptions(
productOptionInfos[selectedBtnOptIdx]?.prdtOptDtl[index]
);
dispatch(
getProductOptionId(productOptionInfos[selectedBtnOptIdx]?.prdtOptDtl[index]?.prodOptCdCval)
getProductOptionId(
productOptionInfos[selectedBtnOptIdx]?.prdtOptDtl[index]?.prodOptCdCval
)
);
setIsOptionValue(true);
};
@@ -509,7 +540,7 @@ const BuyOption = ({
// BuyOption 내에서 arrow up으로 빠져나가지 않도록 처리
const handleArrowUpWithinBuyOption = useCallback((e) => {
e.stopPropagation();
// e.stopPropagation();
// arrow up 이벤트를 막음 (컨테이너의 leaveFor: {}와 함께 작동)
}, []);
@@ -570,52 +601,63 @@ const BuyOption = ({
<Container className={styles.buy_option}>
<div className={styles.buy_option__left_section}>
{/* 동적 옵션 렌더링 */}
{productOptionInfos && productOptionInfos.length > 0 && productInfo?.optProdYn === 'Y' && (
<>
{/* 첫번째 옵션 (여러 옵션이 있을 때만) */}
{productOptionInfos.length > 1 && (
<div className={styles.buy_option__option_row}>
<div className={styles.buy_option__option_label}>
<div className={styles.buy_option__label_text}>OPTION 1</div>
</div>
<div className={styles.buy_option__option_control}>
<CustomDropDown
options={productOptionInfos.map((option) => option.optNm)}
selectedIndex={selectedBtnOptIdx}
onSelect={handleFirstOptionSelect}
spotlightId="buy-option-first-dropdown"
onSpotlightUp={handleArrowUpWithinBuyOption}
/>
</div>
</div>
)}
{/* 두번째 옵션 (옵션 상세값들) */}
{productOptionInfos[selectedBtnOptIdx]?.prdtOptDtl &&
productOptionInfos[selectedBtnOptIdx]?.prdtOptDtl.length > 1 && (
{productOptionInfos &&
productOptionInfos.length > 0 &&
productInfo?.optProdYn === 'Y' && (
<>
{/* 첫번째 옵션 (여러 옵션이 있을 때만) */}
{productOptionInfos.length > 1 && (
<div className={styles.buy_option__option_row}>
<div className={styles.buy_option__option_label}>
<div className={styles.buy_option__label_text}>
{productOptionInfos.length === 1 ? 'OPTION' : 'OPTION 2'}
OPTION 1
</div>
</div>
<div className={styles.buy_option__option_control}>
<CustomDropDown
options={
productOptionInfos[selectedBtnOptIdx]?.prdtOptDtl.map(
(detail) => detail.prodOptCval
) || []
}
selectedIndex={selectedOptionItemIndex}
onSelect={handleSecondOptionSelect}
spotlightId="buy-option-second-dropdown"
options={['Select Option'].concat(
productOptionInfos.map((option) => option.optNm)
)}
selectedIndex={selectedBtnOptIdx}
onSelect={handleFirstOptionSelect}
spotlightId="buy-option-first-dropdown"
onSpotlightUp={handleArrowUpWithinBuyOption}
/>
</div>
</div>
)}
</>
)}
{/* 두번째 옵션 (옵션 상세값들) */}
{productOptionInfos[selectedBtnOptIdx]?.prdtOptDtl &&
productOptionInfos[selectedBtnOptIdx]?.prdtOptDtl.length >
1 && (
<div className={styles.buy_option__option_row}>
<div className={styles.buy_option__option_label}>
<div className={styles.buy_option__label_text}>
{productOptionInfos.length === 1
? 'OPTION'
: 'OPTION 2'}
</div>
</div>
<div className={styles.buy_option__option_control}>
<CustomDropDown
options={[
'Select Option',
...(productOptionInfos[
selectedBtnOptIdx
]?.prdtOptDtl.map((detail) => detail.prodOptCval) ||
[]),
]}
selectedIndex={selectedOptionItemIndex}
onSelect={handleSecondOptionSelect}
spotlightId="buy-option-second-dropdown"
onSpotlightUp={handleArrowUpWithinBuyOption}
/>
</div>
</div>
)}
</>
)}
{/* 수량 선택 */}
<div className={styles.buy_option__option_row}>
@@ -629,7 +671,11 @@ const BuyOption = ({
onSelect={handleQuantitySelect}
spotlightId="buy-option-quantity-dropdown"
/> */}
<ProductQuantity onSpotlightUp={handleArrowUpWithinBuyOption} />
<ProductQuantity
onSpotlightUp={handleArrowUpWithinBuyOption}
setQuantity={setQuantity}
quantity={quantity}
/>
</div>
</div>
</div>

View File

@@ -1,6 +1,10 @@
import React, { useCallback, useState } from 'react';
import React, {
useCallback,
useState,
} from 'react';
import SpotlightContainerDecorator from '@enact/spotlight/SpotlightContainerDecorator';
import SpotlightContainerDecorator
from '@enact/spotlight/SpotlightContainerDecorator';
import Spottable from '@enact/spotlight/Spottable';
import css from './ProductQuantity.module.less';
@@ -8,22 +12,20 @@ import css from './ProductQuantity.module.less';
const Container = SpotlightContainerDecorator('div');
const SpotDiv = Spottable('div');
const ProductQuantity = ({ onSpotlightUp }) => {
const [ea, setEa] = useState(1);
const ProductQuantity = ({ onSpotlightUp, quantity, setQuantity }) => {
const minusClick = useCallback(() => {
if (ea > 1) {
setEa(ea - 1);
if (quantity > 1) {
setQuantity(quantity - 1);
}
}, [ea]);
}, [quantity, setQuantity]);
const plusClick = useCallback(() => {
setEa(ea + 1);
}, [ea]);
setQuantity(quantity + 1);
}, [quantity, setQuantity]);
return (
<Container className={css.container} onSpotlightUp={onSpotlightUp}>
<SpotDiv className={css.minusBtn} onClick={minusClick} />
<div className={css.inputBox}>{ea}</div>
<div className={css.inputBox}>{quantity}</div>
<SpotDiv className={css.plusBtn} onClick={plusClick} />
</Container>
);