+
+
+
goChatRoomInformation()}>
+ {selectChatRoom.title}
+
+
+
goChatRoomInformation()}>
+ {members.map((member, index) => (
+
0) ? '' : `url(${member.profileImage})`
+ }}
+ />
+ ))}
+ {extraProfilesCount > 0 && (
+
+ +{extraProfilesCount}
+
+ )}
+
+
+
+
+
+
+
+ {formatMessages(messages)}
+
+
+
+
+
+
+ )
+ }
+}
+
+export default ChatRoom;
\ No newline at end of file
diff --git a/src/page/Chat/ChatRoom/ChatRoomInformation/ChatRoomInformation.css b/src/page/Chat/ChatRoom/ChatRoomInformation/ChatRoomInformation.css
new file mode 100644
index 0000000..2da054d
--- /dev/null
+++ b/src/page/Chat/ChatRoom/ChatRoomInformation/ChatRoomInformation.css
@@ -0,0 +1,276 @@
+.chatRoomInformation {
+ height: 812px;
+ width: 375px;
+
+ margin: 0 auto;
+
+ .margin-container {
+ display: flex;
+ flex-direction: column;
+ height: 100%;
+ margin: 0 16px;
+ }
+
+ .title {
+ width: 100%;
+ height: 46px;
+ margin-top: 50px;
+ background: #ffffff;
+ display: flex;
+ text-align: center;
+
+ }
+
+ .title-name {
+ /* 채팅방 이름 */
+
+ padding-top: 15px;
+ width: 90px;
+ height: 18px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 16px;
+ line-height: 18px;
+ /* identical to box height, or 112% */
+ display: flex;
+ align-items: center;
+
+ color: #3D3D3D;
+ }
+
+
+ .chat-room-header {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ margin-bottom: 50px;
+ margin-top: 10px
+ }
+
+ .chat-room-image {
+ border-radius: 50%;
+ margin-bottom: 10px;
+
+ /* 채팅방 대표사진 */
+ width: 60px;
+ height: 60px;
+ background-color: #3D3D3D;
+
+ }
+
+ .chat-room-name {
+
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 16px;
+ line-height: 18px;
+
+ color: #3D3D3D;
+ }
+
+
+
+ .chat-room-actions {
+ width: 300px;
+ margin: 0 auto;
+ display: flex;
+ justify-content: space-evenly;
+ margin-bottom: 20px;
+ }
+
+ .action-item {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ justify-content: center;
+ gap: 5px;
+ width: 84px;
+ height: 84px;
+ background-color: #FAFAFA;
+ border-radius: 20%;
+ transition: all 0.3s ease;
+ }
+
+ .action-item img {
+ width: 30px;
+ height: 30px;
+ }
+
+ .action-item span {
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 12px;
+ line-height: 14px;
+
+ color: #000000;
+ }
+
+ .chat-room-timer {
+
+ margin: 0 auto;
+ width: 272px;
+ height: 40px;
+
+
+ background: #FAFAFA;
+ border-radius: 10px;
+ margin-bottom: 20px;
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ }
+
+ .chat-room-timer span {
+
+
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 12px;
+ line-height: 14px;
+ /* identical to box height, or 117% */
+
+
+ color: #000000;
+ }
+
+ .participant-list {
+ margin-top: 20px;
+ display: flex;
+ flex-direction: column;
+ gap: 5px;
+ }
+
+ .participant-list-text {
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 14px;
+ line-height: 18px;
+
+ color: #3D3D3D;
+ margin-bottom: 10px;
+ }
+
+ .gender {
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 12px;
+ line-height: 12px;
+ color: #777777;
+ margin-bottom: 10px;
+ }
+
+
+ .participant-group {
+ max-height: 150px;
+ overflow-y: scroll;
+ scrollbar-width: none;
+ /* Firefox */
+ -ms-overflow-style: none;
+ }
+
+ .participant-group ul {
+ padding-left: 0px;
+ }
+
+
+
+ .bar {
+ width: 343px;
+ height: 6px;
+ background-color: #FAFAFA;
+
+ }
+
+
+ .major {
+
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 400;
+ font-size: 12px;
+ line-height: 14px;
+ /* identical to box height, or 117% */
+ display: flex;
+ align-items: center;
+
+ color: #777777;
+ }
+
+ .nickName {
+
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 12px;
+ line-height: 14px;
+ /* identical to box height, or 117% */
+ display: flex;
+ align-items: center;
+
+ color: #3D3D3D;
+ }
+
+ .user-list {
+ display: flex;
+ flex-direction: row;
+ margin-bottom: 5px;
+ }
+
+ .user-list img {
+ width: 18px;
+ height: 18px;
+ border-radius: 50%;
+ margin-left: 3px;
+ margin-right: 5px;
+ }
+
+ .user-container {
+ display: flex;
+ flex-direction: column;
+ }
+
+
+
+
+
+
+ .action-item svg {
+ fill: none;
+ transition: all 0.3s ease;
+ }
+
+ .action-item span {
+ color: #3D3D3D;
+ transition: all 0.3s ease;
+ }
+
+ .action-item.active {
+ background-color: #FF7898;
+ /* 핑크 배경 */
+ }
+
+ .action-item.active svg {
+ fill: #fff;
+ /* 아이콘 하얀색 */
+ }
+
+ .action-item.active span {
+ color: #fff;
+ /* 글자 하얀색 */
+ }
+
+}
\ No newline at end of file
diff --git a/src/page/Chat/ChatRoom/ChatRoomInformation/ChatRoomInformation.jsx b/src/page/Chat/ChatRoom/ChatRoomInformation/ChatRoomInformation.jsx
new file mode 100644
index 0000000..cf25182
--- /dev/null
+++ b/src/page/Chat/ChatRoom/ChatRoomInformation/ChatRoomInformation.jsx
@@ -0,0 +1,205 @@
+import React, { useState, useEffect } from "react";
+import './ChatRoomInformation.css'
+import ExitDialog from '../../Dialog/ExitDialog'
+import UserIntroduceDialog from '../../Dialog/UserintroduceDialog'
+import { fetchChatroomInformation } from '../../../../api/chatRoom/fetchChatroomInformation'
+
+function ChatRoomInformation({ roomId, socket, chatRoomInformation }) {
+ const [exitDialog, setExitDialog] = useState(false);
+
+ const goChatRoom = () => {
+ chatRoomInformation(false);
+ };
+
+ const [activeItemPromise, setActiveItemPromise] = useState(null);
+ const [activeItemAlarm, setActiveItemAlarm] = useState(null);
+ const [activeItemExit, setActiveItemExit] = useState(null);
+ const [userIntroduceDialog, setUserIntroduceDialog] = useState(false);
+ const [clickUser, setClickUser] = useState();
+
+ const handleClick = (item) => {
+ if (item === "promise") {
+ if (activeItemPromise) {
+ setActiveItemPromise(false);
+ } else {
+ setActiveItemPromise(true);
+ }
+ } else if (item === "alarm") {
+ if (activeItemAlarm) {
+ setActiveItemAlarm(false);
+ } else {
+ setActiveItemAlarm(true);
+ }
+ } else if (item === "exit") {
+ if (activeItemExit) {
+ setActiveItemExit(false);
+ } else {
+ setActiveItemExit(true);
+ }
+ }
+
+ };
+
+
+ const [room, setRoom] = useState({
+ title: "프로그래밍 기초",
+ members: [
+ { gender: "여자", major: "Physics", studentId: "20210003", nickname: "Alice", profileImage: "../../../../asset/ChatRoomPic3.png" },
+ { gender: "여자", major: "Mathematicasdfasdfdassdfsssadfsdf", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic4.png" },
+ { gender: "남자", major: "Mathematicasdfasdfdassdfsssadfsdf", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic4.png" },
+ { gender: "남자", major: "Mathematicasdfasdfdassdfsssadfsdf", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic4.png" }
+ ],
+ profileImage: '../../../../asset/ChatRoomPic1.png',
+ })
+
+ const [possibleEnterNumber, setPossibleEnterNumber] = useState(3);
+ const [remainingTime, setRemainingTime] = useState('');
+ const [dDay, setDDay] = useState(0);
+
+ useEffect(() => {
+ const fetchRoomData = async () => {
+ try {
+ const data = await fetchChatroomInformation(roomId);
+ setRoom(data.room);
+ setPossibleEnterNumber(data.possibleEnterNumber);
+ setRemainingTime(data.remainingTime);
+ setDDay(data.dDay);
+ } catch (error) {
+ console.error("Error fetching room data:", error);
+ }
+ };
+
+ fetchRoomData();
+ }, [roomId]);
+
+
+
+
+ const dialogOpen = (nickname) => {
+ setUserIntroduceDialog(true);
+ setClickUser(nickname);
+ }
+
+
+
+
+ return (
+
+
setUserIntroduceDialog(false)} roomId={roomId} />
+ setExitDialog(false)} possibleEnterNumber={possibleEnterNumber} roomId={roomId} socket={socket} />
+
+
+ {/* 이미지와 채팅방 이름 */}
+
+

+
{room.title}
+
+
+ {/* 버튼들 */}
+
+ {/* 약속 잡기 */}
+
handleClick('promise')}
+ >
+
+
약속 잡기
+
+
+ {/* 알림 끄기 */}
+
handleClick('alarm')}
+ >
+
+ {activeItemAlarm ? <>
알림 키기 > :
알림 끄기
+ }
+
+
+
+ {/* 나가기 */}
+
{ handleClick('exit'); setExitDialog(true) }}
+ >
+
+
+
나가기
+
+
+
+
+ {/* 채팅방 종료 시간 */}
+
+
+ {remainingTime}에 채팅방이 종료됩니다 D-{dDay}
+
+
+
+
+
+ {/* 참여자 목록 */}
+
+
+
+
+ );
+}
+
+export default ChatRoomInformation;
\ No newline at end of file
diff --git a/src/page/Chat/ChatStartPage.jsx b/src/page/Chat/ChatStartPage.jsx
new file mode 100644
index 0000000..661dafd
--- /dev/null
+++ b/src/page/Chat/ChatStartPage.jsx
@@ -0,0 +1,220 @@
+import React, { useState, useEffect } from "react";
+import './ChatPage.css'
+import EnterCheckPage from './EnterCheckPage'
+import NoEnterCheckPage from './NoEnterCheckPage'
+import { useNavigate } from 'react-router-dom';
+import api from '../../api/api'
+import logo from '../../asset/logo.png'
+import { fetchChatRoomFetch } from '../../api/chatRoom/fetchChatRoomFetch'
+
+function ChatStartPage() {
+
+ const navigate = useNavigate();
+ const [loading, setLoading] = useState(true);
+
+ const [isEnterCheck, setIsEnterClick] = useState(false);
+ //유저의 정보를 가져와 성별,입장참여 횟수를 가져온다
+ const [possibleEnterNumber, setPossibleEnterNumber] = useState(3);
+ const [gender, setGender] = useState("남자");
+
+
+ const handleNavigation = (destination) => {
+ switch (destination) {
+ case 'play':
+ navigate('/mbti');
+ break;
+ case 'talk':
+ window.location.reload(); // 페이지 새로고침 (필요에 따라 이 부분을 변경)
+ break;
+ case 'my':
+ navigate('/myPage');
+ break;
+ default:
+ break;
+ }
+ };
+
+
+ // 채팅방 정보를 저장하는 state(예시 백에서 받아와야함)
+ //나중에 역순으로 할거?
+ const [chatRooms, setChatRooms] = useState([
+ {
+ id: 1,
+ //제목 길이 20자 제한
+ title: "채팅방 메인 타이틀아아아아f",
+ //서브제목 길이 30자 제한
+ subTitle: "dddddddddddddddddddddddddddddddddddddddddddddddddd",
+
+ //방아이디로 조회한다.
+
+ //나중에 서버로 부터 바는 member이기 때문에 삭제!
+ members: [
+ { gender: "남자", major: "Computer Science", studentId: "20210001", nickname: "John", profileImage: "../../../../asset/ChatRoomPic1.png" },
+ { gender: "여자", major: "Design", studentId: "20210002", nickname: "Jane", profileImage: "../../../../asset/ChatRoomPic2.png" }
+ ],
+ maxMembers: 2,
+ //입장체크
+ enterCheck: false,
+ host: "asdfasdf1234346",
+ maleCount: 1,
+ femaleCount: 1,
+ profileImage: '../../../../asset/ChatRoomPic1.png',
+ hasStarted: false
+ },
+ {
+ id: 2,
+ title: "프로그래밍 기초",
+ subTitle: "프로그래밍의 기초를 배워봅시다",
+ members: [
+ { gender: "여자", major: "Physics", studentId: "20210003", nickname: "Alice", profileImage: "../../../../asset/ChatRoomPic3.png" },
+ { gender: "여자", major: "Mathematicasdfasdfdassdfsssadfsdf", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic4.png" },
+ { gender: "남자", major: "Mathematicasdfasdfdassdfsssadfsdf", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic4.png" },
+ { gender: "남자", major: "Mathematicasdfasdfdassdfsssadfsdf", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic4.png" }
+ ],
+ maxMembers: 4,
+ enterCheck: true,
+ host: "asdfasdf1234346",
+ maleCount: 2,
+ femaleCount: 2,
+ profileImage: '../../../../asset/ChatRoomPic1.png',
+ hasStarted: false
+ },
+ {
+ id: 3,
+ title: "프로그래밍 기초",
+ subTitle: "프로그래밍의 기초를 배워봅시다",
+ members: [
+ { gender: "여자", major: "Physics", studentId: "20210003", nickname: "Alice", profileImage: "../../../../asset/ChatRoomPic4.png" },
+ { gender: "남자", major: "Mathematics", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic5.png" },
+ { gender: "남자", major: "asd", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic6.png" },
+
+ ],
+ maxMembers: 6,
+ enterCheck: false,
+ host: "asdfasdf1234346",
+ maleCount: 2,
+ femaleCount: 1,
+ profileImage: '../../../../asset/ChatRoomPic1.png',
+ hasStarted: false
+ },
+ {
+ id: 4,
+ title: "프로그래밍 기초",
+ subTitle: "프로그래밍의 기초를 배워봅시다",
+ //사진경로 절대경로로 수정
+ members: [
+ { gender: "여자", major: "Physics", studentId: "20210003", nickname: "Alice", profileImage: "../../../../asset/ChatRoomPic3.png" },
+ { gender: "남자", major: "Mathematics", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic2.png" },
+ { gender: "여자", major: "Mathematics", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic6.png" },
+ { gender: "남자", major: "Mathematics", studentId: "20210004", nickname: "Bob", profileImage: "../../../../asset/ChatRoomPic1.png" },
+ { gender: "여자", major: "asd", studentId: "20210004", nickname: "한준서", profileImage: "../../../../asset/ChatRoomPic5.png" }
+ ],
+ maxMembers: 6,
+ enterCheck: false,
+ host: "asdfasdf1234346",
+ maleCount: 2,
+ femaleCount: 3,
+ profileImage: '../../../../asset/ChatRoomPic1.png',
+ hasStarted: false
+ }
+ ]);
+
+
+ useEffect(() => {
+ const fetchChatRooms = async () => {
+ try {
+ const data = await fetchChatRoomFetch();
+ setChatRooms(data.rooms);
+ setPossibleEnterNumber(data.possibleEnterNumber);
+ setGender(data.gender);
+ } catch (error) {
+ console.error('Error fetching chat rooms:', error);
+ } finally {
+ setLoading(false);
+ }
+ };
+
+ fetchChatRooms();
+ }, []);
+
+
+
+
+
+
+
+
+ const makeChatRoom = () => {
+ //챗룸 만들기로 이동
+ navigate('/makeChatRoom')
+ }
+
+
+
+ if (loading) return (
+
+ );
+
+ return (
+
+
+
+
+
+
+ setIsEnterClick(true)} >참여중
+ setIsEnterClick(false)}>모집중
+
+ {isEnterCheck ?
최대 {possibleEnterNumber}개 방까지 참여 가능합니다 :
}
+
+
+
+
+ {isEnterCheck ? (
+ setIsEnterClick(value)}
+ />
+ ) : (
+ setIsEnterClick(value)}
+ />
+ )}
+
+
+
+
+
+
+
+
handleNavigation('play')}>
+
handleNavigation('talk')}>
+
handleNavigation('my')}>
+
+
+
+ );
+}
+
+export default ChatStartPage;
\ No newline at end of file
diff --git a/src/page/Chat/Dialog/ExitDialog.jsx b/src/page/Chat/Dialog/ExitDialog.jsx
new file mode 100644
index 0000000..503f1ce
--- /dev/null
+++ b/src/page/Chat/Dialog/ExitDialog.jsx
@@ -0,0 +1,57 @@
+import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './dialog.css'
+import { leaveChatRoom } from '../../../api/chatRoom/leaveChatRoom';
+import { sendLeaveMessage, unsubscribeFromRoom } from '../../../api/chatRoom/socket/socketService';
+
+function ExitDialog({ isOpen, onClose, possibleEnterNumber, roomId, socket }) {
+ const navigate = useNavigate();
+ if (!isOpen) return null;
+
+ const exitRoom = async () => {
+ try {
+ await leaveChatRoom(roomId);
+ sendLeaveMessage(socket, roomId);
+ unsubscribeFromRoom(socket, roomId);
+
+ navigate('/chatStartPage');
+ onClose();
+ } catch (error) {
+ console.error("채팅방 나가기 실패:", error);
+ }
+ }
+
+
+ return (
+
+
+
+
+
정말로 채팅방을 나가시겠어요?
+
+ 현재 나의 채팅방 입장 참여 횟수 {possibleEnterNumber}개
+
+
+
+
+
+
+
+
+
+
+ );
+}
+
+export default ExitDialog;
\ No newline at end of file
diff --git a/src/page/Chat/Dialog/LeaveDialog.jsx b/src/page/Chat/Dialog/LeaveDialog.jsx
new file mode 100644
index 0000000..0fba53d
--- /dev/null
+++ b/src/page/Chat/Dialog/LeaveDialog.jsx
@@ -0,0 +1,60 @@
+import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './dialog.css'
+import { deleteUser } from '../../../api/deleteUser';
+
+function LeaveDialog({ isOpen, onClose }) {
+ const navigate = useNavigate();
+ if (!isOpen) return null;
+
+ const exitRoom = async () => {
+ try {
+ const result = await deleteUser();
+ if (result.success) {
+ console.log('User account deleted successfully');
+ // You can add a success message or redirect the user here
+ } else {
+ console.error('Failed to delete user account');
+ // You can add an error message or handle the error here
+ }
+ } catch (error) {
+ console.error('Error deleting user account:', error);
+ // You can add an error message or handle the error here
+ }
+ //chatStartPage로 이동
+ navigate('/');
+ onClose();
+ }
+
+ return (
+
+
+
+
+
정말로 탈퇴하시겠어요?
+
+
+
+
+
+
+
+
+
+
+
+ );
+}
+
+export default LeaveDialog;
\ No newline at end of file
diff --git a/src/page/Chat/Dialog/MaxChanceDialog.jsx b/src/page/Chat/Dialog/MaxChanceDialog.jsx
new file mode 100644
index 0000000..76f9b54
--- /dev/null
+++ b/src/page/Chat/Dialog/MaxChanceDialog.jsx
@@ -0,0 +1,33 @@
+import React, { useState } from "react";
+import './dialog.css'
+
+function MaxChanceDialog({ isOpen, onClose, possibleEnterNumber }) {
+ if (!isOpen) return null;
+
+ return (
+
+
+
+
+
최대 참여 가능한 채팅방 수가 초과되었습니다
+
+ {/* 로직구현 */}
+ 현재 나의 채팅방 입장 잔여 횟수 {possibleEnterNumber}개
+
+
+
+
+
+ );
+}
+
+export default MaxChanceDialog;
\ No newline at end of file
diff --git a/src/page/Chat/Dialog/MaxMemberDialog.jsx b/src/page/Chat/Dialog/MaxMemberDialog.jsx
new file mode 100644
index 0000000..92c0323
--- /dev/null
+++ b/src/page/Chat/Dialog/MaxMemberDialog.jsx
@@ -0,0 +1,31 @@
+import React, { useState } from "react";
+
+function MaxMemberDialog({ isOpen, onClose }) {
+ if (!isOpen) return null;
+
+ return (
+
+
+
+
+
채팅방 인원이 마감되었습니다
+
+
+
+
+
+
+
+ );
+}
+
+export default MaxMemberDialog;
\ No newline at end of file
diff --git a/src/page/Chat/Dialog/OkayDialog.jsx b/src/page/Chat/Dialog/OkayDialog.jsx
new file mode 100644
index 0000000..40e4d6b
--- /dev/null
+++ b/src/page/Chat/Dialog/OkayDialog.jsx
@@ -0,0 +1,77 @@
+import React, { useState } from "react";
+import { useNavigate } from 'react-router-dom';
+import './dialog.css'
+
+function OkayDialog({ isOpen, onClose, selectChatRoom, possibleEnterNumber }) {
+ const navigate = useNavigate();
+
+ if (!isOpen) return null;
+
+
+ const maxVisibleProfiles = 3;
+ const memberLength = selectChatRoom.members.length;
+ const members = selectChatRoom.members.slice(0, maxVisibleProfiles);
+ const extraProfilesCount = memberLength - maxVisibleProfiles;
+
+ const memberLengthClassName = `member-length-${memberLength}`;
+
+
+
+ const goChatRoom = () => {
+ navigate(`/chat/2`); // 원하는 경로로 이동
+ // navigate(`/chat/${selectChatRoom.id}`); // 원하는 경로로 이동
+ //소켓으로 업그레이드 하고 방으로 이동
+ onClose();
+ }
+
+ return (
+
+
+
+
채팅방 메인 타이틀에 입장하시겠습니까?
+
+ {members.map((member, index) => (
+
0) ? '' : `url(${member.profileImage})`
+ }}
+ />
+ ))}
+ {extraProfilesCount > 0 && (
+
+ +{extraProfilesCount}
+
+ )}
+
+
+
+
+ 원활한 서비스 이용을 위해
+ 동시에 최대 3개의 채팅방을 이용할 수 있습니다
+
+
+ 현재 나의 채팅방 입장 참여 횟수 {possibleEnterNumber}개
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ );
+}
+
+export default OkayDialog;
\ No newline at end of file
diff --git a/src/page/Chat/Dialog/UserintroduceDialog.jsx b/src/page/Chat/Dialog/UserintroduceDialog.jsx
new file mode 100644
index 0000000..4d12959
--- /dev/null
+++ b/src/page/Chat/Dialog/UserintroduceDialog.jsx
@@ -0,0 +1,78 @@
+import React, { useState, useEffect } from "react";
+import { fetchAnotherInformation } from '../../../api/chatRoom/fetchAnotherInformation';
+
+function UserIntroduceDialog({ isOpen, onClose, nickname, roomId }) {
+ //유저의 정보를 받아오는 useEffect 사용
+ const [profile, setProfile] = useState({
+ profileImage: "",
+ nickname: "아아",
+ department: "컴공",
+ studentId: "202001485",
+ shortIntroduce: "안녕하세요",
+ mbti: "INFJ",
+ height: "180",
+ drinking: "소주3병마심",
+ smoking: "1갑"
+ });
+
+
+ useEffect(() => {
+ const fetchIntroduceItems = async () => {
+ try {
+ const userData = await fetchAnotherInformation(nickname, roomId);
+ setProfile(userData);
+ } catch (error) {
+ console.error('Error fetching user info:', error);
+ }
+ };
+ fetchIntroduceItems();
+ }, [nickname, roomId]);
+
+
+
+
+
+
+ if (!isOpen) return null;
+
+
+
+ return (
+
+
+
+
+

+
+
{profile.nickname}
+
{profile.department} {profile.studentId.slice(1, 3)}학번
+
+
{profile.shortIntroduce}
+
+
+
+
+ {/* 유저를통한 로직추가 */}
+
+
+
+
+
+
+
+
+
+
+
+
+ );
+}
+
+export default UserIntroduceDialog;
\ No newline at end of file
diff --git a/src/page/Chat/Dialog/dialog.css b/src/page/Chat/Dialog/dialog.css
new file mode 100644
index 0000000..3e3e3fd
--- /dev/null
+++ b/src/page/Chat/Dialog/dialog.css
@@ -0,0 +1,483 @@
+.dialog {
+
+ position: absolute;
+ height: 100%;
+ width: 100%;
+ top: 0px;
+ background: rgba(0, 0, 0, 0.1);
+ z-index: 1000;
+ left: 0px;
+
+ .dialog-backdrop {
+
+
+ display: flex;
+ justify-content: center;
+ align-items: center;
+
+
+ z-index: 1000;
+ /* 앞으로 오게 하기 위해 z-index 값 추가 */
+
+ /* Group 816134 */
+
+ position: absolute;
+ width: 343px;
+ height: 330px;
+ left: calc(50% - 343px/2);
+ top: 199px;
+ }
+
+ .dialog-container {
+ background-color: white;
+ border-radius: 20px;
+ width: 343px;
+ height: 330px;
+ text-align: center;
+ box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);
+ display: flex;
+ flex-direction: column;
+
+
+ }
+
+ .dialog-icon {
+ margin-top: 32px;
+ margin-bottom: 32px;
+ }
+
+ .dialog-title {
+ /* 최대 참여 가능 채팅방 수가 초과되었습니다 */
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 16px;
+ line-height: 18px;
+ margin-bottom: 0;
+ /* identical to box height, or 112% */
+
+
+ color: #3D3D3D;
+ }
+
+ .dialog-message {
+ margin-top: 3px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 12px;
+ line-height: 14px;
+ /* identical to box height, or 117% */
+
+
+ color: #3D3D3D;
+ }
+
+ .highlight-text {
+ color: #FF7898;
+ font-weight: bold;
+ }
+
+
+
+ .dialog-button {
+ background-color: #F5F5F5;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 18px;
+ line-height: 20px;
+ color: #3D3D3D;
+ border: none;
+ border-radius: 14px;
+ padding: 10px 20px;
+ font-size: 16px;
+ cursor: pointer;
+ margin: 10px 31px 0 31px;
+ }
+
+ .dialog-button:hover {
+ background-color: #FF7898;
+ }
+
+
+ .dialog-okay-title {
+ /* 에 입장하시겠습니까? */
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 16px;
+ line-height: 18px;
+ /* identical to box height, or 112% */
+ margin-top: 30px;
+ align-items: center;
+ color: #3D3D3D;
+ }
+
+ .button-container {
+ display: flex;
+ flex-direction: row;
+ justify-content: space-evenly;
+ }
+
+ .dialog-button-cancle {
+ /* Rectangle 3470049 */
+ width: 136px;
+ height: 44px;
+ border: none;
+ background: #F5F5F5;
+ border-radius: 14px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 18px;
+ line-height: 20px;
+ color: #3D3D3D;
+ }
+
+ .dialog-button-pink {
+ /* Rectangle 3470049 */
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 18px;
+ line-height: 20px;
+ color: #FFFFFF;
+ width: 136px;
+ height: 44px;
+ border: none;
+ background: #FF7898;
+ border-radius: 14px;
+ }
+
+
+ .dialog-icon-container {
+ margin-top: 15px;
+ display: flex;
+ justify-content: center;
+ text-align: center;
+ }
+
+ /*원이 3개이상*/
+ .profile-icon-0 {
+ width: 96px;
+ height: 96px;
+ background-size: cover;
+ background-position: center;
+ border-radius: 50%;
+ position: relative;
+ background-color: #A0A0A0;
+ left: 60px;
+ top: 0;
+ z-index: 0;
+ }
+
+ .profile-icon-1 {
+ width: 96px;
+ height: 96px;
+ background-size: cover;
+ background-position: center;
+ border-radius: 50%;
+ position: relative;
+ background-color: #BBBBBB;
+ left: 0;
+ top: 0;
+ z-index: 1;
+ }
+
+ .profile-icon-2 {
+ width: 96px;
+ height: 96px;
+ background-size: cover;
+ background-position: center;
+ border-radius: 50%;
+ position: relative;
+ background-color: #F5F5F5;
+ left: -60px;
+ top: 0;
+ z-index: 2;
+ }
+
+ /*원이 2개*/
+ .profile-icon-0.member-length-2 {
+ width: 96px;
+ height: 96px;
+ background-size: cover;
+ background-position: center;
+ border-radius: 50%;
+ position: relative;
+ background-color: #A0A0A0;
+ left: 30px;
+ top: 0;
+ z-index: 0;
+ }
+
+ .profile-icon-1.member-length-2 {
+ width: 96px;
+ height: 96px;
+ background-size: cover;
+ background-position: center;
+ border-radius: 50%;
+ position: relative;
+ background-color: #BBBBBB;
+ left: -30px;
+ top: 0;
+ z-index: 1;
+ }
+
+ /*원이 1개*/
+ .profile-icon-0.member-length-1 {
+ width: 96px;
+ height: 96px;
+ background-size: cover;
+ background-position: center;
+ border-radius: 50%;
+ position: relative;
+ background-color: #A0A0A0;
+ left: 0px;
+ top: 0;
+ z-index: 0;
+ }
+
+
+ .extra-profile-count {
+
+ /* +2 */
+
+ position: absolute;
+ width: 17px;
+ height: 16px;
+ left: 200px;
+ top: 118px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 14px;
+ line-height: 16px;
+ /* identical to box height, or 114% */
+ display: flex;
+ align-items: center;
+ text-align: center;
+
+ color: #606060;
+ z-index: 3;
+
+ }
+
+ .okayDialog-container {
+ display: flex;
+ flex-direction: column;
+ margin-left: 47px;
+ }
+
+ .dialog-message-2 {
+ /* 원활한 서비스 이용을 위해 동시에 최대 3개의 채팅방을 이용할 수 있습니다 */
+ margin-top: 15px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 12px;
+ line-height: 18px;
+ /* or 150% */
+ margin-bottom: 0px;
+ color: #777777;
+
+ display: flex;
+ justify-content: start;
+ flex-direction: column;
+ text-align: left;
+ }
+
+ .dialog-message.okay {
+ margin-top: 0px;
+ margin-bottom: 16px;
+ text-align: left;
+ }
+}
+
+
+.userIntroduceDialog {
+ position: absolute;
+ height: 100%;
+ width: 100%;
+ top: 0px;
+ background: rgba(0, 0, 0, 0.1);
+ z-index: 1000;
+ left: 0px;
+ display: flex;
+ justify-content: center;
+
+ .dialog-backdrop {
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ z-index: 1000;
+ position: absolute;
+ width: 375px;
+ height: 558px;
+ top: 254px;
+ }
+
+ .dialog-container {
+ background-color: white;
+ border-radius: 20px;
+ width: 100%;
+ height: 100%;
+ text-align: center;
+ box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);
+ display: flex;
+ flex-direction: column;
+
+
+ }
+
+
+ .dialog-title {
+ /* 최대 참여 가능 채팅방 수가 초과되었습니다 */
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 16px;
+ line-height: 18px;
+ margin-bottom: 0;
+ /* identical to box height, or 112% */
+ margin-top: 10px;
+
+ color: #3D3D3D;
+ }
+
+ .dialog-message {
+ margin-top: 3px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 14px;
+ color: #777777;
+ }
+
+
+ .button-container {
+ margin-top: 30px;
+ display: flex;
+ flex-direction: row;
+ justify-content: space-evenly;
+ }
+
+
+
+
+ .dialog-button-cancle {
+ /* Rectangle 3470049 */
+ width: 136px;
+ height: 44px;
+ border: none;
+ background-color: #F5F5F5;
+ border-radius: 14px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 18px;
+ line-height: 20px;
+ cursor: pointer;
+ color: #3D3D3D;
+ }
+
+
+ .dialog-button-cancle:hover {
+ background-color: #FF7898;
+ color: #F5F5F5;
+ }
+
+ .profile-image-container {
+ margin-top: 50px;
+ }
+
+ .profile-image-container img {
+ width: 128px;
+ height: 128px;
+ border-radius: 50%;
+ }
+
+ .introduction-container {
+ margin: 10px auto;
+ margin-bottom: 30px;
+ width: 343px;
+ height: 46px;
+ background: #F5F5F5;
+ border-radius: 10px;
+ align-items: center;
+ display: flex;
+ }
+
+ .introduction {
+ /* 한 줄 소개 안녕하세요~~~~ */
+ width: 100%;
+ height: 16px;
+ padding: 0 20px;
+ text-align: left;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 400;
+ font-size: 14px;
+ line-height: 16px;
+
+
+ color: #3D3D3D;
+ }
+
+ .additional-info-container {
+ margin: 0 20px;
+ padding: 0 10px;
+ background: #F5F5F5;
+ border-radius: 10px;
+
+ }
+
+ .additional-info {
+ width: 100%;
+ height: 100%;
+ text-align: left;
+ display: flex;
+ flex-direction: column;
+ padding: 10px;
+ gap: 7px;
+ }
+
+ .additional-info div {
+ display: flex;
+ flex-direction: row;
+ }
+
+ .additional-info .first {
+
+ width: 45px;
+ height: 16px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 400;
+ font-size: 14px;
+ line-height: 16px;
+
+
+ color: #3D3D3D;
+ }
+
+ .additional-info .second {
+
+ width: 269px;
+ height: 16px;
+ margin-left: 10px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 14px;
+ line-height: 16px;
+
+
+ color: #3D3D3D;
+ }
+
+}
\ No newline at end of file
diff --git a/src/page/Chat/EnterCheckPage.jsx b/src/page/Chat/EnterCheckPage.jsx
new file mode 100644
index 0000000..901e748
--- /dev/null
+++ b/src/page/Chat/EnterCheckPage.jsx
@@ -0,0 +1,254 @@
+import React, { useState, useEffect } from "react";
+import { useNavigate } from 'react-router-dom';
+import './ChatPage.css'
+import { roomStart } from '../../api/chatRoom/roomStart'
+import { fetchRoomParticipants } from '../../api/chatRoom/fetchRoomParticipants';
+
+function EnterCheckPage(props) {
+ const { chatRooms, isEnterCheck } = props;
+ const [expandedRoomIds, setExpandedRoomIds] = useState([]);
+ const [updatedChatRooms, setUpdatedChatRooms] = useState(
+ chatRooms.filter(room => room.enterCheck === true)
+ );
+
+ const navigate = useNavigate();
+
+ //새로고침
+ const [startY, setStartY] = useState(0);
+ const [translateY, setTranslateY] = useState(0);
+ const [isRefreshing, setIsRefreshing] = useState(false);
+
+ const threshold = 80; // 새로고침을 트리거하는 기준 거리
+
+ // 새로고침 함수
+ const handleRefresh = () => {
+ setIsRefreshing(true);
+ setTimeout(() => {
+ setIsRefreshing(false);
+ isEnterCheck(true); // enterCheck를 true로 설정
+ }, 1500);
+ };
+
+ // 터치 시작
+ const handleTouchStart = (event) => {
+ setStartY(event.touches[0].clientY);
+ };
+
+ // 터치 중일 때
+ const handleTouchMove = (event) => {
+ const currentY = event.touches[0].clientY;
+ const distance = currentY - startY;
+
+
+ // 스크롤이 최상단일 때만 동작
+ if (window.scrollY === 0 && distance > 0) {
+ setTranslateY(distance * 0.3); // 끌린 만큼 translateY 값을 설정
+ }
+
+ // 기준 거리를 넘었을 때 새로고침
+ if (distance > threshold) {
+ handleRefresh();
+ }
+ };
+
+ // 터치 끝
+ const handleTouchEnd = () => {
+ setTranslateY(0); // 터치가 끝나면 원래 위치로 돌아가기
+ };
+
+
+
+ //토글확장 관리
+ const toggleExpand = (roomId) => {
+ setExpandedRoomIds(prevState =>
+ prevState.includes(roomId)
+ ? prevState.filter(id => id !== roomId)
+ : [...prevState, roomId]
+ );
+ console.log(expandedRoomIds)
+ };
+
+
+
+ const goChatRoom = (roomId) => {
+ navigate('/chat/2');
+ //navigate(`/chat/${roomId}`); // 원하는 경로로 이동
+ }
+
+ // 수정된 handleButtonClick 함수
+ const handleButtonClick = async (event, room) => {
+ if (room.members.length < room.maxMembers) {
+ event.stopPropagation(); // 이벤트 버블링을 막음
+ } else {
+ event.stopPropagation();
+ const started = await roomStart(room.id);
+ if (started) {
+ goChatRoom(room.id);
+ } else {
+ // 시작 실패 시 에러 처리 (예: 알림 표시)
+ console.error('Failed to start the room');
+ }
+ }
+ };
+
+
+
+
+ useEffect(() => {
+ if (expandedRoomIds.length > 0) {
+ const updateMembers = async () => {
+ const updatedRooms = await Promise.all(
+ updatedChatRooms.map(async (room) => {
+ if (room.id === expandedRoomIds[expandedRoomIds.length - 1]) {
+ const updatedMembers = await fetchRoomParticipants(room.id);
+ return {
+
+ ...room,
+ members: updatedMembers,
+ maleCount: updatedMembers.filter(member => member.gender === "남자").length,
+ femaleCount: updatedMembers.filter(member => member.gender === "여자").length
+ };
+ }
+ return room;
+ })
+ );
+
+ setUpdatedChatRooms(updatedRooms);
+ };
+
+ updateMembers();
+ }
+ }, [expandedRoomIds, isEnterCheck, chatRooms]);
+
+ // // expandedRoomIds가 변경될 때마다 서버에서 members를 가져와 업데이트하는 useEffect
+ // useEffect(() => {
+ // if (expandedRoomIds.length > 0) {
+ // const fetchRoomDetails = async (roomId) => {
+ // try {
+ // const response = await api.get(`/api/chatroom/participants/${roomId}`);
+ // return response.data.members; // 서버로부터 members를 받아옴
+ // } catch (error) {
+ // console.error(`Error fetching room details for roomId: ${roomId}`, error);
+ // return [];
+ // }
+ // };
+
+ // const updateMembers = async () => {
+ // const updatedRooms = await Promise.all(
+ // chatRooms.map(async (room) => {
+ // if (room.id === expandedRoomIds[expandedRoomIds.length - 1]) {
+ // const updatedMembers = await fetchRoomDetails(room.id);
+ // return { ...room, members: updatedMembers };
+ // }
+ // console.log(updatedChatRooms);
+ // return room;
+ // })
+ // );
+
+ // setUpdatedChatRooms(updatedRooms);
+ // };
+
+ // updateMembers();
+ // }
+ // }, [expandedRoomIds,isEnterCheck]); // expandedRoomIds가 변경될 때 reload될 때 마다
+
+
+ return (
+
+ {isRefreshing &&
}
+ {updatedChatRooms
+ .map(room => {
+ const maleCount = room.maleCount;
+ const femaleCount = room.femaleCount;
+
+ const isExpanded = expandedRoomIds.includes(room.id); // 현재 방이 확장되었는지 확인
+ return (
+
+
+
+
+
+
+
+ {/* /사진수정/ */}
+

+
{room.title}
+
남: {maleCount} 여: {femaleCount}
+
{room.subTitle}
+
+
toggleExpand(room.id)}>
+
+ 참여인원 보기
+ {!isExpanded ? :
+ }
+
+
+ {/* 확장된 상태일 때만 멤버 리스트를 렌더링 */}
+
+
+
+
+
+
+
+
+
+
+ );
+ })}
+
+ )
+}
+
+
+export default EnterCheckPage;
\ No newline at end of file
diff --git a/src/page/Chat/MakeChatRoom/MakeChatRoom.css b/src/page/Chat/MakeChatRoom/MakeChatRoom.css
new file mode 100644
index 0000000..bf09277
--- /dev/null
+++ b/src/page/Chat/MakeChatRoom/MakeChatRoom.css
@@ -0,0 +1,255 @@
+.makeChatRoom {
+
+ height: 812px;
+ width: 375px;
+ margin: 0 auto;
+
+ .margin-container {
+ display: flex;
+ flex-direction: column;
+ height: 100%;
+ margin: 0 10px;
+ }
+
+ .title {
+ width: 100%;
+ height: 46px;
+ margin-top: 50px;
+ background: #ffffff;
+ display: flex;
+ text-align: center;
+ margin-left: 6px;
+ justify-content: space-between;
+ }
+
+ .title-name {
+ /* 채팅방 이름 */
+
+ padding-top: 15px;
+ width: 120px;
+ height: 18px;
+
+ cursor: pointer;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 16px;
+ line-height: 18px;
+ /* identical to box height, or 112% */
+ display: flex;
+ align-items: center;
+
+ color: #3D3D3D;
+
+
+ }
+
+ .small-title {
+ /* 채팅방 정보 */
+ margin-top: 20px;
+ width: 73px;
+ height: 18px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 16px;
+ line-height: 18px;
+
+ color: #3D3D3D;
+
+ }
+
+ .top {
+ width: 100%;
+ display: flex;
+ flex-direction: row;
+ gap: 20px;
+ height: 80px;
+ margin-bottom: 20px;
+ justify-content: space-between;
+
+ }
+
+
+ .chat-room-info {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ margin-top: 5px;
+ }
+
+
+
+ .top img {
+ border: 1px solid #ccc;
+ border-radius: 50%;
+ width: 80px;
+ height: 100%;
+ /* background-color: none; */
+ }
+
+
+ .edit-avatar {
+ border: 1px solid #ccc;
+ border-radius: 50%;
+ position: relative;
+ width: 20px;
+ height: 20px;
+ left: -110px;
+ top: 80px;
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ background: #F5F5F5;
+ }
+
+ .chat-room-name {
+
+
+ width: 230px;
+ background: #F5F5F5;
+ border-radius: 10px;
+ margin: auto 0px;
+ height: 50px;
+ border: 1px solid #ccc;
+ padding: 0 10px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 400;
+ font-size: 14px;
+ line-height: 16px;
+ color: #777777;
+ }
+
+ .chat-room-description {
+
+ width: 335px;
+ height: 100px;
+
+ background: #F5F5F5;
+ border-radius: 10px;
+
+ border: 1px solid #ccc;
+ border-radius: 10px;
+ font-size: 14px;
+
+
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 400;
+ font-size: 14px;
+ line-height: 16px;
+ padding: 10px;
+ color: #777777;
+ }
+
+ .members-settings {
+ margin-top: 50px;
+ margin-bottom: 20px;
+ }
+
+ .small-title2 {
+ width: 73px;
+ height: 18px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 16px;
+ line-height: 18px;
+ margin-bottom: 30px;
+ color: #3D3D3D;
+ }
+
+ .gender-settings {
+ margin-left: 10px;
+ display: flex;
+ flex-direction: column;
+ gap: 15px;
+ }
+
+
+ .gender-settings div {
+ display: flex;
+ flex-direction: row;
+ align-items: center;
+ gap: 10px;
+ }
+
+ .gender-settings span {
+
+ width: 25px;
+ height: 16px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 14px;
+ line-height: 16px;
+
+
+ color: #3D3D3D;
+ }
+
+
+
+ .count-button {
+
+ padding: 5px 15px;
+ border-radius: 20px;
+ border: 1px solid #ccc;
+ background-color: #fff;
+ cursor: pointer;
+ }
+
+ .count-button.active {
+ background-color: #FF7898;
+ border-color: #ccc;
+ color: #F5F5F5;
+ }
+
+
+
+ .note {
+ margin-top: 50px;
+ font-size: 12px;
+ color: #888;
+ margin-bottom: 20px;
+ }
+
+ .create-room-button {
+ /* Rectangle 13 */
+ margin: 5px auto;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 700;
+ font-size: 18px;
+ line-height: 20px;
+ color: #FFFFFF;
+ background: #FF7898;
+ width: 343px;
+ height: 50px;
+ background: #FF7898;
+ border-radius: 5px;
+ border: none;
+ }
+
+ .create-room-button:hover {
+ background-color: #FF7898;
+ }
+
+ .error {
+ margin-left: 7px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 400;
+ font-size: 12px;
+ line-height: 14px;
+ display: flex;
+ align-items: center;
+ color: #FF3131;
+ }
+
+}
\ No newline at end of file
diff --git a/src/page/Chat/MakeChatRoom/MakeChatRoom.jsx b/src/page/Chat/MakeChatRoom/MakeChatRoom.jsx
new file mode 100644
index 0000000..609dd7a
--- /dev/null
+++ b/src/page/Chat/MakeChatRoom/MakeChatRoom.jsx
@@ -0,0 +1,224 @@
+import React, { useState, useRef } from "react";
+import './MakeChatRoom.css'
+import { useNavigate } from 'react-router-dom';
+import Pic1 from '../../../asset/ChatRoomPic1.png'
+import Pic2 from '../../../asset/ChatRoomPic2.png'
+import Pic3 from '../../../asset/ChatRoomPic3.png'
+import Pic4 from '../../../asset/ChatRoomPic4.png'
+import Pic5 from '../../../asset/ChatRoomPic5.png'
+import Pic6 from '../../../asset/ChatRoomPic6.png'
+import { makeChatRoom } from '../../../api/chatRoom/makeChatRoom';
+
+
+
+function MakeChatRoom() {
+
+ const profileImages = [
+ Pic1, Pic2, Pic3, Pic4, Pic5, Pic6
+ ]
+ const getRandomImage = () => {
+ return profileImages[Math.floor(Math.random() * profileImages.length)];
+ };
+
+ const navigate = useNavigate();
+
+ const [count, setCount] = useState(3);
+ const [roomTitle, setRoomTitle] = useState('');
+ const [subTitle, setSubTitle] = useState('');//30자 이내로 제한
+ const [profileImage, setProfileImage] = useState(getRandomImage());
+ const [error, setError] = useState('');
+
+ const handleNavigation = (destination) => {
+ switch (destination) {
+ case 'play':
+ window.location.reload();
+ break;
+ case 'talk':
+ navigate('/ChatStartPage'); // 페이지 새로고침 (필요에 따라 이 부분을 변경)
+ break;
+ case 'my':
+ navigate('/myPage');
+ break;
+ default:
+ break;
+ }
+ };
+
+ const fileInputRef = useRef(null);
+
+ const handleImageClick = () => {
+ fileInputRef.current.click();
+ };
+
+ const handleImageChange = (event) => {
+ const file = event.target.files[0];
+ if (file) {
+ const reader = new FileReader();
+ reader.onloadend = () => {
+ setProfileImage(reader.result);
+ };
+ reader.readAsDataURL(file);
+ }
+ };
+
+
+ const handleTitleChange = (e) => {
+ if (e.target.value.length <= 20) {
+ setRoomTitle(e.target.value);
+ }
+ };
+
+ const handleSubTitleChange = (e) => {
+ if (e.target.value.length <= 50) {
+ setSubTitle(e.target.value);
+ }
+ };
+
+ const makeRoom = async () => {
+ if (roomTitle === '' || subTitle === '') {
+ setError('모든 필드를 입력해 주세요.');
+ return;
+ }
+
+ try {
+ const numberOfMembers = count * 2;
+ const roomData = {
+ title: roomTitle,
+ subTitle: subTitle,
+ profileImage: profileImage,
+ maxMembers: numberOfMembers,
+ maleCount: count,
+ femaleCount: count
+ };
+
+ await makeChatRoom(roomData);
+ console.log("Room Created");
+ navigate('/ChatStartPage');
+ setError('');
+ } catch (error) {
+ setError(error.message);
+ }
+ };
+
+
+
+
+ return (
+ <>
+
+
+
+
navigate('/ChatStartPage')} >
+
+
+ 채팅방 만들기
+
+
+
+
+
채팅방 정보
+
+
+
+
+

+
+
+
+
+
+
+
인원 설정
+
+
+ 남자
+ {[2, 3, 4, 5].map(cnt => (
+
+ ))}
+
+
+
+ 여자
+ {[2, 3, 4, 5].map(cnt => (
+
+ ))}
+
+
+
+
+
+ {/* 로직추가 */}
+ - 생성된 채팅방은 30일 후에 자동으로 종료됩니다.
+
+
+ {/* Display error message if needed */}
+ {error &&
+ {error}
}
+
+
+
+
+
+
+
+
+
handleNavigation('play')}>
+
handleNavigation('talk')}>
+
handleNavigation('my')}>
+
+
+
+
+
+ >
+ );
+}
+
+export default MakeChatRoom;
\ No newline at end of file
diff --git a/src/page/Chat/NoEnterCheckPage.jsx b/src/page/Chat/NoEnterCheckPage.jsx
new file mode 100644
index 0000000..f7f985e
--- /dev/null
+++ b/src/page/Chat/NoEnterCheckPage.jsx
@@ -0,0 +1,273 @@
+import React, { useState, useEffect } from "react";
+import './ChatPage.css'
+import OkayDialog from './Dialog/OkayDialog'
+import MaxMemberDialog from './Dialog/MaxMemberDialog'
+import MaxChanceDialog from './Dialog/MaxChanceDialog'
+import { fetchRoomParticipants } from "../../api/chatRoom/fetchRoomParticipants";
+
+function NoEnterCheckPage(props) {
+ const { chatRooms, possibleEnterNumber, gender, isEnterCheck } = props;
+ const [expandedRoomIds, setExpandedRoomIds] = useState([]);
+ const [okayDialog, setOkayDialog] = useState(false);
+ const [maxMemberDialog, setMaxMemberDialog] = useState(false);
+ const [maxChanceDialog, setMaxChanceDialog] = useState(false);
+ const [selectChatRoom, setSelectChatRoom] = useState(false);
+
+
+ const [updatedChatRooms, setUpdatedChatRooms] = useState(
+ chatRooms.filter(room => room.enterCheck === false)
+ );
+
+
+
+
+ //새로고침
+ const [startY, setStartY] = useState(0);
+ const [translateY, setTranslateY] = useState(0);
+ const [isRefreshing, setIsRefreshing] = useState(false);
+
+
+
+ const threshold = 80; // 새로고침을 트리거하는 기준 거리
+
+ // 새로고침 함수
+ const handleRefresh = () => {
+ setIsRefreshing(true);
+ setTimeout(() => {
+ setIsRefreshing(false);
+ isEnterCheck(false); // 페이지 새로고침 (필요에 따라 이 부분을 변경)
+ }, 1500);
+ };
+
+ // 터치 시작
+ const handleTouchStart = (event) => {
+ setStartY(event.touches[0].clientY);
+ };
+
+ // 터치 중일 때
+ const handleTouchMove = (event) => {
+ const currentY = event.touches[0].clientY;
+ const distance = currentY - startY;
+
+
+ // 스크롤이 최상단일 때만 동작
+ if (window.scrollY === 0 && distance > 0) {
+ setTranslateY(distance * 0.3); // 끌린 만큼 translateY 값을 설정
+ }
+
+ // 기준 거리를 넘었을 때 새로고침
+ if (distance > threshold) {
+ handleRefresh();
+ }
+ };
+
+ // 터치 끝
+ const handleTouchEnd = () => {
+ setTranslateY(0); // 터치가 끝나면 원래 위치로 돌아가기
+ };
+
+
+ useEffect(() => {
+ if (expandedRoomIds.length > 0) {
+ const updateMembers = async () => {
+ const updatedRooms = await Promise.all(
+ updatedChatRooms.map(async (room) => {
+ if (room.id === expandedRoomIds[expandedRoomIds.length - 1]) {
+ const updatedMembers = await fetchRoomParticipants(room.id);
+ return {
+
+ ...room,
+ members: updatedMembers,
+ maleCount: updatedMembers.filter(member => member.gender === "남자").length,
+ femaleCount: updatedMembers.filter(member => member.gender === "여자").length
+ };
+ }
+ return room;
+ })
+ );
+
+ setUpdatedChatRooms(updatedRooms);
+ };
+
+ updateMembers();
+ }
+ }, [expandedRoomIds, isEnterCheck, chatRooms]);
+
+
+ //전에꺼
+ // // expandedRoomIds가 변경될 때마다 서버에서 members를 가져와 업데이트하는 useEffect
+ // useEffect(() => {
+ // if (expandedRoomIds.length > 0) {
+ // const fetchRoomDetails = async (roomId) => {
+ // try {
+ // const response = await api.get(`/api/chatroom/participants/${roomId}`);
+ // return response.data; // 서버로부터 members를 받아옴
+ // } catch (error) {
+ // console.error(`Error fetching room details for roomId: ${roomId}`, error);
+ // return [];
+ // }
+ // };
+
+ // const updateMembers = async () => {
+ // const updatedRooms = await Promise.all(
+ // chatRooms.map(async (room) => {
+ // if (room.id === expandedRoomIds[expandedRoomIds.length - 1]) {
+ // const updatedMembers = await fetchRoomDetails(room.id);
+ // return { ...room, members: updatedMembers };
+ // }
+ // console.log(updatedChatRooms);
+ // return room;
+ // })
+ // );
+
+ // setUpdatedChatRooms(updatedRooms);
+ // };
+
+ // updateMembers();
+ // }
+ // }, [expandedRoomIds,isEnterCheck]); // expandedRoomIds가 변경될 때마다
+
+
+
+
+
+
+
+ const toggleExpand = (roomId) => {
+ setExpandedRoomIds(prevState =>
+ prevState.includes(roomId)
+ ? prevState.filter(id => id !== roomId) // 이미 확장된 상태면 닫기
+ : [...prevState, roomId] // 확장되지 않았다면 추가
+ );
+ };
+
+ const enterCheckMessage = (chatRoom) => {
+ const halfMaxMembers = Math.floor(chatRoom.maxMembers / 2); // 최대 인원의 절반 계산
+ let maleCount = chatRoom.maleCount;
+ let femaleCount = chatRoom.femaleCount;
+
+ // 유저가 남자일 때: 남성 인원이 절반보다 적으면 true
+ if (gender === "남자" && maleCount < halfMaxMembers) {
+ return true;
+ }
+
+ // 유저가 여자일 때: 여성 인원이 절반보다 적으면 true
+ if (gender === "여자" && femaleCount < halfMaxMembers) {
+ return true;
+ }
+
+ // 그 외에는 참가 불가
+ return false;
+ };
+
+ const dialogOpen = (room) => {
+ if (!enterCheckMessage(room)) {
+ setMaxMemberDialog(true);
+ } else if (possibleEnterNumber === 0) {
+ setMaxChanceDialog(true)
+ } else {
+ setSelectChatRoom(room)
+ setOkayDialog(true);
+ }
+ }
+
+
+
+
+
+
+
+
+ return (
+ <>
+ {/* 다이얼로그 컴포넌트들 */}
+
setOkayDialog(false)} />
+ setMaxMemberDialog(false)} />
+ setMaxChanceDialog(false)} />
+
+
+ {isRefreshing &&
}
+
+ {updatedChatRooms
+ .map(room => {
+ const maleCount = room.maleCount;
+ const femaleCount = room.femaleCount;
+
+ const isExpanded = expandedRoomIds.includes(room.id); // 현재 방이 확장되었는지 확인
+ return (
+
+
dialogOpen(room)}>
+ {enterCheckMessage(room) ?
참여가능
:
참여불가
}
+
{room.title}
+
+ 남 {enterCheckMessage(room) ? {maleCount} : {maleCount}}/{room.maxMembers / 2}
+ 여 {enterCheckMessage(room) ? {femaleCount} : {femaleCount}}/{room.maxMembers / 2}
+
+
+
{room.subTitle}
+
+
toggleExpand(room.id)}>
+
+ 참여인원 보기
+ {!isExpanded ? :
+ }
+
+
+ {/* 확장된 상태일 때만 멤버 리스트를 렌더링 */}
+
+
+
+ );
+ })}
+
+ >
+ )
+
+}
+
+
+
+export default NoEnterCheckPage;
\ No newline at end of file
diff --git a/src/page/Login/Login.css b/src/page/Login/Login.css
new file mode 100644
index 0000000..0c84c80
--- /dev/null
+++ b/src/page/Login/Login.css
@@ -0,0 +1,419 @@
+.LoginPage {
+ height: 812px;
+ width: 375px;
+ margin: 0 auto;
+
+ .container {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ font-family: 'Pretendard', sans-serif;
+ height: 100%;
+ }
+
+ .login-heading {
+ width: 300px;
+ height: 24px;
+ margin-top: 50px;
+ margin-bottom: 5px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 20px;
+ line-height: 24px;
+ align-items: center;
+ color: #3D3D3D;
+ }
+
+ .login-subtext {
+ /* 안전한 인피 활동을 위해 학교 인증이 필요해요 */
+ width: 300px;
+ height: 18px;
+ margin-bottom: 50px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 16px;
+ align-items: center;
+ color: #3D3D3D;
+ }
+
+ .password-input {
+ /* 이메일 입력창 */
+ width: 290px;
+ height: 46px;
+ margin-top: 1px; /* 상단 여백 */
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ }
+
+ .header {
+ /* 상단 헤더 */
+ width: 100%;
+ display: flex;
+ align-items: center;
+ justify-content: space-between;
+ }
+
+ .back-button {
+ /* 왼쪽 꺽쇠 */
+ border: none;
+ background-color: transparent;
+ font-size: 24px;
+ cursor: pointer;
+ width: 22px;
+ height: 22px;
+ margin-top: 80px;
+ align-self: flex-start;
+ }
+
+ .button-container{
+ margin-top:auto;
+ }
+
+ .bottom-Button {
+ /* 하단 버튼 */
+ width: 300px;
+ height: 50px;
+
+ color: #F7F7F7;
+ background: #FF7898;
+ border-radius: 8px;
+ border-color: rgb(255, 255, 255);
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 700;
+ font-size: 18px;
+
+ margin-bottom: 40px;
+ margin-top:auto;
+
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ }
+
+ .bottom-Button:disabled {
+ background-color: #dadada;
+ color: white;
+ }
+
+ .error-message {
+ color: red;
+ font-size: 0.5em;
+
+ width: 320px;
+ height: 14px;
+
+ }
+
+ .email-input {
+ /* 이메일 입력창 */
+ width: 290px;
+ height: 46px;
+ margin-top: 1px; /* 상단 여백 */
+ display: flex;
+ justify-content: center;
+ align-items: center;
+
+ }
+
+ .code-inputs {
+ /* 인증번호 입력 */
+ display: flex;
+ justify-content: center;
+ gap: 10px;
+ /* 입력 필드 사이의 간격 */
+ }
+
+ .code-input {
+ width: 35px;
+ /* 네모 박스 너비 */
+ height: 35px;
+ /* 네모 박스 높이 */
+ font-size: 16px;
+ text-align: center;
+ border: 1px solid #ccc;
+ /* 테두리 */
+ border-radius: 5px;
+ /* 모서리를 둥글게 */
+ margin-bottom: 40px;
+
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ }
+
+ .resend {
+ /* 메일을 못받으셨나요? */
+ width: 450px;
+ height: 16px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 14px;
+ line-height: 16px;
+
+ margin-left: 160px;
+ margin-bottom: 330px;
+ color: #8C8C8C;
+ }
+
+ .login-subtext1 {
+ width: 300px;
+ height: 18px;
+ margin-top: 30px;
+ margin-bottom: 20px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 16px;
+ display: flex;
+ align-items: center;
+ color: #3D3D3D;
+ }
+
+ .header {
+ /* 상단 헤더 */
+ width: 100%;
+ display: flex;
+ align-items: center;
+ justify-content: space-between;
+ }
+
+ /* 실행 단계 배경 CSS */
+ .progress-bar {
+ width: 240px;
+ height: 10px;
+ margin-top: 90px;
+ align-self: flex-start;
+ margin-right: 70px;
+ background: #D9D9D9;
+ border-radius: 50px;
+ }
+
+ /* 실행 단계 CSS */
+ .progress {
+ height: 100%;
+ background-color: #ff7096;
+ border-radius: 10px;
+ }
+
+ .password-input {
+ /* 비밀번호 입력창 */
+ width: 290px;
+ height: 46px;
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ }
+
+ .repassword-input {
+ /* 비밀번호 확인창 */
+ width: 290px;
+ height: 46px;
+ display: flex;
+ justify-content: center;
+ align-items: center;
+
+ }
+
+ .error-message, .error-message1 {
+ color: red;
+ font-size: 0.5em;
+ margin-left: 20px;
+ margin-top: 10px;
+ width: 320px;
+ height: 14px; /* 고정된 높이 설정 */
+ visibility: hidden; /* 기본적으로 메시지를 숨김 */
+ }
+
+ .error-message.visible, .error-message1.visible {
+ visibility: visible; /* 에러가 있을 때만 보이도록 */
+ }
+
+ .login4-input {
+ /* 닉네임 입력창 */
+ width: 295px;
+ height: 50px;
+ margin-bottom: 15px;
+ }
+
+ .check-button {
+ /* 중복 확인 버튼 */
+ width: 300px;
+ height: 50px;
+ background: #FF7898;
+ border-radius: 8px;
+ color: #fff;
+ font-size: 16px;
+ border: none;
+ border-radius: 5px;
+ cursor: pointer;
+ margin-bottom: 10px;
+ }
+
+ .gender-options {
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ gap: 22px;
+ margin-bottom: 10px;
+}
+
+.rectangle, .rectangle1 {
+ box-sizing: border-box;
+ width: 140px;
+ height: 140px; /* 높이 조정 */
+ background: #FFFFFF;
+ border: 2px solid #DADADA;
+ border-radius: 3px;
+ display: flex;
+ flex-direction: column;
+ justify-content: flex-start; /* 이미지와 텍스트를 위쪽 정렬 */
+ align-items: center;
+ padding-top: 10px; /* 이미지와 텍스트 사이에 패딩 추가 */
+}
+
+.rectangle.selected {
+ background-color: #EAF0FF;
+}
+
+.rectangle1.selected {
+ background-color: #FFF0EF;
+}
+
+ .boy-image {
+ width: 170px;
+ height: 240px;
+ margin-top: -63px;
+ background-size: contain;
+ background-position: center;
+ background-repeat: no-repeat;
+ }
+
+ .girl-image {
+ width: 80px;
+ height: 110px;
+ margin-top:-5px;
+ background-size: contain;
+ background-position: center;
+ background-repeat: no-repeat;
+ }
+
+.boyplace{
+ margin-top: -78px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 20px;
+ line-height: 24px;
+ display: flex;
+ justify-content: center;
+ text-align: center;
+ color: #3D3D3D;
+
+}
+ .girlplace {
+ margin-top: 0px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 20px;
+ margin-top: -5px;
+ line-height: 24px;
+ display: flex;
+ justify-content: center;
+ text-align: center;
+ color: #3D3D3D;
+ }
+
+ .login5-heading {
+ width: 300px;
+ height: 24px;
+ margin-top: 50px;
+ margin-bottom: 30px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 20px;
+ line-height: 24px;
+ display: flex;
+ align-items: center;
+ color: #3D3D3D;
+ }
+
+ /* 단과대 선택 */
+ .input {
+ width: 100%;
+ padding: 10px;
+ font-size: 16px;
+ margin-top: 5px;
+ border: 1px solid #ccc;
+ border-radius: 5px;
+ }
+
+ .student-id {
+ /* 학번 입력창 */
+ width: 290px;
+ height: 46px;
+ margin-bottom: 100px;
+ display: flex;
+ justify-content: center;
+ align-items: center;
+
+ }
+
+ .select-container1 {
+ /* 단과대 선택창 */
+ width: 282px;
+ height: 50px;
+ margin-bottom: 20px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 400;
+ font-size: 16px;
+ line-height: 18px;
+ }
+
+ .select-container2 {
+ /* 학과 선택창 */
+ width: 282px;
+ height: 50px;
+ height: 20px;
+ }
+
+ .select-department {
+ width: 100%;
+ padding: 10px;
+ font-size: 16px;
+ margin-top: 5px;
+ border: 1px solid #ccc;
+ border-radius: 5px;
+ }
+
+ .year-month-day-container {
+ display: flex;
+ gap: 10px;
+ margin-bottom: 410px;
+ }
+
+ .year-input {
+ width: 85px;
+ height: 46px;
+ }
+
+ .month-input {
+ width: 85px;
+ height: 46px;
+ }
+
+ .day-input {
+ width: 85px;
+ height: 46px;
+ }
+}
+
diff --git a/src/page/Login/Login.jsx b/src/page/Login/Login.jsx
new file mode 100644
index 0000000..3945e93
--- /dev/null
+++ b/src/page/Login/Login.jsx
@@ -0,0 +1,91 @@
+import React, { useState } from "react";
+import { useNavigate } from 'react-router-dom';
+import { IoChevronBack } from "react-icons/io5";
+import { postLogin } from "../../api/postLogin";
+import './Login.css';
+
+// 로그인
+const Login = () => {
+ const [password, setPassword] = useState("");
+ const [error, setError] = useState("");
+ const navigate = useNavigate();
+
+
+ const handleNext = async () => {
+ if (password.trim() === "") {
+ setError("비밀번호를 입력해주세요.");
+ return;
+ }
+
+ const storedEmail = localStorage.getItem('userEmail');
+ const logindata = {
+ schoolEmail: storedEmail,
+ password: password
+ }
+ try {
+ const loginResponse = await postLogin(logindata);
+ console.log("로그인 응답:", loginResponse); // 전체 응답 출력
+ // 응답에서 액세스 토큰 추출
+ // 이곳에서 loginResponse.headers를 제대로 접근할 수 있는지 확인
+ const accessToken = loginResponse.headers?.authorization; // Optional chaining 추가
+ if (!accessToken) {
+ throw new Error("Access token not found in response headers");
+ }
+
+ const token = accessToken.split(' ')[1]; // 'Bearer ' 제거
+
+ localStorage.setItem('accessToken', token);
+ navigate('/ChatStartPage');
+ } catch (error) {
+ console.error('Error posting email data:', error);
+ }
+
+ };
+
+ const handleBack = () => {
+ navigate('/'); // 이전 페이지로 이동
+ };
+
+ return (
+
+
+
+
+
+
+
비밀번호를 입력해주세요
+
가입하실 때 설정한 비밀번호를 입력하세요
+
+
{
+ setPassword(e.target.value);
+ setError(""); // 에러 메시지 초기화
+ }}
+ />
+ {error && (
+
{error}
// 에러 메시지 출력
+ )}
+
+
+
+
+
+
+ );
+};
+
+export default Login;
\ No newline at end of file
diff --git a/src/page/Login/Login1.jsx b/src/page/Login/Login1.jsx
new file mode 100644
index 0000000..9764324
--- /dev/null
+++ b/src/page/Login/Login1.jsx
@@ -0,0 +1,80 @@
+import React, { useContext, useState } from "react";
+import { useNavigate } from 'react-router-dom';
+import { IoChevronBack } from "react-icons/io5";
+import { postMail } from "../../api/postMail";
+import './Login.css';
+import { UserContext } from "../../context/UserContext";
+
+// 메일 인증 / 작성
+const Login1 = () => {
+ const { User, updateUser } = useContext(UserContext);
+ const [email, setEmail] = useState("");
+ const navigate = useNavigate();
+
+ const handleInputChange = (e) => {
+ setEmail(e.target.value);
+ };
+
+ const handleButtonClick = async (e) => {
+ e.preventDefault();
+ if (email) {
+ console.log(`Verification code sent to: ${email}`);
+ updateUser({ schoolEmail: email });
+ console.log("context updated");
+
+ // 이메일을 로컬 스토리지에 저장
+ localStorage.setItem('userEmail', email);
+ console.log("Email saved to localStorage");
+
+ } else {
+ console.log("Please enter a valid email");
+ return; // 유효하지 않은 이메일일 경우 함수 종료
+ }
+
+ try {
+ await postMail(email);
+ console.log('email data posted successfully');
+ navigate('/login2');
+ } catch (error) {
+ console.error('Error posting email data:', error);
+ }
+ };
+
+ const handleBack = () => {
+ navigate('/'); // 이전 페이지로 이동
+ };
+
+ return (
+
+
+
+
+
+
학교 이메일을 입력해 주세요
+
안전한 인피 활동을 위해 학교 인증이 필요해요
+
+
+
+
+
+
+
+ );
+};
+
+export default Login1;
diff --git a/src/page/Login/Login2.jsx b/src/page/Login/Login2.jsx
new file mode 100644
index 0000000..56d7e42
--- /dev/null
+++ b/src/page/Login/Login2.jsx
@@ -0,0 +1,119 @@
+import React, { useState, useEffect, useContext } from "react";
+import { useNavigate } from "react-router-dom";
+import { IoChevronBack } from "react-icons/io5";
+import { postMailCheck } from "../../api/postMailCheck";
+import { postMail } from "../../api/postMail";
+import { UserContext } from "../../context/UserContext";
+import './Login.css';
+
+// 메일 인증 / 인증번호 입력
+const Login2 = () => {
+ const { User, updateUser } = useContext(UserContext);
+ const [code, setCode] = useState(new Array(6).fill("")); // 6자리 코드 입력 관리
+ const navigate = useNavigate();
+ const [email, setEmail] = useState(""); // 세션 스토리지에서 가져올 이메일 상태
+
+ useEffect(() => {
+ // 로컬 스토리지에서 이메일 값을 불러옵니다.
+ const storedEmail = localStorage.getItem('userEmail');
+ if (storedEmail) {
+ setEmail(storedEmail);
+ if (User.email !== storedEmail) { // 이메일이 다를 경우에만 업데이트
+ updateUser({ email: storedEmail }); // Context에 이메일 업데이트
+ }
+ }
+ }, [User.email, updateUser]); // User.email을 의존성으로 추가
+
+ const handleInputChange = (element, index) => {
+ let newCode = [...code];
+ const inputValue = element.value;
+
+ // 사용자가 입력을 했을 때
+ newCode[index] = inputValue;
+ setCode(newCode);
+
+ // 입력 후 다음 필드로 이동
+ if (inputValue && element.nextSibling) {
+ element.nextSibling.focus();
+ }
+ };
+
+ const handleKeyDown = (event, index) => {
+ // 백스페이스 키가 눌렸을 때
+ if (event.key === 'Backspace' && code[index] === "") {
+ if (event.target.previousSibling) {
+ event.target.previousSibling.focus(); // 이전 입력 필드로 포커스 이동
+ }
+ }
+ };
+
+
+ const handleResend = async () => {
+ try {
+ await postMail(email);
+ console.log('Email data posted successfully');
+ navigate('/login2');
+ } catch (error) {
+ console.error('Error posting email data:', error);
+ }
+ };
+
+ const handleSubmit = async () => {
+ const enteredCode = code.join("");
+ console.log(`Entered code: ${enteredCode}`);
+
+ try {
+ await postMailCheck(email, enteredCode);
+ console.log('Key data posted successfully');
+ navigate("/login3");
+ } catch (error) {
+ console.error('Error posting key data:', error);
+ }
+ };
+
+ const handleBack = () => {
+ navigate('/login1'); // 이전 페이지로 이동
+ };
+
+ return (
+
+
+
+
+
+
인증 메일이 보내졌습니다
+
인증 번호 6자리를 입력해주세요
+
+
+ {code.map((digit, index) => (
+ handleInputChange(e.target, index)}
+ onKeyDown={(e) => handleKeyDown(e, index)} // onKeyDown 이벤트 추가
+ onFocus={(e) => e.target.select()}
+ />
+ ))}
+
+
+ 메일을 못받으셨나요?
+ 다시 받기
+
+
+
+
+
+
+ );
+};
+
+export default Login2;
diff --git a/src/page/Login/Login3.jsx b/src/page/Login/Login3.jsx
new file mode 100644
index 0000000..02d9cbb
--- /dev/null
+++ b/src/page/Login/Login3.jsx
@@ -0,0 +1,127 @@
+import React, { useState, useContext } from "react";
+import { useNavigate } from "react-router-dom";
+import { IoChevronBack } from "react-icons/io5";
+import { UserContext } from "../../context/UserContext";
+import './Login.css';
+
+// 비밀번호 설정 페이지
+const Login3 = () => {
+ const { User, updateUser } = useContext(UserContext);
+ const [password, setPassword] = useState("");
+ const [confirmPassword, setConfirmPassword] = useState("");
+ const [passwordError, setPasswordError] = useState("");
+ const [confirmPasswordError, setConfirmPasswordError] = useState("");
+
+ const navigate = useNavigate();
+
+ // 비밀번호 유효성 검사 함수
+ const validatePassword = (value) => {
+ const passwordRegex = /^(?=.*[A-Za-z])(?=.*\d)(?=.*[!@#$%^&*])[A-Za-z\d!@#$%^&*]{8,}$/;
+ return passwordRegex.test(value);
+ };
+
+ // 비밀번호 입력 처리
+ const handlePasswordChange = (e) => {
+ const newPassword = e.target.value;
+ setPassword(newPassword);
+
+ if (!validatePassword(newPassword)) {
+ setPasswordError("비밀번호는 영문, 숫자, 특수문자를 포함한 8자 이상이어야 합니다");
+ } else {
+ setPasswordError("");
+ }
+
+ if (newPassword !== confirmPassword && confirmPassword) {
+ setConfirmPasswordError("비밀번호가 일치하지 않습니다");
+ } else {
+ setConfirmPasswordError("");
+ }
+ };
+
+ // 비밀번호 확인 입력 처리
+ const handleConfirmPasswordChange = (e) => {
+ const newConfirmPassword = e.target.value;
+ setConfirmPassword(newConfirmPassword);
+
+ if (newConfirmPassword !== password) {
+ setConfirmPasswordError("비밀번호가 일치하지 않습니다");
+ } else {
+ setConfirmPasswordError("");
+ }
+ };
+
+ // 뒤로 가기 처리
+ const handleBack = () => {
+ navigate('/login2');
+ };
+
+ // 제출 처리
+ const handleSubmit = () => {
+ if (!passwordError && !confirmPasswordError && password && confirmPassword) {
+ updateUser({password: password});
+ console.log("비밀번호 설정 완료:", password, User);
+ navigate("/login4");
+ } else {
+ console.log("비밀번호 설정 오류");
+ }
+ };
+ return (
+
+
+
+
+
+
비밀번호를 설정해주세요
+
영문, 숫자, 특수문자를 조합하여 8자 이상으로 설정해주세요
+
+
+
+ {/* 비밀번호 유효성 검사 에러 메시지 */}
+
+ {passwordError}
+
+
+
+
+
+
+ {/* 비밀번호 확인 에러 메시지 */}
+
+ {confirmPasswordError}
+
+
+
+
+
+
+
+
+ );
+};
+
+export default Login3;
diff --git a/src/page/Login/Login4.jsx b/src/page/Login/Login4.jsx
new file mode 100644
index 0000000..54ed62f
--- /dev/null
+++ b/src/page/Login/Login4.jsx
@@ -0,0 +1,100 @@
+import React, { useState, useContext } from "react";
+import { useNavigate } from "react-router-dom";
+import './Login.css';
+import { IoChevronBack } from "react-icons/io5";
+import { UserContext } from "../../context/UserContext";
+import { getIsNickExist } from "../../api/getIsNickExist";
+
+// 닉네임 설정
+const Login4 = () => {
+ const { User, updateUser } = useContext(UserContext);
+ const [nickname, setNickname] = useState("");
+ const [isNicknameChecked, setIsNicknameChecked] = useState(false); // 중복 확인 완료 상태
+ const navigate = useNavigate();
+
+ const handleCheckNickname = async () => {
+ if (nickname.length >= 2 && nickname.length <= 20) {
+ try {
+ const response = await getIsNickExist(nickname);
+
+ if (response.data === false) {
+ console.log('닉네임 중복 확인 완료');
+ setIsNicknameChecked(true); // 중복 확인 완료
+ alert("닉네임 확인 완료");
+ } else {
+ console.error('닉네임 중복 확인 실패:', response);
+ setIsNicknameChecked(false);
+ alert("닉네임이 이미 존재합니다.");
+ }
+
+ } catch (error) {
+ console.error('Error posting nickname data:', error);
+ setIsNicknameChecked(false); // 중복 확인 실패 시 버튼 비활성화 유지
+ }
+ } else {
+ setIsNicknameChecked(false); // 중복 확인 실패 시 버튼 비활성화 유지
+ alert("닉네임은 2자 이상, 20자 이하로 입력해주세요.");
+ }
+ };
+
+ const handleNext = () => {
+ if (nickname.length >= 2 && nickname.length <= 20 && isNicknameChecked) {
+ updateUser({nickname:nickname});
+ console.log(User);
+ navigate("/login5", { state: { nickname } });
+ } else {
+ alert("닉네임을 다시 확인해주세요.");
+ }
+ };
+
+ const handleBack = () => {
+ navigate('/login3'); // 이전 페이지로 이동
+ };
+
+ return (
+
+
+
+
+
+
+
닉네임을 입력해주세요
+
한글로만 2자 이상, 20자 이하로 가능해요
+
+
{
+ setNickname(e.target.value);
+ setIsNicknameChecked(false); // 닉네임이 변경될 때마다 중복 확인 초기화
+ }}
+ />
+
+
+
+
+
+
+
+
+ );
+};
+
+export default Login4;
\ No newline at end of file
diff --git a/src/page/Login/Login5.jsx b/src/page/Login/Login5.jsx
new file mode 100644
index 0000000..7cfbfe7
--- /dev/null
+++ b/src/page/Login/Login5.jsx
@@ -0,0 +1,81 @@
+import React, { useState, useContext } from 'react';
+import { useNavigate } from 'react-router-dom';
+import { IoChevronBack } from "react-icons/io5";
+import './Login.css';
+import boyImage from '../../asset/boy.png';
+import girlImage from '../../asset/girl.png';
+import { UserContext } from "../../context/UserContext";
+
+// 성별 입력
+const Login5 = () => {
+ const { User, updateUser } = useContext(UserContext);
+ const [selectedGender, setSelectedGender] = useState(null);
+ const navigate = useNavigate();
+
+ const handleGenderSelect = (gender) => {
+ setSelectedGender(gender);
+ };
+
+ const handleSubmit = () => {
+ if (selectedGender) {
+ console.log(`선택된 성별: ${selectedGender}`);
+ updateUser({gender:selectedGender});
+ console.log(User);
+ navigate('/login6', { state: { gender: selectedGender } });
+ }
+ };
+
+ const handleBack = () => {
+ navigate('/login4'); // 이전 페이지로 이동
+ };
+
+ return (
+
+
+
+
+
+
춘식이님의 성별을 알려주세요
+
+
handleGenderSelect('남성')}
+ >
+
+

+
남성
+
+
+
handleGenderSelect('여성')}
+ >
+
+

+
여성
+
+
+
+
+
+
+
+
+ );
+};
+
+export default Login5;
\ No newline at end of file
diff --git a/src/page/Login/Login6.jsx b/src/page/Login/Login6.jsx
new file mode 100644
index 0000000..6f8c3e4
--- /dev/null
+++ b/src/page/Login/Login6.jsx
@@ -0,0 +1,127 @@
+import React, { useState, useContext } from "react";
+import { useNavigate } from "react-router-dom";
+import { IoChevronBack } from "react-icons/io5";
+import { UserContext } from "../../context/UserContext";
+import './Login.css';
+// 학번, 학과 입력
+const Login6 = () => {
+ const { User, updateUser } = useContext(UserContext);
+ const [studentNumber, setStudentNumber] = useState("");
+ const [division, setDivision] = useState("");
+ const [department, setDepartment] = useState("");
+ const navigate = useNavigate();
+
+ // 단과대와 학과 정보를 정의
+ const divisionsAndDepartments = {
+ "인문대학": ["국어국문학과", "영어영문학과", "독어독문학과", "불어불문학과", "일어일문학과", "중어중문학과"],
+ "자연과학대학": ["수학과", "물리학과", "화학과", "패션산업학과", "해양학과"],
+ "사회과학대학": ["사회복지학과", "신문방송학과", "문헌정보학과", "창의인재개발학과"],
+ "글로벌정경대학" : ["행정학과", "정치외교학과", "경제학과", "무역학부", "소비자학과"],
+ "공과대학": ["기계공학과", "메카트로닉스공학과", "전기공학과", "전자공학과", "산업경영학과", "신소재공학과", "안전공학과", "에너지화학공학과"],
+ "정보기술대학" : ["컴퓨터공학부", "정보통신공학과","임베디드시스템공학과"],
+ "경영대학": ["경영학부", "세무회계학과"],
+ "예술체육대학": ["조형예술학부", "디자인학부", "공연예술학과", "체육학부", "운동건강학부"],
+ "사범대학": ["국어교육과", "영어교육과", "일어교육과", "수학교육과", "체육교육과", "유아교육과", "역사교육과", "윤리교육과"],
+ "도시과학대학": ["도시행정학과", "건설환경공학과", "환경공학과", "도시공학과", "도시건축학과"],
+ "생명과학기술": ["생명공학부", "생명공학부 생명공학전공", "생명공학부 나노바이오전공", "도시공학과"],
+ "동북아국제통상학부": ["동북아국제통상학부", "한국통상전공"],
+ "법학부":["법학부"]
+ };
+
+ const handleSubmit = (e) => {
+ e.preventDefault();
+ if (studentNumber && division && department) {
+ updateUser({
+ college:division,
+ studentId: studentNumber,
+ department:department
+ });
+ console.log('context updated:', User);
+ navigate("/login7");
+ } else {
+ alert("모든 항목을 입력해 주세요.");
+ }
+ };
+
+ const handleBack = () => {
+ navigate('/login5'); // 이전 페이지로 이동
+ };
+
+ return (
+
+
+
+
+
+
춘식이님에 대해 알려주세요
+
학번 9자리를 입력해주세요
+
+
+
+
+
+
+
+
+
+ );
+};
+
+export default Login6;
\ No newline at end of file
diff --git a/src/page/Login/Login7.jsx b/src/page/Login/Login7.jsx
new file mode 100644
index 0000000..1e525b9
--- /dev/null
+++ b/src/page/Login/Login7.jsx
@@ -0,0 +1,146 @@
+import React, { useState, useContext, useEffect } from "react";
+import { useNavigate } from "react-router-dom"; // useNavigate 추가
+import { IoChevronBack } from "react-icons/io5";
+import { UserContext } from "../../context/UserContext";
+import { postUser } from "../../api/postUser";
+import './Login.css';
+
+// 생년월일 입력
+const Login7 = () => {
+ const { User, updateUser } = useContext(UserContext);
+ const [year, setYear] = useState("");
+ const [month, setMonth] = useState("");
+ const [day, setDay] = useState("");
+ const [profile,setProfile]=useState("");
+ const navigate = useNavigate(); // navigate 초기화
+ const [birthdate, setBirthdate]=useState("");
+
+ useEffect(() => {
+ if (setYear|setDay|setMonth) {
+
+ console.log("Birthdate updated:", birthdate);
+
+ }
+ }, [setYear,setDay,setMonth]);
+
+ const isLeapYear = (year) => {
+ return (year % 4 === 0 && year % 100 !== 0) || (year % 400 === 0);
+ };
+
+ const validateBirthdate = (year, month, day) => {
+ if (year.length !== 4 || month.length !== 2 || day.length !== 2) {
+ alert("생년월일을 정확히 입력해 주세요.");
+ return false;
+ }
+
+
+ // 형식 체크
+ if (!/^\d{4}$/.test(year) || !/^\d{2}$/.test(month) || !/^\d{2}$/.test(day)) {
+ alert("생년월일은 숫자만 포함해야 합니다.");
+ return false;
+ }
+
+ const yearNum = parseInt(year, 10);
+ const monthNum = parseInt(month, 10);
+ const dayNum = parseInt(day, 10);
+
+ // 월 범위 체크
+ if (monthNum < 1 || monthNum > 12) {
+ alert("월은 1에서 12 사이의 숫자여야 합니다.");
+ return false;
+ }
+
+ // 각 월에 따라 최대 일수 체크
+ const daysInMonth = [31, (isLeapYear(yearNum) ? 29 : 28), 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];
+
+ if (dayNum < 1 || dayNum > daysInMonth[monthNum - 1]) {
+ alert("입력한 날짜는 유효하지 않습니다.");
+ return false;
+ }
+ const birthdate = `${year}-${month}-${day}`;
+ setBirthdate(birthdate);
+ console.log("생일:", birthdate);
+ return true;
+ };
+ const handleSubmit = async(e) => {
+
+ e.preventDefault();
+
+ if (!validateBirthdate(year, month, day)) {
+ return;
+ }
+
+
+ try {
+ const randomImageIndex = Math.floor(Math.random() * 6);
+ await postUser({...User,profile:`${randomImageIndex}`, birthday:birthdate});
+ console.log('user data posted successfully');
+ navigate('/login');
+ } catch (error) {
+ console.error('Error posting user data:', error);
+ }
+
+
+ };
+
+ const handleBack = () => {
+ navigate('/login6'); // 이전 페이지로 이동
+ };
+
+ return (
+
+
+
+
+
+
+
춘식이님의 생일을 알려주세요
+
+
+
+
+
+
+
+
+ );
+};
+
+export default Login7;
diff --git a/src/page/Main/Main.css b/src/page/Main/Main.css
index e69de29..d86f5b5 100644
--- a/src/page/Main/Main.css
+++ b/src/page/Main/Main.css
@@ -0,0 +1,80 @@
+.MainPage {
+ height: 812px;
+ width: 375px;
+ margin: 0 auto;
+
+ .img-title {
+ /* 인피 로고 */
+ width: 95px;
+ height: 45px;
+ background: url('../../asset/logo.png');
+ background-size: contain;
+ margin-top: 100px; /* 상단 여백 */
+ margin-bottom: 20px;
+ align-self: flex-start;
+ margin-right: 170px;
+ }
+
+ .img-container{
+ display: flex;
+ justify-content: center
+ }
+
+ .img-bg {
+ /* 메인 이미지 */
+ width: 290px;
+ height: 211px;
+ background: url('../../asset/main.png');
+ background-size: contain;
+ margin-top: 10px;
+ margin-bottom: 50px;
+ }
+
+ .img-subtitle {
+ /* 인천대에서 피어나다 */
+ width: 184.2px;
+ height: 18.35px;
+ background: url('../../asset/sublogo.png');
+
+ background-size: contain;
+ margin-top: 10px;
+
+ align-self: flex-start;
+ margin-left: 110px;
+ }
+
+ .container {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ font-family: 'Pretendard', sans-serif;
+ height: 100%;
+ }
+
+ .botton-container{
+ margin-top:auto;
+ }
+
+ .bottom-Button {
+ /* 하단 버튼 */
+ width: 300px;
+ height: 50px;
+
+ color: #F7F7F7;
+ background: #FF7898;
+ border-radius: 8px;
+ border-color: rgb(255, 255, 255);
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 700;
+ font-size: 18px;
+
+ margin-bottom: 40px;
+ margin-top: auto;
+
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ }
+}
\ No newline at end of file
diff --git a/src/page/Main/Main.jsx b/src/page/Main/Main.jsx
index c647dac..1a96bcb 100644
--- a/src/page/Main/Main.jsx
+++ b/src/page/Main/Main.jsx
@@ -1,11 +1,48 @@
import React from "react";
+import './Main.css'
+import { useNavigate } from 'react-router-dom';
+import mainImage from '../../asset/main.png';
+import mainLogo from '../../asset/logo.png';
+import subLogo from '../../asset/sublogo.png';
-function Main(){
- return(
-
- 메인
-
- )
-}
+// 시작화면
+function Main() {
+ const navigate = useNavigate(); // useNavigate 훅 사용
+
+ //로컬스토리지 확인후 로그인 페이지 혹은 회원가입 페이지로 이동
+ const handleButtonClick = () => {
+ if (localStorage.getItem('userEmail')) {
+ navigate('../Login'); // '/next' 경로로 이동
+ } else {
+ navigate('../Login1'); // '/next' 경로로 이동
+ //navigate('../SignUp'); // '/next' 경로로 이동
+ }
+ };
+
+
+ return (
+
+
+
+

+
-export default Main;
\ No newline at end of file
+
+

+
+
+
+

+
+
+
+
+
+
+
+ )
+}
+
+ export default Main;
\ No newline at end of file
diff --git a/src/page/Mbti/Mbti.css b/src/page/Mbti/Mbti.css
index cfe42e6..a11b70c 100644
--- a/src/page/Mbti/Mbti.css
+++ b/src/page/Mbti/Mbti.css
@@ -6,6 +6,7 @@
background-color: #FFFFFF ;
width: 375px;
height: 100vh;
+
header {
/* 상단 헤더 */
@@ -14,7 +15,7 @@
flex-direction: row;
align-items: center;
justify-content: flex-start;
- margin-top: 62px;
+ margin-top: 15%;
}
.back-button {
@@ -57,7 +58,7 @@
background: #FF7898;
border-radius: 5px;
position: absolute;
- bottom: 83px;
+ bottom: 10%;
font-family: 'Pretendard';
font-style: normal;
font-weight: 700;
@@ -70,8 +71,8 @@
margin: 16px;
display: flex;
position: absolute;
- bottom: 240px;
- margin-top: 140px;
+ bottom: 28%;
+
flex-direction: column;
align-items: center;
@@ -140,7 +141,7 @@
font-family: 'Pretendard';
font-style: normal;
font-weight: 600;
- font-size: 20px;
+ font-size: 19px;
line-height: 20px;
/* identical to box height, or 88% */
display: flex;
@@ -148,8 +149,94 @@
color: #3D3D3D;
- margin-bottom: 130px;
+ margin-bottom: 100px;
+
+
+ }
+ #mbti_main{
+ justify-content: center;
+ }
+ #mbti_title{
+
+ background-image: url('../../asset/횃불이\ 테스트.png');
+ background-repeat: no-repeat;
+ width: 280px;
+ height: 50px;
+ margin-bottom: 30px;
+ margin-top:100px ;
+ }
+ #subTitle{
+ /* 당신의 횃불이 유형은? */
+
+ width: 176px;
+ height: 14px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 20px;
+ line-height: 14px;
+ color: #777777;
+ margin-bottom: 45px;
+ }
+ #mbtiMain_img{
+
+ width: 80%;
+ height: 300px;
+ background: #D9D9D9;
+ place-self: center center;
+
}
-}
\ No newline at end of file
+
+
+
+}
+.modal {
+ position: absolute;
+ top: 50%;
+ left: 50%;
+ transform: translate(-50%, -50%);
+ background: white;
+ padding: 20px;
+ border: 1px solid #ccc;
+ border-radius: 4px;
+ outline: none;
+ max-width: 375px;
+ width: 300px;
+ z-index: 1000; /* 모달이 다른 요소들 위에 표시되도록 */
+ text-align: center; /* 텍스트 가운데 정렬 */
+ background: #FFFFFF;
+ border-radius: 10px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 18px;
+ line-height: 28px;
+ letter-spacing: -1px;
+ color: #000000;
+}
+
+.overlay {
+ position: fixed;
+ top: 0;
+ left: 0;
+ right: 0;
+ bottom: 0;
+ background-color: rgba(0, 0, 0, 0.75);
+ z-index: 999; /* 모달 오버레이가 다른 요소들 위에 표시되도록 */
+}
+
+#img {
+ background-image: url('../../asset/loading.gif');
+ background-size: contain;
+ background-repeat: no-repeat;
+ background-position: center; /* 이미지를 수평, 수직 중앙 정렬 */
+ max-width: 100%;
+ width: 30%;
+ height: 200px;
+ margin-bottom: 20px; /* 이미지 아래 여백 추가 */
+ display: block; /* img를 블록 요소로 변경 */
+ margin: 0 auto; /* 수평 가운데 정렬 */
+}
diff --git a/src/page/Mbti/Mbti.jsx b/src/page/Mbti/Mbti.jsx
index c46b47d..61820b6 100644
--- a/src/page/Mbti/Mbti.jsx
+++ b/src/page/Mbti/Mbti.jsx
@@ -1,11 +1,48 @@
import React from 'react';
+import { useNavigate } from "react-router-dom";
+import './Mbti.css';
function Mbti (){
+
+ const navigate = useNavigate();
+
+
+ const handleNavigation = (destination) => {
+ switch (destination) {
+ case 'play':
+ window.location.reload(); // 페이지 새로고침 (필요에 따라 이 부분을 변경)
+ break;
+ case 'talk':
+ navigate('/ChatStartPage');
+ break;
+ case 'my':
+ navigate('/myPage');
+ break;
+ default:
+ break;
+ }
+ };
+ const handleNext = () => {
+ navigate('/mbti1')
+ }
return (
-
-
+
+
+
당신의 횃불이 유형은?
+
+
+
+
+
handleNavigation('play')}>
+
handleNavigation('talk')}>
+
handleNavigation('my')}>
+
+
);
};
diff --git a/src/page/Mbti/Mbti1.jsx b/src/page/Mbti/Mbti1.jsx
index cc2248a..6ab37c5 100644
--- a/src/page/Mbti/Mbti1.jsx
+++ b/src/page/Mbti/Mbti1.jsx
@@ -11,7 +11,6 @@ function Mbti1(){
const [isa2Checked,setIsa2Checked]=useState(false);
const [selectedAnswer, setSelectedAnswer] = useState(null); // 선택된 답변 상태
const selectedValue1 = Mbti.selectList["1"];
- const eVal = Mbti.e;
const navigate = useNavigate();
useEffect(() =>{
if(selectedValue1){
@@ -43,11 +42,11 @@ function Mbti1(){
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ e: eVal + 1, selectList: { ...Mbti.selectList, "1": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "1": true } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ e: eVal, selectList: { ...Mbti.selectList, "1": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "1": false } });
}
navigate("/mbti2");
};
@@ -65,7 +64,7 @@ function Mbti1(){
{
if(selectedValue1){
@@ -42,11 +42,11 @@ function Mbti10(){
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ p: eVal + 1, selectList: { ...Mbti.selectList, "10": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "10": true } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ p: eVal, selectList: { ...Mbti.selectList, "10": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "10": false } });
}
navigate("/mbti11");
};
@@ -62,8 +62,8 @@ function Mbti10(){
{
if(selectedValue1){
@@ -32,21 +31,22 @@ function Mbti11(){
};
const handleBack = () => {
if (selectedAnswer === 1) {
- updateMbti({ selectList: { ...Mbti.selectList, "11": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "11": false } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ selectList: { ...Mbti.selectList, "11": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "11": true } });
}
navigate("/mbti10"); // 이전 페이지로 이동
};
const handleNext = () => {
+
if (selectedAnswer === 1) {
- updateMbti({ f: eVal + 1, selectList: { ...Mbti.selectList, "11": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "11": false } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ f: eVal, selectList: { ...Mbti.selectList, "11": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "11": true } });
}
navigate("/mbti12");
};
@@ -62,7 +62,7 @@ function Mbti11(){
{
- console.log(Mbti);
- if (selectedValue1) {
- setIsa1Checked(true);
- setIsa2Checked(false);
- } else {
- setIsa1Checked(false);
- setIsa2Checked(true);
- }
- }, [selectedValue1]);
+ const storedToken = localStorage.getItem('accessToken');
+ if (storedToken) {
+ setToken(storedToken);
+ }
+ }, []);
- const mbtiHandler = () => {
- console.log("mbtiHandler called");
+ useEffect(() => {
+ const fetchMypageData = async () => {
+ if (!token) return;
+
+ try {
+ const mypageData = await getUser(token);
+ setData(mypageData);
+ } catch (error) {
+ console.error('Error fetching mypage data:', error);
+ }
+ };
- let mbti = '';
- if (eVal >= 2) mbti += 'E';
- else mbti += 'I';
+ fetchMypageData();
+ }, [token]);
- if (sVal >= 2) mbti += 'S';
- else mbti += 'N';
+ const eVal = () => {
+ return ["1", "2", "5"].reduce((acc, key) => acc + (Mbti.selectList[key] ? 1 : 0), 0);
+ };
+
+ const sVal = () => {
+ return ["3", "8", "12"].reduce((acc, key) => acc + (Mbti.selectList[key] ? 1 : 0), 0);
+ };
+
+ const fVal = () => {
+ return ["6", "7", "11"].reduce((acc, key) => acc + (Mbti.selectList[key] ? 1 : 0), 0);
+ };
+
+ const pVal = () => {
+ return ["4", "9", "10"].reduce((acc, key) => acc + (Mbti.selectList[key] ? 1 : 0), 0);
+ };
- if (fVal >= 2) mbti += 'F';
- else mbti += 'T';
+ const navigate = useNavigate();
- if (pVal >= 2) mbti += 'P';
- else mbti += 'J';
+ useEffect(() => {
+ setIsa1Checked(selectedValue1);
+ setIsa2Checked(!selectedValue1);
+ }, [selectedValue1]);
- setMbtiChecked(mbti);
- console.log('Calculated MBTI:',mbti); // 디버깅 로그
+ const mbtiHandler = () => {
+ let mbti = '';
+ mbti += eVal() >= 2 ? 'E' : 'I';
+ mbti += sVal() >= 2 ? 'S' : 'N';
+ mbti += fVal() >= 2 ? 'F' : 'T';
+ mbti += pVal() >= 2 ? 'P' : 'J';
+ return mbti;
};
const handleAnswerSelected = (answer) => {
setSelectedAnswer(answer);
+ updateMbti({ selectList: { ...Mbti.selectList, "12": answer === 1 } });
};
- const handleBack = () => {
- if (selectedAnswer === 1) {
- updateMbti({ selectList: { ...Mbti.selectList, "12": true } });
- } else if (selectedAnswer === 2) {
- updateMbti({ selectList: { ...Mbti.selectList, "12": false } });
- }
- navigate("/mbti11");
+ const openModal = () => {
+ setModalIsOpen(true);
+ setTimeout(closeModal, 3000);
};
- const handleNext = () => {
- // 선택한 답변에 따라 MBTI 업데이트
- if (selectedAnswer === 1) {
- updateMbti({ s: sVal + 1, selectList: { ...Mbti.selectList, "12": true } });
- } else if (selectedAnswer === 2) {
- updateMbti({ s: sVal, selectList: { ...Mbti.selectList, "12": false } });
- }
-
- // MBTI 타입 계산
- mbtiHandler();
-
- // mbtiChecked가 업데이트된 후 라우팅
- if (mbtiChecked) {
- switch (mbtiChecked) {
- case 'ESTJ':
- navigate("/estj_result");
- break;
- case 'ISTJ':
- navigate("/istj_result");
- break;
- case 'ENTP':
- navigate("/entp_result");
- break;
- case 'INTP':
- navigate("/intp_result");
- break;
- case 'ESFJ':
- navigate("/esfj_result");
- break;
- case 'ISFJ':
- navigate("/isfj_result");
- break;
- case 'ENFJ':
- navigate("/enfj_result");
- break;
- case 'INFJ':
- navigate("/infj_result");
- break;
- case 'ESTP':
- navigate("/estp_result");
- break;
- case 'ISTP':
- navigate("/istp_result");
- break;
- case 'ENTJ':
- navigate("/entj_result");
- break;
- case 'INTJ':
- navigate("/intj_result");
- break;
- case 'ESFP':
- navigate("/esfp_result");
- break;
- case 'ISFP':
- navigate("/isfp_result");
- break;
- case 'ENFP':
- navigate("/enfp_result");
- break;
- case 'INFP':
- navigate("/infp_result");
- break;
- default:
- navigate("/default_result"); // 일치하는 값이 없을 경우
- break;
- }
- }
+ const closeModal = () => {
+ setModalIsOpen(false);
};
useEffect(() => {
- console.log('mbti:', mbtiChecked);
- }, [mbtiChecked]); // mbtiChecked가 변경될 때마다 콘솔 로그
+ const computeAndNavigate = async () => {
+ if (mbtiChecked) {
+ const computedMbti = mbtiHandler();
+ setMbtiChecked(computedMbti); // Update MBTI state
+
+ // Navigate based on computed MBTI
+ switch (computedMbti) {
+ case 'ESTJ': navigate("/estj_result"); break;
+ case 'ISTJ': navigate("/istj_result"); break;
+ case 'ENTP': navigate("/entp_result"); break;
+ case 'INTP': navigate("/intp_result"); break;
+ case 'ESFJ': navigate("/esfj_result"); break;
+ case 'ISFJ': navigate("/isfj_result"); break;
+ case 'ENFJ': navigate("/enfj_result"); break;
+ case 'INFJ': navigate("/infj_result"); break;
+ case 'ESTP': navigate("/estp_result"); break;
+ case 'ISTP': navigate("/istp_result"); break;
+ case 'ENTJ': navigate("/entj_result"); break;
+ case 'INTJ': navigate("/intj_result"); break;
+ case 'ESFP': navigate("/esfp_result"); break;
+ case 'ISFP': navigate("/isfp_result"); break;
+ case 'ENFP': navigate("/enfp_result"); break;
+ case 'INFP': navigate("/infp_result"); break;
+ default: navigate("/default_result");
+ }
+
+ // Update user data with MBTI
+ try {
+ await putUser(token, { ...data, mbti: computedMbti });
+ } catch (error) {
+ console.error('Error updating user data:', error);
+ }
+ }
+ };
+
+ computeAndNavigate();
+ }, [mbtiChecked, navigate, token, data]);
+
+ const handleNext = () => {
+ openModal();
+ setMbtiChecked(mbtiHandler()); // Calculate MBTI when moving to the next question
+ };
return (
다음
+
+
+
+ 횃불이 유형을 분석하고 있어요
+ 잠시만 기다려주세요
+
);
}
diff --git a/src/page/Mbti/Mbti2.jsx b/src/page/Mbti/Mbti2.jsx
index e424362..a01e2e3 100644
--- a/src/page/Mbti/Mbti2.jsx
+++ b/src/page/Mbti/Mbti2.jsx
@@ -11,7 +11,7 @@ function Mbti2(){
const [isa2Checked,setIsa2Checked]=useState(false);
const [selectedAnswer, setSelectedAnswer] = useState(null); // 선택된 답변 상태
const selectedValue2 = Mbti.selectList["2"];
- const eVal = Mbti.e;
+
const navigate = useNavigate();
useEffect(() =>{
console.log(Mbti);
@@ -33,21 +33,21 @@ function Mbti2(){
};
const handleBack = () => {
if (selectedAnswer === 1) { //1번선택하면 그대로
- updateMbti({ selectList: { ...Mbti.selectList, "2": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "2": false } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ selectList: { ...Mbti.selectList, "2": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "2": true } });
}
navigate("/mbti1"); // 이전 페이지로 이동
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ e: eVal, selectList: { ...Mbti.selectList, "2": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "2": false } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ e: eVal + 1, selectList: { ...Mbti.selectList, "2": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "2": true } });
}
navigate("/mbti3");
};
@@ -63,7 +63,7 @@ function Mbti2(){
{
if(selectedValue1){
@@ -31,21 +30,21 @@ function Mbti3(){
};
const handleBack = () => {
if (selectedAnswer === 1) {
- updateMbti({ selectList: { ...Mbti.selectList, "3": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "3": false } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ selectList: { ...Mbti.selectList, "3": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "3": true } });
}
navigate("/mbti2"); // 이전 페이지로 이동
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ s: eVal, selectList: { ...Mbti.selectList, "3": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "3": false } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ s: eVal+1, selectList: { ...Mbti.selectList, "3": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "3": true } });
}
navigate("/mbti4");
};
diff --git a/src/page/Mbti/Mbti4.jsx b/src/page/Mbti/Mbti4.jsx
index eea4da1..665eb8c 100644
--- a/src/page/Mbti/Mbti4.jsx
+++ b/src/page/Mbti/Mbti4.jsx
@@ -11,7 +11,7 @@ function Mbti4(){
const [isa2Checked,setIsa2Checked]=useState(false);
const [selectedAnswer, setSelectedAnswer] = useState(null); // 선택된 답변 상태
const selectedValue1 = Mbti.selectList["4"];
- const eVal = Mbti.p;
+
const navigate = useNavigate();
useEffect(() =>{
if(selectedValue1){
@@ -31,21 +31,21 @@ function Mbti4(){
};
const handleBack = () => {
if (selectedAnswer === 1) {
- updateMbti({ selectList: { ...Mbti.selectList, "4": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "4": false } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ selectList: { ...Mbti.selectList, "4": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "4": true } });
}
navigate("/mbti3"); // 이전 페이지로 이동
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ p: eVal, selectList: { ...Mbti.selectList, "4": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "4": false } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ p: eVal + 1, selectList: { ...Mbti.selectList, "4": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "4": true } });
}
navigate("/mbti5");
};
diff --git a/src/page/Mbti/Mbti5.jsx b/src/page/Mbti/Mbti5.jsx
index 2405d92..772c56a 100644
--- a/src/page/Mbti/Mbti5.jsx
+++ b/src/page/Mbti/Mbti5.jsx
@@ -12,7 +12,7 @@ function Mbti5(){
const [isa2Checked,setIsa2Checked]=useState(false);
const [selectedAnswer, setSelectedAnswer] = useState(null); // 선택된 답변 상태
const selectedValue1 = Mbti.selectList["5"];
- const eVal = Mbti.e;
+
const navigate = useNavigate();
useEffect(() =>{
if(selectedValue1){
@@ -42,11 +42,11 @@ function Mbti5(){
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ e: eVal + 1, selectList: { ...Mbti.selectList, "5": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "5": true } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ e: eVal, selectList: { ...Mbti.selectList, "5": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "5": false } });
}
navigate("/mbti6");
};
diff --git a/src/page/Mbti/Mbti6.jsx b/src/page/Mbti/Mbti6.jsx
index b869ee4..a209c82 100644
--- a/src/page/Mbti/Mbti6.jsx
+++ b/src/page/Mbti/Mbti6.jsx
@@ -12,7 +12,7 @@ function Mbti6(){
const [isa2Checked,setIsa2Checked]=useState(false);
const [selectedAnswer, setSelectedAnswer] = useState(null); // 선택된 답변 상태
const selectedValue1 = Mbti.selectList["6"];
- const eVal = Mbti.f;
+
const navigate = useNavigate();
useEffect(() =>{
if(selectedValue1){
@@ -42,11 +42,11 @@ function Mbti6(){
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ f: eVal + 1, selectList: { ...Mbti.selectList, "6": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "6": true } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ f: eVal, selectList: { ...Mbti.selectList, "6": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "6": false } });
}
navigate("/mbti7");
};
diff --git a/src/page/Mbti/Mbti7.jsx b/src/page/Mbti/Mbti7.jsx
index 5bbd1b9..a1a141c 100644
--- a/src/page/Mbti/Mbti7.jsx
+++ b/src/page/Mbti/Mbti7.jsx
@@ -12,7 +12,7 @@ function Mbti7(){
const [isa2Checked,setIsa2Checked]=useState(false);
const [selectedAnswer, setSelectedAnswer] = useState(null); // 선택된 답변 상태
const selectedValue1 = Mbti.selectList["7"];
- const eVal = Mbti.f;
+
const navigate = useNavigate();
useEffect(() =>{
if(selectedValue1){
@@ -42,11 +42,11 @@ function Mbti7(){
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ f: eVal + 1, selectList: { ...Mbti.selectList, "7": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "7": true } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ f: eVal, selectList: { ...Mbti.selectList, "7": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "7": false } });
}
navigate("/mbti8");
};
@@ -62,7 +62,7 @@ function Mbti7(){
{
if(selectedValue1){
@@ -42,11 +42,11 @@ function Mbti8(){
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ s: eVal + 1, selectList: { ...Mbti.selectList, "8": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "8": true } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ s: eVal, selectList: { ...Mbti.selectList, "8": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "8": false } });
}
navigate("/mbti9");
};
@@ -62,7 +62,7 @@ function Mbti8(){
{
if(selectedValue1){
@@ -42,11 +42,11 @@ function Mbti9(){
};
const handleNext = () => {
if (selectedAnswer === 1) {
- updateMbti({ p: eVal + 1, selectList: { ...Mbti.selectList, "9": true } });
+ updateMbti({ selectList: { ...Mbti.selectList, "9": true } });
console.log("Context updated:");
} else if (selectedAnswer === 2) {
- updateMbti({ p: eVal, selectList: { ...Mbti.selectList, "9": false } });
+ updateMbti({ selectList: { ...Mbti.selectList, "9": false } });
}
navigate("/mbti10");
};
diff --git a/src/page/Mbti/Mbti_result/ENFJ.jsx b/src/page/Mbti/Mbti_result/ENFJ.jsx
index 2e3f5a0..2567f26 100644
--- a/src/page/Mbti/Mbti_result/ENFJ.jsx
+++ b/src/page/Mbti/Mbti_result/ENFJ.jsx
@@ -1,11 +1,64 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ENFJImage from '../../../asset/ENFJ.png';
+import ISFPImage from '../../../asset/ISFP.png';
+import INTJImage from '../../../asset/INTJ.png';
function Enfj(){
- return(
-
- Enfj
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
모두가 함께 성장할 수 있어!
+
사교 횃불이
+
+
+

+
+
+
+ - ★ 친구들을 잘 이끌며 학교 내 분위기 메이커
+ - ★ 발표나 토론에서 중재 역할을 잘 함
+ - ★ 팀 프로젝트에서 협력과 조화를 강조
+ - ★ 리더십과 공감을 바탕으로 학급을 이끌어가는 스타일
+ - ★ 봉사활동이나 학교 행사에서 적극적으로 참여
+
+
+
+
+
+
잘 맞는 햇불이
+

+
귀찮 햇불이
+
+
+
+
안 맞는 햇불이
+

+
분석 햇불이
+
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Enfj;
\ No newline at end of file
+export default Enfj;
diff --git a/src/page/Mbti/Mbti_result/ENFP.jsx b/src/page/Mbti/Mbti_result/ENFP.jsx
index e69f6ad..9be7993 100644
--- a/src/page/Mbti/Mbti_result/ENFP.jsx
+++ b/src/page/Mbti/Mbti_result/ENFP.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ENFPImage from '../../../asset/ENFP.png';
+import INFJImage from '../../../asset/INFJ.png';
+import ESTJImage from '../../../asset/ESTJ.png';
function Enfp(){
- return(
-
- Enfp
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
상상력이 가득한 자유로운 영혼!
+
꽃밭 횃불이
+
+
+

+
+
+
+ - ★ 창의적 아이디어로 학교 프로젝트에서 활약
+ - ★ 수업 시간에도 새로운 아이디어를 끊임없이 제안
+ - ★ 교우 관계에서 자발적으로 새로운 사람과 친해짐
+ - ★ 발표나 연극 같은 활동에서 특유의 열정과 유머를 발휘
+ - ★ 정형화된 틀보다는 자유로운 수업 방식을 선호
+
+
+
+
+
+
잘 맞는 햇불이
+

+
낭만 햇불이
+
+
+
+
안 맞는 햇불이
+

+
모범 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Enfp;
\ No newline at end of file
+export default Enfp;
diff --git a/src/page/Mbti/Mbti_result/ENTJ.jsx b/src/page/Mbti/Mbti_result/ENTJ.jsx
index ba9ec8c..abf2a60 100644
--- a/src/page/Mbti/Mbti_result/ENTJ.jsx
+++ b/src/page/Mbti/Mbti_result/ENTJ.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ENTJImage from '../../../asset/ENTJ.png';
+import ISFPImage from '../../../asset/ISFP.png';
+import INTJImage from '../../../asset/INTJ.png';
function Entj(){
- return(
-
- Entj
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
안돼. 돌아가.
+
단호 횃불이
+
+
+

+
+
+
+ - ★ 리더십이 강해 팀 프로젝트에서 주도적 역할
+ - ★ 목표 달성에 매우 집중하고 계획적
+ - ★ 토론 수업에서 설득력 있는 주장을 펼침
+ - ★ 친구들과도 경쟁적이지만 결과로 인정받고 싶어 함
+ - ★ 학교 활동에서 효율성 강조, 비효율적인 것에 불만
+
+
+
+
+
+
잘 맞는 햇불이
+

+
분석 햇불이
+
+
+
+
안 맞는 햇불이
+

+
귀찮 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Entj;
\ No newline at end of file
+export default Entj;
diff --git a/src/page/Mbti/Mbti_result/ENTP.jsx b/src/page/Mbti/Mbti_result/ENTP.jsx
index ae7eb6d..c610b50 100644
--- a/src/page/Mbti/Mbti_result/ENTP.jsx
+++ b/src/page/Mbti/Mbti_result/ENTP.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ENTPImage from '../../../asset/ENTP.png';
+import INFJImage from '../../../asset/INFJ.png';
+import ESTJImage from '../../../asset/ESTJ.png';
function Entp(){
- return(
-
- Entp
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
내 길은 내가 만든다!
+
마이웨이 횃불이
+
+

+
+
+
+ - ★ 수업 중 새로운 아이디어로 토론을 리드
+ - ★ 독창적인 해결책으로 팀 프로젝트에서 창의적인 역할
+ - ★ 논쟁을 즐기며 다양한 관점을 탐구함
+ - ★ 교실에서는 규칙보다는 자유로운 사고를 중요시함
+ - ★ 학업보다는 실습과 창의력 발휘에 중점을 둠
+
+
+
+
+
+
잘 맞는 햇불이
+

+
낭만 햇불이
+
+
+
+
안 맞는 햇불이
+

+
모범 햇불이
+
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Entp;
\ No newline at end of file
+export default Entp;
diff --git a/src/page/Mbti/Mbti_result/ESFJ.jsx b/src/page/Mbti/Mbti_result/ESFJ.jsx
index 3d5d90c..c9fec9d 100644
--- a/src/page/Mbti/Mbti_result/ESFJ.jsx
+++ b/src/page/Mbti/Mbti_result/ESFJ.jsx
@@ -1,11 +1,62 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ESFJImage from '../../../asset/ESFJ.png';
+import ISFPImage from '../../../asset/ISFP.png';
+import INTPImage from '../../../asset/INTP.png';
function Esfj(){
- return(
-
- Esfj
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
모두가 행복해야 나도 행복해!
+
친절 횃불이
+
+

+
+
+ - ★ 친구를 챙기며 학급 분위기를 화목하게 만듦
+ - ★ 발표나 팀 활동에서 조화와 협동을 중시
+ - ★ 친구의 고민 상담을 자주 받아주는 따뜻한 성격
+ - ★ 선생님과 동급생 모두에게 신뢰받는 존재
+ - ★ 학교 행사나 봉사활동에 자발적으로 참여
+
+
+
+
+
+
잘 맞는 햇불이
+

+
귀찮 햇불이
+
+
+
+
안 맞는 햇불이
+

+
공상 햇불이
+
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Esfj;
\ No newline at end of file
+export default Esfj;
diff --git a/src/page/Mbti/Mbti_result/ESFP.jsx b/src/page/Mbti/Mbti_result/ESFP.jsx
index f667061..c25aa25 100644
--- a/src/page/Mbti/Mbti_result/ESFP.jsx
+++ b/src/page/Mbti/Mbti_result/ESFP.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ESFPImage from '../../../asset/ESFP.png';
+import ISFJImage from '../../../asset/ISFJ.png';
+import INTJImage from '../../../asset/INTJ.png';
function Esfp(){
- return(
-
- Esfp
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
놀면서 배우자!
+
파티 횃불이
+
+
+

+
+
+
+ - ★ 친구들과 교실 분위기를 띄우는 에너자이저
+ - ★ 즉흥적인 이벤트나 발표에 강함
+ - ★ 수업보단 실습과 체험형 학습을 선호
+ - ★ 팀 프로젝트에서 활기 넘치는 아이디어 제안
+ - ★ 축제나 체육대회 같은 활동에 리더 역할 자주 맡음
+
+
+
+
+
+
잘 맞는 햇불이
+

+
평화 햇불이
+
+
+
+
안 맞는 햇불이
+

+
분석 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Esfp;
\ No newline at end of file
+export default Esfp;
diff --git a/src/page/Mbti/Mbti_result/ESTJ.jsx b/src/page/Mbti/Mbti_result/ESTJ.jsx
index 7845f4c..d7dba15 100644
--- a/src/page/Mbti/Mbti_result/ESTJ.jsx
+++ b/src/page/Mbti/Mbti_result/ESTJ.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ESTJImage from '../../../asset/ESTJ.png';
+import ISTJImage from '../../../asset/ISTJ.png';
+import INFPImage from '../../../asset/INFP.png';
function Estj(){
- return(
-
- Estj
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
규칙이 곧 법이다!
+
모범 횃불이
+
+
+

+
+
+
+ - ★ 규칙과 시스템을 중시하여 질서 있는 학교 생활을 지향
+ - ★ 팀 프로젝트에서 리더를 맡아 효율적으로 이끌음
+ - ★ 성과 중심으로 학업 목표를 설정하고 달성
+ - ★ 토론 수업에서 논리적이고 명확한 의견을 제시
+ - ★ 조직력과 책임감이 강해 학교 내 다양한 직책을 수행
+
+
+
+
+
+
잘 맞는 햇불이
+

+
진지 햇불이
+
+
+
+
안 맞는 햇불이
+

+
내향 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Estj;
\ No newline at end of file
+export default Estj;
diff --git a/src/page/Mbti/Mbti_result/ESTP.jsx b/src/page/Mbti/Mbti_result/ESTP.jsx
index 65ae00b..4cda0ba 100644
--- a/src/page/Mbti/Mbti_result/ESTP.jsx
+++ b/src/page/Mbti/Mbti_result/ESTP.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ESTPImage from '../../../asset/ESTP.png';
+import ISTPImage from '../../../asset/ISTP.png';
+import INFJImage from '../../../asset/INFJ.png';
function Estp(){
- return(
-
- Estp
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
도전이 없다면 재미도 없다!
+
도전 횃불이
+
+
+

+
+
+
+ - ★ 문제 해결 능력이 뛰어나서 빠른 판단과 실행력
+ - ★ 수업 중 갑작스러운 질문이나 상황에도 즉각 대응
+ - ★ 운동이나 동아리 같은 다양한 활동에 도전하는 걸 즐김
+ - ★ 경쟁심이 강해서 성취감을 느끼는 일에 적극적
+ - ★ 실습과 실전에서 더 강한 모습을 보임
+
+
+
+
+
+
잘 맞는 햇불이
+

+
과묵 햇불이
+
+
+
+
안 맞는 햇불이
+

+
낭만 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Estp;
\ No newline at end of file
+export default Estp;
diff --git a/src/page/Mbti/Mbti_result/INFJ.jsx b/src/page/Mbti/Mbti_result/INFJ.jsx
index cf60b8e..4f1a778 100644
--- a/src/page/Mbti/Mbti_result/INFJ.jsx
+++ b/src/page/Mbti/Mbti_result/INFJ.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import INFJImage from '../../../asset/INFJ.png';
+import ENFPImage from '../../../asset/ENFP.png';
+import ESTPImage from '../../../asset/ESTP.png';
function Infj(){
- return(
-
- Infj
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
낭만은 챙기면서 살아야지~
+
낭만 횃불이
+
+
+

+
+
+
+ - ★ 창의적이고 깊이 있는 사고로 프로젝트를 수행
+ - ★ 다른 사람들의 감정을 잘 이해해 학급 내 중재 역할을 함
+ - ★ 독립적으로 일하는 것을 선호하지만 팀 프로젝트에서도 깊이 있는 기여를 함
+ - ★ 선생님과 친구들에게 신뢰받는 진지한 태도를 지님
+ - ★ 새로운 아이디어를 바탕으로 학교 행사나 프로젝트 기획에 적극적
+
+
+
+
+
+
잘 맞는 햇불이
+

+
꽃밭 햇불이
+
+
+
+
안 맞는 햇불이
+

+
도전 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Infj;
\ No newline at end of file
+export default Infj;
diff --git a/src/page/Mbti/Mbti_result/INFP.jsx b/src/page/Mbti/Mbti_result/INFP.jsx
index 8011aba..85e2e79 100644
--- a/src/page/Mbti/Mbti_result/INFP.jsx
+++ b/src/page/Mbti/Mbti_result/INFP.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import INFPImage from '../../../asset/INFP.png';
+import ENFJImage from '../../../asset/ENFJ.png';
+import ESTJImage from '../../../asset/ESTJ.png';
function Infp(){
- return(
-
- Infp
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
모두가 행복해야 나도 행복해!
+
내향 횃불이과
+
+
+

+
+
+
+ - ★ 자유롭고 창의적인 환경에서 아이디어를 발산하는 것을 좋아함
+ - ★ 감정이 풍부해 예술 과목이나 문예 활동에서 두각을 나타냄
+ - ★ 친구들과 깊이 있는 대화를 즐기고 고민 상담을 잘 들어줌
+ - ★ 조용하지만 팀 프로젝트에서는 독특한 관점을 제시함
+ - ★ 내성적이지만 개인적인 생각을 글이나 그림으로 표현하는 걸 선호
+
+
+
+
+
+
잘 맞는 햇불이
+

+
사교 햇불이
+
+
+
+
안 맞는 햇불이
+

+
모범 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Infp;
\ No newline at end of file
+export default Infp;
diff --git a/src/page/Mbti/Mbti_result/INTJ.jsx b/src/page/Mbti/Mbti_result/INTJ.jsx
index 801db58..5ad7322 100644
--- a/src/page/Mbti/Mbti_result/INTJ.jsx
+++ b/src/page/Mbti/Mbti_result/INTJ.jsx
@@ -1,11 +1,61 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import INTJImage from '../../../asset/INTJ.png';
+import ENTJImage from '../../../asset/ENTJ.png';
+import ESFPImage from '../../../asset/ESFP.png';
function Intj(){
- return(
-
- Intj
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
모두가 행복해야 나도 행복해!
+
분석 횃불이
+
+

+
+
+ - ★ 철저한 계획 아래 학업을 진행하고 목표를 설정함
+ - ★ 학업 성취도가 높으며 깊이 있는 학습을 선호함
+ - ★ 팀 프로젝트에서 전략적인 사고로 전체 방향을 설정함
+ - ★ 자신의 능력을 믿고 독립적으로 학업을 수행하는 스타일
+ - ★ 논리적이고 분석적인 수업에서 두각을 나타냄
+
+
+
+
+
+
잘 맞는 햇불이
+

+
단호 햇불이
+
+
+
+
안 맞는 햇불이
+

+
파티 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Intj;
\ No newline at end of file
+export default Intj;
diff --git a/src/page/Mbti/Mbti_result/INTP.jsx b/src/page/Mbti/Mbti_result/INTP.jsx
index 416e455..a0b7cae 100644
--- a/src/page/Mbti/Mbti_result/INTP.jsx
+++ b/src/page/Mbti/Mbti_result/INTP.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import INTPImage from '../../../asset/INTP.png';
+import INTJImage from '../../../asset/INTJ.png';
+import ESFJImage from '../../../asset/ESFJ.png';
function Intp(){
- return(
-
- Intp
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
모두가 행복해야 나도 행복해!
+
공상 횃불이
+
+
+

+
+
+
+ - ★ 수업 중 깊이 있는 질문을 던지며 학문적 호기심이 강함
+ - ★ 독립적인 학습을 선호하며 스스로 자료를 찾아 학습함
+ - ★ 논리적이고 분석적인 수업에서 두각을 나타냄
+ - ★ 팀 프로젝트에서 혼자 깊이 있는 분석을 제공하는 스타일
+ - ★ 팀 활동보다는 개별적인 연구나 과제에서 더 큰 성과를 냄
+
+
+
+
+
+
잘 맞는 햇불이
+

+
분석 햇불이
+
+
+
+
안 맞는 햇불이
+

+
친절 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Intp;
\ No newline at end of file
+export default Intp;
diff --git a/src/page/Mbti/Mbti_result/ISFJ.jsx b/src/page/Mbti/Mbti_result/ISFJ.jsx
index 112d5cd..74c6207 100644
--- a/src/page/Mbti/Mbti_result/ISFJ.jsx
+++ b/src/page/Mbti/Mbti_result/ISFJ.jsx
@@ -1,11 +1,64 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ISFJImage from '../../../asset/ISFJ.png';
+import ISFPImage from '../../../asset/ISFP.png';
+import INTPImage from '../../../asset/INTP.png';
function Isfj(){
- return(
-
- Isfj
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
모두가 행복해야 나도 행복해!
+
평화 횃불이
+
+
+

+
+
+
+ - ★ 친구를 챙기며 학급 분위기를 화목하게 만듦
+ - ★ 발표나 팀 활동에서 조화와 협동을 중시
+ - ★ 친구의 고민 상담을 자주 받아주는 따뜻한 성격
+ - ★ 선생님과 동급생 모두에게 신뢰받는 존재
+ - ★ 학교 행사나 봉사활동에 자발적으로 참여
+
+
+
+
+
+
잘 맞는 햇불이
+

+
귀찮 햇불이
+
+
+
+
안 맞는 햇불이
+

+
공상 햇불이
+
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Isfj;
\ No newline at end of file
+export default Isfj;
diff --git a/src/page/Mbti/Mbti_result/ISFP.jsx b/src/page/Mbti/Mbti_result/ISFP.jsx
index a96c013..ad9ee6f 100644
--- a/src/page/Mbti/Mbti_result/ISFP.jsx
+++ b/src/page/Mbti/Mbti_result/ISFP.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ISFPImage from '../../../asset/ISFP.png';
+import INTPImage from '../../../asset/INTP.png';
+import ISFJImage from '../../../asset/ISFJ.png';
function Isfp(){
- return(
-
- Isfp
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
모두가 행복해야 나도 행복해!
+
귀찮 횃불이
+
+
+

+
+
+
+ - ★ 친구를 챙기며 학급 분위기를 화목하게 만듦
+ - ★ 발표나 팀 활동에서 조화와 협동을 중시
+ - ★ 친구의 고민 상담을 자주 받아주는 따뜻한 성격
+ - ★ 선생님과 동급생 모두에게 신뢰받는 존재
+ - ★ 학교 행사나 봉사활동에 자발적으로 참여
+
+
+
+
+
+
잘 맞는 햇불이
+

+
공상 햇불이
+
+
+
+
안 맞는 햇불이
+

+
평화 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Isfp;
\ No newline at end of file
+export default Isfp;
diff --git a/src/page/Mbti/Mbti_result/ISTJ.jsx b/src/page/Mbti/Mbti_result/ISTJ.jsx
index 4242f6f..28002ef 100644
--- a/src/page/Mbti/Mbti_result/ISTJ.jsx
+++ b/src/page/Mbti/Mbti_result/ISTJ.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ISTJImage from '../../../asset/ISTJ.png';
+import ISFPImage from '../../../asset/ISFP.png';
+import ISFJImage from '../../../asset/ISFJ.png';
function Istj(){
- return(
-
- Istj
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
모두가 행복해야 나도 행복해!
+
진지 횃불이
+
+
+

+
+
+
+ - ★ 친구를 챙기며 학급 분위기를 화목하게 만듦
+ - ★ 발표나 팀 활동에서 조화와 협동을 중시
+ - ★ 친구의 고민 상담을 자주 받아주는 따뜻한 성격
+ - ★ 선생님과 동급생 모두에게 신뢰받는 존재
+ - ★ 학교 행사나 봉사활동에 자발적으로 참여
+
+
+
+
+
+
잘 맞는 햇불이
+

+
귀찮 햇불이
+
+
+
+
안 맞는 햇불이
+

+
평화 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Istj;
\ No newline at end of file
+export default Istj;
diff --git a/src/page/Mbti/Mbti_result/ISTP.jsx b/src/page/Mbti/Mbti_result/ISTP.jsx
index 107dbc4..0d3379e 100644
--- a/src/page/Mbti/Mbti_result/ISTP.jsx
+++ b/src/page/Mbti/Mbti_result/ISTP.jsx
@@ -1,11 +1,63 @@
import React from "react";
+import { useNavigate } from 'react-router-dom';
+import './Result.css';
+import ISTPImage from '../../../asset/ISTP.png';
+import ISFPImage from '../../../asset/ISFP.png';
+import ISFJImage from '../../../asset/ISFJ.png';
function Istp(){
- return(
-
- Istp
+ const navigate = useNavigate();
+
+ const handleBackToHome = () => {
+ navigate('/ChatStartPage');
+ };
+
+ return (
+
+
+
모두가 행복해야 나도 행복해!
+
과묵 횃불이
+
+
+

+
+
+
+ - ★ 친구를 챙기며 학급 분위기를 화목하게 만듦
+ - ★ 발표나 팀 활동에서 조화와 협동을 중시
+ - ★ 친구의 고민 상담을 자주 받아주는 따뜻한 성격
+ - ★ 선생님과 동급생 모두에게 신뢰받는 존재
+ - ★ 학교 행사나 봉사활동에 자발적으로 참여
+
+
+
+
+
+
잘 맞는 햇불이
+

+
귀찮 햇불이
+
+
+
+
안 맞는 햇불이
+

+
평화 햇불이
+
+
+
+
+
+
+
+
- )
-}
+ );
+};
-export default Istp;
\ No newline at end of file
+export default Istp;
diff --git a/src/page/Mbti/Mbti_result/Result.css b/src/page/Mbti/Mbti_result/Result.css
new file mode 100644
index 0000000..fabfccb
--- /dev/null
+++ b/src/page/Mbti/Mbti_result/Result.css
@@ -0,0 +1,137 @@
+.Mbti_result{
+ height: 812px;
+ width: 375px;
+ margin: 0 auto;
+
+ .container {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ height: 100%;
+ }
+
+ .title {
+ /* 횃불이 테스트 결과 */
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 700;
+ font-size: 30px;
+ align-items: center;
+ color: #FF7898;
+ };
+
+ .subtitle {
+ margin-top: 30px;
+ margin-bottom: -15px;
+ flex-direction: row;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 18px;
+ line-height: 20px;
+ text-align: center;
+ color: #000000;
+ }
+
+ .profile-image {
+ width: 300px;
+ margin-top: -20px;
+ margin-bottom: 10px;
+ height: auto;
+ }
+
+ .traits {
+ margin-top: -55px;
+ list-style-type: none;
+ padding: 0;
+ font-size: 16px;
+ font-family: 'Pretendard';
+ align-items: center;
+ justify-content: center;
+ }
+
+ .traits1 {
+ margin-top: -35px;
+ list-style-type: none;
+ padding: 0;
+ font-size: 16px;
+ font-family: 'Pretendard';
+ align-items: center;
+ justify-content: center;
+ }
+
+ .traits li {
+ margin-bottom: 8px;
+ }
+
+ .matches {
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ }
+
+ .good-bad-match {
+ text-align: center;
+ border-radius: 10px; /* 박스 둥글게 */
+ display: flex;
+ gap: 30px; /* 두 항목 간 간격 조정 */
+ margin-bottom: 20px;
+ }
+
+ .good-match, .bad-match {
+ text-align: center;
+ border: 2px solid #FF7898;
+ border-radius: 10px;
+ position: relative;
+ }
+
+ .good-match img, .bad-match img {
+ margin-top: -20px;
+ width: 130px;
+ height: auto;
+ position: relative;
+ z-index: 1; /* 낮은 z-index 값으로 뒤로 보냄 */
+
+ }
+
+ .combination{
+ font-size: 15px;
+ margin-top: 8px;
+ position: relative;
+ z-index: 2;
+ }
+ .nickname{
+ font-size: 15px;
+ position: relative;
+ z-index: 2;
+ margin-top: -20px;
+
+ }
+
+ .button-container{
+ margin-top:auto;
+ }
+
+ .bottom-Button {
+ /* 하단 버튼 */
+ width: 300px;
+ height: 50px;
+
+ color: #F7F7F7;
+ background: #FF7898;
+ border-radius: 8px;
+ border-color: rgb(255, 255, 255);
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 700;
+ font-size: 18px;
+
+ margin-bottom: 40px;
+ margin-top:auto;
+
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ }
+}
\ No newline at end of file
diff --git a/src/page/Mbti/Question.jsx b/src/page/Mbti/Question.jsx
index c84358e..d9e5b0e 100644
--- a/src/page/Mbti/Question.jsx
+++ b/src/page/Mbti/Question.jsx
@@ -1,12 +1,12 @@
-import React, { useContext } from "react";
+
import { useState , useEffect} from "react";
-import { MbtiContext } from "../../context/MbitContext";
+
function Question({question, answer1, answer2, a1Checked, a2Checked, onAnswerSelected}){
- const [selectedAnswer1, setSelectedAnswer1] = useState(false);
- const [selectedAnswer2, setSelectedAnswer2] = useState(false);
+ const [selectedAnswer1, setSelectedAnswer1] = useState();
+ const [selectedAnswer2, setSelectedAnswer2] = useState();
useEffect(()=>{
if(a1Checked){
setSelectedAnswer1(true);
diff --git a/src/page/Mypage/Mypage.css b/src/page/Mypage/Mypage.css
index 75c63b7..0574422 100644
--- a/src/page/Mypage/Mypage.css
+++ b/src/page/Mypage/Mypage.css
@@ -1,31 +1,33 @@
-.mypage{
+.mypage {
display: flex;
flex-direction: column;
- align-items: flex-start;
- background-color: #FFFFFF ;
+ align-items: flex-start;
+ background-color: #FFFFFF;
width: 375px;
height: 100vh;
}
-.mypage{
- #title{
-
- width: auto;
- height: 18px;
- margin-top: 58px;
- margin-left: 16px;
-
- font-family: 'Pretendard';
- font-style: normal;
- font-weight: 600;
- font-size: 16px;
- line-height: 18px;
- display: flex;
- align-items: flex-start;
-
- color: #3D3D3D;
-
- }
- #profile{
+
+.mypage {
+ #title {
+
+ width: auto;
+ height: 18px;
+ margin-top: 58px;
+ margin-left: 16px;
+
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 600;
+ font-size: 16px;
+ line-height: 18px;
+ display: flex;
+ align-items: flex-start;
+
+ color: #3D3D3D;
+
+ }
+
+ #profile {
margin-top: 14px;
width: 100%;
@@ -34,8 +36,9 @@
align-items: center;
}
- #profile_img{
-
+
+ #profile_img {
+
width: 74px;
height: 74px;
top: 90px;
@@ -44,11 +47,12 @@
background: #BABABA;
}
- #nickname{
-
+
+ #nickname {
+
width: auto;
height: 16px;
- margin-top: 10px ;
+ margin-top: 10px;
font-family: 'Pretendard';
font-style: normal;
font-weight: 600;
@@ -58,11 +62,12 @@
}
- #etc{
-
+
+ #etc {
+
width: auto;
height: 16px;
- margin-top: 4px;
+ margin-top: 4px;
font-family: 'Pretendard';
font-style: normal;
font-weight: 500;
@@ -73,43 +78,49 @@
}
- #divider{
- margin-top: 18px;
+
+ #divider {
+ margin-top: 18px;
width: 375px;
height: 6px;
border-top: 6px;
- background-color:#F5F6F7 ;
+ background-color: #F5F6F7;
margin-bottom: 12px;
}
- .tab-content{
+
+ .tab-content {
display: flex;
flex-direction: column;
width: auto;
height: auto;
margin-top: 8px;
-
+
padding-right: 16px;
}
- #tabCont{
+
+ #tabCont {
display: flex;
flex-direction: row;
justify-content: center;
justify-self: flex-start;
width: 339px;
- padding-left: 16px;
+ padding-left: 16px;
}
- .tabs{
+
+ .tabs {
display: flex;
flex-direction: column;
justify-content: flex-start;
width: 100%;
}
- #tabs_divider{
+
+ #tabs_divider {
display: flex;
flex-direction: row;
}
- .tab{
-
+
+ .tab {
+
width: auto;
height: 18px;
padding-left: 13px;
@@ -123,7 +134,8 @@
}
- .tabactive{
+
+ .tabactive {
width: auto;
height: 18px;
font-family: 'Pretendard';
@@ -138,10 +150,10 @@
border-bottom: 2px solid #FF7898;
}
- #profile_info{
- /* 키워드 사이엔 쉼표(,)로 구분해주세요 */
+ #profile_info {
+ /* 키워드 사이엔 쉼표(,)로 구분해주세요 */
+
-
width: auto;
height: 14px;
@@ -159,17 +171,17 @@
}
- #ment_cont{
+ #ment_cont {
display: flex;
flex-direction: column;
}
- #ment_title{
- /* 나의 한 마디 */
+ #ment_title {
+ /* 나의 한 마디 */
width: auto;
height: 16px;
- margin-top:22px ;
+ margin-top: 22px;
font-family: 'Pretendard';
font-style: normal;
font-weight: 600;
@@ -183,7 +195,7 @@
}
- #ment_input{
+ #ment_input {
width: 343px;
height: auto;
display: flex;
@@ -192,17 +204,17 @@
justify-content: flex-start;
}
-
- #ment_btn{
-
+
+ #ment_btn {
+
width: 42px;
height: 46px;
border: none;
margin-left: 4px;
background: #F5F5F5;
border-radius: 10px;
-
+
font-family: 'Pretendard';
font-style: normal;
font-weight: 400;
@@ -216,8 +228,8 @@
}
- #others{
- margin-top: 31px;
+ #others {
+ margin-top: 31px;
width: 321px;
height: 127px;
display: flex;
@@ -225,15 +237,18 @@
justify-content: space-around;
background: #F5F5F5;
border-radius: 10px;
- padding:11px ;
+ padding: 11px;
}
- .option{
-
+ .option {
+ display: flex;
+ /* text-align: center; */
+ justify-content: start;
+
width: auto;
height: 16px;
-
+
font-family: 'Pretendard';
font-style: normal;
@@ -249,8 +264,34 @@
}
- .option_info{
-
+ .mbti-test {
+ position: relative;
+ left: 79px;
+ height: 22px;
+ font-family: 'Pretendard';
+ font-style: normal;
+ font-weight: 500;
+ font-size: 12px;
+ line-height: 15px;
+ letter-spacing: -1.5px;
+ text-align: center;
+ border: none;
+ color: #FFFFFF;
+ background: #FF7898;
+ border-radius: 16px;
+ }
+
+ .mbti_input {
+ width: 150px;
+ }
+
+ #others .empty {
+ font-weight: 300;
+ color: #999;
+ }
+
+ .option_info {
+
width: auto;
height: 18px;
@@ -268,7 +309,26 @@
}
- #email{
+
+ .top {
+ height: 74px;
+ }
+
+ .edit-avatar {
+ border: 1px solid #ccc;
+ border-radius: 50%;
+ position: relative;
+ width: 20px;
+ height: 20px;
+ left: 50px;
+ top: -25px;
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ background: #F5F5F5;
+ }
+
+ #email {
margin-top: 14px;
display: flex;
flex-direction: column;
@@ -276,7 +336,8 @@
height: auto;
margin-left: 11px;
}
- #email_info{
+
+ #email_info {
margin-top: 4px;
margin-left: 11px;
width: auto;
@@ -293,12 +354,13 @@
color: #3D3D3D;
}
- #secession{
-
+ #secession {
+
+
width: auto;
height: 30px;
- margin-top: 21px;
+ margin-top: 21px;
font-family: 'Pretendard';
font-style: normal;
font-weight: 400;
@@ -313,7 +375,8 @@
background-color: #FFFFFF;
}
- input{
+
+ input {
background-color: #F5F5F5;
border: none;
width: auto;
@@ -331,13 +394,15 @@
color: #3D3D3D;
}
- input:focus{
+
+ input:focus {
outline: none;
}
- .mTitle{
+
+ .mTitle {
display: flex;
justify-content: space-between;
-
+
font-family: 'Pretendard';
font-weight: 900;
font-size: 14px;
@@ -347,8 +412,9 @@
}
- #ment{
-
+
+ #shortIntroduce {
+
width: 278px;
height: 46px;
border: none;
@@ -358,16 +424,16 @@
padding-left: 15px;
margin: 0;
}
-
- #submit{
-
+
+ #submit {
+
display: flex;
justify-content: center;
align-items: center;
-
+
width: 37px;
height: 22px;
-
+
font-family: 'Pretendard';
font-style: normal;
@@ -383,51 +449,47 @@
border-radius: 16px;
}
- .banUserList{
-
- }
- #banUser{
-
- }
- #listForm{
-
- }
- #ban_profile{
- }
- #ban_nickname{
+}
- }
- #ban_userinfo{
-
- }
+/* Rectangle 5199 */
-}
-#navi{
+#navi-con {
position: fixed;
width: 375px;
height: 53px;
+ bottom: 0;
+}
+
+#navi {
+ padding-top: 5px;
+ background: #FFFFFF;
+ /* navi */
+ box-shadow: 0px -2px 3px rgba(0, 0, 0, 0.08);
+ border-radius: 20px 20px 0px 0px;
display: flex;
justify-content: space-around;
flex-direction: row;
- bottom: 0px;
}
-#play{
-
+
+#play {
+
width: 34px;
height: 48px;
- background-image:url('../../asset/play.png');
+ background-image: url('../../asset/play.png');
}
-#talk{
-
+
+#talk {
+
width: 32px;
height: 46px;
- background-image: url('../../asset/talk.png');
+ background-image: url('../../asset/talk.png');
}
-#my{
+
+#my {
width: 32px;
height: 46px;
background-image: url('../../asset/my.png');
diff --git a/src/page/Mypage/Mypage.jsx b/src/page/Mypage/Mypage.jsx
index adfde2b..30c7f44 100644
--- a/src/page/Mypage/Mypage.jsx
+++ b/src/page/Mypage/Mypage.jsx
@@ -1,131 +1,243 @@
-import React from "react";
+import React, { useState, useEffect} from "react";
import Tabs from "./Tabs";
import "./Mypage.css";
-function Mypage(){
- const UserInfo = {
- email:"metlab.inu.ac.kr",
- mbti:"ESFP",
- height:"160",
- drinking:"술 마시는 걸 즐겨요",
- smoking:"비흡연자"
- };
+import { useNavigate } from "react-router-dom";
+import { getUser } from "../../api/getUser";
+import { putUser} from "../../api/putUser";
+import profileImage1 from "../../asset/ChatRoomPic1.png"
+import profileImage2 from "../../asset/ChatRoomPic2.png"
+import profileImage3 from "../../asset/ChatRoomPic3.png"
+import profileImage4 from "../../asset/ChatRoomPic4.png"
+import profileImage5 from "../../asset/ChatRoomPic5.png"
+import profileImage6 from "../../asset/ChatRoomPic6.png"
+
+
+function Mypage() {
+ const navigate = useNavigate();
+ const profileImages =[
+ profileImage1,
+ profileImage2,
+ profileImage3,
+ profileImage4,
+ profileImage5,
+ profileImage6
+ ]
+ const [data, setData] = useState({
+ nickname: "",
+ schoolEmail: 0,
+ studentId: "",
+ department:"",
+ mbti:"",
+ college:"",
+ shortIntroduce:"",
+ profile:""
+ });
+
+ const [newData, setNewData] = useState({
+ college: data.college,
+ department: data.department,
+ drinking: "",
+ height: "",
+ mbti: "",
+ nickname: data.nickname,
+ schoolEmail: data.schoolEmail,
+ smoking: "",
+ shortIntroduce:"",
+ profile:""
+ })
+ const [token, setToken] = useState('');
+
+ useEffect(() => {
+ // 로컬 스토리지에서 토큰 읽어오기
+ const storedToken = localStorage.getItem('accessToken');
+ console.log(storedToken);
+ if (storedToken) {
+ setToken(storedToken);
+ }
+ }, []);
+
+ useEffect(() => {
+ if (!token) return; // 토큰이 없으면 데이터를 가져오지 않음
- const dummyBanList = [
- {
- nickname:"귀여운 횃불이1",
- userinfo:"컴퓨터공학부 22학번"
- },
- {
- nickname:"귀여운 횃불이2",
- userinfo:"컴퓨터공학부 23학번"
- },
- {
- nickname:"귀여운 횃불이3",
- userinfo:"컴퓨터공학부 24학번"
+ // 마이페이지 정보를 가져오는 함수 호출
+ const fetchMypageData = async () => {
+ try {
+ const mypageData = await getUser(token);
+ setData(mypageData);
+ setNewData(mypageData);
+ } catch (error) {
+ console.error('Error fetching mypage data:', error);
+ }
+ };
+
+ fetchMypageData();
+ }, [token]);
+
+ const handleInputChange = (event) => {
+ const { id, value } = event.target;
+ setNewData((prevData) => ({
+ ...prevData,
+ [id]: value // 입력 필드의 name 속성에 따라 상태를 업데이트
+ }));
+ };
+ const handleNavigation = (destination) => {
+ switch (destination) {
+ case 'play':
+ navigate('/mbti');
+ break;
+ case 'talk':
+ navigate('/ChatStartPage');
+ break;
+ case 'my':
+ navigate('/myPage');
+ break;
+ default:
+ break;
}
- ]
-
- const BanUserList=({banUserList})=>{
- return (
-
- 차단 목록
-
- {banUserList.map((user)=>(
-
- ))}
-
-
)
+ const handleMbtiTest=()=>{
+ navigate('/mbti');
}
- return(
-
-
- 마이페이지
-
-
-
-
귀여운 횃불이
-
컴퓨터공학부 22학번
-
-
-
-
-
-
내 정보에서 프로필 내용을 수정할 수 있어요
-
-
-
· MBTI
-
{UserInfo.mbti}
-
-
· 키
-
{UserInfo.height}cm
-
-
· 음주
-
{UserInfo.drinking}
-
-
· 흡연
-
{UserInfo.smoking}
-
-
-
-
-
· 이메일
-
{UserInfo.email}
-
-
+ return (
+
+
+
+
+ 마이페이지
+
+
+
+
+
-
-
키워드 사이엔 쉼표(,)로 구분해주세요
-
-
-
· 이메일
-
{UserInfo.email}
-
-
-
-
프로필
-
+
{data.nickname}
+
{data.department} {data.studentId.substring(2, 4)}학번
+
+
+
+
+
+
내 정보에서 프로필 내용을 수정할 수 있어요
+
-
· MBTI
-
+
+
+
· 키
+
{data.height ? (
+
{data.height}cm
+ ) : (
+
+ )}
+
+
+
-
· 키
-
+
+
· 이메일
+
{data.schoolEmail}
-
· 음주
-
+ {/**/}
+
+
+
+
+
키워드 사이엔 쉼표(,)로 구분해주세요
+
+
+
· 이메일
+
{data.schoolEmail}
-
-
-
-
-
+
+
+
+
+
+
handleNavigation('play')}>
+
handleNavigation('talk')}>
+
handleNavigation('my')}>
-
-
-
+
-
+
)
}
diff --git a/src/page/Mypage/Tabs.jsx b/src/page/Mypage/Tabs.jsx
index 3ffef53..9ab2777 100644
--- a/src/page/Mypage/Tabs.jsx
+++ b/src/page/Mypage/Tabs.jsx
@@ -11,14 +11,14 @@ const Tabs = ({ children }) => {
return (
- {children.map((child) => (
-
- ))}
+ {children.map((child) => (
+
+ ))}
@@ -26,7 +26,7 @@ const Tabs = ({ children }) => {
child.props.label === activeTab ? child.props.children : null
)}
-
+
);
};