diff --git a/static/css/main.css b/static/css/main.css index 184ffda..36c26d1 100644 --- a/static/css/main.css +++ b/static/css/main.css @@ -122,7 +122,7 @@ a { background-color: transparent; border: 2px solid white; overflow: visible; - color: #444; + color: white; font: inherit; padding: .5rem 1.5rem; margin: .5rem 1rem; @@ -131,9 +131,9 @@ a { .mg-tag-filter:hover { border-color: #b2b2b2; text-decoration: none; } - .mg-tag-filter-enabled { + .mg-tag-filter-include { background-color: #33b5e5; } - .mg-tag-filter-disabled { + .mg-tag-filter-exclude { background-color: #FF9148; } .mg-nav-small { diff --git a/templates/index.html b/templates/index.html index 7440c56..d836c1a 100644 --- a/templates/index.html +++ b/templates/index.html @@ -6,11 +6,11 @@ {% if MG_LANG_FILTER_TAGS or MG_FILTER_TAGS %} {% endif %} diff --git a/templates/js/filter-tags.js b/templates/js/filter-tags.js index ff93383..a497635 100644 --- a/templates/js/filter-tags.js +++ b/templates/js/filter-tags.js @@ -9,23 +9,25 @@ window.tagFilters = {} function indexOf(array, predicate) { for (var i = 0; i < array.length; i++) if (predicate(array[i])) return array[i]; } -function startsWith(searchString, position) { - position = position || 0; - return this.substr(position, searchString.length) === searchString; +function includes(array, value) { + return array.indexOf(value) !== -1; }; function toggleTagFilter(tag) { var filterState = window.tagFilters[tag] if (filterState === true) { - this.classList.remove('mg-tag-filter-enabled'); + this.classList.remove('mg-tag-filter-exclude'); filterState = false; - this.classList.add('mg-tag-filter-disabled'); + this.classList.add('mg-tag-filter-include'); + this.title = 'Tag filter (include matching articles)'; } else if (filterState === false) { - this.classList.remove('mg-tag-filter-disabled'); + this.classList.remove('mg-tag-filter-include'); filterState = undefined; + this.title = 'Tag filter (disabled)'; } else { filterState = true; - this.classList.add('mg-tag-filter-enabled'); + this.classList.add('mg-tag-filter-exclude'); + this.title = 'Tag filter (exclude matching articles)'; } window.tagFilters[tag] = filterState; updateArticlesVisibility(); @@ -33,38 +35,38 @@ function toggleTagFilter(tag) { function toggleLangTagFilter(langs) { var lang = this.textContent; - if (lang === 'lang') { - lang = langs[0]; - window.tagFilters['lang:'+lang] = true; + window.tagFilters['lang:'+lang] = undefined; + lang = langs[langs.indexOf(lang) + 1]; + if (typeof lang === 'undefined') { + lang = 'lang' + this.title = 'Language filter (disabled)'; } else { - window.tagFilters['lang:'+lang] = undefined; - lang = langs[langs.indexOf(lang) + 1]; - if (typeof lang === 'undefined') { - lang = 'lang' - } else { - window.tagFilters['lang:'+lang] = true; - } + window.tagFilters['lang:'+lang] = true; + this.title = 'Language filter (include only "' + lang + '" articles)'; } this.textContent = lang; updateArticlesVisibility(); } function updateArticlesVisibility() { - var anyTrueFilter = Object.keys(window.tagFilters).some(function (tagFilter) { - return !!window.tagFilters[tagFilter]; + var includeFilters = Object.keys(window.tagFilters).filter(function (tagFilter) { + return window.tagFilters[tagFilter] === true; + }); + var excludeFilters = Object.keys(window.tagFilters).filter(function (tagFilter) { + return window.tagFilters[tagFilter] === false; }); Array.prototype.slice.call(document.getElementsByTagName('article')).forEach(function (article) { if (!article.dataset.tags) { // article-excerpt: we ignore it return; } var articleTags = JSON.parse(article.dataset.tags); - var anyTagWhitelisted = articleTags.some(function (tag) { return window.tagFilters[tag] === true; }); - var anyTagBlacklisted = articleTags.some(function (tag) { return window.tagFilters[tag] === false; }); + var allIncludeTags = includeFilters.every(function (tag) { return includes(articleTags, tag); }); + var anyExcludeTag = excludeFilters.some(function (tag) { return includes(articleTags, tag); }); // Now implementing the core logic - var shouldDisplay = !anyTagBlacklisted; - if (shouldDisplay && anyTrueFilter) { - shouldDisplay = anyTagWhitelisted; + var shouldDisplay = !anyExcludeTag; + if (shouldDisplay && includeFilters.length > 0) { + shouldDisplay = allIncludeTags; } if (shouldDisplay) {