toggle css class for two buttons when either is clicked - css

import React, { Component } from 'react';
class Buttons extends Component {
constructor(props) {
super(props);
}
render() {
return (
<div className="displayButtons">
<input className='button1' onClick={this.props.get_menu_items_api}
value="Categories" type="button" ref="button"></input>
<input className='button2' onClick={this.props.get_addons_items_api}
value="Add Ons" ref="button1" type="button"></input>
</div>
)
}
}
export default Buttons;
I have these two buttons in react class.Their css is given below. What I want to do is on whichever button I click on it should turn orange and other should turn white. Initially Categories button is orange and Addons button is white.
I tried calling a function onClick that changes its class but how will it change the class of other button also.
.button2 {
border: none;
padding: 11px 32px;
text-align: center;
text-decoration: none;
line-height: 14px;
font-family: Roboto-Regular;
font-size: 12px;
border-radius: 2px 0 0 2px;
display: inline-block;
float: left;
}
.button1 {
background-color:#F6A623;
color: white;
}
.button2 {
background-color:white;
color: black;
}

You can save the status of the component identifier of the orange button and change it with using onClick.
Component:
class App extends React.Component{
constructor(){
super();
this.state = {
orangeButtonId: null
}
this.setOrangeButton = this.setOrangeButton.bind(this);
}
setOrangeButton(id){
this.setState({orangeButtonId: id});
}
render(){
return(
<div>
<input className={this.state.orangeButtonId === 1? "button1 orange" : "button1"} onClick={() => this.setOrangeButton(1)} value="Categories" type="button" ref="button" />
<input className={this.state.orangeButtonId === 2? "button2 orange" : "button2"} onClick={() => this.setOrangeButton(2)}
value="Add Ons" ref="button1" type="button" />
</div>
)
}
}
And styles:
input[type="button"]{
background-color: white;
}
input[type="button"].orange{
background-color: orange;
}
Check the fiddle https://jsfiddle.net/69z2wepo/83389/.

