Skip to content

Commit c34d100

Browse files
add users and teams search
1 parent 4a31bcd commit c34d100

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

44 files changed

+578
-106
lines changed

src/Components/Friends/FriendsList.jsx

Lines changed: 0 additions & 20 deletions
This file was deleted.

src/Components/GlobalComponents/SearchField.jsx

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,27 @@
1+
/* eslint-disable react/prop-types */
12
import searchIcon from '../../assets/images/global/searchIcon.svg'
23

3-
function SearchField() {
4+
function SearchField({setKeyWord,getSearch,setCurrent,type}) {
5+
6+
7+
const changeHandler=async(e)=>{
8+
setKeyWord(e.target.value);
9+
const resData=await getSearch();
10+
if(resData.ok && type=='users'){
11+
setCurrent(resData.data.users)
12+
}
13+
else if(resData.ok && type=='teams'){
14+
setCurrent(resData.data.teams)
15+
}
16+
17+
18+
19+
20+
}
421
return (
522
<div className="relative w-full bg-white rounded-2xl shadow-[0px_6px_20px_0px_rgba(218,218,218,0.3)] ">
623
<input
24+
onChange={changeHandler}
725
type="text"
826
placeholder="Search..."
927
className=" py-4 pl-10 pr-8 border w-full rounded-2xl outline-none border-none focus:outline-none focus:ring focus:border-blue-500"

src/Components/Home/FriendsList/FriendsList.jsx

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,8 @@ import Requests from "./Requests/Requests"
44
function FriendsList({isFixed}) {
55
return (
66
<div className="w-1/4">
7-
<div className={`w-full p-4 ${!isFixed?'':'fixed !w-1/4 top-0 transform '} `}>
7+
<div className={`w-full ${!isFixed?'':'fixed !w-1/4 top-0 transform '} `}>
88
<Requests/>
9-
<MyFriends/>
109
</div>
1110
</div>
1211

src/Components/Home/FriendsList/Requests/RequestItem.jsx

Lines changed: 15 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,20 @@
1-
import profileImg from '../../../../assets/images/home/Ellipse 64.svg'
2-
function RequestItem() {
1+
import { imgLink } from '../../../../api'
2+
import { transferDate } from '../../../../Functions/transferDate'
3+
import RespondToInvite from './RespondToInvite'
4+
function RequestItem({request}) {
35
return (
4-
<div className='flex justify-between gap-2 py-2 '>
5-
<div className='flex-grow px-4'>
6-
<h4 className='text-end text-xs mb-1'>Lincoln</h4>
7-
<div className='font-inter font-bold text-lg flex justify-between' >
8-
<button >delete</button>
9-
<button className='ml-2 p-2 rounded-xl bg-[rgba(200,174,125,1)] '>Confirm</button>
6+
<div className='flex justify-between items-center py-2 '>
7+
<div className='flex gap-4'>
8+
<img src={`${imgLink}/${request.team.imageUrl}`} alt='profile img' className='align-middle justify-self-center w-14 h-14 rounded-full'/>
9+
<div>
10+
<h5 className='font-semibold text-sm mb-3'>you are invited to join {request.team.name}</h5>
11+
<p className='text-xs'>{transferDate(request.created_at)}</p>
12+
</div>
1013
</div>
11-
</div>
12-
<img src={profileImg} alt='profile img' className='align-middle justify-self-center w-fit'/>
14+
<RespondToInvite request={request} response='accept'/>
15+
<RespondToInvite request={request} response='reject'/>
16+
17+
1318
</div>
1419
)
1520
}
Lines changed: 38 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,45 @@
1-
import RequestItem from "./RequestItem"
2-
1+
import { useEffect, useState } from "react";
2+
import { useSelector } from "react-redux";
3+
import { api } from "../../../../api";
4+
import useFetch from "../../../../CustomHooks/useFetch";
5+
import { getOptions } from "../../../../options";
6+
import RequestItem from "./RequestItem";
7+
let init=false
38
function Requests() {
9+
const {fetchApi:getJoinRequest,loading}=useFetch(`${api}/invite-requests`,getOptions,true)
10+
const user=useSelector(state=>state.auth.user)
11+
const [requests,setRequest]=useState([])
12+
useEffect(()=>{
13+
const fetchData=async()=>{
14+
const resData= await getJoinRequest()
15+
if(resData.ok && user && !init){
16+
setRequest(resData.data.invite_requests)
17+
init=true
18+
}
19+
}
20+
fetchData()
21+
},[user])
22+
if(requests.length>0)
423
return (
524
<div className="border-b-4 border-b-white">
6-
<div className="flex justify-between items-center text-inter ">
7-
<h3 className=" font-bold text-xl text-customblack">Follow-up requests</h3>
8-
<button className="text-base">View all</button>
9-
</div>
10-
<div className="flex flex-col gap-3">
11-
<RequestItem/>
12-
<RequestItem/>
13-
<RequestItem/>
25+
<div className="flex justify-between items-center pl-6 pt-9 ">
26+
<h3 className="font-bold text-xl text-mulish text-customblack">Invite to teams requests</h3>
27+
</div>
28+
<div className="flex flex-col gap-3 mt-10">
29+
{requests.map((request, index) => (
30+
<div
31+
key={index}
32+
className={`${
33+
index % 2 == 0 ? 'bg-white' : ''
34+
} p-4 rounded-md`}
35+
>
36+
<RequestItem request={request} />
1437

15-
</div>
38+
</div>
39+
))}
40+
</div>
1641
</div>
17-
)
42+
);
1843
}
1944

20-
export default Requests
45+
export default Requests;
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
/* eslint-disable react/prop-types */
2+
3+
import { api } from "../../../../api"
4+
import useFetch from "../../../../CustomHooks/useFetch"
5+
import ReactLoading from 'react-loading';
6+
import { postOptions } from "../../../../options";
7+
8+
9+
function RespondToInvite({response,request}) {
10+
const {fetchApi:respondToJoin,loading}=useFetch(`${api}/join-requests/${response}-join/${request.id}`,postOptions)
11+
12+
const clickHandler=async()=>{
13+
console.log(request.id)
14+
const resData=await respondToJoin()
15+
if(resData.ok){
16+
console.log(resData)
17+
}
18+
}
19+
const style=' py-2 px-4 rounded-xl text-sm font-medium transition-all duration-300 border-2 border-solid'
20+
return (
21+
<div className="flex">
22+
{!loading?<button onClick={clickHandler} className={response=='accept'?`bg-primary mr-[10px] text-white border-transparent ${style}
23+
hover:border-primary hover:bg-white hover:text-primary `
24+
:`bg-white text-primary border-primary ${style} hover:bg-primary
25+
hover:text-white `}>{response=='accept'?'Accept':'Reject'}</button>:
26+
<div className="element-center center-element mx-auto w-[60px]">
27+
<ReactLoading
28+
className="mx-auto"
29+
type="spin"
30+
color="#D9C6A4"
31+
height={40}
32+
width={40}
33+
/></div>
34+
35+
}
36+
37+
</div>
38+
)
39+
}
40+
41+
export default RespondToInvite

src/Components/Home/HomeSideBar/SelectionsSearch.jsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ import SearchField from '../../GlobalComponents/SearchField'
99

1010
function SelectionsSearch() {
1111
const links = [
12-
{ imgPath: FriendsImg, text: 'Friends',path:'friends' },
12+
{ imgPath: FriendsImg, text: 'Individuals',path:'individuals' },
1313
{ imgPath: MentorsImg, text: 'Mentors',path:'/mentors' },
1414
{ imgPath: TeamImg, text: 'Teams',path:'/teams' },
1515
{ imgPath: ResourcesImg, text: 'Resources', path:'/resources' },
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
/* eslint-disable react/prop-types */
2+
import { imgLink } from '../../api'
3+
import noImage from '../../assets/images/profile/no-profile-picture.svg'
4+
function Indivdual({name,img,followed,track}) {
5+
return (
6+
<div className='flex justify-between items-center'>
7+
<div className='flex items-center gap-6'>
8+
<img src={img?`${imgLink}/${img}`:noImage} alt="profile img" className='w-14' />
9+
<div>
10+
<h3 className='text-base font-semibold'>{name}</h3>
11+
<p className='text-xs font-semibold'>{track}</p>
12+
13+
</div>
14+
</div>
15+
<button className={`${followed?'bg-white !text-primary border-[1px] border-primary border-solid':'bg-primary text-white'} py-2 px-5 w-fit rounded-[10px] h-fit`}>Following</button>
16+
</div>
17+
)
18+
}
19+
20+
export default Indivdual
Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
import { useEffect, useState } from 'react'
2+
import { api } from '../../api'
3+
import useFetch from '../../CustomHooks/useFetch'
4+
import { getOptions } from '../../options'
5+
import SearchField from '../GlobalComponents/SearchField'
6+
import Indivdual from './Individual'
7+
import ReactLoading from 'react-loading';
8+
9+
10+
function IndividualsList() {
11+
const {fetchApi:getAllUsers, loading}=useFetch(`${api}/users`,getOptions,true)
12+
const [keyword,setKeyWord]=useState('')
13+
const {fetchApi:getSearch,loading:searchLoading}=useFetch(`${api}/search/users?query=${keyword}`,getOptions,true)
14+
const [currentUsers,setCurrentUsers]=useState([]);
15+
useEffect(()=>{
16+
const fetchUsers=async()=>{
17+
const resData=await getAllUsers();
18+
if(resData){
19+
setCurrentUsers(resData.data.users)
20+
}
21+
22+
}
23+
fetchUsers()
24+
25+
},[])
26+
27+
return (
28+
<>
29+
<SearchField setKeyWord={setKeyWord} getSearch={getSearch} type='users' setCurrent={setCurrentUsers}/>
30+
{(searchLoading | loading)? <div className="element-center center-element mx-auto h-full mt-10 w-[60px]"> <ReactLoading
31+
className="mx-auto"
32+
type="spin"
33+
color="#D9C6A4"
34+
height={40}
35+
width={40}
36+
/></div>:<div className='flex flex-col gap-4 w-full py-8 h-[calc(100vh_-_99px)]'>
37+
{ currentUsers.map(user=> <Indivdual key={user.id} name={user.name}
38+
img={user.imageUrl} track={user.track} followed={true}/>)}
39+
</div>}
40+
</>
41+
)
42+
}
43+
44+
export default IndividualsList
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
import { api } from "../../api"
2+
import useFetch from "../../CustomHooks/useFetch"
3+
4+
function SearcQuery(type,keyword) {
5+
const {fetchApi:setSearch,loading:searchLoading}=useFetch(`${api}/search/${type}?query=${keyword}`)
6+
return {
7+
setSearch,
8+
searchLoading
9+
}
10+
11+
}
12+
13+
export default SearcQuery
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
2+
function InviteRequestItem() {
3+
return (
4+
<div>InviteRequestItem</div>
5+
)
6+
}
7+
8+
export default InviteRequestItem
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
2+
function InviteRequests() {
3+
return (
4+
<div className="w-1/">InviteRequests</div>
5+
)
6+
}
7+
8+
export default InviteRequests

src/Components/Posts/CreatePost.jsx

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
11
import { useState } from 'react';
2-
import Profileimg from '../../assets/images/posts/Ellipse 25 (1).svg'
32
import ModalComponent from './Post/ModalComponent';
4-
5-
3+
import noPicture from '../../assets/images/profile/no-profile-picture.svg'
4+
import { useSelector } from 'react-redux';
5+
import { imgLink } from '../../api';
66

77
const CreatePost=()=> {
88
const [open, setOpen] = useState(false);
9+
const user = useSelector(state=>state.auth.user)
910

1011
const openModal=()=>{
1112
setOpen(true)
@@ -15,7 +16,7 @@ const CreatePost=()=> {
1516
}
1617
return (
1718
<> <div className='mt-[32px] mb-[50px] mb-2 element-center' >
18-
<img src={Profileimg}/>
19+
<img className='w-14 rounded-full h-14' src={user&&user.imageUrl?`${imgLink}/${user.imageUrl}`:noPicture}/>
1920

2021
<button onClick={openModal} className="text-[rgba(152,150,150,1)] text-base flex items-center text-roboto text-xl bg-white pl-11 shadow-[shadow:0px_10px_10px_0px_rgba(218,218,218,0.3)] hover:opacity-50 transition-all duration-30000 w-full rounded-2xl h-[50px]">
2122
What’s on your mind?

src/Components/Posts/Post/Post.jsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ function Post({ post }) {
3636
<div >
3737
<PostContent post={post} />
3838
<PostDetails post={post} openLikesList={setOpenLikesList} openCommentsList={()=>setOpenCommentsList(true)} likesNumber={likesDataForPost?likesDataForPost.length:0} commentsNumber={commentsDataForPost?commentsDataForPost.length:0} />
39-
<PostActions post={post} usersLikesThisPost={existedPost?existedPost.likesData:[]} />
39+
<PostActions post={post} openCommentsList={()=>setOpenCommentsList(true)} usersLikesThisPost={existedPost?existedPost.likesData:[]} />
4040
</div>
4141
{openLikesList &&<LikesList datalikes={likesDataForPost} closeLikesList={()=>setOpenLikesList(false)}/>}
4242
{openCommentsList&& <CommentList closeCommentsList={()=>setOpenCommentsList(false)} comments={commentsofPost?commentsofPost.commentsData:[]} id={post.id}/>}

src/Components/Posts/Post/PostActions/LikeButton.jsx

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,18 @@
1+
/* eslint-disable react/prop-types */
12
import { useState, useEffect } from 'react';
3+
import { useDispatch } from 'react-redux';
24
import likeIcon from '../../../../assets/images/posts/icons8-like-24 2.svg';
35
import useFetch from '../../../../CustomHooks/useFetch';
46
import { postOptions } from '../../../../options';
7+
import { fetchLikesForPost } from '../../../../store/posts/fetchLikesForPost';
8+
import { fetchPosts } from '../../../../store/posts/fetchPosts';
59

610
const user_id = 2;
711

812
function LikeButton({ post, usersLikesThisPost }) {
913
const { fetchApi: likePost } = useFetch(`http://localhost:8000/api/posts/${post.id}/like`, postOptions);
1014
const [userLikedPost, setUserLikedPost] = useState(false);
15+
const dispatch=useDispatch()
1116

1217

1318

@@ -19,6 +24,9 @@ function LikeButton({ post, usersLikesThisPost }) {
1924
const resData = await likePost();
2025
if (resData.ok) {
2126
setUserLikedPost(!userLikedPost);
27+
dispatch(fetchPosts())
28+
dispatch(fetchLikesForPost(resData.data.post_id))
29+
2230
}
2331
};
2432

src/Components/Posts/Post/PostActions/PostActions.jsx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,13 @@
1+
/* eslint-disable react/prop-types */
12
import { actions } from "./postActionsData"
23
import LikeButton from './LikeButton'
34

4-
function PostActions({post,usersLikesThisPost}) {
5+
function PostActions({post,usersLikesThisPost,openCommentsList}) {
56

67
return (
78
<div className='flex justify-between text-base font-medium py-4'>
89
<LikeButton post={post} usersLikesThisPost={usersLikesThisPost}/>
9-
{actions.map((action,index)=><button className='flex flex-row-reverse items-center gap-3' key={index}><img className="w-5" src={action.icon}/><span>{action.text}</span></button>
10-
)}
10+
<button className='flex flex-row-reverse items-center gap-3' onClick={openCommentsList} ><img className="w-5" src={actions[0].icon}/><span>{actions[0].text}</span></button>
1111
</div>
1212
)
1313
}

0 commit comments

Comments
 (0)