Convert reader image styling to vw/vh
Preparation for infinite scroll, since there will be a wrapper which fits its content in width and height, thus, percentage based dimension won't work anymore
This commit is contained in:
@@ -24,6 +24,8 @@ import { applyStyles } from '@/modules/core/utils/ApplyStyles.ts';
|
|||||||
import { useReaderScrollbarContext } from '@/modules/reader/contexts/ReaderScrollbarContext.tsx';
|
import { useReaderScrollbarContext } from '@/modules/reader/contexts/ReaderScrollbarContext.tsx';
|
||||||
import { MediaQuery } from '@/modules/core/utils/MediaQuery.tsx';
|
import { MediaQuery } from '@/modules/core/utils/MediaQuery.tsx';
|
||||||
import { withPropsFrom } from '@/modules/core/hoc/withPropsFrom.tsx';
|
import { withPropsFrom } from '@/modules/core/hoc/withPropsFrom.tsx';
|
||||||
|
import { useNavBarContext } from '@/modules/navigation-bar/contexts/NavbarContext.tsx';
|
||||||
|
import { NavbarContextType } from '@/modules/navigation-bar/NavigationBar.types.ts';
|
||||||
|
|
||||||
const getCustomFilterString = (customFilter: ReaderCustomFilter): string =>
|
const getCustomFilterString = (customFilter: ReaderCustomFilter): string =>
|
||||||
Object.keys(customFilter)
|
Object.keys(customFilter)
|
||||||
@@ -73,10 +75,12 @@ const BaseReaderPage = ({
|
|||||||
onLoad,
|
onLoad,
|
||||||
onError,
|
onError,
|
||||||
setRef,
|
setRef,
|
||||||
|
readerNavBarWidth,
|
||||||
...props
|
...props
|
||||||
}: Omit<ComponentProps<typeof SpinnerImage>, 'ref' | 'spinnerStyle' | 'imgStyle' | 'onLoad' | 'onError'> &
|
}: Omit<ComponentProps<typeof SpinnerImage>, 'ref' | 'spinnerStyle' | 'imgStyle' | 'onLoad' | 'onError'> &
|
||||||
Pick<IReaderSettings, 'readingMode' | 'customFilter' | 'pageScaleMode' | 'shouldStretchPage' | 'readerWidth'> &
|
Pick<IReaderSettings, 'readingMode' | 'customFilter' | 'pageScaleMode' | 'shouldStretchPage' | 'readerWidth'> &
|
||||||
Pick<TReaderScrollbarContext, 'scrollbarXSize' | 'scrollbarYSize'> & {
|
Pick<TReaderScrollbarContext, 'scrollbarXSize' | 'scrollbarYSize'> &
|
||||||
|
Pick<NavbarContextType, 'readerNavBarWidth'> & {
|
||||||
pageIndex: number;
|
pageIndex: number;
|
||||||
pagesIndex: number;
|
pagesIndex: number;
|
||||||
isPrimaryPage: boolean;
|
isPrimaryPage: boolean;
|
||||||
@@ -129,7 +133,15 @@ const BaseReaderPage = ({
|
|||||||
...getImageMarginStyling(doublePage, position),
|
...getImageMarginStyling(doublePage, position),
|
||||||
}}
|
}}
|
||||||
imgStyle={{
|
imgStyle={{
|
||||||
...getReaderImageStyling(readingMode, shouldStretchPage, pageScaleMode, doublePage, readerWidth),
|
...getReaderImageStyling(
|
||||||
|
readingMode,
|
||||||
|
shouldStretchPage,
|
||||||
|
pageScaleMode,
|
||||||
|
doublePage,
|
||||||
|
readerWidth,
|
||||||
|
readerNavBarWidth + scrollbarYSize,
|
||||||
|
scrollbarXSize,
|
||||||
|
),
|
||||||
display: 'block',
|
display: 'block',
|
||||||
...applyStyles(!display, {
|
...applyStyles(!display, {
|
||||||
display: 'none',
|
display: 'none',
|
||||||
@@ -156,7 +168,7 @@ const BaseReaderPage = ({
|
|||||||
|
|
||||||
export const ReaderPage = withPropsFrom(
|
export const ReaderPage = withPropsFrom(
|
||||||
memo(BaseReaderPage),
|
memo(BaseReaderPage),
|
||||||
[ReaderService.useSettingsWithoutDefaultFlag, useReaderScrollbarContext],
|
[ReaderService.useSettingsWithoutDefaultFlag, useReaderScrollbarContext, useNavBarContext],
|
||||||
[
|
[
|
||||||
'readingMode',
|
'readingMode',
|
||||||
'customFilter',
|
'customFilter',
|
||||||
@@ -165,5 +177,6 @@ export const ReaderPage = withPropsFrom(
|
|||||||
'readerWidth',
|
'readerWidth',
|
||||||
'scrollbarXSize',
|
'scrollbarXSize',
|
||||||
'scrollbarYSize',
|
'scrollbarYSize',
|
||||||
|
'readerNavBarWidth',
|
||||||
],
|
],
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -9,7 +9,7 @@
|
|||||||
import { memo, ReactNode, useCallback, useEffect, useMemo, useRef } from 'react';
|
import { memo, ReactNode, useCallback, useEffect, useMemo, useRef } from 'react';
|
||||||
import Box, { BoxProps } from '@mui/material/Box';
|
import Box, { BoxProps } from '@mui/material/Box';
|
||||||
import { ReaderService } from '@/modules/reader/services/ReaderService.ts';
|
import { ReaderService } from '@/modules/reader/services/ReaderService.ts';
|
||||||
import { getPageIndexesToLoad, getReaderImageWrapperStyling } from '@/modules/reader/utils/ReaderPager.utils.tsx';
|
import { getPageIndexesToLoad } from '@/modules/reader/utils/ReaderPager.utils.tsx';
|
||||||
import { ReaderStatePages } from '@/modules/reader/types/ReaderProgressBar.types.ts';
|
import { ReaderStatePages } from '@/modules/reader/types/ReaderProgressBar.types.ts';
|
||||||
import { IReaderSettings, ReaderPagerProps, ReaderTransitionPageMode } from '@/modules/reader/types/Reader.types.ts';
|
import { IReaderSettings, ReaderPagerProps, ReaderTransitionPageMode } from '@/modules/reader/types/Reader.types.ts';
|
||||||
import { ReaderTransitionPage } from '@/modules/reader/components/viewer/ReaderTransitionPage.tsx';
|
import { ReaderTransitionPage } from '@/modules/reader/components/viewer/ReaderTransitionPage.tsx';
|
||||||
@@ -23,15 +23,9 @@ const BaseBasePager = ({
|
|||||||
createPage,
|
createPage,
|
||||||
slots,
|
slots,
|
||||||
readingMode,
|
readingMode,
|
||||||
pageScaleMode,
|
|
||||||
shouldStretchPage,
|
|
||||||
readerWidth,
|
|
||||||
imagePreLoadAmount,
|
imagePreLoadAmount,
|
||||||
}: Omit<ReaderPagerProps, 'pageLoadStates' | 'retryFailedPagesKeyPrefix'> &
|
}: Omit<ReaderPagerProps, 'pageLoadStates' | 'retryFailedPagesKeyPrefix'> &
|
||||||
Pick<
|
Pick<IReaderSettings, 'readingMode' | 'imagePreLoadAmount'> & {
|
||||||
IReaderSettings,
|
|
||||||
'readingMode' | 'pageScaleMode' | 'shouldStretchPage' | 'readerWidth' | 'imagePreLoadAmount'
|
|
||||||
> & {
|
|
||||||
createPage: (
|
createPage: (
|
||||||
page: ReaderStatePages['pages'][number],
|
page: ReaderStatePages['pages'][number],
|
||||||
pagesIndex: number,
|
pagesIndex: number,
|
||||||
@@ -68,10 +62,7 @@ const BaseBasePager = ({
|
|||||||
return (
|
return (
|
||||||
<Box
|
<Box
|
||||||
{...slots?.boxProps}
|
{...slots?.boxProps}
|
||||||
sx={[
|
sx={[...(Array.isArray(slots?.boxProps?.sx) ? (slots?.boxProps?.sx ?? []) : [slots?.boxProps?.sx])]}
|
||||||
...(Array.isArray(slots?.boxProps?.sx) ? (slots?.boxProps?.sx ?? []) : [slots?.boxProps?.sx]),
|
|
||||||
getReaderImageWrapperStyling(readingMode, shouldStretchPage, pageScaleMode, readerWidth),
|
|
||||||
]}
|
|
||||||
>
|
>
|
||||||
<ReaderTransitionPage type={ReaderTransitionPageMode.PREVIOUS} />
|
<ReaderTransitionPage type={ReaderTransitionPageMode.PREVIOUS} />
|
||||||
{pages.map((page, pagesIndex) =>
|
{pages.map((page, pagesIndex) =>
|
||||||
@@ -91,5 +82,5 @@ const BaseBasePager = ({
|
|||||||
export const BasePager = withPropsFrom(
|
export const BasePager = withPropsFrom(
|
||||||
memo(BaseBasePager),
|
memo(BaseBasePager),
|
||||||
[ReaderService.useSettingsWithoutDefaultFlag],
|
[ReaderService.useSettingsWithoutDefaultFlag],
|
||||||
['readingMode', 'pageScaleMode', 'shouldStretchPage', 'readerWidth', 'imagePreLoadAmount'],
|
['readingMode', 'imagePreLoadAmount'],
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -10,7 +10,12 @@ import { Direction, useTheme } from '@mui/material/styles';
|
|||||||
import { Fragment, memo, useMemo } from 'react';
|
import { Fragment, memo, useMemo } from 'react';
|
||||||
import { BasePager } from '@/modules/reader/components/viewer/pager/BasePager.tsx';
|
import { BasePager } from '@/modules/reader/components/viewer/pager/BasePager.tsx';
|
||||||
import { ReaderService } from '@/modules/reader/services/ReaderService.ts';
|
import { ReaderService } from '@/modules/reader/services/ReaderService.ts';
|
||||||
import { IReaderSettings, ReaderPagerProps, ReadingDirection } from '@/modules/reader/types/Reader.types.ts';
|
import {
|
||||||
|
IReaderSettings,
|
||||||
|
ReaderPagerProps,
|
||||||
|
ReaderPageScaleMode,
|
||||||
|
ReadingDirection,
|
||||||
|
} from '@/modules/reader/types/Reader.types.ts';
|
||||||
import { applyStyles } from '@/modules/core/utils/ApplyStyles.ts';
|
import { applyStyles } from '@/modules/core/utils/ApplyStyles.ts';
|
||||||
import { createReaderPage } from '@/modules/reader/utils/ReaderPager.utils.tsx';
|
import { createReaderPage } from '@/modules/reader/utils/ReaderPager.utils.tsx';
|
||||||
import { getNextIndexFromPage, getPage } from '@/modules/reader/utils/ReaderProgressBar.utils.tsx';
|
import { getNextIndexFromPage, getPage } from '@/modules/reader/utils/ReaderProgressBar.utils.tsx';
|
||||||
@@ -44,8 +49,9 @@ const BaseReaderDoublePagedPager = ({
|
|||||||
pageLoadStates,
|
pageLoadStates,
|
||||||
retryFailedPagesKeyPrefix,
|
retryFailedPagesKeyPrefix,
|
||||||
readingDirection,
|
readingDirection,
|
||||||
|
pageScaleMode,
|
||||||
...props
|
...props
|
||||||
}: ReaderPagerProps & Pick<IReaderSettings, 'readingDirection'>) => {
|
}: ReaderPagerProps & Pick<IReaderSettings, 'readingDirection' | 'pageScaleMode'>) => {
|
||||||
const { currentPageIndex, pages, totalPages } = props;
|
const { currentPageIndex, pages, totalPages } = props;
|
||||||
|
|
||||||
const { direction: themeDirection } = useTheme();
|
const { direction: themeDirection } = useTheme();
|
||||||
@@ -102,7 +108,13 @@ const BaseReaderDoublePagedPager = ({
|
|||||||
slots={{
|
slots={{
|
||||||
boxProps: {
|
boxProps: {
|
||||||
sx: {
|
sx: {
|
||||||
|
...applyStyles(pageScaleMode === ReaderPageScaleMode.ORIGINAL, {
|
||||||
margin: 'auto',
|
margin: 'auto',
|
||||||
|
}),
|
||||||
|
width: '100%',
|
||||||
|
minWidth: 'fit-content',
|
||||||
|
height: '100%',
|
||||||
|
minHeight: 'fit-content',
|
||||||
display: 'flex',
|
display: 'flex',
|
||||||
flexDirection: 'row',
|
flexDirection: 'row',
|
||||||
flexWrap: 'nowrap',
|
flexWrap: 'nowrap',
|
||||||
@@ -122,5 +134,5 @@ const BaseReaderDoublePagedPager = ({
|
|||||||
export const ReaderDoublePagedPager = withPropsFrom(
|
export const ReaderDoublePagedPager = withPropsFrom(
|
||||||
memo(BaseReaderDoublePagedPager),
|
memo(BaseReaderDoublePagedPager),
|
||||||
[ReaderService.useSettingsWithoutDefaultFlag],
|
[ReaderService.useSettingsWithoutDefaultFlag],
|
||||||
['readingDirection'],
|
['readingDirection', 'pageScaleMode'],
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -38,20 +38,22 @@ const getPageWidth = (
|
|||||||
pageScaleMode: IReaderSettings['pageScaleMode'],
|
pageScaleMode: IReaderSettings['pageScaleMode'],
|
||||||
isDoublePage: boolean,
|
isDoublePage: boolean,
|
||||||
readerWidth: IReaderSettings['readerWidth'],
|
readerWidth: IReaderSettings['readerWidth'],
|
||||||
shouldStretchPage: IReaderSettings['shouldStretchPage'],
|
|
||||||
isImage: boolean,
|
isImage: boolean,
|
||||||
): string => {
|
): string => {
|
||||||
// only return 50% in case pages should get stretched, otherwise, pages might unintentionally shrink in size (e.g. 2 pages with different dimensions, the bigger page will shrink due to taking up more than 50%)
|
if (shouldApplyReaderWidth(readerWidth, pageScaleMode)) {
|
||||||
if (isImage && isDoublePage && shouldStretchPage) {
|
const width = readerWidth.value;
|
||||||
return '50%';
|
if (isImage && isDoublePage) {
|
||||||
|
return `${width / 2}vw`;
|
||||||
}
|
}
|
||||||
|
|
||||||
// the image wrapper gets applied the reader width limit and therefore the images can take up 100%
|
return `${width}vw`;
|
||||||
if (!isImage && shouldApplyReaderWidth(readerWidth, pageScaleMode)) {
|
|
||||||
return `${readerWidth?.value}%`;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return '100%';
|
if (isImage && isDoublePage) {
|
||||||
|
return `50vw`;
|
||||||
|
}
|
||||||
|
|
||||||
|
return `100vw`;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const getImagePlaceholderStyling = (
|
export const getImagePlaceholderStyling = (
|
||||||
@@ -142,7 +144,13 @@ const getReaderDimensionStyling = (
|
|||||||
readingMode: IReaderSettings['readingMode'],
|
readingMode: IReaderSettings['readingMode'],
|
||||||
shouldStretchPage: IReaderSettings['shouldStretchPage'],
|
shouldStretchPage: IReaderSettings['shouldStretchPage'],
|
||||||
pageScaleMode: IReaderSettings['pageScaleMode'],
|
pageScaleMode: IReaderSettings['pageScaleMode'],
|
||||||
|
widthOffset: number,
|
||||||
|
heightOffset: number,
|
||||||
): CSSObject => {
|
): CSSObject => {
|
||||||
|
const finalWidthOffset = readingMode === ReadingMode.DOUBLE_PAGE ? widthOffset / 2 : widthOffset;
|
||||||
|
const fullWidth = `calc(${width} - ${finalWidthOffset}px)`;
|
||||||
|
const fullHeight = `calc(100vh - ${heightOffset}px)`;
|
||||||
|
|
||||||
switch (pageScaleMode) {
|
switch (pageScaleMode) {
|
||||||
case ReaderPageScaleMode.WIDTH:
|
case ReaderPageScaleMode.WIDTH:
|
||||||
return {
|
return {
|
||||||
@@ -151,9 +159,9 @@ const getReaderDimensionStyling = (
|
|||||||
minWidth: 'unset',
|
minWidth: 'unset',
|
||||||
}),
|
}),
|
||||||
...applyStyles(shouldStretchPage, {
|
...applyStyles(shouldStretchPage, {
|
||||||
minWidth: width,
|
minWidth: fullWidth,
|
||||||
}),
|
}),
|
||||||
maxWidth: width,
|
maxWidth: fullWidth,
|
||||||
};
|
};
|
||||||
case ReaderPageScaleMode.HEIGHT:
|
case ReaderPageScaleMode.HEIGHT:
|
||||||
return {
|
return {
|
||||||
@@ -162,9 +170,9 @@ const getReaderDimensionStyling = (
|
|||||||
minHeight: 'unset',
|
minHeight: 'unset',
|
||||||
}),
|
}),
|
||||||
...applyStyles(shouldStretchPage, {
|
...applyStyles(shouldStretchPage, {
|
||||||
minHeight: '100%',
|
minHeight: fullHeight,
|
||||||
}),
|
}),
|
||||||
maxHeight: `100%`,
|
maxHeight: fullHeight,
|
||||||
};
|
};
|
||||||
case ReaderPageScaleMode.SCREEN:
|
case ReaderPageScaleMode.SCREEN:
|
||||||
return {
|
return {
|
||||||
@@ -175,19 +183,19 @@ const getReaderDimensionStyling = (
|
|||||||
minHeight: 'unset',
|
minHeight: 'unset',
|
||||||
}),
|
}),
|
||||||
...applyStyles(shouldStretchPage, {
|
...applyStyles(shouldStretchPage, {
|
||||||
minWidth: width,
|
minWidth: fullWidth,
|
||||||
minHeight: '100%',
|
minHeight: fullHeight,
|
||||||
...applyStyles(readingMode === ReadingMode.CONTINUOUS_HORIZONTAL, {
|
...applyStyles(readingMode === ReadingMode.CONTINUOUS_HORIZONTAL, {
|
||||||
minWidth: 'unset',
|
minWidth: 'unset',
|
||||||
minHeight: '100%',
|
minHeight: fullHeight,
|
||||||
}),
|
}),
|
||||||
...applyStyles(isContinuousVerticalReadingMode(readingMode), {
|
...applyStyles(isContinuousVerticalReadingMode(readingMode), {
|
||||||
minWidth: width,
|
minWidth: fullWidth,
|
||||||
minHeight: 'unset',
|
minHeight: 'unset',
|
||||||
}),
|
}),
|
||||||
}),
|
}),
|
||||||
maxWidth: width,
|
maxWidth: fullWidth,
|
||||||
maxHeight: `100%`,
|
maxHeight: fullHeight,
|
||||||
};
|
};
|
||||||
case ReaderPageScaleMode.ORIGINAL:
|
case ReaderPageScaleMode.ORIGINAL:
|
||||||
return {};
|
return {};
|
||||||
@@ -196,56 +204,25 @@ const getReaderDimensionStyling = (
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
export const getReaderImageWrapperStyling = (
|
|
||||||
readingMode: IReaderSettings['readingMode'],
|
|
||||||
shouldStretchPage: IReaderSettings['shouldStretchPage'],
|
|
||||||
pageScaleMode: IReaderSettings['pageScaleMode'],
|
|
||||||
readerWidth: IReaderSettings['readerWidth'],
|
|
||||||
): CSSObject => {
|
|
||||||
const width = getPageWidth(pageScaleMode, false, readerWidth, shouldStretchPage, false);
|
|
||||||
const readerImageStyling = getReaderDimensionStyling(width, readingMode, shouldStretchPage, pageScaleMode);
|
|
||||||
|
|
||||||
switch (pageScaleMode) {
|
|
||||||
case ReaderPageScaleMode.WIDTH:
|
|
||||||
case ReaderPageScaleMode.SCREEN:
|
|
||||||
return {
|
|
||||||
...readerImageStyling,
|
|
||||||
...applyStyles(shouldStretchPage, {
|
|
||||||
width: '100%',
|
|
||||||
}),
|
|
||||||
// setting the "width" of the wrapper is required for being able to properly size the image placeholders
|
|
||||||
...applyStyles(shouldApplyReaderWidth(readerWidth, pageScaleMode), {
|
|
||||||
width,
|
|
||||||
}),
|
|
||||||
};
|
|
||||||
case ReaderPageScaleMode.HEIGHT:
|
|
||||||
case ReaderPageScaleMode.ORIGINAL:
|
|
||||||
return {
|
|
||||||
...readerImageStyling,
|
|
||||||
};
|
|
||||||
default:
|
|
||||||
throw new Error(`Unexpected "PageScaleMode" (${pageScaleMode})`);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
export const getReaderImageStyling = (
|
export const getReaderImageStyling = (
|
||||||
readingMode: IReaderSettings['readingMode'],
|
readingMode: IReaderSettings['readingMode'],
|
||||||
shouldStretchPage: IReaderSettings['shouldStretchPage'],
|
shouldStretchPage: IReaderSettings['shouldStretchPage'],
|
||||||
pageScaleMode: IReaderSettings['pageScaleMode'],
|
pageScaleMode: IReaderSettings['pageScaleMode'],
|
||||||
isDoublePage: boolean,
|
isDoublePage: boolean,
|
||||||
readerWidth: IReaderSettings['readerWidth'],
|
readerWidth: IReaderSettings['readerWidth'],
|
||||||
|
widthOffset: number,
|
||||||
|
heightOffset: number,
|
||||||
): CSSObject => {
|
): CSSObject => {
|
||||||
const width = getPageWidth(pageScaleMode, isDoublePage, readerWidth, shouldStretchPage, true);
|
const width = getPageWidth(pageScaleMode, isDoublePage, readerWidth, true);
|
||||||
return getReaderDimensionStyling(width, readingMode, shouldStretchPage, pageScaleMode);
|
return getReaderDimensionStyling(width, readingMode, shouldStretchPage, pageScaleMode, widthOffset, heightOffset);
|
||||||
};
|
};
|
||||||
|
|
||||||
export const getImageMarginStyling = (doublePage: boolean, objectFitPosition?: 'left' | 'right'): CSSObject => ({
|
export const getImageMarginStyling = (doublePage: boolean, objectFitPosition?: 'left' | 'right'): CSSObject => ({
|
||||||
m: 'auto',
|
m: 'auto',
|
||||||
...applyStyles(doublePage, {
|
...applyStyles(doublePage, {
|
||||||
m: 'unset',
|
// the margin on the object fit position needs to be removed so that there is no space between both images
|
||||||
// the applied margin is the opposite of the objectFitPosition
|
...applyStyles(objectFitPosition === 'right', { mr: 'unset ' }),
|
||||||
...applyStyles(objectFitPosition === 'right', { ml: 'auto ' }),
|
...applyStyles(objectFitPosition === 'left', { ml: 'unset ' }),
|
||||||
...applyStyles(objectFitPosition === 'left', { mr: 'auto ' }),
|
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user