/* * Copyright (C) 2026 Fluxer Contributors * * This file is part of Fluxer. * * Fluxer is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * Fluxer is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Affero General Public License for more details. * * You should have received a copy of the GNU Affero General Public License * along with Fluxer. If not, see . */ .mediaContainer { position: relative; display: flex; align-items: center; justify-content: center; width: 100%; height: 100%; max-width: 100%; max-height: 100%; min-width: 0; min-height: 0; overflow: hidden; pointer-events: none; } .mediaContainer img, .mediaContainer canvas, .mediaContainer picture, .mediaContainer svg { max-width: 100%; max-height: 100%; width: auto; height: auto; object-fit: contain; display: block; pointer-events: auto; } .mediaContainer video { max-width: 100%; max-height: 100%; object-fit: contain; display: block; pointer-events: auto; } .transformWrapper { width: 100% !important; height: 100% !important; display: flex; align-items: center; justify-content: center; overflow: hidden; min-width: 0; min-height: 0; } .transformContent { display: flex; align-items: center; justify-content: center; width: 100% !important; height: 100% !important; overflow: hidden; min-width: 0; min-height: 0; } .controlButton { border-radius: 0.375rem; padding: 0.375rem; transition-property: color, background-color, transform; transition-duration: 150ms; transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1); cursor: pointer; display: flex; align-items: center; justify-content: center; border: none; background: transparent; } .controlButton:active { transform: scale(0.95); } @media (pointer: coarse), (max-width: 767px) { .controlButton:active { transform: none; } } .controlButtonDefault { color: var(--text-tertiary); } .controlButtonDefault:hover { color: var(--text-secondary); } .controlButtonDefaultActive { background-color: var(--background-tertiary); color: var(--text-primary); } .controlButtonPrimary { color: var(--text-tertiary); } .controlButtonPrimary:hover { color: var(--text-secondary); } .controlButtonPrimaryActive { background-color: var(--brand-primary); color: var(--text-on-brand-primary); } .controlButtonPrimaryActive:hover { background-color: var(--brand-primary); } .controlButtonDanger { color: var(--text-tertiary); } .controlButtonDanger:hover { color: var(--text-secondary); } .controlButtonDangerActive { background-color: var(--status-danger); color: var(--text-on-brand-primary); } .controlButtonDangerActive:hover { background-color: var(--status-danger); } .controlButtonDisabled { opacity: 0.5; cursor: not-allowed; } .fileInfoInline { display: flex; align-items: center; gap: 0.5rem; min-width: 0; flex: 1; } .fileInfoContent { display: flex; min-width: 0; flex-direction: column; gap: 1px; } .fileInfoName { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; font-weight: 500; font-size: 0.875rem; line-height: 1.125rem; color: var(--text-primary); } .fileInfoMeta { color: var(--text-primary-muted); font-size: 0.75rem; line-height: 0.875rem; } .fileInfoExpiry { color: var(--text-primary-muted); } .fileInfoNavigation { display: flex; align-items: center; gap: 0.25rem; margin-left: auto; flex-shrink: 0; } .fileInfoNavigationText { font-size: 0.75rem; line-height: 1rem; color: var(--text-primary-muted); padding: 0 0.25rem; } .controlsBox { display: flex; align-items: center; gap: 0.5rem; pointer-events: auto; flex-shrink: 0; } .controlsDivider { margin-left: 0.25rem; margin-right: 0.25rem; height: 1.25rem; width: 1px; background-color: var(--background-modifier-accent); } .modalOverlay { position: fixed; inset: 0; z-index: var(--z-index-modal); display: flex; align-items: center; justify-content: center; pointer-events: auto; } .modalBackdrop { position: absolute; inset: 0; background-color: rgb(0 0 0 / 0.6); backdrop-filter: blur(4px); pointer-events: auto; } @media (max-width: 768px) { .modalBackdrop { background-color: rgb(0 0 0 / 0.85); backdrop-filter: blur(8px); } } .modalContent { position: absolute; inset: 0; display: flex; flex-direction: column; align-items: center; justify-content: center; pointer-events: none; } .modalContentInner { --media-content-inner-gap: 0.75rem; --media-content-inner-padding: var(--media-content-padding, 1rem); position: relative; display: flex; flex-direction: column; align-items: center; justify-content: center; width: 100%; height: 100%; pointer-events: none; gap: var(--media-content-inner-gap); padding: var(--media-content-inner-padding); box-sizing: border-box; } @media (max-width: 768px) { .modalContentInner { --media-content-inner-gap: 0; --media-content-inner-padding: 0; } } .modalContentInnerZoomed { padding: 0; max-width: 100%; max-height: 100%; width: 100%; height: 100%; } .headerBar { position: absolute; top: var(--media-content-padding, 1rem); left: var(--media-content-padding, 1rem); right: var(--media-content-padding, 1rem); display: flex; align-items: stretch; justify-content: space-between; gap: 0.5rem; z-index: 100; pointer-events: none; min-height: 48px; } :global(html.platform-native) .headerBar { top: calc(var(--media-content-padding, 1rem) + var(--native-titlebar-height)); } @media (max-width: 768px) { .headerBar { top: 0.5rem; left: 0.5rem; right: 0.5rem; min-height: 40px; } } .headerMeta { display: flex; align-items: center; gap: 0.375rem; padding: 0.25rem 0.5rem; border-radius: var(--radius-lg); background-color: var(--background-textarea); border: 1px solid var(--background-modifier-accent); box-shadow: 0 2px 8px rgb(0 0 0 / 0.15); pointer-events: auto; min-width: 0; max-width: calc(100% - 180px); height: 100%; box-sizing: border-box; } @media (max-width: 768px) { .headerMeta { display: none; } } .headerControls { display: flex; align-items: stretch; gap: 0.75rem; margin-left: auto; flex-shrink: 0; pointer-events: none; height: 100%; } @media (max-width: 768px) { .headerControls { width: 100%; margin-left: 0; } } .mobileTopBarControls { display: flex; align-items: center; justify-content: space-between; width: 100%; pointer-events: none; } .mobileTopBarControls .controlButton { pointer-events: auto; background: transparent; color: white; } .mobileTopBarControls .controlButton:hover { color: white; } .actionControlsBox { display: flex; align-items: center; gap: 0.125rem; padding: 0.25rem 0.375rem; border-radius: var(--radius-lg); background-color: var(--background-textarea); border: 1px solid var(--background-modifier-accent); box-shadow: 0 2px 8px rgb(0 0 0 / 0.15); pointer-events: auto; height: 100%; box-sizing: border-box; } .closeControlBox { display: flex; align-items: center; padding: 0.25rem; border-radius: var(--radius-lg); background-color: var(--background-textarea); border: 1px solid var(--background-modifier-accent); box-shadow: 0 2px 8px rgb(0 0 0 / 0.15); pointer-events: auto; height: 100%; box-sizing: border-box; aspect-ratio: 1 / 1; } .mediaArea { position: relative; flex: 1; display: flex; align-items: center; justify-content: center; padding-top: calc(var(--media-top-overlay-height, 48px) + var(--media-overlay-gap, 8px)); padding-bottom: calc(var(--media-bottom-overlay-height, 48px) + var(--media-overlay-gap, 8px)); padding-left: var(--media-side-overlay-width, 0px); padding-right: var(--media-side-overlay-width, 0px); width: 100%; height: 100%; box-sizing: border-box; pointer-events: none; min-width: 0; min-height: 0; } .mediaArea > * { pointer-events: auto; } @media (max-width: 768px) { .mediaArea { padding: 0; } } .mediaAreaZoomed { padding: 0; } .desktopViewerContainer { display: flex; height: 100%; width: 100%; align-items: center; justify-content: center; overflow: hidden; border: 0; background-color: transparent; } .desktopViewerContent { display: flex; align-items: center; justify-content: center; width: 100%; height: 100%; max-width: 100%; max-height: 100%; min-width: 0; min-height: 0; will-change: transform; pointer-events: none; } .mobileViewerContainer { display: flex; height: 100%; width: 100%; align-items: center; justify-content: center; overflow: hidden; } .nonZoomMediaContainer { position: relative; display: flex; height: 100%; width: 100%; align-items: center; justify-content: center; } .nonZoomBackdrop { position: absolute; inset: 0; cursor: pointer; } .nonZoomContent { pointer-events: none; position: relative; z-index: 10; display: flex; height: 100%; width: 100%; align-items: center; justify-content: center; padding: 0; box-sizing: border-box; } @media (max-width: 768px) { .nonZoomContent { padding: 0; } } .nonZoomContentInner { pointer-events: auto; width: fit-content; height: fit-content; max-width: 100%; max-height: 100%; display: inline-flex; align-items: center; justify-content: center; } .navigationOverlay { position: absolute; bottom: 1rem; left: 50%; transform: translateX(-50%); display: flex; align-items: center; gap: 0.5rem; border-radius: 9999px; background-color: rgb(0 0 0 / 0.6); padding: 0.5rem 1rem; backdrop-filter: blur(4px); pointer-events: auto; } .navigationText { font-weight: 500; font-size: 0.875rem; line-height: 1.25rem; color: white; } .thumbnailCarouselWrapper { position: absolute; bottom: calc(var(--media-content-padding, 1rem) * 0.65); left: 50%; transform: translateX(-50%); padding: 0.35rem 0.4rem; pointer-events: auto; max-width: min(760px, 90vw); width: auto; overflow: hidden; background-clip: padding-box; display: inline-flex; align-items: center; justify-content: center; } .thumbnailCarouselScroller { max-width: 100%; } .thumbnailCarousel { display: flex; width: auto; min-width: max-content; gap: 1px; padding: 0.125rem; margin: 0; border-radius: 0.5rem; background-color: transparent; } .thumbnailButton { border: none; padding: 0; background: transparent; cursor: pointer; border-radius: 0; flex: 0 0 auto; } .thumbnailImageWrapper { position: relative; width: 44px; height: 44px; border-radius: 0; overflow: hidden; background-color: var(--background-secondary); filter: grayscale(0.25) brightness(0.7); opacity: 0.55; transition: opacity 150ms ease, filter 150ms ease; } .thumbnailImageWrapperFirst { border-top-left-radius: 0.375rem; border-bottom-left-radius: 0.375rem; } .thumbnailImageWrapperLast { border-top-right-radius: 0.375rem; border-bottom-right-radius: 0.375rem; } .thumbnailButtonSelected .thumbnailImageWrapper { opacity: 1; filter: none; } .thumbnailImage { width: 100%; height: 100%; object-fit: cover; display: block; } .thumbnailVideo { width: 100%; height: 100%; object-fit: cover; display: block; background-color: var(--background-secondary); } .thumbnailPlaceholder { width: 100%; height: 100%; display: flex; align-items: center; justify-content: center; background: linear-gradient(135deg, rgb(255 255 255 / 0.06), rgb(255 255 255 / 0.02)); color: var(--text-primary-muted); font-weight: 600; font-size: 0.75rem; text-transform: uppercase; letter-spacing: 0.02em; } .floatingNavButtonLeft, .floatingNavButtonRight { position: absolute; top: 50%; transform: translateY(-50%); z-index: 100; pointer-events: auto; } .floatingNavButtonLeft { left: 12px; } .floatingNavButtonRight { right: 12px; } .floatingNavButton { display: flex; align-items: center; justify-content: center; width: 48px; height: 48px; border-radius: 9999px; background-color: var(--background-textarea); border: 1px solid var(--background-modifier-accent); box-shadow: 0 2px 8px rgb(0 0 0 / 0.15); color: var(--text-secondary); cursor: pointer; transition: background-color 150ms ease, color 150ms ease, transform 150ms ease, opacity 150ms ease; } .floatingNavButton:hover { background-color: var(--background-secondary-alt); color: var(--text-primary); } .floatingNavButton:active { transform: scale(0.95); } .floatingNavButtonDisabled { opacity: 0.4; cursor: not-allowed; } .floatingNavButtonDisabled:hover { background-color: var(--background-textarea); color: var(--text-secondary); } .floatingNavButtonDisabled:active { transform: none; } .klipyAttribution { position: absolute; bottom: var(--media-content-padding, 1rem); right: var(--media-content-padding, 1rem); z-index: 50; display: flex; align-items: center; padding: 0.5rem 0.75rem; border-radius: var(--radius-lg); background-color: var(--background-textarea); border: 1px solid var(--background-modifier-accent); box-shadow: 0 2px 8px rgb(0 0 0 / 0.15); pointer-events: none; } .klipyAttribution svg { height: 16px; width: auto; color: var(--text-primary-muted); }