Skip to content

Instantly share code, notes, and snippets.

@DavidP1983
Created January 12, 2022 00:01
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save DavidP1983/03cf49f07c1565fe778917cd1ec4c614 to your computer and use it in GitHub Desktop.
Save DavidP1983/03cf49f07c1565fe778917cd1ec4c614 to your computer and use it in GitHub Desktop.
import { useState, useEffect, useRef } from 'react';
// import { HideUntilLoaded } from 'react-animation';
import PropTypes from 'prop-types';
import Spinner from '../spinner/Spinner';
import ErrorMessage from '../errorMessage/ErrorMessage';
import MarvelServices from '../services/MarvelServices';
import './charlist.scss';
const CharList = (props) => {
const [charList, setCharList] = useState([]);
const [loading, setLoading] = useState(true);
const [error, setError] = useState(false);
const [newItemLoading, setNewItemLoading] = useState(false);
const [offset, setOffset] = useState(1548);
const [charEnded, setCharEnded] = useState(true);
console.log(offset);
const marvelService = new MarvelServices();
useEffect(() => {
console.log('updateChar');
updateChar();
}, []);
function handleScroll() {
if (newItemLoading) return;
if (charEnded) {
if (window.pageYOffset + document.documentElement.clientHeight >= document.documentElement.scrollHeight) {
onCharListLoading();
updateChar(offset);
}
}
}
useEffect(() => {
console.log('scroll');
window.addEventListener('scroll', handleScroll);
return () => {
window.removeEventListener('scroll', handleScroll);
console.log('unmount');
}
});
const updateChar = (offset) => {
onCharListLoading();
marvelService.getAllCharacters(offset)
.then(onCharListLoaded)
.catch(onError)
}
//loading new items button disable
const onCharListLoading = () => {
setNewItemLoading(true);
}
const onCharListLoaded = (newCharList) => {
let ended = true;
if (newCharList.length < 9) {
ended = false;
}
setCharList(charList => [...charList, ...newCharList]);
setLoading(loading => false);
setNewItemLoading(newItemLoading => false);
setOffset(offset => offset + 9);
setCharEnded(charEnded => ended);
}
const onError = () => {
//We use without callback, because we don't mind wich state we have had before
setError(true);
setLoading(false);
}
const myRefs = useRef([]);
// we use function declaration
function renderItems(arr) {
const items = arr.map((item, i) => {
let imgStyle = { 'objectFit': 'cover' };
if (item.thumbnail === 'http://i.annihil.us/u/prod/marvel/i/mg/b/40/image_not_available.jpg') {
imgStyle = { 'objectFit': 'unset' };
}
return (
// <HideUntilLoaded key={item.id} animationIn="bounceIn" durationOut={2000}>
<li tabIndex={0}
//instead of callback function setRef we will do all the stuff inside this map
ref={elem => myRefs.current[i] = elem}
className="char__item"
key={item.id}
onClick={() => props.onCharSelected(item.id, myRefs.current[i], myRefs.current)}
onFocus={() => props.onCharSelected(item.id, myRefs.current[i], myRefs.current)}>
<img src={item.thumbnail} alt={item.name} style={imgStyle} />
<div className="char__name">{item.name}</div>
</li>
// </HideUntilLoaded>
)
});
// А эта конструкция вынесена для центровки спиннера/ошибки
return (
<ul className="char__grid">
{items}
</ul>
)
}
const items = renderItems(charList);
const errorMessage = error ? <ErrorMessage /> : null;
const spinner = loading ? <Spinner /> : null;
const content = !(loading || error) ? items : null;
// let name = charEnded ? 'There are no items to load' : 'load more';
// const styleField = {
// 'minWidth': '300px',
// 'color': 'white',
// 'filter': 'grayscale(.5)'
// }
return (
<div className="char__list">
{errorMessage}
{spinner}
{content}
{/* <button className="button button__main button__long"
disabled={newItemLoading}
style={{'display': charEnded ? 'none' : 'block'}}
// style={charEnded ? styleField : null}
onClick={() => updateChar(offset)}>
<div className="inner">{name}</div>
</button> */}
</div>
)
}
CharList.propTypes = {
onCharSelected: PropTypes.func.isRequired
}
export default CharList;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment