1
0
Fork 0
mirror of https://github.com/jellyfin/jellyfin-web synced 2025-03-30 19:56:21 +00:00

update lazy loader

This commit is contained in:
Luke Pulverenti 2016-11-16 01:00:28 -05:00
parent 0291450ffb
commit 71b0be28b8
8 changed files with 226 additions and 126 deletions

View file

@ -0,0 +1,87 @@
define(['visibleinviewport', 'browser', 'dom'], function (visibleinviewport, browser, dom) {
'use strict';
function LazyLoader(options) {
this.options = options;
}
LazyLoader.prototype.createObserver = function () {
var observerOptions = {};
var options = this.options;
var loadedCount = 0;
var callback = options.callback;
//options.rootMargin = "300%";
var self = this;
var observer = new IntersectionObserver(function (entries) {
for (var j = 0, length2 = entries.length; j < length2; j++) {
var entry = entries[j];
var target = entry.target;
observer.unobserve(target);
callback(target);
loadedCount++;
if (loadedCount >= self.elementCount) {
self.destroyObserver();
}
}
},
observerOptions
);
this.observer = observer;
};
LazyLoader.prototype.addElements = function (elements) {
var observer = this.observer;
if (!observer) {
this.createObserver();
observer = this.observer;
}
this.elementCount = (this.elementCount || 0) + elements.length;
for (var i = 0, length = elements.length; i < length; i++) {
observer.observe(elements[i]);
}
};
LazyLoader.prototype.destroyObserver = function (elements) {
var observer = this.observer;
if (observer) {
observer.disconnect();
this.observer = null;
}
};
LazyLoader.prototype.destroy = function (elements) {
this.destroyObserver();
this.options = null;
};
function unveilElements(elements, root, callback) {
if (!elements.length) {
return;
}
var lazyLoader = new LazyLoader({
callback: callback
});
lazyLoader.addElements(elements);
}
LazyLoader.lazyChildren = function (elem, callback) {
unveilElements(elem.getElementsByClassName('lazy'), elem, callback);
}
return LazyLoader;
});

View file

