'Changing video-background based on weather description using React
I am trying to have it so that the video background of my weather app will change based on the weather condition using React. This is my App.js
import React, { useState } from "react";
import axios from 'axios';
import Background from './Background';
function App() {
const [location,setLocation] = useState('')
const [data,setData] = useState({})
const apiUrl = `https://api.openweathermap.org/data/2.5/weather?q=${location}&appid=681134f49a40ffa25a43fd6bd3a2f480`
const searchLocation = (event) => {
if(event.key === 'Enter') {
axios.get(apiUrl + "&units=metric")
.then((response) => {
setData(response.data)
console.log(response.data)
})
}
}
return (
<div className="app">
<div className="search">
<input
value={location}
onChange={event => setLocation(event.target.value)}
onKeyPress = {searchLocation}
placeholder='Enter Location'
type="text"/>
</div>
<div className="container">
<div>
<Background weatherDescription = {data.weather ? <p>{data.weather[0].main}</p> : null} />
</div>
<div className="top">
<div className="location">
<p>{data.name}</p>
</div>
<div className="temp">
{data.main ? <h1>{data.main.temp.toFixed()}°C</h1> : null}
</div>
<div className="description">
{data.weather ? <p>{data.weather[0].main}</p> : null}
</div>
</div>
{data.name != undefined &&
<div className="bottom">
<div className="feels">
{data.main ? <p className="bold">{data.main.feels_like.toFixed()}°C</p> : null}
<p>Feels Like</p>
</div>
<div className="humidity">
{data.main ? <p className="bold">{data.main.humidity}%</p> : null}
<p>Humidity</p>
<p></p>
</div>
<div className="wind">
{data.wind ? <p className="bold">{data.wind.speed.toFixed()} KPH</p> : null}
<p>Wind Speed</p>
</div>
</div>
}
</div>
</div>
);
}
export default App;
An this is my video background component, Background.js
import React from "react";
import video1 from "./Videos/Clouds.mp4";
import video2 from "./Videos/Thunderstorm.mp4";
function Background(props) {
const videos = [
{
name:"Clouds",
background: video1
},
{
name:"Thunderstorm",
background: video2
}
]
return (
<div>
<video id="background" autoPlay loop muted>
<source src = {props.weatherDescription === videos[0].name ? null : videos[0].background} type="video/mp4"/>
</video>
</div>
)
}
export default Background;
I have passed in the 'weatherDescription' props in App.js so that I can use it in Background.js. I have already tried If-else and I have tried ternary operator as well but it is not changing based on the description. Due to how the weatherAPI works a ternary operator has to be used to access the weather description.
I am very new to React and I am pretty sure that I am passing in the props correctly. Would you be able to see what I am doing wrong? I have tried console.logging stuff but I haven't had much luck.
Solution 1:[1]
- In your App.js, the props.weatherDescription you pass to Background component is JXS element(
<p>{data.weather[0].main}</p>), it should be a value as string to compare, fix it like following:
<div>
<Background weatherDescription = {data.weather ? data.weather[0].main : null} />
</div>
- On source tag of video, It's src have to suitable with videos array.
- You have to put key={videoURL} to tell React know which video to update. Below is this Background.js i think will help you:
import React from "react";
import video1 from "./Videos/Clouds.mp4";
import video2 from "./Videos/Thunderstorm.mp4";
function Background(props) {
const videos = [
{
name:"Clouds",
background: video1
},
{
name:"Thunderstorm",
background: video2
}
]
const videoURL = videos.find(el => el.name === props.weatherDescription)?.background
return (
<div>
<video id="background" key={videoURL} autoPlay loop muted>
<source src = {videoURL} type="video/mp4"/>
</video>
</div>
)
}
export default Background;
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | VMT |
