Skip to content

Commit

Permalink
Merge branch 'refactor/#363-DropDownBox' of https://github.com/TEAM-M…
Browse files Browse the repository at this point in the history
…ODEE/modee-web into refactor/#384-POSTAPI
  • Loading branch information
aazkgh committed Feb 19, 2024
2 parents cf94597 + 4df8966 commit be4b063
Show file tree
Hide file tree
Showing 2 changed files with 74 additions and 86 deletions.
46 changes: 31 additions & 15 deletions src/views/ApplicationPage/components/ServiceHistory.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import { useEffect, useRef, useState } from 'react';
import { useNavigate } from 'react-router-dom';
import { useRecoilState } from 'recoil';
import { styled } from 'styled-components';
Expand All @@ -8,25 +9,37 @@ import { INFO_MESSAGE } from '../constants/message';

import ServiceHistoryListItem from './ServiceHistoryListItem';

import { applyStepState, historyDetailProps, historyState } from '@/recoil/atoms/applicationState';
import { applyStepState, historyState } from '@/recoil/atoms/applicationState';
import ProgressBar from '@/views/@common/components/ProgressBar';

const ServiceHistory = () => {
const MAX_LENGTH = 3;

const [step, setStep] = useRecoilState(applyStepState);
const [serviceHistory, setServiceHistory] = useRecoilState(historyState);
const { hairServiceRecords } = serviceHistory;
const [currentDropDown, setCurrentDropDown] = useState<number | null>(null);
const historyRef = useRef<HTMLUListElement>(null);
const navigate = useNavigate();

useEffect(() => {
const handleFocus = (e: MouseEvent) => {
if (historyRef.current && !historyRef.current.contains(e.target as Node)) setCurrentDropDown(null);
};
document.addEventListener('mouseup', handleFocus);

return () => {
document.removeEventListener('mouseup', handleFocus);
};
}, [historyRef.current]);

const addHistory = () => {
if (hairServiceRecords.length < MAX_LENGTH) {
const tempServiceHistoryList: historyDetailProps[] = [
...hairServiceRecords,
{ hairService: '', hairServiceTerm: '' },
];
setServiceHistory({ ...serviceHistory, hairServiceRecords: tempServiceHistoryList });
}
setServiceHistory((prev) => ({
...prev,
hairServiceRecords:
prev.hairServiceRecords.length < MAX_LENGTH
? [...prev.hairServiceRecords, { hairService: '', hairServiceTerm: '' }]
: prev.hairServiceRecords,
}));
};

const exceptionNull = () => {
Expand Down Expand Up @@ -55,12 +68,15 @@ const ServiceHistory = () => {
<h2>{INFO_MESSAGE.SERVICE_TITLE}</h2>
<h3>{INFO_MESSAGE.SERVICE_SUBTITLE}</h3>
</S.Title>
<S.ServiceHistoryList>
{hairServiceRecords.map((item, idx: number) =>
idx < hairServiceRecords.length ? (
<ServiceHistoryListItem key={'history' + item.hairService + item.hairServiceTerm + idx} idx={idx} />
) : null,
)}
<S.ServiceHistoryList ref={historyRef}>
{serviceHistory.hairServiceRecords.map((item, idx) => (
<ServiceHistoryListItem
key={'history' + item.hairService + item.hairServiceTerm + idx}
currentDropDown={currentDropDown}
setCurrentDropDown={setCurrentDropDown}
idx={idx}
/>
))}
</S.ServiceHistoryList>
<S.AddHistoryBtn type="button" onClick={addHistory}>
{INFO_MESSAGE.ADD_HISTORY}
Expand Down
114 changes: 43 additions & 71 deletions src/views/ApplicationPage/components/ServiceHistoryListItem.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { useState } from 'react';
import React, { useEffect, useState } from 'react';
import { useRecoilState } from 'recoil';
import { css, styled } from 'styled-components';

Expand All @@ -7,110 +7,90 @@ import { IcDelete } from '../assets/icons';
import { SELECT_PERIOD, SELECT_SERVICE } from '../constants/select';

import { historyState } from '@/recoil/atoms/applicationState';

interface ServiceHistoryListItem {
idx: number;
currentDropDown: number | null;
setCurrentDropDown: React.Dispatch<React.SetStateAction<number | null>>;
}

const ServiceHistoryListItem = ({ idx }: ServiceHistoryListItem) => {
const ServiceHistoryListItem = ({ idx, currentDropDown, setCurrentDropDown }: ServiceHistoryListItem) => {
const [serviceHistory, setServiceHistory] = useRecoilState(historyState);
const { hairServiceRecords } = serviceHistory;
const [isServiceClicked, setIsServiceClicked] = useState(false);
const [isPeriodClicked, setIsPeriodClicked] = useState(false);

const activateServiceBox = (event: React.MouseEvent<HTMLButtonElement, MouseEvent>) => {
setIsServiceClicked((prev) => !prev);
const tempService = event.currentTarget.innerText;
const tempServiceHistoryList = hairServiceRecords.map((item, i) => {
if (i === idx) {
return {
...item,
hairService: tempService,
};
}
return item;
});

setServiceHistory({ ...serviceHistory, hairServiceRecords: tempServiceHistoryList });
};

const activatePeriodBox = (event: React.MouseEvent<HTMLButtonElement, MouseEvent>) => {
setIsPeriodClicked((prev) => !prev);
const tempPeriod = event.currentTarget.innerText;
const tempServiceHistoryList = hairServiceRecords.map((item, i) => {
const [clickedDropdown, setClickedDropdown] = useState<string | null>(null);

useEffect(() => {
if (currentDropDown !== idx) setClickedDropdown(null);
}, [currentDropDown]);

const handleDropdownClick = (
event: React.MouseEvent<HTMLButtonElement, MouseEvent>,
field: 'hairService' | 'hairServiceTerm',
) => {
const newValue = event.currentTarget.innerText;
const newServiceHistoryRecords = serviceHistory.hairServiceRecords.map((item, i) => {
if (i === idx) {
return {
...item,
hairServiceTerm: tempPeriod,
[field]: newValue,
};
}
return item;
});

setServiceHistory({ ...serviceHistory, hairServiceRecords: tempServiceHistoryList });
setServiceHistory({ ...serviceHistory, hairServiceRecords: newServiceHistoryRecords });
setClickedDropdown(null);
};

const deleteHistory = () => {
const tempServiceHistoryList = hairServiceRecords.filter((_, i) => i !== idx);
if (tempServiceHistoryList.length >= 0) {
setServiceHistory({ ...serviceHistory, hairServiceRecords: tempServiceHistoryList });
}
const newServiceHistoryRecords = serviceHistory.hairServiceRecords.filter((_, i) => i !== idx);
setServiceHistory({ ...serviceHistory, hairServiceRecords: newServiceHistoryRecords });
};

return (
<S.ServiceHistoryListItemLayout>
<S.SelectBox $height={idx}>
<S.SelectServiceBox
$isServiceClicked={isServiceClicked}
<S.DropDownBox
$isClicked={clickedDropdown === 'service'}
onClick={() => {
setIsServiceClicked((prev) => !prev);
setCurrentDropDown(idx);
clickedDropdown === 'service' ? setClickedDropdown(null) : setClickedDropdown('service');
}}>
<input
type="button"
value={hairServiceRecords[idx].hairService !== '' ? hairServiceRecords[idx].hairService : '시술 선택'}
/>
{isServiceClicked ? <IcUpBlue /> : <IcDownGrey />}
</S.SelectServiceBox>
<div>
{isServiceClicked && (
<input type="button" value={serviceHistory.hairServiceRecords[idx].hairService || '시술 선택'} />
{clickedDropdown === 'service' ? <IcUpBlue /> : <IcDownGrey />}
{clickedDropdown === 'service' && (
<S.SelectDetailList>
{Object.keys(SELECT_SERVICE).map((value, key) => (
<li key={key}>
<button type="button" onClick={activateServiceBox}>
<button type="button" onClick={(e) => handleDropdownClick(e, 'hairService')}>
{value}
</button>
</li>
))}
</S.SelectDetailList>
)}
</div>
</S.DropDownBox>
</S.SelectBox>
<S.SelectBox $height={idx}>
<S.SelectPeriodBox
$isPeriodClicked={isPeriodClicked}
<S.DropDownBox
$isClicked={clickedDropdown === 'period'}
onClick={() => {
setIsPeriodClicked((prev) => !prev);
setCurrentDropDown(idx);
clickedDropdown === 'period' ? setClickedDropdown(null) : setClickedDropdown('period');
}}>
<input
type="button"
value={
hairServiceRecords[idx].hairServiceTerm !== '' ? hairServiceRecords[idx].hairServiceTerm : '기간 선택'
}
/>
{isPeriodClicked ? <IcUpBlue /> : <IcDownGrey />}
</S.SelectPeriodBox>
<div>
{isPeriodClicked && (
<input type="button" value={serviceHistory.hairServiceRecords[idx].hairServiceTerm || '기간 선택'} />
{clickedDropdown === 'period' ? <IcUpBlue /> : <IcDownGrey />}
{clickedDropdown === 'period' && (
<S.SelectDetailList>
{Object.keys(SELECT_PERIOD).map((value, key) => (
<li key={key}>
<button type="button" onClick={activatePeriodBox}>
<button type="button" onClick={(e) => handleDropdownClick(e, 'hairServiceTerm')}>
{value}
</button>
</li>
))}
</S.SelectDetailList>
)}
</div>
</S.DropDownBox>
</S.SelectBox>
<button type="button" onClick={deleteHistory}>
<IcDelete />
Expand Down Expand Up @@ -187,25 +167,17 @@ const selectBtn = css`
}
`;

const SelectServiceBox = styled.div<{ $isServiceClicked: boolean }>`
border: 1px solid
${({ $isServiceClicked, theme }) => ($isServiceClicked ? theme.colors.moddy_blue : theme.colors.moddy_gray50)};
const DropDownBox = styled.div<{ $isClicked: boolean }>`
border: 1px solid ${({ $isClicked, theme }) => ($isClicked ? theme.colors.moddy_blue : theme.colors.moddy_gray50)};
${selectBtn};
`;

const SelectPeriodBox = styled.div<{ $isPeriodClicked: boolean }>`
border: 1px solid
${({ $isPeriodClicked, theme }) => ($isPeriodClicked ? theme.colors.moddy_blue : theme.colors.moddy_gray50)};
${selectBtn};
`;
const S = {
ServiceHistoryListItemLayout,
SelectBox,
SelectDetailList,
SelectServiceBox,
SelectPeriodBox,
DropDownBox,
};

export default ServiceHistoryListItem;

0 comments on commit be4b063

Please sign in to comment.