1- import { FC , useState } from "react" ;
1+ import { FC , useState , useEffect } from "react" ;
22import { Button } from "@/components/ui/button" ;
3- import PictopyLogo from "@/assets/PictoPy_Logo.png" ; // Adjust this import path as needed
4- import MacLogo from "@/assets/mac-logo.png" ; // Add your Mac logo
5- import WindowsLogo from "@/assets/windows-logo.svg" ; // Add your Windows logo
6- import LinuxLogo from "@/assets/linux-logo.svg" ; // Add your Linux logo
3+ import PictopyLogo from "@/assets/PictoPy_Logo.png" ;
4+ import MacLogo from "@/assets/mac-logo.png" ;
5+ import WindowsLogo from "@/assets/windows-logo.svg" ;
6+ import LinuxLogo from "@/assets/linux-logo.svg" ;
7+
8+ interface GitHubAsset {
9+ name : string ;
10+ browser_download_url : string ;
11+ }
12+
13+ interface GitHubRelease {
14+ tag_name : string ;
15+ assets : GitHubAsset [ ] ;
16+ }
717
818const PictopyLanding : FC = ( ) => {
9- // State for showing the notification
1019 const [ downloadStarted , setDownloadStarted ] = useState < string | null > ( null ) ;
20+ const [ downloadLinks , setDownloadLinks ] = useState < {
21+ mac : string | null ;
22+ windows : string | null ;
23+ linux : string | null ;
24+ } > ( { mac : null , windows : null , linux : null } ) ;
25+ const [ loading , setLoading ] = useState ( true ) ;
26+
27+ // Fetch latest release from GitHub API
28+ useEffect ( ( ) => {
29+ const fetchLatestRelease = async ( ) => {
30+ try {
31+ const response = await fetch (
32+ "https://api.github.com/repos/AOSSIE-Org/PictoPy/releases/latest"
33+ ) ;
34+ const data : GitHubRelease = await response . json ( ) ;
35+
36+ // Find download links for each platform
37+ const macAsset = data . assets . find (
38+ ( asset ) =>
39+ asset . name . toLowerCase ( ) . includes ( ".dmg" ) ||
40+ asset . name . toLowerCase ( ) . includes ( ".app" )
41+ ) ;
42+
43+ const windowsAsset = data . assets . find (
44+ ( asset ) =>
45+ asset . name . toLowerCase ( ) . includes ( ".exe" ) ||
46+ asset . name . toLowerCase ( ) . includes ( ".msi" )
47+ ) ;
48+
49+ const linuxAsset = data . assets . find ( ( asset ) =>
50+ asset . name . toLowerCase ( ) . includes ( ".deb" )
51+ ) ;
52+
53+ setDownloadLinks ( {
54+ mac : macAsset ?. browser_download_url || null ,
55+ windows : windowsAsset ?. browser_download_url || null ,
56+ linux : linuxAsset ?. browser_download_url || null ,
57+ } ) ;
58+ setLoading ( false ) ;
59+ } catch ( error ) {
60+ console . error ( "Error fetching latest release:" , error ) ;
61+ setLoading ( false ) ;
62+ }
63+ } ;
64+
65+ fetchLatestRelease ( ) ;
66+ } , [ ] ) ;
67+
68+ // Function to handle button click and show notification
69+ const handleDownloadClick = (
70+ platform : string ,
71+ downloadUrl : string | null
72+ ) => {
73+ if ( ! downloadUrl ) {
74+ setDownloadStarted ( `${ platform } download not available yet` ) ;
75+ setTimeout ( ( ) => setDownloadStarted ( null ) , 3000 ) ;
76+ return ;
77+ }
78+
79+ // Trigger download
80+ window . location . href = downloadUrl ;
1181
12- // Function to handle button click and show the notification
13- const handleDownloadClick = ( platform : string ) => {
1482 setDownloadStarted ( `Download for ${ platform } started!` ) ;
15- // Hide the notification after 3 seconds
1683 setTimeout ( ( ) => {
1784 setDownloadStarted ( null ) ;
1885 } , 3000 ) ;
1986 } ;
2087
2188 return (
22- < section className = "w-full py-12 md:py-24 bg-white dark:bg-black transition-colors duration-300 relative overflow-hidden" >
89+ < section
90+ id = "downloads-section"
91+ className = "w-full py-12 md:py-24 bg-white dark:bg-black transition-colors duration-300 relative overflow-hidden"
92+ >
2393 { /* Background Animated SVG */ }
2494 < div className = "absolute inset-0 z-0" >
2595 < svg
@@ -47,7 +117,7 @@ const PictopyLanding: FC = () => {
47117 </ div >
48118
49119 { /* Content */ }
50- < div className = "px-4 md:px-6 relative z-10 " >
120+ < div className = "px-4 md:px-6 relative z-10" >
51121 < div className = "flex flex-col items-center text-center" >
52122 { /* Heading with Gradient Text and Logo */ }
53123 < div className = "flex items-center justify-center gap-4 mb-4" >
@@ -63,50 +133,61 @@ const PictopyLanding: FC = () => {
63133
64134 { /* Subheading */ }
65135 < p className = "text-xl md:text-2xl text-green-700 dark:text-yellow-300 max-w-3xl mb-8 transition-colors duration-300" >
66- Organize your photos effortlessly. Available for Mac, Windows, and Linux.
136+ Organize your photos effortlessly. Available for Mac, Windows, and
137+ Linux.
67138 </ p >
68139
140+ { /* Loading State */ }
141+ { loading && (
142+ < div className = "text-gray-600 dark:text-gray-400 mb-4" >
143+ Loading latest releases...
144+ </ div >
145+ ) }
146+
69147 { /* Download Buttons */ }
70148 < div className = "flex flex-col sm:flex-row gap-4 justify-center" >
71149 < Button
72150 className = "bg-black text-white hover:bg-gray-800 dark:bg-white dark:text-black dark:hover:bg-gray-200 h-12 px-8 transition-all duration-300
73151 border-2 border-transparent hover:border-black dark:hover:border-white
74- transform hover:-translate-y-1 hover:shadow-lg"
152+ transform hover:-translate-y-1 hover:shadow-lg disabled:opacity-50 disabled:cursor-not-allowed "
75153 size = "lg"
76- onClick = { ( ) => handleDownloadClick ( "Mac" ) }
154+ onClick = { ( ) => handleDownloadClick ( "Mac" , downloadLinks . mac ) }
155+ disabled = { loading || ! downloadLinks . mac }
77156 >
78157 < img src = { MacLogo } alt = "Mac" className = "h-7 w-7 mr-2" />
79158 Download for Mac
80159 </ Button >
81160 < Button
82161 className = "bg-black text-white hover:bg-gray-800 dark:bg-white dark:text-black dark:hover:bg-gray-200 h-12 px-8 transition-all duration-300
83162 border-2 border-transparent hover:border-black dark:hover:border-white
84- transform hover:-translate-y-1 hover:shadow-lg"
163+ transform hover:-translate-y-1 hover:shadow-lg disabled:opacity-50 disabled:cursor-not-allowed "
85164 size = "lg"
86165 variant = "outline"
87- onClick = { ( ) => handleDownloadClick ( "Windows" ) }
166+ onClick = { ( ) =>
167+ handleDownloadClick ( "Windows" , downloadLinks . windows )
168+ }
169+ disabled = { loading || ! downloadLinks . windows }
88170 >
89171 < img src = { WindowsLogo } alt = "Windows" className = "h-7 w-7 mr-2" />
90172 Download for Windows
91173 </ Button >
92174 < Button
93175 className = "bg-black text-white hover:bg-gray-800 dark:bg-white dark:text-black dark:hover:bg-gray-200 h-12 px-8 transition-all duration-300
94176 border-2 border-transparent hover:border-black dark:hover:border-white
95- transform hover:-translate-y-1 hover:shadow-lg"
177+ transform hover:-translate-y-1 hover:shadow-lg disabled:opacity-50 disabled:cursor-not-allowed "
96178 size = "lg"
97179 variant = "outline"
98- onClick = { ( ) => handleDownloadClick ( "Linux" ) }
180+ onClick = { ( ) => handleDownloadClick ( "Linux" , downloadLinks . linux ) }
181+ disabled = { loading || ! downloadLinks . linux }
99182 >
100- < img src = { LinuxLogo } alt = "Linux" className = "h-9 w-9 mr-2" /> { /* Larger Linux logo */ }
183+ < img src = { LinuxLogo } alt = "Linux" className = "h-9 w-9 mr-2" />
101184 Download for Linux(.deb)
102185 </ Button >
103186 </ div >
104187
105188 { /* Download Notification (Popup) */ }
106189 { downloadStarted && (
107- < div
108- className = "fixed top-16 right-4 md:right-8 bg-green-500 text-white py-3 px-6 rounded-lg shadow-xl text-lg z-50 opacity-0 animate-slideInRight"
109- >
190+ < div className = "fixed top-16 right-4 md:right-8 bg-green-500 text-white py-3 px-6 rounded-lg shadow-xl text-lg z-50 opacity-0 animate-slideInRight" >
110191 { downloadStarted }
111192 </ div >
112193 ) }
0 commit comments