DEV Community

Suad Macaulay
Suad Macaulay

Posted on

Portfolio Website Documentation

Introduction

This documentation provides step-by-step guidance on how to build a portfolio website using Next js. The goal is to help others set up their own portfolio efficiently.

Here's a link to have an overview of the portfolio site
https://www.loom.com/share/04a6843f67de48d0962ab2ddf2311a9f?sid=43940911-7c80-4fbe-ba19-f683e662ff90

Prerequisites

Before starting, ensure you have the following installed:
Basic knowledge of HTML, CSS, and JavaScript

Project Setup

  1. Open your a Code Editor
  • Open the project folder in your preferred code editor.
  1. Run the development command line
  • Run the command line in the terminal of vscode
  • npm run dev

Local host img

After click on the local url, so it's opened in your browser

Folder Structure

portfolio-project/
│-- next

│-- app/
| | -- components/
| | |-- About.jsx
| | |-- Contact.jsx
| | |-- Footer.jsx
| | |-- Head.jsx
| | |-- Navbar.jsx
| | |-- Project.jsx
| | |-- Service.jsx
| -- global.css
| -- layout.js
| -- page.js
│-- node.modules
│--public

│-- tailwind.config.ms

*NOTE: You must create the components folder in the app folder and then create the about, contact, footer, head, navbar, project and service within the component folder.
*

Customization

  1. Update the tailwind.config.mjs code
  • Open tailwind.config.mjs and update the file with this code
/** @type {import('tailwindcss').Config} */

import { Montserrat, Poppins } from "next/font/google";

// eslint-disable-next-line import/no-anonymous-default-export
export default {
  content: [
    "./pages/**/*.{js,ts,jsx,tsx,mdx}",
    "./components/**/*.{js,ts,jsx,tsx,mdx}",
    "./app/**/*.{js,ts,jsx,tsx,mdx}",
  ],
  theme: {
    extend: {
      colors: {
        background: "var(--background)",
        foreground: "var(--foreground)",
      },
    },
    fontFamily: {
      Poppins: ["Poppins", "sans-serif"],
      Montserrat: ["Montserrat", "serif"],
    },

    boxShadow: {
      shadowWhite: "2px 2px 0 #cbd5e1",
    },
    gridTemplateColumns: {
      auto: "repeat(auto-fit, minmax(200px, 1fr))",
    },
  },
  plugins: [],
};

Enter fullscreen mode Exit fullscreen mode
  1. Update the global.css
  • Change the code the the global.css file with this
@tailwind base;
@tailwind components;
@tailwind utilities;

:root {
  --foreground: #ffffff;
  --background: #171717;
}

*,
*::before,
*::after {
  box-sizing: border-box;
  overflow-x: hidden;
}

body {
  color: var(--foreground);
  background: var(--background);
  font-family: Poppins;
}

Enter fullscreen mode Exit fullscreen mode
  1. Modify layout.js Section
  • Update the code in layout.js with the code below
import { Poppins, Montserrat } from "next/font/google";
import "./globals.css";

const poppins = Poppins({
  subsets: ["latin"],
  weight: ["400", "500", "600", "700"],
});

const montserrat = Montserrat({
  subsets: ["latin"],
  weight: ["400"],
});

export const metadata = {
  title: "Portfolio - "Your name",
  description:
    "Showcasing the work and skills of a passionate frontend developer with a focus on web development, UX/UI design, and problem-solving",
};

export default function RootLayout({ children }) {
  return (
    <html lang="en" className="scroll-smooth">
      <body
        className={`${poppins.className} ${montserrat.className} antialiased`}
      >
        {children}
      </body>
    </html>
  );
}

Enter fullscreen mode Exit fullscreen mode

3.** Modify page.js Section**
Update the code in page.js with the code below

import Image from "next/image";
import Navbar from "./components/Navbar";
import Head from "./components/Head";
import About from "./components/About";
import Service from "./components/Service";
import Project from "./components/Project";
import Contact from "./components/Contact";
import Footer from "./components/Footer";

export default function Home() {
  return (
    <div>
      <Navbar />
      <Head />
      <About />
      <Service />
      <Project />
      <Contact />
      <Footer />
    </div>
  );
}

Enter fullscreen mode Exit fullscreen mode
  1. *Open the Navbar.jsx *
  • In this file follow this code format
