How to override notification configuration for specific notification only? - reactjs

I use react-toastify for notifications in my React app. In its configuration I've set a default autoClose setting. Is there a way that I can override this setting for specific notifications only? Please find my current code below.
I set react-toastify default configuration in the index page:
import { ToastContainer } from "react-toastify";
<ToastContainer
closeButton={false}
autoClose={6000}
/>
On other pages I for example have the code blow. It's there where I would like to set a custom configuration for autoClose for that specific message only.
Notify({
message: `A message`,
});
This uses a component called Notify:
const User = ({ message, closeToast }) => (
<div key={0} className="notification">
<span style={{ backgroundImage: `url('/icons/user.svg')` }}></span>
<label dangerouslySetInnerHTML={{ __html: message }}></label>
<button onClick={closeToast}>+</button>
</div>
);
const Notification = (props) => {
const { message, user } = props;
return (
<div>
toast(<User message={message} />, {
className: "white-background",
bodyClassName: "grow-font-size",
progressClassName: "fancy-progress-bar",
})
</div>
);
};

According to the documentation for react-toastify, you can pass the autoClose prop into the toast() emitter, as well as the ToastContainer
toast('My message', {autoClose: 5000});
https://fkhadra.github.io/react-toastify/introduction/

Related

How to disable the Text field name is disappearing when we moved out the input filed box in react js

