Move in the poster list with h,j,k,l
This commit is contained in:
parent
48a6dc9fef
commit
20ca2adefc
@ -1,4 +1,4 @@
|
|||||||
import React, { useState, useEffect } from "react"
|
import React, { useState, useEffect, useCallback } from "react"
|
||||||
import PropTypes from "prop-types"
|
import PropTypes from "prop-types"
|
||||||
import { OrderedMap, Map } from "immutable"
|
import { OrderedMap, Map } from "immutable"
|
||||||
import fuzzy from "fuzzy";
|
import fuzzy from "fuzzy";
|
||||||
@ -81,6 +81,99 @@ ListPosters.propTypes = {
|
|||||||
export default ListPosters;
|
export default ListPosters;
|
||||||
|
|
||||||
const Posters = (props) => {
|
const Posters = (props) => {
|
||||||
|
const addMoreCount = 20;
|
||||||
|
const [size, setSize] = useState(0);
|
||||||
|
const [postersPerRow, setPostersPerRow] = useState(0);
|
||||||
|
const [posterHeight, setPosterHeight] = useState(0);
|
||||||
|
|
||||||
|
const loadMore = () => {
|
||||||
|
if ((size === props.elmts.size)) { return }
|
||||||
|
|
||||||
|
const newSize = (((size + addMoreCount) >= props.elmts.size)
|
||||||
|
? props.elmts.size
|
||||||
|
: size + addMoreCount);
|
||||||
|
|
||||||
|
setSize(newSize);
|
||||||
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
loadMore()
|
||||||
|
}, [props.elmts.size]);
|
||||||
|
|
||||||
|
const move = (event) => {
|
||||||
|
// Only run the function if nothing else if actively focused
|
||||||
|
if (document.activeElement.tagName.toLowerCase() !== "body") { return }
|
||||||
|
|
||||||
|
let diff = 0;
|
||||||
|
let moveFocus = 0;
|
||||||
|
switch (event.key) {
|
||||||
|
case "Enter":
|
||||||
|
props.onKeyEnter(props.selectedImdbId);
|
||||||
|
return;
|
||||||
|
case "l":
|
||||||
|
diff = 1;
|
||||||
|
break;
|
||||||
|
case "h":
|
||||||
|
diff = -1;
|
||||||
|
break;
|
||||||
|
case "k":
|
||||||
|
diff = -1*postersPerRow;
|
||||||
|
moveFocus = -1*posterHeight;
|
||||||
|
break;
|
||||||
|
case "j":
|
||||||
|
diff = postersPerRow;
|
||||||
|
moveFocus = posterHeight;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get the index of the currently selected item
|
||||||
|
const idx = props.elmts.keySeq().findIndex(k => k === props.selectedImdbId);
|
||||||
|
|
||||||
|
var newIdx = idx + diff;
|
||||||
|
|
||||||
|
// Handle edge cases
|
||||||
|
if (newIdx > props.elmts.size -1) {
|
||||||
|
newIdx = props.elmts.size -1;
|
||||||
|
} else if (newIdx < 0) {
|
||||||
|
newIdx = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get the imdbID of the newly selected item
|
||||||
|
var selectedImdb = Object.keys(props.elmts.toJS())[newIdx];
|
||||||
|
|
||||||
|
// Select the movie
|
||||||
|
props.selectPoster(selectedImdb);
|
||||||
|
if (moveFocus !== 0) {
|
||||||
|
window.scrollBy(0, moveFocus);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const posterCount = useCallback(node => {
|
||||||
|
if (node === null) { return }
|
||||||
|
const parentWidth = node.getBoundingClientRect().width;
|
||||||
|
const childContainer = node.getElementsByClassName("img-thumbnail");
|
||||||
|
let childWidth = 0;
|
||||||
|
let posterHeight = 0;
|
||||||
|
if ((childContainer !== null) && (childContainer.item(0) !== null)) {
|
||||||
|
const child = childContainer.item(0);
|
||||||
|
childWidth = child.getBoundingClientRect().width + child.getBoundingClientRect().left;
|
||||||
|
posterHeight = child.getBoundingClientRect().height;
|
||||||
|
}
|
||||||
|
|
||||||
|
let numberPerRow = (childWidth >= parentWidth) ? 1 : Math.floor(parentWidth/childWidth);
|
||||||
|
setPostersPerRow(numberPerRow);
|
||||||
|
setPosterHeight(posterHeight);
|
||||||
|
})
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
document.onkeypress = move;
|
||||||
|
return () => {
|
||||||
|
document.onkeypress = null;
|
||||||
|
}
|
||||||
|
}, [move])
|
||||||
|
|
||||||
if (props.loading) {
|
if (props.loading) {
|
||||||
return (<Loader />);
|
return (<Loader />);
|
||||||
}
|
}
|
||||||
@ -93,46 +186,31 @@ const Posters = (props) => {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const addMoreCount = 20;
|
|
||||||
const [size, setSize] = useState(0);
|
|
||||||
useEffect(() => {
|
|
||||||
loadMore()
|
|
||||||
}, [props.elmts.size]);
|
|
||||||
const hasMore = () => (size !== props.elmts.size);
|
|
||||||
|
|
||||||
const loadMore = () => {
|
|
||||||
if (!hasMore()) { return }
|
|
||||||
|
|
||||||
const newSize = (((size + addMoreCount) >= props.elmts.size)
|
|
||||||
? props.elmts.size
|
|
||||||
: size + addMoreCount);
|
|
||||||
|
|
||||||
setSize(newSize);
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<InfiniteScroll
|
<div ref={posterCount}>
|
||||||
className="poster-list d-flex flex-column flex-sm-row flex-sm-wrap justify-content-around"
|
<InfiniteScroll
|
||||||
dataLength={size}
|
className="poster-list d-flex flex-column flex-sm-row flex-sm-wrap justify-content-around"
|
||||||
next={loadMore}
|
dataLength={size}
|
||||||
hasMore={hasMore()}
|
next={loadMore}
|
||||||
loader={<Loader />}
|
hasMore={(size !== props.elmts.size)}
|
||||||
>
|
loader={<Loader />}
|
||||||
{props.elmts.slice(0, size).toIndexedSeq().map(function(el, index) {
|
>
|
||||||
const imdbId = el.get("imdb_id");
|
{props.elmts.slice(0, size).toIndexedSeq().map(function(el, index) {
|
||||||
const selected = (imdbId === props.selectedImdbId) ? true : false;
|
const imdbId = el.get("imdb_id");
|
||||||
|
const selected = (imdbId === props.selectedImdbId) ? true : false;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Poster
|
<Poster
|
||||||
data={el}
|
data={el}
|
||||||
key={`poster-${imdbId}-${index}`}
|
key={`poster-${imdbId}-${index}`}
|
||||||
selected={selected}
|
selected={selected}
|
||||||
onClick={() => props.selectPoster(imdbId)}
|
onClick={() => props.selectPoster(imdbId)}
|
||||||
onDoubleClick={() => props.onDoubleClick(imdbId)}
|
onDoubleClick={() => props.onDoubleClick(imdbId)}
|
||||||
/>
|
/>
|
||||||
)
|
)
|
||||||
} ,this)}
|
} ,this)}
|
||||||
</InfiniteScroll>
|
</InfiniteScroll>
|
||||||
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Posters.propTypes = {
|
Posters.propTypes = {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user