"use client";

import Image from "next/image";
import React, { useRef } from "react";
import logo from "../assets/logo3.png";
import close from "../assets/close-white.png";
import menu from "../assets/menu-white.png";

const Navbar = () => {
  const sideMenu = useRef();

  const openMenu = () => {
    sideMenu.current.style.transform = "translateX(-15rem)";
  };

  const closeMenu = () => {
    sideMenu.current.style.transform = "translateX(16rem)";
  };

  return (
    <nav>
      <div className=" hidden sm:flex justify-between bg-opacity-50 backdrop-blur-md bg-[#222222] py-2  px:[5rem] sm:px-20 lg:px-[20rem] fixed top-0 right-0 left-0 z-50">
        <Image src={logo} className=" w-20 md:w-24 " alt="" />
        <div className="flex sm:gap-5 text-xs lg:text-sm lg:gap-12 items-center gap-2">
          <a href="#top" className="hover:text-[#ffbc92] duration-500">
            Home
          </a>
          <a href="#about" className="hover:text-[#ffbc92] duration-500 ">
            About
          </a>
          <a href="#service" className="hover:text-[#ffbc92] duration-500">
            Services
          </a>
          <a href="#project" className="hover:text-[#ffbc92] duration-500">
            Projects
          </a>
          <a href="#contacts" className="hover:text-[#ffbc92] duration-500">
            Contact
          </a>
        </div>
      </div>
      <div className="bg-[#222222] fixed w-full h-[4rem] bg-opacity-50 backdrop-blur-md sm:hidden z-50">
        <Image src={logo} className=" w-20 md:w-24  mt-7 ml-5 fixed " alt="" />
        <button>
          <Image
            onClick={openMenu}
            src={menu}
            className="w-6 mt-3 sm:hidden -right-[1px] mr-3 fixed"
            alt=""
          />
        </button>
      </div>
      <div>
        <ul
          ref={sideMenu}
          className="sm:hidden flex flex-col gap-4 bg-slate-700 z-50 py-12 px-5 fixed rounded-sm h-screen -right-[15rem]  w-[12rem] duration-500"
        >
          <div onClick={closeMenu}>
            <button>
              <Image
                src={close}
                className="w-4 absolute top-5 left-[10rem] "
                alt=""
              />
            </button>
          </div>
          <li>
            <a href="#top" onClick={closeMenu}>
              Home
            </a>
          </li>
          <li>
            <a href="#about" onClick={closeMenu}>
              About
            </a>
          </li>{" "}
          <li>
            <a href="#service" onClick={closeMenu}>
              Services
            </a>
          </li>{" "}
          <li>
            <a href="#project" onClick={closeMenu}>
              Projects
            </a>
          </li>{" "}
          <li>
            <a href="#contacts" onClick={closeMenu}>
              Contact
            </a>
          </li>
        </ul>
      </div>
    </nav>
  );
};

export default Navbar;

Enter fullscreen mode Exit fullscreen mode
  1. *Open the Head.jsx *
  • In this file follow this code format
import Image from "next/image";
import React from "react";
import profileImg from "../assets/profile-img.png";
import hand from "../assets/hand-icon.png";

const Head = () => {
  return (
    <div className="">
      <div className=" flex flex-col items-center mx-auto mt-20 text-center gap-2">
        <Image src={profileImg} className="rounded-full w-32" alt="" />
        <p className="  text-[1rem] w-[20rem]  sm:w-full justify-center sm:text-2xl flex sm:gap-2 font-semibold lg:text-2xl">
          Hey There! I go by the name _[Your name]_
          <Image
            src={hand}
            className=" w-7 h-[28px] -translate-x-2 sm:translate-x-0 sm:h-auto sm:w-7 "
          />
        </p>
        <h2 className="text-2xl sm:text-[2rem] sm:w-[40rem] mt-2 overflow-y-hidden lg:text-5xl lg:w-[58rem]">
          A frontend Developer and Blockchain enthusiast 
        </h2>
        <p className=" text-[13px] w-[20rem] sm:text-[15px] sm:w-[38rem] mt-3 lg:text-[16px] lg:w-[45rem]">
          I am an IT student with a strong interest in frontend development and
          the blockchain field. I am focused on building user-friendly,
          responsive websites and am actively exploring blockchain technologies.
          My goal is to contribute positively to the ecosystem by developing
          innovative solutions and improving the user experience.
        </p>
        <div className="flex flex-col gap-5 sm:flex-row sm:gap-20 mt-10 font-bold">
          <a
            href="#contacts"
            className="border rounded-3xl py-3 px-6 bg-white text-black hover:text-[#f08847] duration-500"
          >
            Let's connect
          </a>
          <a
            href="/Your-Resume.pdf"
            className="border rounded-3xl py-3 px-8 hover:text-[#ffbc92] duration-500"
            download
          >
            My resume
          </a>
        </div>
      </div>
    </div>
  );
};

