2
2
import React , { useState , useEffect } from 'react' ;
3
3
import { Link } from 'react-router-dom' ;
4
4
import client from '../client' ;
5
- import { NavBarBlog } from '../components/Blog' ;
5
+ import { Filter , NavBarBlog } from '../components/Blog' ;
6
6
import { motion } from 'framer-motion' ;
7
7
import Loader from '../components/Loader/Loader' ; // Import the Loader component
8
8
9
9
const Blog = ( ) => {
10
10
const [ posts , setPosts ] = useState ( [ ] ) ;
11
+ const [ categories , setCategories ] = useState ( [ ] )
11
12
const [ loading , setLoading ] = useState ( true ) ; // Loading state
13
+ const [ activeFilter , setActiveFilter ] = useState ( 'All' )
12
14
13
15
useEffect ( ( ) => {
14
- client . fetch (
15
- `*[_type == "post"] | order(publishedAt desc) {
16
- title,
17
- slug,
18
- body,
19
- publishedAt,
20
- mainImage {
21
- asset -> {
22
- _id,
23
- url
24
- },
25
- alt
26
- },
27
- categories[]->{
28
- _id,
29
- title
30
- }
31
- }`
32
- )
33
- . then ( ( data ) => {
34
- setPosts ( data ) ;
35
- setLoading ( false ) ; // Set loading to false once data is fetched
36
- } )
37
- . catch ( ( error ) => {
38
- console . error ( error ) ;
39
- setLoading ( false ) ; // In case of error, also stop loading
40
- } ) ;
16
+ const fetchData = async ( ) => {
17
+ try {
18
+ const [ postsData , categoriesData ] = await Promise . all ( [
19
+ client . fetch ( `
20
+ *[_type == "post"] | order(publishedAt desc) {
21
+ title,
22
+ slug,
23
+ body,
24
+ publishedAt,
25
+ mainImage {
26
+ asset -> {
27
+ _id,
28
+ url
29
+ },
30
+ alt
31
+ },
32
+ categories[]->{
33
+ _id,
34
+ title
35
+ }
36
+ }
37
+ ` ) ,
38
+ client . fetch ( `
39
+ *[_type == "category"] {
40
+ _id,
41
+ title
42
+ }
43
+ ` )
44
+ ] )
45
+
46
+ setPosts ( postsData )
47
+ setCategories ( [ { _id : 'all' , title : 'All' } , ...categoriesData ] )
48
+ setLoading ( false )
49
+ } catch ( error ) {
50
+ console . error ( error )
51
+ setLoading ( false )
52
+ }
53
+ }
54
+
55
+ fetchData ( ) ;
41
56
} , [ ] ) ;
42
57
43
58
const formatDate = ( isoString ) => {
@@ -49,9 +64,17 @@ const Blog = () => {
49
64
} ) ;
50
65
} ;
51
66
67
+ const filteredPosts = activeFilter === 'All'
68
+ ? posts
69
+ : posts . filter ( post => post . categories ?. some ( category => category ?. title === activeFilter ) )
70
+
71
+
52
72
return (
53
73
< div className = 'bg-white' >
54
74
< NavBarBlog />
75
+
76
+ < Filter categories = { categories } activeFilter = { activeFilter } setActiveFilter = { setActiveFilter } />
77
+
55
78
< section className = 'px-10' >
56
79
< motion . div
57
80
style = { { y : 30 } } animate = { { y : 0 } }
@@ -67,7 +90,7 @@ const Blog = () => {
67
90
< Loader /> // Show loader when posts are being fetched
68
91
) : (
69
92
< div className = 'grid grid-cols-1 gap-5 md:grid-cols-2 lg:grid-cols-3 2xl:grid-cols-4 lg:gap-24 mb-11' >
70
- { posts . map ( ( post ) => (
93
+ { filteredPosts . map ( ( post ) => (
71
94
< motion . div
72
95
style = { { y : 30 } } animate = { { y : 0 } }
73
96
transition = { { duration : 0.55 } }
0 commit comments