@ -8,16 +8,6 @@ define(['visibleinviewport', 'browser', 'dom'], function (visibleinviewport, bro
fn(); fn();
}; };
var supportsIntersectionObserver = function () {
if (window.IntersectionObserver) {
return true;
}
return false;
}();
function resetThresholds() { function resetThresholds() {
var x = screen.availWidth; var x = screen.availWidth;
@ -32,11 +22,9 @@ define(['visibleinviewport', 'browser', 'dom'], function (visibleinviewport, bro
thresholdY = y; thresholdY = y;
} }
if (!supportsIntersectionObserver) {
dom.addEventListener(window, "orientationchange", resetThresholds, { passive: true }); dom.addEventListener(window, "orientationchange", resetThresholds, { passive: true });
dom.addEventListener(window, 'resize', resetThresholds, { passive: true }); dom.addEventListener(window, 'resize', resetThresholds, { passive: true });
resetThresholds(); resetThresholds();
}
function isVisible(elem) { function isVisible(elem) {
return visibleinviewport(elem, true, thresholdX, thresholdY); return visibleinviewport(elem, true, thresholdX, thresholdY);
@ -52,50 +40,18 @@ define(['visibleinviewport', 'browser', 'dom'], function (visibleinviewport, bro
} }
} }
function unveilWithIntersection(elements, root, callback) { function unveilElementsInternal(instance, callback) {
var filledCount = 0;
var options = {};
//options.rootMargin = "300%";
var observer = new IntersectionObserver(function (entries) {
for (var j = 0, length2 = entries.length; j < length2; j++) {
var entry = entries[j];
var target = entry.target;
observer.unobserve(target);
callback(target);
filledCount++;
}
},
options
);
// Start observing an element
for (var i = 0, length = elements.length; i < length; i++) {
observer.observe(elements[i]);
}
}
function unveilElements(elements, root, callback) {
if (!elements.length) {
return;
}
if (supportsIntersectionObserver) {
unveilWithIntersection(elements, root, callback);
return;
}
var unveiledElements = []; var unveiledElements = [];
var cancellationTokens = []; var cancellationTokens = [];
var loadedCount = 0;
function unveilInternal(tokenIndex) { function unveilInternal(tokenIndex) {
var anyFound = false; var anyFound = false;
var out = false; var out = false;
var elements = instance.elements;
// TODO: This out construct assumes left to right, top to bottom // TODO: This out construct assumes left to right, top to bottom
for (var i = 0, length = elements.length; i < length; i++) { for (var i = 0, length = elements.length; i < length; i++) {
@ -111,6 +67,7 @@ define(['visibleinviewport', 'browser', 'dom'], function (visibleinviewport, bro
anyFound = true; anyFound = true;
unveiledElements[i] = true; unveiledElements[i] = true;
callback(elem); callback(elem);
loadedCount++;
} else { } else {
if (anyFound) { if (anyFound) {
@ -119,7 +76,7 @@ define(['visibleinviewport', 'browser', 'dom'], function (visibleinviewport, bro
} }
} }
if (!elements.length) { if (loadedCount >= elements.length) {
dom.removeEventListener(document, 'focus', unveil, { dom.removeEventListener(document, 'focus', unveil, {
capture: true, capture: true,
passive: true passive: true
@ -171,12 +128,58 @@ define(['visibleinviewport', 'browser', 'dom'], function (visibleinviewport, bro
unveil(); unveil();
} }
function lazyChildren(elem, callback) { function LazyLoader(options) {
this.options = options;
}
LazyLoader.prototype.createObserver = function () {
unveilElementsInternal(this, this.options.callback);
this.observer = 1;
};
LazyLoader.prototype.addElements = function (elements) {
this.elements = this.elements || [];
for (var i = 0, length = elements.length; i < length; i++) {
this.elements.push(elements[i]);
}
var observer = this.observer;
if (!observer) {
this.createObserver();
}
};
LazyLoader.prototype.destroyObserver = function (elements) {
};
LazyLoader.prototype.destroy = function (elements) {
this.destroyObserver();
this.options = null;
};
function unveilElements(elements, root, callback) {
if (!elements.length) {
return;
}
var lazyLoader = new LazyLoader({
callback: callback
});
lazyLoader.addElements(elements);
}
LazyLoader.lazyChildren = function (elem, callback) {
unveilElements(elem.getElementsByClassName('lazy'), elem, callback); unveilElements(elem.getElementsByClassName('lazy'), elem, callback);
} }
self.lazyChildren = lazyChildren; return LazyLoader;
return self;
}); });

View file

@ -7,9 +7,14 @@ define(['appSettings', 'events', 'browser'], function (appsettings, events, brow
var currentUserId; var currentUserId;
var currentApiClient; var currentApiClient;
var displayPrefs; var displayPrefs;
var saveTimeout;
self.setUserInfo = function (userId, apiClient) { self.setUserInfo = function (userId, apiClient) {
if (saveTimeout) {
clearTimeout(saveTimeout);
}
currentUserId = userId; currentUserId = userId;
currentApiClient = apiClient; currentApiClient = apiClient;
@ -24,7 +29,6 @@ define(['appSettings', 'events', 'browser'], function (appsettings, events, brow
}); });
}; };
var saveTimeout;
function onSaveTimeout() { function onSaveTimeout() {
saveTimeout = null; saveTimeout = null;
currentApiClient.updateDisplayPreferences('usersettings', displayPrefs, currentUserId, 'emby'); currentApiClient.updateDisplayPreferences('usersettings', displayPrefs, currentUserId, 'emby');

View file

@ -22,34 +22,32 @@
} }
} }
function loadSection(page, user, displayPreferences, index) { function loadSection(page, user, userSettings, index) {
var userId = user.Id; var userId = user.Id;
var section = displayPreferences.CustomPrefs['home' + index] || getDefaultSection(index); var section = userSettings.get('homesection' + index) || getDefaultSection(index);
if (section == 'folders') { if (section == 'folders') {
section = defaultFirstSection; section = defaultFirstSection;
} }
var showLibraryTileNames = displayPreferences.CustomPrefs.enableLibraryTileNames != '0';
var elem = page.querySelector('.section' + index); var elem = page.querySelector('.section' + index);
if (section == 'latestmedia') { if (section == 'latestmedia') {
return Sections.loadRecentlyAdded(elem, user); return Sections.loadRecentlyAdded(elem, user);
} }
else if (section == 'librarytiles') { else if (section == 'librarytiles') {
return Sections.loadLibraryTiles(elem, user, 'backdrop', index, false, showLibraryTileNames); return Sections.loadLibraryTiles(elem, user, 'backdrop', index, false);
} }
else if (section == 'smalllibrarytiles') { else if (section == 'smalllibrarytiles') {
return Sections.loadLibraryTiles(elem, user, 'smallBackdrop', index, false, showLibraryTileNames); return Sections.loadLibraryTiles(elem, user, 'smallBackdrop', index, false);
} }
else if (section == 'smalllibrarytiles-automobile') { else if (section == 'smalllibrarytiles-automobile') {
return Sections.loadLibraryTiles(elem, user, 'smallBackdrop', index, true, showLibraryTileNames); return Sections.loadLibraryTiles(elem, user, 'smallBackdrop', index, true);
} }
else if (section == 'librarytiles-automobile') { else if (section == 'librarytiles-automobile') {
return Sections.loadLibraryTiles(elem, user, 'backdrop', index, true, showLibraryTileNames); return Sections.loadLibraryTiles(elem, user, 'backdrop', index, true);
} }
else if (section == 'librarybuttons') { else if (section == 'librarybuttons') {
return Sections.loadlibraryButtons(elem, userId, index); return Sections.loadlibraryButtons(elem, userId, index);
@ -77,7 +75,7 @@
} }
} }
function loadSections(page, user, displayPreferences) { function loadSections(page, user, userSettings) {
var i, length; var i, length;
var sectionCount = 5; var sectionCount = 5;
@ -98,7 +96,7 @@
for (i = 0, length = sectionCount; i < length; i++) { for (i = 0, length = sectionCount; i < length; i++) {
promises.push(loadSection(page, user, displayPreferences, i)); promises.push(loadSection(page, user, userSettings, i));
} }
return Promise.all(promises); return Promise.all(promises);
@ -186,25 +184,38 @@
}); });
} }
function getRequirePromise(deps) {
return new Promise(function (resolve, reject) {
require(deps, resolve);
});
}
function loadHomeTab(page, tabContent) { function loadHomeTab(page, tabContent) {
if (window.ApiClient) { if (window.ApiClient) {
var userId = Dashboard.getCurrentUserId(); var userId = Dashboard.getCurrentUserId();
Dashboard.showLoadingMsg(); Dashboard.showLoadingMsg();
getDisplayPreferences('home', userId).then(function (result) { var promises = [
getDisplayPreferences('home', userId),
Dashboard.getCurrentUser(),
getRequirePromise(['userSettings'])
];
Dashboard.getCurrentUser().then(function (user) { Promise.all(promises).then(function(responses) {
var displayPreferences = responses[0];
var user = responses[1];
var userSettings = responses[2];
loadSections(tabContent, user, result).then(function () { loadSections(tabContent, user, userSettings).then(function () {
if (!AppInfo.isNativeApp) { if (!AppInfo.isNativeApp) {
showWelcomeIfNeeded(page, result); showWelcomeIfNeeded(page, displayPreferences);
} }
Dashboard.hideLoadingMsg(); Dashboard.hideLoadingMsg();
}); });
});
}); });
} }
} }

View file

@ -308,7 +308,7 @@
html += '<div class="sidebarDivider"></div>'; html += '<div class="sidebarDivider"></div>';
if (user.localUser && (AppInfo.isNativeApp && browserInfo.android)) { if (user.localUser && (AppInfo.isNativeApp && browserInfo.android)) {
html += '<a class="sidebarLink lnkMediaFolder lnkMySettings" onclick="return LibraryMenu.onLinkClicked(event, this);" href="mypreferencesmenu.html?userId=' + user.localUser.Id + '"><i class="md-icon sidebarLinkIcon">settings</i><span class="sidebarLinkText">' + Globalize.translate('ButtonSettings') + '</span></a>'; html += '<a class="sidebarLink lnkMediaFolder lnkMySettings" onclick="return LibraryMenu.onLinkClicked(event, this);" href="mypreferencesmenu.html"><i class="md-icon sidebarLinkIcon">settings</i><span class="sidebarLinkText">' + Globalize.translate('ButtonSettings') + '</span></a>';
} }
html += '<a class="sidebarLink lnkMediaFolder lnkManageOffline" data-itemid="manageoffline" onclick="return LibraryMenu.onLinkClicked(event, this);" href="mysync.html?mode=offline"><i class="md-icon sidebarLinkIcon">file_download</i><span class="sidebarLinkText">' + Globalize.translate('ManageOfflineDownloads') + '</span></a>'; html += '<a class="sidebarLink lnkMediaFolder lnkManageOffline" data-itemid="manageoffline" onclick="return LibraryMenu.onLinkClicked(event, this);" href="mysync.html?mode=offline"><i class="md-icon sidebarLinkIcon">file_download</i><span class="sidebarLinkText">' + Globalize.translate('ManageOfflineDownloads') + '</span></a>';

View file

@ -1,4 +1,4 @@
define(['listViewStyle'], function () { define(['userSettingsBuilder', 'listViewStyle'], function (userSettingsBuilder) {
'use strict'; 'use strict';
function renderViews(page, user, result) { function renderViews(page, user, result) {
@ -113,14 +113,14 @@
page.querySelector('.viewOrderList').innerHTML = html; page.querySelector('.viewOrderList').innerHTML = html;
} }
function loadForm(page, user, displayPreferences) { function loadForm(page, user, userSettings) {
page.querySelector('.chkHidePlayedFromLatest').checked = user.Configuration.HidePlayedInLatest || false; page.querySelector('.chkHidePlayedFromLatest').checked = user.Configuration.HidePlayedInLatest || false;
page.querySelector('#selectHomeSection1').value = displayPreferences.CustomPrefs.home0 || ''; page.querySelector('#selectHomeSection1').value = userSettings.get('homesection0') || '';
page.querySelector('#selectHomeSection2').value = displayPreferences.CustomPrefs.home1 || ''; page.querySelector('#selectHomeSection2').value = userSettings.get('homesection1') || '';
page.querySelector('#selectHomeSection3').value = displayPreferences.CustomPrefs.home2 || ''; page.querySelector('#selectHomeSection3').value = userSettings.get('homesection2') || '';
page.querySelector('#selectHomeSection4').value = displayPreferences.CustomPrefs.home3 || ''; page.querySelector('#selectHomeSection4').value = userSettings.get('homesection3') || '';
var promise1 = ApiClient.getUserViews({}, user.Id); var promise1 = ApiClient.getUserViews({}, user.Id);
var promise2 = ApiClient.getJSON(ApiClient.getUrl("Users/" + user.Id + "/GroupingOptions")); var promise2 = ApiClient.getJSON(ApiClient.getUrl("Users/" + user.Id + "/GroupingOptions"));
@ -135,14 +135,6 @@
}); });
} }
function displayPreferencesKey() {
if (AppInfo.isNativeApp) {
return 'Emby Mobile';
}
return 'webclient';
}
function getCheckboxItems(selector, page, isChecked) { function getCheckboxItems(selector, page, isChecked) {
var inputs = page.querySelectorAll(selector); var inputs = page.querySelectorAll(selector);
@ -159,7 +151,7 @@
return list; return list;
} }
function saveUser(page, user, displayPreferences) { function saveUser(page, user, userSettings) {
user.Configuration.HidePlayedInLatest = page.querySelector('.chkHidePlayedFromLatest').checked; user.Configuration.HidePlayedInLatest = page.querySelector('.chkHidePlayedFromLatest').checked;
@ -183,18 +175,15 @@
user.Configuration.OrderedViews = orderedViews; user.Configuration.OrderedViews = orderedViews;
displayPreferences.CustomPrefs.home0 = page.querySelector('#selectHomeSection1').value; userSettings.set('homesection0', page.querySelector('#selectHomeSection1').value);
displayPreferences.CustomPrefs.home1 = page.querySelector('#selectHomeSection2').value; userSettings.set('homesection1', page.querySelector('#selectHomeSection2').value);
displayPreferences.CustomPrefs.home2 = page.querySelector('#selectHomeSection3').value; userSettings.set('homesection2', page.querySelector('#selectHomeSection3').value);
displayPreferences.CustomPrefs.home3 = page.querySelector('#selectHomeSection4').value; userSettings.set('homesection3', page.querySelector('#selectHomeSection4').value);
return ApiClient.updateDisplayPreferences('home', displayPreferences, user.Id, displayPreferencesKey()).then(function () {
return ApiClient.updateUserConfiguration(user.Id, user.Configuration); return ApiClient.updateUserConfiguration(user.Id, user.Configuration);
});
} }
function save(page, userId) { function save(page, userId, userSettings) {
Dashboard.showLoadingMsg(); Dashboard.showLoadingMsg();
@ -204,9 +193,7 @@
ApiClient.getUser(userId).then(function (user) { ApiClient.getUser(userId).then(function (user) {
ApiClient.getDisplayPreferences('home', user.Id, displayPreferencesKey()).then(function (displayPreferences) { saveUser(page, user, userSettings).then(function () {
saveUser(page, user, displayPreferences).then(function () {
Dashboard.hideLoadingMsg(); Dashboard.hideLoadingMsg();
if (!AppInfo.enableAutoSave) { if (!AppInfo.enableAutoSave) {
@ -218,8 +205,6 @@
}, function () { }, function () {
Dashboard.hideLoadingMsg(); Dashboard.hideLoadingMsg();
}); });
});
}); });
} }
@ -257,14 +242,21 @@
return function (view, params) { return function (view, params) {
var userId = getParameterByName('userId') || Dashboard.getCurrentUserId(); var userId = params.userId || Dashboard.getCurrentUserId();
var userSettings = new userSettingsBuilder();
var userSettingsLoaded;
function onSubmit(e) { function onSubmit(e) {
save(view, userId); userSettings.setUserInfo(userId, ApiClient).then(function () {
save(view, userId, userSettings);
});
// Disable default form submission // Disable default form submission
if (e) {
e.preventDefault(); e.preventDefault();
}
return false; return false;
} }
@ -329,19 +321,18 @@
ApiClient.getUser(userId).then(function (user) { ApiClient.getUser(userId).then(function (user) {
ApiClient.getDisplayPreferences('home', user.Id, displayPreferencesKey()).then(function (result) { userSettings.setUserInfo(userId, ApiClient).then(function () {
loadForm(page, user, result); userSettingsLoaded = true;
loadForm(page, user, userSettings);
}); });
}); });
}); });
view.addEventListener('viewbeforehide', function () { view.addEventListener('viewbeforehide', function () {
var page = this;
if (AppInfo.enableAutoSave) { if (AppInfo.enableAutoSave) {
save(page, userId); onSubmit();
} }
}); });
}; };

View file

@ -388,7 +388,7 @@
}); });
} }
function loadLibraryTiles(elem, user, shape, index, autoHideOnMobile, showTitles) { function loadLibraryTiles(elem, user, shape, index, autoHideOnMobile) {
return getUserViews(user.Id).then(function (items) { return getUserViews(user.Id).then(function (items) {
@ -418,7 +418,7 @@
html += cardBuilder.getCardsHtml({ html += cardBuilder.getCardsHtml({
items: items, items: items,
shape: scrollX ? 'overflowBackdrop' : shape, shape: scrollX ? 'overflowBackdrop' : shape,
showTitle: showTitles, showTitle: true,
centerText: true, centerText: true,
overlayText: false, overlayText: false,
lazy: true, lazy: true,

View file

@ -314,7 +314,7 @@ var Dashboard = {
showUserFlyout: function () { showUserFlyout: function () {
Dashboard.navigate('mypreferencesmenu.html?userId=' + ApiClient.getCurrentUserId()); Dashboard.navigate('mypreferencesmenu.html');
}, },
getPluginSecurityInfo: function () { getPluginSecurityInfo: function () {
@ -1222,7 +1222,11 @@ var AppInfo = {};
define("libjass", [bowerPath + "/libjass/libjass.min", "css!" + bowerPath + "/libjass/libjass"], returnFirstDependency); define("libjass", [bowerPath + "/libjass/libjass.min", "css!" + bowerPath + "/libjass/libjass"], returnFirstDependency);
define("lazyLoader", [embyWebComponentsBowerPath + "/images/lazyloader"], returnFirstDependency); if (window.IntersectionObserver) {
define("lazyLoader", [embyWebComponentsBowerPath + "/lazyloader/lazyloader-intersectionobserver"], returnFirstDependency);
} else {
define("lazyLoader", [embyWebComponentsBowerPath + "/lazyloader/lazyloader-scroll"], returnFirstDependency);
}
define("imageLoader", [embyWebComponentsBowerPath + "/images/imagehelper"], returnFirstDependency); define("imageLoader", [embyWebComponentsBowerPath + "/images/imagehelper"], returnFirstDependency);
define("syncJobList", ["components/syncjoblist/syncjoblist"], returnFirstDependency); define("syncJobList", ["components/syncjoblist/syncjoblist"], returnFirstDependency);
define("appfooter", ["components/appfooter/appfooter"], returnFirstDependency); define("appfooter", ["components/appfooter/appfooter"], returnFirstDependency);
@ -1543,7 +1547,7 @@ var AppInfo = {};
}; };
embyRouter.showSettings = function () { embyRouter.showSettings = function () {
Dashboard.navigate('mypreferencesmenu.html?userId=' + ApiClient.getCurrentUserId()); Dashboard.navigate('mypreferencesmenu.html');
}; };
embyRouter.showGuide = function () { embyRouter.showGuide = function () {