How to Build a Responsive Filterable Gallery Using React?

The Responsive filterable gallery is useful when your website contains different types of content or so many contents. With the help of a filterable gallery, you can easily display all the contents on your front page to the user. But if user wants some specific contents then we need to attach filters on the website gallery.



Starting from scratch, building a Filterable Gallery using React. We'll learn about the basic setup for reacting. To finish off, we will design out a filterable gallery using React style-component.


By starting from nothing, let's go over what we are going to cover in detail:

  • Setup Basic React application using create-react-app.
  • Learn how to use React class component and function component.
  • Learn how to use React useState.
  • Get Started with styling using React style-component.

To find the complete Source code of the project you can download it by clicking the download button below.





Let's start building,


Our Project Structure 

Before we begin let's talk about how our project is going to be organized. Once we create our React app using create-react-app, we will have our base React app. Remove all unwanted files and images used in default react app. Our folder structure will look like the following:

filterable gallery using react folder structure

Now after removing all those unwanted files and their code used in all the files. we have to create a few files in our application.

 


Building React Component 


In this tutorial, we are going to use 3 files.

  1. Filterable gallery of multiple images and filter buttons at the top.
  2. Data file for storing all the data related to images such as(title, category, image, description).
  3. The style for styling our filterable gallery using React style components.

 

Let’s create those files. In the src/ folder, create the following folder: src/components/filter_items. Within that newly created folder, let’s create three files:

  • src/components/filter_items/home.js
  • src/components/filter_items/data.js
  • src/components/filter_items/home_style.js

 

Now create an images folder in the public folder of application public/images where our gallery images will be stored. After following all the above steps your new application structure will look like this.


Filterable gallery using react folder structure


Now open your data.js file and create a set of data items or project items that you are going to use in your filterable gallery. In this project, we are going to use the 5 values of a gallery component.

 

  • ID (Each gallery component will have a unique ID so that we will be able to access them easily)
  • CAT( The category from which filterable gallery component is related)
  • TITLE( Title or heading of the filterable gallery component)
  • DESC( Mini description of the filterable gallery component)
  • IMAGE( Image file path that is going to use as image of filterable gallery component)


write the following code in the data.js file as follow or you can create it by own.





 const ProjectData=[
    {
        id:1,
        cat:'Django',
        title:'Alabaster',
        desc: 'very white and smooth.',
        image:'./images/project-1.png'
    },
    {
        id:2,
        cat:'React',
        title:'Alabaster',
        desc: 'very white and smooth.',
        image:'./images/project-2.png',
    },
    {
        id:3,
        cat:'React',
        title:'Alabaster',
        desc: 'very white and smooth.',
        image:'./images/project-3.png',

    },
    {
        id:4,
        cat:'JavaScript',
        title:'Alabaster',
        desc: 'very white and smooth.',
        image:'/images/project-4.png',
    },
    {
        id:5,
        cat:'JavaScript',
        title:'Alabaster',
        desc: 'very white and smooth.',
        image:'/images/project-8.jpg',
    },
    {
        id:6,
        cat:'React',
        title:'Alabaster',
        desc: 'very white and smooth.',
        image:'/images/project-7.jpg',
    },
    {
        id:7,
        cat:'Django',
        title:'Alabaster',
        desc: 'very white and smooth.',
        image:'/images/project-6.png',
    },
    {
        id:8,
        cat:'Django',
        title:'Alabaster',
        desc: 'very white and smooth.',
        image:'/images/project-5.png',
    },
]
export default ProjectData;


Now open App.js file and write the following code in the App.js file. Each step of the process/code is explained using the comment in the code itself.



import { useState } from 'react';
import ProjectData from './components/filter_items/data';
import Home from './components/filter_items/home';

//creating a array of all category of data items.
const allCategories = ['All',...new Set(ProjectData.map(item => item.cat)) ]


function App() {
  //setting state variable of filterable gallery using useState hooks
  const [projectItem, setProjectItem] = useState(ProjectData);
  const [buttons] = useState(allCategories);

  const filter = (button) => {
    //if button value is All then display all the data item.
    if(button === 'All'){
      setProjectItem(ProjectData);
      return;
    }
    //if any other button value is clicked then filter the item as per clicked button.
    const filterData = ProjectData.filter(item => item.cat === button);
    setProjectItem(filterData);
  }
  return (
    <div className="App">
      {/* passing props to Home Component */}
      <Home projectItem = {projectItem} button = {buttons}  filter = {filter} />
    </div>
  );
}

export default App;


Now we have to write the code for Home component which will render the all project items, category buttons and it will handle all the functionality of filter props.

Let's open your home.js file and write the code as follow each line of the code is explained through the comments that will bring better understanding with the code of filterable gallery.



 import React from 'react';
//import style-component from home-style file, we yet not created it but we will style our application in next step.
import {ProjectSection , Head, Headline,ProjectFilters,Filter,FilterCategory, ProjectRow,ProjectColumn ,ProjectImage,ProjectImageOverlay, OverlayTitle,OverlayText} from './home_style';


export default function Home({projectItem, button , filter} ) {//accessing props values.
    return (
        <div>
            <section id="projects" name="projects">
                <ProjectSection>
                    <Head className="project-head">
                        <Headline>Projects</Headline>
                    </Head>
                    <ProjectFilters>
                        <Filter>
                            {/* mapping/looping over the button array to display all the filter buttons */}
                            {button.map((cat,index) => {
                                return (
                                    <FilterCategory  key={cat} onClick={()=> filter(cat)}>{cat}</FilterCategory> //on click calling the filter function and passing the clicked button value as category. 
                                    //filter function defined in the app.js file will filtered the component according to clicked button and set it projectItem state value.
                                )
                            })}
                        </Filter>
                    </ProjectFilters>

                    {/* project row start here  */}
                    <ProjectRow>
                        {/* project column first  */}
                         {/* mapping/looping over the projectItem array to display all the filtered component accoding to clicked button */}
                        {projectItem.map(project => {
                            return (
                                <ProjectColumn key={project.id} className={`item ${project.cat}`}>
                                    <div className="ProjectImages">
                                        <ProjectImage src={project.image} alt="Porject images " />
                                    </div>
                                    <ProjectImageOverlay>
                                        <OverlayTitle>{project.title}</OverlayTitle>
                                        <OverlayText>{project.desc}</OverlayText>
                                    </ProjectImageOverlay>
                                </ProjectColumn>
                            )
                        })}
                        {/* project column first end  */}
                    </ProjectRow>
                    {/* project row end here  */}
                </ProjectSection>

            </section>
        </div>
    )
}




We are now just going to wrap up this application. The last step that we have to is applying  style component in our application for it's beauty and attractive look. You can modify this component as per your need and your choice of design.

Now open the home-style.js file and write the following code in the file.

import styled from 'styled-components';
///styling for project section 
export const Head = styled.div `
    text-align:center;
    padding:10px 0; 
`
export const Headline = styled.h3 `
    position:relative;
    color:#fff;
    font-size:30px;

    &::after{
        position:absolute;
        content: "";
        top:100%;
        left:47%;
        width:7vw;
        height:3px;
        transform: skewy(-3deg);
        background-color:#00D84A;

        @media screen and (max-width:764px){
            width:20vw;
            left:40%;
        }
    }
    
`
export const ProjectSection = styled.div `

`;
export const ProjectFilters= styled.div `

`;

export const Filter = styled.ul `
    text-decoration:none;
    display:flex;
    justify-content:center;
    flex-wrap :wrap;
    margin-bottom:3rem;
`;

export const FilterCategory = styled.li `
    padding:6px 20px;
    border-radius:20px;
    list-style:none;
    margin:1.5rem 1rem 0rem 1rem;
    color:white;
    transition:all 0.5s;
    border:2px solid #fff;
    background:none;
    cursor:pointer;

    &.active{
        background-color:#00D84A;
        border:none;
    }

    &:hover{
        background-color:#00D84A;
        border:none;
    }

`;
export const ProjectRow = styled.div `
    display:flex;
    justify-content:space-evenly;
    align-items:center;
    width:75vw;
    flex-wrap:wrap;
    margin:auto;
    @media screen and (max-width:968px){
        width:90vw;
    }
    @media screen and (max-width:764px){
        width:95vw;
        margin-bottom:1.5rem;
        flex-direction:column;
    }


`
export const ProjectColumn = styled.div `
    max-height:35vh;
    width:21vw;
    background-color:#000;
    color:white;
    margin-bottom:1.5rem;
    position:relative;
    @media screen and (max-width:968px){
        width:40vw;
        margin-bottom:1.5rem;
    }
    @media screen and (max-width:764px){
        width:85vw;
        margin-bottom:1.5rem;
    }
    &:hover::before{
        content: "";
        position:absolute;
        width:100%;
        height:100%;
        top:0;
        left:0;
        z-index:1;
        background:rgba(0,0,0,0.6);

    }
`
export const ProjectImage = styled.img`
    width:100%;
    max-height:35vh;
    margin:auto;  
`

export const ProjectImageOverlay = styled.div `
   opacity:0;
   position:absolute;
   top:15%;
   left:5%;
   padding:0.5rem;

   ${ProjectColumn}:hover & {
       opacity:1;
       z-index:2;
   }
`;

export const OverlayTitle = styled.h4 `
   font-size:22px;
   text-transform:uppercase;
`;

export const OverlayText = styled.p `
   font-size:14px;

`


That's it we have successfully developed the Responsive Filterable Gallery Using React JS.

 

If you have any queries related to the Responsive Filterable Gallery Using React JS article write down it below in the comment section. You can also connect with me on social media platforms and email for other discussions related to articles, etc.

Post a Comment

0 Comments