I am unable to modify this section of code.
const DisplayTheSecret = props => (
<div>
<span aria-hidden="true">
The secret to life is {props.secretToLife}.
</span>
</div>
);
How can I remove the attribute aria-hidden from it?
HTML
<div id="app"></div>
JS file
const DisplayTheSecret = props => (
<div>
<span aria-hidden="true">
The secret to life is {props.secretToLife}.
</span>
</div>
);
const withSecretToLife = (WrappedComponent) => {
class HOC extends React.Component {
render() {
return (
<WrappedComponent
{...this.props}
secretToLife={42}
// like to remove aria-hidden or set it to aria-hidden="false"
/>
);
}
}
return HOC;
};
const Life = withSecretToLife(DisplayTheSecret);
ReactDOM.render(<Life />, document.querySelector("#app"))
Related
on my Project I have a banner on top of my site with 2 buttons. when I click the button profile I want it to change the css style of a div in another component.
this is my code for the banner:
import Profile from "./Profile";
function Banner() {
const invis=false;
return (
<div className="banner">
<span className="bannerbtnsettings">
<button className="btnbannersettings">Settings</button>
</span>
<span className="bannerbtnprofile">
<button className="btnbannerprofile" onClick={Profile.changeStyle}>Profile</button>
</span>
</div>
);
}
export default Banner;
this is my code for the div in the other component:
import "../index.css";
import React, { useState } from "react";
const Profile = () => {
const [style, setStyle] = useState("profile-hidden");
const changeStyle = () => {
console.log("you just clicked");
setStyle("profile-displayed");
};
return (
<div>
<div className={style}> hellllo</div>
</div>
);
};
export default Profile;
I can only find information about this with parent-child components.
They said I should use a usestate import but I can't seem to get it working. what's the proper way to do this?
All you need is lift your state to parent component, if you have a long trip to your common ancestor you can try to use a context. Attached a working example. Hope it helps!
const Banner = ({ onClickHandler }) => {
return (
<div className="banner">
<span className="bannerbtnsettings">
<button className="btnbannersettings">Settings</button>
</span>
<span className="bannerbtnprofile">
<button className="btnbannerprofile" onClick={() => onClickHandler()}>Profile</button>
</span>
</div>
)}
const Profile = ({ style }) => {
return (
<div>
<div className={style}>I'm your profile :)</div>
</div>
);
};
const App = () => {
// We lift the state
const [style, setStyle] = React.useState("profile-hidden");
const profileHandler = () => {
setStyle(style === 'profile-hidden'
? 'profile-displayed'
: 'profile-hidden')
}
return(
<div>
<Banner onClickHandler={profileHandler} />
<Profile style={style} />
</div>
)
}
// Render
ReactDOM.createRoot(
document.getElementById("root")
).render(
<App />
);
.profile-hidden {
display: none;
}
.profile-displayed {
display: block;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/18.1.0/umd/react.development.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/18.1.0/umd/react-dom.development.js"></script>
<div id="root"></div>
You cannot use this syntax for React Components COMPONENT.method
, in your case onClick={Profile.changeStyle} !
Instead you should make Banner parent component and use Profile component as child inside it or vise versa !
then You should pass the state style as props so then you will be able to use its value.
your code should look like this :
function Banner() {
const [style, setStyle] = useState("profile-hidden");
const changeStyle = () => {
console.log("you just clicked");
setStyle("profile-displayed");
};
return (
<div className="banner">
<span className="bannerbtnsettings">
<button className="btnbannersettings">Settings</button>
</span>
<span className="bannerbtnprofile">
<button className="btnbannerprofile" onClick={changeStyle}>Profile</button>
</span>
<Profile style={style} />
</div>
);
}
export default Banner;
and your Profile component :
const Profile = (props) => {
return (
<div>
<div className={props.style}> hellllo</div>
</div>
)
}
I have two React components
class App extends React.Component {
render() {
return (
<div id="appWrapper">
<ConfigureWindow />
<button id="configureClocksButton">Configure clocks</button>
<section id="clocksHere"></section>
</div>
);
}
}
const ConfigureWindow = () => (
<div id="configureWindowWrapper">
<div id="configureWindow">
<section id="addCitySection">TODO: adding a city</section>
<div id="verticalLine"></div>
<section id="listOfCities">
<header>
<h1>Available cities</h1>
<div id="closeConfigureWindowWrapper">
<img src="..\src\images\exit.png" id="closeConfigureWindow" alt="" />
</div>
</header>
<section id="availableCities"></section>
</section>
</div>
</div>
);
I want "ConfigureWindow" to be shown when "configureClocksButton". I tried to execute it with props, state and a function but got errors. It also would be nice if you explain me how to create new React components with React functions?
You probably want to use the React.JS event onClick (https://reactjs.org/docs/handling-events.html), and a state to store the action. To create a function component, you just have to return the JSX you want to render, and use hooks (https://reactjs.org/docs/hooks-intro.html) and then do a conditional rendering (https://reactjs.org/docs/conditional-rendering.html):
const App = () => {
const [toggleConfiguration, setToggleConfiguration] = useState(false)
return (
<div id="appWrapper">
{toggleConfiguration && <ConfigureWindow />}
<button onClick{() => setToggleConfiguration(true)} id="configureClocksButton">Configure clocks</button>
<section id="clocksHere"></section>
</div>
);
}
It's a bit difficult to understand your post, but I gather you want to click the button with id="configureClocksButton" and conditionally render the ConfigureWindow component.
You can accomplish this with some boolean state, a click handler to toggle the state, and some conditional rendering.
class App extends React.Component {
this.state = {
showConfigureWindow: false,
}
toggleShowConfigureWindow = () => this.setState(prevState => ({
showConfigureWindow: !prevState.showConfigureWindow,
}))
render() {
return (
<div id="appWrapper">
{showConfigureWindow && <ConfigureWindow />}
<button
id="configureClocksButton"
onClick={this.toggleShowConfigureWindow}
>
Configure clocks
</button>
<section id="clocksHere"></section>
</div>
);
}
}
A function component equivalent:
const App = () => {
const [showConfigureWindow, setShowConfigureWindow] = React.useState(false);
const toggleShowConfigureWindow = () => setShowConfigureWindow(show => !show);
return (
<div id="appWrapper">
{showConfigureWindow && <ConfigureWindow />}
<button
id="configureClocksButton"
onClick={toggleShowConfigureWindow}
>
Configure clocks
</button>
<section id="clocksHere"></section>
</div>
);
}
I am using functional component in react js , in the below code
the class right-panel-active is not being added / is undefined. Someone help to enable the class be added when the button is toggled
import React from 'react';
import './style.css';
import {
Modal,
DropdownMenu
} from '../MaterialUI';
/**
* #author
* #function Header
**/
const Header = (props) => {
const container = () => {
document.getElementById('container');
}
const signUpButton = () => {
container.classList.add('right-panel-active');
};
const signInButton = () => {
container.classList.remove('right-panel-active');
};
return (
<div className="header">
<div className="container" id="container">
<button className="ghost" id="signIn" onClick={signInButton} >Sign In</button>
</div>
<div className="overlay-panel overlay-right">
<p>Enter your personal details and start journey with us</p>
<button className="ghost" id="signUp" onClick={signUpButton} >Sign Up</button>
</div>
</div>
)
}
export default Header
You are not utilising any of React's functionality.
Read about state management in React
and Event Handlers in React
const Header = (props) => {
const [isContainerActive, setIsContainerActive] = React.useState(false);
const signUpButton = () => {
setIsContainerActive(false);
};
const signInButton = () => {
setIsContainerActive(true);
};
return (
<div className="header">
<div id="container" className={`container${isContainerActive ? " right-panel-active" : ""}`}>
<button className="ghost" id="signIn" onClick={signInButton}>Sign In</button>
</div>
<div className="overlay-panel overlay-right">
<p>Enter your personal details and start journey with us</p>
<button className="ghost" id="signUp" onClick={signUpButton}>Sign Up</button>
</div>
</div>
);
}
ReactDOM.render(<Header />, document.getElementById("root"));
.header {height: 120px;}
.container {float:left;}
.overlay-right {display: none;background: red;float:right;height:100%;}
.right-panel-active ~ .overlay-right {display: inline-block;}
<div id="root"></div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.8.4/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.8.4/umd/react-dom.production.min.js"></script>
PS: I also recommend https://www.npmjs.com/package/classnames , or the cx library for className management.
I think the best solution for this is to making a state and handle the style by a ternarian
function Welcome(props) {
const {name} = props;
return (
<h1 style={name === 'Sara' ? right-panel-active : right-panel-inactive}>Hello, {name}</h1>
)}
function App() {
return (
<div>
<Welcome name="Sara" />
</div>
);
}
This is the React way of doing,
You have to keep a local state (useState) and track the button click and based on the state change update the class to the container. You shouldn't directly change the DOM.
Click on the button to see the CSS is adding or not.
import React, { useState } from "react";
import "./styles.css";
export default function App() {
const [isSignUp, setSignUp] = useState(true);
return (
<div id="container" className={isSignUp ? "right-panel-active" : ""}>
<button onClick={() => setSignUp(false)}>SignIn</button>
<button onClick={() => setSignUp(true)}>SignUp</button>
//for testing the change
{isSignUp ? "right-panel-active added" : "right-panel-active removed"}
</div>
);
}
Sample working code - https://codesandbox.io/s/fragrant-http-qo6du?file=/src/App.js
No need to add click event with vanilla js, you could add an React onClick event. You forgot to return the container.
// if you use curly braces you must return the value
const container = () => {
return document.getElementById('container');
};
// or skip the curly braces
const container = () =>
document.getElementById('container');
I have this presentational component that includes a LoginForm which uses redux connect... when i try to see if the component is there by using wrapper.debug(), instead of the component i see: <Connect(Component) />
What do i have to do in order to see the actual LoginForm and test its length?
This is my component:
const LoginSection = ({ intl }) => (
<div className={styles.loginSection}>
<div className={styles.wrapper}>
<div className={styles.form}>
<p className={styles.title}>
<FormattedMessage
id="Dashboard.login.title"
defaultMessage="Login to an account"
/>
</p>
<LoginForm />
<p className={styles.createAccountWrapper}>
<span className={styles.dontHaveAccount}>
<FormattedMessage
id="Dashboard.login.subline"
defaultMessage="Dont have an account?"
/>
</span>
<a
className={styles.createAccount}
href={`${localeToDomainMap[intl.locale]}/register`}
>
<span className={styles.createOneHere}>
<FormattedMessage
id="Dashboard.login.createAccount"
defaultMessage="Create one here."
/>
</span>
</a>
</p>
</div>
</div>
</div>
);
and this is my test:
const setup = (newProps) => {
const props = {};
const wrapper = shallow(<LoginSection {...props} />);
return {
wrapper,
props,
};
};
describe('LoginSection', () => {
test('that it contains LoginForm', () => {
const { wrapper } = setup();
console.log(wrapper.debug());
expect(wrapper.find('.loginFrom')).toEqual(1);
});
});
and this is the result of wrapper.debug():
<div className="loginSection">
... other stuff here ...
<Connect(Component) />
... other stuff here ...
</div>
I want to get key attribute of parent div when child button is click. Using the code I write, I am getting null in console. Can't understand why?
I tried
let a = e.target.parentElement.getAttribute("key");
But this gives me null in console.
deletepost(e) {
let a = e.target.parentElement.getAttribute("key");
console.log(a);
}
render() {
return (
<div>
{ this.props.posts.map((post, i) =>
<div id="a" key="1">
<span> <h3>{post.title}</h3><p>{post.post}</p></span>
<input type="button" value="Delete" id="1" onClick={this.deletepost}/>
</div>
)
}
</div>
)
}
}
I am expecting "1" but getting null. Thanks in advance.
In ReactJS, the "key" is for React's internal use and won't be included in the DOM. That may be the reason you are getting null.
You need to simply add another prop/attribute.
Something like below should work.
deletepost(e) {
let a = e.target.parentNode.getAttribute("postid"));
console.log(a);
}
render() {
return (
<div>
{
this.props.posts.map((post, i) =>
<div id="a" key="1" postId="1">
<span> <h3>{post.title}</h3><p>{post.post}</p></span>
<input type="button" value="Delete" id="1" onClick={this.deletepost}/>
</div>
)
}
</div>
)
}
}
Also, if the "id" on the input element is same as the "key" on your div (parent) element, then you can simply do the following:
deletepost(e) {
let a = e.target.id;
console.log(a);
}
render() {
return (
<div>
{
this.props.posts.map((post, i) =>
<div id="a" key="1">
<span> <h3>{post.title}</h3><p>{post.post}</p></span>
<input type="button" value="Delete" id="1" onClick={this.deletepost}/>
</div>
)
}
</div>
)
}
}
you can change 'key' attribute to 'data-key' and get attribute like this:
// Example class component
class Test extends React.Component {
constructor(props){
super(props);
this.deletepost = this.deletepost.bind(this);
}
deletepost(e) {
let a = e.currentTarget.parentNode.getAttribute("data-key");
console.log(a);
}
render() {
return (
<div>
{ this.props.posts.map((post, i) =>
<div id="a" data-key={post.key}>
<span> <h3>{post.title}</h3><p>{post.post}</p></span>
<input type="button" value="Delete" id={i} onClick={this.deletepost}/>
</div>
)
}
</div>
)
}
}
// Render it
ReactDOM.render(
<Test posts={[{post:'a',key:1},{post:'b',key:2}]} />,
document.getElementById("react")
);
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>
<div id="react"></div>
You can try with currentTarget
let a = e.currentTarget.parentNode.getAttribute("key");
Or
let a = ReactDOM.findDOMNode(this).parentNode.getAttribute("key")
Now you can use the useRef hook to easily reference an element:
function MyComponent() {
const inputEl = useRef(null);
const onButtonClick = () => {
// #ts-ignore (us this comment if typescript raises an error)
inputEl.current.focus();
};
return (
<>
<input ref={inputEl} type="text" />
<button onClick={onButtonClick}>Focus on input</button>
</>
);
}