I'm making my portfolio where i have made a react component where i will be using grids from responsiveness. The Grid contains 2 columns, one contains the profile photo and the other contains my skills progress bar.
My grid works just fine on computer screens, but as soon as the screen size shrinks to less than 768px,
the second column suddenly becomes invisible.
below is my react code:
import React from 'react'
import img from '../../images/1cut.png'
import {
AboutContainer,
AboutWrapper,
AboutRow,
Column1,
Column2,
ImgWrapper,
Img,
TextWrapper,
TopLine,
Heading,
Progress,
ProgressDone,
} from './aboutMe2Elements'
const AboutMe2 = (props) => {
return (
<>
<AboutContainer id='about'>
<AboutWrapper>
<AboutRow>
<Column1>
<ImgWrapper>
<Img src={img} alt='Profile Photo' />
</ImgWrapper>
</Column1>
<Column2>
<TextWrapper>
<TopLine>My Skills</TopLine>
<Heading>Frontend Development</Heading>
<Progress>
<ProgressDone width={85}></ProgressDone>
</Progress>
<Heading>Backend Development</Heading>
<Progress>
<ProgressDone width={75}></ProgressDone>
</Progress>
<Heading>Data Structures and Algorithms</Heading>
<Progress>
<ProgressDone width={69}></ProgressDone>
</Progress>
</TextWrapper>
</Column2>
</AboutRow>
</AboutWrapper>
</AboutContainer>
</>
)
}
export default AboutMe2
Here is my styled components code:
import styled from 'styled-components'
export const AboutContainer = styled.div`
color: #fff;
background: #010606;
#media screen and(max-width:768px) {
padding: 100px 0;
}
`
export const AboutWrapper = styled.div`
display: grid;
z-index: 1;
height: 900px;
width: 100%;
max-width: 1100px;
margin-right: auto;
margin-left: auto;
padding: 0 24px;
justify-content: center;
`
export const AboutRow = styled.div`
display: grid;
grid-auto-columns: minmax(auto, 1fr);
align-items: center;
grid-template-areas: 'col1 col2';
#media screen and (max-width: 1100px) {
grid-template-areas: 'col1 ' 'col2';
}
`
export const Column1 = styled.div`
margin-bottom: 15px;
padding: 0 15px;
grid-area: col1;
`
export const Column2 = styled.div`
margin-bottom: 15px;
padding: 0 15px;
grid-area: col2;
`
export const ImgWrapper = styled.div`
max-width: 555px;
height: 100%;
background: #010606;
`
export const Img = styled.img`
width: 100%;
margin: 0 0 10px 10;
background: #010606;
padding-right: 0;
`
export const TextWrapper = styled.div`
max-width: 540px;
padding-top: 0;
padding-bottom: 60px;
`
export const TopLine = styled.p`
color: #01bf71;
font-size: 20px;
line-height: 16px;
font-weight: 700;
letter-spacing: 1.4px;
text-transform: uppercase;
margin-bottom: 16px;
`
export const Heading = styled.h1`
color: #fff;
margin-bottom: 24px;
font-size: 28px;
line-height: 1.1;
font-weight: 600;
color: #f7f8fa;
#media screen and (max-width: 480px) {
font-size: 32px;
}
`
export const Progress = styled.div`
background-color: #fff;
border-radius: 20px;
position: relative;
margin: 15px 0;
height: 20px;
width: 300px;
`
export const ProgressDone = styled.div`
background: #01bf71;
/* box-shadow: 0 3px 3px -5px #01bf71, 0 2px 5px #01bf71; */
border-radius: 20px;
color: #fff;
display: flex;
align-items: center;
justify-content: center;
height: 100%;
width: ${(props) => (props.width ? props.width + '%' : 0)};
opacity: 1;
transition: 1s ease 0.3s;
`
This is how it looks on on a computer screen
This is how it looks like on a mobile screen
Related
I'm trying to add Dark Mode to my website, which is built in React, that I've created, and while I don't want to create an actual Dark Mode, I want to add lazy dark mode using filter: invert(1) in CSS.
The issue came mainly when trying to communicate between the TSX file and CSS file to check which mode do I want to show, and trying to use data-theme doesn't seem to work for me.
My App.tsx is as follows:
function App() {
const defaultDark = window.matchMedia('(prefers-color-scheme: dark)').matches;
const [theme, setTheme] = useLocalStorage('theme', defaultDark ? 'dark' : 'light');
const toggleTheme = () => {
setTheme(theme === 'light' ? 'dark' : 'light');
console.log(theme);
}
return (
<div className="outer-container" id="outer-container" data-theme={theme}>
<Sidebar />
<button onClick={toggleTheme}>
Click here to switch to {theme === 'light' ? 'dark' : 'light'} mode
</button>
<div className='page'>
<Outlet />
</div>
<Footer />
</div>
);
}
export default App;
(I do have certain imports but all the components are different file)
My App.css is as follows:
.outer-container {
display: flex;
flex-direction: column;
min-height: 85vh;
}
.page {
flex: 1;
}
footer {
position: relative;
margin: 0 1rem;
}
footer .row {
display: flex;
flex-direction: row;
width: 100%;
justify-content: space-between;
}
hr {
height: 0px;
margin: 0;
border: 1px solid #000000;
}
p#p1 {
position: absolute;
width: 20vw;
height: 34px;
left: 19px;
font-family: 'PT Serif';
font-style: normal;
font-weight: 400;
font-size: 13px;
line-height: 95.52%;
/* or 12px */
color: #000000;
}
p#p2 {
position: absolute;
width: 20vw;
height: 34px;
left: calc(50vw - 10vw);
font-family: 'PT Serif';
font-style: normal;
font-weight: 400;
font-size: 13px;
line-height: 95.52%;
/* or 12px */
color: #000000;
}
p#p3 {
position: absolute;
width: 20vw;
height: 34px;
left: calc(100vw - 20vw);
font-family: 'PT Serif';
font-style: normal;
font-weight: 400;
font-size: 13px;
line-height: 95.52%;
color: #000000;
}
div.main {
position: absolute;
width: 20vw;
height: 34px;
top: 5vw;
left: calc(100vw - 20vw);
}
a.social {
margin: 0 1rem;
transition: transform 250ms;
display: inline-block;
align-items: center;
}
a.social:hover {
transform: translateY(-2px);
}
a.youtube, a.youtube:hover {
color: #eb3223;
}
a.github, a.github:hover {
color: #24292e;
}
a.discord, a.discord:hover {
color: #7289da;
}
html[data-theme='dark'] {
filter: invert(1) hue-rotate(180deg);
}
(I'm not sure if it matters and hence I've shown the whole thing, but the important thing is the last one; also I do have some CSS for internal components)
However, even so, when I click on the button, nothing changes, even though the value of the theme changes. How would I fix this?
Thank you :)
I have made some pure banner CSS js with react. Right now it's static not autoplay. How to make my banner autoplay properly and responsive for mobile. Autoplay and smooth transition when going to another banner.
This is the code for working static banner without autoplay things :
import { ArrowLeftOutlined, ArrowRightOutlined } from "#material-ui/icons"
import { useState } from 'react'
import styled from "styled-components"
import {sliderItems} from '../data'
const Container = styled.div`
width: 100%;
height: 80vh;
display: flex;
position: relative;
overflow: hidden;
`
const Arrow = styled.div`
width: 50px;
height: 50px;
background-color: #fff7f7;
border-radius: 50%;
display: flex;
align-items: center;
justify-content: center;
position: absolute;
top: 0;
bottom: 0;
left: ${props=> props.direction === "left" && "10px"};
right: ${props=> props.direction === "right" && "10px"};
margin: auto;
cursor: pointer;
opacity: 0.5;
z-index: 2;
`
const Wrapper = styled.div`
height: 100%;
display: flex;
transition: all 1.5s ease;
transform: translateX(${props=>props.slideIndex * -100}vw);
`
const Slide = styled.div`
width: 100vw;
height: 100vh;
display: flex;
align-items: center;
background: ${props => `url(${props.bg}) no-repeat top center`};
`
const ImgContainer = styled.div`
height: 80%;
flex: 1;
`
const Image = styled.img`
height: 80%;
`
const Image2 = styled.img`
height: 40%;
`
const InfoContainer = styled.div`
flex: 1;
padding: 50px;
`
const Title = styled.h1`
color: white;
font-size: 70px;
`
const Desc = styled.p`
color: white;
margin: 50px 0px;
font-size: 20px;
font-weight: bold;
letter-spacing: 3px;
`
const Button = styled.button`
border: 1px solid white;
padding: 10px;
font-size: 20px;
color: #0070ba;
background-color: white;
border-radius: 25px;
cursor: pointer;
font-weight: 800;
&:hover{
color: white;
background-color: #0070ba;
}
`
const Banner = () => {
const [slideIndex, setSlideIndex] = useState(0)
const handleClick = (direction) => {
if(direction==="left"){
setSlideIndex(slideIndex > 0 ? slideIndex-1 : 6)
} else {
setSlideIndex(slideIndex < 6 ? slideIndex +1 : 0)
}
}
return (
<Container>
<Arrow direction="left" onClick={()=>handleClick("left")}>
<ArrowLeftOutlined />
</Arrow>
<Wrapper slideIndex={slideIndex}>
{sliderItems.map(item=>(
<Slide bg={item.bg}>
<Image2 src={item.img2}/>
<InfoContainer>
<Title>{item.title}</Title>
<Desc>{item.desc}</Desc>
<Button>COBA SEKARANG</Button>
</InfoContainer>
<ImgContainer>
<Image src={item.img}/>
</ImgContainer>
</Slide>
))}
</Wrapper>
<Arrow direction="right" onClick={()=>handleClick("right")}>
<ArrowRightOutlined />
</Arrow>
</Container>
)
}
export default Banner
Thank you guys for helping!
I am trying to make a button that allows the user to switch between light and dark theme. The method I am using is to change the className of my App div. All of the other components in my project are inside of the App component. Then in the individual CSS files for the components I first select the className of the App div which is either .light or .dark. Then I write the name of the component that I want to set a theme color to. For example:
.light p {
background-color: white;
}
However, this doesn't work.
Here are some of the files:
/*App.js*/
import { useState } from "react";
import TaskPage from "./pages/taskPage";
import { fas } from "#fortawesome/free-solid-svg-icons";
import { library } from "#fortawesome/fontawesome-svg-core";
import { MainContextProvider } from "./store/MainContext";
library.add(fas);
function App() {
const [theme, setTheme] = useState("light");
const switchTheme = () => {
setTheme((prevTheme) => (prevTheme === "light" ? "dark" : "light"));
};
return (
<MainContextProvider>
<div className={`App ${theme}`}>
<div className="pageTop">
<h1 className="title">Task Board</h1>
</div>
<button className="button" onClick={switchTheme}>
Change theme
</button>
<TaskPage />
</div>
</MainContextProvider>
);
}
export default App;
/*index.css*/
#import url("https://fonts.googleapis.com/css2?family=Roboto:wght#400;500;700&display=swap");
.App {
overflow-x: hidden;
padding-bottom: 40px;
height: 100%;
width: 100%;
}
.light {
background-color: #fcfcfc;
}
.dark {
background-color: #181A1B;
}
.title {
font-family: "Roboto", sans-serif;
font-size: 50px;
font-weight: 700;
text-align: center;
margin-top: 40px;
text-shadow: 0px 3px 4px rgba(0, 0, 0, 0.2);
}
.light .title {
color: black;
}
.dark .title {
color: white;
}
.pageTop {
margin-bottom: 50px;
}
/*todo.module.css*/
.taskCard {
box-shadow: 0 4px 8px 0 rgba(0, 0, 0, 0.2);
transition: 0.3s;
width: 340px;
height: 260px;
min-width: 340px;
min-height: 260px;
display: flex;
flex-wrap: wrap;
flex-direction: column;
border-radius: 12px;
padding: 14px;
box-sizing: border-box;
}
.light .taskCard {
background-color: white;
}
.dark .taskCard {
background-color: #2B2E30;
}
I used this sandbox as an example: https://codesandbox.io/s/stupefied-jackson-0ynz6?file=/src/App.js
I am a beginner with React.js
I’d like two hide one div and show another one with animation from right to left and the progress bar has to stay in its position. The one already visible has to hide from right to left and the one that is hidden has to become visible with animation from right to left. I saw that with position: absolute on the two div can work, but then the progress bar would move up the page, above the divs. How could you do it?
The div that is already visible is "RegisterChoice" and I want to hide it and show "RegisterChoiceEmail".
I use React and bootstrap for the progress bar.
Thanks in advance!
import React, {useState} from 'react'
import $ from 'jquery';
import 'jquery-ui';
import "jquery-ui/ui/effects/effect-slide";
import {ProgressBar, Button} from 'react-bootstrap';
import {Register, RegisterChoice, RegisterChoiceEmail, RegisterChoiceH1, RegisterChoiceWrapper, RegisterChoiceWrapperEmail, RegisterChoiceCard, RegisterChoiceIcon, RegisterChoiceH2} from './SceltaRegistrazioneElements'
import FacebookLogin from 'react-facebook-login';
import {FaFacebookF} from 'react-icons/fa';
import GoogleLogin from 'react-google-login';
import GoogleButton from 'react-google-button';
const responseFacebook = (response) => {
console.log(response);
console.log(response.profileObj);
}
const responseGoogle = (response) => {
console.log(response);
console.log(response.profileObj);
}
const Registrazione = () => {
const [percentage, setPercentage] = useState(20);
let active = 'registerChoice';
function RegisterChoiceClicked() {
return (
$("#"+active ).hide("slide", { direction: "left" }, 500),
$("#registerChoiceEmail").delay(600).show("slide", { direction: "left" }, 500).css("display", "flex"),
setPercentage((oldPercentage) => {
return oldPercentage + 20;
})
)
}
return (
<Register>
<RegisterChoice id="registerChoice">
<RegisterChoiceH1>Sei una struttura, vuoi diventare un pet sitter o un cliente?</RegisterChoiceH1>
<RegisterChoiceWrapper>
<RegisterChoiceCard onClick={RegisterChoiceClicked}>
<RegisterChoiceIcon src={require('../../../images/structure.jpg').default}/>
<RegisterChoiceH2>Struttura</RegisterChoiceH2>
</RegisterChoiceCard>
<RegisterChoiceCard onClick={RegisterChoiceClicked}>
<RegisterChoiceIcon src={require('../../../images/petSitter.jpg').default}/>
<RegisterChoiceH2>Pet sitter</RegisterChoiceH2>
</RegisterChoiceCard>
<RegisterChoiceCard onClick={RegisterChoiceClicked}>
<RegisterChoiceIcon src={require('../../../images/client.jpg').default}/>
<RegisterChoiceH2>Cliente</RegisterChoiceH2>
</RegisterChoiceCard>
</RegisterChoiceWrapper>
</RegisterChoice>
<RegisterChoiceEmail id="registerChoiceEmail">
<RegisterChoiceH1>Come vuoi registrarti?</RegisterChoiceH1>
<RegisterChoiceWrapperEmail>
<Button variant="primary w-50" style={{marginBottom: "20px", height: "50px", minWidth: "240px", width: "50%"}} onClick={RegisterChoiceClicked}>Accedi con l'email</Button>
<FacebookLogin
appId=""
autoLoad={false}
fields="name,email,picture"
callback={responseFacebook}
textButton="Registrati con Facebook"
icon={<FaFacebookF style={{marginRight: "10px", marginBottom: "3px"}}></FaFacebookF>}
cssClass="btnFacebook"
language="it_IT"
/>
<GoogleLogin
clientId=""
buttonText="Accedi con Google"
onSuccess={responseGoogle}
onFailure={responseGoogle}
cookiePolicy={'single_host_origin'}
isSignedIn={true}
language="it_IT"
render={renderProps => (
<GoogleButton
onClick={renderProps.onClick}
label='Registrati con Google'
style={{fontWeight: "700", fontFamily: "Helvetica, sans-serif", WebkitFontSmoothing: "antialiased", justifyContent: "center", minWidth: "240px", width: "50%"}}
/>
)}
/>
</RegisterChoiceWrapperEmail>
</RegisterChoiceEmail>
<ProgressBar id="progressBar" striped animated variant="success" now={percentage} style={{width: "70%", margin: "90px auto"}} />
</Register>
)
}
export default Registrazione
In another file, 'RegistrazioneElements.js':
import styled from "styled-components";
export const Register = styled.div`
min-height: 100vh;
background: #010606;
padding-bottom: 30px;
clear: both;
overflow: auto;
padding: 0px 10px 10px 10px;
`
export const RegisterChoice = styled.div`
display: flex;
flex-direction: column;
align-items: center;
clear: both;
#media screen and (max-width: 1250px) {
padding: 20px;
}
`
export const RegisterChoiceEmail = styled.div`
flex-direction: column;
align-items: center;
display: none;
#media screen and (max-width: 1250px) {
padding: 20px;
}
`
export const RegisterChoiceWrapper = styled.div`
justify-content: center;
display: grid;
grid-template-columns: 1fr 1fr 1fr;
grid-gap: 16px;
padding: 40px 50px;
width: 70%;
#media screen and (max-width: 1250px){
grid-template-columns: 1fr 1fr;
padding: 0px 0px;
}
#media screen and (max-width: 980px){
grid-template-columns: 1fr;
padding: 20px 0px;
}
`
export const RegisterChoiceWrapperEmail = styled.div`
display: flex;
flex-direction: column;
padding: 40px 50px;
width: 70%;
justify-content: center;
> {
text-align: center;
}
`
export const RegisterChoiceCard = styled.div`
background: #fff;
display: flex;
flex-direction: column;
align-items: center;
border-radius: 10px;
min-height: 300px;
max-height: 340px;
padding: 30px;
box-shadow: 0 1px 3px rgba(0,0,0,0.2);
transition: all 0.2 ease-in-out;
cursor: pointer;
&:hover {
transform: scale(1.02);
transition: all 0.2s ease-in-out;
}
`
export const RegisterChoiceIcon = styled.img`
height: 240px;
width: 240px;
margin-bottom: 30px;
`
export const RegisterChoiceH1 = styled.h1`
font-size: 2.5rem;
color: #fff;
margin-bottom: 30px;
padding-top: 150px;
#media screen and (max-width: 480px) {
font-size: 2rem;
}
`
export const RegisterChoiceH2 = styled.h2`
font-size: 1rem;
margin-bottom: 10px;
font-weight: bold;
`
I'm still a beginner with ReactJS and I need to create a Carousel that is responsive, the way I need to leave is like this:
I was able to create Carousel on both desktop and responsive using the react-responsive-carousel library.
The problem is that in the mobile format, when I pass the slides of each Carousel, the expected behavior is not happening. When I click to show the next slide, in Carousel it still shows the current slide, and just a piece of the next slide.
It is easier to explain by showing a short gif I made, notice what happens when I click to show the next slide.
When it is in the desktop format, Carousel works the right way, I also created a small gif to show it.
Can you tell me what you’re doing wrong so that Carousel is working that way?
import React from "react";
import PropTypes from "prop-types";
import "./carousel.scss";
import { Carousel as CarouselLib } from "react-responsive-carousel";
import { CAROUSEL_ITEMS } from "./Carousel.utils";
const Carousel = ({ subtitle, testID, title }) => {
const items = React.useMemo(
() =>
CAROUSEL_ITEMS.map((item) => (
<div key={item.id}>
<div className="images">
<img className="image" src={item.url} alt="" />
</div>
<div className="infos">
<h3>{item.title}</h3>
<span>{item.subtitle}</span>
</div>
</div>
)),
[]
);
return (
<div data-testid={`${testID}_Container`} className="carousel-container">
<div className="carousel-header">
<h5>{subtitle}</h5>
<h3>{title}</h3>
</div>
<div className="carousel-content">
<CarouselLib
centerMode
showStatus={false}
dynamicHeight={false}
emulateTouch
swipeScrollTolerance={50}
centerSlidePercentage={30}
showThumbs={false}
infiniteLoop
showIndicators
renderArrowPrev={(onClickHandler, hasPrev, label) =>
hasPrev && <div />
}
renderArrowNext={(onClickHandler, hasNext, label) =>
hasNext && (
<button
type="button"
onClick={onClickHandler}
className="custom-arrow"
data-testid={`${testID}_Button_Next`}
/>
)
}
>
{items}
</CarouselLib>
</div>
</div>
);
};
Carousel.propTypes = {
subtitle: PropTypes.string,
testID: PropTypes.string.isRequired,
title: PropTypes.string
};
Carousel.defaultProps = {
testID: "Carousel",
subtitle: "READ OUR CLIENT",
title: "CASES"
};
export default Carousel;
.carousel {
&-container {
.images {
background-color: #fff;
width: 100%;
max-width: 416px;
height: 280px;
.image {
width: 100%;
height: auto;
background-position: center center;
background-repeat: no-repeat;
}
#media (max-width: 600px) {
max-width: 270px;
height: auto;
}
}
.infos {
display: flex;
flex-direction: column;
justify-content: center;
align-items: flex-start;
h3 {
font-family: Alliance2;
color: #000;
line-height: 0.76;
font-size: 2.5rem;
letter-spacing: normal;
font-style: normal;
font-weight: normal;
font-stretch: normal;
margin: 24px 0 20px 0;
#media (max-width: 600px) {
font-size: 1.5rem;
}
}
span {
font-family: Alliance2;
color: #000;
line-height: 0.76;
font-size: 1rem;
letter-spacing: normal;
font-style: normal;
font-weight: 500;
font-stretch: normal;
text-transform: uppercase;
margin-bottom: 30px;
#media (max-width: 600px) {
font-size: 0.625rem;
}
}
}
.carousel {
.slide {
background-color: transparent !important;
#media (max-width: 1024px) {
min-width: 50% !important;
}
#media (max-width: 600px) {
min-width: 90% !important;
}
}
.control-dots {
.dot {
border-radius: 0 !important;
background-color: #000 !important;
width: 33px !important;
height: 3px !important;
box-shadow: none !important;
opacity: 1 !important;
&.selected {
height: 7px !important;
}
&:focus {
outline: none !important;
}
}
}
}
}
&-header {
color: #000;
font-family: 'Alliance2';
font-weight: 300;
margin: auto;
max-width: 1300px;
text-transform: uppercase;
#media (max-width: 960px) {
align-items: center;
display: flex;
flex-direction: column;
}
h5 {
font-size: 1rem;
font-weight: bold;
margin: 0;
}
h3 {
height: 80px;
margin-top: 13px;
margin-bottom: 44px;
color: #000;
font-size: 3.5rem;
line-height: 1.04;
letter-spacing: -1.1px;
#media (max-width: 960px) {
font-size: 1.87rem;
}
#media (max-width: 600px) {
margin-bottom: 0;
}
}
}
&-content {
margin: auto;
max-width: 1440px;
width: 100%;
.custom-arrow {
position: absolute;
top: 7em;
bottom: auto;
right: 4.3em;
background-color: transparent;
border: none;
border-left: 4px solid #000;
border-bottom: 4px solid #000;
width: 67px;
height: 67px;
transform: rotate(225deg);
cursor: pointer;
&:focus {
outline: none !important;
}
}
}
}
Thank you very much in advance for any help/tip.
I don't know react-responsive-carousel , I'm using react-slick (here) in my projects and I never had a problem with the responsive.
I had a similar trouble with this lib, i solved the mobile question adding a few lines of CSS to the main div of my Carousel component:
#media only screen and (max-width: 600px) {
.carousel-wrapper{
max-width: 100%;
}
}