import { TextureLoader } from "three" ; import { AssetType } from "./AssetTypes" ; const REGEXP_EXT = /(?:\.([^.]+))?$/ ; export interface ThreeLoaderConstructor { new ( ) : ThreeLoaderInterface ; } export interface ThreeLoaderInterface { load ( name , success ? , progress ? , failure ? ) : void ; } export class Loader { private static _extensions = new Map < string , ThreeLoaderConstructor > ( ) ; public static registerExtension ( extension , loader ) { this . _extensions . set ( extension , loader ) ; } public static unregisterExtension ( extension ) { this . _extensions . delete ( extension ) ; } public getFileExtension ( file ) { return REGEXP_EXT . exec ( file ) ! [ 1 ] ; } public promisifyLoader < T > ( loaderCtor , errorTransformer ? ) { return ( src , name ) => { return new Promise < T > ( ( resolve , reject ) => { if ( ! loaderCtor ) { return reject ( new Error ( `Loader for "${ name }" is undefined` ) ) ; } const loader = new loaderCtor ( ) ; loader . load ( src , resolve , undefined , ( e ) => { const err = errorTransformer ? errorTransformer ( e , name ) : e . error ; console . error ( err ) ; reject ( err ) ; } ) ; } ) ; } ; } public load ( src , name ) { const ext = this . getFileExtension ( src ) ; const loaderClass = Loader . _extensions . get ( ext ) ; if ( ! loaderClass ) { throw new Error ( `Asset "${ name }" could not be loaded: extension ${ ext } is not registered` ) ; } return new Promise ( ( resolve , reject ) => { const loader = new loaderClass ( ) ; loader . load ( src , resolve , undefined , ( e ) => { const err = new Error ( `Asset "${ name }" could not be loaded: ${ e . message }` ) ; reject ( err ) ; } ) ; } ) ; } public texture = this . promisifyLoader < THREE . Texture > ( TextureLoader , ( e , name ) => { return new Error ( `Model "${ name }" could not be loaded: ${ e . message }` ) ; } ) ; }