Active dots class on Slick Slider with ReactJS - reactjs

so I'm using slick slider on my ReactJS app, by the config I set custom class from my modular CSS, slick slider dots active class (".slick-active) is automatically toggled
but my CSS wont applied, how is the proper way to style the active state of the dots
thanks in advance,
import style from "./MainSlider.module.scss";
const settings = {
dots: true,
infinite: true,
autoplaySpeed: 5000,
speed: 1500,
autoplay: true,
dotsClass: style.slickDots,
slidesToShow: 1,
slidesToScroll: 1
};
<Slider {...settings}>
{
sliderItems.map((sliderItem, idx) => (
<div key={idx} className={style.sliderItem}>
<div className={style.image}>
<img src={sliderItem.image} alt="" />
</div>
<div className={style.text}>
<p>{sliderItem.title}</p>
<Link to="/service" className={style.more}>
<img src={ViewMore} alt=""/>
</Link>
</div>
</div>
))
}
</Slider>
this is my MainSlider.module.scss
.slider {
width: 70vw;
height: 70vh;
.slickDots {
position: absolute;
bottom: -50px;
display: block;
width: 100%;
padding: 0;
margin: 0;
list-style: none;
li{
position: relative;
display: inline-block;
margin-right: 30px;
padding: 0;
cursor: pointer;
&.slick-active {
background: magenta !important;
button {
&::before {
background: red;
}
}
}
button {
font-size: 0;
line-height: 0;
display: block;
width: 15px;
height: 15px;
border-radius: 50%;
border:2px solid white;
cursor: pointer;
outline: none;
background: transparent;
&::before {
position: absolute;
top: 0;
left: 0;
width: 15px;
height: 15px;
border-radius: 50%;
content: ' ';
color: black;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
}
}
}
}
}
I add image instead of code so it will be more readable and can help you understand more about my problem
code

For applying your styles to global styles, like slick-active in css-modules you should use this approach:
:global(.slick-active) {
background-color: red;
}

Related

Structuring Sidebar in React

Relatively new to React, and am wanting to recreate the design below
enter image description here
I have the base formatting down, but as you will notice, there are lines separating the logo blocks, from the login and signup blocks, with the signup and login buttons pushed to the bottom.
Below is my current code
CSS:
width: 100vw;
height: 100vh;
}
body {
margin: 0;
padding: 0;
}
.Sidebar {
height: 100%;
width: 20%;
background-color: white;
border-right: 1px solid #F0F4FB;
padding-left: 15px;
box-sizing: border-box;
}
.SidebarList {
height: auto;
width: 100%;
padding-left: 15px;
font-size: 18px;
border: 2px #FD954E;
box-sizing: border-box
}
.SidebarList .row {
width: 100%;
height: 50px;
background-color: white;
list-style-type: none;
margin: 0%;
padding-bottom: 15px;
display: flex;
color: #A7ACB6;
justify-content: center;
align-items: center;
font-family: Arial, Helvetica, sans-serif;
}
.SidebarList .row:hover {
cursor: pointer;
background-color: #E7E7E7 ;
}
.SidebarList #active {
background-color: white;
color: #FD954E
}
.SidebarList .Login {
background-color: white;
color: #FD954E;
width: 279px;
height: 39px;
right: 1596px;
top: 958px;
border: 1px solid #FD954E;
box-sizing: border-box;
border-radius: 19.5px;
}
.SidebarList .SignUp {
width: 279px;
height: 39px;
right: 1596px;
top: 1011px;
background: #FD954E;
border-radius: 19.5px;
border: none;
}
.row #icon {
flex: 30%;
display: grid;
place-items: center;
transform: scale(1.2)
}
.row #title {
flex: 70%;
}
.Logo {
padding-left: 25px;
padding-top: 25px;
padding-bottom: 30px;
border-bottom: 1px solid #F0F4FB;
width: 55%;
}
Sidebar.js
import React from "react";
import "../App.css";
import { SidebarData } from './SidebarData'
import Logo from './Logo.svg'
function Sidebar() {
return (
<div className="Sidebar">
<div>
<img src = {Logo} alt='Logo’ className=‘Logo’ />
</div>
<ul className="SidebarList">
{SidebarData.map((val, key) => {
return (
<li
key={key}
className="row"
id={window.location.pathname == val.link ? "active" : ""}
onClick={() => {
window.location.pathname = val.link;
}}
>
<div id="icon">{val.icon}</div> <div id="title">{val.title}</div>
</li>
);
})}
</ul>
<div className= "SidebarList">
<button className="Login">
Login
</button>
</div>
<div className= "SidebarList">
<button className="SignUp">
Sign Up
</button>
</div>
</div>
);
}
export default Sidebar;
How should I structure my code in order to acheive my desired result? Ex: with the logo at the top with the seperator, the list of navigation elements, and then the login and signup buttons at the bottom with the seperator?
Currently, my sidebar looks as follows, with the seperator not full width between the logo and navigation elements, and the buttons extending beyond the sidebar.
enter image description here
It would be easier to simplify the problem with just HTML and CSS as that's much easier to troubleshoot. Part of your problem is that you are defining the width of the sidebar as a percentage of the screen width but elements within the sidebar are defined with a width in pixels. When the browser window is too small, your buttons will appear outside the full width of the sidebar. You could either code all your values as percentages or in pixels. Alternatively, you could use a mix and just set a min-width for the sidebar so that you don't end up with elements out of place.
The reason that your line break is not the full width of your sidebar is because you are defining it with the border-bottom property of the logo. Your logo is not 100% the width of the sidebar so your line break will only be the width of the logo. A better solution would be to define a div that is set to width: 100%. This way, you will have more control.
Here is a simplified solution to your sidebar problem using pixels to define the widths.
HTML:
<div class="sidebar">
<div class="header">
<div class="logo">Logo</div>
</div>
<div class="line-break" />
<div class="content">
<ul class="nav">
<li>Home</li>
<li>Blog</li>
</ul>
</div>
<div class="line-break" />
<div class="footer">
<button class="login">Login</button>
<button class="sign-up">Sign up</button>
</div>
</div>
CSS:
html, body {
height: 100%;
margin: 0;
padding: 0;
}
.sidebar {
width: 300px;
height: 100%;
border-right: 1px solid grey;
}
.line-break {
height: 1px;
width: 100%;
background-color: grey;
}
.header .logo {
height: 40px;
width: 200px;
background-color: grey;
margin: 20px;
}
ul.nav {
list-style-type: none;
padding: 20px 0 0 40px;
}
ul.nav li {
margin-bottom: 14px;
}
ul.nav li:last-child {
margin-bottom: 0;
}
.footer {
display: flex;
flex-direction: column;
align-items: center;
padding: 20px 0;
}
.footer button {
padding: 6px 0;
width: 80%;
margin-bottom: 14px;
}
.footer button:last-child {
margin-bottom: 0;
}
And here is a link to a CodePen
where you can see this in action.

How to make react slick carousel resizable when I zoom out?

So like the title says, what I am trying to achieve is that when I zoom out, I want my carousel to be 100% width of the screen all time, here is what I mean by that. Right now when I zoom out, my carousel looks like this:
But when it is 100% zoom, a.k.a my normal screen it looks like this:
So, how do I make this be resizable meaning it is going to be like it is on a normal screen (100%) on every zoom.
Here is my code:
const Works = () => {
var settings = {
centerMode: true,
dots: true,
infinite: true,
speed: 500,
slidesToShow: 4,
slidesToScroll: 1,
centerPadding: "10px",
customPaging: (i) => <div className="works-dots"></div>,
arrows: false,
};
return (
<div className="mainWorks-container">
<div className="works-popup-container">
<h3 className="works-title">WORKS</h3>
<div className="works-popup-image-container">
<Slider {...settings}>
{worksImages.map((image, index) => {
return (
<div key={index} className="works-image">
<img
src={image.image}
alt={image.alt}
className="works-popup-image"
/>
<div className="image-overlay">
<h3>{image.title}</h3>
</div>
</div>
);
})}
</Slider>
</div>
</div>
<div className="works-button-container">
<a href="/">
<Button text="View Works" isFilled={false} type="border" />
</a>
</div>
</div>
);
};
export default Works;
This is my Works.js component.
.mainWorks-container {
height: 675px;
position: relative;
}
.works-popup-container {
height: 780px;
width: 986px;
background: url("../../../images/gradient-background.jpg") no-repeat;
background-size: cover;
position: absolute;
top: 10%;
left: 50%;
transform: translate(-50%, -50%);
border-radius: 10px;
}
.works-title {
margin-top: 50px;
letter-spacing: 0.5em;
font-size: 12px;
color: white;
text-align: center;
}
.works-popup-image-container {
.slick-list {
position: relative;
left: -30%;
width: 105rem;
}
.works-image {
position: relative;
margin-bottom: 8rem;
width: 385px;
height: 513px;
border-radius: 3px;
box-shadow: 0px 70px 100px -40px rgba(0, 0, 0, 0.5);
img {
width: 385px;
height: 100%;
object-fit: contain;
cursor: pointer;
}
.image-overlay {
position: absolute;
top: 0;
left: 0;
width: 91.7%;
background: rgba(0, 0, 0, 0.5);
height: 100%;
display: flex;
justify-content: center;
align-items: center;
color: white;
opacity: 0;
cursor: pointer;
text-align: center;
font-size: 1.2rem;
word-break: break-word;
}
.image-overlay:hover {
opacity: 1;
}
}
}
.works-dots {
background: rgba(247, 247, 247, 0.75);
border-radius: 50%;
width: 8px;
height: 8px;
margin: 0 5px;
}
.works-dots:hover {
height: 10px;
width: 10px;
transition: all 0.2s ease;
}
.slick-active {
.works-dots {
height: 10px;
width: 10px;
}
}
.works-button-container {
position: absolute;
top: 90%;
left: 50%;
transform: translate(-50%, -50%);
}
And this is my worksStyles.scss file.
If anyone knows how to do this, I would be thankful.

Is it possible to use the same React component with different CSS, using css modules?

I found the React CSS modules usefull, but having problem when I tried to reuse the same component with a little modified css I stuck. For example I created Neon glowing button, but now need to change only the width of the Button and some additional small changes in the css.
The only option I see is component without css and for every different case need to rewrite the whole css. Is there a smarter way?
import React from "react";
import styles from "./index.module.css";
import { Link } from "react-router-dom";
const GlowingButton = ({ title, path }) => {
return (
<div className={styles.buttonWrapper}>
<Link className={styles.button} to={path}>
<button className={styles["glow-on-hover"]}>{title}</button>
</Link>
</div>
);
};
export default GlowingButton;
And here is index.module.css
.buttonWrapper {
margin: 0px;
padding: 0px;
display: flex;
justify-content: center;
align-items: center;
background: transparent;
font-family: "consolas";
}
.button {
margin: 0;
padding: 0;
width: 80%;
height: 8vh;
display: flex;
flex-direction: row;
justify-content: center;
align-items: center;
background: #100f;
text-decoration: none;
}
.glow-on-hover {
width: 400px;
height: 50px;
border: none;
outline: none;
color: #fff;
background: #111;
cursor: pointer;
position: relative;
z-index: 0;
border-radius: 10px;
}
.glow-on-hover:before {
content: "";
background: linear-gradient(
45deg,
#ff0000,
#ff7300,
#fffb00,
#48ff00,
#00ffd5,
#002bff,
#7a00ff,
#ff00c8,
#ff0000
);
position: absolute;
top: -2px;
left: -2px;
background-size: 400%;
z-index: -1;
filter: blur(5px);
width: calc(100% + 4px);
height: calc(100% + 4px);
animation: glowing 20s linear infinite;
opacity: 0;
transition: opacity 0.3s ease-in-out;
border-radius: 10px;
}
.glow-on-hover:active {
color: #000;
}
.glow-on-hover:active:after {
background: transparent;
}
.glow-on-hover:hover:before {
opacity: 1;
}
.glow-on-hover:after {
z-index: -1;
content: "";
position: absolute;
width: 100%;
height: 100%;
background: #111;
left: 0;
top: 0;
border-radius: 10px;
}
#keyframes glowing {
0% {
background-position: 0 0;
}
50% {
background-position: 400% 0;
}
100% {
background-position: 0 0;
}
}

How to convert from TSX to JSX in this Codesandbox

I am learning React and JavaScript and now I have this CodeSandbox but I can't convert it to JavaScript React I have tried this for the Card Component:
import React, { useState } from "react";
const Card = props => {
const [expanded, setExpanded] = useState(false);
const RenderCard = (className) => {
return (
<div
className={`card ${className}${expanded ? " expanded" : ""}`}
onClick={() => {
setExpanded(!expanded);
}}
>
<div className="image">
<img alt="digger" src={props.image} />
</div>
<div className="info">
<div
className="bg1"
style={{ backgroundImage: "url('" + props.image + "')" }}
/>
<div
className="bg2"
style={{ backgroundImage: "url('" + props.image + "')" }}
/>
<div
className="bg3"
style={{ backgroundImage: "url('" + props.image + "')" }}
/>
<h1>JCB OES System</h1>
<h2>Report Number #1</h2>
<h3>Load lifter work area</h3>
<div className="button">Open</div>
</div>
</div>
);
};
return (
<div className={`card-container${expanded ? " expanded" : ""}`}>
{expanded && <div className="background" />}
{<RenderCard className="card1"/>}
{<RenderCard className="card2"/>}
</div>
);
};
export default Card;
And I show the Card like this. It's very simple, it's just that when I click a card it does not pop up like the CodeSandbox does.
import Card from "./Card";
import "./styles.scss";
const CreateContent = () => {
return (
<div className="app">
<link rel="stylesheet" href="https://use.typekit.net/jli8mqj.css" />
<Card image="https://www.thetimes.co.uk/imageserver/image/methode%2Fsundaytimes%2Fprodmigration%2Fweb%2Fbin%2Fbeae8dfb-0a41-4f8e-b076-ffd68417287b.jpg?crop=1024%2C683%2C0%2C0&resize=685" />
<Card image="https://www.virginexperiencedays.co.uk/content/img/product/large/PJCBRA__01.jpg" />
<Card image="https://www.toyfarmers.co.uk/images/britains-jcb-3cx-backhoe-loader.jpg" />
<Card image="https://seatylive.blob.core.windows.net/eventimages/2019-Aug-20-Tue_18-37-31-969.png" />
</div>
);
};
export default CreateContent;
The styles is the same, with no changes: I understand that the expanded background when set to expanded=true using the hook that the scss style for background should be in effect but all I get is a black screen.
.app {
font-family: sans-serif;
text-align: center;
padding: 4em 0;
}
* {
box-sizing: border-box;
padding: 0;
margin: 0;
border: 0;
}
.card-container {
font-family: niveau-grotesk, sans-serif !important;
position: relative;
z-index: 0;
&.expanded {
z-index: 3;
#keyframes fade-in {
0% { opacity: 0; }
100% { opacity: 1; }
}
.background {
animation: fade-in .3s ease-out;
z-index: 2;
position: fixed;
background: black;
top: 0;
left: 0;
right: 0;
bottom: 0;
width: 100%;
height: 100%;
}
}
.card {
margin: 0 auto;
width: 25em;
cursor: pointer;
border-radius: .5em;
box-shadow: 0 50px 100px -20px rgba(50,50,93,.25),
0 30px 60px -30px rgba(0,0,0,.3),
0 -18px 60px -10px rgba(0,0,0,.03);
margin-bottom: 4em;
&.card2 {
transition: .2s ease-out;
position: absolute;
top: 0;
width: 25em;
left: 50%;
z-index: 4;
transform: translateX(-50%);
&.expanded {
width: 40em;
}
}
.image {
img {
display: block;
border-top-left-radius: .5em;
border-top-right-radius: .5em;
width: 100%;
}
}
$button-color: rgb(87, 87, 228);
&:hover {
.info .button {
color: white;
background: $button-color;
}
}
.info {
background: white;
position: relative;
border-bottom-left-radius: .5em;
border-bottom-right-radius: .5em;
overflow: hidden;
padding: .9em 1.2em;
text-align: left;
$darkness: 0;
&:after {
content: '';
position: absolute;
top: -20%;
left: -20%;
right: -20%;
bottom: -20%;
height: 140%;
width: 140%;
// filter: blur(8px);
// -webkit-filter: blur(8px);
background: linear-gradient(to right,
rgba(0, 0, 0, 0.4) 30%,
rgba(0, 0, 0, 0) 100%);
}
.bg1, .bg2 {
position: absolute;
top: -20%;
left: -20%;
right: -20%;
bottom: -20%;
height: 140%;
width: 140%;
z-index: 0;
background-position: center;
background-repeat: no-repeat;
background-size: 100%;
transform: rotate(180deg);
filter: blur(16px);
}
.bg2 {
background-position: bottom;
transform: rotate(0deg);
opacity:0.4;
}
.bg3 {
background-position: top;
transform: rotate(180deg);
opacity:0.4;
}
.button {
transition: .2s ease-out;
text-transform: uppercase;
line-height: 1.2em;
position: absolute;
top: 50%;
transform: translateY(-50%);
right: 1.8em;
z-index: 1;
background: white;
border-radius: 1em;
padding: .4em 1.1em;
font-weight: 600;
color: $button-color;
}
h1, h2, h3 {
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
max-width: 13em;
color: white;
position: relative;
z-index: 1;
text-shadow: 1px 1px 1px rgba(0,0,0,0.8);
}
h1 {
line-height: .8em;
letter-spacing: .03em;
font-size: 1.1em;
font-weight: 900;
padding: .1em 0;
}
h2 {
letter-spacing: .02em;
font-size: 1.0em;
font-weight: 400;
padding: .1em 0;
opacity: 0.6;
}
h3 {
letter-spacing: .02em;
font-size: .9em;
font-weight: 400;
padding: .1em 0;
}
}
}
}
What am I missing?
To swap your Code Sandbox from TypeScript to JavaScript you should just need to:
Remove all typescript specific syntax from your ".ts" and ".tsx" files (interfaces, typings, etc)
Change all the file extensions to their JavaScript equivalent i.e. ".ts" -> ".js" and ".tsx" -> ".jsx".
Update the "main" property of the "package.json" file to point to the renamed entry point. i.e. "src/index.jsx".
I created a quick CodeSandbox with this already done.

