From c343b93a37cb7d50f7d610cdcd55aeb20e6310ef Mon Sep 17 00:00:00 2001 From: Baris Usakli Date: Sat, 17 Nov 2018 14:07:48 -0500 Subject: [PATCH] optimize ajaxify - do not call $.timeago twice on topic load and for widgets - do not use toLocaleString for each timeago string, use a single Intl.DateTimeFormat instance instead - do not call format for empty timeago strings, ie a post that isnt edited doesnt have a timeago string - do not call isTouchDevice for every element - remove app.replaceSelfLinks, this is superceded with /me route - store references to jquery objects in navigator instead of creating them on every scroll --- public/src/ajaxify.js | 13 ++---- public/src/app.js | 66 ++++++++++++------------------ public/src/client/topic.js | 2 +- public/src/client/topic/events.js | 1 - public/src/client/topic/posts.js | 16 +++++--- public/src/client/topic/replies.js | 4 +- public/src/modules/navigator.js | 56 ++++++++++++++----------- public/src/overrides.js | 13 +++--- public/src/widgets.js | 17 ++------ 9 files changed, 87 insertions(+), 101 deletions(-) diff --git a/public/src/ajaxify.js b/public/src/ajaxify.js index 2b49b7f860..77dd6d1d3e 100644 --- a/public/src/ajaxify.js +++ b/public/src/ajaxify.js @@ -202,15 +202,10 @@ $(document).ready(function () { } ajaxify.end = function (url, tpl_url) { - var count = 2; - function done() { - count -= 1; - if (count === 0) { - $(window).trigger('action:ajaxify.end', { url: url, tpl_url: tpl_url, title: ajaxify.data.title }); - } - } - ajaxify.loadScript(tpl_url, done); - ajaxify.widgets.render(tpl_url, done); + ajaxify.loadScript(tpl_url, function done() { + $(window).trigger('action:ajaxify.end', { url: url, tpl_url: tpl_url, title: ajaxify.data.title }); + }); + ajaxify.widgets.render(tpl_url); $(window).trigger('action:ajaxify.contentLoaded', { url: url, tpl: tpl_url }); diff --git a/public/src/app.js b/public/src/app.js index 87d33969af..70fe4f5c1a 100644 --- a/public/src/app.js +++ b/public/src/app.js @@ -12,6 +12,7 @@ app.cacheBuster = null; var params = utils.params(); var showWelcomeMessage = !!params.loggedin; var registerMessage = params.register; + var isTouchDevice = utils.isTouchDevice(); require(['benchpress'], function (Benchpress) { Benchpress.setGlobal('config', config); @@ -277,19 +278,20 @@ app.cacheBuster = null; } app.createUserTooltips = function (els, placement) { + if (isTouchDevice) { + return; + } els = els || $('body'); els.find('.avatar,img[title].teaser-pic,img[title].user-img,div.user-icon,span.user-icon').each(function () { - if (!utils.isTouchDevice()) { - $(this).tooltip({ - placement: placement || $(this).attr('title-placement') || 'top', - title: $(this).attr('title'), - }); - } + $(this).tooltip({ + placement: placement || $(this).attr('title-placement') || 'top', + title: $(this).attr('title'), + }); }); }; app.createStatusTooltips = function () { - if (!utils.isTouchDevice()) { + if (!isTouchDevice) { $('body').tooltip({ selector: '.fa-circle.status', placement: 'top', @@ -297,16 +299,6 @@ app.cacheBuster = null; } }; - app.replaceSelfLinks = function (selector) { - selector = selector || $('a'); - selector.each(function () { - var href = $(this).attr('href'); - if (href && app.user.userslug && href.indexOf('user/_self_') !== -1) { - $(this).attr('href', href.replace(/user\/_self_/g, 'user/' + app.user.userslug)); - } - }); - }; - app.processPage = function () { highlightNavigationLink(); @@ -320,8 +312,6 @@ app.cacheBuster = null; app.createStatusTooltips(); - app.replaceSelfLinks(); - // Scroll back to top of page if (!ajaxify.isCold()) { window.scrollTo(0, 0); @@ -516,34 +506,30 @@ app.cacheBuster = null; function createHeaderTooltips() { var env = utils.findBootstrapEnvironment(); - if (env === 'xs' || env === 'sm') { + if (env === 'xs' || env === 'sm' || isTouchDevice) { return; } $('#header-menu li a[title]').each(function () { - if (!utils.isTouchDevice()) { - $(this).tooltip({ - placement: 'bottom', - trigger: 'hover', - title: $(this).attr('title'), - }); - } - }); - - if (!utils.isTouchDevice()) { - $('#search-form').parent().tooltip({ + $(this).tooltip({ placement: 'bottom', trigger: 'hover', - title: $('#search-button i').attr('title'), + title: $(this).attr('title'), }); - } + }); - if (!utils.isTouchDevice()) { - $('#user_dropdown').tooltip({ - placement: 'bottom', - trigger: 'hover', - title: $('#user_dropdown').attr('title'), - }); - } + + $('#search-form').parent().tooltip({ + placement: 'bottom', + trigger: 'hover', + title: $('#search-button i').attr('title'), + }); + + + $('#user_dropdown').tooltip({ + placement: 'bottom', + trigger: 'hover', + title: $('#user_dropdown').attr('title'), + }); } app.handleSearch = function () { diff --git a/public/src/client/topic.js b/public/src/client/topic.js index a73f884482..6a56a7f6fa 100644 --- a/public/src/client/topic.js +++ b/public/src/client/topic.js @@ -45,7 +45,7 @@ define('forum/topic', [ app.enterRoom('topic_' + tid); - posts.processPage(components.get('post')); + posts.onTopicPageLoad(components.get('post')); postTools.init(tid); threadTools.init(tid); diff --git a/public/src/client/topic/events.js b/public/src/client/topic/events.js index 544d8039a6..95e5b2720a 100644 --- a/public/src/client/topic/events.js +++ b/public/src/client/topic/events.js @@ -129,7 +129,6 @@ define('forum/topic/events', [ editedPostEl.fadeOut(250, function () { editedPostEl.html(translator.unescape(data.post.content)); editedPostEl.find('img:not(.not-responsive)').addClass('img-responsive'); - app.replaceSelfLinks(editedPostEl.find('a')); images.wrapImagesInLinks(editedPostEl.parent()); images.unloadImages(editedPostEl.parent()); images.loadImages(); diff --git a/public/src/client/topic/posts.js b/public/src/client/topic/posts.js index 3016e91b4d..2283d444b4 100644 --- a/public/src/client/topic/posts.js +++ b/public/src/client/topic/posts.js @@ -205,7 +205,7 @@ define('forum/topic/posts', [ $(window).trigger('action:posts.loaded', { posts: data.posts }); - Posts.processPage(html); + Posts.onNewPostsAddedToDom(html); callback(html); }); @@ -251,18 +251,22 @@ define('forum/topic/posts', [ }); }; - Posts.processPage = function (posts) { + Posts.onTopicPageLoad = function (posts) { images.unloadImages(posts); Posts.showBottomPostBar(); posts.find('[component="post/content"] img:not(.not-responsive)').addClass('img-responsive'); + addBlockquoteEllipses(posts.find('[component="post/content"] > blockquote > blockquote')); + hidePostToolsForDeletedPosts(posts); + }; + + Posts.onNewPostsAddedToDom = function (posts) { + Posts.onTopicPageLoad(posts); + app.createUserTooltips(posts); - app.replaceSelfLinks(posts.find('a')); + utils.addCommasToNumbers(posts.find('.formatted-number')); utils.makeNumbersHumanReadable(posts.find('.human-readable-number')); posts.find('.timeago').timeago(); - - addBlockquoteEllipses(posts.find('[component="post/content"] > blockquote > blockquote')); - hidePostToolsForDeletedPosts(posts); }; Posts.showBottomPostBar = function () { diff --git a/public/src/client/topic/replies.js b/public/src/client/topic/replies.js index 82bd224173..a931ce6eec 100644 --- a/public/src/client/topic/replies.js +++ b/public/src/client/topic/replies.js @@ -48,7 +48,7 @@ define('forum/topic/replies', ['navigator', 'components', 'forum/topic/posts'], app.parseAndTranslate('topic', 'posts', tplData, function (html) { $('
', { component: 'post/replies' }).html(html).hide().insertAfter(button) .slideDown('fast'); - posts.processPage(html); + posts.onNewPostsAddedToDom(html); $(window).trigger('action:posts.loaded', { posts: data }); }); }); @@ -73,7 +73,7 @@ define('forum/topic/replies', ['navigator', 'components', 'forum/topic/posts'], var replies = $('[component="post"][data-pid="' + post.toPid + '"] [component="post/replies"]').first(); if (replies.length) { replies.append(html); - posts.processPage(html); + posts.onNewPostsAddedToDom(html); } }); }; diff --git a/public/src/modules/navigator.js b/public/src/modules/navigator.js index e02a8910c9..c4fa80548e 100644 --- a/public/src/modules/navigator.js +++ b/public/src/modules/navigator.js @@ -13,6 +13,12 @@ define('navigator', ['forum/pagination', 'components'], function (pagination, co navigator.scrollActive = false; + var paginationBlockEl = $('.pagination-block'); + var paginationTextEl = $('.pagination-block .pagination-text'); + var paginationBlockMeterEl = $('.pagination-block meter'); + var paginationBlockProgressEl = $('.pagination-block .progress-bar'); + + $(window).on('action:ajaxify.start', function () { $(window).off('keydown', onKeyDown); }); @@ -26,22 +32,21 @@ define('navigator', ['forum/pagination', 'components'], function (pagination, co $(window).off('scroll', navigator.delayedUpdate).on('scroll', navigator.delayedUpdate); - $('.pagination-block .dropdown-menu').off('click').on('click', function (e) { + paginationBlockEl.find('.dropdown-menu').off('click').on('click', function (e) { e.stopPropagation(); }); - $('.pagination-block').off('shown.bs.dropdown', '.dropdown').on('shown.bs.dropdown', '.dropdown', function () { + paginationBlockEl.off('shown.bs.dropdown', '.dropdown').on('shown.bs.dropdown', '.dropdown', function () { setTimeout(function () { $('.pagination-block input').focus(); }, 100); }); + paginationBlockEl.find('.pageup').off('click').on('click', navigator.scrollUp); + paginationBlockEl.find('.pagedown').off('click').on('click', navigator.scrollDown); + paginationBlockEl.find('.pagetop').off('click').on('click', navigator.toTop); + paginationBlockEl.find('.pagebottom').off('click').on('click', navigator.toBottom); - $('.pagination-block .pageup').off('click').on('click', navigator.scrollUp); - $('.pagination-block .pagedown').off('click').on('click', navigator.scrollDown); - $('.pagination-block .pagetop').off('click').on('click', navigator.toTop); - $('.pagination-block .pagebottom').off('click').on('click', navigator.toBottom); - - $('.pagination-block input').on('keydown', function (e) { + paginationBlockEl.find('input').on('keydown', function (e) { if (e.which === 13) { var input = $(this); if (!utils.isNumber(input.val())) { @@ -169,7 +174,7 @@ define('navigator', ['forum/pagination', 'components'], function (pagination, co return; } - $('.pagination-block').toggleClass('ready', flag); + paginationBlockEl.toggleClass('ready', flag); } navigator.delayedUpdate = function () { @@ -247,10 +252,10 @@ define('navigator', ['forum/pagination', 'components'], function (pagination, co } index = index > count ? count : index; var relIndex = getRelativeIndex(); - $('.pagination-block .pagination-text').translateHtml('[[global:pagination.out_of, ' + relIndex + ', ' + count + ']]'); + paginationTextEl.translateHtml('[[global:pagination.out_of, ' + relIndex + ', ' + count + ']]'); var fraction = (relIndex - 1) / (count - 1 || 1); - $('.pagination-block meter').val(fraction); - $('.pagination-block .progress-bar').width((fraction * 100) + '%'); + paginationBlockMeterEl.val(fraction); + paginationBlockProgressEl.width((fraction * 100) + '%'); }; function getRelativeIndex() { @@ -394,16 +399,7 @@ define('navigator', ['forum/pagination', 'components'], function (pagination, co var done = false; function animateScroll() { - var scrollTop = 0; - if (postHeight < viewportHeight) { - scrollTop = (scrollTo.offset().top - (viewportHeight / 2) + (postHeight / 2)); - } else { - scrollTop = scrollTo.offset().top - navbarHeight; - } - - $('html, body').animate({ - scrollTop: scrollTop + 'px', - }, duration, function () { + function onAnimateComplete() { if (done) { // Re-enable onScroll behaviour $(window).on('scroll', navigator.update); @@ -417,7 +413,21 @@ define('navigator', ['forum/pagination', 'components'], function (pagination, co highlightPost(); $('body').scrollTop($('body').scrollTop() - 1); $('html').scrollTop($('html').scrollTop() - 1); - }); + } + + var scrollTop = 0; + if (postHeight < viewportHeight) { + scrollTop = (scrollTo.offset().top - (viewportHeight / 2) + (postHeight / 2)); + } else { + scrollTop = scrollTo.offset().top - navbarHeight; + } + if (duration === 0) { + $(window).scrollTop(scrollTop); + return onAnimateComplete(); + } + $('html, body').animate({ + scrollTop: scrollTop + 'px', + }, duration, onAnimateComplete); } function highlightPost() { diff --git a/public/src/overrides.js b/public/src/overrides.js index b74d93efba..b19b91aecc 100644 --- a/public/src/overrides.js +++ b/public/src/overrides.js @@ -118,17 +118,20 @@ if (typeof window !== 'undefined') { } $.timeago.settings.allowFuture = true; - + var userLang = config.userLang.replace('_', '-'); + var options = { year: 'numeric', month: 'short', day: 'numeric', hour: 'numeric', minute: 'numeric' }; + var dtFormat = new Intl.DateTimeFormat(userLang, options); + var iso; $.fn.timeago = function () { var els = $(this); - // Convert "old" format to new format (#5108) - var options = { year: 'numeric', month: 'short', day: 'numeric', hour: 'numeric', minute: 'numeric' }; - var iso; els.each(function () { iso = this.getAttribute('title'); + if (!iso) { + return; + } this.setAttribute('datetime', iso); - $(this).text(new Date(iso).toLocaleString(config.userLang.replace('_', '-'), options)); + this.textContent = dtFormat.format(new Date(iso)); }); timeagoFn.apply(this, arguments); diff --git a/public/src/widgets.js b/public/src/widgets.js index badc55c892..b543f08134 100644 --- a/public/src/widgets.js +++ b/public/src/widgets.js @@ -3,11 +3,9 @@ (function (ajaxify) { ajaxify.widgets = {}; - ajaxify.widgets.render = function (template, callback) { - callback = callback || function () {}; - + ajaxify.widgets.render = function (template) { if (template.match(/^admin/)) { - return callback(); + return; } var locations = Object.keys(ajaxify.data.widgets); @@ -42,6 +40,7 @@ area = $('#content [widget-area="' + location + '"]'); if (html && area.length) { area.html(html); + area.find('img:not(.not-responsive)').addClass('img-responsive'); } if (widgetsAtLocation.length) { @@ -49,16 +48,6 @@ } }); - var widgetAreas = $('#content [widget-area]'); - widgetAreas.find('img:not(.not-responsive)').addClass('img-responsive'); - widgetAreas.find('.timeago').timeago(); - widgetAreas.find('img[title].teaser-pic,img[title].user-img').each(function () { - $(this).tooltip({ - placement: 'top', - title: $(this).attr('title'), - }); - }); $(window).trigger('action:widgets.loaded', {}); - callback(); }; }(ajaxify || {}));