App-MHFS
view release on metacpan or search on metacpan
share/public_html/static/music_worklet_inprogress/player/mhfsplayer.js view on Meta::CPAN
if(! that.ByHash[pichash]) {
that.ByHash[pichash] = [];
}
else {
for(const elm of that.ByHash[pichash]) {
if((elm.size === picture.picsize) && (elm.mime === picture.mime)) {
return elm.url;
}
}
}
const picurl = picture.toURL();
console.log('loaded picture at ' + picurl);
that.ByHash[pichash].push({
size : picture.picsize,
mime : picture.mime,
url : picurl
});
return picurl;
};
return that;
};
const FolderMap = function() {
const that = {};
that.ByFolder = {};
const LookupFolder = function(trackname) {
const lastSlash = trackname.lastIndexOf('/');
return (lastSlash !== -1) ? trackname.substring(0, lastSlash) : '';
};
that.AddArtIfNotExists = function(trackname, url) {
const foldername = LookupFolder(trackname);
if(!foldername || that.ByFolder[foldername]) return;
that.ByFolder[foldername] = url;
};
that.GetArt = function(trackname) {
const foldername = LookupFolder(trackname);
if(! foldername) return undefined;
return that.ByFolder[foldername];
};
return that;
};
const MHFSPlayer = async function(opt) {
let that = {};
that.gui = opt.gui;
that.artDB = ArtDB();
that.trackdb = {};
that.guiarturl = {};
that.foldermap = FolderMap();
const cdimage = new Blob ([CDIMAGE], { type: 'image/svg+xml' });
that.cdimage = URL.createObjectURL(cdimage);
const SetTrackArt = function(track, url) {
// update the foldermap so we can guess the art for other tracks in the folder / album
that.foldermap.AddArtIfNotExists(track.md.trackname, url);
// set this as definite art for trackname
track.md.artbloburl = url;
// gui needs to reload track art urls
that.gui.UpdateTrackImage(track);
};
const LoadTrackArt = function(track, dectrack) {
if(! track.md.artbloburl) {
let urlToSet;
// first try loading the art directly from the file
const embeddedart = dectrack._openPictureIfExists();
if(embeddedart) {
urlToSet = that.artDB.addPictureIfNotExists(embeddedart);
}
else {
// try using the gui's art locater. We cache it all as blobs to avoid lookups
const url = that.gui.getarturl(track.md.trackname);
if(!that.guiarturl[url]) {
(async function() {
const fetchResponse = await fetch(url);
if(!fetchResponse.ok) return;
const blobert = await fetchResponse.blob();
that.guiarturl[url] = URL.createObjectURL(blobert);
SetTrackArt(track, that.guiarturl[url]);
})();
return;
}
urlToSet = that.guiarturl[url];
}
SetTrackArt(track, urlToSet);
}
};
that.sampleRate = opt.sampleRate;
that.channels = opt.channels;
that.pborder = "pborder_default";
that.maxdecodetime = opt.maxdecodetime;
that._createaudiocontext = function(options) {
let mycontext = (window.hasWebKit) ? new webkitAudioContext(options) : (typeof AudioContext != "undefined") ? new AudioContext(options) : null;
return mycontext;
};
// create AC
that.ac = that._createaudiocontext({'sampleRate' : opt.sampleRate, 'latencyHint' : 0.1});
that.ac.suspend(); // save power start suspended
that.lastACState = that.ac.state;
that.ac.onstatechange = function() {
console.log('changing acstate was ' + that.lastACState + ' now ' + that.ac.state);
that.lastACState = that.ac.state;
that.gui.onACStateUpdate(that.lastACState);
};
// connect GainNode
that.GainNode = that.ac.createGain();
that.GainNode.connect(that.ac.destination);
// create ring buffers
that.ARBLen = that.ac.sampleRate * 2;
if (!self.SharedArrayBuffer) {
( run in 1.068 second using v1.01-cache-2.11-cpan-5837b0d9d2c )