Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feat fe ask question page수정 #67

Merged
merged 2 commits into from
Aug 16, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
45 changes: 41 additions & 4 deletions client/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions client/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
"react-redux": "^8.1.2",
"react-router-dom": "^6.14.2",
"react-scripts": "5.0.1",
"redux": "^4.1.2",
"styled-components": "^6.0.7",
"web-vitals": "^2.1.4"
},
Expand Down
9 changes: 3 additions & 6 deletions client/src/App.js
Original file line number Diff line number Diff line change
@@ -1,15 +1,12 @@
import './App.css';
import AskQuestionPage from './pages/AskQuestionPage';

import Sidebar from './components/sidebar';
import Header from './components/Header';
import Footer from './components/Footer';
// import LoginPage from './pages/LoginPage';

function App() {
return (
<div className="App">
<Header />
<Sidebar />
<Footer />
<AskQuestionPage />
</div>
);
}
Expand Down
15 changes: 11 additions & 4 deletions client/src/components/Editor5.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@ import { CKEditor } from '@ckeditor/ckeditor5-react';
import ClassicEditor from '@ckeditor/ckeditor5-build-classic';
import { styled } from 'styled-components';
import PropTypes from 'prop-types';
import { useState } from 'react';
import { useDispatch, useSelector } from 'react-redux';
// import { useState } from 'react';

// ========== styled-components ==========
const StyledEditor = styled.div`
max-width: 800px;
background-color: #ffffff;
Expand Down Expand Up @@ -50,15 +52,20 @@ function Editor5({
handleButtonClick,
editorRef,
}) {
const [editorContent, setEditorContent] = useState(''); // 텍스트 내용을 상태로 관리
const dispatch = useDispatch();

const editorContent = useSelector((state) => ({
editorContent: state.editorContent,
}));

const handleEditorChange = (event, editor) => {
const data = editor.getData();
setEditorContent(data); // 텍스트 내용 업데이트
dispatch({ type: 'SET_EDITOR_CONTENT', payload: data });
};

// 처음 글자입력시 <p> 태그까지 글자로 인식하여 8부터 시작함 때문에 length를 26으로 설정
const isButtonDisabled = editorContent.length < 26;
// editorContent가 객체 형태라서 editorContent.editorContent.length
const isButtonDisabled = editorContent.editorContent.length < 26;
return (
<StyledEditor isButtonDisabled={isButtonDisabled}>
<div className="editor-container">
Expand Down
1 change: 1 addition & 0 deletions client/src/images/facebook-icon.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
2 changes: 2 additions & 0 deletions client/src/images/github-icon.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
11 changes: 11 additions & 0 deletions client/src/images/google-icon.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
19 changes: 19 additions & 0 deletions client/src/images/small-logo.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
10 changes: 7 additions & 3 deletions client/src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,16 @@ import ReactDOM from 'react-dom/client';
import './index.css';
import App from './App';
import reportWebVitals from './reportWebVitals';
import { Provider } from 'react-redux';
import store from './store';

const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
<React.StrictMode>
<App />
</React.StrictMode>,
<Provider store={store}>
<React.StrictMode>
<App />
</React.StrictMode>
</Provider>,
);

// If you want to start measuring performance in your app, pass a function
Expand Down
114 changes: 76 additions & 38 deletions client/src/pages/AskQuestionPage.js
Original file line number Diff line number Diff line change
@@ -1,13 +1,18 @@
import { styled } from 'styled-components';
import Editor5 from '../components/Editor5';
import { useState, useRef } from 'react';
import { useRef } from 'react';
import { useSelector, useDispatch } from 'react-redux';
import QuestionPageDropdown from '../components/QuestionPageDropdown';
// import Header from '../components/Header';
// import Footer from '../components/Footer';

const StyleAskPage = styled.div`
background-color: #f8f9f9;
display: flex;
flex-direction: column;
align-items: center;
height: 100vh;
margin-top: 56px;

