React JS - How to hide parent component content when child is rendering? - reactjs

I have some nested components and I use outlet to render the children's content, but the page is getting crowded and I want to hide the parent content after the child is rendered . How can I do that?
let params = useParams();
<div>
!params.id && (<div>
*render your contents here* </div>)
<Outlet />
</div>
This should work , but where I have to put the code , in the parent component or in the child ?

Related

Rendering Child Component after Parent in React

I am rendering a child component of a parent component. The text inside the render method of the child component is being rendered, but the map function is not being called on the JSON array I have in the child component. I used console.log and the array has the right values in it. Here is the render function of the child component:
console.log("rerender: " + JSON.stringify(this.state.myDropdownMessages));
this.state.myDropdownMessages && console.log("DID THIS!");
//}
return (
<>
TESTING 1234---does render
{this.state.myDropdownMessages && this.state.myDropdownMessages.map((oneMessage) =>
{
{/*let blueDotDisplay = false;
if (oneMessage.hasBeenViewed = "false"){
blueDotDisplay = true;
}*/
}
<>
Inside map function--doesn't render
<img src={oneMessage.posterprofilesrc} className='OneHeaderMessageProfilePic' />
<div className="OneHeaderMessageRightDiv">
test again
<div className="OneHeaderMessageInfo">
<div className="OneHeaderMessageNameDiv">
{oneMessage.postername}
</div>
</div>
<div className="OneHeaderMessageTimeDiv">
{oneMessage.time}
</div>
</div>
<div display = {(oneMessage.hasBeenViewed == 'false') ? 'block' : 'none'} className="OneHeaderMessageBlueDot" id={'OneHeaderMessageBlueDot' + oneMessage.id}>';
</div>
</>
}
)}
The child component is rendered on the click of a button from the parent component. It renders the code before the map--"TESTING 1234"--but doesn't render the code inside the map function even though the map function is loaded. It even prints out on the console right before the render function is supposed to return that the array is fully loaded with the right values. Is the problem that the parent component doesn't rerender the child component once the data is loaded in the child component? I tried calling the parent render function from the child but it didn't work. Neither did calling child component's render function. Thank you very much for your help.
Make sure to return from the mapping loop, you are looping but never returning hence no react node are being rendered.
myArray.map(item => {
return (<div> Hello World </div>)
})
Just add return to your map function or just remove curly brackets ...myDropdownMessages.map((oneMessage) => <> //..some code.. </>
or
...myDropdownMessages.map((oneMessage) => { return (<> //..some code.. </>)}

How to open a new react component at the end of a stepper?

When I reach the end of my stepper component, how can I open a separate component that is decoupled from the stepper?
This is part of my react functional component which controls forward navigation. When I reach the 'Done' button, I want the component to open:
<ButtonContainer>
{activeStep !== 0 && (
<PrevButton onClick={handleBack}>Back</PrevButton>
)}
<NextButton
variant="contained"
color="primary"
onClick={handleNext}
>
{stepList && activeStep === stepList.length - 1
? 'Done'
: 'Next'}
</NextButton>
</ButtonContainer>
Is this something I would do in my handleNext function or do I create a separate function for this? Thanks in advance.
To open a decoupled component, you could use a Portal:
Portals provide a first-class way to render children into a DOM node that exists outside the DOM hierarchy of the parent component.
What you would have to do is add another <div id="my-comp"/> somewhere next to your root div (<div id="root" />). Inside this div, the Portal will be rendered, instead of as normally as a descendant of the root div. The portal component would have to return something like this from it's render() function:
render() {
return ReactDOM.createPortal(
this.props.children,
myNode,
);
}
The first argument (this.props.children) is the component, which can be an element, string, or fragment, and the second argument (myNode) is a DOM element.
You can then import the Portal component in your react functional component and place it somewhere there. But it won't be rendered as child of that component thanks to the portal.
Check out this codepen for an example.
Regarding the done button. Either create a new function and use a ternary conditition in the onClick prop or add an if to handleNext.

React component seems to rerender because of child components (but shouldn't)

I have a page with a tabbed view. If tab 1 is active it should show component A, otherwise component B.
Based on which page/route I come from before, it should default to component B. Both the components don't need props (as they handle data/state internally).
Problem: The parent component renders three times. Because of this, I loose the state value from useLocation and can't display the second tab. Simplified parent component code:
function ContractOverview() {
const location = useLocation();
console.log(location);
const showBillingCycleTab = location.state?.selectedTab === 'billing-cycles';
return (
<Container>
<h1>
<Trans i18nKey="navigation.billing" />
</h1>
{showBillingCycleTab ? <BillingCycleTable /> : <ContractTable />} // if I do it like this, ContractOverview renders three times (and I loose location state)
{showBillingCycleTab ? <p>component A</p> : <p>component B</p>} // if I do it like this, ContractOverview renders only once and the location state is correct.
</Container>
);
}
The route is set up like this:
<Route path="/contracts" component={ContractOverview} exact />
Screenshot of the location logs:
Usually I'd expect the parent component to only render once as there are no props that could change nor component state that could do something. What am I doing wrong?

When Reactjs has functional component as parent and child component as class

I am new in reactjs and learning bit and pieces. I am facing an issue. The scenario is like. I have a functional component as a parent. It has a child component as a class component. I would like to set or reset the child component's state on parent's button click. Or is there any way to call the child component's any method from the parent component. I tried as
// this call from a functional component.
<PhotoPreviewUploaend setSelectedFile={setSelectedFile} ref={setImagePreviewUrl} />
Later after a button click does this:-
setImagePreviewUrl('');
I read ref attribute allows access to the component. I tried this ref between 2 class component both parent and child is class components and it works as expected. But when did the same from a functional component it has no effect at all. How can I do it?
You are not embracing react one-way data flow by using refs like that; it might not behave the way you expect;
You should pass parent state handler logic function to the child component,
then child component call it with proper value; as the result your parent state will be updated and you have nice and clean one way data flow; you can use this in any kind of component, since you don't mess with this bindings in functional components;
This example demonstrates it in action:
function App() {
// Define your state
const [someState, setSomeState] = useState(0);
return (
<div className="container">
<Child parentCallback={setSomeState} />
</div>
);
}
class Child extends Component {
render(){
return(
<div>
<button
onClick={() => this.props.parentCallback(/*someValue*/)}
>
click me!
</button>
</div>
)
}
}

React js: component is not unmounted properly

We have following scenario:
1. Parent component has child components.
==============================================================
<ContainerComponent>
<Layout>
<CustomComponent>
<ActualComponent>
<CustomComponent>
<ActualComponent>
==============================================================
This way component mounting takes place, and each ContainerComponent rendered according to task.
Component Container contain :
return (
<div className='row' >
<div className='col-md-12' >
<div className="ic-component" id="MainComponent" >
<div style={{'border':'5px;solid #e0e7f0'}}>
<div id="rootwizard3" className='wizard'>
<ul>
{TabHeader}
</ul>
<div className="tab-content" id="tabcontent" >
</div>
</div>
</div>
</div>
</div>
</div>
);
Then ContainerComponent contain Layout component :
$("#tabcontent").empty();
if(LayOut===null)
{
}
else {
React.render(
<div id={tabid}><div id={layoutid}>
<LayOut CurrentStepId={CurrentStepId} TaskDetails={TaskDetails} IsActualComponent="true"/>
</div>
</div>,document.getElementById('tabcontent'));
}
},
Layout component contains CustomComponent :
var findDiv1=$("div > #"+TabbId+" > div > div > div > div > div")[0];
$(findDiv1).empty();
var valueP3=1;
React.render(<CustomComponent inputType={Set} ItemName="" ItemId="" KeyValue={valueP3} addbtndispaly="" editbtndispaly="" deletebtndispaly="" Views="" />,findDiv1);
Unmounting of Container page:
React.unmountComponentAtNode(document.getElementById('tabcontent'));
Following way the components get mounted.
Initial component mounting. Here layout component loaded into Container Component. but custom component is not showing under Layout ? but output is poperly showing.
chrome react tool component loading structure
Second time component mounting, but here it only remove component under "ctab137". not unmounting custom component . Second copy of cutom component get created.
chrome react tool component loading structure-Second time loading
When we go to task(functionality) it mounts parent component and accordingly
respective child component gets mounted.
When we click to another task mean containerComponent then only containerComponent unmount get called. for that we are clearing container componenet div where its child componenet get mounted. and load another task child componenet.
But here is we are facing problem when we mount child componenet every times it get mounted separately if that component is already present. and that create problem. Here is above mentioned custom component is not get propely unmounted. Every time separate customComponent copy is created and that times that funtionality get executed.
Also here is child componenets componentWillUnmount not get called.
I want to know answers of following questions .
How to unmount child components if it is not unmounted ?
How to call child components unmount method if it's not called ?
Is there any way to unmount component by component name ?

Resources