How to Use Classes in Styled-Component

I am new to styled-component. I want to convert custom CSS to Styled-Component. I have already used className in React File.
App.js
<div className="left-menus">
{menus.map(item => {
return (
<Link to={item.name} name={item.name} key={item.name}
className={this.state.activeMenu === item.name ? 'menu active' : 'menu' }
onClick={() => this.setState({ activeMenu: item.name })}
>
<Icon name={item.icon} size="large"/>
<span>{item.name}</span>
</Link>
)
})}
</div>
App.css
.left-menus {
position: fixed;
width: 200px;
padding-right: 0 !important;
background-color: #fff;
height: 100%;
margin-top: 20px;
top: 47px;
font-size: 12px !important;
border-right: 2px solid #e8e8ec; }
.left-menus .menu {
color: #4a4a4a;
width: 100%;
display: block;
cursor: pointer;
text-transform: capitalize !important;
padding: 15px 10px 15px 18px; }
.left-menus .menu .angle.down.icon,
.left-menus .menu .angle.up.icon {
right: 10px;
position: absolute; }
.left-menus .menu .icon:first-child {
margin-right: 10px; }
.left-menus .menu.active {
border-right: 4px solid #3cbfc8;
background-color: #f8f8f8; }
.left-menus .sub-menu-container .sub-menu {
display: none;
height: 0;
transition: 0.3s all ease; }
.left-menus .sub-menu-container.active .sub-menu {
display: block;
height: 100%;
text-transform: capitalize;
transition: 0.3s all ease; }
.left-menus .sub-menu-container.active .sub-menu a {
color: #4a4a4a; }
.left-menus .sub-menu-container.active .sub-menu .icon {
margin: 10px 10px 0 10px; }
CSS with a class selector will only match elements that are members of a class.
To give a styled component that class, you need to do it when you instantiate it.
For example:
const MyStyledComponent = styled.div`
background: red;
`;
const myFunctionComponent = () => {
const myClass = "left-menus";
return(
<div>
Here is MyStyledComponent
<MyStyledComponent className={myClass}>
Example
</MyStyledComponent>
</div>
);
}
If you have an existing stylesheet you want to apply, it is likely that styled components are not the right tool for the job.

Resources