// 사이드 여백 조정
.inner {
Expand Down Expand Up @@ -135,75 +140,109 @@ const StyleAskPage = styled.div`
`;

function AskQuestionPage() {
const [isChecked, SetIsChecked] = useState(false);

const handleCheckboxChange = (event) => {
const checkedValue = event.target.checked;
SetIsChecked(checkedValue); // 체크박스 상태 업데이트
};

const isButtonDisabled = !isChecked;

const [checkContainerVisible, setCheckContainerVisible] = useState(false);

const [titleButtonVisible, setTitleButtonVisible] = useState(true);
const [editorButtonVisible, setEditorButtonVisible] = useState(false);
const [editor2ButtonVisible, setEditor2ButtonVisible] = useState(false);

const [tagButtonVisible, setTagButtonVisible] = useState(false);
const [reviewButtonVisible, setReviewButtonVisible] = useState(false);

const editorRef = useRef(null);
const editor2Ref = useRef(null);
const TagRef = useRef(null);

const handleTitleButtonClick = () => {
setTitleButtonVisible(false);
setEditorButtonVisible(true);
// 리덕스 스토어에 액션을 디스패치하여 상태를 업데이트 하는 dispatch함수
const dispatch = useDispatch();

const {
checkContainerVisible,
isChecked,
titleButtonVisible,
editorButtonVisible,
editor2ButtonVisible,
tagButtonVisible,
reviewButtonVisible,
isDropdownOpen,
} = useSelector((state) => ({
// 리덕스 스토어에서 상태값을 가져옴
checkContainerVisible: state.checkContainerVisible,
isChecked: state.isChecked,
titleButtonVisible: state.titleButtonVisible,
tagButtonVisible: state.tagButtonVisible,
reviewButtonVisible: state.reviewButtonVisible,
editorButtonVisible: state.editorButtonVisible,
editor2ButtonVisible: state.editor2ButtonVisible,
isDropdownOpen: state.isDropdownOpen,
}));

// isChecked 상태의 반전 값을 가짐
const isButtonDisabled = !isChecked;

// ========== 핸들러 함수내 액션을 디스패치하여 Redux 상태를 업데이트하는 부분입니다. ==========

// 첫 번째 에디터에 포커스 설정
// 제목 버튼 클릭 핸들러
const handleTitleButtonClick = () => {
// titleButtonVisible 상태를 숨김(false)으로 변경
dispatch({ type: 'SET_TITLE_BUTTON_VISIBLE', payload: false });
// editorButtonVisible 상태를 표시(true)로 변경
dispatch({ type: 'SET_EDITOR_BUTTON_VISIBLE', payload: true });
// 만약 editorRef가 현재 존재하고 에디터 인스턴스가 있는 경우,
// 첫 번째 에디터의 인스턴스에 포커스를 설정
if (editorRef.current && editorRef.current.editor) {
const editorInstance = editorRef.current.editor;
editorInstance.focus();
}
};

// 첫 번째 에디터 버튼 클릭 핸들러
const handleEditorButtonClick = () => {
setEditorButtonVisible(false);
setEditor2ButtonVisible(true);
// 두 번째 에디터에 포커스 설정
// editorButtonVisible 상태를 숨김(false)으로 변경
dispatch({ type: 'SET_EDITOR_BUTTON_VISIBLE', payload: false });
// editor2ButtonVisible 상태를 표시(true)로 변경
dispatch({ type: 'SET_EDITOR2_BUTTON_VISIBLE', payload: true });
// 만약 editor2Ref가 현재 존재하고 에디터 인스턴스가 있는 경우,
// 두 번째 에디터의 인스턴스에 포커스를 설정
if (editor2Ref.current && editor2Ref.current.editor) {
const editorInstance = editor2Ref.current.editor;
editorInstance.focus();
}
};

// 두 번째 에디터 버튼 클릭 핸들러
const handleEditor2ButtonClick = () => {
setEditor2ButtonVisible(false);
setTagButtonVisible(true);
// 태그에 포커스 설정
// editor2ButtonVisible 상태를 숨김(false)으로 변경
dispatch({ type: 'SET_EDITOR2_BUTTON_VISIBLE', payload: false });
// tagButtonVisible 상태를 표시(true)로 변경
dispatch({ type: 'SET_TAG_BUTTON_VISIBLE', payload: true });
// 만약 TagRef가 현재 존재하면 (태그 입력란이 마운트되어 있으면),해당 태그 인풋에 포커스를 설정
if (TagRef.current) {
TagRef.current.focus();
}
};

// 태그 버튼 클릭 핸들러
const handleTagButtonClick = () => {
setTagButtonVisible(false);
setReviewButtonVisible(true);
setCheckContainerVisible(true);
// tagButtonVisible 상태를 숨김(false)으로 변경
dispatch({ type: 'SET_TAG_BUTTON_VISIBLE', payload: false });
// checkContainerVisible 상태를 표시(true)로 변경
dispatch({ type: 'SET_CHECK_CONTAINER_VISIBLE', payload: true });
// reviewButtonVisible 상태를 표시(true)로 변경
dispatch({ type: 'SET_REVIEW_BUTTON_VISIBLE', payload: true });
};

// 질문 검토 버튼 클릭 핸들러
const handleReviewButtonClick = () => {
setReviewButtonVisible(false);
setCheckContainerVisible(false);
// reviewButtonVisible 상태를 숨김(false)으로 변경
dispatch({ type: 'SET_REVIEW_BUTTON_VISIBLE', payload: false });
//checkContainerVisible 상태를 숨김(false)으로 변경
dispatch({ type: 'SET_CHECK_CONTAINER_VISIBLE', payload: false });
};

// 드롭다운 상태를 관리하는 상태 변수
const [isDropdownOpen, setIsDropdownOpen] = useState(false);
// 체크박스 변경 핸들러 함수
const handleCheckboxChange = (event) => {
// 체크박스의 선택 여부를 가져옴
const checkedValue = event.target.checked;
// 리덕스 스토어에 액션을 디스패치하여 isChecked 상태를 업데이트함
dispatch({ type: 'SET_IS_CHECKED', payload: checkedValue });
};

// 드롭다운 토글 함수
const handleDropdownToggle = () => {
setIsDropdownOpen(!isDropdownOpen);
// isDropdownOpen 상태를 토글함
dispatch({ type: 'SET_IS_DROPDOWN_OPEN' });
};

return (
Expand Down Expand Up @@ -325,7 +364,6 @@ function AskQuestionPage() {
isOpen={isDropdownOpen}
onToggle={handleDropdownToggle}
/>
{/* */}
</div>
{checkContainerVisible && (
<div className="check-container">
Expand Down
Loading