mirror of
https://github.com/cheeaun/phanpy.git
synced 2024-11-29 04:38:55 +03:00
Little adjustments, show more captions
This commit is contained in:
parent
6a16b25722
commit
359fd92ae0
3 changed files with 163 additions and 133 deletions
|
@ -59,6 +59,7 @@ function Media({
|
||||||
lang,
|
lang,
|
||||||
showOriginal,
|
showOriginal,
|
||||||
autoAnimate,
|
autoAnimate,
|
||||||
|
showCaption,
|
||||||
onClick = () => {},
|
onClick = () => {},
|
||||||
}) {
|
}) {
|
||||||
const {
|
const {
|
||||||
|
@ -169,6 +170,48 @@ function Media({
|
||||||
aspectRatio: `${width} / ${height}`,
|
aspectRatio: `${width} / ${height}`,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const multilineDesc =
|
||||||
|
!!description && description.trim().split('\n').length > 2;
|
||||||
|
const longDesc = description?.length > MEDIA_CAPTION_LIMIT || multilineDesc;
|
||||||
|
const showInlineDesc =
|
||||||
|
!!showCaption &&
|
||||||
|
!showOriginal &&
|
||||||
|
!!description &&
|
||||||
|
!longDesc &&
|
||||||
|
!multilineDesc;
|
||||||
|
const Figure = !showInlineDesc
|
||||||
|
? Fragment
|
||||||
|
: (props) => {
|
||||||
|
const { children, ...restProps } = props;
|
||||||
|
return (
|
||||||
|
<figure {...restProps}>
|
||||||
|
{children}
|
||||||
|
<figcaption
|
||||||
|
class={`media-caption media-caption-${
|
||||||
|
longDesc ? 'long' : 'short'
|
||||||
|
}`}
|
||||||
|
lang={lang}
|
||||||
|
dir="auto"
|
||||||
|
onClick={(e) => {
|
||||||
|
e.preventDefault();
|
||||||
|
e.stopPropagation();
|
||||||
|
states.showMediaAlt = {
|
||||||
|
alt: description,
|
||||||
|
lang,
|
||||||
|
};
|
||||||
|
}}
|
||||||
|
title={
|
||||||
|
description.length > MEDIA_CAPTION_LIMIT
|
||||||
|
? description
|
||||||
|
: undefined
|
||||||
|
}
|
||||||
|
>
|
||||||
|
{description}
|
||||||
|
</figcaption>
|
||||||
|
</figure>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
if (isImage) {
|
if (isImage) {
|
||||||
// Note: type: unknown might not have width/height
|
// Note: type: unknown might not have width/height
|
||||||
quickPinchZoomProps.containerProps.style.display = 'inherit';
|
quickPinchZoomProps.containerProps.style.display = 'inherit';
|
||||||
|
@ -187,83 +230,85 @@ function Media({
|
||||||
}, [mediaURL]);
|
}, [mediaURL]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Parent
|
<Figure>
|
||||||
ref={parentRef}
|
<Parent
|
||||||
class={`media media-image`}
|
ref={parentRef}
|
||||||
onClick={onClick}
|
class={`media media-image`}
|
||||||
data-orientation={orientation}
|
onClick={onClick}
|
||||||
data-has-alt={!!description || undefined}
|
data-orientation={orientation}
|
||||||
style={
|
data-has-alt={!showInlineDesc}
|
||||||
showOriginal
|
style={
|
||||||
? {
|
showOriginal
|
||||||
backgroundImage: `url(${previewUrl})`,
|
? {
|
||||||
backgroundSize: imageSmallerThanParent
|
backgroundImage: `url(${previewUrl})`,
|
||||||
? `${width}px ${height}px`
|
backgroundSize: imageSmallerThanParent
|
||||||
: undefined,
|
? `${width}px ${height}px`
|
||||||
}
|
: undefined,
|
||||||
: mediaStyles
|
|
||||||
}
|
|
||||||
>
|
|
||||||
{showOriginal ? (
|
|
||||||
<QuickPinchZoom {...quickPinchZoomProps}>
|
|
||||||
<img
|
|
||||||
ref={mediaRef}
|
|
||||||
src={mediaURL}
|
|
||||||
alt={description}
|
|
||||||
width={width}
|
|
||||||
height={height}
|
|
||||||
data-orientation={orientation}
|
|
||||||
loading="eager"
|
|
||||||
decoding="sync"
|
|
||||||
onLoad={(e) => {
|
|
||||||
e.target.closest('.media-image').style.backgroundImage = '';
|
|
||||||
e.target.closest('.media-zoom').style.display = '';
|
|
||||||
setPinchZoomEnabled(true);
|
|
||||||
}}
|
|
||||||
onError={(e) => {
|
|
||||||
const { src } = e.target;
|
|
||||||
if (src === mediaURL) {
|
|
||||||
e.target.src = remoteMediaURL;
|
|
||||||
}
|
}
|
||||||
}}
|
: mediaStyles
|
||||||
/>
|
}
|
||||||
</QuickPinchZoom>
|
>
|
||||||
) : (
|
{showOriginal ? (
|
||||||
<>
|
<QuickPinchZoom {...quickPinchZoomProps}>
|
||||||
<img
|
<img
|
||||||
src={mediaURL}
|
ref={mediaRef}
|
||||||
alt={description}
|
src={mediaURL}
|
||||||
width={width}
|
alt={description}
|
||||||
height={height}
|
width={width}
|
||||||
data-orientation={orientation}
|
height={height}
|
||||||
loading="lazy"
|
data-orientation={orientation}
|
||||||
style={{
|
loading="eager"
|
||||||
backgroundColor:
|
decoding="sync"
|
||||||
rgbAverageColor && `rgb(${rgbAverageColor.join(',')})`,
|
onLoad={(e) => {
|
||||||
backgroundPosition: focalBackgroundPosition || 'center',
|
e.target.closest('.media-image').style.backgroundImage = '';
|
||||||
// Duration based on width or height in pixels
|
e.target.closest('.media-zoom').style.display = '';
|
||||||
// 100px per second (rough estimate)
|
setPinchZoomEnabled(true);
|
||||||
// Clamp between 5s and 120s
|
}}
|
||||||
'--anim-duration': `${Math.min(
|
onError={(e) => {
|
||||||
Math.max(Math.max(width, height) / 100, 5),
|
const { src } = e.target;
|
||||||
120,
|
if (src === mediaURL) {
|
||||||
)}s`,
|
e.target.src = remoteMediaURL;
|
||||||
}}
|
}
|
||||||
onLoad={(e) => {
|
}}
|
||||||
e.target.closest('.media-image').style.backgroundImage = '';
|
/>
|
||||||
e.target.dataset.loaded = true;
|
</QuickPinchZoom>
|
||||||
}}
|
) : (
|
||||||
onError={(e) => {
|
<>
|
||||||
const { src } = e.target;
|
<img
|
||||||
if (src === mediaURL) {
|
src={mediaURL}
|
||||||
e.target.src = remoteMediaURL;
|
alt={showInlineDesc ? '' : description}
|
||||||
}
|
width={width}
|
||||||
}}
|
height={height}
|
||||||
/>
|
data-orientation={orientation}
|
||||||
<AltBadge alt={description} lang={lang} />
|
loading="lazy"
|
||||||
</>
|
style={{
|
||||||
)}
|
backgroundColor:
|
||||||
</Parent>
|
rgbAverageColor && `rgb(${rgbAverageColor.join(',')})`,
|
||||||
|
backgroundPosition: focalBackgroundPosition || 'center',
|
||||||
|
// Duration based on width or height in pixels
|
||||||
|
// 100px per second (rough estimate)
|
||||||
|
// Clamp between 5s and 120s
|
||||||
|
'--anim-duration': `${Math.min(
|
||||||
|
Math.max(Math.max(width, height) / 100, 5),
|
||||||
|
120,
|
||||||
|
)}s`,
|
||||||
|
}}
|
||||||
|
onLoad={(e) => {
|
||||||
|
e.target.closest('.media-image').style.backgroundImage = '';
|
||||||
|
e.target.dataset.loaded = true;
|
||||||
|
}}
|
||||||
|
onError={(e) => {
|
||||||
|
const { src } = e.target;
|
||||||
|
if (src === mediaURL) {
|
||||||
|
e.target.src = remoteMediaURL;
|
||||||
|
}
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
{!showInlineDesc && <AltBadge alt={description} lang={lang} />}
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</Parent>
|
||||||
|
</Figure>
|
||||||
);
|
);
|
||||||
} else if (type === 'gifv' || type === 'video' || isVideoMaybe) {
|
} else if (type === 'gifv' || type === 'video' || isVideoMaybe) {
|
||||||
const shortDuration = original.duration < 31;
|
const shortDuration = original.duration < 31;
|
||||||
|
@ -291,11 +336,8 @@ function Media({
|
||||||
></video>
|
></video>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
const showInlineDesc = !showOriginal && !isGIF && !!description;
|
|
||||||
const Container = showInlineDesc ? 'figure' : Fragment;
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Container>
|
<Figure>
|
||||||
<Parent
|
<Parent
|
||||||
class={`media media-${isGIF ? 'gif' : 'video'} ${
|
class={`media media-${isGIF ? 'gif' : 'video'} ${
|
||||||
autoGIFAnimate ? 'media-contain' : ''
|
autoGIFAnimate ? 'media-contain' : ''
|
||||||
|
@ -303,7 +345,7 @@ function Media({
|
||||||
data-orientation={orientation}
|
data-orientation={orientation}
|
||||||
data-formatted-duration={formattedDuration}
|
data-formatted-duration={formattedDuration}
|
||||||
data-label={isGIF && !showOriginal && !autoGIFAnimate ? 'GIF' : ''}
|
data-label={isGIF && !showOriginal && !autoGIFAnimate ? 'GIF' : ''}
|
||||||
data-has-alt={!!description || undefined}
|
data-has-alt={!showInlineDesc}
|
||||||
// style={{
|
// style={{
|
||||||
// backgroundColor:
|
// backgroundColor:
|
||||||
// rgbAverageColor && `rgb(${rgbAverageColor.join(',')})`,
|
// rgbAverageColor && `rgb(${rgbAverageColor.join(',')})`,
|
||||||
|
@ -391,67 +433,48 @@ function Media({
|
||||||
<div class="media-play">
|
<div class="media-play">
|
||||||
<Icon icon="play" size="xl" />
|
<Icon icon="play" size="xl" />
|
||||||
</div>
|
</div>
|
||||||
|
{!showInlineDesc && <AltBadge alt={description} lang={lang} />}
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
{!showOriginal && !showInlineDesc && (
|
{!showOriginal && !showInlineDesc && (
|
||||||
<AltBadge alt={description} lang={lang} />
|
<AltBadge alt={description} lang={lang} />
|
||||||
)}
|
)}
|
||||||
</Parent>
|
</Parent>
|
||||||
{showInlineDesc && (
|
</Figure>
|
||||||
<figcaption
|
|
||||||
class={`media-caption media-caption-${
|
|
||||||
description.length <= MEDIA_CAPTION_LIMIT ? 'short' : 'long'
|
|
||||||
}`}
|
|
||||||
lang={lang}
|
|
||||||
dir="auto"
|
|
||||||
onClick={(e) => {
|
|
||||||
e.preventDefault();
|
|
||||||
e.stopPropagation();
|
|
||||||
states.showMediaAlt = {
|
|
||||||
alt: description,
|
|
||||||
lang,
|
|
||||||
};
|
|
||||||
}}
|
|
||||||
title={
|
|
||||||
description.length > MEDIA_CAPTION_LIMIT ? description : undefined
|
|
||||||
}
|
|
||||||
>
|
|
||||||
{description}
|
|
||||||
</figcaption>
|
|
||||||
)}
|
|
||||||
</Container>
|
|
||||||
);
|
);
|
||||||
} else if (type === 'audio') {
|
} else if (type === 'audio') {
|
||||||
const formattedDuration = formatDuration(original.duration);
|
const formattedDuration = formatDuration(original.duration);
|
||||||
return (
|
return (
|
||||||
<Parent
|
<Figure>
|
||||||
class="media media-audio"
|
<Parent
|
||||||
data-formatted-duration={formattedDuration}
|
class="media media-audio"
|
||||||
data-has-alt={!!description || undefined}
|
data-formatted-duration={formattedDuration}
|
||||||
onClick={onClick}
|
data-has-alt={!showInlineDesc}
|
||||||
style={!showOriginal && mediaStyles}
|
onClick={onClick}
|
||||||
>
|
style={!showOriginal && mediaStyles}
|
||||||
{showOriginal ? (
|
>
|
||||||
<audio src={remoteUrl || url} preload="none" controls autoplay />
|
{showOriginal ? (
|
||||||
) : previewUrl ? (
|
<audio src={remoteUrl || url} preload="none" controls autoplay />
|
||||||
<img
|
) : previewUrl ? (
|
||||||
src={previewUrl}
|
<img
|
||||||
alt={description}
|
src={previewUrl}
|
||||||
width={width}
|
alt={showInlineDesc ? '' : description}
|
||||||
height={height}
|
width={width}
|
||||||
data-orientation={orientation}
|
height={height}
|
||||||
loading="lazy"
|
data-orientation={orientation}
|
||||||
/>
|
loading="lazy"
|
||||||
) : null}
|
/>
|
||||||
{!showOriginal && (
|
) : null}
|
||||||
<>
|
{!showOriginal && (
|
||||||
<div class="media-play">
|
<>
|
||||||
<Icon icon="play" size="xl" />
|
<div class="media-play">
|
||||||
</div>
|
<Icon icon="play" size="xl" />
|
||||||
<AltBadge alt={description} lang={lang} />
|
</div>
|
||||||
</>
|
{!showInlineDesc && <AltBadge alt={description} lang={lang} />}
|
||||||
)}
|
</>
|
||||||
</Parent>
|
)}
|
||||||
|
</Parent>
|
||||||
|
</Figure>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -719,6 +719,7 @@
|
||||||
color: var(--text-insignificant-color);
|
color: var(--text-insignificant-color);
|
||||||
line-height: 1.2;
|
line-height: 1.2;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
|
white-space: pre-line;
|
||||||
|
|
||||||
&.media-caption-long {
|
&.media-caption-long {
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
|
@ -1027,6 +1028,11 @@ body:has(#modal-container .carousel) .status .media img:hover {
|
||||||
z-index: 1;
|
z-index: 1;
|
||||||
text-shadow: 0 var(--hairline-width) var(--bg-color);
|
text-shadow: 0 var(--hairline-width) var(--bg-color);
|
||||||
mix-blend-mode: luminosity;
|
mix-blend-mode: luminosity;
|
||||||
|
white-space: pre-line;
|
||||||
|
|
||||||
|
&:is(:hover, :focus) {
|
||||||
|
mix-blend-mode: normal;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
.carousel-item button.media-alt .media-alt-desc {
|
.carousel-item button.media-alt .media-alt-desc {
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
|
@ -1684,7 +1690,7 @@ a.card:is(:hover, :focus):visited {
|
||||||
transition: 0.15s ease-out;
|
transition: 0.15s ease-out;
|
||||||
transition-property: transform, opacity, mix-blend-mode;
|
transition-property: transform, opacity, mix-blend-mode;
|
||||||
transform: scale(1.15);
|
transform: scale(1.15);
|
||||||
opacity: 0.8;
|
opacity: 0.9;
|
||||||
mix-blend-mode: normal;
|
mix-blend-mode: normal;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1269,6 +1269,7 @@ function Status({
|
||||||
key={media.id}
|
key={media.id}
|
||||||
media={media}
|
media={media}
|
||||||
autoAnimate={isSizeLarge}
|
autoAnimate={isSizeLarge}
|
||||||
|
showCaption={mediaAttachments.length === 1}
|
||||||
lang={language}
|
lang={language}
|
||||||
to={`/${instance}/s/${id}?${
|
to={`/${instance}/s/${id}?${
|
||||||
withinContext ? 'media' : 'media-only'
|
withinContext ? 'media' : 'media-only'
|
||||||
|
|
Loading…
Reference in a new issue