I have a sync popup when I click "Yes", the client queries the server and the isLoading variable is set to true and the brake appears. During synchronization, I want my user interface to be blocked, for example, when the user clicks somewhere in the component, nothing to happens, but I want the user interface to be visible. Is it possible only with reactjs, html and css or do I have to use some kind of library? If there is any way without a library I want it this way.
This is my code:
const Contact = () => {
const location = useLocation();
const navigate = useNavigate();
const [page, setPage] = useState(0);
const [entry, setEntry] = useState([]);
const [isLoading, setIsLoading] = useState();
const [contacts, setContacts] = useState([]);
const [searchTerm, setSearchTerm] = useState('');
const [countOfContacts, setCountOfContacts] = useState(0);
const [isSynchronizedClicked, setIsSynchronizedClicked] = useState(false);
const synchronize = async () => {
requester(urls.synchronize, methods.get)
.then(() => {
setIsLoading(false);
navigate(urls.mainPage);
setIsSynchronizedClicked(false);
})
.catch((e) => {
<Alert severity="error">
<AlertTitle>Error</AlertTitle>
The synchronization is not successful.
</Alert>
console.log(e.message);
});
};
return (
<>
<div className='button-search-bar-container'>
<div className='overview-buttons-container'>
<button className='buttons overview-synchronize-button' type="submit" onClick={() => setIsSynchronizedClicked(true)}><SyncIcon /> Synchronize</button>
</div>
<div style={{ height: 630, width: '100%' }}>
<DataGrid
id={contacts.map((contact) => contact.id)}
rows={contacts}
loading={isLoading}
paginationMode='server'
/>
</div>
{isSynchronizedClicked && <ClickAwayListener onClickAway={() => setIsSynchronizedClicked(false)}>
<div className='popup synchronize-popup'>
Do you want to synchronize all contacts ?
<div className='second-message'>This will take a while.</div>
<div className='synchronize-popup-buttons-container'>
<button className='buttons reject' onClick={() => setIsSynchronizedClicked(false)}>No</button>
<button className='buttons approve' onClick={() => { synchronize(); setIsLoading(true); setIsSynchronizedClicked(false); }}>Yes</button>
</div>
</div></ClickAwayListener>}
</>
);
};
CodePudding user response:
You can return early from a component. Add the following snippet (change the logic as you want, specifically I have not added handling of error within synchronize
):
[...]
if (isLoading) {
return null;
}
return <>
// existing component
</>
[...]
Moreover, I don't see synchronize()
being called anywhere. You need to introduce a useEffect
to call synchronize()
within the component.
CodePudding user response:
I make it like that in the .css file
.disabled {
opacity: 0.4;
pointer-events: none;
}
and in my component:
<div className={isLoading ? 'disabled' : ''}>
<Component />
</div>