GDPS bugfixes and improvements

This commit is contained in:
GDColon 2021-01-14 18:18:19 -05:00
parent 5c98087a1f
commit 87a6ae8eaa
15 changed files with 40 additions and 20 deletions

View file

@ -57,7 +57,7 @@ forms.json is a list of the different icon forms, their ingame filenames, and th
## Misc
Inevitable misc folder
**For level analysis**
**Level Analysis Stuff (in a separate folder)**
blocks.json - The object IDs in the different 'families' of blocks
@ -69,7 +69,11 @@ objectProperties.json - Object property cheatsheet. Low budget version of [AlFas
objects.json - IDs for portals, orbs, triggers, and misc stuff
**Not for level analysis**
**Everything Else**
achievements.json - List of all GD/meltdown/subzero/etc achievements. `parseAchievementPlist.js` automatically creates this file
achievementTypes.json - An object containing different categories of achievements (stars, shards, vault, etc) and how to identify them
colors.json - List of icon colors in RGB format
@ -79,12 +83,16 @@ dragscroll.js - Used on several pages for drag scrolling
level.json - An array of the official GD tracks, and also difficulty face stuff for level searching
parseAchievementPlist.js - A script that reads GD's achievement .plist files and converts it into achievements.json
sampleIcons.json - A pool of icons, one of which will randomly appear when visiting the icon kit. Syntax is [Name, ID, Col1, Col2, Glow],
secretStuff.json - GJP goes here, needed for level leaderboards. Not included in the repo for obvious reasons
settings.js - Tweak small settings here, mainly for local use or GDPS'es
shops.js - A hardcoded list of all the shop icons in GD
sizecheck.js - Excecuted on most pages. Used for the 'page isn't wide enough' message, back button, and a few other things
---

View file

@ -1,9 +1,9 @@
const zlib = require('zlib')
const properties = require('../misc/objectProperties.json')
const init = require('../misc/initialProperties.json')
const colorStuff = require('../misc/colorProperties.json')
const ids = require('../misc/objects.json')
const blocks = require('../misc/blocks.json')
const blocks = require('../misc/analysis/blocks.json')
const colorStuff = require('../misc/analysis/colorProperties.json')
const init = require('../misc/analysis/initialProperties.json')
const properties = require('../misc/analysis/objectProperties.json')
const ids = require('../misc/analysis/objects.json')
module.exports = async (app, req, res, level) => {
let unencrypted = level.data.startsWith('kS') // some gdps'es don't encrypt level data

View file

@ -58,7 +58,8 @@ module.exports = async (app, req, res, api, analyze) => {
else return fs.readFile('./html/level.html', 'utf8', function (err, data) {
let html = data;
level.songName = level.songName.replace(/[^ -~]/g, "") // strip off unsupported characters
let filteredSong = level.songName.replace(/[^ -~]/g, "") // strip off unsupported characters
level.songName = filteredSong || level.songName
let variables = Object.keys(level)
variables.forEach(x => {
let regex = new RegExp(`\\[\\[${x.toUpperCase()}\\]\\]`, "g")

View file

@ -10,10 +10,10 @@ module.exports = async (app, req, res, api, getLevels) => {
let skipRequest = accountMode || foundID
// if you're searching by account id, an intentional error is caused to skip the first request to the gd servers. see i pulled a sneaky on ya. (fuck callbacks man)
request.post(skipRequest ? "" : app.endpoint + 'getGJUsers20.php', skipRequest ? {} : req.gdParams({ str: username }), function (err1, res1, b1) {
let searchResult = foundID ? foundID[0] : (accountMode || err1 || b1 == '-1' || b1.startsWith("<!") || !b1) ? req.params.id : app.parseResponse(b1)[16]
request.post(skipRequest ? "" : app.endpoint + 'getGJUsers20.php', skipRequest ? {} : req.gdParams({ str: username, page: 0 }), function (err1, res1, b1) {
let searchResult = foundID ? foundID[0] : (accountMode || err1 || b1 == '-1' || b1.startsWith("<!") || !b1) ? req.params.id : app.parseResponse(b1.split("|")[0])[16]
if (getLevels) {
req.params.text = foundID ? foundID[1] : app.parseResponse(b1)[2]
return app.run.search(app, req, res)

View file

@ -90,14 +90,14 @@ module.exports = async (app, req, res) => {
}
request.post(app.endpoint + 'getGJLevels21.php', req.gdParams(filters), async function(err, resp, body) {
if (err || !body || body == '-1' || body.startsWith("<!")) return res.send("-1")
let splitBody = body.split('#')
let preRes = splitBody[0].split('|')
let authorList = {}
let songList = {}
let authors = splitBody[1].split('|')
let songs = '~' + splitBody[2]; songs = songs.split('|~1~:').map(x => app.parseResponse(x + '|~1~', '~|~'))
let songs = '~' + splitBody[2]; songs = songs.split(':').map(x => app.parseResponse(x, '~|~'))
songs.forEach(x => {songList[x['~1']] = x['2']})
authors.forEach(x => {

View file

@ -1,7 +1,7 @@
<head>
<script async src="https://www.googletagmanager.com/gtag/js?id=UA-135255146-3"></script><script>window.dataLayer = window.dataLayer || []; function gtag(){dataLayer.push(arguments);}gtag('js', new Date());gtag('config', 'UA-135255146-3');</script>
<title>Online Icon Kit</title>
<link href="../assets/css/iconkit.css?v=1" type="text/css" rel="stylesheet">
<link href="../assets/css/iconkit.css" type="text/css" rel="stylesheet">
<meta name="viewport" content="width=1024">
<meta property="og:description" content="Build and save your very own Geometry Dash icons, right from the internet!">
<meta property="og:title" content="Geometry Dash Online Icon Kit">
@ -432,7 +432,8 @@ fetch('./api/icons').then(res => {
let form = $(this).attr('form') || $(this).attr('colType')
let iconNumber = $(this).attr('num') || $(this).attr('col')
if (iconNumber == 1 || ((form == "cube") && iconNumber <= 4) || ((form.startsWith('color')) && iconNumber <= 3)) return $('#howto').html("Always unlocked")
if (form == "swing") return $('#howto').html("Coming soon™")
else if (iconNumber == 1 || ((form == "cube") && iconNumber <= 4) || ((form.startsWith('color')) && iconNumber <= 3)) return $('#howto').html("Always unlocked")
else if (iconNumber == miniIcon && form == "cube") return $('#howto').html("Legacy mini icon, enable in GD settings")
else if (iconNumber == 13 && form == "cube") return $('#howto').html("Click lock on icon kit")

View file

@ -209,7 +209,7 @@ $('#levelInfo').html($('#levelInfo').html()
if (!'[[UPLOADED]]'.startsWith('[')) {
$('#levelInfo').html($('#levelInfo').html()
.replace('[[PASS]]', `<br>Password: <span style="color:orange">${'[[PASSWORD]]' == '0' ? "No copy" : '[[PASSWORD]]' == 1 ? "Free copy" : '[[PASSWORD]]'}</span>`)
.replace('[[PASS]]', `<br>Password: <span style="color:orange">${'[[PASSWORD]]' == '0' || '[[PASSWORD]]'.startsWith("[") ? "No copy" : '[[PASSWORD]]' == 1 ? "Free copy" : '[[PASSWORD]]'}</span>`)
.replace('[[LOWDETAIL]]', `<br>Low Detail: <span style="color:orange">${[[LDM]] ? "Yes" : "No"}</span>`)
.replace('[[TIME1]]', [[EDITORTIME]] == 0 ? "" : `<br>Editor Time: <span style="color:lightgreen">${colonize([[EDITORTIME]])}</span>`)
.replace('[[TIME2]]', [[TOTALEDITORTIME]] == 0 ? "" : `<br>Editor Time (+copies): <span style="color:lightgreen">${colonize([[TOTALEDITORTIME]])}</span>`)

View file

@ -178,10 +178,12 @@ function Append(firstLoad) {
accID = x.authorID
}
let filteredSong = x.songName.replace(/[^ -~]/g, "")
if (!filteredSong) filteredSong = x.songName
$('#searchBox').append(`<div class="searchresult">
<h1 class="lessspaced pre">${x.name}</h1>
<h2 class="lessSpaced pre smaller inline gdButton ${hasAuthor ? "" : "green unregistered"}">${hasAuthor ? `<a href="../u/${x.author}">By ${x.author}</a>` : `<a href="../search/${x.authorID}?user">By ${x.author}</a>`}</h2><h2 class="inline" style="margin-left: 1.5%; transform:translateY(30%)"> ${x.copiedID == '0' ? "" : '<img class="valign sideSpace" src="../assets/copied.png" height="12%">'}${x.large ? '<img class="valign sideSpaceD" src="../assets/large.png" height="12%">' : ''}</h2>
<h3 class="lessSpaced pre ${x.customSong == 0 ? "blue" : "whatIfItWasPurple"}" style="overflow: hidden;">${x.songName.replace(/[^ -~]/g, "")}</h3>
<h3 class="lessSpaced pre ${x.customSong == 0 ? "blue" : "whatIfItWasPurple"}" style="overflow: hidden; max-height: 19%">${filteredSong}</h3>
<h3 class="lessSpaced">
<img class="valign" src="../assets/time.png" height="14%"> ${x.length}
<img class="valign" src="../assets/download.png" height="14%"> ${x.downloads}

View file

@ -53,7 +53,11 @@ app.use(function(req, res, next) {
req.gdParams = function(obj={}) {
Object.keys(app.config.params).forEach(x => { if (!obj[x]) obj[x] = app.config.params[x] })
let ip = req.headers['x-real-ip'] || req.headers['x-forwarded-for']
return {form: obj, headers: app.config.ipForwarding && ip ? {'x-forwarded-for': ip, 'x-real-ip': ip} : {}}
let params = {form: obj, headers: app.config.ipForwarding && ip ? {'x-forwarded-for': ip, 'x-real-ip': ip} : {}}
for (let sub in app.config.substitutions) {
if (params.form[sub]) { params.form[app.config.substitutions[sub]] = params.form[sub]; delete params.form[sub] }
}
return params
}
next()
})
@ -96,6 +100,7 @@ catch(e) {
app.parseResponse = function (responseBody, splitter) {
if (!responseBody || responseBody == "-1") return {};
if (responseBody.startsWith("\nWarning:")) responseBody = responseBody.split("\n").slice(2).join("\n") // GDPS'es are wild
let response = responseBody.split('#')[0].split(splitter || ':');
let res = {};
for (let i = 0; i < response.length; i += 2) {

View file

@ -4,7 +4,7 @@
module.exports = {
port: 2000, // Port to host website on
endpoint: "http://boomlings.com/database/", // Server endpoint to send requests to
endpoint: "http://boomlings.com/database/", // Server endpoint to send requests to, must end with a slash
params: { // Always send this stuff to the servers
secret: 'Wmfd2893gb7',
@ -22,5 +22,8 @@ module.exports = {
base64descriptions: true, // Are level descriptions encoded in Base64?
xorPasswords: true, // Are level passwords XOR encrypted?
timestampSuffix: " ago", // Suffix to add after timestamps, if any.
substitutions: { // Any parameters that are renamed on the GDPS should be listed here, e.g. { levelID: "abcde" }
// levelID: "oiuyhxp4w9I"
}
}