DEV Community

Cover image for Hire+Plus! For Employees Here's how I built it (UI - Company)
AjeaS
AjeaS

Posted on

Hire+Plus! For Employees Here's how I built it (UI - Company)

Overview: All views and functionality related to the Company, all funcs called are coming from the authSlice reducer.


Company Route Page

inside routes > company > company-page.tsx
imports that assist with components to render, and functions to call from companyReducer. useParams will be used to get the id of the company that's passed in the url. -> company/:id route. On mount, I fetch the appropriate company in DB by id. To clarify, when I fetch this data I set it to state.

import { useEffect } from 'react';
import { useParams } from 'react-router';
import BeatLoader from 'react-spinners/BeatLoader';
import { getCompany } from '../../app/features/company/companySlice';
import { useAppDispatch, useAppSelector } from '../../app/hooks';
import ViewCompany from '../../components/company/view-company.component';

const CompanyPage = () => {
    const { id } = useParams();
    const dispatch = useAppDispatch();
    const { isLoading } = useAppSelector((state) => state.company);

    useEffect(() => {
        dispatch(getCompany(id));
    }, [id, dispatch]);
    return <>{isLoading ? <BeatLoader /> : <ViewCompany />}</>;
};

export default CompanyPage;

Enter fullscreen mode Exit fullscreen mode

View Company Component

inside components > company > view-company.component.tsx
I created a helper method truncateString for text that's too long. If text reaches max length it shows ...

import { useAppSelector } from '../../app/hooks';
import { truncateString } from '../../utils/truncateString';
Enter fullscreen mode Exit fullscreen mode

Functionality

get company state from companyReducer

const ViewCompany = () => {
    const { company } = useAppSelector((state) => state.company);

    return ({/* removed for simplicity */});
};

export default ViewCompany;

Enter fullscreen mode Exit fullscreen mode

UI

In a nutshell, it renders company details(who they are, location, hiring, etc.), along with the jobs they posted.

const ViewCompany = () => {
    const { company } = useAppSelector((state) => state.company);
    return (
        <>
            <section style={{ backgroundColor: '#252731' }} className="mb-3">
                <div className="container mx-auto py-5 px-5 md:px-0 text-right text-white flex justify-between">
                    <div className="flex justify-center text-md text-slate-200">
                        {company.isHiring ? (
                            <p>We are hiring!</p>
                        ) : (
                            <p>Not hiring at the moment</p>
                        )}
                    </div>
                </div>
                <div className="md:px-12 lg:px-24 max-w-7xl relative items-center w-full px-5 py-5 mx-auto">
                    <div className="mx-auto flex flex-col w-full max-w-lg mb-12 text-center">
                        <p className="mb-5 font-medium text-2xl text-white">
                            {company.companyName}
                        </p>
                        <img
                            alt="testimonial"
                            className="inline-block object-cover object-center w-20 h-20 mx-auto mb-8 rounded-full"
                            src="https://picsum.photos/200"
                        />
                        <div className="flex justify-center">
                            {company.companyUrl ? (
                                <a
                                    href={company.companyUrl}
                                    className="text-base leading-relaxed text-indigo-500 border-r-2 border-gray-500 pr-2"
                                >
                                    Company Website
                                </a>
                            ) : null}
                            {company.companySize ? (
                                <p className="text-base leading-relaxed font-color pl-2">
                                    Company size: {company.companySize}
                                </p>
                            ) : null}
                        </div>
                    </div>
                </div>
            </section>
            <ul
                className="nav nav-tabs flex flex-col md:flex-row flex-wrap list-none border-b-0 pl-0 mb-4 text-white"
                id="tabs-tabFill"
                role="tablist"
            >
                <li className="nav-item flex-auto text-center" role="presentation">
                    <a
                        href="#tabs-homeFill"
                        className="
                                nav-link
                                w-full
                                block
                                font-medium
                                text-sm
                                leading-tight
                                uppercase
                                border-x-0 border-t-0 border-b-2 border-transparent
                                px-6
                                py-3
                                my-2
                                hover:border-transparent hover:bg-transparent
                                focus:border-transparent
                                active
                                "
                        id="tabs-home-tabFill"
                        data-bs-toggle="pill"
                        data-bs-target="#tabs-homeFill"
                        role="tab"
                        aria-controls="tabs-homeFill"
                        aria-selected="true"
                    >
                        About the company
                    </a>
                </li>
                <li className="nav-item flex-auto text-center" role="presentation">
                    <a
                        href="#tabs-profileFill"
                        className="
                                nav-link
                                w-full
                                block
                                font-medium
                                text-sm
                                leading-tight
                                uppercase
                                border-x-0 border-t-0 border-b-2 border-transparent
                                px-6
                                py-3
                                my-2
                                hover:border-transparent hover:bg-transparent
                                focus:border-transparent
                                "
                        id="tabs-profile-tabFill"
                        data-bs-toggle="pill"
                        data-bs-target="#tabs-profileFill"
                        role="tab"
                        aria-controls="tabs-profileFill"
                        aria-selected="false"
                    >
                        Jobs Posted
                    </a>
                </li>
            </ul>
            <div className="tab-content font-color" id="tabs-tabContentFill">
                <div
                    className="tab-pane fade show active w-full max-w-4xl"
                    id="tabs-homeFill"
                    role="tabpanel"
                    aria-labelledby="tabs-home-tabFill"
                >
                    <p className="text-md px-10">{company.companyDescription}</p>
                </div>
                <div
                    className="tab-pane fade"
                    id="tabs-profileFill"
                    role="tabpanel"
                    aria-labelledby="tabs-profile-tabFill"
                >
                    {company.jobs.length ? (
                        <section className="text-gray-600 body-font">
                            <div className="container py-5 mx-auto">
                                <div className="flex flex-wrap -m-4">
                                    {company.jobs.map((job, index) => {
                                        return (
                                            <div className="p-4 md:w-1/2 w-full" key={index}>
                                                <div className="h-full secondary-bg-color p-8 rounded">
                                                    <h2 className="mb-3 text-indigo-500">
                                                        <a href={job.applyUrl}>APPLY FOR JOB</a>
                                                    </h2>
                                                    <p className="leading-relaxed mb-6 font-color">
                                                        {truncateString(job.description, 250)}
                                                    </p>

                                                    <span className="flex-grow flex flex-col">
                                                        <span className="title-font font-medium text-white">
                                                            {job.position}
                                                        </span>
                                                        <div className="flex font-color">
                                                            <span className="text-sm">
                                                                {job.location.toUpperCase()}
                                                            </span>
                                                            <span className="text-sm mx-2">
                                                                {job.jobType.toUpperCase()}
                                                            </span>
                                                            <span className="text-sm">
                                                                ${job.salary.toUpperCase()}
                                                            </span>
                                                        </div>
                                                    </span>
                                                </div>
                                            </div>
                                        );
                                    })}
                                </div>
                            </div>
                        </section>
                    ) : (
                        <p className="text-md">No Jobs posted </p>
                    )}
                </div>
            </div>
        </>
    );
};

export default ViewCompany;

Enter fullscreen mode Exit fullscreen mode

Screenshots

about company

company jobs

That's all for the UI/Company portion of the project, stay tuned!

Top comments (0)