Professional Documents
Culture Documents
B2 Project Report
B2 Project Report
B2 Project Report
A PROJECT REPORT
Submitted
In partial fulfillment of the requirements for
the award of the degree of
BACHELOR OF TECHNOLOGY
in
INFORMATION TECHNOLOGY
by
K.Sai Rashmika [20B01A1290] M.Geethika [20B01A1296]
Reddy Ramya
Associate Professor
DECLARATION
The work is unique and has not been submitted to a limited extent or
full for the honor of any Degree in any other University or Institute.
Place: Bhimavaram
Date:
SHRI VISHNU ENGINEERING COLLEGE FOR WOMEN
(AUTONOMOUS)
BHIMAVARAM – 534 202
DEPARTMENT OF INFORMATION TECHNOLOGY
CERTIFICATE
This is to certify that the Project Report entitled “CHATROOM HUB” that
is being submitted by K. SAI RASHMIKA REDDY [ 20B01A1290], M.
GEETHIKA RAMYA [20B01A1296], M. SRIJITHA DEVI [20B01A12B2], M.
PRANEETHA DEVI [20B01A12B3] in partial fulfillment for the award of
Bachelor of Technology in Information Technology to the Shri Vishnu
Engineering College for Women, Bhimavaram is a record of bonafide work did by
them under my supervision during the academic year 2020 - 24.
To the best of my insight, the work consolidated in this postulation has not been
submitted somewhere else for the honor of any degree.
External Examiner
DECLARATION
This project work entitled “CHATROOM HUB” has been carried out by us in the partial fulfillment of the
requirements for the award of the degree of B. Tech (IT), Shri Vishnu Engineering College for Women. I
hereby declare that this project work/ project report has not been submitted to any other University/ Institute
for the award of any other degree/ diploma.
Project Associates:
We wish to place our deep sense of gratitude to Sri. K. V. Vishnu Raju, Chairman
of SVECW for his constant support on our each and every progressive work.
We wish to express our sincere thanks to our Dr. D. Venkata Naga Raju, Head
of the Department of Information Technology of SVECW, for his valuable advice
in completing this project successfully.
We wish to thank our guide Dr. P. Venkata Rama Raju for his unflinching
devotion and valuable suggestions to complete our main project successfully in
time.
Project Associates
ensuring that every interaction is a reflection of their unique interests. Users have
chatroom engagements.
The technology stack powering the Chatroom Hub comprises ReactJS for a
responsive and intuitive user interface, Firebase for real-time data management, and
and feature-rich user experience, making the Chatroom Hub a game-changer in the
The Chatroom Hub project introduces a user experience that is deeply customizable
i
LIST OF FIGURES
Figure No. & Description Page No
3.4 Authentication 11
ii
i
LIST OF TABLES
iv
CHATROOM HUB
1. INTRODUCTION
In the digital realm, chatroom hubs emerge as dynamic centers of interaction and
community, embodying the essence of connectivity in the modern age. These platforms
offer a virtual haven where individuals from diverse backgrounds converge to share ideas,
seek advice, and forge meaningful connections. Serving as digital town squares, chatroom
hubs accommodate a myriad of interests and discussions, from niche hobbies to global
issues, transcending geographical boundaries and cultural barriers.
Within these vibrant spaces, users find solace in the anonymity afforded by screen names,
enabling authentic expression and fostering mutual respect. Chatroom hubs catalyze
innovation and collaboration, serving as incubators for new ideas and collective
intelligence. Through lively debates, brainstorming sessions, and collaborative projects,
participants harness the power of community to address complex problems and drive
positive change.
Moreover, the relationships formed within chatroom hubs often extend beyond the digital
realm, shaping real-world experiences and connections. As participants engage in
spontaneous conversations and deliberate exchanges, they cultivate a sense of belonging
and empowerment, reaffirming the intrinsic human need for connection and camaraderie
in virtual spaces. In essence, chatroom hubs epitomize the transformative potential of
online communities, where every keystroke holds the promise of insight, connection, and
shared humanity.
System Modules
User Authentication
Chatroom Creation
User Profiles
User Authentication
Chatroom Creation
A chatroom creation module facilitates the establishment of virtual spaces for real-time
User profiles
A user profiles module centralizes and manages information about individuals within a
digital system or application. It allows users to create, update, and customize their profiles
with personal details, preferences, and settings. These profiles often include user-
generated content, such as biographical information, profile pictures. The module may
offer privacy controls for users to manage the visibility of their profiles and control access
to specific information. The user profiles module serves as a cornerstone for
personalization and community building within digital platforms.
2. SYSTEM ANALYSIS
System analysis is an important activity that’s takes place when we are building a
new system or changing the existing one. Analysis helps to understand the existing
system and requirements necessary for building the new system. If there is no existing
system then analysis defines only the requirements.
One of the most important factors in the system analysis is to understand the
system and its problems. A good understanding of the system enables designer to identify
and correct problems. Based on the drawbacks of existing system is being planned. So the
total definition of the given problem has been analyzed.
Drawbacks
Due to limited flexibility, This lack of customization hinders users from organizing
and participating in discussions that align precisely with their interests, potentially
resulting in less engagement.
The absence of integration with popular platforms like Google and Facebook in the
existing system can be a drawback.
Advantages
This application creates new chatrooms and send text messages, images, and
audio clips.
It shows the status of other users whether he/she is online (or) offline and users
can like or delete the messages.
Chatroom Hub implement admin controls in chatrooms, such as the ability to add
or remove permissions.
This Interface allows users to change or upload their avatar. And to make the
application responsive.
The System Architecture is represented in fig 2.1. Initially the user will open the
application link by logging or signing in by using their Email or Facebook or Google
accounts. The User can either successfully logs into their respective account or gets an
error alert for incorrect approach. Then the User will enter into the application. The user
can edit their details like Name, avatar, and can create new chat rooms and this
information will be stored in our Realtime database. Chat room provides different
features like User status, admin permissions, sharing multi-media files and notification
settings and the users can log out of their application after completing their respective
tasks.
Types of Feasibilities
1. Technical Feasibility
2. Operational Feasibility
3. Economical Feasibility
Technical Feasibility
The system is technically feasible as we have implemented this application using
technologies like Android Studio, Firebase, and One Signal which have many inbuilt
features for developing an application.
Operational Feasibility
The system is operationally feasible as we can access this application from any
location irrespective of place and time.
Economical Feasibility
The system is economically feasible as it is developed using open sources and
free tools like Android Studio, Firebase, and One Signal which doesn’t require any
maintenance cost.
Modules
1. User Authentication
2. Chatroom Creation
3. Real Time Messaging
4. User Profiles
1. User Authentication
The User Authentication module in the chatroom hub ensures secure access to user
accounts by implementing robust login mechanisms.
Incorporating Facebook and Gmail authentication into the chatroom hub enables
users to seamlessly log in using their existing Facebook or Gmail credentials.
It securely stores user credentials using encryption techniques like hashing and
salting to prevent unauthorized access to sensitive information.
Users can register with unique usernames and strong passwords, with optional multi-
factor authentication for added security layers.
The module also manages user sessions securely, enforcing session timeouts and
employing HTTPS encryption to protect data during transmission.
2. Chatroom Creation
The chatroom creation module facilitates users in creating new chatrooms within
the platform, offering options to set room names, privacy settings, and invite participants.
Users can specify room topics, access controls, and moderation preferences, ensuring
customization according to their needs.
The module manages the creation process, assigns unique identifiers to new chatrooms,
and integrates features for administrators to monitor and moderate discussions effectively.
Through this module, users can foster communities, organize discussions, and engage with
peers in dynamic and purpose-driven chat environments.
4. User Profiles
Purpose: The main purpose for preparing this document is to give a general insight into
the analysis and requirements of the existing system or situation for determining the
operational characteristics of the system.
Scope: This document plays a vital role in the software development life cycle (SDLC)
as it describes the complete requirements of the system. It is meant for use by the
developers and will be the basis for testing the system. Any changes made to the
requirements in the future will have to go through formal change approval process.
Software Requirements
FRONT END : REACTJS
DATABASE : FIREBASE
IDE : VISUAL STUDIO CODE
OPERATING SYSTEM : Windows 11
Hardware Requirements
8GB RAM
3.3 Technologies
3.3.1 ReactJs
React.js is an open-source JavaScript library, crafted with precision by
Facebook, that aims to simplify the intricate process of building interactive
user interfaces. Imagine a user interface built with React as a collection of
components, each responsible for outputting a small, reusable piece of
HTML code.
In addition, React allows you to build applications using reusable components, similar to
independent Lego blocks, creating a modular and organized structure.
Its primary role is handling the view layer, encouraging developers to separate complex
UIs into reusable components for efficient rendering.
In 2011, Facebook created React to enhance user experience with dynamic and
responsive interfaces. Jordan Walke, a software engineer, simplified development by
introducing reusable components, starting with Facebook's newsfeed.
React facilitates single-page applications (SPAs) that load a single HTML document
initially and then update specific sections dynamically without reloading the entire page.
This client-side routing enhances performance and user experience.
React employs a virtual DOM, a copy of the actual DOM, to quickly reflect changes in
data states. By comparing and patching the virtual DOM to the actual DOM, React
efficiently updates components without reloading the entire page, resulting in fast and
dynamic UI changes.
Features in ReactJS
Features
Authentication
Firebase Authentication gives backend services, simple to-use SDKs, and instant
UI libraries to confirm clients over your application. It supports authentication using
Dept of Information Technology, SVECW Page 8
CHATROOM HUB
You can allow users to sign in to your Firebase app either by using Firebase UI as
a complete drop-in authentication solution or by using the Firebase Authentication SDK
to manually integrate one or a few sign-in techniques into your application
Fig 3.1
Firebase Dashboard
Fig 3.3 JSON Structure shows the fields present in the specific
key (Like Name, description...) of the collection (Rooms).
5. SYSTEM DESIGN
Introduction
Software design is a process of problem solving and planning for software
solutions after the purpose and specification of software are determined, software
developers will design or employ designers to develop a plan for a solution. It includes
low level component and algorithm implementation issues as well as the architectural
view.
Compatibility
The application is compatible for any android version mobiles.
Extensibility
New capabilities can be added to the application without major changes to the
underlying architecture.
Fault-Tolerance
The application is resistant to and able to recover from failure.
Maintainability
The application can be restored to a specified condition within a specified period
of time.
Modularity:
The resulting application comprises well defined, independent modules that lead
to better maintainability.
Reliability:
The application is able to perform a required function under stated conditions for
a specified period of time.
Security:
The application is able to withstand hostile acts and influences.
Table structure
We have four collections in our Realtime Database.
Messages
Profiles
Rooms
Status
Messages
author
o avatar
o createdAt
o name
o uid
createdAt
likeCount
text
Profiles
uid
o createdAt
o email
o name
Rooms
roomid
o admins
o createdAt
o description
o lastMessage
author
avatar
createdAt
name
uid
createdAt
file
contentType
name
url
likeCount
msgId
roomId
o name
Status
roomid
o last_changed
o state
Use Case diagrams are one of the five diagrams in UML for modeling the
dynamic aspects of systems. Use Case diagrams are central to modeling the behavior of a
system, a subsystem, or a class. Actors are external entities that interact with the system.
Examples of actors include users like client, administrator etc, or another system like
central database.
The step-by-step procedure that is involved in between the user and server in the below
use case diagram is:
1. Open Browser: User starts by opening a web browser.
2. Login: Then navigate to the Chatroom Hub website and enter your login credentials.
If the credentials are incorrect, you will receive an error message. Or else you will be
successfully logged into the application.
3. Profile Creation: If you’re new to Chatroom Hub, create a profile by adding a name
and avatar. You also have the option to connect your Facebook or Google accounts for
easier access and profile creation.
4. Create Chatroom: Once logged in, you can create a chatroom to start interacting with
others.
5. Send Message: Choose between sending different types of messages: text, image,
audio, document, or video. Select the type of message and upload or type the content,
then send it into the chatroom for others to view and interact with.
6. Liking a Message: You can like messages within the chatroom as a form of
interaction or acknowledgment.
7. Get Notifications from Chatrooms: You will receive notifications about new
messages or interactions within your chatrooms.
8. Logout of Application: When you’re done, you can log out of the application
securely.
The overview of the whole project through use case diagram is as follows:
Class Diagram
A class diagram shows a set of classes, interfaces, and collaborations and their
relationships. Class diagrams are used to illustrate the static design view of a system
The Fig 4.2 shows three classes: User Account, Rooms and Messages along with their
attributes and methods that they can perform.
9. Sequence Diagram
These details are stored in the Firebase database and presented back to the user. The user
can create chat rooms. The details related to the room are stored in the Firebase database
and the chatroom is added to the website. The user can send and like messages. These
Dept of Information Technology, SVECW Page 17
CHATROOM HUB
actions are stored in the Firebase database and updated in real-time on the website. When
the user signs out, this status is updated on both the website and Firebase.
This sequence diagram provides a comprehensive guide to the user interactions with a
website and Firebase for authentication, data storage, and real-time updates.
5. SYSTEM TESTING
5.1 Introduction
Testing is the process of detecting errors. Testing performs a very critical role for
quality assurance and for ensuring the reliability of software. The results of testing are
used later on during maintenance also.
Psychology of Testing
The aim of testing is often to demonstrate that a program works by showing that it
has no errors. The basic purpose of testing phase is to detect the errors that may be
present in the program. Hence one should not start testing with the intent of showing that
a program works, but the intent should be to show that a program doesn’t work. Testing
is the process of executing a program with the intent of finding the errors.
Testing Objectives
The main objective of testing is to uncover a host of errors, systematically and with
minimum effort and time. Stating formally, we can say,
Unit Testing
Unit testing focuses verification effort on the smallest unit of software i.e. the
module. Using the detailed design and the process specifications testing is done to
uncover errors within the boundary of the module. All modules must be successful in the
unit test before the start of the integration testing begins.
Link Testing
Link testing does not test software but rather the integration of each module in
system. The primary concern is the compatibility of each module. The programmer tests
where modules are designed with different parameters, length, type etc.
Integration Testing
After the unit testing we have to perform integration testing. The goal here is to
see if modules can be integrated properly, the emphasis being on testing interfaces
between modules. This testing activity can be considered as testing the design and hence
the emphasis on testing module interactions.
System Testing
Here the entire software system is tested. The reference document for this process
is the requirements document, and the goal is to see if software meets its requirements.
Here entire project has been tested against requirements of project and it is checked
whether all requirements of project have been satisfied or not.
Acceptance Testing
Acceptance Test is performed with realistic data of the client to demonstrate that
the software is working satisfactorily. Testing here is focused on external behavior of the
system; the internal logic of program is not emphasized.
4 Chatroom creation with existing Chatroom is not created and gets a Chatroom is not created and
name popup “Already exists” gets a popup “Already exists”
5 Edit the Username Username set successfully. Username set successfully.
6 Upload the new Avatar Avatar has been uploaded Avatar has been uploaded
7 User sends the Text Message Message is displayed in the Message is displayed in the
chatroom for all users to see. chatroom for all users to see.
8 User sends the Documents Documents are displayed in the Documents are displayed in the
chatroom for all users to see. chatroom for all users to see.
9 User sends the Pictures Pictures are displayed in the Pictures are displayed in the
chatroom for all users to see. chatroom for all users to see.
10 User sends the Voice Message Message is displayed in the Message is displayed in the
chatroom for all users to see. chatroom for all users to see.
11 User likes the Message Heart emoji is attached to the Heart emoji is attached to the
message. message.
12 User Logout Successfully logged out Successfully logged out
6. LAYOUT DESIGNS
Welcome page: It is the first Web Interface that appears when we enter into the Chatroom Hub
application. This page consists of Login/Signup options through Facebook, Google and Email.
Google Sign up page: When the user chooses to login through google, it provide his/her
Google accounts details like below.
Login Page: The user logs into the application by providing registered Email and password.
Fig 6.4 Starting page inside of chatroom hub with successful sign-in alert
Fig 6.5 User’s Dashboard with their name associated with their respective account
Updating Username: The user has an option to change their name by their choice from the
name that is associated with their account. It gives success alert after updating it.
Fig 6.6 Showing Success alert after updating their username in the dash board
Uploading new avatar: When user clicks on the icon with their starting initials of their
name which is a default feature if we didn’t add a avatar, it displays a window to choose an
image of formats (jpg, jpeg, png) and after fixing the image, the page appears as below figure.
Displaying updated avatar: On clicking the UPLOAD NEW AVATAR button, the new
avatar of user’s choice will be updated on their dashboard and gives a successful alert for it.
Changing Nickname: On clicking the input text box and updating the nickname
will change the nickname in the user dashboard.
Displaying created chatrooms and chats: The below figure shows a web
interface which shows different chatrooms created by different people and chats available
in each chatroom.
Fig 6.10 Displaying chats available in different chatrooms like Fitness Fusion,
Wanderlust Explorers...etc.
Dept of Information Technology, SVECW Page 26
OUTING MANAGEMENT
Liking a message: The below figure shows a message sent by Geethika was liked by
some other user in Wanderlust Explorers chatroom.
Deleting a message: The user can delete their own message that is sent in a chatroom
but doesn’t have access to delete messages sent by others.
Editing room details: Every chatroom has a admin who created it and will have access to
change name and description of the chatroom which was shown in the below figure.
Shows User profile: Every admin has access to give admin permissions to other members in
the chatroom which is shown in the below figure.
Uploading files: By clicking ‘PIN’ symbol button, we will get a dialog box as shown in the
below figure.
After Uploading files: The file will be uploaded and displayed in the chatroom as below.
The platform offers a wide array of communication tools, promoting efficient and
engaging discussions among users. The application's responsiveness across various devices
enhances accessibility, ensuring a seamless user experience. Users can tailor chatrooms to their
specific interests and needs, creating a personalized environment. Document sharing and real-
time editing capabilities facilitate collaborative projects and discussions. The Seamlessly
integrate multimedia content into conversations, making communication more dynamic and
expressive.
The project not only meets the technical requirements but also focuses on user experience
and interactivity. The incorporation of admin controls adds an additional layer of customization
and security to the chatrooms. Overall, Chatroom Hub successfully leverages cutting-edge
technologies to create a feature-rich and user-friendly communication platform.
It is not possible to develop a system that makes all the requirements of the user. User
requirements keep changing as the system is being used. Some of the future enhancements that
can be done to the system are:
As the technology emerges, it is possible to upgrade the system and can be adaptable to
desired environment.
We can allow users to customize the look and feel of their chatrooms by providing various
themes and color schemes.
We can develop an offline mode that allows users to access and interact with previously
loaded content, even without an active internet connection.
We can strengthen security measures by implementing end-to-end encryption for messages,
ensuring a higher level of privacy for users.
We can enhance accessibility features to ensure the application is usable by individuals with
disabilities, adhering to accessibility standards and guidelines.
These future enhancements aim to elevate the Chatroom Hub project by expanding its features,
improving user engagement, and adapting to emerging trends in communication and technology.
8. REFERENCES
⚫ https://en.wikipedia.org/wiki/Firebase
⚫ https://react.dev/
⚫ https://legacy.reactjs.org/docs/handling-events.html
⚫ https://firebase.google.com/
⚫ https://youtu.be/8QgQKRcAUvM?si=swrk9sZXvWMHTxM7
⚫ https://youtu.be/ad6IavyAHsQ?si=x1tXd8-SAsMcGMxD
9. APPENDIX
SAMPLE CODE :
src
components
chat-window
bottom
AttachmentBtn.js:
useEffect(()=>{
const node = selfRef.current;
loadMessages();
setTimeout(()=>{
node.scrollTop = node.scrollHeight;
},200);
return ()=>{
off(messagesRef,'value');
}
},[loadMessages]);
}
}
return admins;
});
toast.info(alertMsg, {
position: toast.POSITION.TOP_CENTER, // Align to the center
autoClose: 4000, // Auto-close the alert after 5000 milliseconds (5 seconds)
});
},[chatId])
...messages[messages.length - 2],
msgId : messages[messages.length - 2].id
}
}
if(isLast && messages.length === 1){
updates[`/rooms/${chatId}/lastMessage`] = null;
}
try{
await update(ref(database),updates);
toast.info('Message has been deleted', {
position: toast.POSITION.TOP_CENTER, // Align to the center
autoClose: 4000, // Auto-close the alert after 5000 milliseconds (5 seconds)
});
}catch(err){
return toast.error(err.message, {
position: toast.POSITION.TOP_CENTER, // Align to the center
autoClose: 4000, // Auto-close the alert after 5000 milliseconds (5 seconds)
});
}
if(file){
try{
const fileRef = await storageRef(storage,file.url);
await deleteObject(fileRef);
}catch(err){
toast.error(err.message, {
position: toast.POSITION.TOP_CENTER, // Align to the center
autoClose: 4000, // Auto-close the alert after 5000 milliseconds (5 seconds)
});
}
}
},[chatId,messages])
AudioMsgBtn.js :
setIsUploading(false);
afterUpload([file]);
}catch(err){
setIsUploading(false);
toast.error(err.message, {
position: toast.POSITION.TOP_CENTER, // Align to the center
autoClose: 4000, // Auto-close the alert after 5000 milliseconds (5 seconds)
});
}
},[afterUpload,chatId])
const onClick = useCallback(()=>{
setIsRecording(p => !p);
},[]);
return (
<InputGroup.Button onClick={onClick} disabled = {isUploading} className={isRecording ?
'animate-blink' : ''}>
<FontAwesomeIcon icon={faMicrophone} />
<ReactMic
record = {isRecording}
className = "d-none"
onStop = {onUpload}
mimeType = "audio/mp3"
/>
</InputGroup.Button>
)
}
index.js :
function assembleMessage(profile,chatId){
return{
Dept of Information Technology, SVECW Page 38
OUTING MANAGEMENT
roomId : chatId,
author : {
name : profile.name,
uid : profile.uid,
createdAt : profile.createdAt,
...(profile.avatar ? {avatar : profile.avatar} : {})
},
createdAt : serverTimestamp(),
likeCount : 0
}
}
setIsLoading(false);
toast.error(err.message, {
position: toast.POSITION.TOP_CENTER,
autoClose: 2000,
});
}
})
const lastMsgId = Object.keys(updates).pop();
updates[`/rooms/${chatId}/lastMessage`] = {
...updates[lastMsgId],
msgId : lastMsgId,
};
try{
await update(ref(database), updates);
setIsLoading(false);
}catch(err){
setIsLoading(false);
toast.error(err.message, {
position: toast.POSITION.TOP_CENTER,
autoClose: 2000,
});
}
},[chatId,profile])
return (
<div>
<InputGroup style={{width : "66%"}}>
<AttachmentBtnModal afterUpload={afterUpload}/>
<AudioMsgBtn afterUpload={afterUpload}/>
<Input name='chat' placeholder='Write new messages here.....' value = {input}
onChange={onInputChange} onKeyDown={onKeyDown} style={{width:"66%",color: 'black',
fontWeight: 'bolder' }}/>
<InputGroup.Button title="Send Message" color='blue' appearance='primary'
onClick={onSendClick} disabled={isLoading}>
<SendIcon />
</InputGroup.Button>
</InputGroup>
<ToastContainer />
</div>
);
};
messages
IconBtnControl.js :
ImgBtnModal.js :
index.js :
},[loadMessages,limit]);
useEffect(()=>{
const node = selfRef.current;
loadMessages();
setTimeout(()=>{
node.scrollTop = node.scrollHeight;
},200);
return ()=>{
off(messagesRef,'value');
}
},[loadMessages]);
if(!msg.likes){
msg.likes = {};
}
msg.likes[uid] = true;
alertMsg = 'Like added';
}
}
return msg;
});
toast.info(alertMsg, {
position: toast.POSITION.TOP_CENTER, // Align to the center
autoClose: 4000, // Auto-close the alert after 5000 milliseconds (5 seconds)
});
},[]);
await deleteObject(fileRef);
}catch(err){
toast.error(err.message, {
position: toast.POSITION.TOP_CENTER, // Align to the center
autoClose: 4000, // Auto-close the alert after 5000 milliseconds (5 seconds)
});
}
}
},[chatId,messages])
MessageItem.js
return (
<li className={`padded mb-1 cursor-pointer ${isHovered ? 'bg-black-02' : ''}`}
ref={selfRef}>
<div className='d-flex align-items-center font-bolder mb-1'>
<PresenceDot uid = {author.uid}/>
Dept of Information Technology, SVECW Page 47
OUTING MANAGEMENT
</div>
</li>
)
}
ProfileInfoBtn.js :
return (
<>
<Button {...btnProps} onClick={open} >
{shortName}
</Button>
<Modal open = {isOpen} onClose = {close}>
<Modal.Header>
<Modal.Title>{shortName} profile</Modal.Title>
</Modal.Header>
<Modal.Body className='text-center'>
<ProfileAvatar src = {avatar} name = {name} className = "width-200 height-200 img-
fullsize font-huge"/>
<h4 className='mt-2'>{name}</h4>
<p>Member since {memberSince}</p>
</Modal.Body>
<Modal.Footer>
{children}
<Button block onClick={close}>Close</Button>
</Modal.Footer>
</Modal>
</>
)
}
top
EditRoomBtnDrawer.js :
</Drawer.Body>
</Drawer>
<ToastContainer/>
</div>
)
}
index.js :
RoomInfoBtnModel.js :
dashboard
AvatarUploadBtn.js:
setIsLoading(false);
toast.success('Avatar has been uploaded', {
position: toast.POSITION.TOP_CENTER,
autoClose: 2000,
});
}catch(err){
setIsLoading(false);
toast.error(`Error: ${err.message}`, {
position: toast.POSITION.TOP_CENTER,
autoClose: 2000,
});
}
}
return (
<div className='mt-3 text-center'>
<ProfileAvatar src = {profile.avatar} name = {profile.name} className = "width-200 height-
200 img-fullsize font-huge"/>
Dept of Information Technology, SVECW Page 54
OUTING MANAGEMENT
<div>
<label htmlFor='avatar-upload' className='d-block cursor-pointer padded'>
Select new avatar
<input id='avatar-upload' type="file" className='d-none' accept={fileInputTypes}
onChange={onFileInputChange}/>
</label>
<Modal open={isOpen} onClose={close}>
<Modal.Header>
<Modal.Title>Adjust and upload new avatar</Modal.Title>
</Modal.Header>
<Modal.Body>
<div className='d-flex justify-content-center align-items-center h-100'>
{
image &&
<AvatarEditor
ref = {avatarEditorRef}
image={image}
width={200}
height={200}
border={10}
borderRadius={100}
rotate={0}
/>
}
</div>
</Modal.Body>
<Modal.Footer>
<Button appearance='ghost' block onClick = {onUploadClick} disabled =
{isLoading}>Upload new avatar</Button>
</Modal.Footer>
</Modal>
</div>
</div>
)
}
DashboardToggle.js:
}, [close]);
useEffect(() => {
const handleBeforeUnload = () => {
updateStatus();
};
window.addEventListener('beforeunload', handleBeforeUnload);
return () => {
window.removeEventListener('beforeunload', handleBeforeUnload);
};
}, [updateStatus]);
return (
<>
index.js:
};
return (
<>
{console.log("profile",profile)}
<Drawer.Header>
<Drawer.Title>
Dashboard
</Drawer.Title>
</Drawer.Header>
<Drawer.Body style={{
margin: 0,
padding: 0,
}}>
<h3>Hey, {profile.name}</h3>
<ProviderBlock/>
<Divider/>
<EditableInput initialValue = {profile.name} onSave = {onSave} label = {<h6
className='mb-2'>Nickname</h6>} name = "nickname"/>
<AvatarUploadBtn/>
<Button block color='red' appearance='primary' style={{ position: 'absolute', bottom: '0'}}
onClick={onSignOut} >
Sign Out
</Button>
</Drawer.Body>
</>
)
}
ProviderBlock.js:
}catch(error){
toast.error(`Error: ${error.message}`, {
position: toast.POSITION.TOP_CENTER,
autoClose: 3000,
});
}
}
const unlinkGoogle = () => {
unlinking('google.com');
}
const unlinkFacebook = () => {
unlinking('facebook.com');
}
const link = async(provider) => {
try{
await linkWithPopup(auth.currentUser, provider);
toast.success(`Linked to ${provider.providerId}`, {
position: toast.POSITION.TOP_CENTER,
autoClose: 3000,
});
Dept of Information Technology, SVECW Page 59
OUTING MANAGEMENT
updateIsConnected(provider.providerId,true);
}catch(error){
toast.error(`Error: ${error.message}`, {
position: toast.POSITION.TOP_CENTER,
autoClose: 3000,
});
}
}
const linkGoogle = () => {
const googleProvider = new GoogleAuthProvider();
link(googleProvider);
}
const linkFacebook = () => {
const facebookProvider = new FacebookAuthProvider();
link(facebookProvider);
}
return (
<div>
{
isConnected["google.com"] &&
<Tag color='green' closable onClose={unlinkGoogle}>
<FaGoogle/> Connected
</Tag>
}
{
isConnected["facebook.com"] &&
<Tag color='blue' closable onClose={unlinkFacebook}>
<FacebookOfficialIcon/> Connected
</Tag>
}
<div className='mt-2'>
{
!isConnected["google.com"] &&
<Button block color='green' appearance='primary' onClick={linkGoogle}>
<FaGoogle/> Link To Google
</Button>
}
{
!isConnected["facebook.com"] &&
<Button block color='blue' appearance='primary' onClick={linkFacebook}>
<FacebookOfficialIcon/> Link To Facebook
</Button>
}
</div>
</div>
)
Dept of Information Technology, SVECW Page 60
OUTING MANAGEMENT
rooms
ChatRoomList.js:
return (
<div>
<Nav
appearance="subtle"
vertical
reversed
className="overflow-y-scroll custom-scroll"
activeKey={location.pathname}
>
{!rooms && (
<Loader
center
vertical
content="Loading..."
speed="slow"
size="md"
/>
)}
{rooms &&
rooms.length > 0 &&
rooms.map((room) => (
<Nav.Item key={room.id} as={Link} to={`/chat/${room.id}`} eventKey = {`/chat/$
{room.id}`}>
<RoomItem
id={room.id}
name={room.name}
createdAt={room.createdAt}
lastMessage={room.lastMessage}
/>
</Nav.Item>
))}
</Nav>
</div>
);
};
RoomItem.js:
</div>
</div>
);
};
CreateRoomBtnModel.js:
const Textarea = React.forwardRef((props, ref) => <Input {...props} as="textarea" ref={ref} />);
const INITIAL_FORM = {
name : "",
description : ""
}
setFormValue(value);
},[]);
const onSubmit = async() => {
if(!formRef.current.check()){
return;
}
setIsLoading(true);
const newRoomdata = {
...formValue,
createdAt : serverTimestamp(),
admins : {
[auth.currentUser.uid] : true,
}
}
try{
const roomsRef = await ref(database, 'rooms');
const newRoomRef = push(roomsRef);
await set(newRoomRef, newRoomdata);
setIsLoading(false);
setFormValue(INITIAL_FORM);
close();
}catch(error){
setIsLoading(false);
toast.error(`Error: ${error.message}`, {
position: toast.POSITION.TOP_CENTER,
autoClose: 3000,
});
}
}
return (
<div className='mt-1'>
<Button block color='green' appearance='primary' onClick = {open}>
<CreativeIcon/> Create new chat room
</Button>
<Modal open = {isOpen} onClose = {close}>
<Modal.Header>
<Modal.Title>
New chat room
Dept of Information Technology, SVECW Page 64
OUTING MANAGEMENT
</Modal.Title>
</Modal.Header>
<Modal.Body>
<Form fluid onChange = {onFormChange} formValue = {formValue} model = {model}
ref={formRef}>
<Form.Group>
<Form.ControlLabel>Room name</Form.ControlLabel>
<Form.Control name = "name" placeholder = 'Enter chat room
name.....'></Form.Control>
</Form.Group>
<Form.Group>
<Form.ControlLabel>Description</Form.ControlLabel>
<Form.Control rows={5} name="description" accepter={Textarea} placeholder =
'Enter room description'></Form.Control>
</Form.Group>
</Form>
</Modal.Body>
<Modal.Footer>
<Button block appearance='primary' onClick = {onSubmit} disabled = {isLoading}>
Create new chat room
</Button>
</Modal.Footer>
</Modal>
<ToastContainer />
</div>
)
}
EditableInput.js:
if(trimmed != initialValue){
await onSave(trimmed);
}
setIsEditable(false);
}
return (
<div className={wrapperClassName}>
{label}
<InputGroup>
<Input {...inputProps} disabled = {!isEditable} placeholder={placeholder} value = {input}
onChange={onInputChange}/>
<InputGroup.Button onClick={onEditClick}>
{
isEditable ? <CloseIcon /> : <EditIcon />
}
</InputGroup.Button>
{isEditable &&
<InputGroup.Button onClick={onSaveClick}>
<CheckIcon/>
</InputGroup.Button>}
</InputGroup>
</div>
)
}
PresenceDot.js:
if(!presence){
return "Unknown state";
}
return presence.state === 'online' ? 'Online' : `Last online ${new
Date(presence.last_changed).toLocaleDateString()}`;
}
PrivateRoute.js:
ProfileAvatar.js :
PublicRoute.js :
Sidebar.js:
import '../styles/main.scss';
Context
current-room.context.js:
ProfileContext.js:
const isOnlineForDatabase = {
state: 'online',
last_changed: serverTimestamp(),
};
useEffect(() => {
let userRef = null;
let userStatusRef;
if (data) {
const { name, createdAt,avatar } = data;
console.log(name, createdAt);
const userData = {
name: name,
createdAt: createdAt,
avatar : avatar,
email: user.email,
Dept of Information Technology, SVECW Page 71
OUTING MANAGEMENT
uid: user.uid,
};
setProfile(userData);
console.log("username in pc"+" "+userData.name)
}else {
setProfile(null);
}
setIsLoading(false);
});
return () => {
unsub();
const connectedRef = ref(database, '.info/connected');
off(connectedRef);
if (userRef) {
off(userRef);
}
if(userStatusRef){
off(userStatusRef);
}
};
}, []);
Dept of Information Technology, SVECW Page 72
OUTING MANAGEMENT
return(
<div>
<ProContext.Provider value = {{profile,isLoading}}>
{children}
</ProContext.Provider>
</div>
)
}
rooms.context.js:
misc
custom-hooks.js:
return {isOpen,open,close}
}
useEffect(() => {
const queryList = window.matchMedia(query);
setMatches(queryList.matches);
queryList.addEventListener('change', listener);
return () => queryList.removeEventListener('change', listener);
}, [query]);
return matches;
};
off(userStatusRef);
}
}, [uid]);
return presence;
}
firebase.js :
const config = {
apiKey: "AIzaSyATBnXZ-u9eC0AeOPPPiRO_mebvGcRSGrI",
authDomain: "chatroomhub-5ffa3.firebaseapp.com",
databaseURL: "https://chatroomhub-5ffa3-default-rtdb.asia-southeast1.firebasedatabase.app",
projectId: "chatroomhub-5ffa3",
storageBucket: "chatroomhub-5ffa3.appspot.com",
messagingSenderId: "600693016942",
appId: "1:600693016942:web:5812a2d907226b26db197f"
};
export { auth,database,storage };
helper.js :
return updates;
}
Dept of Information Technology, SVECW Page 76
OUTING MANAGEMENT
Pages
Home
Chat.js:
return (
<CurrentRoomProvider data = {currentRoomData}>
<div className='chat-top'>
<ChatTop/>
</div>
<div className='chat-middle'>
<Messages/>
</div>
<div className='chat-bottom' style={{ position: 'fixed', bottom: 0, width: '100%' }}>
<ChatBottom/>
</div>
</CurrentRoomProvider>
)
}
index.js:
useEffect(() => {
const handleResize = () => {
setIsDesktop(window.innerWidth > 768); // Adjust the threshold as needed
};
Dept of Information Technology, SVECW Page 78
OUTING MANAGEMENT
return(
<div >
<RoomsProvider>
<Grid fluid className='h-100'>
<Row className='h-100'>
{canRenderSidebar &&
(<Col xs = {24} md = {8} className='h-100'>
<Sidebar/>
</Col>
)}
<Routes>
<Route path='/chat/:chatId' element={
<React.Fragment>
<Col xs={24} md={16} className='h-100'>
{console.log("hello in chat application")}
<Chat />
</Col>
</React.Fragment>
}/>
<Route path='/' element={
<React.Fragment>
{
isDesktop && (<Col xs = {24} md = {16} className='h-100'>
<h6 className='text-center mt-page'>Please Select Chat</h6>
</Col>
)}
</React.Fragment>
}/>
</Routes>
</Row>
</Grid>
</RoomsProvider>
</div>
)
Dept of Information Technology, SVECW Page 79
OUTING MANAGEMENT
logins
InputControl
InputControl.js :
InputControl.css :
.container{
display: flex;
flex-direction: column;
gap: 8px;
}
.container label{
font-weight: 500;
font-size: 1rem;
color: #4b4b4b;
}
.container input{
border-radius: 5px;
border: 1px solid #eee;
outline: none;
padding: 10px 15px;
color: #000;
}
.container input:hover{
Dept of Information Technology, SVECW Page 80
OUTING MANAGEMENT
border-color:#ccc ;
}
.container input:focus{
border-color:#9900ff ;
}
Login
Login.js:
const[errorMsg,setErrorMsg] = useState("");
const[submitButtonDisabled,setSubmitButtonDisabled] = useState(false);
await set(userRef, {
name: user.displayName,
email: user.email,
createdAt: serverTimestamp(),
});
}
navigate("/");
}).catch((err)=>{
setSubmitButtonDisabled(false)
setErrorMsg(err.message);
})
}
return (
<div className={styles.container}>
<div className={styles.innerBox}>
<h1 className={styles.heading}>Login</h1>
<InputControl label = "Email" placeholder = "Enter email address"
onChange={(event)=>
setValues((prev)=>({...prev,email:event.target.value}))
}/>
<InputControl label = "Password" placeholder = "Enter password"
onChange={(event)=>
setValues((prev)=>({...prev,pass:event.target.value}))
}/>
<div className={styles.footer}>
<b className={styles.error}>{errorMsg}</b>
<button onClick={handleSubmission}
disabled={submitButtonDisabled}>Login</button>
<p>Already have an account?{" "}
<span><Link to = "/signin">LogOut</Link></span>
</p>
</div>
</div>
</div>
)
}
LogIn.module.css:
.container{
height: 100%;
min-height: 100vh;
width: 100%;
background:linear-gradient(to right,#9900ff,#cc80ff);
Dept of Information Technology, SVECW Page 82
OUTING MANAGEMENT
display:flex;
justify-content: center;
align-items: center;
}
.innerBox{
min-width: 480px;
height: fit-content;
width: fit-content;
background-color: #fff;
box-shadow: 1px 1px 4px rgba(0,0,0,0.2);
padding: 30px;
border-radius: 10px;
display: flex;
flex-direction: column;
gap: 30px;
}
.footer{
display: flex;
flex-direction: column;
gap: 20px;
}
.footer.error{
font-weight: bold;
flex-direction: column;
gap: 20px;
color: #ff3300;
text-align: center;
}
.footer button{
outline: none;
border: none;
background-color: #9900ff;
color: #fff;
border-radius: 5px;
font-weight: bold;
font-size: 1rem;
padding: 10px 16px;
width: 100%;
transition: 100ms;
}
.footer button:disabled{
background-color: gray !important;
}
.footer button:hover{
background-color: #aa2aff;
Dept of Information Technology, SVECW Page 83
OUTING MANAGEMENT
}
.footer p{
font-weight: 700;
color: #000;
}
.footer p span a{
font-weight: bold;
color: #9900ff;
letter-spacing: 1px;
font-size: 1rem;
text-decoration: none;
}
SignUp
SignUp.js:
const[errorMsg,setErrorMsg] = useState("");
const[submitButtonDisabled,setSubmitButtonDisabled] = useState(false);
console.log(values);
createUserWithEmailAndPassword(auth,values.email,values.pass).then(async(res) => {
setSubmitButtonDisabled(false);
const user = res.user;
await updateProfile(user,{
displayName : values.name
});
setErrorMsg("");
}).catch((err)=>{
setSubmitButtonDisabled(false)
setErrorMsg(err.message);
})
}
return (
<div className={styles.container}>
<div className={styles.innerBox}>
<h1 className={styles.heading}>SignUp</h1>
<InputControl label = "Name" placeholder = "Enter your name" onChange={(event)=>
setValues((prev)=>({...prev,name:event.target.value}))
}/>
<InputControl label = "Email" placeholder = "Enter email address" onChange={(event)=>
setValues((prev)=>({...prev,email:event.target.value}))
}/>
<InputControl label = "Password" placeholder = "Enter password" onChange={(event)=>
setValues((prev)=>({...prev,pass:event.target.value}))
}/>
<div className={styles.footer}>
<b className={styles.error}>{errorMsg}</b>
<button onClick={handleSubmission} disabled =
{submitButtonDisabled}>SignUp</button>
<p>Already have an account?{" "}
<span><Link to = "/login">LogIn</Link></span>
</p>
</div>
</div>
</div>
)
}
SignUp.module.css:
.container{
height: 100%;
min-height: 100vh;
width: 100%;
background:linear-gradient(to right,#9900ff,#cc80ff);
display:flex;
justify-content: center;
align-items: center;
}
.innerBox{
min-width: 480px;
height: fit-content;
width: fit-content;
background-color: #fff;
box-shadow: 1px 1px 4px rgba(0,0,0,0.2);
padding: 30px;
border-radius: 10px;
display: flex;
flex-direction: column;
gap: 30px;
}
.footer{
display: flex;
flex-direction: column;
gap: 20px;
}
.footer.error{
font-weight: bold;
flex-direction: column;
gap: 20px;
color: #ff3300;
text-align: center;
}
.footer button{
outline: none;
border: none;
background-color: #9900ff;
color: #fff;
border-radius: 5px;
Dept of Information Technology, SVECW Page 86
OUTING MANAGEMENT
font-weight: bold;
font-size: 1rem;
padding: 10px 16px;
width: 100%;
transition: 100ms;
}
.footer button:disabled{
background-color: gray !important;
}
.footer button:hover{
background-color: #aa2aff;
}
.footer p{
font-weight: 700;
color: #000;
}
.footer p span a{
font-weight: bold;
color: #9900ff;
letter-spacing: 1px;
font-size: 1rem;
text-decoration: none;
}
Logins.css:
.app-container {
margin: 20px;
}
.top-right-buttons {
display: flex;
justify-content: flex-end;
}
.button1{
width: auto;
margin-top: 7px;
margin-right: 20px;
padding: 5px 10px;
cursor: pointer;
color: rgb(2, 2, 24);
font-weight: bolder;
font-size: larger;
font-family: 'Gill Sans', 'Gill Sans MT', Calibri, 'Trebuchet MS', sans-serif;
Dept of Information Technology, SVECW Page 87
OUTING MANAGEMENT
background-color: white;
border: 2px solid rgb(2, 2, 24);
border-radius: 25px;
}
.button2 {
margin-top: 7px;
margin-right: 13px;
padding: 5px 10px;
cursor: pointer;
color: rgb(2, 2, 24);
font-weight: bolder;
font-size: larger;
font-family: 'Gill Sans', 'Gill Sans MT', Calibri, 'Trebuchet MS', sans-serif;
background-color: white;
border: 2px solid rgb(2, 2, 24);
border-radius: 25px;
}
.button1:hover {
background-color: black;
color: white;
border: 2px solid white;
border-radius: 25px;
}
.button2:hover {
background-color: black;
color: white;
border: 2px solid white;
border-radius: 25px;
}
NavigateButtons.js:
// buttonface
const theme = {
'b': {
default: 'White',
hover: 'Azure', // Change this to the desired hover color
Dept of Information Technology, SVECW Page 88
OUTING MANAGEMENT
},
};
&:before {
content: '';
position: absolute;
width: 100%;
height: 0.8px; /* Set the thickness of the underline */
bottom: 0;
left: 0;
background-color: Darkgreen; /* Set the color of the underline */
transform: scaleX(0); /* Initially hide the underline */
transform-origin: bottom right;
transition: transform 0.4s ease-out;
}
&:hover{
color: DarkGreen;
}
&:hover:before {
transform: scaleX(1); /* Show the underline on hover */
transform-origin: bottom left;
}
}
`;
// &:hover {
// background-color: ${props => theme[props.theme].hover};
// color: Dimgray;
// border-radius: 20px;
Dept of Information Technology, SVECW Page 89
OUTING MANAGEMENT
// }
// opacity: 1;
// border-color: Dimgray;
// box-shadow: 3px 3px 2px ;
// Dimgray
//lightgrey
const ButtonGroup = styled.div`
display: flex;
justify-content: flex-en;
position: absolute;
top:10px;
right: 10px;
`;
Button.defaultProps = {
theme: 'b',
};
SignIn.js:
};
return(
<div>
<NavigateButtons/>
<Container>
<Grid className='mt-page'>
<Row>
<Col xs = {24} md = {12} mdOffset={6}>
<Panel>
<div className = "text-center">
<h2>Welcome To Chat</h2>
<p>Progressive chat platform for neophytes</p>
</div>
<div className='mt-3'>
<Button block color = "blue" appearance = "primary" startIcon =
{<FacebookOfficialIcon style={{ fontSize: '2em' }}/>} onClick={onFacebookSignIn}>
Continue with facebook
</Button>
<Button block color = "green" appearance = "primary"
startIcon={<FaGoogle style={{ fontSize: '1.5em' }} />} onClick={onGoogleSignIn}>
Continue with google
</Button>
</div>
</Panel>
</Col>
</Row>
</Grid>
</Container>
<ToastContainer />
</div>
)
}
styles
main.scss:
@import 'override';
@import 'utility';
@import 'utility_colors';
body {
margin: 0;
// font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', 'Oxygen',
// 'Ubuntu', 'Cantarell', 'Fira Sans', 'Droid Sans', 'Helvetica Neue',
// sans-serif;
font-family: 'Poppins', sans-serif;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
// background-image: url('');
// background-repeat: no-repeat;
// background-size: cover;
background-color: #1a1d22;
}
html,
body,
#root,
#root > div {
height: 100%;
}
.overflow-y-scroll {
overflow-y: auto;
}
.custom-scroll {
/* Customize the scrollbar appearance */
scrollbar-width: thin;
scrollbar-color: #ccc #f0f0f0;
height: calc(100% - 108px);
&::-webkit-scrollbar-thumb {
background-color: #ccc;
border-radius: 4px;
}
&::-webkit-scrollbar-track {
background-color: #f0f0f0;
}
}
.room-item {
Dept of Information Technology, SVECW Page 93
OUTING MANAGEMENT
display: flex;
flex-direction: column; /* Ensures the children stack vertically */
}
.time-ago {
margin-left: 290px !important;
}
.chat-room-list-wrapper {
height: 100%;
}
.img-fullsize {
*{
width: auto !important;
height: auto !important;
}
}
.chat-top,
.chat-middle,
.chat-bottom {
margin: 0;
padding: 0;
}
.chat-top,
.chat-bottom {
display: flex;
flex-direction: column;
justify-content: center;
}
$chat-t: 75px;
$chat-b: 65px;
.chat-top {
height: $chat-t;
}
.chat-bottom {
height: $chat-b;
}
.chat-middle {
height: calc(100% - #{$chat-t} - #{$chat-b});
Dept of Information Technology, SVECW Page 94
OUTING MANAGEMENT
.msg-list {
padding: 0;
margin: 0;
height: 100%;
overflow-y: auto;
list-style-type: none;
li {
&:last-child {
margin-bottom: 0 !important;
padding-bottom: 0 !important;
}
}
}
.animate-blink {
animation: blink normal 1.5s infinite ease-in-out;
color: red !important;
@keyframes blink {
0% {
opacity: 1;
}
50% {
opacity: 0.3;
}
100% {
opacity: 1;
}
}
}
#chat-container {
max-width: 400px;
margin: auto;
padding: 20px;
border: 1px solid #ccc;
border-radius: 5px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
}
#chat-input {
width: 70%;
padding: 8px;
margin-right: 8px;
Dept of Information Technology, SVECW Page 95
OUTING MANAGEMENT
#send-button {
padding: 8px;
border: 1px solid #4CAF50;
background-color: #4CAF50;
color: white;
border-radius: 4px;
cursor: pointer;
}
.lucky1{
overflow: hidden;
}
.lucky2{
display: inline-block;
visibility: visible;
}
.input-container {
display: flex;
}
.input-container > * {
flex: 1;
}
.rs-input-group{
width: 66%;
}
override.scss:
.rs-drawer-body {
margin: 20px;
}
.rs-input[disabled] {
color: #575757;
}
.rs-modal {
Dept of Information Technology, SVECW Page 96
OUTING MANAGEMENT
max-width: 100%;
padding-left: 10px;
padding-right: 10px;
}
.rs-modal-body {
padding-top: 5px;
padding-bottom: 5px;
margin-top: 10px;
margin-bottom: 10px;
min-height: 250px;
}
textarea.rs-input {
min-width: 160px;
min-height: 35px;
}
.rs-popover {
max-height: 70vh;
min-width: 300px;
overflow-y: auto;
}
.w-100 {
.rs-uploader-trigger-btn {
width: 100%;
}
}
.rs-notification-item-wrapper {
@media screen and (max-width: 450px) {
max-width: 300px;
}
}
utility_colors.scss:
.text-green {
color: #4caf50;
}
.text-blue {
color: #2196f3 ;
}
.text-black {
color: #10110f !important;
}
.text-white {
color: #d2d5cc;
}
.text-red {
color: red;
}
.text-black-45 {
// color: rgba(0, 0, 0, 0.45);
color: #d2d5cc;
}
.text-black-70 {
// color: rgba(0, 0, 0, 0.7);
color: #d2d5cc;
}
.border-green {
border: 3px solid rgb(17, 255, 17);
}
.img-b {
border: 3px solid rgb(16, 82, 0);
border-radius: 5px;
}
.bg-black-02 {
background-color: rgba(0, 0, 0, 0.02);
}
.bg-black-01 {
background-color: #22252a;
}
.rs-avatar-image {
position: inherit;
}
.text-wrap {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
utility.scss:
$indent_1: 5px;
$indent_2: 10px;
$indent_3: 15px;
.link-unstyled {
&,
&:visited,
&:hover,
&:active,
&:focus,
&:active:hover {
text-decoration: none;
}
}
.text-center {
text-align: center;
}
.text-right {
text-align: right;
}
.text-disappear {
white-space: nowrap !important;
text-overflow: ellipsis !important;
overflow: hidden !important;
}
.overflow-y-scroll {
overflow-y: scroll;
}
.width-250 {
width: 250px;
}
.width-200 {
width: 200px;
Dept of Information Technology, SVECW Page 99
OUTING MANAGEMENT
.height-150 {
height: 150px;
}
.width-150 {
width: 150px;
}
.height-200 {
height: 200px;
}
.height-220 {
height: 220px;
}
.h-100 {
height: 100%;
}
.w-100 {
width: 100%;
}
.mw-100 {
max-width: 100%;
}
.mh-100 {
max-height: 100%;
}
.w-auto {
width: auto;
}
.h-auto {
height: auto;
}
.d-none {
display: none;
}
.d-inline-block {
display: inline-block;
Dept of Information Technology, SVECW Page
100
OUTING MANAGEMENT
.d-block {
display: block;
}
.d-flex {
display: flex;
}
.d-inline-flex {
display: inline-flex;
}
.flex-column {
flex-direction: column;
}
.flex-wrap {
flex-wrap: wrap;
}
.align-items-center {
align-items: center;
}
.justify-content-between {
justify-content: space-between;
}
.justify-content-center {
justify-content: center;
}
.padded {
padding: 10px;
}
.cursor-pointer {
&:hover {
cursor: pointer;
}
}
.ws-nowrap {
white-space: nowrap;
Dept of Information Technology, SVECW Page
101
OUTING MANAGEMENT
.br-circle {
border-radius: 50%;
}
.font-bolder {
font-weight: 500;
}
.font-normal {
font-weight: 400;
}
.italic {
font-style: italic;
}
.word-break-all {
word-break: break-all;
}
.font-huge {
font-size: 100px;
}
.font-small {
font-size: 17px;
}
.contain-scroll {
overscroll-behavior: contain;
}
.mx-auto {
margin-left: auto;
margin-right: auto;
}
.px-0 {
padding-left: 0;
padding-right: 0;
}
.p-0 {
padding: 0;
}
Dept of Information Technology, SVECW Page
102
OUTING MANAGEMENT
.m-0 {
margin: 0;
}
.mt-page {
margin-top: 150px;
}
.mt-1 {
margin-top: $indent_1;
}
.mt-2 {
margin-top: $indent_2;
}
.mt-3 {
margin-top: $indent_3;
}
.mb-1 {
margin-bottom: $indent_1;
}
.mb-2 {
margin-bottom: $indent_2;
}
.mb-3 {
margin-bottom: $indent_3;
}
.ml-1 {
margin-left: $indent_1;
}
.ml-2 {
margin-left: $indent_2;
}
.ml-3 {
margin-left: $indent_3;
}
.mr-1 {
Dept of Information Technology, SVECW Page
103
OUTING MANAGEMENT
margin-right: $indent_1;
}
.mr-2 {
margin-right: $indent_2;
}
.mr-3 {
margin-right: $indent_3;
}
.pt-1 {
padding-top: $indent_1;
}
.pt-2 {
padding-top: $indent_2;
}
.pt-3 {
padding-top: $indent_3;
}
.pb-1 {
padding-bottom: $indent_1;
}
.pb-2 {
padding-bottom: $indent_2;
}
.pl-1 {
padding-left: 0.5rem;
}
.pr-4 {
padding-right: 1rem;
}
.op-color {
color: rgb(141, 141, 141);
opacity: 0.6;
}
.bg-c-grey {
background-color: #17141d;
}
App.css:
.App {
text-align: center;
}
.App-logo {
height: 40vmin;
pointer-events: none;
}
.App-header {
background-color: #282c34;
min-height: 100vh;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
font-size: calc(10px + 2vmin);
color: white;
}
.App-link {
color: #61dafb;
}
@keyframes App-logo-spin {
from {
transform: rotate(0deg);
}
to {
transform: rotate(360deg);
}
}
Dept of Information Technology, SVECW Page
105
OUTING MANAGEMENT
App.js:
import './styles/main.scss';
import 'rsuite/dist/rsuite.min.css';
import './App.css';
import {BrowserRouter as Router,Routes,Route} from 'react-router-dom';
import PrivateRoute from './components/PrivateRoute';
import PublicRoute from './components/PublicRoute';
import { ProfileContext } from './context/ProfileContext';
import LogIn from './pages/logins/LogIn/LogIn';
import SignUp from './pages/logins/SignUp/SignUp';
import Home from './pages/Home/index';
function App() {
return (
<div>
<Router>
<ProfileContext>
<Routes>
<Route path = "/signin" element = {<PublicRoute />}/>
<Route path = "/" element = {<PrivateRoute />}/>
<Route path = "/login" element = {<LogIn />}/>
<Route path = "/signup" element = {<SignUp />}/>
<Route path = "*" element={<Home />} />
</Routes>
</ProfileContext>
</Router>
</div>
);
}
index.js:
.firebaserc
{
"projects": {
"default": "chatroomhub-5ffa3"
}
}
database.rules.json
{
"rules": {
"profiles": {
"$user_id": {
".read": "$user_id === auth.uid",
".write": "$user_id === auth.uid"
}
},
"rooms": {
".read": "auth !== null",
"$room_id": {
".read": "auth !== null",
".write": "!data.exists() || data.child('admins').child(auth.uid).val() == true",
"lastMessage":{
".write" : "auth !== null"
}
}
},
"messages": {
".read": "auth !== null",
".write": "auth !== null",
".indexOn": ["author/uid", "roomId"],
"$message_id": {
".read": "auth !== null",
".write": "auth !== null"
}
},
"status": {
"$user_id": {
".read": "auth !== null",
".write": "$user_id === auth.uid"
}
},
".read": false,
".write": false
}
}
firebase.json
{
"database": {
"rules": "database.rules.json"
},
"hosting": {
"public": "build",
"ignore": [
"firebase.json",
"**/.*",
"**/node_modules/**"
],
"rewrites": [
{
"source": "**",
"destination": "/index.html"
}
]
}
}
Package.json
{
"name": "chatroomhub",
"version": "0.1.0",
"private": true,
"dependencies": {
"@fortawesome/fontawesome-svg-core": "^6.5.1",
"@fortawesome/free-solid-svg-icons": "^6.5.1",
"@fortawesome/react-fontawesome": "^0.2.0",
"@rsuite/icons": "^1.0.3",
"@testing-library/jest-dom": "^5.17.0",
"@testing-library/react": "^13.4.0",
"@testing-library/user-event": "^13.5.0",
"cross-env": "^7.0.3",
"file-type": "^19.0.0",
"firebase": "^10.6.0",
"node-sass": "^7.0.3",
"react": "^18.2.0",
"react-avatar-editor": "^13.0.0",
"react-dom": "^18.2.0",
"react-icons": "^4.12.0",
"react-mic": "^12.4.6",
"react-router": "^6.18.0",
"react-router-dom": "^6.20.0",
"react-scripts": "5.0.1",
"react-toastify": "^9.1.3",
"rsuite": "^5.45.0",
"styled-components": "^6.1.1",
"sweetalert2": "^11.10.0",
"timeago-react": "^3.0.6",
"use-context-selector": "^1.4.1",
"web-vitals": "^2.1.4"
},
"scripts": {
"start": "react-scripts start",
"build": "react-scripts build",
"test": "react-scripts test",
"eject": "react-scripts eject",
"lint": "eslint ."
},
"eslintConfig": {
"extends": [
"react-app",
"react-app/jest"
]
},
"browserslist": {
"production": [
">0.2%",
"not dead",
"not op_mini all"
],
"development": [
"last 1 chrome version",
"last 1 firefox version",
"last 1 safari version"
Dept of Information Technology, SVECW Page
109
OUTING MANAGEMENT
]
},
"devDependencies": {
"eslint": "^8.55.0"
}
}