- gf25036 的博客
《章鱼&游戏之遗忘深渊 · 记忆追寻》html
- @ 2026-4-8 17:41:24
这是html的
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no">
<title>?? 小黄VS白切鸡 · 灵灯绽放版 ??</title>
<style>
* {
box-sizing: border-box;
user-select: none;
-webkit-tap-highlight-color: transparent;
}
body {
margin: 0;
min-height: 100vh;
background: linear-gradient(135deg, #0a1f0a, #030803);
display: flex;
justify-content: center;
align-items: center;
font-family: system-ui, 'Segoe UI', 'Courier New', monospace;
padding: 16px;
}
.game-container {
max-width: 540px;
width: 100%;
background: #1e2a1c;
border-radius: 48px;
padding: 16px;
box-shadow: 0 20px 40px rgba(0,0,0,0.5);
border: 2px solid #9bc47c;
}
.status-bar {
background: #0f180f;
border-radius: 60px;
padding: 10px 12px;
margin-bottom: 16px;
display: flex;
justify-content: space-between;
flex-wrap: wrap;
gap: 8px;
color: #f9f2cf;
}
.stat {
background: #253a22;
padding: 5px 14px;
border-radius: 30px;
font-weight: bold;
font-size: 13px;
display: flex;
align-items: center;
gap: 4px;
}
.loc-name {
background: #2c4527;
padding: 5px 14px;
border-radius: 30px;
font-weight: bold;
font-size: 13px;
}
.map-area {
background: #172015;
border-radius: 32px;
padding: 14px;
margin-bottom: 16px;
}
.map-title {
color: #d8f0bc;
font-size: 13px;
margin-bottom: 10px;
text-align: center;
}
.map-grid {
display: flex;
flex-direction: column;
gap: 8px;
}
.map-row {
display: flex;
justify-content: center;
gap: 8px;
flex-wrap: wrap;
}
.map-node {
background: #2a4028;
border: 2px solid #8faf7a;
color: #fcf9e8;
padding: 8px 10px;
border-radius: 40px;
font-weight: bold;
font-size: 12px;
text-align: center;
cursor: pointer;
min-width: 80px;
transition: 0.05s linear;
}
.map-node.current {
background: #6f9a5c;
border-color: #ffefb0;
box-shadow: 0 0 8px #ffd966;
}
.map-node:active { transform: scale(0.96); background: #5a8748; }
.inventory-area {
background: #111c10;
border-radius: 28px;
padding: 10px 14px;
margin-bottom: 16px;
}
.inv-title {
color: #d8f0bc;
font-size: 12px;
margin-bottom: 6px;
}
.inv-list {
display: flex;
flex-wrap: wrap;
gap: 6px;
min-height: 50px;
}
.inv-item {
background: #2e4b2a;
padding: 5px 12px;
border-radius: 30px;
border: 1px solid #cae2ac;
color: #fffef0;
font-size: 11px;
cursor: pointer;
}
.inv-item:active { background: #4e7848; transform: scale(0.96); }
.npc-area {
background: #0f1a0e;
border-radius: 28px;
padding: 10px 14px;
margin-bottom: 16px;
}
.npc-title {
color: #dfefcd;
font-size: 12px;
margin-bottom: 6px;
}
.npc-list {
display: flex;
flex-wrap: wrap;
gap: 6px;
}
.npc-tag {
background: #26412a;
padding: 5px 14px;
border-radius: 30px;
border: 1px solid #b3d494;
cursor: pointer;
font-size: 12px;
}
.npc-tag:active { background: #4a7346; transform: scale(0.96); }
.log-area {
background: #0a1109;
border-radius: 28px;
padding: 10px;
height: 240px;
overflow-y: auto;
color: #eff7e3;
font-size: 12px;
margin-bottom: 16px;
}
.log-line {
padding: 4px 0;
border-bottom: 1px solid #3a5536;
word-break: break-word;
}
.log-sys { color: #b8f0a0; }
.log-warn { color: #f7bc8c; }
.log-battle { color: #ffcc66; font-weight: bold; }
.btn-bar {
display: flex;
gap: 8px;
margin-bottom: 16px;
flex-wrap: wrap;
}
.btn {
background: #3b5c34;
border: none;
border-radius: 40px;
padding: 8px 0;
font-weight: bold;
color: white;
cursor: pointer;
flex: 1;
text-align: center;
font-size: 13px;
}
.btn:active { transform: scale(0.96); background: #5a8750; }
.btn-danger { background: #6f4e3a; }
.skill-bar {
display: flex;
gap: 6px;
flex-wrap: wrap;
margin-top: 8px;
}
.skill-btn {
background: #4a2e2e;
border: 1px solid #e6bc7e;
border-radius: 40px;
padding: 7px 0;
font-weight: bold;
color: #ffefc0;
cursor: pointer;
flex: 1;
text-align: center;
font-size: 11px;
}
.skill-ult { background: #8b3c3c; }
.skill-btn:active { transform: scale(0.96); background: #7a4a3a; }
.hidden { display: none; }
.pickup-area {
display: flex;
gap: 6px;
flex-wrap: wrap;
margin-top: 8px;
padding: 6px;
background: #1e2e1a;
border-radius: 28px;
}
.pickup-btn {
background: #4a7342;
border: none;
border-radius: 30px;
padding: 5px 12px;
color: white;
font-size: 11px;
cursor: pointer;
}
.energy-highlight {
background: #ffd96633;
border: 1px solid #ffd966;
}
footer {
text-align: center;
color: #8faa7a;
font-size: 10px;
margin-top: 10px;
}
</style>
</head>
<body>
<div class="game-container">
<div class="status-bar">
<span class="stat">?? 小黄 <span id="hpVal">48</span>/48</span>
<span class="stat">?? 灵灯 <span id="energyVal">24</span>/24</span>
<span class="stat">?? 灵晶 <span id="crystalVal">0</span>/5</span>
<span class="loc-name" id="locName">回廊大厅</span>
</div>
<div class="map-area">
<div class="map-title">??? 点击地点移动 (灵灯充足)</div>
<div id="mapContainer" class="map-grid"></div>
</div>
<div class="inventory-area">
<div class="inv-title">?? 背包 (点击使用物品)</div>
<div id="invList" class="inv-list"></div>
</div>
<div class="npc-area">
<div class="npc-title">?? 角色 (点击对话获取线索/增益)</div>
<div id="npcList" class="npc-list"></div>
</div>
<div id="logArea" class="log-area">
<div class="log-line log-sys">✨ 小黄 VS 白切鸡 · 灵灯绽放版 ✨</div>
<div class="log-line">?? 目标:集齐5枚灵晶,前往【玄光出口】决战白切鸡!</div>
<div class="log-line">?? 灵灯增至24点,探索更自由!技能华丽升级!</div>
</div>
<div class="btn-bar">
<button class="btn" id="lookBtn">?? 观察/拾取</button>
<button class="btn" id="bagBtn">?? 查看背包</button>
<button class="btn" id="combineBtn">?? 合成短刃</button>
<button class="btn btn-danger" id="resetBtn">?? 重开游戏</button>
</div>
<div id="skillArea" class="hidden">
<div class="skill-bar">
<button class="skill-btn" id="skill1">?? 崩拳</button>
<button class="skill-btn" id="skill2">?? 疾风连打</button>
<button class="skill-btn" id="skill3">??? 铁壁</button>
<button class="skill-btn skill-ult" id="skillUlt">?? 五灵归一斩</button>
</div>
<div style="font-size:10px; text-align:center; color:#d4b87a; margin-top:5px;">⚡ 普攻/技能消耗1灵灯 · 大招消耗2 | 铁壁回血+减伤</div>
</div>
<footer>✨ 灵灯充沛!多探索可拾取「灵灯甘露」「星辉花」等宝物,战斗更轻松 ✨</footer>
</div>
<script>
(function(){
// ========== 灵灯大幅提升 + 新增丰富道具 ==========
let game = {
locations: ["回廊大厅", "演武厅", "书阁", "幽暗牢房", "星语祭坛", "菌菇洞穴", "灵晶矿脉", "玄光出口"],
exits: {
"回廊大厅": ["演武厅", "书阁", "幽暗牢房"],
"演武厅": ["回廊大厅", "星语祭坛"],
"书阁": ["回廊大厅", "菌菇洞穴"],
"幽暗牢房": ["回廊大厅", "灵晶矿脉"],
"星语祭坛": ["演武厅"],
"菌菇洞穴": ["书阁", "玄光出口"],
"灵晶矿脉": ["幽暗牢房"],
"玄光出口": ["菌菇洞穴"]
},
current: "回廊大厅",
lamp: 24, // 灵灯从12大幅提升至24
maxLamp: 24,
hp: 48, // 血量也略微提升让战斗更爽快
maxHp: 48,
crystals: new Set(),
// 丰富物品列表 (新增两种消耗品)
items: [
{ name: "赤炎灵晶", desc: "🔥 红色灵晶·演武厅", isKey: true, loc: "演武厅", taken: false },
{ name: "霜月灵晶", desc: "❄️ 蓝色灵晶·书阁", isKey: true, loc: "书阁", taken: false },
{ name: "苍翠灵晶", desc: "🌿 绿色灵晶·幽暗牢房", isKey: true, loc: "幽暗牢房", taken: false },
{ name: "紫霄灵晶", desc: "✨ 紫色灵晶·星语祭坛", isKey: true, loc: "星语祭坛", taken: false },
{ name: "曜金灵晶", desc: "🌟 金色灵晶·灵晶矿脉", isKey: true, loc: "灵晶矿脉", taken: false },
{ name: "断刃匕首", desc: "🗡️ 生锈匕首·回廊大厅", isKey: false, loc: "回廊大厅", taken: false },
{ name: "流光磨刀石", desc: "💎 磨刀石·演武厅", isKey: false, loc: "演武厅", taken: false },
{ name: "灵灯余烬", desc: "🪔 恢复3灵灯·书阁", isKey: false, loc: "书阁", taken: false },
{ name: "残破卷轴", desc: "📜 五灵卷轴·星语祭坛", isKey: false, loc: "星语祭坛", taken: false },
{ name: "魂晶碎块", desc: "🧩 交易品·菌菇洞穴", isKey: false, loc: "菌菇洞穴", taken: false },
// 新增丰富道具:灵灯甘露(恢复5灵灯) 和 星辉花(恢复6生命)
{ name: "灵灯甘露", desc: "💧 甘甜露水,恢复5灵灯 · 菌菇洞穴", isKey: false, loc: "菌菇洞穴", taken: false },
{ name: "星辉花", desc: "🌼 夜光花瓣,恢复6生命 · 星语祭坛", isKey: false, loc: "星语祭坛", taken: false }
],
inventory: [],
// NPC 丰富对话和增益
npcs: [
{ name: "黄炎硕", loc: "菌菇洞穴", dialogues: ["白切鸡背叛了五灵!", "用魂晶碎块换情报,可让大招威力飙升。"], specialItem: "魂晶碎块", specialMsg: "白切鸡弱点暴露!五灵归一斩伤害+12!", specialUsed: false, ultBuff: 12 },
{ name: "坤哥", loc: "星语祭坛", dialogues: ["集齐五晶才能对抗白切鸡。", "卷轴记载了五灵归一斩的奥秘。"], specialItem: "残破卷轴", specialMsg: "卷轴力量注入!你的大招伤害永久+10!", specialUsed: false, ultBuff: 10 },
{ name: "章鱼", loc: "灵晶矿脉", dialogues: ["小黄,白切鸡就在出口等你。", "战斗时使用铁壁能撑过狂风暴雨。"], specialItem: null, specialMsg: null, specialUsed: false }
],
inBattle: false,
bossHp: 0,
bossMaxHp: 62, // 稍微提高boss难度但灵灯充裕
gameOver: false,
escaped: false,
ironShieldActive: false,
permanentUltBuff: 0 // 通过NPC永久提升大招伤害
};
// DOM 元素
const logDiv = document.getElementById('logArea');
const hpSpan = document.getElementById('hpVal');
const energySpan = document.getElementById('energyVal');
const crystalSpan = document.getElementById('crystalVal');
const locSpan = document.getElementById('locName');
const mapDiv = document.getElementById('mapContainer');
const invDiv = document.getElementById('invList');
const npcDiv = document.getElementById('npcList');
const skillArea = document.getElementById('skillArea');
function addLog(msg, type='normal') {
const line = document.createElement('div');
line.className = 'log-line';
if (type === 'sys') line.classList.add('log-sys');
else if (type === 'warn') line.classList.add('log-warn');
else if (type === 'battle') line.classList.add('log-battle');
line.innerText = msg;
logDiv.appendChild(line);
logDiv.scrollTop = logDiv.scrollHeight;
while(logDiv.children.length > 55) logDiv.removeChild(logDiv.firstChild);
}
function refreshUI() {
hpSpan.innerText = `${game.hp}/${game.maxHp}`;
energySpan.innerText = `${game.lamp}/${game.maxLamp}`;
crystalSpan.innerText = `${game.crystals.size}/5`;
locSpan.innerText = game.current;
renderMap();
renderInventory();
renderNPCs();
if (game.gameOver) skillArea.classList.add('hidden');
}
function renderMap() {
const rows = [['回廊大厅','演武厅','书阁'], ['幽暗牢房','星语祭坛','菌菇洞穴'], ['灵晶矿脉','玄光出口']];
let html = '';
for (let row of rows) {
html += '<div class="map-row">';
for (let loc of row) {
let cls = 'map-node';
if (loc === game.current) cls += ' current';
html += `<div class="${cls}" data-loc="${loc}">${loc}</div>`;
}
html += '</div>';
}
mapDiv.innerHTML = html;
document.querySelectorAll('.map-node').forEach(el => {
el.addEventListener('click', (e) => {
e.stopPropagation();
if (game.gameOver) { addLog('游戏已结束,请重开', 'warn'); return; }
if (game.inBattle) { addLog('战斗中无法移动!', 'warn'); return; }
const dest = el.dataset.loc;
if (dest === game.current) return;
moveTo(dest);
});
});
}
function renderInventory() {
if (game.inventory.length === 0) {
invDiv.innerHTML = '<span style="color:#8faa7a;">空空如也</span>';
return;
}
let html = '';
for (let item of game.inventory) {
html += `<div class="inv-item" data-item="${item}">✨ ${item}</div>`;
}
invDiv.innerHTML = html;
document.querySelectorAll('.inv-item').forEach(el => {
el.addEventListener('click', (e) => {
e.stopPropagation();
if (game.gameOver || game.inBattle) { addLog('无法使用物品', 'warn'); return; }
useItem(el.dataset.item);
});
});
}
function renderNPCs() {
let here = game.npcs.filter(n => n.loc === game.current);
if (here.length === 0) {
npcDiv.innerHTML = '<span style="color:#8faa7a;">无人在此</span>';
return;
}
let html = '';
for (let n of here) {
html += `<div class="npc-tag" data-npc="${n.name}">${n.name}</div>`;
}
npcDiv.innerHTML = html;
document.querySelectorAll('.npc-tag').forEach(el => {
el.addEventListener('click', (e) => {
e.stopPropagation();
if (game.gameOver || game.inBattle) return;
talkToNPC(el.dataset.npc);
});
});
}
function moveTo(dest) {
if (!game.exits[game.current].includes(dest)) {
addLog(`? 无法从 ${game.current} 前往 ${dest}`, 'warn');
return;
}
if (game.lamp <= 0) {
addLog('灵灯能量耗尽,无法移动!请使用灵灯余烬或甘露', 'warn');
return;
}
game.lamp--;
game.current = dest;
addLog(`🚶 来到 ${dest}`, 'sys');
const desc = {
"回廊大厅":"🏛️ 破败回廊,断刃匕首插在石缝中。",
"演武厅":"🥋 废弃练武场,赤炎灵晶和磨刀石散落。",
"书阁":"📚 尘封书房,霜月灵晶与灵灯余烬在书架上。",
"幽暗牢房":"🔒 阴冷地牢,苍翠灵晶在角落发光。",
"星语祭坛":"🌠 神秘法阵,紫霄灵晶、残破卷轴与星辉花悬浮。",
"菌菇洞穴":"🍄 荧光蘑菇丛,魂晶碎块和灵灯甘露闪耀。",
"灵晶矿脉":"💎 璀璨晶矿,曜金灵晶由章鱼守护。",
"玄光出口":"🚪 封印石门,五枚灵晶凹槽等待共鸣。"
};
addLog(`✨ ${desc[dest] || dest}`);
if (dest === '玄光出口' && game.crystals.size >= 5 && !game.inBattle && !game.gameOver && !game.escaped) {
startBattle();
}
refreshUI();
}
function takeItem(itemName) {
let item = game.items.find(i => i.name === itemName && !i.taken && i.loc === game.current);
if (!item) { addLog(`这里没有 ${itemName}`, 'warn'); return; }
item.taken = true;
game.inventory.push(item.name);
addLog(`🎁 获得 ${item.name}!${item.desc}`);
if (item.isKey) {
game.crystals.add(item.name);
addLog(`💎 灵晶 ${game.crystals.size}/5`, 'sys');
let p = document.getElementById('pickupPanel');
if(p) p.remove();
}
refreshUI();
}
function useItem(itemName) {
if (itemName === '灵灯余烬') {
let rec = Math.min(3, game.maxLamp - game.lamp);
if (rec > 0) {
game.lamp += rec;
game.inventory = game.inventory.filter(i => i !== '灵灯余烬');
addLog(`🪔 灵灯恢复 ${rec} 点能量`);
} else addLog('灵灯已满');
}
else if (itemName === '灵灯甘露') {
let rec = Math.min(5, game.maxLamp - game.lamp);
if (rec > 0) {
game.lamp += rec;
game.inventory = game.inventory.filter(i => i !== '灵灯甘露');
addLog(`💧 饮用甘露,灵灯恢复 ${rec} 点!`);
} else addLog('灵灯能量已满');
}
else if (itemName === '星辉花') {
let rec = Math.min(6, game.maxHp - game.hp);
if (rec > 0) {
game.hp += rec;
game.inventory = game.inventory.filter(i => i !== '星辉花');
addLog(`🌼 星辉花瓣绽放,生命恢复 ${rec} 点!`);
} else addLog('生命已满');
}
else if (itemName === '破晓短刃') {
addLog('🗡️ 破晓短刃寒光闪烁,战斗中伤害+3!(被动生效)');
// 增加被动标记
if (!window.weaponBuff) window.weaponBuff = true;
}
else if (itemName.includes('灵晶')) {
addLog(`${itemName} 散发着灵韵,集齐5枚去玄光出口`);
}
else {
addLog(`使用了 ${itemName},似乎有神秘力量环绕`);
}
refreshUI();
}
function combineWeapon() {
if (game.inventory.includes('断刃匕首') && game.inventory.includes('流光磨刀石')) {
game.inventory = game.inventory.filter(i => i !== '断刃匕首' && i !== '流光磨刀石');
game.inventory.push('破晓短刃');
addLog('⚔️ 合成成功!获得破晓短刃!战斗伤害永久+3', 'sys');
refreshUI();
} else {
addLog('需要同时拥有断刃匕首和流光磨刀石', 'warn');
}
}
function talkToNPC(name) {
let npc = game.npcs.find(n => n.name === name);
if (!npc) return;
if (npc.specialItem && game.inventory.includes(npc.specialItem) && !npc.specialUsed) {
let bonus = npc.ultBuff || 0;
game.permanentUltBuff += bonus;
addLog(`✨ ${npc.name}: 「${npc.specialMsg}」`, 'sys');
game.inventory = game.inventory.filter(i => i !== npc.specialItem);
npc.specialUsed = true;
addLog(`🌟 消耗 ${npc.specialItem},五灵归一斩伤害永久 +${bonus}!`, 'sys');
} else {
let msg = npc.dialogues[Math.floor(Math.random() * npc.dialogues.length)];
addLog(`💬 ${npc.name}: 「${msg}」`);
// 章鱼额外赠送情报
if (npc.name === '章鱼' && !npc.specialUsed) {
addLog(`🐙 章鱼悄悄告诉你:铁壁可以抵挡巨量伤害,灵灯甘露在洞穴深处!`);
}
}
refreshUI();
}
function lookAround() {
let itemsHere = game.items.filter(i => !i.taken && i.loc === game.current);
if (itemsHere.length === 0) {
addLog('这里没有可拾取的物品');
return;
}
let panel = document.getElementById('pickupPanel');
if (panel) panel.remove();
panel = document.createElement('div');
panel.id = 'pickupPanel';
panel.className = 'pickup-area';
for (let item of itemsHere) {
let btn = document.createElement('button');
btn.innerText = `🎒 拾取 ${item.name}`;
btn.className = 'pickup-btn';
btn.onclick = () => takeItem(item.name);
panel.appendChild(btn);
}
document.querySelector('.map-area').after(panel);
}
// ========== 华丽战斗系统 ==========
function startBattle() {
game.inBattle = true;
game.bossHp = game.bossMaxHp;
game.ironShieldActive = false;
addLog('⚔️========================================⚔️', 'battle');
addLog('🐔 白切鸡 挡住了去路!「小黄,今日便是你的末日!」', 'battle');
addLog(`💢 白切鸡 HP: ${game.bossHp}/${game.bossMaxHp}`, 'battle');
addLog('🔥 使用技能栏攻击!灵灯充足,尽情释放!', 'battle');
skillArea.classList.remove('hidden');
refreshUI();
}
function getWeaponBonus() {
let hasBlade = game.inventory.includes('破晓短刃') || (window.weaponBuff === true);
return hasBlade ? 3 : 0;
}
function battleAction(skillName, baseDamage, energyCost, extraEffect = null) {
if (!game.inBattle) return;
if (game.gameOver) return;
if (game.lamp < energyCost) {
addLog(`灵灯不足,无法使用${skillName}!`, 'warn');
return;
}
game.lamp -= energyCost;
let weaponBonus = getWeaponBonus();
let damage = baseDamage + weaponBonus;
// 大招额外永久增益
if (skillName === '五灵归一斩') {
damage += game.permanentUltBuff;
}
let isCrit = Math.random() < 0.2;
if (isCrit) {
damage = Math.floor(damage * 1.5);
addLog(`✨ 暴击一击!`, 'battle');
}
if (extraEffect) extraEffect();
game.bossHp -= damage;
addLog(`💥 小黄使用【${skillName}】造成 ${damage} 伤害!`, 'battle');
if (game.bossHp <= 0) {
addLog('🎉 白切鸡轰然倒下!小黄胜利!深渊解放!恭喜通关!🎉', 'battle');
game.inBattle = false;
game.escaped = true;
game.gameOver = true;
skillArea.classList.add('hidden');
refreshUI();
return;
}
let bossDamage = 8 + Math.floor(Math.random() * 10);
if (skillName === '五灵归一斩') bossDamage = Math.max(4, bossDamage - 6);
if (game.ironShieldActive) {
bossDamage = Math.floor(bossDamage / 2);
addLog(`🛡️ 铁壁减伤生效!`, 'battle');
game.ironShieldActive = false;
}
game.hp -= bossDamage;
addLog(`🐔 白切鸡疯狂反击造成 ${bossDamage} 伤害!`, 'battle');
if (game.hp <= 0) {
game.hp = 0;
addLog(`💀 小黄战败了... 游戏结束,重开再战`, 'battle');
game.inBattle = false;
game.gameOver = true;
skillArea.classList.add('hidden');
refreshUI();
return;
}
addLog(`📊 战况: 白切鸡 ${Math.max(0, game.bossHp)}/${game.bossMaxHp} 小黄 ${game.hp}/${game.maxHp}`, 'battle');
refreshUI();
}
function skill1() { battleAction('崩拳', 12 + Math.floor(Math.random() * 7), 1, null); }
function skill2() {
let baseDmg = 18 + Math.floor(Math.random() * 11);
let extraDmg = 0;
if (Math.random() < 0.25) {
extraDmg = Math.floor(baseDmg * 0.5);
addLog(`🌀 疾风连打触发连击!+${extraDmg}伤害!`, 'battle');
}
battleAction('疾风连打', baseDmg + extraDmg, 1, null);
}
function skill3() {
if (!game.inBattle) return;
if (game.gameOver) return;
if (game.lamp < 1) {
addLog(`灵灯不足,无法使用铁壁!`, 'warn');
return;
}
game.lamp--;
let healAmount = 14;
game.hp = Math.min(game.maxHp, game.hp + healAmount);
addLog(`🛡️ 小黄使用【铁壁】,恢复 ${healAmount} 生命!`, 'battle');
game.ironShieldActive = true;
addLog(`🔰 下回合受到伤害减半!`, 'battle');
let bossDamage = 7 + Math.floor(Math.random() * 6);
if (game.ironShieldActive) {
bossDamage = Math.floor(bossDamage / 2);
addLog(`🛡️ 铁壁减伤生效!`, 'battle');
game.ironShieldActive = false;
}
game.hp -= bossDamage;
addLog(`🐔 白切鸡反击造成 ${bossDamage} 伤害!`, 'battle');
if (game.hp <= 0) {
game.hp = 0;
addLog(`💀 小黄战败...`, 'battle');
game.inBattle = false;
game.gameOver = true;
skillArea.classList.add('hidden');
}
refreshUI();
}
function skillUlt() {
let bonusDamage = game.permanentUltBuff;
battleAction('五灵归一斩', 32 + Math.floor(Math.random() * 20), 2, null);
if (bonusDamage > 0) addLog(`✨ 五灵之力共鸣,额外加持 +${bonusDamage} 伤害!`, 'battle');
}
function resetGame() {
game = {
locations: ["回廊大厅", "演武厅", "书阁", "幽暗牢房", "星语祭坛", "菌菇洞穴", "灵晶矿脉", "玄光出口"],
exits: {
"回廊大厅": ["演武厅", "书阁", "幽暗牢房"],
"演武厅": ["回廊大厅", "星语祭坛"],
"书阁": ["回廊大厅", "菌菇洞穴"],
"幽暗牢房": ["回廊大厅", "灵晶矿脉"],
"星语祭坛": ["演武厅"],
"菌菇洞穴": ["书阁", "玄光出口"],
"灵晶矿脉": ["幽暗牢房"],
"玄光出口": ["菌菇洞穴"]
},
current: "回廊大厅",
lamp: 24,
maxLamp: 24,
hp: 48,
maxHp: 48,
crystals: new Set(),
items: [
{ name: "赤炎灵晶", desc: "🔥 红色灵晶·演武厅", isKey: true, loc: "演武厅", taken: false },
{ name: "霜月灵晶", desc: "❄️ 蓝色灵晶·书阁", isKey: true, loc: "书阁", taken: false },
{ name: "苍翠灵晶", desc: "🌿 绿色灵晶·幽暗牢房", isKey: true, loc: "幽暗牢房", taken: false },
{ name: "紫霄灵晶", desc: "✨ 紫色灵晶·星语祭坛", isKey: true, loc: "星语祭坛", taken: false },
{ name: "曜金灵晶", desc: "🌟 金色灵晶·灵晶矿脉", isKey: true, loc: "灵晶矿脉", taken: false },
{ name: "断刃匕首", desc: "🗡️ 生锈匕首·回廊大厅", isKey: false, loc: "回廊大厅", taken: false },
{ name: "流光磨刀石", desc: "💎 磨刀石·演武厅", isKey: false, loc: "演武厅", taken: false },
{ name: "灵灯余烬", desc: "🪔 恢复3灵灯·书阁", isKey: false, loc: "书阁", taken: false },
{ name: "残破卷轴", desc: "📜 五灵卷轴·星语祭坛", isKey: false, loc: "星语祭坛", taken: false },
{ name: "魂晶碎块", desc: "🧩 交易品·菌菇洞穴", isKey: false, loc: "菌菇洞穴", taken: false },
{ name: "灵灯甘露", desc: "💧 甘甜露水,恢复5灵灯 · 菌菇洞穴", isKey: false, loc: "菌菇洞穴", taken: false },
{ name: "星辉花", desc: "🌼 夜光花瓣,恢复6生命 · 星语祭坛", isKey: false, loc: "星语祭坛", taken: false }
],
inventory: [],
npcs: [
{ name: "黄炎硕", loc: "菌菇洞穴", dialogues: ["白切鸡背叛了五灵!", "用魂晶碎块换情报,可让大招威力飙升。"], specialItem: "魂晶碎块", specialMsg: "白切鸡弱点暴露!五灵归一斩伤害+12!", specialUsed: false, ultBuff: 12 },
{ name: "坤哥", loc: "星语祭坛", dialogues: ["集齐五晶才能对抗白切鸡。", "卷轴记载了五灵归一斩的奥秘。"], specialItem: "残破卷轴", specialMsg: "卷轴力量注入!你的大招伤害永久+10!", specialUsed: false, ultBuff: 10 },
{ name: "章鱼", loc: "灵晶矿脉", dialogues: ["小黄,白切鸡就在出口等你。", "战斗时使用铁壁能撑过狂风暴雨。"], specialItem: null, specialMsg: null, specialUsed: false }
],
inBattle: false,
bossHp: 0,
bossMaxHp: 62,
gameOver: false,
escaped: false,
ironShieldActive: false,
permanentUltBuff: 0
};
window.weaponBuff = false;
logDiv.innerHTML = '';
addLog('✨ 小黄 VS 白切鸡 · 灵灯绽放版 ✨', 'sys');
addLog('🎯 目标:集齐5枚灵晶,前往【玄光出口】决战白切鸡!', 'sys');
addLog('💡 灵灯上限24,新增「灵灯甘露」「星辉花」助你冒险!', 'sys');
skillArea.classList.add('hidden');
let panel = document.getElementById('pickupPanel');
if(panel) panel.remove();
refreshUI();
}
function bindEvents() {
document.getElementById('lookBtn').onclick = () => { if(!game.gameOver && !game.inBattle) lookAround(); else addLog('无法观察', 'warn'); };
document.getElementById('bagBtn').onclick = () => { if(!game.gameOver) addLog(`🎒 背包:${game.inventory.join('、') || '空'}`); };
document.getElementById('combineBtn').onclick = () => { if(!game.gameOver && !game.inBattle) combineWeapon(); };
document.getElementById('resetBtn').onclick = resetGame;
document.getElementById('skill1').onclick = () => { if(game.inBattle && !game.gameOver) skill1(); };
document.getElementById('skill2').onclick = () => { if(game.inBattle && !game.gameOver) skill2(); };
document.getElementById('skill3').onclick = () => { if(game.inBattle && !game.gameOver) skill3(); };
document.getElementById('skillUlt').onclick = () => { if(game.inBattle && !game.gameOver) skillUlt(); };
}
resetGame();
bindEvents();
})();
</script>
</body>
</html>
c++版的
需要Easy x库
#include <graphics.h>
#include <conio.h>
#include <string>
#include <vector>
#include <map>
#include <set>
#include <algorithm>
#include <random>
#include <ctime>
using namespace std;
// ==================== 颜色定义 ====================
#define COLOR_BG 0x221C0A
#define COLOR_PANEL 0x2D2B1A
#define COLOR_BTN 0x4A5D3E
#define COLOR_BTN_HOVER 0x6B8C5A
#define COLOR_TEXT 0xEFE8C9
#define COLOR_HP 0xFF6B6B
#define COLOR_ENERGY 0xFFD93B
#define COLOR_CRYSTAL 0x6BCBFF
#define COLOR_BATTLE 0xFF8C42
#define COLOR_SKILL1 0x8B5A2B
#define COLOR_SKILL2 0x2B6B8B
#define COLOR_SKILL3 0x2B8B5A
#define COLOR_SKILL_ULT 0x8B2B6B
// ==================== 游戏数据 ====================
struct GameData {
string currentLocation = "回廊大厅";
int lampEnergy = 12;
int maxLamp = 12;
int hp = 36;
int maxHp = 36;
set<string> crystals;
vector<string> inventory;
bool inBattle = false;
int bossHp = 56;
int bossMaxHp = 56;
bool gameOver = false;
bool escaped = false;
bool ironShield = false;
vector<tuple<string, string, bool>> items = {
{"赤炎灵晶", "演武厅", false}, {"霜月灵晶", "书阁", false},
{"苍翠灵晶", "幽暗牢房", false}, {"紫霄灵晶", "星语祭坛", false},
{"曜金灵晶", "灵晶矿脉", false}, {"断刃匕首", "回廊大厅", false},
{"流光磨刀石", "演武厅", false}, {"灵灯余烬", "书阁", false},
{"残破卷轴", "星语祭坛", false}, {"魂晶碎块", "菌菇洞穴", false}
};
vector<string> locations = {"回廊大厅", "演武厅", "书阁", "幽暗牢房",
"星语祭坛", "菌菇洞穴", "灵晶矿脉", "玄光出口"};
map<string, vector<string>> exits = {
{"回廊大厅", {"演武厅", "书阁", "幽暗牢房"}},
{"演武厅", {"回廊大厅", "星语祭坛"}},
{"书阁", {"回廊大厅", "菌菇洞穴"}},
{"幽暗牢房", {"回廊大厅", "灵晶矿脉"}},
{"星语祭坛", {"演武厅"}},
{"菌菇洞穴", {"书阁", "玄光出口"}},
{"灵晶矿脉", {"幽暗牢房"}},
{"玄光出口", {"菌菇洞穴"}}
};
map<string, vector<string>> npcs = {
{"菌菇洞穴", {"黄炎硕"}}, {"星语祭坛", {"坤哥"}}, {"灵晶矿脉", {"章鱼"}}
};
map<string, vector<string>> npcDialogs = {
{"黄炎硕", {"白切鸡背叛了五灵!", "用魂晶碎块换情报。"}},
{"坤哥", {"集齐五晶才能对抗白切鸡。", "卷轴记载了五灵归一斩。"}},
{"章鱼", {"小黄,白切鸡就在出口等你。", "战斗时用大招可以重创他。"}}
};
map<string, string> npcSpecial = {
{"黄炎硕", "魂晶碎块"}, {"坤哥", "残破卷轴"}
};
};
GameData game;
mt19937 rng(time(0));
// 按钮结构
struct Button {
int x, y, w, h;
string text;
int color;
int hoverColor;
bool enabled;
function<void()> onClick;
void draw() {
if (!enabled) {
setfillcolor(0x333333);
} else {
int mx = getmousex(), my = getmousey();
if (mx >= x && mx <= x + w && my >= y && my <= y + h) {
setfillcolor(hoverColor);
} else {
setfillcolor(color);
}
}
solidroundrect(x, y, x + w, y + h, 10, 10);
setcolor(COLOR_TEXT);
setbkmode(TRANSPARENT);
settextstyle(18, 0, _T("微软雅黑"));
int tw = textwidth(text.c_str());
outtextxy(x + (w - tw) / 2, y + (h - 20) / 2, text.c_str());
}
bool isHover() {
int mx = getmousex(), my = getmousey();
return enabled && mx >= x && mx <= x + w && my >= y && my <= y + h;
}
};
vector<Button> mapButtons;
vector<Button> skillButtons;
Button takeBtn, combineBtn, resetBtn, talkBtn;
// 日志系统
vector<pair<string, int>> logs;
void addLog(const string& msg, int color = COLOR_TEXT) {
logs.insert(logs.begin(), {msg, color});
if (logs.size() > 20) logs.pop_back();
}
// ==================== 游戏逻辑 ====================
void refreshUI() {
// 重新创建地图按钮
mapButtons.clear();
int bx = 30, by = 200;
for (int i = 0; i < game.locations.size(); i++) {
string loc = game.locations[i];
bool canGo = false;
for (const auto& e : game.exits[game.currentLocation]) {
if (e == loc) canGo = true;
}
Button btn;
btn.x = bx + (i % 4) * 110;
btn.y = by + (i / 4) * 55;
btn.w = 100;
btn.h = 45;
btn.text = (loc == game.currentLocation) ? loc + " ✨" : loc;
btn.color = (loc == game.currentLocation) ? COLOR_SKILL_ULT : COLOR_BTN;
btn.hoverColor = COLOR_BTN_HOVER;
btn.enabled = canGo && !game.inBattle && !game.gameOver;
btn.onClick = [loc]() {
if (game.lampEnergy <= 0) {
addLog("灵灯能量耗尽!", COLOR_BATTLE);
return;
}
game.lampEnergy--;
game.currentLocation = loc;
addLog("🚶 来到 " + loc);
// 自动拾取灵晶(简化)
for (auto& item : game.items) {
if (get<1>(item) == loc && !get<2>(item) && get<0>(item).find("灵晶") != string::npos) {
get<2>(item) = true;
game.inventory.push_back(get<0>(item));
game.crystals.insert(get<0>(item));
addLog("🌀 获得 " + get<0>(item) + "! (" + to_string(game.crystals.size()) + "/5)", COLOR_CRYSTAL);
}
}
if (loc == "玄光出口" && game.crystals.size() >= 5 && !game.inBattle) {
game.inBattle = true;
game.bossHp = game.bossMaxHp;
addLog("🐔 白切鸡挡住了去路!战斗开始!", COLOR_BATTLE);
}
refreshUI();
};
mapButtons.push_back(btn);
}
// 技能按钮
skillButtons.clear();
const char* skillNames[] = {"🔥 崩拳", "💨 疾风连打", "🛡️ 铁壁", "🌟 五灵归一斩"};
int skillColors[] = {COLOR_SKILL1, COLOR_SKILL2, COLOR_SKILL3, COLOR_SKILL_ULT};
for (int i = 0; i < 4; i++) {
Button btn;
btn.x = 30 + i * 110;
btn.y = 520;
btn.w = 100;
btn.h = 45;
btn.text = skillNames[i];
btn.color = skillColors[i];
btn.hoverColor = COLOR_BTN_HOVER;
btn.enabled = game.inBattle && !game.gameOver;
btn.onClick = [i]() {
if (!game.inBattle) return;
int cost = (i == 3) ? 2 : 1;
if (game.lampEnergy < cost) {
addLog("灵灯不足!", COLOR_BATTLE);
return;
}
game.lampEnergy -= cost;
if (i == 2) { // 铁壁
int heal = 12;
game.hp = min(game.maxHp, game.hp + heal);
game.ironShield = true;
addLog("🛡️ 铁壁恢复 " + to_string(heal) + " 生命!");
} else {
uniform_int_distribution<int> dmgDist((i == 0) ? 12 : (i == 1) ? 18 : 30,
(i == 0) ? 18 : (i == 1) ? 28 : 48);
int damage = dmgDist(rng);
uniform_int_distribution<int> critDist(1, 100);
if (critDist(rng) <= 20) {
damage = damage * 1.5;
addLog("⚡ 暴击!");
}
if (i == 1 && critDist(rng) <= 25) {
damage += damage * 0.5;
addLog("💨 连击触发!");
}
game.bossHp -= damage;
addLog("✨ 使用" + string((i == 0) ? "崩拳" : (i == 1) ? "疾风连打" : "五灵归一斩") +
" 造成 " + to_string(damage) + " 伤害!");
}
if (game.bossHp <= 0) {
addLog("🏆 击败白切鸡!逃离深渊!", COLOR_CRYSTAL);
game.inBattle = false;
game.escaped = true;
game.gameOver = true;
refreshUI();
return;
}
// 敌人反击
uniform_int_distribution<int> bossDist(7, 15);
int bossDmg = bossDist(rng);
if (i == 3) bossDmg = max(4, bossDmg - 5);
if (game.ironShield) {
bossDmg /= 2;
addLog("🛡️ 铁壁减伤!");
game.ironShield = false;
}
game.hp -= bossDmg;
addLog("🐔 白切鸡反击造成 " + to_string(bossDmg) + " 伤害!", COLOR_BATTLE);
if (game.hp <= 0) {
addLog("💀 小黄被击败了...", COLOR_BATTLE);
game.gameOver = true;
}
refreshUI();
};
skillButtons.push_back(btn);
}
// 操作按钮
takeBtn = {30, 580, 110, 40, "📦 拾取", COLOR_BTN, COLOR_BTN_HOVER,
!game.inBattle && !game.gameOver, []() {
for (auto& item : game.items) {
if (get<1>(item) == game.currentLocation && !get<2>(item)) {
get<2>(item) = true;
game.inventory.push_back(get<0>(item));
if (get<0>(item).find("灵晶") != string::npos) {
game.crystals.insert(get<0>(item));
addLog("🌀 获得 " + get<0>(item) + "! (" + to_string(game.crystals.size()) + "/5)", COLOR_CRYSTAL);
} else {
addLog("✋ 获得 " + get<0>(item));
}
refreshUI();
return;
}
}
addLog("这里没有可拾取的物品");
}};
combineBtn = {150, 580, 110, 40, "⚔️ 合成", COLOR_BTN, COLOR_BTN_HOVER,
!game.inBattle && !game.gameOver, []() {
auto hasDagger = find(game.inventory.begin(), game.inventory.end(), "断刃匕首") != game.inventory.end();
auto hasStone = find(game.inventory.begin(), game.inventory.end(), "流光磨刀石") != game.inventory.end();
if (hasDagger && hasStone) {
game.inventory.erase(find(game.inventory.begin(), game.inventory.end(), "断刃匕首"));
game.inventory.erase(find(game.inventory.begin(), game.inventory.end(), "流光磨刀石"));
game.inventory.push_back("破晓短刃");
addLog("⚔️ 合成成功!获得破晓短刃!");
} else {
addLog("需要断刃匕首和流光磨刀石");
}
refreshUI();
}};
resetBtn = {270, 580, 110, 40, "🔄 重置", COLOR_BTN, COLOR_BTN_HOVER, true, []() {
game = GameData();
addLog("🔄 游戏已重置!");
refreshUI();
}};
talkBtn = {390, 580, 110, 40, "💬 对话", COLOR_BTN, COLOR_BTN_HOVER,
!game.inBattle && !game.gameOver, []() {
if (game.npcs.count(game.currentLocation)) {
string npc = game.npcs[game.currentLocation][0];
// 检查特殊物品
if (game.npcSpecial.count(npc)) {
auto it = find(game.inventory.begin(), game.inventory.end(), game.npcSpecial[npc]);
if (it != game.inventory.end()) {
game.inventory.erase(it);
addLog("💬 " + npc + ": \"获得战斗增益!\"");
refreshUI();
return;
}
}
vector<string> dialogs = game.npcDialogs[npc];
addLog("💬 " + npc + ": \"" + dialogs[rand() % dialogs.size()] + "\"");
} else {
addLog("这里没有人可以对话");
}
}};
}
// ==================== 绘图函数 ====================
void draw() {
cleardevice();
// 背景
setfillcolor(COLOR_BG);
solidrectangle(0, 0, 800, 700);
// 标题
setcolor(COLOR_CRYSTAL);
settextstyle(28, 0, _T("微软雅黑"));
outtextxy(200, 15, _T("🐔 遗忘深渊 · 小黄 VS 白切鸡 🐙"));
// 状态栏
setfillcolor(COLOR_PANEL);
solidroundrect(20, 60, 780, 120, 15, 15);
char status[256];
sprintf(status, "❤️ 小黄 %d/%d 💡 灵灯 %d/%d 🌀 灵晶 %d/5 📍 %s",
game.hp, game.maxHp, game.lampEnergy, game.maxLamp,
(int)game.crystals.size(), game.currentLocation.c_str());
setcolor(COLOR_TEXT);
settextstyle(20, 0, _T("微软雅黑"));
outtextxy(40, 85, status);
// 血量条
setfillcolor(0x442222);
solidrectangle(40, 115, 40 + 200, 130);
setfillcolor(COLOR_HP);
solidrectangle(40, 115, 40 + 200 * game.hp / game.maxHp, 130);
// 灵灯条
setfillcolor(0x443300);
solidrectangle(260, 115, 260 + 150, 130);
setfillcolor(COLOR_ENERGY);
solidrectangle(260, 115, 260 + 150 * game.lampEnergy / game.maxLamp, 130);
// 地图区域标题
setcolor(COLOR_TEXT);
settextstyle(16, 0, _T("微软雅黑"));
outtextxy(30, 165, _T("🗺️ 深渊地图 (点击移动)"));
// 绘制地图按钮
for (auto& btn : mapButtons) btn.draw();
// 背包区域
setfillcolor(COLOR_PANEL);
solidroundrect(30, 430, 400, 510, 10, 10);
outtextxy(35, 440, _T("🎒 背包"));
int iy = 465;
for (const auto& item : game.inventory) {
setcolor(COLOR_CRYSTAL);
outtextxy(40, iy, item.c_str());
iy += 22;
}
// NPC区域
solidroundrect(410, 430, 780, 510, 10, 10);
outtextxy(415, 440, _T("👥 角色"));
iy = 465;
if (game.npcs.count(game.currentLocation)) {
for (const auto& npc : game.npcs[game.currentLocation]) {
setcolor(COLOR_SKILL2);
outtextxy(420, iy, npc.c_str());
iy += 22;
}
} else {
setcolor(0x888888);
outtextxy(420, 465, _T("无人在此"));
}
// 技能区域
if (game.inBattle) {
setfillcolor(COLOR_BATTLE);
solidroundrect(20, 510, 780, 560, 10, 10);
setcolor(COLOR_TEXT);
char bossHpStr[100];
sprintf(bossHpStr, "🐔 白切鸡 HP: %d/%d", game.bossHp, game.bossMaxHp);
outtextxy(30, 522, bossHpStr);
}
for (auto& btn : skillButtons) btn.draw();
takeBtn.draw();
combineBtn.draw();
resetBtn.draw();
talkBtn.draw();
// 日志区域
solidroundrect(20, 635, 780, 690, 10, 10);
int ly = 645;
for (int i = 0; i < min((int)logs.size(), 6); i++) {
setcolor(logs[i].second);
outtextxy(30, ly, logs[i].first.c_str());
ly += 22;
}
// 胜利/失败提示
if (game.gameOver) {
if (game.escaped) {
setcolor(COLOR_CRYSTAL);
settextstyle(36, 0, _T("微软雅黑"));
outtextxy(250, 300, _T("🎉 胜利!逃离深渊! 🎉"));
} else if (game.hp <= 0) {
setcolor(COLOR_BATTLE);
settextstyle(36, 0, _T("微软雅黑"));
outtextxy(250, 300, _T("💀 游戏结束 💀"));
}
}
}
// ==================== 主函数 ====================
int main() {
initgraph(800, 700);
setbkcolor(COLOR_BG);
srand(time(0));
addLog("🐔 小黄 VS 白切鸡 - 点击式游戏");
addLog("🎯 目标:集齐5枚灵晶,前往玄光出口决战!");
addLog("🔥 点击地图移动,点击技能战斗");
refreshUI();
ExMessage msg;
while (true) {
draw();
if (peekmessage(&msg, EM_MOUSE)) {
if (msg.message == WM_LBUTTONDOWN) {
// 检查所有按钮
for (auto& btn : mapButtons) {
if (btn.isHover() && btn.enabled) btn.onClick();
}
for (auto& btn : skillButtons) {
if (btn.isHover() && btn.enabled) btn.onClick();
}
if (takeBtn.isHover() && takeBtn.enabled) takeBtn.onClick();
if (combineBtn.isHover() && combineBtn.enabled) combineBtn.onClick();
if (resetBtn.isHover() && resetBtn.enabled) resetBtn.onClick();
if (talkBtn.isHover() && talkBtn.enabled) talkBtn.onClick();
}
}
Sleep(16);
}
closegraph();
return 0;
}