Load movies in iframe for new item page preview

Hey hey, it's working! Still stuff to add like pause/play, but yeah!
This commit is contained in:
Emi Matchu 2024-07-03 20:15:35 -07:00
parent 5b2062754d
commit 97e6c39402
4 changed files with 64 additions and 22 deletions

View file

@ -7,19 +7,47 @@ class OutfitLayer extends HTMLElement {
} }
connectedCallback() { connectedCallback() {
setTimeout(() => this.#initializeImage(), 0); setTimeout(() => this.#connectToChildren(), 0);
} }
#initializeImage() { disconnectedCallback() {
this.image = this.querySelector("img"); window.removeEventListener("message", this.#onMessage);
if (!this.image) {
throw new Error(`<outfit-layer> must contain an <img> tag`);
} }
this.image.addEventListener("load", () => this.#setStatus("loaded")); #connectToChildren() {
this.image.addEventListener("error", () => this.#setStatus("error")); const image = this.querySelector("img");
const iframe = this.querySelector("iframe");
this.#setStatus(this.image.complete ? "loaded" : "loading"); if (image) {
image.addEventListener("load", () => this.#setStatus("loaded"));
image.addEventListener("error", () => this.#setStatus("error"));
this.#setStatus(image.complete ? "loaded" : "loading");
} else if (iframe) {
this.iframe = iframe;
window.addEventListener("message", (m) => this.#onMessage(m));
this.#setStatus("loading");
} else {
throw new Error(
`<outfit-layer> must contain an <img> or <iframe> tag`,
);
}
}
#onMessage({ source, data }) {
if (source !== this.iframe.contentWindow) {
return;
}
if (
data.type === "status" &&
["loaded", "error"].includes(data.status)
) {
this.#setStatus(data.status);
} else {
throw new Error(
`<outfit-layer> got unexpected message: ${JSON.stringify(data)}`,
);
}
} }
#setStatus(newStatus) { #setStatus(newStatus) {

View file

@ -301,12 +301,21 @@ window.addEventListener("message", ({ data }) => {
} }
}); });
startMovie().catch((error) => { startMovie()
.then(() => {
parent.postMessage(
{ type: "status", status: "loaded" },
document.location.origin,
);
})
.catch((error) => {
console.error(logPrefix, error); console.error(logPrefix, error);
loadingStatus = "error"; loadingStatus = "error";
canvas.setAttribute("data-status", "error"); parent.postMessage(
canvas.setAttribute("data-error-message", error.message); { type: "status", status: "error" },
document.location.origin,
);
// If loading the movie fails, show the fallback image instead, by moving // If loading the movie fails, show the fallback image instead, by moving
// it out of the canvas content and into the body. // it out of the canvas content and into the body.

View file

@ -54,13 +54,16 @@ body.items-show
position: absolute position: absolute
inset: 0 inset: 0
img img, iframe
width: 100% width: 100%
height: 100% height: 100%
&:has(outfit-layer:state(loading)) &:has(outfit-layer:state(loading))
background: gray background: gray
&:has(outfit-layer:state(error))
border-color: $error-border-color
.species-color-picker .species-color-picker
.error-icon .error-icon
cursor: help cursor: help
@ -70,4 +73,3 @@ body.items-show
select select
border-color: $error-border-color border-color: $error-border-color
color: $error-color color: $error-color

View file

@ -6,4 +6,7 @@
"zone": swf_asset.zone.label, "zone": swf_asset.zone.label,
}, },
} }
- if swf_asset.canvas_movie?
%iframe{src: swf_asset_path(swf_asset) + "?playing"}
- else
= image_tag swf_asset.image_url, alt: "" = image_tag swf_asset.image_url, alt: ""