-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathcode.js
More file actions
125 lines (125 loc) · 5.8 KB
/
Copy pathcode.js
File metadata and controls
125 lines (125 loc) · 5.8 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
(() => {
'use strict';
let arm9FileName = null;
let armDataView = null;
const ARM_OFFSETS = {
"Rain Slot": 0x082B80,
"Snow Slot": 0x082B78,
"Flashing Camera Slot": 0x08BBC0
};
const COURSE_REFERENCE = [
"1 - gcn yoshi circuit", "2 - old_mario_gc", "3 - luigi_course", "4 - dokan_course",
"5 - test1_course", "6 - donkey_course", "7 - wario_course", "8 - nokonoko_course",
"9 - gcn baby park", "10 - snes mario circuit 1", "11 - n64 moo mario farm",
"12 - gba bowser castle 2", "13 - gba peach circuit", "14 - gcn luigi circuit",
"15 - snes koopa beach 2", "16 - n64 frappe snowland (snow default)", "17 - tick-tock clock",
"18 - luigi's mansion", "19 - airship fortress", "20 - figure-8 circuit",
"21 - test_circle", "22 - yoshi falls", "23 - n64 banshee boardwalk", "24 - shroom ridge",
"25 - mario circuit", "26 - peach gardens", "27 - desert hills", "28 - delfino square",
"29 - rainbow road", "30 - dk pass", "31 - cheep cheep beach", "32 - bowser castle",
"33 - waluigi pinball", "34 - wario stadium (flashing lights default)", "35 - snes donut plains 1",
"36 - n64 choco mountain", "37 - gba luigi circuit (rain default)", "38 - gcn mushroom bridge",
"39 - snes choco island 2", "40 - gba sky garden", "41 - mini_block_course", "42 - block fort",
"43 - pipe plaza", "44 - nintendo ds", "45 - twilight house", "46 - palm shore",
"47 - tart top", "48 - mr_stage1", "49 - mr_stage2", "50 - mr_stage3",
"51 - mr_stage4", "52 - award", "53 - staffroll", "54 - staffrolltrue"
];
const elements = {
fileInput: document.getElementById('fileInput'),
btnOpen: document.getElementById('btnOpen'),
btnSave: document.getElementById('btnSave'),
btnHelp: document.getElementById('btnHelp'),
btnRepo: document.getElementById('btnRepo'),
trackList: document.getElementById('trackList'),
courseList: document.getElementById('courseList'),
mainContent: document.getElementById('mainContent')
};
function init() {
populateCourseReference();
bindEvents();
}
function bindEvents() {
elements.btnOpen.addEventListener('click', () => elements.fileInput.click());
elements.btnSave.addEventListener('click', saveFile);
elements.btnHelp.addEventListener('click', showHelp);
elements.btnRepo.addEventListener('click', () => window.open('https://github.com/LandonAndEmma/MKDS-ARM9-Slots-Swapper', '_blank'));
elements.fileInput.addEventListener('change', handleFileOpen);
elements.trackList.addEventListener('change', handleSlotSelection);
}
function populateCourseReference() {
const fragment = document.createDocumentFragment();
COURSE_REFERENCE.forEach(course => {
const li = document.createElement('li');
li.textContent = course;
fragment.appendChild(li);
});
elements.courseList.appendChild(fragment);
}
function refreshTrackList() {
elements.trackList.innerHTML = '';
for (const [trackName, offset] of Object.entries(ARM_OFFSETS)) {
const currentVal = armDataView ? armDataView[offset] : '?';
const option = document.createElement('option');
option.value = offset;
option.text = `${trackName} (Current ID: ${currentVal})`;
elements.trackList.add(option);
}
}
async function handleFileOpen(event) {
const file = event.target.files[0];
if (!file) return;
arm9FileName = file.name;
try {
const arrayBuffer = await file.arrayBuffer();
armDataView = new Uint8Array(arrayBuffer);
refreshTrackList();
elements.btnSave.disabled = false;
elements.mainContent.classList.remove('hidden');
} catch (error) {
alert('Failed to read file: ' + error.message);
}
event.target.value = '';
}
function handleSlotSelection(event) {
const selectedOption = event.target.options[event.target.selectedIndex];
if (!selectedOption) return;
const offset = parseInt(selectedOption.value, 10);
const trackName = Object.keys(ARM_OFFSETS).find(key => ARM_OFFSETS[key] === offset);
const currentVal = armDataView[offset];
const input = prompt(`Enter new course ID (1-54) for ${trackName}:`, currentVal);
if (input !== null) {
const intValue = parseInt(input, 10);
if (!isNaN(intValue) && intValue >= 1 && intValue <= 54) {
armDataView[offset] = intValue;
alert(`Success! ${trackName} updated to ID: ${intValue}`);
} else {
alert('Invalid input. Course ID must be a number between 1 and 54.');
}
}
refreshTrackList();
elements.trackList.selectedIndex = -1;
}
function saveFile() {
if (!armDataView || !arm9FileName) return;
const blob = new Blob([armDataView], { type: 'application/octet-stream' });
const url = URL.createObjectURL(blob);
const a = document.createElement('a');
a.href = url;
a.download = arm9FileName;
document.body.appendChild(a);
a.click();
document.body.removeChild(a);
URL.revokeObjectURL(url);
}
function showHelp() {
alert(
"MKDS ARM9 Slot Swapper\n\n" +
"1. Click 'Open arm9.bin' and select your file.\n" +
"2. Click a slot in the dropdown list to edit its course ID.\n" +
"3. Enter a valid ID (1-54) based on the provided reference list.\n" +
"4. Click 'Save' to download your modified file.\n\n" +
"Documentation: Southport\nCode by Landon & Emma"
);
}
init();
})();