Skip to content

Commit

Permalink
Add files via upload
Browse files Browse the repository at this point in the history
  • Loading branch information
Shanekhan authored Jul 30, 2024
0 parents commit 074baf5
Show file tree
Hide file tree
Showing 15 changed files with 267 additions and 0 deletions.
1 change: 1 addition & 0 deletions .env
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
VITE_APP_ID="cefe612bcf0d2866aa80dbab07820af2"
42 changes: 42 additions & 0 deletions App.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
#root {
max-width: 1280px;
margin: 0 auto;
padding: 2rem;
text-align: center;
}

.logo {
height: 6em;
padding: 1.5em;
will-change: filter;
transition: filter 300ms;
}
.logo:hover {
filter: drop-shadow(0 0 2em #646cffaa);
}
.logo.react:hover {
filter: drop-shadow(0 0 2em #61dafbaa);
}

@keyframes logo-spin {
from {
transform: rotate(0deg);
}
to {
transform: rotate(360deg);
}
}

@media (prefers-reduced-motion: no-preference) {
a:nth-of-type(2) .logo {
animation: logo-spin infinite 20s linear;
}
}

.card {
padding: 2em;
}

.read-the-docs {
color: #888;
}
13 changes: 13 additions & 0 deletions App.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@

import React from 'react'
import Weather from './components/Weather'

const App = () => {
return (
<div className='app'>
<Weather/>
</div>
)
}

export default App
Binary file added assets/clear.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added assets/cloudy.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added assets/drizzle.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added assets/humidity.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added assets/rain.jfif
Binary file not shown.
Binary file added assets/search.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added assets/snow.jfif
Binary file not shown.
Binary file added assets/windy.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
75 changes: 75 additions & 0 deletions components/Weather.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
.weather{
place-self:center;
padding:40px;
border-radius: 10px;
background-image: linear-gradient(135deg, rgb(88, 120, 88), #d4fc79, #96e6a1);
display: flex;
flex-direction: column;
align-items: center;
}

.search-bar img {
width: 24px;
padding:15px;
border-radius: 50%;
background: #d5f9da;
cursor:pointer;
}

.search-bar{
display: flex;
align-items: center;
gap:12px;
}

.search-bar input{
height: 50px;
border: none;
outline: none;
border-radius: 40px;
padding-left: 25px;
color:#3f472a;
background-color: #d5f9da;
font-size: 18px;
}

.weather-icon{
width: 150px;
margin:30px 0;
}

.temprature{
color: #3f472a;
font-size: 80px;
line-height: 1;
}

.location{
color:#3f472a;
font-size: 40px;
}

.weather-data{
width: 100%;
margin-top: 40px;
color:#3f472a;
display: flex;
justify-content:space-between;
}

.weather-data .col{
display: flex;
align-items: flex-start;
gap:12px;
font-size: 22px;
}

.weather-data .col span{
display: flex;
font-size: 16px;
}

.weather-data .col img{
width: 25px;
margin-top: 9px;
}
109 changes: 109 additions & 0 deletions components/Weather.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,109 @@

import React, { useEffect, useRef, useState } from 'react';
import './Weather.css';
import search_icon from '../assets/search.png';
import clear_icon from '../assets/clear.png';
import humidity_icon from '../assets/humidity.png';
import windy_icon from '../assets/windy.png';
import cloudy_icon from '../assets/cloudy.png';
import drizzle_icon from '../assets/drizzle.png';
import rain_icon from '../assets/rain.jfif';
import snow_icon from '../assets/snow.jfif';

const Weather = () => {
const inputRef = useRef();
const [weatherData, setWeatherData] = useState({});
const [loading, setLoading] = useState(false);
const [error, setError] = useState(null);

const allIcons = {
"01d": clear_icon,
"01n": clear_icon,
"02d": cloudy_icon,
"02n": cloudy_icon,
"03d": cloudy_icon,
"03n": cloudy_icon,
"04d": drizzle_icon,
"04n": drizzle_icon,
"09d": rain_icon,
"09n": rain_icon,
"10d": rain_icon,
"10n": rain_icon,
"13d": snow_icon,
"13n": snow_icon,
};

const search = async (city = 'London') => {
setLoading(true);
setError(null); // Reset error state
try {
const url = `https://api.openweathermap.org/data/2.5/weather?q=${city}&units=metric&appid=cefe612bcf0d2866aa80dbab07820af2`;
const response = await fetch(url);
if (!response.ok) {
throw new Error(`HTTP error! Status: ${response.status}`);
}
const data = await response.json();
console.log('API Data:', data); // Log the response data

if (data.weather && data.weather.length > 0) {
const icon = allIcons[data.weather[0].icon] || clear_icon;
setWeatherData({
humidity: data.main.humidity,
windSpeed: data.wind.speed,
temperature: Math.floor(data.main.temp), // Temp is already in Celsius
location: data.name,
icon: icon
});
} else {
throw new Error('Unexpected weather data format');
}
} catch (error) {
console.error('Error fetching weather data:', error.message);
setError(error.message);
setWeatherData({}); // Clear weather data on error
} finally {
setLoading(false);
}
};

useEffect(() => {
search();
}, []);

return (
<div className='weather'>
<div className='search-bar'>
<input ref={inputRef} type="text" placeholder='Search city' />
<img src={search_icon} alt='Search' onClick={() => search(inputRef.current.value)} />
</div>
{loading && <p>Loading...</p>}
{error && <p className='error-message'>Error: {error}</p>}
{!loading && !error && (
<>
{weatherData.icon && <img src={weatherData.icon} alt="Weather icon" className='weather-icon' />}
{weatherData.temperature !== undefined && <p className='temperature'>{weatherData.temperature}°C</p>}
{weatherData.location && <p className='location'>{weatherData.location}</p>}
<div className="weather-data">
<div className="col">
<img src={humidity_icon} alt="Humidity" />
<div>
<p>{weatherData.humidity}%</p>
<span>Humidity</span>
</div>
</div>
<div className="col">
<img src={windy_icon} alt="Wind Speed" />
<div>
<p>{weatherData.windSpeed} km/hr</p>
<span>Wind Speed</span>
</div>
</div>
</div>
</>
)}
</div>
);
};

export default Weather;

17 changes: 17 additions & 0 deletions index.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
@import url('https://fonts.googleapis.com/css2?family=Kalam:wght@300;400;700&family=Playfair+Display:ital,wght@0,400..900;1,400..900&display=swap');




*{
margin:0;
padding:0;
border: border-box;
font-family: "Kalam", cursive;
}

.app{
min-height: 100vh;
display: grid;
background: rgb(88, 120, 88);
}
10 changes: 10 additions & 0 deletions main.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import React from 'react'
import ReactDOM from 'react-dom/client'
import App from './App.jsx'
import './index.css'

ReactDOM.createRoot(document.getElementById('root')).render(
<React.StrictMode>
<App />
</React.StrictMode>,
)

0 comments on commit 074baf5

Please sign in to comment.