Compare commits
2 Commits
Author | SHA1 | Date | |
---|---|---|---|
|
64614fdd7c | ||
e2f0f5c7e6 |
2
package-lock.json
generated
2
package-lock.json
generated
@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "image-viewer",
|
"name": "image-viewer",
|
||||||
"version": "0.1.2",
|
"version": "0.1.3",
|
||||||
"lockfileVersion": 1,
|
"lockfileVersion": 1,
|
||||||
"requires": true,
|
"requires": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import React, {createContext} from 'react'
|
import React, { createContext } from 'react'
|
||||||
import OnePageView from './OnePageView'
|
import OnePageView from './OnePageView'
|
||||||
import TwoPagesView from './TwoPagesView'
|
import TwoPagesView from './TwoPagesView.jsx'
|
||||||
import BookComponentsController from './BookComponentsController'
|
import BookComponentsController from './BookComponentsController'
|
||||||
import './index.css'
|
import './index.css'
|
||||||
|
|
||||||
@ -12,7 +12,7 @@ export interface IBookPage {
|
|||||||
thumbnail?: string
|
thumbnail?: string
|
||||||
}
|
}
|
||||||
|
|
||||||
export const getBookViewModes = (currIndex = 0, srcLength = 0)=>[
|
export const getBookViewModes = (currIndex = 0, srcLength = 0) => [
|
||||||
{
|
{
|
||||||
text: 'One Page',
|
text: 'One Page',
|
||||||
value: 'one page',
|
value: 'one page',
|
||||||
@ -41,25 +41,25 @@ export interface IBookContext {
|
|||||||
src?: IBookPage[],
|
src?: IBookPage[],
|
||||||
flagToReverse?: boolean,
|
flagToReverse?: boolean,
|
||||||
mode?: BookViewMode,
|
mode?: BookViewMode,
|
||||||
readonly setBookContextState: (newState: any)=> undefined
|
readonly setBookContextState: (newState: any) => undefined
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
const getPagesCountToTurn = (mode: string)=>{
|
const getPagesCountToTurn = (mode: string) => {
|
||||||
let pagesToTurn = getBookViewModes().find(item=> item.value === mode)?.pagesToTurn
|
let pagesToTurn = getBookViewModes().find(item => item.value === mode)?.pagesToTurn
|
||||||
return pagesToTurn || 0
|
return pagesToTurn || 0
|
||||||
}
|
}
|
||||||
|
|
||||||
class BookComponent extends React.Component<any, any>{
|
class BookComponent extends React.Component<any, any>{
|
||||||
constructor(props: any){
|
constructor(props: any) {
|
||||||
super(props)
|
super(props)
|
||||||
this.state = {
|
this.state = {
|
||||||
currIndex: 0,
|
currIndex: 0,
|
||||||
src: [],
|
src: [],
|
||||||
flagToReverse: false,
|
flagToReverse: false,
|
||||||
mode: "one page",
|
mode: "one page",
|
||||||
setBookContextState: (newState: IBookContext)=>{
|
setBookContextState: (newState: IBookContext) => {
|
||||||
this.setState((oldState: any)=> ({
|
this.setState((oldState: any) => ({
|
||||||
...oldState,
|
...oldState,
|
||||||
...newState
|
...newState
|
||||||
}))
|
}))
|
||||||
@ -69,10 +69,10 @@ class BookComponent extends React.Component<any, any>{
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
changePage = (goToPrevious: boolean, indexToGo?: number)=>{
|
changePage = (goToPrevious: boolean, indexToGo?: number) => {
|
||||||
const {mode, currIndex} = this.state
|
const { mode, currIndex } = this.state
|
||||||
const pagesCountToTurn = indexToGo || getPagesCountToTurn(mode)
|
const pagesCountToTurn = indexToGo || getPagesCountToTurn(mode)
|
||||||
const prefixPageCount = goToPrevious? -1 : 1
|
const prefixPageCount = goToPrevious ? -1 : 1
|
||||||
|
|
||||||
this.setState({
|
this.setState({
|
||||||
currIndex: (pagesCountToTurn * prefixPageCount) + currIndex,
|
currIndex: (pagesCountToTurn * prefixPageCount) + currIndex,
|
||||||
@ -80,12 +80,12 @@ class BookComponent extends React.Component<any, any>{
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
componentDidMount(){
|
componentDidMount() {
|
||||||
fetch('https://picsum.photos/v2/list')
|
fetch('https://picsum.photos/v2/list?limit=30')
|
||||||
.then(response=>{
|
.then(response => {
|
||||||
return response.json()
|
return response.json()
|
||||||
}).then(data=>{
|
}).then(data => {
|
||||||
data = data.map((item: any)=>{
|
data = data.map((item: any) => {
|
||||||
return {
|
return {
|
||||||
src: item.download_url,
|
src: item.download_url,
|
||||||
alt: item.author
|
alt: item.author
|
||||||
@ -98,9 +98,9 @@ class BookComponent extends React.Component<any, any>{
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
getControlsDisable = ()=>{
|
getControlsDisable = () => {
|
||||||
const {mode, currIndex, src} = this.state
|
const { mode, currIndex, src } = this.state
|
||||||
const {nextDisable, prevDisable} = getBookViewModes(currIndex, src.length).find(item=> item.value === mode) || {
|
const { nextDisable, prevDisable } = getBookViewModes(currIndex, src.length).find(item => item.value === mode) || {
|
||||||
nextDisable: true,
|
nextDisable: true,
|
||||||
prevDisable: true
|
prevDisable: true
|
||||||
}
|
}
|
||||||
@ -111,20 +111,20 @@ class BookComponent extends React.Component<any, any>{
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
render(){
|
render() {
|
||||||
const {mode} = this.state
|
const { mode } = this.state
|
||||||
|
|
||||||
return <BookContext.Provider value={{...this.state}}>
|
return <BookContext.Provider value={{ ...this.state }}>
|
||||||
<BookContext.Consumer>
|
<BookContext.Consumer>
|
||||||
{state=>(
|
{state => (
|
||||||
<>
|
<>
|
||||||
{mode === "one page" && <OnePageView {...state}/>}
|
{mode === "one page" && <OnePageView {...state} />}
|
||||||
{mode === "two pages" && <TwoPagesView {...state}/>}
|
{mode === "two pages" && <TwoPagesView {...state} />}
|
||||||
<BookComponentsController
|
<BookComponentsController
|
||||||
onPrevClick={()=>{
|
onPrevClick={() => {
|
||||||
this.changePage(true)
|
this.changePage(true)
|
||||||
}}
|
}}
|
||||||
onNextClick={()=>{
|
onNextClick={() => {
|
||||||
this.changePage(false)
|
this.changePage(false)
|
||||||
}}
|
}}
|
||||||
{...this.getControlsDisable()}
|
{...this.getControlsDisable()}
|
||||||
|
91
src/components/TwoPagesView.jsx
Normal file
91
src/components/TwoPagesView.jsx
Normal file
@ -0,0 +1,91 @@
|
|||||||
|
import React, { useState, useEffect } from 'react';
|
||||||
|
import { useTransition, animated } from 'react-spring';
|
||||||
|
import {
|
||||||
|
ComponentContainer,
|
||||||
|
PageComponent,
|
||||||
|
PageContainer,
|
||||||
|
} from './OnePageView';
|
||||||
|
|
||||||
|
export default function TwoPagesView(props) {
|
||||||
|
let { src, currIndex, flagToReverse } = props;
|
||||||
|
const [pagesToshow, setPagesToShow] = useState([
|
||||||
|
{
|
||||||
|
src: '',
|
||||||
|
alt: '',
|
||||||
|
thumbnail: '',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
src: '',
|
||||||
|
alt: '',
|
||||||
|
thumbnail: '',
|
||||||
|
},
|
||||||
|
]);
|
||||||
|
|
||||||
|
const transitionFirst = useTransition(pagesToshow[0], (item) => item.src, {
|
||||||
|
from: {opacity: 1, transform: flagToReverse? "translate3d(-50%, 0, 0)": "translate3d(100%, 0, 0)"},
|
||||||
|
enter: { opacity: 1, transform: "translate3d(0%, 0, 0)" },
|
||||||
|
leave: { opacity: 0, transform: flagToReverse? "translate3d(100%, 0, 0)": "translate3d(-50%, 0, 0)"},
|
||||||
|
});
|
||||||
|
|
||||||
|
const transitionSecond = useTransition(pagesToshow[1], (item) => item.src, {
|
||||||
|
from: {opacity: 1, transform: flagToReverse? "translate3d(0%, 0, 0)": "translate3d(150%, 0, 0)"},
|
||||||
|
enter: { opacity: 1, transform: "translate3d(50%, 0, 0)" },
|
||||||
|
leave: { opacity: 0, transform: flagToReverse? "translate3d(150%, 0, 0)": "translate3d(0%, 0, 0)"},
|
||||||
|
});
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
const shouldShowPage = (pageIndex) => {
|
||||||
|
return src.length > 0 && pageIndex <= src.length - 1;
|
||||||
|
};
|
||||||
|
|
||||||
|
const newCurrIndex = currIndex % 2 === 0 ? currIndex : currIndex - 1;
|
||||||
|
|
||||||
|
const shouldShowFirstPage = shouldShowPage(newCurrIndex);
|
||||||
|
if (shouldShowFirstPage) {
|
||||||
|
const shouldShowSecondPage = shouldShowPage(newCurrIndex + 1);
|
||||||
|
setPagesToShow([
|
||||||
|
src[newCurrIndex],
|
||||||
|
shouldShowSecondPage
|
||||||
|
? src[newCurrIndex + 1]
|
||||||
|
: {
|
||||||
|
src: '',
|
||||||
|
alt: '',
|
||||||
|
thumbnail: '',
|
||||||
|
},
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
}, [currIndex, src]);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<ComponentContainer>
|
||||||
|
<PageContainer>
|
||||||
|
{transitionFirst.map(({ item, key, props }) => {
|
||||||
|
return (
|
||||||
|
item && (
|
||||||
|
<animated.div style={{ ...props }} key={key}>
|
||||||
|
<PageComponent width={'50%'} src={item.src} />
|
||||||
|
</animated.div>
|
||||||
|
)
|
||||||
|
);
|
||||||
|
})}
|
||||||
|
|
||||||
|
{transitionSecond.map(({ item, key, props }) => {
|
||||||
|
return (
|
||||||
|
item && (
|
||||||
|
<animated.div
|
||||||
|
style={{
|
||||||
|
...props,
|
||||||
|
transformOrigin: 'left center',
|
||||||
|
}}
|
||||||
|
key={key}
|
||||||
|
>
|
||||||
|
<PageComponent width={'50%'} src={item.src} />
|
||||||
|
</animated.div>
|
||||||
|
)
|
||||||
|
);
|
||||||
|
})}
|
||||||
|
</PageContainer>
|
||||||
|
</ComponentContainer>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
@ -1,91 +0,0 @@
|
|||||||
import React, {useState, useEffect} from 'react'
|
|
||||||
import {Transition, animated} from 'react-spring/renderprops'
|
|
||||||
import {ComponentContainer, PageComponent, PageContainer} from './OnePageView'
|
|
||||||
import { IBookContext } from './BookComponent'
|
|
||||||
|
|
||||||
export default function TwoPagesView(props: any) {
|
|
||||||
let {src, currIndex, flagToReverse} = props
|
|
||||||
const [pagesToshow, setPagesToShow] = useState<IBookContext[]>([])
|
|
||||||
|
|
||||||
useEffect(()=>{
|
|
||||||
const shouldShowPage = (pageIndex: number)=>{
|
|
||||||
return src.length > 0 && pageIndex <= src.length - 1
|
|
||||||
}
|
|
||||||
|
|
||||||
const newCurrIndex = currIndex % 2 === 0 ? currIndex: currIndex - 1
|
|
||||||
|
|
||||||
const shouldShowFirstPage = shouldShowPage(newCurrIndex)
|
|
||||||
if(shouldShowFirstPage){
|
|
||||||
const shouldShowSecondPage = shouldShowPage(newCurrIndex + 1)
|
|
||||||
setPagesToShow([
|
|
||||||
src[newCurrIndex],
|
|
||||||
shouldShowSecondPage? src[newCurrIndex + 1]: {
|
|
||||||
src: '',
|
|
||||||
alt: '',
|
|
||||||
thumbnail: '',
|
|
||||||
}
|
|
||||||
])
|
|
||||||
}
|
|
||||||
}, [currIndex, src])
|
|
||||||
|
|
||||||
return (
|
|
||||||
<ComponentContainer>
|
|
||||||
<PageContainer>
|
|
||||||
<Transition
|
|
||||||
reset
|
|
||||||
unique
|
|
||||||
items={pagesToshow}
|
|
||||||
keys={(item: any)=> item.src}
|
|
||||||
initial={{}}
|
|
||||||
from={{opacity: 1, transform: flagToReverse? "translate3d(-50%, 0, 0)": "translate3d(100%, 0, 0)"}}
|
|
||||||
enter={{ opacity: 1, transform: "translate3d(0%, 0, 0)" }}
|
|
||||||
leave={{ opacity: 0, transform: flagToReverse? "translate3d(100%, 0, 0)": "translate3d(-50%, 0, 0)"}}
|
|
||||||
>
|
|
||||||
{
|
|
||||||
currIndex=> style=>{
|
|
||||||
return(
|
|
||||||
<animated.div style={{
|
|
||||||
...style,
|
|
||||||
}}>
|
|
||||||
{React.createElement(()=>{
|
|
||||||
return <PageComponent width={"50%"} src={pagesToshow[0]? pagesToshow[0].src: null}/>
|
|
||||||
})}
|
|
||||||
</animated.div>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</Transition>
|
|
||||||
|
|
||||||
<Transition
|
|
||||||
reset
|
|
||||||
unique
|
|
||||||
items={pagesToshow}
|
|
||||||
keys={(item: any)=> item.src}
|
|
||||||
from={{opacity: 1, transform: flagToReverse? "translate3d(0%, 0, 0)": "translate3d(150%, 0, 0)"}}
|
|
||||||
enter={{ opacity: 1, transform: "translate3d(50%, 0, 0)" }}
|
|
||||||
leave={{ opacity: 0, transform: flagToReverse? "translate3d(150%, 0, 0)": "translate3d(0%, 0, 0)"}}
|
|
||||||
initial={{}}
|
|
||||||
>
|
|
||||||
{
|
|
||||||
currIndex=> style=>{
|
|
||||||
return(
|
|
||||||
<animated.div style={{
|
|
||||||
...style,
|
|
||||||
}}>
|
|
||||||
{React.createElement(()=>{
|
|
||||||
return <PageComponent width={"50%"} src={pagesToshow[1]? pagesToshow[1].src: null}/>
|
|
||||||
})}
|
|
||||||
</animated.div>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</Transition>
|
|
||||||
</PageContainer>
|
|
||||||
</ComponentContainer>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
interface Book {
|
|
||||||
name: string
|
|
||||||
}
|
|
||||||
|
|
Loading…
Reference in New Issue
Block a user