it can easily achived by using the component inner state + classnames library:
class Buttons extends Component {
constructor(props) {
super(props);
this.onButtonClick = this.onButtonClick.bind(this);
this.state = {
selectedButton: 'categories'
}
}
onButtonClick(e) {
this.setState({
selectedButton: e.target.value
});
if (e.target.value === 'categories') {
this.props.get_menu_items_api();
} else {
this.props.get_addons_items_api();
}
}
render() {
return (
<div className="displayButtons">
<input className={classnames({'button': true, 'selected': this.state.selectedButton === 'categories'} onClick={onButtonClick}
value="Categories" type="button" ref="button"></input>
<input className={classnames({'button': true, 'selected': this.state.selectedButton === 'addons'})} onClick={onButtonClick}
value="Add Ons" ref="button1" type="button"></input>
</div>
)
}
}

You need to keep track of button state within your class. When onClick is called set your state.
onButton1Click() {
this.setState({button1Down: true});
}
Then in the render call you need to use this state to set the class names to apply to your buttons.
render() {
let button1ClassName = 'button1';
if (this.state.button1Down) {
button1ClassName += 'button-down';
}
return ...

Related

Access other className on hover in emotion css

I use EmotionCSS. I want to get an access to other className while catching focus on another. For example I have a component like that:
<div className={styles.root}>
<input className={styles.input} ... />
<div/>
The style file looks like that:
import { css } from '#emotion/css';
export const styles = {
root: css`
border: 1px solid black;
`
input: css`
...
&:focus {
// Here I want to access 'root' className and change its colour. Is it possible?
}
`,
}
You can try to use the :has() pseudo-class on the root to change the focus styles in input tag.
import { css } from "#emotion/css";
export const styles = {
root: css`
border: 3px solid black;
&:has(input:focus) {
border-color: red;
}
`,
input: css`
font-size: 1.5rem;
&:focus {
text-transform: uppercase;
}
`
};
export default function App() {
return (
<div className="App">
<div className={styles.root}>
<input type="text" className={styles.input} />
</div>
</div>
);
}

toggle between two button style in react js

I want the button's style to change when I click on them.
I want the option 1 button to be selected and background color to change to by default. If I click on the option 2 button, I want the option 2 button to change and unchanged option 1.
I already used the method found in this post
However, the method doesn't seems to be working correctly since the color of my buttons is the default HTML button color.
My code:
import React, {Component} from 'react';
import './OptionButtons.css'
export class OptionButtons extends Component{
constructor() {
super();
this.state = {
selected: "btn1"
};
}
changeColor = (btn) => {
this.setState({ selected: btn });
};
addClass = (btn) => {
if (this.state.selected === btn) return "selected";
else return "notSelect";
};
render() {
return (
<div class = "option">
<h2> Options </h2>
<div class = "buttons">
<button id = "option1Btn" className = {this.addClass("btn1")} onClick = {this.changeColor.bind(this, "btn1")}> Option 1 </button>
<button className = {this.addClass("btn2")} onClick = {this.changeColor.bind(this, "btn2")}> Option 2 </button>
</div>
</div>
);
}
}
OptionButtons.css
.option {
box-sizing: border-box;
position: relative;
margin-top: 655px;
margin-left: auto;
margin-right: auto;
width: 80%;
max-width: 650px;
}
.option .buttons {
flex: 20%;
display: flex;
justify-content: center;
align-items: center;
}
.option .buttons button {
flex-direction: row;
border-radius: 5px;
padding: 0 1.3rem;
font-family: 'Nunito';
font-style: normal;
font-weight: 700;
font-size: 1.2rem;
line-height: 27px;
text-align: center;
width: 320px;
height: 40px;
left: 50px;
cursor: pointer;
}
#option1Btn{
margin-right: 10px;
}
.selected {
color: "#fff";
background-color: "#00867D";
border: 1px solid "#00867D";
}
.notSelected {
color: "#00867D";
background-color: "#F2F2F2";
border: 1px solid "#F2F2F2";
}
Result of my code
I am not sure. did you say that when you click button 2, Its color will be changed and button 1 will be unchanged(active always)? or button 1 will be inactive?
https://codesandbox.io/s/priceless-tamas-yjr1lw?file=/src/Some.js
check it, do you want like this?
You can easily change colors on button clicks in react:
const [backgroundColor, setBackgroundColor] = useState("white");
const [buttonColors, setButtonColors] = useState({
color1: "red",
color2: "green"
});
const button1Clicked = () => {
setBackgroundColor("gray");
setButtonColors({
...buttonColors,
color1: "green"
});
};
const button2Clicked = () => {
setBackgroundColor("green");
setButtonColors({
...buttonColors,
color2: "red"
});
};
return (
<div
className="App"
style={{
backgroundColor
}}
>
<button
style={{ backgroundColor: buttonColors.color1 }}
onClick={button1Clicked}
>
Button 1
</button>
<button
style={{ backgroundColor: buttonColors.color2 }}
onClick={button2Clicked}
>
Button 2
</button>
</div>
);
You can find a working example here.
There are a couple things that are not ok with your react code and CSS.
Number one you have elements with the property class instead of className.
Second, the color codes you are trying to attribute are strings ("#000"), so your browser doesn't know what to do with them. They should either be clear hexadecimals or using the rgb function.
I'll leave a Codesandbox using your component/CSS so you can take a look.
I think what you are doing is just wrong and very confusing as there is a very elegant way to do it.
import React, {
Component
} from 'react';
import './OptionButtons.css'
export class OptionButtons extends Component {
constructor() {
super();
this.state = {
selected: "btn1" //make this state a boolean so that it will turn true when you press button 1 and false when you press button 2 or vice versa
};
}
changeColor = (btn) => {
this.setState({
selected: btn
});
};
//I have read it many times but I still don't understand what this function does in the code. In my opinion, it has no value to the action you are trying to achieve.
addClass = (btn) => {
if (this.state.selected === btn) return "selected";
else return "notSelect";
};
render() {
return ( <
div class = "option" >
<
h2 > Options < /h2> <
div class = "buttons" >
//it its better and easy to use a turnery operator rather than a function
<
button id = "option1Btn"
className = {
this.addClass("btn1")
}
onClick = {
this.changeColor.bind(this, "btn1")
} > Option 1 < /button> <
button className = {
this.addClass("btn2")
}
onClick = {
this.changeColor.bind(this, "btn2")
} > Option 2 < /button> <
/div> <
/div>
);
}
Instead, you can do like this
import React, {
Component
} from 'react';
import './OptionButtons.css'
export class OptionButtons extends Component {
constructor() {
super();
this.state = {
selected: null //null so that when you click, you can assign a boolean value
};
}
changeColorBtn1 = () => {
this.setState({
selected: true
})
}
changeColorBtn2 = () => {
this.setState({
selected: false
})
}
render() {
return ( <
div class = "option" >
<
h2 > Options < /h2> <
div class = "buttons" >
//I'm using turnery expression which means if selected: true then classname will be btn1
<
button id = "option1Btn"
className = {
this.state.selected && 'btn1'
}
onClick = {
this.changeColorBtn2.bind(this, "btn1")
} > Option 1 < /button>
//same as I did in the previous button but it's vice-versa
<
button className = {!this.state.selected && 'btn2'
}
onClick = {
this.changeColorBtn2.bind(this)
} > Option 2 < /button> <
/div> <
/div>
);
}
I hope it answers your question

Render two Buttons in React but only one got the styling of the css Stylesheet

I am currently in the process of adding a stylesheet to my React Todo app. In the Todo component, two buttons are rendered that get the class clearButton or addButton depending on the label.
Button Component:
import './Button.css'
interface ButtonProps {
lable: string,
disabled: boolean,
onClick: MouseEventHandler<HTMLButtonElement>
}
export const Button: FunctionComponent<ButtonProps> = ({ lable, disabled, onClick}): ReactElement => {
let style: string = lable == 'ADD' ? 'addButton' : 'clearButton';
console.log(lable);
console.log(style);
return(
<div>
<button className= {`button ${style}`} type='button' disabled= { disabled } onClick= { onClick }>
{lable}
</button>
</div>
);
}
Strangely, only one styling of style class is ever applied to a button. It depends on which style class is in first place in the stylesheet. If the addButton class is in first place, only the styling of the addButton is displayed, if the clearButton class is in first place, only the styling of the other button is loaded.
.button {
width: 70px;
height: 25px;
border-radius: 10px;
border: none;
cursor: pointer;
font-family: 'Poppins', sans-serif;
font-weight: bold;
};
.clearButton {
background-color: #8c00ff;
}
.addButton {
background-color: #7ce0ff;
}
Addutional
Parent Component
export const InputBar: FunctionComponent<InputBarProps> = ({ enterTodo, handleEnterTodo, handleCreateTodo, handleClearTodos}): ReactElement => {
return(
<>
<div className="inputBar">
<form>
<TextField value={ enterTodo } onChange={ handleEnterTodo }/>
<div className="buttonsContainer">
<Button lable= 'ADD' disabled= { enterTodo == '' } onClick= { handleCreateTodo } />
<Button lable= 'CLEAR' disabled= { false } onClick= { handleClearTodos } />
</div>
</form>
</div>
</>
);
}

React did not render new css style

This is my code logic, When user click the box , I will set the state active to true
and getCssStyle() will return drag-and-resize-box-text clicked
and then the background image(T) should disappear
class Box extends Component {
constructor(props) {
super(props);
this.state = {
active: false,
}
}
// decide which style to be used
getCssStyle = (type) => {
switch (type) {
case 'text':
if (this.state.active) {
console.log("AAA")
return 'drag-and-resize-box-text clicked'
} else {
console.log("BBB")
return 'drag-and-resize-box-text';
}
// break;
default:
return '';
}
}
onClick = () => {
this.setState({active: true});
}
render() {
return (
<div className={this.getCssStyle(boxType)} >
{this.boxFillContent()}
</div>
</div>
);
}
}
The dev tools show the background image is delete, but the page is still show the image
What's wrong with this??
css
.drag-and-resize-box-text{
border: dashed 3px LightSeaGreen;
background: url(../images/bottom/text_normal.png) no-repeat;
background-position:center;
width: inherit;
height: inherit;
}
.drag-and-resize-box-text.clicked{
border: dashed 3px LightSeaGreen;
/*background: url(../images/bottom/text_normal.png) no-repeat;*/
background-position:center;
width: inherit;
height: inherit;
}
.drag-and-resize-box-text.clicked should have background: none.
Also your code could be made much simpler by using
<div className={this.state.active ? 'drag-and-resize-box-text clicked' : 'drag-and-resize-box-text'} >
{this.boxFillContent()}
</div>

Custom ReactJS component that respects 'valueLink'

I'm building a custom ReactJS component (A 'Select2' dropdown library wrapper) and want to implement support for the standard two-way binding helper with the 'valueLink' parameter.
However it appears the mixin to handle the 'valueLink' parameter only applies to standard components, not custom components.
Is there a way to have my component implement the standard valueLink behaviour automatically, or will I need to explicitly parse and implement this support myself (Potentially introducing bugs or odd behaviours that aren't present in the base library)
The object returned from this.linkState when using the LinkedStateMixin has two relevant properties: value and requestChange(). Simply use those two properties as your value and change handler, respectively, just as if they had been passed to your custom component via value and onChange.
Here's an example of a composite component that wraps a jQuery color picker; it works both with valueLink and with standard value and onChange properties. (To run the example, expand the "Show code snippet" then click "Run code snippet" at the bottom.)
var ColorPicker = React.createClass({
render: function() {
return <div />;
},
getValueLink: function(props) {
// Create an object that works just like the one
// returned from `this.linkState` if we weren't passed
// one; that way, we can always behave as if we're using
// `valueLink`, even if we're using plain `value` and `onChange`.
return props.valueLink || {
value: props.value,
requestChange: props.onChange
};
},
componentDidMount: function() {
var valueLink = this.getValueLink(this.props);
jQuery(this.getDOMNode()).colorPicker({
pickerDefault: valueLink.value,
onColorChange: this.onColorChange
});
},
componentWillReceiveProps: function(nextProps) {
var valueLink = this.getValueLink(nextProps);
var node = jQuery(this.getDOMNode());
node.val(valueLink.value);
node.change();
},
onColorChange: function(id, color) {
this.getValueLink(this.props).requestChange(color);
}
});
div.colorPicker-picker {
height: 16px;
width: 16px;
padding: 0 !important;
border: 1px solid #ccc;
background: url(https://raw.github.com/laktek/really-simple-color-picker/master/arrow.gif) no-repeat top right;
cursor: pointer;
line-height: 16px;
}
div.colorPicker-palette {
width: 110px;
position: absolute;
border: 1px solid #598FEF;
background-color: #EFEFEF;
padding: 2px;
z-index: 9999;
}
div.colorPicker_hexWrap {width: 100%; float:left }
div.colorPicker_hexWrap label {font-size: 95%; color: #2F2F2F; margin: 5px 2px; width: 25%}
div.colorPicker_hexWrap input {margin: 5px 2px; padding: 0; font-size: 95%; border: 1px solid #000; width: 65%; }
div.colorPicker-swatch {
height: 12px;
width: 12px;
border: 1px solid #000;
margin: 2px;
float: left;
cursor: pointer;
line-height: 12px;
}
<script src="http://fb.me/react-with-addons-0.11.2.js"></script>
<script src="http://fb.me/JSXTransformer-0.11.2.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script>
<script src="https://dl.dropboxusercontent.com/u/113308/dnd/jsfiddle/jquery.colorPicker.min.js"></script>
<p><strong>With valueLink</strong></p>
<div id="app1"></div>
<hr>
<p><strong>With value and onChange</strong></p>
<div id="app2"></div>
<script type="text/jsx">
/** #jsx React.DOM */
var ApplicationWithValueLink = React.createClass({
mixins: [React.addons.LinkedStateMixin],
getInitialState: function() {
return { color: "#FF0000" }
},
render: function() {
return (
<div>
<div>
<span style={{color: this.state.color}}>My Color Picker</span>
<button onClick={this.changeColor.bind(null, "#FF0000")}>Red</button>
<button onClick={this.changeColor.bind(null, "#00FF00")}>Green</button>
<button onClick={this.changeColor.bind(null, "#0000FF")}>Blue</button>
<input type="text" valueLink={this.linkState("color")} />
</div>
<div>
<ColorPicker valueLink={this.linkState("color")} />
</div>
</div>
);
},
changeColor: function(color) {
this.setState({color: color});
}
});
var ApplicationWithoutValueLink = React.createClass({
getInitialState: function() {
return { color: "#FF0000" }
},
render: function() {
return (
<div>
<div>
<span style={{color: this.state.color}}>My Color Picker</span>
<button onClick={this.changeColor.bind(null, "#FF0000")}>Red</button>
<button onClick={this.changeColor.bind(null, "#00FF00")}>Green</button>
<button onClick={this.changeColor.bind(null, "#0000FF")}>Blue</button>
<input type="text" value={this.state.color} onChange={this.changeColorText} />
</div>
<div>
<ColorPicker value={this.state.color} onChange={this.changeColor} />
</div>
</div>
);
},
changeColor: function(color) {
this.setState({color: color});
},
changeColorText: function(evt) {
this.changeColor(evt.target.value);
}
});
var ColorPicker = React.createClass({
render: function() {
return (
<div />
);
},
getValueLink: function(props) {
return props.valueLink || {
value: props.value,
requestChange: props.onChange
};
},
componentDidMount: function() {
var valueLink = this.getValueLink(this.props);
jQuery(this.getDOMNode()).colorPicker({
pickerDefault: valueLink.value,
onColorChange: this.onColorChange
});
},
componentWillReceiveProps: function(nextProps) {
var valueLink = this.getValueLink(nextProps);
var node = jQuery(this.getDOMNode());
node.val(valueLink.value);
node.change();
},
onColorChange: function(id, color) {
this.getValueLink(this.props).requestChange(color);
}
});
React.renderComponent(<ApplicationWithValueLink />, document.getElementById("app1"));
React.renderComponent(<ApplicationWithoutValueLink />, document.getElementById("app2"));
</script>

Resources