Access local variables and more fun features. Shift + L (VM), Shift + Y (Tweaks). Hook by ginger
// ==UserScript==
// @name Capture Client Beta
// @version 1.3
// @description Access local variables and more fun features. Shift + L (VM), Shift + Y (Tweaks). Hook by ginger
// @author Цветочек Кактус (timofeycacti)
// @match https://*.bloxd.io/*
// @namespace CaptureClient
// @license CC-BY-2.0
// @icon https://i.postimg.cc/XJFnxv3m/Capture-Client-v1-(3).png
// @grant none
// @run-at document-start
// ==/UserScript==
(function() {
'use strict';
// === 1. ОРИГИНАЛЬНЫЙ СЕТЕВОЙ ХУК ===
let packetDelayActive = false;
const originalSend = WebSocket.prototype.send;
WebSocket.prototype.send = function(data) {
if (packetDelayActive) {
let isPing = false;
if (typeof data === 'string') {
if (data === '{}' || data.includes('ping') || data.length < 15) {
isPing = true;
}
} else if (data instanceof ArrayBuffer || ArrayBuffer.isView(data)) {
let buffer = data.buffer || data;
if (buffer.byteLength <= 8) {
isPing = true;
}
}
if (!isPing) return;
}
return originalSend.apply(this, arguments);
};
function initClient() {
let font = document.createElement('link');
font.href = 'https://fonts.googleapis.com/css2?family=Lobster&display=swap';
font.rel = 'stylesheet';
document.head.appendChild(font);
let style = document.createElement('style');
style.textContent = `
@font-face { font-family: 'Lobster'; }
@keyframes spin{to{transform:rotate(360deg)}}
.Crosshair{display:inline-block;animation:spin 1s linear infinite}
@keyframes hudRotate { from { background-position: 0% 50%; } to { background-position: 100% 50%; } }
@keyframes flash { 0%, 100% { color:#FFF176 } 50% { color:#660000 } }
.changed { animation: flash 0.4s ease }
.vm-item { padding:3px 4px; cursor:pointer; color:#FFF176; white-space:pre-wrap; word-break:break-word; user-select: none; }
.vm-item:hover { color:#FFFFFF; background:rgba(255,255,255,0.08); }
.btn { background: rgba(255, 241, 118, 0.15); color: #FFF176; border: 1px solid #FFF176; padding: 5px; margin: 5px 0; text-align: center; cursor: pointer; font-family: monospace; font-weight: bold; user-select: none; transition: background 0.2s, color 0.2s; }
.btn:hover { background: #FFF176; color: #330000; }
.btn.active { background: rgba(76, 175, 80, 0.3); color: #4CAF50; border-color: #4CAF50; }
.btn.active:hover { background: #4CAF50; color: #fff; border-color: #4CAF50; }
.vm-search-box { display: flex; padding: 4px; background: rgba(0,0,0,0.4); border-bottom: 1px solid rgba(255, 241, 118, 0.3); gap: 4px; }
.vm-input { flex: 1; background: rgba(0,0,0,0.6); border: 1px solid #FFF176; color: #FFF176; font-family: monospace; font-size: 12px; padding: 2px 4px; outline: none; }
.vm-checkbox-label { color: #FFF176; font-family: monospace; font-size: 11px; display: flex; align-items: center; gap: 3px; cursor: pointer; user-select: none; }
.vm-checkbox-label input { cursor: pointer; accent-color: #FFF176; margin: 0; }
`;
document.head.appendChild(style);
let vmOpen = false, vmBox, vmPath = [], vmCurrent;
let tweaksOpen = false, tweaksBox;
let vmSearchQuery = '', vmDeepSearchEnabled = false;
let tracked = JSON.parse(localStorage.getItem('capture_tracked') || '{}');
let lastValues = {};
function saveTracked() {
localStorage.setItem('capture_tracked', JSON.stringify(tracked));
}
function makeDraggable(header, box) {
let isDown = false, ox = 0, oy = 0;
header.addEventListener('mousedown', e => {
isDown = true;
ox = e.clientX - box.offsetLeft;
oy = e.clientY - box.offsetTop;
});
document.addEventListener('mousemove', e => {
if (isDown) {
box.style.left = (e.clientX - ox) + 'px';
box.style.top = (e.clientY - oy) + 'px';
}
});
document.addEventListener('mouseup', () => { isDown = false; });
}
let trackerBox = document.createElement('div');
Object.assign(trackerBox.style, {
position: 'fixed', right: '10px', bottom: '10px', color: '#FFF176',
fontFamily: 'monospace', fontSize: '12px', zIndex: 99999,
textAlign: 'right', pointerEvents: 'none', maxWidth: '300px', wordBreak: 'break-word'
});
document.body.appendChild(trackerBox);
function getSafeValue(obj, key) {
try { return (obj && typeof obj === 'object') ? obj[key] : undefined; } catch { return undefined; }
}
function findBloxdCaptured() {
try {
let crosshair = document.querySelector(".Crosshair");
if (!crosshair) return null;
let reactKey = Object.keys(crosshair).find(key => key.startsWith('__reactFiber$'));
if (!reactKey) return null;
let searchFiber = f => f?.memoizedState?.bloxd || searchFiber(f?.next);
let noa = Object.values(searchFiber(crosshair[reactKey].return.memoizedState))[2];
return noa;
} catch (e) {
return null;
}
}
setInterval(() => {
if (!window.Captured) return;
trackerBox.innerHTML = '';
let entries = Object.entries(tracked);
for (let i = 0; i < entries.length; i++) {
let [pathStr, path] = entries[i];
try {
let val = window.Captured;
for (let j = 0; j < path.length; j++) {
val = getSafeValue(val, path[j]);
}
let line = document.createElement('div');
line.textContent = `${pathStr}: ${val}`;
if (lastValues[pathStr] !== undefined && lastValues[pathStr] !== val) {
line.className = 'changed';
}
lastValues[pathStr] = val;
trackerBox.appendChild(line);
} catch {}
}
}, 200);
function setValue(path, val) {
try {
let obj = window.Captured;
for (let i = 0; i < path.length - 1; i++) {
obj = getSafeValue(obj, path[i]);
}
let key = path[path.length - 1];
obj[key] = val;
if (obj[key] !== val) {
Object.defineProperty(obj, key, { value: val, writable: true, configurable: true, enumerable: true });
}
} catch {}
}
function createVmItem(displayKey, value, itemPath) {
let item = document.createElement('div');
item.className = 'vm-item';
let pathStr = itemPath.join('.');
item.textContent = value === null ? `${displayKey} : null` : typeof value === 'object' ? `${displayKey} >` : `${displayKey} : ${value}`;
let handleTrack = (e) => {
e.preventDefault(); e.stopPropagation();
tracked[pathStr] ? delete tracked[pathStr] : tracked[pathStr] = itemPath;
saveTracked();
};
item.onclick = (e) => {
if (e.shiftKey) return handleTrack(e);
e.preventDefault(); e.stopPropagation();
if (value && typeof value === 'object') {
vmPath = [...itemPath];
vmUpdate();
} else if (typeof value === 'boolean') {
setValue(itemPath, !value);
vmUpdate();
} else {
let input = prompt(`Set ${pathStr}`, value);
if (input !== null) {
setValue(itemPath, typeof value === 'number' ? Number(input) : input);
vmUpdate();
}
}
};
item.oncontextmenu = e => { if (e.shiftKey) handleTrack(e); };
return item;
}
function vmRender() {
let box = vmBox._content;
box.innerHTML = '';
if (vmPath.length) {
let back = document.createElement('div');
back.textContent = '[..]';
back.className = 'vm-item';
back.onclick = (e) => { e.preventDefault(); e.stopPropagation(); vmPath.pop(); vmUpdate(); };
box.appendChild(back);
}
let query = vmSearchQuery.toLowerCase().trim();
if (query) {
if (vmDeepSearchEnabled) {
let results = [], visited = new Set();
let stack = [{ obj: vmCurrent, path: [...vmPath], depth: 0 }];
while (stack.length > 0) {
let { obj, path, depth } = stack.pop();
if (depth > 4 || !obj || typeof obj !== 'object' || visited.has(obj)) continue;
visited.add(obj);
try {
let keys = Object.keys(obj);
for (let i = 0; i < keys.length; i++) {
let k = keys[i];
let p = [...path, k];
let val = getSafeValue(obj, k);
if (k.toLowerCase().includes(query) || (val !== null && typeof val !== 'object' && String(val).toLowerCase().includes(query))) {
results.push({ keyPath: p, val: val });
}
if (val && typeof val === 'object') {
stack.push({ obj: val, path: p, depth: depth + 1 });
}
}
} catch {}
}
if (!results.length) {
let empty = document.createElement('div');
Object.assign(empty, { className: 'vm-item', textContent: 'No results found...' });
empty.style.color = '#660000'; box.appendChild(empty);
} else {
results.forEach(res => box.appendChild(createVmItem(res.keyPath.slice(vmPath.length).join('.'), res.val, res.keyPath)));
}
} else {
Object.keys(vmCurrent || {}).forEach(k => {
let val = getSafeValue(vmCurrent, k);
if (k.toLowerCase().includes(query) || (val !== null && typeof val !== 'object' && String(val).toLowerCase().includes(query))) {
box.appendChild(createVmItem(k, val, [...vmPath, k]));
}
});
}
} else {
Object.keys(vmCurrent || {}).forEach(k => {
box.appendChild(createVmItem(k, getSafeValue(vmCurrent, k), [...vmPath, k]));
});
}
}
function vmUpdate() {
try {
let val = window.Captured;
for (let i = 0; i < vmPath.length; i++) {
val = getSafeValue(val, vmPath[i]);
}
vmCurrent = val;
} catch { vmPath = []; vmCurrent = window.Captured; }
vmRender();
}
function setupUiIsolation(el) {
['mousedown', 'mouseup', 'click', 'contextmenu'].forEach(evt => {
el.addEventListener(evt, e => {
if (!e.target.closest('[style*="cursor: move"]') && !e.shiftKey) e.stopPropagation();
});
});
}
function vmToggle() {
vmOpen = !vmOpen;
if (vmOpen) {
vmBox = document.createElement('div');
Object.assign(vmBox.style, {
position: 'fixed', top: '20px', left: '20px', width: '320px', color: '#FFF176', zIndex: 99999,
border: '2px solid #FFF176', background: 'linear-gradient(270deg,#330000,#000,#330000)',
backgroundSize: '400% 400%', animation: 'hudRotate 8s linear infinite', display: 'flex', flexDirection: 'column'
});
let header = document.createElement('div');
header.textContent = 'Capture Client';
Object.assign(header.style, { background: '#FFF176', color: '#330000', padding: '5px', cursor: 'move', textAlign: 'center', fontFamily: 'Lobster' });
let searchBar = document.createElement('div');
searchBar.className = 'vm-search-box';
let input = document.createElement('input');
Object.assign(input, { type: 'text', className: 'vm-input', placeholder: 'Search keys or values...', value: vmSearchQuery });
['keydown', 'keyup', 'keypress'].forEach(evt => input.addEventListener(evt, e => e.stopPropagation()));
input.addEventListener('input', e => { vmSearchQuery = e.target.value; vmRender(); });
let label = document.createElement('label');
label.className = 'vm-checkbox-label';
let checkbox = document.createElement('input');
Object.assign(checkbox, { type: 'checkbox', checked: vmDeepSearchEnabled });
checkbox.addEventListener('change', e => { vmDeepSearchEnabled = e.target.checked; vmRender(); });
label.append(checkbox, "Deep");
searchBar.append(input, label);
let content = document.createElement('div');
Object.assign(content.style, { padding: '5px', overflow: 'auto', maxHeight: '320px', fontFamily: 'monospace' });
vmBox.append(header, searchBar, content);
document.body.appendChild(vmBox);
vmBox._content = content;
vmPath = []; vmUpdate();
makeDraggable(header, vmBox);
setupUiIsolation(vmBox);
} else vmBox.remove();
}
function getExportGeometry() {
let targetScene = null;
let visited = new Set();
let stack = [{ obj: window, depth: 0 }];
while (stack.length > 0) {
let { obj, depth } = stack.pop();
if (depth > 5 || !obj || typeof obj !== 'object' || visited.has(obj)) continue;
visited.add(obj);
if (obj._isScene && obj.meshes) {
targetScene = obj;
break;
}
try {
let keys = Object.keys(obj);
for (let i = 0; i < keys.length; i++) {
stack.push({ obj: obj[keys[i]], depth: depth + 1 });
}
} catch {}
}
if (!targetScene && window.Captured) {
targetScene = window.Captured.scene || window.Captured.engine?.scenes?.[0];
}
if (!targetScene) return null;
let meshes = targetScene.meshes || [];
let allVertices = [], allFaces = [], vertexOffset = 0;
meshes.forEach((mesh) => {
if (!mesh || typeof mesh.isEnabled !== 'function' || !mesh.isEnabled()) return;
let meshName = (mesh.name || "").toLowerCase();
if (!meshName.includes("chunk") && !meshName.includes("render") && !meshName.includes("terrain")) return;
if (['sky', 'shadow', 'ui', 'menu', 'atmosphere'].some(w => meshName.includes(w))) return;
let geom = mesh._geometry || mesh.geometry;
if (!geom) return;
let positions = geom._positions || geom.positions || (mesh.getVerticesData ? mesh.getVerticesData("position") : null);
let indices = geom._indices || geom.indices || (mesh.getIndices ? mesh.getIndices() : null);
if (!positions || !indices || positions.length < 12) return;
let dx = 0, dy = 0, dz = 0, useMatrix = false;
let m = [1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1];
let wm = mesh.getWorldMatrix ? mesh.getWorldMatrix() : mesh._worldMatrix;
if (wm) {
let raw = typeof wm.asArray === 'function' ? wm.asArray() : (wm._m || wm);
if (raw && !isNaN(raw[12])) { m = raw; useMatrix = true; }
}
if (!useMatrix) {
dx = mesh.position?.x || mesh.chunkX || 0;
dy = mesh.position?.y || mesh.chunkY || 0;
dz = mesh.position?.z || mesh.chunkZ || 0;
}
let cx = mesh.chunkX || dx || 0, cz = mesh.chunkZ || dz || 0;
let r = Math.abs(Math.sin(cx * 0.05)) * 0.6 + 0.2;
let g = Math.abs(Math.cos(cz * 0.05)) * 0.6 + 0.3;
let b = Math.abs(Math.sin((cx + cz) * 0.03)) * 0.5 + 0.5;
for (let i = 0; i < indices.length; i += 3) {
let i1 = indices[i], i2 = indices[i+1], i3 = indices[i+2];
[i1, i2, i3].forEach(idx => {
let x = positions[idx * 3], y = positions[idx * 3 + 1], z = positions[idx * 3 + 2];
let rx, ry, rz;
if (useMatrix) {
rx = x * m[0] + y * m[4] + z * m[8] + m[12];
ry = x * m[1] + y * m[5] + z * m[9] + m[13];
rz = x * m[2] + y * m[6] + z * m[10] + m[14];
} else {
rx = x + dx; ry = y + dy; rz = z + dz;
}
allVertices.push({x: rx, y: ry, z: rz, r: Math.floor(r*255), g: Math.floor(g*255), b: Math.floor(b*255)});
});
allFaces.push([vertexOffset, vertexOffset + 1, vertexOffset + 2]);
vertexOffset += 3;
}
});
return { vertices: allVertices, faces: allFaces };
}
const tweaksConfig = {
forceInject: {
name: 'Force Inject',
type: 'action',
callback: () => {
let cap = findBloxdCaptured();
if (cap) {
window.Captured = cap;
if (vmOpen) vmUpdate();
}
}
},
toggleLag: {
name: 'Packet Lag: OFF',
type: 'action',
callback: function() {
packetDelayActive = !packetDelayActive;
this.name = `Packet Lag: ${packetDelayActive ? 'ON' : 'OFF'}`;
let buttons = document.querySelectorAll('.btn');
buttons.forEach(btn => {
if (btn.textContent.includes('Packet Lag')) {
btn.textContent = this.name;
btn.classList.toggle('active', packetDelayActive);
}
});
}
},
exportObj: {
name: 'Export OBJ',
type: 'action',
callback: () => {
let geomData = getExportGeometry();
if (!geomData || geomData.vertices.length === 0) return;
let objLines = ["# Bloxd.io Wireframe\n# Format: OBJ XYZRGB\n"];
geomData.vertices.forEach(v => {
objLines.push(`v ${v.x.toFixed(4)} ${v.y.toFixed(4)} ${v.z.toFixed(4)} ${(v.r / 255).toFixed(4)} ${(v.g / 255).toFixed(4)} ${(v.b / 255).toFixed(4)}`);
});
objLines.push("g map_mesh");
geomData.faces.forEach(f => {
objLines.push(`f ${f[0]+1} ${f[1]+1} ${f[2]+1}`);
});
let blob = new Blob([objLines.join("\n")], { type: "text/plain" });
let url = URL.createObjectURL(blob);
let a = document.createElement("a");
a.href = url;
a.download = "bloxd_wireframe_colors.obj";
document.body.appendChild(a);
a.click();
document.body.removeChild(a);
URL.revokeObjectURL(url);
}
},
allCraft: {
name: 'All Craft',
type: 'action',
callback: () => {
try {
Object.values(window.Captured.bloxd.craftingManager.playerRecipes[1] || {}).forEach(arr => {
if (Array.isArray(arr)) arr.forEach(o => { if (o) delete o.station; });
});
} catch {}
}
},
defineAll: {
name: 'Define All',
type: 'action',
callback: () => {
try {
let visited = new Set();
let stack = [{ obj: window.Captured, depth: 0 }];
let found = null;
while (stack.length > 0) {
let { obj, depth } = stack.pop();
if (depth > 4 || !obj || typeof obj !== 'object' || visited.has(obj)) continue;
visited.add(obj);
if (obj.hasOwnProperty('playerZoom')) {
found = obj;
break;
}
let keys = Object.keys(obj);
for (let i = 0; i < keys.length; i++) {
stack.push({ obj: obj[keys[i]], depth: depth + 1 });
}
}
if (found) {
window.Captured.cBloxdStats = found;
if (vmOpen) vmUpdate();
}
} catch {}
}
},
resetAcc: {
name: 'Reset Acc',
type: 'action',
callback: () => {
try {
[".bloxd.io", location.hostname, ""].forEach(d => {
document.cookie = `__Secure-3PSIDMC=; expires=Thu, 01 Jan 1970 00:00:00 UTC; path=/;${d ? ` domain=${d};` : ''} Secure; SameSite=None`;
});
location.reload();
} catch {}
}
}
};
function renderTweaks() {
let content = tweaksBox._content;
content.innerHTML = '';
Object.keys(tweaksConfig).forEach(key => {
let tweak = tweaksConfig[key];
let btn = document.createElement('div');
btn.className = 'btn';
if (key === 'toggleLag' && packetDelayActive) {
btn.className = 'btn active';
btn.textContent = `Packet Lag: ON`;
} else {
btn.textContent = tweak.name;
}
btn.onclick = (e) => { e.preventDefault(); e.stopPropagation(); tweak.callback.call(tweak); };
content.appendChild(btn);
});
}
function tweaksToggle() {
tweaksOpen = !tweaksOpen;
if (tweaksOpen) {
tweaksBox = document.createElement('div');
Object.assign(tweaksBox.style, {
position: 'fixed', top: '20px', right: '20px', width: '220px', color: '#FFF176', zIndex: 99999,
border: '2px solid #FFF176', background: 'linear-gradient(270deg,#330000,#000,#330000)',
backgroundSize: '400% 400%', animation: 'hudRotate 8s linear infinite', display: 'flex', flexDirection: 'column'
});
let header = document.createElement('div');
header.textContent = 'Tweaks';
Object.assign(header.style, { background: '#FFF176', color: '#330000', padding: '5px', cursor: 'move', textAlign: 'center', fontFamily: 'Lobster' });
let content = document.createElement('div');
content.style.padding = '5px';
tweaksBox._content = content;
tweaksBox.append(header, content);
document.body.appendChild(tweaksBox);
renderTweaks();
makeDraggable(header, tweaksBox);
setupUiIsolation(tweaksBox);
} else tweaksBox.remove();
}
document.addEventListener('keydown', e => {
if (e.target.tagName !== 'INPUT' && e.shiftKey) {
if (e.code === 'KeyL') vmToggle();
if (e.code === 'KeyY') tweaksToggle();
}
});
let checker = setInterval(() => {
let cap = findBloxdCaptured();
if (cap) {
window.Captured = cap;
clearInterval(checker);
let crosshair = document.querySelector(".Crosshair");
if (crosshair) crosshair.innerText = "x";
if (vmOpen) vmUpdate();
}
}, 1000);
}
if (document.readyState === 'loading') {
document.addEventListener('DOMContentLoaded', initClient);
} else {
initClient();
}
})();