Pass correct mimetype to Firefox

When we switched to supporting .png skins, we forced Firefox to fallback to a sub-optimal image parsing strategy.
This commit is contained in:
Jordan Eldredge 2018-04-12 06:26:43 -07:00
parent d700100626
commit a180b96801
3 changed files with 40 additions and 13 deletions

View file

@ -6,6 +6,7 @@ import {
DEFAULT_VIS_COLORS,
DEFAULT_PLAYLIST_STYLE
} from "./constants";
import { parseViscolors, parseIni, getFileExtension } from "./utils";
const shallowMerge = objs =>
objs.reduce((prev, img) => Object.assign(prev, img), {});
@ -89,7 +90,10 @@ async function genFileFromZip(zip, fileName, ext, mode) {
return null;
}
// Return a promise (awaitable).
return files[0].async(mode);
return {
contents: await files[0].async(mode),
name: files[0].name
};
}
function getSpriteUrisFromImg(img, sprites) {
@ -110,14 +114,16 @@ async function genImgFromFilename(zip, fileName) {
// Winamp only supports .bmp images, but WACUP set a precidence of supporting
// .png as well to reduce size. Since we care about size as well, we follow
// suit. Our default skin uses .png to save 14kb.
const blob = await genFileFromZip(zip, fileName, "(png|bmp)", "blob");
if (!blob) {
const file = await genFileFromZip(zip, fileName, "(png|bmp)", "blob");
if (!file) {
return null;
}
const mimeType = `image/${getFileExtension(file.name) || "*"}`;
// The spec for createImageBitmap() says the browser should try to sniff the
// mime type, but it looks like Firefox does not. So we specify it here
// explicitly.
const typedBlob = new Blob([blob], { type: "image/*" });
const typedBlob = new Blob([file.contents], { type: mimeType });
return genImgFromBlob(typedBlob);
}
@ -130,13 +136,13 @@ async function genSpriteUrisFromFilename(zip, fileName) {
}
async function getCursorFromFilename(zip, fileName) {
const base64 = await genFileFromZip(zip, fileName, "CUR", "base64");
return base64 && `data:image/x-win-bitmap;base64,${base64}`;
const file = await genFileFromZip(zip, fileName, "CUR", "base64");
return file && `data:image/x-win-bitmap;base64,${file.contents}`;
}
async function genPlaylistStyle(zip) {
const pleditContent = await genFileFromZip(zip, "PLEDIT", "txt", "text");
const data = pleditContent && parseIni(pleditContent).text;
const pledit = await genFileFromZip(zip, "PLEDIT", "txt", "text");
const data = pledit && parseIni(pledit.contents).text;
if (!data) {
// Corrupt or missing PLEDIT.txt file.
return DEFAULT_PLAYLIST_STYLE;
@ -159,8 +165,8 @@ async function genPlaylistStyle(zip) {
}
async function genColors(zip) {
const viscolorContent = await genFileFromZip(zip, "VISCOLOR", "txt", "text");
return viscolorContent ? parseViscolors(viscolorContent) : DEFAULT_VIS_COLORS;
const viscolor = await genFileFromZip(zip, "VISCOLOR", "txt", "text");
return viscolor ? parseViscolors(viscolor.contents) : DEFAULT_VIS_COLORS;
}
async function genImages(zip) {
@ -182,8 +188,8 @@ async function genCursors(zip) {
}
async function genRegion(zip) {
const regionContent = await genFileFromZip(zip, "REGION", "txt", "text");
return regionContent ? regionParser(regionContent) : {};
const region = await genFileFromZip(zip, "REGION", "txt", "text");
return region ? regionParser(region.contents) : {};
}
async function genGenTextSprites(zip) {

View file

@ -58,6 +58,11 @@ export const getTimeStr = (time, truncate = true) => {
].join("");
};
export const getFileExtension = fileName => {
const matches = /\.([a-z]{3,4})$/i.exec(fileName);
return matches ? matches[1].toLowerCase() : null;
};
export const parseViscolors = text => {
const entries = text.split("\n");
const regex = /^(\d+)\s*,\s*(\d+)\s*,\s*(\d+)/;

View file

@ -10,7 +10,8 @@ import {
denormalize,
segment,
moveSelected,
spliceIn
spliceIn,
getFileExtension
} from "./utils";
const fixture = filename =>
@ -47,6 +48,21 @@ describe("getTimeStr", () => {
});
});
describe("getFileExtension", () => {
it("can get bmp", () => {
expect(getFileExtension("foo.bmp")).toBe("bmp");
});
it("can match four char extension", () => {
expect(getFileExtension("foo.html")).toBe("html");
});
it("converts to lower case", () => {
expect(getFileExtension("foo.BMP")).toBe("bmp");
});
it("returns null if a match is not found", () => {
expect(getFileExtension("foo")).toBe(null);
});
});
describe("clamp", () => {
it("respects the max value", () => {
const actual = clamp(101, 0, 100);