UNPKG

@loaders.gl/core

Version:

Framework-independent loaders for 3D graphics formats

124 lines (101 loc) 2.92 kB
import { getRegisteredLoaders } from './register-loaders'; import { normalizeLoader } from './loader-utils/normalize-loader'; const EXT_PATTERN = /[^.]+$/; export function selectLoader(loaders, url = '', data = null, { nothrow = false } = {}) { url = url || ''; if (loaders && !Array.isArray(loaders)) { const loader = loaders; normalizeLoader(loader); return loader; } loaders = loaders || getRegisteredLoaders(); normalizeLoaders(loaders); url = url.replace(/\?.*/, ''); let loader = null; loader = loader || findLoaderByUrl(loaders, url); loader = loader || findLoaderByExamingInitialData(loaders, data); if (!loader) { if (nothrow) { return null; } throw new Error("No valid loader found for ".concat(url)); } return loader; } function normalizeLoaders(loaders) { for (const loader of loaders) { normalizeLoader(loader); } } function findLoaderByUrl(loaders, url) { const match = url.match(EXT_PATTERN); const extension = match && match[0]; const loader = extension && findLoaderByExtension(loaders, extension); return loader; } function findLoaderByExtension(loaders, extension) { extension = extension.toLowerCase(); for (const loader of loaders) { for (const loaderExtension of loader.extensions) { if (loaderExtension.toLowerCase() === extension) { return loader; } } } return null; } function findLoaderByExamingInitialData(loaders, data) { if (!data) { return null; } for (const loader of loaders) { if (typeof data === 'string') { if (testText(data, loader)) { return loader; } } else if (ArrayBuffer.isView(data)) { if (testBinary(data.buffer, data.byteOffset, loader)) { return loader; } } else if (data instanceof ArrayBuffer) { const byteOffset = 0; if (testBinary(data, byteOffset, loader)) { return loader; } } } return null; } function testText(data, loader) { return loader.testText && loader.testText(data); } function testBinary(data, byteOffset, loader) { const type = Array.isArray(loader.test) ? 'array' : typeof loader.test; switch (type) { case 'function': return loader.test(data, loader); case 'string': case 'array': const tests = Array.isArray(loader.test) ? loader.test : [loader.test]; return tests.some(test => { const magic = getMagicString(data, byteOffset, test.length); return test === magic; }); default: return false; } } function getMagicString(arrayBuffer, byteOffset, length) { if (arrayBuffer.byteLength <= byteOffset + length) { return ''; } const dataView = new DataView(arrayBuffer); let magic = ''; for (let i = 0; i < length; i++) { magic += String.fromCharCode(dataView.getUint8(byteOffset + i)); } return magic; } //# sourceMappingURL=select-loader.js.map