Auto hide

Needs the new CSS, but it'll work when that is enabled
This commit is contained in:
Manav Rathi
2025-02-11 17:17:46 +05:30
parent 78334d2e22
commit b4e01d5ab5
2 changed files with 69 additions and 3 deletions

View File

@@ -56,6 +56,7 @@ import { resumeExportsIfNeeded } from "services/export";
import { photosLogout } from "services/logout";
import "photoswipe/dist/photoswipe.css";
// TODO(PS): Note, auto hide only works with the new CSS.
// import "../../../../packages/new/photos/components/ps5/dist/photoswipe.css";
import "styles/global.css";

View File

@@ -126,6 +126,19 @@ export class FileViewerPhotoSwipe {
* start with the thumbnail but then also update this with the original etc.
*/
private itemDataByFileID: Map<number, SlideData> = new Map();
/**
* An interval that invokes a periodic check of whether we should the hide
* controls if the user does not perform any pointer events for a while.
*/
private autoHideCheckIntervalId: ReturnType<typeof setTimeout> | undefined;
/**
* The time the last activity occurred. Used in tandem with
* {@link autoHideCheckIntervalId} to implement the auto hiding of controls
* when the user stops moving the pointer for a while.
*
* This will be "hidden" if controls have already been hidden.
*/
private lastActivityDate: Date | "hidden";
constructor({
files,
@@ -170,11 +183,14 @@ export class FileViewerPhotoSwipe {
// TODO(PS): will we need this?
mainClass: "our-extra-pswp-main-class",
});
// Provide data about slides to PhotoSwipe via callbacks
// https://photoswipe.com/data-sources/#dynamically-generated-data
pswp.addFilter("numItems", () => {
return this.files.length;
});
pswp.addFilter("itemData", (_, index) => {
const file = files[index];
@@ -203,8 +219,19 @@ export class FileViewerPhotoSwipe {
log.debug(() => ["[ps]", { itemData, index, file, itemData }]);
if (!file) assertionFailed();
this.lastActivityDate = new Date();
return itemData ?? {};
});
pswp.addFilter("preventPointerEvent", (originalResult) => {
// There was a pointer event. We don't care which one, we just use
// this as a hook to show UI again (if needed) and update our last
// activity date.
this.onPointerActivity();
return originalResult;
});
pswp.on("contentLoad", (e) => {
console.log("contentLoad", e);
if (e.content.data.videoURL) {
@@ -226,16 +253,25 @@ export class FileViewerPhotoSwipe {
"position: absolute; left: 0; right: 0; width: 100%; height: 100%; z-index: 1; pointer-events: none;";
}
});
pswp.on("close", () => {
// The user did some action within the file viewer to close it. Let
// our parent know that we have been closed.
// The user did some action within the file viewer to close it.
//
// Clear intervals.
clearIntervals();
// Let our parent know that we have been closed.
onClose();
});
// Initializing PhotoSwipe adds it to the DOM as a dialog-like div with
// the class "pswp".
pswp.init();
this.pswp = pswp;
this.autoHideCheckIntervalId = setInterval(() => {
this.autoHideIfInactive();
}, 1000);
}
/**
@@ -254,13 +290,42 @@ export class FileViewerPhotoSwipe {
// closed internally (e.g. the user activated the close button within
// the file viewer), then PhotoSwipe will ignore this extra close.
this.pswp.close();
this.clearAutoHideIntervalIfNeeded();
}
updateFiles(files: EnteFile[]) {
// TODO(PS)
}
async enqueueUpdates(index: number, file: EnteFile) {
private clearAutoHideIntervalIfNeeded() {
if (this.autoHideCheckIntervalId) {
clearInterval(this.autoHideCheckIntervalId);
this.autoHideCheckIntervalId = undefined;
}
}
private onPointerActivity() {
if (this.lastActivityDate == "hidden") this.showUIControls();
this.lastActivityDate = new Date();
}
private autoHideIfInactive() {
if (this.lastActivityDate == "hidden") return;
if (Date.now() - this.lastActivityDate.getTime() > 3000) {
this.hideUIControls();
this.lastActivityDate = "hidden";
}
}
private showUIControls() {
this.pswp.element.classList.add("pswp--ui-visible");
}
private hideUIControls() {
this.pswp.element.classList.remove("pswp--ui-visible");
}
private async enqueueUpdates(index: number, file: EnteFile) {
const update = (itemData: SlideData) => {
this.itemDataByFileID.set(file.id, itemData);
this.pswp.refreshSlideContent(index);