// ==UserScript==
// @name [GC] - SDB Contents Collection
// @namespace https://greasyfork.org/en/users/1225524-kaitlin
// @match https://www.grundos.cafe/safetydeposit/*
// @grant GM.setValue
// @grant GM.getValue
// @grant GM.addStyle
// @license MIT
// @version 1.0
// @author Cupkait
// @icon https://i.imgur.com/4Hm2e6z.png
// @description 2/25/2024, 11:26:31 PM
// ==/UserScript==
let collect = false;
let active = false;
const sdbStyle = createSdbStyle();
document.head.appendChild(sdbStyle);
const collectContainer = createCollectContainer();
document.querySelector('main p:nth-child(4)').append(collectContainer);
initialize();
async function initialize() {
collect = await GM.getValue('collect', false);
active = await GM.getValue('active', false);
collect ? showNextButtons() : active ? enableNextPageNavigation() : showEnableButton();
}
function createSdbStyle() {
const style = document.createElement('style');
style.innerHTML = `
.collect-sdb {
text-align: center;
margin: 10px;
}
.collect-sdb a {
background-color: var(--grid_head);
border: 1px solid grey;
padding: 5px 15px;
margin: 10px;
}
`;
return style;
}
function createCollectContainer() {
const container = document.createElement('div');
container.classList.add('collect-sdb');
return container;
}
function showEnableButton() {
collectContainer.append(createButton('Begin SDB Data Collection', () => {
GM.setValue('collect', true).then(showNextButtons);
}));
}
function showNextButtons() {
removeAllButtons();
collectContainer.append(
createButton('Collect full SDB', () => setActiveAndNavigate('https://www.grundos.cafe/safetydeposit/?view=100')),
createButton('Collect quest only', () => setActiveAndNavigate('https://www.grundos.cafe/safetydeposit/?page=1&&max_rarity=89&view=100'))
);
}
function createButton(text, onClick) {
const button = document.createElement('a');
button.textContent = text;
button.addEventListener('click', onClick);
return button;
}
function removeAllButtons() {
while (collectContainer.firstChild) collectContainer.firstChild.remove();
}
async function setActiveAndNavigate(url) {
await Promise.all([GM.setValue('collect', false), GM.setValue('active', true)]);
window.location.href = url;
}
function enableNextPageNavigation() {
removeEnableButton();
collectContainer.append(createButton('Cancel/Restart Collection', cancelCollection));
initTableProcessing();
}
function removeEnableButton() {
const enableButton = collectContainer.querySelector('button');
if (enableButton) enableButton.remove();
}
function appendMessages(messageText) {
const message = document.createElement('p');
message.innerHTML = messageText;
collectContainer.append(message);
}
async function initTableProcessing() {
await processTableData();
displayPageInfo();
setupKeyboardNavigation();
}
async function loadSdbContents() {
return GM.getValue('sdbContents', []);
}
async function saveSdbContents(contents) {
await GM.setValue('sdbContents', contents);
}
async function processTableData() {
const sdbContents = await loadSdbContents();
const data = document.querySelectorAll('.data');
const rows = [];
for (let i = 0; i < data.length; i += 7) {
const row = createRow(data, i);
const existingItemIndex = sdbContents.findIndex(item => item.n === row.n);
if (existingItemIndex > -1) sdbContents[existingItemIndex] = row;
else sdbContents.push(row);
rows.push(row);
}
await saveSdbContents(sdbContents);
}
function createRow(data, index) {
return {
n: data[index + 1].querySelector('strong').textContent,
r: parseInt(data[index + 1].querySelector('span').textContent.match(/\d+/)[0]),
p: data[index + 2].querySelector('img').src.split('/').pop(),
q: parseInt(data[index + 3].textContent),
t: data[index + 4].querySelector('strong').textContent,
};
}
function setupKeyboardNavigation() {
document.addEventListener('keydown', (event) => {
if (event.key === 'ArrowRight' && !['INPUT', 'TEXTAREA'].includes(document.activeElement.tagName)) {
const nextPageLink = [...document.querySelectorAll('.center a')].find(link => link.textContent.trim().startsWith('Next'));
if (nextPageLink) nextPageLink.click();
}
});
}
async function displayPageInfo() {
const pageCount = document.querySelectorAll('#page option').length;
const currentPage = parseInt(new URLSearchParams(window.location.search).get('page')) || 1;
const sdbContents = await loadSdbContents();
const totalItems = sdbContents.length;
const endTotal = parseFloat(document.querySelector('.center').childNodes[4].textContent.replace(/[^0-9.]/g, '').replace(/,/g, ''));
appendMessages(`Total items collected: <strong>${totalItems.toLocaleString()}</strong> <br>You are viewing page <strong>${currentPage.toLocaleString()}</strong> / <strong>${pageCount.toLocaleString()}</strong>.`);
appendMessages(`Click "Next" or press the right arrow key to go to the next page.`);
if (totalItems === endTotal) appendExportButtons();
}
function appendExportButtons() {
collectContainer.append(createButton('Export to CSV', exportToCSV), createButton('Copy to Clipboard', copyToClipboard));
appendMessages(`Export to CSV to make a spreadsheet of the results. Copy to Clipboard to paste into a Virtupets.net Checklist.`)
}
function exportToCSV() {
loadSdbContents().then(sdbContents => {
const csvContent = "data:text/csv;charset=utf-8," + sdbContents.map(e => Object.values(e).join(",")).join("\n");
const link = document.createElement("a");
link.setAttribute("href", encodeURI(csvContent));
link.setAttribute("download", "sdbContents.csv");
document.body.appendChild(link);
link.click();
link.remove();
displayCompletionMessage();
});
}
function copyToClipboard() {
loadSdbContents().then(sdbContents => {
navigator.clipboard.writeText(JSON.stringify(sdbContents)).then(displayCompletionMessage).catch(err => {
console.error('Could not copy text: ', err);
});
});
}
function displayCompletionMessage() {
let message = collectContainer.querySelector('.completion-message');
let button = collectContainer.querySelector('button');
button.textContent = 'Done Collecting'
if (!message) {
message = document.createElement('p');
message.classList.add('completion-message');
collectContainer.append(message);
}
message.innerHTML = 'Action complete! Press "Done Collecting" to return to your usual SDB view.';
}
async function cancelCollection() {
await Promise.all([GM.setValue('active', false), GM.setValue('sdbContents', [])]);
window.location.href = 'https://www.grundos.cafe/safetydeposit/?view=100';
}