我正在考虑从浏览器实现
Image
类,目前正在实现 ICO 支持。然而,我一直在寻找算法来决定从 ICO 文件中加载哪个图像。
这是我在浏览器中使用的代码:
const img = new Image()
img.src = 'test.ico'
img.onload = () => {
console.log(img.width, img.height)
document.body.append(img)
}
在测试一些不同的图像时,我进行了以下观察:
一个猜测是,它会获取第一张具有最大尺寸的图像(例如,首先找到最大尺寸,然后选择与该尺寸匹配的第一张图像)。
是否有任何标准文件来管理如何做到这一点?或者任何其他可遵循的文档来源?
根据Chrome和Firefox的源代码,图像首先根据大小进行优先级排序,其次根据位深度进行排序。
火狐:
if (!biggestEntry ||
(e.mBitCount >= biggestEntry->mBitCount &&
e.mSize.width * e.mSize.height >=
biggestEntry->mSize.width * biggestEntry->mSize.height)) {
biggestEntry = &e;
if (!desiredSize) {
mDirEntry = &e;
}
}
铬:
bool ICOImageDecoder::CompareEntries(const IconDirectoryEntry& a,
const IconDirectoryEntry& b) {
// Larger icons are better. After that, higher bit-depth icons are better.
const int a_entry_area = a.size_.width() * a.size_.height();
const int b_entry_area = b.size_.width() * b.size_.height();
return (a_entry_area == b_entry_area) ? (a.bit_count_ > b.bit_count_)
: (a_entry_area > b_entry_area);
}
// ...
// Arrange frames in decreasing quality order.
std::sort(dir_entries_.begin(), dir_entries_.end(), CompareEntries);
请注意,在图像大小和位深度相同的情况下,行为略有不同。 Firefox 将始终选择最后一个图像,而 Chrome 使用
std::sort
,这不保证相等元素的顺序。