I have made autocomplete features using Downshift using react js. But the problem is when I am searching for something its input field value is disappearing when I click on the outside. Here is the sample code.
import logo from './logo.svg';
import './App.css';
import React, { useState } from "react";
import Highlighter from "react-highlight-words";
import Downshift from "downshift";
import axios from 'axios';
function App() {
const [names, setnames] = useState([{
const [searchTerm, setSearchTerm] = useState('')
const [movie, setmovie] = useState([])
fetchMovies = fetchMovies.bind(this);
inputOnChange = inputOnChange.bind(this);
function inputOnChange(event) {
if (!event.target.value) {
return;
}
fetchMovies(event.target.value);
}
function downshiftOnChange(selectedMovie) {
alert(`your favourite movie is ${selectedMovie.title}`);
}
function fetchMovies(movie) {
const moviesURL = `https://api.themoviedb.org/3/search/movie?api_key=1b5adf76a72a13bad99b8fc0c68cb085&query=${movie}`;
axios.get(moviesURL).then(response => {
setmovie(response.data.results);
// this.setState({ movies: response.data.results });
});
}
return (
<Downshift
onChange={downshiftOnChange}
itemToString={item => (item ? item.title : "")}
>
{({
selectedItem,
getInputProps,
getItemProps,
highlightedIndex,
isOpen,
inputValue,
getLabelProps
}) => (
<div>
<label
style={{ marginTop: "1rem", display: "block" }}
{...getLabelProps()}
>
Choose your favourite movie
</label>{" "}
<br />
<input
{...getInputProps({
placeholder: "Search movies",
onChange: inputOnChange
})}
/>
{isOpen ? (
<div className="downshift-dropdown">
{movie
.filter(
item =>
!inputValue ||
item.title
.toLowerCase()
.includes(inputValue.toLowerCase())
)
.slice(0, 10)
.map((item, index) => (
<div
className="dropdown-item"
{...getItemProps({ key: index, index, item })}
style={{
backgroundColor:
highlightedIndex === index ? "lightgray" : "white",
fontWeight: selectedItem === item ? "bold" : "normal"
}}
>
{item.title}
</div>
))}
</div>
) : null}
</div>
)}
</Downshift>
);
}
export default App;
This is the sample code I have written. Also, when I click shift+home, it is also not working.
Problem 1: when the user clicked the outside text field value whatever I searched this is disappearing.
Problem 2: shift + home is not working also.
Anyone has any idea how to solve this problem?
when the user clicked the outside text field value whatever I searched this is disappearing.
One way you could do it is to set the stateReducer on the Downshift component:
This function will be called each time downshift sets its internal state (or calls your onStateChange handler for control props). It allows you to modify the state change that will take place which can give you fine grain control over how the component interacts with user updates without having to use Control Props. It gives you the current state and the state that will be set, and you return the state that you want to set.
state: The full current state of downshift.
changes: These are the properties that are about to change. This also has a type property which you can learn more about in the stateChangeTypes section.
function stateReducer(state, changes) {
switch (changes.type) {
case Downshift.stateChangeTypes.mouseUp:
return {
...changes,
isOpen: true,
inputValue: state.inputValue,
};
default:
return changes;
}
}
This way if you click outside the text field the dropdown will stay open and the input value won't be reset.
For a list of all state change types see the documentation here
You might also be able to get something working using the onBlur prop on the input, but I didn't get that working.

How to add places parameter in google map API URL to fetch specific type of location for auto-complete

I'm trying to implement a autocomplete search input bar for auto-completing the results of searching colleges and university in my React app.
my code is as per the following:
import React, { Component } from 'react'
import './App.css'
import PlacesAutocomplete from "react-places-autocomplete";
export class App extends Component {
constructor(props) {
super(props);
this.state = { address: '' };
}
handleChange = address => {
this.setState({ address });
};
render() {
return (
<div>
<PlacesAutocomplete
value={this.state.address}
onChange={this.handleChange}
onSelect={this.handleSelect}
// searchOptions={searchOptions}
shouldFetchSuggestions={this.state.address.length > 3}
>
{({ getInputProps, suggestions, getSuggestionItemProps, loading }) => (
<div >
<input maxLength="50" className="typo"{...getInputProps({ placeholder: "Search Your College" })} />
<div>
{loading ? <div>...loading</div> : null}
{suggestions.map(suggestion => {
const style = {
backgroundColor: suggestion.active ? "#41b6e6" : "",
};
return (
<div className="suggestion" {...getSuggestionItemProps(suggestion, { style })}>
{suggestion.description}
</div>
);
})}
</div>
</div>
)}
</PlacesAutocomplete>
</div>
)
}
}
export default App
and obviously the <script> tag in index.html
<script src="https://maps.googleapis.com/maps/api/js?key=YOUR_API_KEY&libraries=places"></script>
According to The gmaps docs, in order to only get selective results from these types: school,university,secondary-school and college I need to modify it. But, i clearly didn't got the docs correctly and wasn't able to understand it well.
so I wanted to know whats the correct way of formatting the url?
=> React-Places-Autocomplete docs
Note that what you're using is Place Autocomplete, not Place Search. The supported types for Autocomplete are listed in table 3:
geocode
address
establishment
(regions)
(cities)
So using other types like school won't work with Autocomplete; only with the Place Search service.
Hope this helps!

React Facebook Login popping up on page load

I have this code in React:
import React from 'react';
import { FACEBOOK_ID } from '../../../config/credentials';
import FacebookLogin from 'react-facebook-login/dist/facebook-login-render-props';
const responseFacebook = response => {
console.log(response);
};
const FacebookLoginButton = () => (
<div>
<FacebookLogin
appId={FACEBOOK_ID}
autoLoad
callback={responseFacebook}
render={renderProps => (
<button onClick={e => {
console.trace();
}
}>Login via FB</button>
)}
/>
</div>
);
export default FacebookLoginButton;
This is just a simple react facebook login, now my problem is when I reload my local development site, The facebook authorization always popup on load or when I am currently logged in, it automatically logins the user and returns to the console the information from Facebook. is that the normal behavior of this library? I am new to react so any comments would really be appreciated.
Edit:
I've researched a few videos like this one: https://www.youtube.com/watch?v=ea9KyE78qKI&t=10s
It seems like his facebook component popups too when he visit it on his local site at around 12:48 mark but got blocked because Chrome doesn't allow automatic popups.
Make autoLoad as false.
<FacebookLogin
appId={FACEBOOK_ID}
autoLoad={false}
callback={responseFacebook}
render={renderProps => (
<button onClick={e => {
console.trace();
}
}>Login via FB</button>
)}
/>
Just remove the autoLoad option will work fine.
By mentioning autoLoad will take autoLoad = true by default.
autoLoad = false or remove autoload will do the same thing.
Hope this will clear more.
const FacebookLoginButton = () => (
<div>
<FacebookLogin
appId={FACEBOOK_ID}
callback={responseFacebook}
render={renderProps => (
<button onClick={e => {
console.trace();
}
}>Login via FB</button>
)}
/>
</div>
);

Access Gatsby Component from a function

I am trying to access a Gatsby component (Anime) from outside of it.
Can not figure out what instance name this would have or how to name it.
Here is my code:
import React from 'react'
import PropTypes from 'prop-types'
import PreviewCompatibleImage from '../components/PreviewCompatibleImage'
import Anime from 'react-anime';
import VisibilitySensor from 'react-visibility-sensor';
function onChange (isVisible) {
console.log('Element is now %s', isVisible ? 'visible' : 'hidden')
}
const FeatureGrid = ({ gridItems }) => (
<div className="columns is-multiline">
<VisibilitySensor onChange={onChange}>
<Anime delay={(e, i) => i * 100}
scale={[.1, .9]}
autoplay={false}>
{gridItems.map(item => (
<div key={item.text} className="column is-3">
<section className="section">
<div className="has-text-centered">
<div
style={{
width: '160px',
display: 'inline-block',
}}
>
<PreviewCompatibleImage imageInfo={item} />
</div>
</div>
<p>{item.text}</p>
</section>
</div>
))}
</Anime>
</VisibilitySensor>
</div>
)
FeatureGrid.propTypes = {
gridItems: PropTypes.arrayOf(
PropTypes.shape({
image: PropTypes.oneOfType([PropTypes.object, PropTypes.string]),
text: PropTypes.string,
})
),
}
export default FeatureGrid
I want to get the animation to trigger from the onChange function.
How do I get the name or set the name of the Anime component so I can access it from the function?
Or is there another way I should address this?
Using a Gatsby starter netlify CMS as the base, so extending on their code, but seems that const is not the route I should take.
I want the animation to trigger when it becomes visible.
Any suggestions?
According to the docs react-visibility-sensor :
You can pass a child function, which can be convenient if you don't need to store the visibility anywhere
so maybe instead of using the onchange function you can just pass the isVisible parameter, something like:
<VisibilitySensor>
{({isVisible}) =>
<Anime delay={(e, i) => i * 100}
// the rest of your codes here ...
</Anime>
}
</VisibilitySensor>
Otherwise you can convert this function to a react component and set states, etc..

Ckeditor disable auto inline won't disable inline from being selected on page load

I'm trying to develop a simple CMS for my page. I want it to where I can edit and delete a users reply on click of a button. I got the delete functionality done so I figured for the reply functionality I would use CKeditor. What I'm struggling with is not being able to disable the autoinline feature. I can still select my div on load of the page rather than clicking a button to enable the inline feature but I don't know what I am doing wrong?
I have tried setting the feature directly in my index.html file, a custom js script file and the config.js ckeditor file but none worked. I am using Ckeditor 4.
this is the snippit of code I'm trying to use to disable inline on my div element but it's not working and I don't know why, i currently have it placed in a custom.js script file and I'm calling it from my index.html file
CKEDITOR.disableAutoInline = true;
Here is my code for my replies page:
import React from 'react';
import CKEditor from 'react-ckeditor-component';
import ForumpageService from '../../services/forumService';
import appController from '../../controllers/appController';
class Forumreplies extends React.Component {
constructor(props){
super(props);
this.elementName = "editor_" + this.props.id;
this.editReply = this.editReply.bind(this);
this.state = {
reply: '',
errorMsg: '',
isLoggedin: false,
// Ck Editor State
reply: '',
}
}
async componentDidMount(){
const topicId = this.props.match.params.topicid
const postDetails = await ForumpageService.replyDetails({topicId: topicId})
this.setState({
postDetails: postDetails[0],
topicId: topicId
})
await this.postReplies();
}
// Edit the reply
async editReply(id, e){
//CKEDITOR.inline(this.elementName);
}
async postReplies(){
const repliesData = await ForumpageService.postreplyDetails({topicId: this.state.topicId})
await this.setState({repliesData});
}
render(){
const repliesData = currentReply.map((row, index) => {
return (
<div className="row" id="reply-messages" key={index}>
<div className="col-md-8" suppressContentEditableWarning contentEditable="true" id={this.elementName}>
<p dangerouslySetInnerHTML={{__html: row.reply_message }} />
</div>
<div className="col-md-2">
{this.state.isloggedinuserId == row.reply_user_id && this.state.isLoggedin == true ? <i className="far fa-edit" onClick={this.editReply.bind(this, row.reply_id)} title="Edit this reply?"></i> : null }
</div>
</div>
})
return (
<div className="container" id="forum-replies">
<div className="row">
{repliesData}
</div>
</div>
)
}
}
export default Forumreplies;
Instead of creating a div and calling CKEDITOR.inline, you should try to use the react-ckeditor-component as its own way (not as an inline editor).
You could do something like: if the button wasn't pressed, render a div with the text content, but after the button was pressed, render a <CKEditor /> component as in the documentation
There is no documented way to set the editor as inline in this package that you are using.
EDIT:
I can see you are not using the react-ckeditor-component features, but following what you've done so far, you could set the contentEditable="true" property of the div only when the button is pressed:
<div className="col-md-8" suppressContentEditableWarning contentEditable={this.state.isEditing} id={this.elementName}>
<p dangerouslySetInnerHTML={{__html: row.reply_message }} />
</div>
And then set the isEditing to true on the onClick handler. Your component will update and then re-render with the contentEditable property set to true

Resources