Fix broken layout on lyrics scroll
- App layout would break when transitioning into the full-screen due to scrollIntoView - Replace scroll action with scrollTop implementation
This commit is contained in:
parent
493e13ebc0
commit
72811dbedb
2 changed files with 37 additions and 7 deletions
|
@ -6,7 +6,7 @@ import { RiInformationFill } from 'react-icons/ri';
|
||||||
import styled from 'styled-components';
|
import styled from 'styled-components';
|
||||||
import { useSongLyricsByRemoteId, useSongLyricsBySong } from './queries/lyric-query';
|
import { useSongLyricsByRemoteId, useSongLyricsBySong } from './queries/lyric-query';
|
||||||
import { SynchronizedLyrics } from './synchronized-lyrics';
|
import { SynchronizedLyrics } from './synchronized-lyrics';
|
||||||
import { ScrollArea, Spinner, TextTitle } from '/@/renderer/components';
|
import { Spinner, TextTitle } from '/@/renderer/components';
|
||||||
import { ErrorFallback } from '/@/renderer/features/action-required';
|
import { ErrorFallback } from '/@/renderer/features/action-required';
|
||||||
import { UnsynchronizedLyrics } from '/@/renderer/features/lyrics/unsynchronized-lyrics';
|
import { UnsynchronizedLyrics } from '/@/renderer/features/lyrics/unsynchronized-lyrics';
|
||||||
import { getServerById, useCurrentSong, usePlayerStore } from '/@/renderer/store';
|
import { getServerById, useCurrentSong, usePlayerStore } from '/@/renderer/store';
|
||||||
|
@ -53,11 +53,12 @@ const LyricsContainer = styled.div`
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
|
|
||||||
const ScrollContainer = styled(motion(ScrollArea))`
|
const ScrollContainer = styled(motion.div)`
|
||||||
position: relative;
|
position: relative;
|
||||||
z-index: 1;
|
z-index: 1;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
transform: translateY(-2rem);
|
|
||||||
|
|
||||||
mask-image: linear-gradient(
|
mask-image: linear-gradient(
|
||||||
180deg,
|
180deg,
|
||||||
|
@ -182,7 +183,6 @@ export const Lyrics = () => {
|
||||||
<ScrollContainer
|
<ScrollContainer
|
||||||
animate={{ opacity: 1 }}
|
animate={{ opacity: 1 }}
|
||||||
initial={{ opacity: 0 }}
|
initial={{ opacity: 0 }}
|
||||||
scrollHideDelay={0}
|
|
||||||
transition={{ duration: 0.5 }}
|
transition={{ duration: 0.5 }}
|
||||||
>
|
>
|
||||||
{isSynchronizedLyrics ? (
|
{isSynchronizedLyrics ? (
|
||||||
|
|
|
@ -16,7 +16,19 @@ import styled from 'styled-components';
|
||||||
const mpvPlayer = isElectron() ? window.electron.mpvPlayer : null;
|
const mpvPlayer = isElectron() ? window.electron.mpvPlayer : null;
|
||||||
|
|
||||||
const SynchronizedLyricsContainer = styled.div`
|
const SynchronizedLyricsContainer = styled.div`
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
padding: 5rem 0;
|
padding: 5rem 0;
|
||||||
|
overflow: scroll;
|
||||||
|
transform: translateY(-2rem);
|
||||||
|
|
||||||
|
mask-image: linear-gradient(
|
||||||
|
180deg,
|
||||||
|
transparent 5%,
|
||||||
|
rgba(0, 0, 0, 100%) 20%,
|
||||||
|
rgba(0, 0, 0, 100%) 85%,
|
||||||
|
transparent 95%
|
||||||
|
);
|
||||||
`;
|
`;
|
||||||
|
|
||||||
interface SynchronizedLyricsProps extends Omit<FullLyricsMetadata, 'lyrics'> {
|
interface SynchronizedLyricsProps extends Omit<FullLyricsMetadata, 'lyrics'> {
|
||||||
|
@ -120,7 +132,10 @@ export const SynchronizedLyrics = ({
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const currentLyric = document.querySelector(`#lyric-${index}`);
|
const doc = document.getElementById('sychronized-lyrics-scroll-container') as HTMLElement;
|
||||||
|
const currentLyric = document.querySelector(`#lyric-${index}`) as HTMLElement;
|
||||||
|
const offsetTop = currentLyric?.offsetTop - doc?.clientHeight / 2 ?? 0;
|
||||||
|
|
||||||
if (currentLyric === null) {
|
if (currentLyric === null) {
|
||||||
lyricRef.current = undefined;
|
lyricRef.current = undefined;
|
||||||
return;
|
return;
|
||||||
|
@ -129,7 +144,7 @@ export const SynchronizedLyrics = ({
|
||||||
currentLyric.classList.add('active');
|
currentLyric.classList.add('active');
|
||||||
|
|
||||||
if (followRef.current) {
|
if (followRef.current) {
|
||||||
currentLyric.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
doc?.scroll({ behavior: 'smooth', top: offsetTop });
|
||||||
}
|
}
|
||||||
|
|
||||||
if (index !== lyricRef.current!.length - 1) {
|
if (index !== lyricRef.current!.length - 1) {
|
||||||
|
@ -254,8 +269,23 @@ export const SynchronizedLyrics = ({
|
||||||
timerEpoch.current += 1;
|
timerEpoch.current += 1;
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
|
const hideScrollbar = () => {
|
||||||
|
const doc = document.getElementById('sychronized-lyrics-scroll-container') as HTMLElement;
|
||||||
|
doc.classList.add('hide-scrollbar');
|
||||||
|
};
|
||||||
|
|
||||||
|
const showScrollbar = () => {
|
||||||
|
const doc = document.getElementById('sychronized-lyrics-scroll-container') as HTMLElement;
|
||||||
|
doc.classList.remove('hide-scrollbar');
|
||||||
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<SynchronizedLyricsContainer className="synchronized-lyrics">
|
<SynchronizedLyricsContainer
|
||||||
|
className="synchronized-lyrics overlay-scrollbar"
|
||||||
|
id="sychronized-lyrics-scroll-container"
|
||||||
|
onMouseEnter={showScrollbar}
|
||||||
|
onMouseLeave={hideScrollbar}
|
||||||
|
>
|
||||||
{source && (
|
{source && (
|
||||||
<LyricLine
|
<LyricLine
|
||||||
className="lyric-credit"
|
className="lyric-credit"
|
||||||
|
|
Reference in a new issue