I quite like the inline CSS pattern in React and decided to use it.
However, you can\'t use the :hover
and similar selectors. So what\'s the best way to
This can be a nice hack for having inline style inside a react component (and also using :hover CSS function):
...
<style>
{`.galleryThumbnail.selected:hover{outline:2px solid #00c6af}`}
</style>
...
Checkout Typestyle if you are using React with Typescript.
Below is a sample code for :hover
import {style} from "typestyle";
/** convert a style object to a CSS class name */
const niceColors = style({
transition: 'color .2s',
color: 'blue',
$nest: {
'&:hover': {
color: 'red'
}
}
});
<h1 className={niceColors}>Hello world</h1>
In regards to styled-components and react-router v4 you can do this:
import {NavLink} from 'react-router-dom'
const Link = styled(NavLink)`
background: blue;
&:hover {
color: white;
}
`
...
<Clickable><Link to="/somewhere">somewhere</Link></Clickable>
I'm not 100% sure if this is the answer, but its the trick i use to simulate the CSS :hover effect with colours and images inline.
`This works best with an image`
class TestHover extends React.PureComponent {
render() {
const landingImage = {
"backgroundImage": "url(https://i.dailymail.co.uk/i/pix/2015/09/01/18/2BE1E88B00000578-3218613-image-m-5_1441127035222.jpg)",
"BackgroundColor": "Red", `this can be any color`
"minHeight": "100%",
"backgroundAttachment": "fixed",
"backgroundPosition": "center",
"backgroundRepeat": "no-repeat",
"backgroundSize": "cover",
"opacity": "0.8", `the hove trick is here in the opcaity slightly see through gives the effect when the background color changes`
}
return (
<aside className="menu">
<div className="menu-item">
<div style={landingImage}>SOME TEXT</div>
</div>
</aside>
);
}
}
ReactDOM.render(
<TestHover />,
document.getElementById("root")
);
CSS:
.menu {
top: 2.70em;
bottom: 0px;
width: 100%;
position: absolute;
}
.menu-item {
cursor: pointer;
height: 100%;
font-size: 2em;
line-height: 1.3em;
color: #000;
font-family: "Poppins";
font-style: italic;
font-weight: 800;
text-align: center;
display: flex;
flex-direction: column;
justify-content: center;
}
Before hover
.menu-item:nth-child(1) {
color: white;
background-color: #001b37;
}
On hover
.menu-item:nth-child(1):hover {
color: green;
background-color: white;
}
Example: https://codepen.io/roryfn/pen/dxyYqj?editors=0011
Full CSS support is exactly the reason this huge amount of CSSinJS libraries, to do this efficiently, you need to generate actual CSS, not inline styles. Also inline styles are much slower in react in a bigger system. Disclaimer - I maintain JSS.
I use a pretty hack-ish solution for this in one of my recent applications that works for my purposes, and I find it quicker than writing custom hover settings functions in vanilla js (though, I recognize, maybe not a best practice in most environments..) So, in case you're still interested, here goes.
I create a parent element just for the sake of holding the inline javascript styles, then a child with a className or id that my css stylesheet will latch onto and write the hover style in my dedicated css file. This works because the more granular child element receives the inline js styles via inheritance, but has its hover styles overridden by the css file.
So basically, my actual css file exists for the sole purpose of holding hover effects, nothing else. This makes it pretty concise and easy to manage, and allows me to do the heavy-lifting in my in-line React component styles.
Here's an example:
const styles = {
container: {
height: '3em',
backgroundColor: 'white',
display: 'flex',
flexDirection: 'row',
alignItems: 'stretch',
justifyContent: 'flex-start',
borderBottom: '1px solid gainsboro',
},
parent: {
display: 'flex',
flex: 1,
flexDirection: 'row',
alignItems: 'stretch',
justifyContent: 'flex-start',
color: 'darkgrey',
},
child: {
width: '6em',
textAlign: 'center',
verticalAlign: 'middle',
lineHeight: '3em',
},
};
var NavBar = (props) => {
const menuOptions = ['home', 'blog', 'projects', 'about'];
return (
<div style={styles.container}>
<div style={styles.parent}>
{menuOptions.map((page) => <div className={'navBarOption'} style={styles.child} key={page}>{page}</div> )}
</div>
</div>
);
};
ReactDOM.render(
<NavBar/>,
document.getElementById('app')
);
.navBarOption:hover {
color: black;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
<div id="app"></div>
Notice that the "child" inline style does not have a "color" property set. If it did, this would not work because the inline style would take precedence over my stylesheet.