VulpesOS/assets/webapps/search.gaiamobile.org/js/providers/places.js
OverSu b38dea0597 Publish Vulpes Preview 15 sources for desktop, Android and Tundra
Share Gaia assets and adapters, keep private profiles and development documents local, and update both public READMEs.
2026-09-30 23:13:03 +02:00

33 lines
No EOL
7.2 KiB
JavaScript

;;(function(exports){'use strict';var _=navigator.mozL10n.get;var MAX_AWESOME_RESULTS=4;var MAX_HISTORY_RESULTS=20;var MAX_TOPSITES_RESULTS=6;var STORE_NAME='places';var topSitesWrapper=document.getElementById('top-sites');var historyWrapper=document.getElementById('history');if(topSitesWrapper&&historyWrapper){topSitesWrapper.addEventListener('click',itemClicked);historyWrapper.addEventListener('click',itemClicked);}
var cachedLink=document.createElement('a');function parseUrl(url){cachedLink.href=url;return cachedLink;}
var icons={};var iconUrls={};function getIcon(place){if(place.url in icons&&icons[place.url]){return icons[place.url];}
IconsHelper.getIcon(place.url,null,place).then(icon=>{saveIcon(place.url,icon);});return false;}
function saveIcon(key,url){if(key in icons){return;}
icons[key]=null;iconUrls[key]=url;fetchIcon(url,function(err,icon){if(!err){icons[key]=icon;}});}
function fetchIcon(uri,callback){var xhr=new XMLHttpRequest({mozSystem:true});xhr.open('GET',uri,true);xhr.responseType='blob';xhr.addEventListener('load',function(){if(!(xhr.status===200||xhr.status===0)){return callback(new Error('error_downloading'));}
var blob=xhr.response;if(blob.size>this.MAX_ICON_SIZE){return callback(new Error('image_to_large'));}
var img=document.createElement('img');img.src=window.URL.createObjectURL(blob);img.onload=function(){window.URL.revokeObjectURL(img.src);if(img.naturalWidth<=0){return callback(new Error('Cannot load image'));}
callback(null,blob);};img.onerror=function(){window.URL.revokeObjectURL(img.src);return callback(new Error('Cannot load image'));};});xhr.onerror=function(err){return callback(new Error('Cannot load uri'));};xhr.send();}
function itemClicked(e){if(e.target.dataset.url){Search.navigate(e.target.dataset.url);}}
var listTemplate=createList();function createList(){var list=document.createElement('ul');list.setAttribute('role','listbox');return list;}
function incrementHistoryThreshold(timestamp,currentThreshold,thresholds){var newThreshold=currentThreshold+=1;if(timestamp<thresholds[newThreshold]){return incrementHistoryThreshold(timestamp,newThreshold,thresholds);}
return newThreshold;}
function drawHistoryHeading(parent,threshold,timestamp){var LABELS=['future','today','yesterday','last-7-days','this-month','last-6-months','older-than-6-months'];var text='';if(threshold==5&&timestamp){var date=new Date(timestamp);var now=new Date();text=_('month-'+date.getMonth());if(date.getFullYear()!=now.getFullYear()){text+=' '+date.getFullYear();}}else{text=_(LABELS[threshold]);}
var h3=document.createElement('h3');var spanNode=document.createElement('span');spanNode.textContent=text;var ul=listTemplate.cloneNode(true);h3.appendChild(spanNode);parent.appendChild(h3);parent.appendChild(ul);}
function updateIcon(visit,iconWrapper){var iconDom=iconWrapper.querySelector('img');IconsHelper.getIcon(visit.url,null,visit).then((icon)=>{if(icon&&iconDom){iconDom.onload=function(){iconWrapper.classList.remove('empty');iconDom.style.display='block';};iconDom.src=icon;}});}
function buildHistory(visits){var thresholds=[Date.now(),DateHelper.todayStarted(),DateHelper.yesterdayStarted(),DateHelper.thisWeekStarted(),DateHelper.thisMonthStarted(),DateHelper.lastSixMonthsStarted(),0];var threshold=0;var month=null;var year=null;var fragment=document.createDocumentFragment();visits.forEach(function(visit){if(visit.date>0&&visit.date<thresholds[threshold]){threshold=incrementHistoryThreshold(visit.date,threshold,thresholds);if(threshold!=5){drawHistoryHeading(fragment,threshold);}}
if(threshold===5){var timestampDate=new Date(visit.date);if(timestampDate.getMonth()!=month||timestampDate.getFullYear()!=year){month=timestampDate.getMonth();year=timestampDate.getFullYear();drawHistoryHeading(fragment,threshold,visit.date);}}
visit.meta=visit.url;visit.dataset={url:visit.url};var dom=exports.Places.buildResultsDom([visit]);var iconDom=dom.querySelector('.icon');fragment.appendChild(dom);updateIcon(visit,iconDom);});return fragment;}
function showStartPage(){if(!topSitesWrapper||!historyWrapper){return;}
var store=exports.Places.persistStore;var urls=[];store.readVisits(MAX_HISTORY_RESULTS,function(results){var docFragment=buildHistory(results);historyWrapper.innerHTML='';historyWrapper.appendChild(docFragment);},function filter(visit){var isStored=visit.url in urls;urls[visit.url]=true;return!isStored;});store.read('frecency',MAX_TOPSITES_RESULTS,function(results){var docFragment=document.createDocumentFragment();results.forEach(function(x){docFragment.appendChild(formatTopResult(x));});topSitesWrapper.innerHTML='';topSitesWrapper.appendChild(docFragment);});}
function formatTopResult(result){var div=document.createElement('div');var span=document.createElement('span');if(result.title){span.setAttribute('dir','auto');span.textContent=result.title;}else{span.setAttribute('dir','ltr');span.textContent=result.url;}
div.dataset.url=result.url;div.classList.add('top-site');div.appendChild(span);div.setAttribute('role','link');if(result.screenshot||result.tile){var img=result.screenshot||result.tile;var imgUrl=(typeof img==='string')?img:URL.createObjectURL(img);div.style.backgroundImage='url('+imgUrl+')';}
return div;}
function matchesFilter(value,filter){return!filter||(value&&value.match(new RegExp(filter,'i'))!==null);}
function formatPlace(placeObj,filter){var result={'title':placeObj.title,'meta':placeObj.url,'icon':getIcon(placeObj),'dataset':{'url':placeObj.url},'label':placeObj.title};return result;}
function Places(){}
Places.prototype={__proto__:Provider.prototype,name:'Places',click:itemClicked,init:function(){if(!topSitesWrapper||!historyWrapper){this.header=document.getElementById(this.name.toLowerCase()+'-header');this.container=document.getElementById(this.name.toLowerCase());this.container.addEventListener('click',this.click.bind(this));}
this.persistStore=new PlacesIdbStore();this.persistStore.init().then(()=>{this.syncStore=new SyncDataStore(STORE_NAME,this.persistStore,'url');this.syncStore.filter=function(place){return place.url.startsWith('app://')||place.url==='about:blank';};this.syncStore.onChange=function(){showStartPage();};var rev=this.persistStore.latestRevision||0;return this.syncStore.sync(rev).then(()=>{return new Promise(resolve=>{function done(){showStartPage();resolve();}
asyncStorage.getItem('have-preloaded-sites',(havePreloaded)=>{if(!havePreloaded){this.preloadTopSites().then(()=>{asyncStorage.setItem('have-preloaded-sites',true);done();});}else{done();}});});});});},saveSites:function(sites){return Promise.all(sites.map(site=>{site.frecency=-2;return this.persistStore.addPlace(site);}));},preloadTopSites:function(){return LazyLoader.getJSON('/js/inittopsites.json').then(sites=>{return this.saveSites(sites);});},search:function(filter){return new Promise((resolve,reject)=>{var matchedOrigins={};this.persistStore.read('frecency',MAX_AWESOME_RESULTS,(results)=>{resolve(results.map(function(result){return formatPlace(result,filter);}));},function filterFun(result){if(result.frecency<=0){return false;}
var url=parseUrl(result.url);var matches=!(url.hostname in matchedOrigins)&&(matchesFilter(result.title,filter)||matchesFilter(result.url,filter));if(matches){matchedOrigins[url.hostname]=true;}
return matches;});});}};exports.Places=new Places();Search.provider(exports.Places);}(window));