export default Head;

Enter fullscreen mode Exit fullscreen mode
  1. *Open the About.jsx *
  • In this file follow this code format
import Image from "next/image";
import React from "react";
import myImage from "../assets/user-image.png";
import lang from "../assets/Logos.png";
import vscode from "../assets/vscode.png";
import vercel from "../assets/vercel.png";
import netlify from "../assets/netlify.png";
import figma from "../assets/figma.png";
import github from "../assets/github.png";

const About = () => {
  return (
    <div id="about">
      <div className="mt-32 text-center ">
        <h2 className="mb-12 text-3xl sm:text-4xl lg:text-5xl font-bold bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text overflow-y-hidden">
          About me
        </h2>
        <div className="flex flex-col lg:flex-row  items-center lg:justify-center lg:gap-40 lg:items-start gap-5">
          <Image src={myImage} className="rounded-xl w-52 lg:w-64" alt="" />
          <div>
            <p className="text-[13px] w-[21rem] mx-auto sm:mx-0 sm:text-[14px] sm:w-[30rem] lg:text-[16px] lg:w-[40rem] lg:text-left">
              I am an aspiring frontend developer, learning the necessary tech
              stack i need to succeed in my field. I have worked on few projects
              that helped me to reinforce what i've learnt as well as improve
              upon my skills. I'm willing to work and collaborate with people to
              learn and grow.
            </p>
            <div className="mt-10 lg:text-left">
              <p className="mb-5 font-bold text-lg lg:text-xl bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
                Experience with
              </p>
              <a className="flex lg:justify-start justify-center ">
                <Image src={lang} className="w-72 sm:w-80" />
              </a>
            </div>
            <div className=" mt-7 ">
              <p className=" font-bold text-lg lg:text-xl lg:text-left bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
                Tools I use
              </p>
              <div className=" flex gap-7 sm:gap-10 lg:justify-start justify-center overflow-y-visible ">
                <a href="https://code.visualstudio.com/" target="_blank">
                  <Image
                    alt=""
                    src={vscode}
                    className="w-9 sm:w-10  mt-4 duration-500  bg-white rounded-xl  border p-2  hover:bg-slate-200 hover:shadow-shadowWhite hover:-translate-y-1"
                  />
                </a>
                <a href="https://www.figma.com/" target="_blank">
                  <Image
                    alt=""
                    src={figma}
                    className="w-9 sm:w-10 duration-500 mt-4 bg-white rounded-xl border p-2  hover:bg-slate-200 hover:shadow-shadowWhite hover:-translate-y-1"
                  />
                </a>
                <a href="https://vercel.com/" target="_blank">
                  <Image
                    alt=""
                    src={vercel}
                    className="w-[38px] sm:w-[40px] duration-500 mt-4 border rounded-xl bg-white r p-2  hover:bg-slate-200 hover:shadow-shadowWhite hover:-translate-y-1"
                  />
                </a>
                <a href="https://www.netlify.com/" target="_blank">
                  <Image
                    alt=""
                    src={netlify}
                    className="w-[38px] sm:w-[40px] duration-500 mt-4 bg-white rounded-xl border p-2  hover:bg-slate-200 hover:shadow-shadowWhite hover:-translate-y-1"
                  />
                </a>
                <a href="https://github.com/" target="_blank">
                  <Image
                    alt=""
                    src={github}
                    className="w-[40px] sm:w-[42px] duration-500 mt-4 bg-white rounded-xl border p-2 hover:bg-slate-200 hover:shadow-shadowWhite hover:-translate-y-1"
                  />
                </a>
              </div>{" "}
            </div>
          </div>
        </div>
      </div>
    </div>
  );
};

export default About;

Enter fullscreen mode Exit fullscreen mode
  1. *Open the Service.jsx *
  • In this file follow this code format
import Image from "next/image";
import React from "react";
import ui from "../assets/ui-icon.png";
import graphic from "../assets/graphics-icon.png";
import web from "../assets/web-icon.png";

const Service = () => {
  return (
    <div id="service" className="">
      <div className="my-32 ">
        <h2 className="text-3xl sm:text-4xl lg:text-5xl overflow-y-hidden font-bold text-center bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
          What I do
        </h2>
        <ul className="mt-10 flex flex-col sm:flex-row items-center mx-auto gap-6 w-[80%] lg:w-[60%]">
          <li className="  border-none rounded-xl p-8 w-3/4 h-[15rem] bg-slate-900 hover:bg-slate-800 duration-500  ">
            <Image alt="" src={web} className="w-10 mb-3" />
            <h2 className="text-sm lg:text-[1rem] font-semibold mb-3 bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
              Web development
            </h2>
            <p className=" text-[13px] ">
              Building fast and responsive websites.
            </p>
          </li>
          <li className=" border-none rounded-xl p-8 w-3/4 h-[15rem]  bg-slate-900  hover:bg-slate-800 duration-500 ">
            <Image alt="" src={ui} className="w-10 mb-3" />
            <h2 className="text-sm lg:text-[1rem] font-semibold mb-3 bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
              UI/UX design
            </h2>
            <p className=" text-[13px]">
              Designing simple and intuitive websites
            </p>
          </li>
          <li className="border-none rounded-xl p-7 w-3/4 h-[15rem] bg-slate-900 hover:bg-slate-800 duration-500  ">
            <Image alt="" src={graphic} className="w-10 mb-3" />
            <h2 className="text-sm lg:text-[1rem] font-semibold mb-3 bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
              Graphic design
            </h2>
            <p className=" text-[13px]">Creating visually appealing designs</p>
          </li>
        </ul>
      </div>
    </div>
  );
};

export default Service;

Enter fullscreen mode Exit fullscreen mode
  1. Open the Project.jsx In this file follow this code format
import React from "react";
import profileLinks from "../assets/work-1.png";
import guessGame from "../assets/guess_game.png";
import pigGame from "../assets/pig_game.png";
import landingPage from "../assets/landing_page.jpg";
import send from "../assets/send-icon.png";
import Image from "next/image";

const Project = () => {
  return (
    <div id="project">
      <div className=" mt-20 mb-10 w-3/4 mx-auto">
        <div className="">
          <h2 className="mb-10 text-3xl sm:text-4xl lg:text-5xl overflow-y-hidden text-center bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
            Projects i Built
          </h2>
          <ul className="grid grid-cols-auto gap-4 place-items-center ">
            <li>
              <Image src={profileLinks} className="w-[17rem] h-44" alt="" />
              <div className="bg-slate-900 hover:bg-slate-800 py-2 px-5 rounded-xl mt-2 flex gap-10 items-center w-[17rem]">
                <a
                  href="https://social-links-profile-main-six-xi.vercel.app/"
                  target="_blank"
                >
                  <p className="font-semi-bold   bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
                    Social links profile
                  </p>
                  <p className="text-sm">Web design</p>
                </a>
                <a
                  href="https://social-links-profile-main-six-xi.vercel.app/"
                  target="_blank"
                >
                  <Image
                    alt=""
                    src={send}
                    className="bg-white w-8 p-2 aspect-square rounded-xl hover:bg-gray-200"
                  />
                </a>
              </div>
            </li>
            <li>
              <Image src={guessGame} className="w-[17rem] rounded-xl" alt="" />
              <div className="bg-slate-900  w-[17rem] hover:bg-slate-800 py-2 px-5 rounded-xl mt-2 flex gap-24 items-center">
                <a href="https://guess-game-by-suad.netlify.app/" className="">
                  <p className="font-semi-bold   bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
                    Guess game
                  </p>
                  <p className="text-sm">Web design</p>
                </a>
                <a
                  href="https://guess-game-by-suad.netlify.app/"
                  target="_blank"
                >
                  <Image
                    alt=""
                    src={send}
                    className="bg-white w-8 p-2 aspect-square rounded-xl hover:bg-gray-200"
                  />
                </a>
              </div>
            </li>
            <li>
              <Image src={pigGame} className="w-[17rem] rounded-xl" alt="" />
              <div className="bg-slate-900 w-[17rem] hover:bg-slate-800 py-2 px-5 rounded-xl mt-2 flex gap-28 items-center">
                <a href="" target="_blank">
                  <p className="font-semi-bold   bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
                    Pig game
                  </p>
                  <p className="text-sm">Web design</p>
                </a>
                <a href="https://pig-game-by-suad.netlify.app/" target="_blank">
                  <Image
                    alt="https://pig-game-by-suad.netlify.app/"
                    src={send}
                    className="bg-white w-8 p-2 aspect-square rounded-xl  hover:bg-gray-200"
                  />
                </a>
              </div>
            </li>
            <li>
              <Image
                src={landingPage}
                className="w-[17rem] rounded-xl"
                alt=""
              />
              <div className="bg-slate-900 w-[17rem] hover:bg-slate-800 py-2 px-5 rounded-xl mt-2 flex gap-7 items-center">
                <a
                  href="https://huddle-landing-page-by-suad.netlify.app/"
                  target="_blank"
                >
                  <p className="font-semi-bold   bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
                    Huddle landing page
                  </p>
                  <p className="text-sm">UI/UX</p>
                </a>
                <a
                  href="https://huddle-landing-page-by-suad.netlify.app/"
                  target="_blank"
                >
                  <Image
                    alt=""
                    src={send}
                    className="bg-white w-8 p-2 aspect-square rounded-xl hover:bg-gray-200"
                  />
                </a>
              </div>
            </li>
          </ul>
        </div>
      </div>
    </div>
  );
};

export default Project;

Enter fullscreen mode Exit fullscreen mode
  1. *Open the Contact.jsx *
  • In this file follow this code format
import Image from "next/image";
import React from "react";
import x from "../assets/x.png";
import linkedin from "../assets/linkedin.png";
import whatsapp from "../assets/whatsapp.png";
import email from "../assets/mail_icon_dark.png";

const Contact = () => {
  return (
    <div
      id="contacts"
      className="mt-36 mb-16 flex flex-col items-center  gap-5"
    >
      <div className="text-center">
        <h2 className=" text-xl sm:text-4xl font-bold  overflow-y-hidden mb-2 bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
          Want to collaborate with me?
        </h2>
        <p className=" text-md sm:text-xl font-semibold ">
          Lets connect on social media app!{" "}
        </p>
      </div>
      <div className="flex gap-4 sm:gap-6">
        <p className="bg-gradient-to-r from-[#FF8660] to-[#9A33FF] text-transparent bg-clip-text">
          Connect:
        </p>
        <a href=" " target="_blank">
          <Image
            alt="mailto:suadmacaulay50@gmail.com"
            src={email}
            className="w-[1.4rem] sm:w-[1.6rem] translate-y-1"
          />
        </a>
        <a href=" " target="_blank">
          <Image
            alt="https://www.linkedin.com/in/suad-macaulay"
            src={linkedin}
            className="w-[1.5rem] sm:w-[1.7rem]"
          />
        </a>
        <a href=" " target="_blank">
          <Image
            alt="https://wa.me/0598399951"
            src={whatsapp}
            className="w-[1.6rem] sm:w-[1.8rem]"
          />
        </a>
        <a href=" " target="_blank">
          <Image
            alt="https://x.com/moreofababe"
            src={x}
            className="w-[1.6rem] sm:w-7"
          />
        </a>
      </div>
    </div>
  );
};

export default Contact;

Enter fullscreen mode Exit fullscreen mode
  1. *Open the Footer.jsx *
  • In this file follow this code format
import React from "react";

const Footer = () => {
  return (
    <div>
      <div className="border-t text-center mx-[15%]">
        <p className="my-5">© [Your name]. All rights reserved</p>
      </div>
    </div>
  );
};

export default Footer;

Enter fullscreen mode Exit fullscreen mode

Deployment

Once you’ve customized your portfolio, deploy it online.
**

Use this link to watch a step by step guide on how to push your project to github and how to deploy on Netlify or Vercel.
https://scrimba.com/learn-html-and-css-c0p/~020

Conclusion
This documentation provides a foundation to build and customize your own portfolio website. If you encounter issues, feel free to reach out!

Author: Suad Macaulay

Top comments (0)