v0.14.21 - Show purchasable (buy) items in gearSummary

- logGearSummary() now shows 3 sources: 🟢 equipped, 📦 stored, 🛒 purchasable
- Highlights buy items NOT already in armory inventory
- Summary: Gear DB: 746 total (7 🟢 equipped, 305 📦 stored, 434 🛒 purchasable)
- Works with manual HV.scrapeGear() call on Purchase page
This commit is contained in:
GaboGG 2026-07-27 20:54:16 -04:00
parent 5286f66b3e
commit 229d81b86c
5 changed files with 39 additions and 21 deletions

View file

@ -1,7 +1,7 @@
// ==UserScript== // ==UserScript==
// @name HV Unified // @name HV Unified
// @namespace hvunified // @namespace hvunified
// @version 0.14.20 // @version 0.14.21
// @description HV Unified — battle automation, guidance, and UI enhancements for HentaiVerse // @description HV Unified — battle automation, guidance, and UI enhancements for HentaiVerse
// @author GaboGG + Hermes // @author GaboGG + Hermes
// @match *://*.hentaiverse.org/* // @match *://*.hentaiverse.org/*
@ -17,7 +17,7 @@
// CONFIG — default settings // CONFIG — default settings
// ═══════════════════════════════════════════════════════════════════════ // ═══════════════════════════════════════════════════════════════════════
const VERSION = '0.14.20'; const VERSION = '0.14.21';
const CFG = { const CFG = {
// — Battle automation // — Battle automation
@ -3312,13 +3312,19 @@ function logGearSummary() {
const db = getGearDB(); const db = getGearDB();
const equipped = db.filter(e => e.source === 'character'); const equipped = db.filter(e => e.source === 'character');
const armory = db.filter(e => e.source === 'armory'); const armory = db.filter(e => e.source === 'armory');
console.log(`%c[HV] 📦 Gear DB: ${db.length} total (${equipped.length} equipped, ${armory.length} armory)`, 'color:#0f0'); const buy = db.filter(e => e.source === 'buy');
console.log(`%c[HV] 📦 Gear DB: ${db.length} total (${equipped.length} 🟢 equipped, ${armory.length} 📦 stored, ${buy.length} 🛒 purchasable)`, 'color:#0f0');
equipped.forEach(item => { equipped.forEach(item => {
console.log(` 🗡 [${item.slotType}] ${item.name} (ID: ${item.id}) — ${item.stats ? Object.keys(item.stats).length + ' stats' : 'no stats'}`); console.log(` 🟢 [${item.slotType}] ${item.name} (ID: ${item.id}) — ${item.stats ? Object.keys(item.stats).length + ' stats' : 'no stats'}`);
}); });
armory.forEach(item => { if (buy.length > 0) {
console.log(` 📦 [${item.category}] ${item.name} (ID: ${item.id}) — ${item.stats ? Object.keys(item.stats).length + ' stats' : 'no stats'}`); const used = new Set(armory.map(i => i.id).concat(equipped.filter(i => i.id).map(i => i.id)));
const newOnly = buy.filter(i => !used.has(i.id));
console.log(`%c 🛒 ${buy.length} purchasable (${newOnly.length} not in armory)`, 'color:#0f0');
newOnly.slice(0, 5).forEach(item => {
console.log(` 💰 ${item.name}${item.price || '?'}${item.stats ? ' (' + Object.keys(item.stats).length + ' stats)' : ''}`);
}); });
}
} }
// ── Parse tooltip HTML string into structured stats ── // ── Parse tooltip HTML string into structured stats ──

View file

@ -1,7 +1,7 @@
// ==UserScript== // ==UserScript==
// @name HV Unified // @name HV Unified
// @namespace hvunified // @namespace hvunified
// @version 0.14.20 // @version 0.14.21
// @description HV Unified — battle automation, guidance, and UI enhancements for HentaiVerse // @description HV Unified — battle automation, guidance, and UI enhancements for HentaiVerse
// @author GaboGG + Hermes // @author GaboGG + Hermes
// @match *://*.hentaiverse.org/* // @match *://*.hentaiverse.org/*
@ -17,7 +17,7 @@
// CONFIG — default settings // CONFIG — default settings
// ═══════════════════════════════════════════════════════════════════════ // ═══════════════════════════════════════════════════════════════════════
const VERSION = '0.14.20'; const VERSION = '0.14.21';
const CFG = { const CFG = {
// — Battle automation // — Battle automation
@ -3312,13 +3312,19 @@ function logGearSummary() {
const db = getGearDB(); const db = getGearDB();
const equipped = db.filter(e => e.source === 'character'); const equipped = db.filter(e => e.source === 'character');
const armory = db.filter(e => e.source === 'armory'); const armory = db.filter(e => e.source === 'armory');
console.log(`%c[HV] 📦 Gear DB: ${db.length} total (${equipped.length} equipped, ${armory.length} armory)`, 'color:#0f0'); const buy = db.filter(e => e.source === 'buy');
console.log(`%c[HV] 📦 Gear DB: ${db.length} total (${equipped.length} 🟢 equipped, ${armory.length} 📦 stored, ${buy.length} 🛒 purchasable)`, 'color:#0f0');
equipped.forEach(item => { equipped.forEach(item => {
console.log(` 🗡 [${item.slotType}] ${item.name} (ID: ${item.id}) — ${item.stats ? Object.keys(item.stats).length + ' stats' : 'no stats'}`); console.log(` 🟢 [${item.slotType}] ${item.name} (ID: ${item.id}) — ${item.stats ? Object.keys(item.stats).length + ' stats' : 'no stats'}`);
}); });
armory.forEach(item => { if (buy.length > 0) {
console.log(` 📦 [${item.category}] ${item.name} (ID: ${item.id}) — ${item.stats ? Object.keys(item.stats).length + ' stats' : 'no stats'}`); const used = new Set(armory.map(i => i.id).concat(equipped.filter(i => i.id).map(i => i.id)));
const newOnly = buy.filter(i => !used.has(i.id));
console.log(`%c 🛒 ${buy.length} purchasable (${newOnly.length} not in armory)`, 'color:#0f0');
newOnly.slice(0, 5).forEach(item => {
console.log(` 💰 ${item.name}${item.price || '?'}${item.stats ? ' (' + Object.keys(item.stats).length + ' stats)' : ''}`);
}); });
}
} }
// ── Parse tooltip HTML string into structured stats ── // ── Parse tooltip HTML string into structured stats ──

View file

@ -2,7 +2,7 @@
// CONFIG — default settings // CONFIG — default settings
// ═══════════════════════════════════════════════════════════════════════ // ═══════════════════════════════════════════════════════════════════════
const VERSION = '0.14.20'; const VERSION = '0.14.21';
const CFG = { const CFG = {
// — Battle automation // — Battle automation

View file

@ -41,13 +41,19 @@ function logGearSummary() {
const db = getGearDB(); const db = getGearDB();
const equipped = db.filter(e => e.source === 'character'); const equipped = db.filter(e => e.source === 'character');
const armory = db.filter(e => e.source === 'armory'); const armory = db.filter(e => e.source === 'armory');
console.log(`%c[HV] 📦 Gear DB: ${db.length} total (${equipped.length} equipped, ${armory.length} armory)`, 'color:#0f0'); const buy = db.filter(e => e.source === 'buy');
console.log(`%c[HV] 📦 Gear DB: ${db.length} total (${equipped.length} 🟢 equipped, ${armory.length} 📦 stored, ${buy.length} 🛒 purchasable)`, 'color:#0f0');
equipped.forEach(item => { equipped.forEach(item => {
console.log(` 🗡 [${item.slotType}] ${item.name} (ID: ${item.id}) — ${item.stats ? Object.keys(item.stats).length + ' stats' : 'no stats'}`); console.log(` 🟢 [${item.slotType}] ${item.name} (ID: ${item.id}) — ${item.stats ? Object.keys(item.stats).length + ' stats' : 'no stats'}`);
}); });
armory.forEach(item => { if (buy.length > 0) {
console.log(` 📦 [${item.category}] ${item.name} (ID: ${item.id}) — ${item.stats ? Object.keys(item.stats).length + ' stats' : 'no stats'}`); const used = new Set(armory.map(i => i.id).concat(equipped.filter(i => i.id).map(i => i.id)));
const newOnly = buy.filter(i => !used.has(i.id));
console.log(`%c 🛒 ${buy.length} purchasable (${newOnly.length} not in armory)`, 'color:#0f0');
newOnly.slice(0, 5).forEach(item => {
console.log(` 💰 ${item.name}${item.price || '?'}${item.stats ? ' (' + Object.keys(item.stats).length + ' stats)' : ''}`);
}); });
}
} }
// ── Parse tooltip HTML string into structured stats ── // ── Parse tooltip HTML string into structured stats ──

View file

@ -1,7 +1,7 @@
// ==UserScript== // ==UserScript==
// @name HV Unified // @name HV Unified
// @namespace hvunified // @namespace hvunified
// @version 0.14.20 // @version 0.14.21
// @description HV Unified — battle automation, guidance, and UI enhancements for HentaiVerse // @description HV Unified — battle automation, guidance, and UI enhancements for HentaiVerse
// @author GaboGG + Hermes // @author GaboGG + Hermes
// @match *://*.hentaiverse.org/* // @match *://*.hentaiverse.org/*