Skip to content

Instantly share code, notes, and snippets.

@yurighensev
Last active May 10, 2023 15:44
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save yurighensev/c638e18f394a7bf8530ad2afdfa457ff to your computer and use it in GitHub Desktop.
Save yurighensev/c638e18f394a7bf8530ad2afdfa457ff to your computer and use it in GitHub Desktop.
archidekt deck page improvements
// ==UserScript==
// @name Archidekt deck page improvements
// @namespace http://tampermonkey.net/
// @version 0.1
// @description try to take over the world!
// @author You
// @include *archidekt.com/decks/*
// @grant GM_log
// @require https://code.jquery.com/jquery-3.5.1.min.js
// @updateURL https://gist.github.com/yurighensev/c638e18f394a7bf8530ad2afdfa457ff
// ==/UserScript==
$(document).ready(function() {
const startFilterCountUpdateLoop = () => {
var el = document.createElement('span')
el.style = 'width: 10px; margin-top: 22px'
var group = document.querySelector('div[class^=deckFilters_group]')
group.append(el)
setInterval(() => {
let sum = 0
document.querySelectorAll('#inner_stack_container .imageCard_container__Kv4_c .cornerQuantity_quantity__dx7jg')
.forEach((e) => sum += Number(e.innerText))
el.innerText = sum
}, 1000)
}
const sleep = (ms) => new Promise(resolve => setTimeout(resolve, ms))
const waitPageLoadAndInstall = async () => {
// main and deck errors loaders must be gone
while ($('div.ui.tiny.active.inline.loader').length > 0 ||
$('div.ui.active.inverted.dimmer').length > 0) {
console.log("sleeping waiting for loaders to hide...")
await sleep(1000)
}
while (document.querySelector('div[class^=deckFilters_group]') === null) {
console.log("sleeping waiting for deckFilters_group...")
await sleep(1000)
}
startFilterCountUpdateLoop()
}
waitPageLoadAndInstall();
})
function old() {
var searchInput = () => $('#StyledRecommendationTab').find('form input[type="text"].prompt')
var isCtrlEnter = (event) => (event.keyCode == 10 || event.keyCode == 13) && event.ctrlKey
// ctrl+enter on search input clicks the first '+' button found
searchInput().on('keydown', function(e) {
if (isCtrlEnter(e)) {
$('#StyledRecommendationTab')
.find('i.plus.icon:first').click()
$(this).select()
}
})
//===================
var errorCardsCount = (parent = 'body') => $(parent).find('div[name="ErrorCard"]').length
var startActualDeckSizeUpdateLoop = () => {
var deckSizeHolder = () => $('div.meta:first').next().find('span:first')
var deckSize = () => parseInt(deckSizeHolder().text()) || 0
var createActualDeckSizeHolders = () => {
deckSizeHolder().after(`Actual Deck Size: <strong><span class="actualDeckSize sc-dXfzlN BPnfY"></span>`)
$('body').append(`<div style="z-index: 999; position: absolute; bottom: 0; right: 3px; border: 2px solid #517ca1; background-color: #ccc; width: 125px; height: 20px; font-size: 12px; padding: 0 4px">
Actual Deck Size <strong class="actualDeckSize"></strong>
</div>`)
}
var findSection = (name) => $(`div.${name.split(' ').join('.')}`)
var toAddCount = () => {
const toAddSection = findSection('To Add')
if (toAddSection.length == 0)
return 0;
const header = toAddSection.find('div > div > h3 > span > span').text()
return parseInt(header.replace('(', '').replace(')', '')) || 0
}
createActualDeckSizeHolders()
setInterval(() => {
// marking as error means marking the card to be removed from the deck
const actualDeckSize = deckSize() - (errorCardsCount() * 2) - toAddCount()
$('.actualDeckSize').text(actualDeckSize)
}, 500)
}
var startActualSectionSizeUpdateLoop = () => {
var extraBasicLandsCount = (cardEls) => {
var count = 0
cardEls.each((i, e) => {
if ($(e).find('div[name="ErrorCard"]').length > 0)
return
const cardCount = parseInt($(e).find('div.corner > div').text()) || 0
count += cardCount - 1
})
return count
}
setInterval(() => {
var sections = $('.DeckContainer > div:first > div > div')
sections.each((i, e) => {
var cardEls = $(e).find('div:first > div.dragSource')
const actualSectionSize = cardEls.length - errorCardsCount(e) + extraBasicLandsCount(cardEls)
var sectionSizeEl = $(e).find('div > div:first > h3 > span span')
sectionSizeEl.text(`(${actualSectionSize})`)
})
}, 500)
}
//===================
var cardsTextForColumn = (column) => document.querySelector(`span[title="${column}"]`).parentElement.parentElement.parentElement.querySelectorAll(`div.TextCard div`)
var cardsList = (column) => {
console.debug('cardsList - ' + column + ' - cardsTextForColumn:', cardsTextForColumn(column))
var cards = []
cardsTextForColumn(column).forEach((e) => {
cards.push(e.innerText.replace(/^\d[^a-zA-Z]*/, ''))
})
return cards
}
var createCopyButton = (column) => {
var copyButton = document.createElement('button')
copyButton.style.zIndex = '999999'
copyButton.textContent = column
copyButton.style.border = 'border: 2px solid #517ca1'
copyButton.style.backgroundColor = '#ccc'
$(copyButton).on('click', () => {
var copiedContent = ''
console.log(cardsList(column))
copyToClipboard(cardsList(column).sort().join("\n"))
})
return copyButton
}
var copyToClipboard = (selectedContent) => {
var $tempClipboardArea = document.createElement('textarea')
document.body.append($tempClipboardArea)
$tempClipboardArea.value = selectedContent
$tempClipboardArea.select()
document.execCommand('copy')
$tempClipboardArea.remove()
}
var cardColumns = () => {
return document.querySelectorAll(".DeckContainer > div > div > div:nth-of-type(1)")
}
var addColumnClickCopyToClipboard = () => {
cardColumns().forEach((col) => {
let span = col.querySelector("div > h4 > span")
if (!span) {
console.error('SCRIPT ERROR: span not found for ', col)
console.log(col)
return
} else {
console.debug('span found', span)
}
span.onclick = () => {
console.debug('span clicked', span)
let colName = span.title
console.log(cardsList(colName))
copyToClipboard(cardsList(colName).sort().join("\n"))
showAlert('column contents copied to clipboard')
}
})
}
//===================
var findStackByDropdown = () => {
var stackBy = '';
document.querySelectorAll('span > span > label > i').forEach((e) => {
if (e.parentElement.innerText == "Stack By") {
stackBy = e.parentElement;
}
})
return stackBy.parentElement.querySelector('div[role="listbox"] > div[role="alert"]')
}
var observeStackByChange = () => {
var observer = new MutationObserver(function(mutations) {
console.debug('mutation observer run')
mutations.forEach(function(mutation) {
console.debug('mutation occurred, type: ' + mutation.type, mutation)
if (mutation.type == 'characterData') {
console.debug('stack by changed')
addColumnClickCopyToClipboard()
}
})
})
console.log('starting to observe stack by changes')
console.debug('stackByDropdown:', findStackByDropdown())
observer.observe(findStackByDropdown(), { characterData: true, attributes: true, childList: true, subtree: true })
}
//===================
var createAlert = () => {
var alertEl = document.createElement('span')
alertEl.setAttribute('style', 'border: 1px solid #ccc; position: absolute; bottom: 0; left: 50px; background: rgb(110, 110, 110); color: #fff; transition: 0.8s; opacity: 0')
alertEl.setAttribute('id', 'alert-el')
document.body.append(alertEl)
}
var showAlert = (msg) => {
var alertEl = document.getElementById('alert-el')
alertEl.textContent = msg
alertEl.style.opacity = 1
setTimeout(() => {
alertEl.style.opacity = 0
}, 1500)
}
//===================
var removeAdBlockerMessage = () => {
const a = document.querySelector('a[href="https://www.patreon.com/archidekt"]')
a.parentElement.parentElement.parentElement.parentElement.remove()
}
const sleep = (ms) => new Promise(resolve => setTimeout(resolve, ms))
const waitPageLoadAndInstall = async () => {
// main and deck errors loaders must be gone
while ($('div.ui.tiny.active.inline.loader').length > 0 ||
$('div.ui.active.inverted.dimmer').length > 0) {
await sleep(500)
}
while (cardColumns().length == 0) {
console.debug('no card columns, sleeping...')
await sleep(500)
}
startActualDeckSizeUpdateLoop()
startActualSectionSizeUpdateLoop()
addColumnClickCopyToClipboard()
observeStackByChange()
createAlert()
console.log("loaded");
//removeAdBlockerMessage() - breaking new interface on load
}
waitPageLoadAndInstall();
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment