diff --git a/CHANGELOG.md b/CHANGELOG.md index 14584f327..ea9de1bea 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,8 @@ +- More index navigation improvements: + - New setting: `Anchor Hidden Threads`, enabled by default. Hidden threads will be moved at the end of the index to fill the first pages. + - New setting: `Refreshed Navigation`, disabled by default. When enabled, navigating through pages will refresh the index. + - The last index refresh timer will now indicate the last time the index changed from 4chan's side, instead of the last time you refreshed the index. + ### 3.14.3 - *2013-12-09* - Minor bug fixes. diff --git a/src/General/Config.coffee b/src/General/Config.coffee index 086bb7262..14b665337 100644 --- a/src/General/Config.coffee +++ b/src/General/Config.coffee @@ -143,6 +143,8 @@ Config = 'Index Mode': 'paged' 'Index Sort': 'bump' 'Show Replies': true + 'Anchor Hidden Threads': true + 'Refreshed Navigation': false Header: 'Header auto-hide': false 'Header auto-hide on scroll': false diff --git a/src/General/Index.coffee b/src/General/Index.coffee index 81c04d9bb..06d19b3e8 100644 --- a/src/General/Index.coffee +++ b/src/General/Index.coffee @@ -37,18 +37,33 @@ Index = $.on input, 'change', @cb.sort repliesEntry = - el: $.el 'label', innerHTML: ' Show replies' - input = repliesEntry.el.firstChild - input.checked = Conf['Show Replies'] - $.on input, 'change', $.cb.checked - $.on input, 'change', @cb.replies + el: $.el 'label', + innerHTML: ' Show replies' + anchorEntry = + el: $.el 'label', + innerHTML: ' Anchor hidden threads' + title: 'Move hidden threads at the end of the index.' + refNavEntry = + el: $.el 'label', + innerHTML: ' Refreshed navigation' + title: 'Refresh index when navigating through pages.' + for label in [repliesEntry, anchorEntry, refNavEntry] + input = label.el.firstChild + {name} = input + input.checked = Conf[name] + $.on input, 'change', $.cb.checked + switch name + when 'Show Replies' + $.on input, 'change', @cb.replies + when 'Anchor Hidden Threads' + $.on input, 'change', @cb.sort $.event 'AddMenuEntry', type: 'header' el: $.el 'span', textContent: 'Index Navigation' order: 90 - subEntries: [modeEntry, sortEntry, repliesEntry] + subEntries: [modeEntry, sortEntry, repliesEntry, anchorEntry, refNavEntry] $.addClass doc, 'index-loading' @update() @@ -110,13 +125,18 @@ Index = return return if a.textContent is 'Catalog' e.preventDefault() - Index.pageNav +a.pathname.split('/')[2] + Index.userPageNav +a.pathname.split('/')[2] scrollToIndex: -> Header.scrollToIfNeeded Index.root getCurrentPage: -> +window.location.pathname.split('/')[2] + userPageNav: (pageNum) -> + if Conf['Refreshed Navigation'] and Conf['Index Mode'] is 'paged' + Index.update pageNum + else + Index.pageNav pageNum pageNav: (pageNum) -> return if Index.currentPage is pageNum history.pushState null, '', if pageNum is 0 then './' else pageNum @@ -173,7 +193,7 @@ Index = $.before a, strong $.add strong, a - update: -> + update: (pageNum) -> return unless navigator.onLine Index.req?.abort() Index.notice?.close() @@ -188,13 +208,15 @@ Index = return unless Index.req and !Index.notice Index.notice = new Notice 'info', 'Refreshing index...' ), 5 * $.SECOND - (Date.now() - now) + pageNum = null if typeof pageNum isnt 'number' # event + onload = (e) -> Index.load e, pageNum Index.req = $.ajax "//a.4cdn.org/#{g.BOARD}/catalog.json", - onabort: Index.load - onloadend: Index.load + onabort: onload + onloadend: onload , whenModified: true $.addClass Index.button, 'fa-spin' - load: (e) -> + load: (e, pageNum) -> $.rmClass Index.button, 'fa-spin' {req, notice} = Index delete Index.req @@ -206,7 +228,10 @@ Index = return try - Index.parse JSON.parse req.response if req.status is 200 + if req.status is 200 + Index.parse JSON.parse(req.response), pageNum + else if req.status is 304 and pageNum? + Index.pageNav pageNum catch err c.error 'Index failure:', err.stack # network error or non-JSON content for example. @@ -224,15 +249,18 @@ Index = setTimeout notice.close, $.SECOND timeEl = $ '#index-last-refresh', Index.navLinks - timeEl.dataset.utc = e.timeStamp <% if (type === 'userscript') { %>/ 1000<% } %> + timeEl.dataset.utc = Date.parse req.getResponseHeader 'Last-Modified' RelativeDates.update timeEl Index.scrollToIndex() - parse: (pages) -> + parse: (pages, pageNum) -> Index.parseThreadList pages Index.buildThreads() Index.sort() - Index.buildIndex() Index.buildPagelist() + if pageNum? + Index.pageNav pageNum + return + Index.buildIndex() Index.setPage() parseThreadList: (pages) -> Index.pagesNum = pages.length @@ -318,12 +346,17 @@ Index = Index.sortedNodes.push Index.nodes[i], Index.nodes[i + 1] if Index.isSearching Index.sortedNodes = Index.querySearch(Index.searchInput.value) or Index.sortedNodes - # Put the sticky threads on top of the index. + # Move non-hidden threads on top of the index. + if Conf['Anchor Hidden Threads'] + offset = 0 + for threadRoot, i in Index.sortedNodes by 2 when not Get.threadFromRoot(threadRoot).isHidden + Index.sortedNodes.splice offset++ * 2, 0, Index.sortedNodes.splice(i, 2)... + # Move sticky threads on top of the index. offset = 0 for threadRoot, i in Index.sortedNodes by 2 when Get.threadFromRoot(threadRoot).isSticky Index.sortedNodes.splice offset++ * 2, 0, Index.sortedNodes.splice(i, 2)... return unless Conf['Filter'] - # Put the highlighted thread &
on top of the index + # Move highlighted threads &
on top of the index # while keeping the original order they appear in. offset = 0 for threadRoot, i in Index.sortedNodes by 2 when Get.threadFromRoot(threadRoot).isOnTop diff --git a/src/Miscellaneous/Keybinds.coffee b/src/Miscellaneous/Keybinds.coffee index 76370e38c..c158cb183 100644 --- a/src/Miscellaneous/Keybinds.coffee +++ b/src/Miscellaneous/Keybinds.coffee @@ -75,7 +75,7 @@ Keybinds = # Board Navigation when Conf['Front page'] if g.VIEW is 'index' - Index.pageNav 0 + Index.userPageNav 0 else window.location = "/#{g.BOARD}/" when Conf['Open front page']