diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..7f80b85 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,2 @@ +* text=auto +* text eol=lf \ No newline at end of file diff --git a/frontend/src/Components/Channels.js b/frontend/src/Components/Channels.js index 5df1dd3..8bca5fc 100644 --- a/frontend/src/Components/Channels.js +++ b/frontend/src/Components/Channels.js @@ -1,16 +1,22 @@ -import { useSelector } from 'react-redux'; +import { useSelector, useDispatch } from 'react-redux'; import { PlusSquare } from 'react-bootstrap-icons'; import ChannelBtn from './ChannelBtn'; +import { openModal } from '../slices/modalSlice'; const Channels = () => { const channelsInfo = useSelector((state) => state.channelsInfo); + const dispatch = useDispatch(); const { channels } = channelsInfo; + const handleAddChannel = () => { + dispatch(openModal({ type: 'addChannel' })); + }; + return (
Каналы - diff --git a/frontend/src/Components/Layout.js b/frontend/src/Components/Layout.js index 5a26285..c1862e2 100644 --- a/frontend/src/Components/Layout.js +++ b/frontend/src/Components/Layout.js @@ -1,13 +1,15 @@ import { Link, Outlet, useLocation, Navigate, } from 'react-router-dom'; +import { useSelector } from 'react-redux'; import getRoutes from '../routes'; import useAuth from '../hook/useAuth'; -import Modal from './Modal'; +import getModal from './Modals/index'; const Layout = () => { const location = useLocation(); const { userToken } = useAuth(); + const { type } = useSelector(((state) => state.modal)); if (location.pathname === getRoutes.main() && !userToken) { return ; } @@ -19,7 +21,7 @@ const Layout = () => {
- + {getModal(type)} ); }; diff --git a/frontend/src/Components/LoginForm.js b/frontend/src/Components/LoginForm.js index ba90d02..511e0c0 100644 --- a/frontend/src/Components/LoginForm.js +++ b/frontend/src/Components/LoginForm.js @@ -26,7 +26,6 @@ const LoginForm = () => { try { setAuthFailed(false); const response = (await axios.post('/api/v1/login', values)); - console.log(response); const { data } = response; signIn(data, () => navigate(fromPage, { replace: true })); } catch (err) { diff --git a/frontend/src/Components/Modal.js b/frontend/src/Components/Modal.js deleted file mode 100644 index 8d14af1..0000000 --- a/frontend/src/Components/Modal.js +++ /dev/null @@ -1,27 +0,0 @@ -import { useSelector } from 'react-redux'; -import { Modal as Mbs } from 'react-bootstrap'; - -const getTitle = (type) => { - switch (type) { - case 'addChannel': - return 'Добавить канал'; - - default: - return 'Неизвестная модалка!!! О_О'; - } -}; - -const Modal = () => { - const { isOpened, type, extra } = useSelector((state) => state.modal); - - return ( - - - {getTitle(type)} - - {getBody(type)} - - ); -}; - -export default Modal; diff --git a/frontend/src/Components/Modals/AddChannel.js b/frontend/src/Components/Modals/AddChannel.js new file mode 100644 index 0000000..15693c3 --- /dev/null +++ b/frontend/src/Components/Modals/AddChannel.js @@ -0,0 +1,63 @@ +import { Modal, Form, Button } from 'react-bootstrap'; +import { useDispatch, useSelector } from 'react-redux'; +import { useFormik } from 'formik'; +import { + useContext, useEffect, useRef, useState, +} from 'react'; +import cn from 'classnames'; +import { modalClose } from '../../slices/modalSlice'; +import { ApiContext } from '../../hoc/ApiProvider'; + +const ModalAddChannel = () => { + const { isOpened } = useSelector((state) => state.modal); + const { sendNewChannel } = useContext(ApiContext); + const dispatch = useDispatch(); + const inputRef = useRef(); + const [inputInvalid] = useState(false); + // setInputInvalid + const handlerСlosure = () => dispatch(modalClose()); + + const formik = useFormik({ + initialValues: { + name: '', + }, + onSubmit: async (values) => { + sendNewChannel(values.name); + }, + }); + + useEffect(() => { + inputRef.current.select(); + }, []); + + return ( + + + Добавить канал + + +
+ + + Имя канала +
+ + +
+
+
+
+
+ ); +}; + +export default ModalAddChannel; diff --git a/frontend/src/Components/Modals/index.js b/frontend/src/Components/Modals/index.js new file mode 100644 index 0000000..ce59f1a --- /dev/null +++ b/frontend/src/Components/Modals/index.js @@ -0,0 +1,11 @@ +import AddChannel from './AddChannel.js'; +// import RemoveChannel from './RemoveChannel.jsx'; +// import RenameChannel from './RenameChannel.jsx'; + +const modals = { + addChannel: , + // removeChannel: RemoveChannel, + // renameChannel: RenameChannel, +}; + +export default (modalType) => modals[modalType]; diff --git a/frontend/src/assets/favicon.ico b/frontend/src/assets/favicon.ico new file mode 100644 index 0000000..40a0b25 Binary files /dev/null and b/frontend/src/assets/favicon.ico differ diff --git a/frontend/src/hoc/ApiProvider.js b/frontend/src/hoc/ApiProvider.js index 375f363..ec36793 100644 --- a/frontend/src/hoc/ApiProvider.js +++ b/frontend/src/hoc/ApiProvider.js @@ -25,9 +25,16 @@ const ApiProvider = ({ children }) => { }); }; + const sendNewChannel = (nameNewChannel) => { + socket.timeout(msTimeout).emit('newChannel', { nameNewChannel }, (err, response) => { + console.log(err, response); + }); + }; + const value = useMemo(() => ({ sendMessage, takeMessage, + sendNewChannel, }), []); return ({children}); diff --git a/frontend/src/slices/modalSlice.js b/frontend/src/slices/modalSlice.js index 5bf6eda..c31e507 100644 --- a/frontend/src/slices/modalSlice.js +++ b/frontend/src/slices/modalSlice.js @@ -13,12 +13,13 @@ export const modalSlice = createSlice({ initialState, reducers: { modalClose: (state) => { - state.isOpened = null; + state.isOpened = false; state.extra = null; state.type = null; }, openModal: (state, { payload }) => { const { type, extra } = payload; + console.log(type); state.type = type; state.extra = extra ?? null; state.isOpened = true; @@ -26,6 +27,6 @@ export const modalSlice = createSlice({ }, }); -export const { modalClose } = modalSlice.actions; +export const { modalClose, openModal } = modalSlice.actions; export default modalSlice.reducer;