Last active
July 17, 2019 13:32
-
-
Save CermakM/e51c2fead4e97e9bf341afdad62aac18 to your computer and use it in GitHub Desktop.
Sort trello cards by aging class
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
* This is a Trello "plugin" for sorting cards by their age (using the Card Aging Trello Plugin). | |
* | |
* The Card Aging plugin has to be enabled. | |
* Usage: | |
* 1) Use with CJS extension | |
Chrome : https://chrome.google.com/webstore/detail/custom-javascript-for-web/ddbjnfjiigjmcpcpkmhogomapikjbjdk?hl=en | |
Firefox: https://addons.mozilla.org/en-US/firefox/addon/codeinjector/ | |
* 2) Go to your Trello Board and include the following loading script in the extension. | |
* | |
* ``` | |
* const plugins = [ | |
* "https://gist.githubusercontent.com/CermakM/e51c2fead4e97e9bf341afdad62aac18/raw/e990b4ac5990d6c863ad3ee1abc8a330acf90e78/trello-sort.js" | |
* ] | |
* const scripts = [] | |
* | |
* $('.trello-root').ready(function () { | |
* plugins.forEach( p => { | |
* const script = $('<script/>', { | |
* id : "trello-sort-cards-by-age", | |
* type: "text/javascript", | |
* crossorigin: 'anonymous' | |
* }) | |
* | |
* fetch(p) | |
* .then( r => r.text()) | |
* .then( t => script.text(t)) | |
* .then( $('body').append(script) ) | |
* .catch(console.error) | |
* }) | |
* }) | |
* ``` | |
* | |
* 3) Click `save` and you should be all set | |
* 4) [optional] Check console logs that everything went fine | |
*/ | |
console._debug = function() {console.debug("[TrelloCardAging]", ...arguments)} | |
var _cacheLastColumnName; | |
var actionListObserver, | |
contentObserver; | |
var targetNode; | |
// Options for the observer (which mutations to observe) | |
const observerConfig = { childList: true }; | |
/** | |
* Sort Trello cards in the given column by their age | |
*/ | |
let sortTrelloCardsByAge = function(columnName) { | |
const cards = $(`.list-header-name:contains(${columnName})`).parent().siblings().find('.list-card') | |
const sortedCards = cards.sort( (c1, c2) => { | |
let s1 = c1.classList.toString() | |
let m1 = s1.match(/(?:aging-level-)(\d)/) | |
const ageCard1 = m1 ? Number(m1[1]) : Infinity | |
let s2 = c2.classList.toString() | |
let m2 = s2.match(/(?:aging-level-)(\d)/) | |
const ageCard2 = m2 ? Number(m2[1]) : Infinity | |
if ( ageCard1 === ageCard2 ) | |
return 0 | |
return ageCard1 < ageCard2 ? -1 : 1 | |
}) | |
let container = cards.parent() | |
container.html(sortedCards) | |
console._debug(`Cards in column ${columnName} have been sorted by age.`) | |
} | |
/** | |
* Callback for Sort By mutations | |
*/ | |
let callbackSortBy = function(mutationsList, observer) { | |
console._debug("Content list mutation observed.", mutationsList) | |
if ( $(targetNode).find('.pop-over-header-title:contains(Sort List)') ) { | |
const optionList = $(targetNode).find('ul.pop-over-list') | |
const option = $('<li/>') | |
.html('<a class="js-sort-card-age" href="#">Card Age</a>') | |
.click(() => { | |
sortTrelloCardsByAge(_cacheLastColumnName) | |
// TODO: emit click to hide the menu (feels more natural) | |
}) | |
optionList.append(option) | |
console.debug("'Card Age' has been attached.", option) | |
} | |
observer.disconnect() | |
} | |
/** | |
* Callback for Action List mutations | |
*/ | |
let callbackListActions = function(mutationsList, observer) { | |
console._debug("Action list mutation observed.", mutationsList) | |
let contentNode = $(targetNode).find('div.pop-over-content').get(0) | |
if ( !contentNode ) | |
return | |
try { | |
contentObserver.disconnect() | |
} catch {} | |
contentObserver = new MutationObserver(callbackSortBy) | |
contentObserver.observe(contentNode, observerConfig) | |
console._debug("New observer has been attached to the content list.") | |
observer.takeRecords() | |
}; | |
console._debug("Waiting for Board to be initialized.") | |
$('.board').ready(function() { | |
$('div.list-header').each( (i, e) => { | |
const columnName = $(e).find('textarea.list-header-name').text() | |
const buttonExtras = $(e).find('a.list-header-extras-menu') | |
buttonExtras.click( () => _cacheLastColumnName = columnName ) | |
}) | |
try { | |
actionListObserver.disconnect() | |
} catch {} | |
// Select the node that will be observed for mutations | |
targetNode = $('div.pop-over').get(0); | |
// Create an observer instance linked to the callback function | |
actionListObserver = new MutationObserver(callbackListActions); | |
// Start observing the target node for configured mutations | |
actionListObserver.observe(targetNode, observerConfig); | |
console._debug("Mutation observers has been attached.") | |
}) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment