肉鸽文字地牢
一款为小屏幕定制的极简打怪游戏。没有画面,只有数值。 玩法: 点点【攻击】互砍,掉落金币。 用金币买药,或永久升级“攻防血”。 小心,喝药会白挨一刀;每 5 层有 Boss 守关。
适配设备:Pro / RW
作者:dengyuhang
下载量:53 · 点赞:2
可信源码风险提示:保存或下载前请阅读源码和权限声明。
let state = {
hp: 100,
maxHp: 100,
atk: 10,
def: 2,
gold: 0,
potions: 2,
floor: 1,
maxFloor: 1,
inBattle: false,
enemy: null,
logs: ["[系统] 欢迎来到幽暗地牢。", "[系统] 你的目标是生存并向下探索。"],
isBusy: false,
isDead: false
};
const MONSTERS = [
{ name: "史莱姆", baseHp: 40, baseAtk: 6, baseDef: 0, gold: 15 },
{ name: "哥布林", baseHp: 80, baseAtk: 12, baseDef: 2, gold: 30 },
{ name: "骷髅兵", baseHp: 150, baseAtk: 20, baseDef: 5, gold: 50 },
{ name: "石像鬼", baseHp: 250, baseAtk: 30, baseDef: 10, gold: 80 },
{ name: "幼龙", baseHp: 400, baseAtk: 45, baseDef: 15, gold: 150 }
];
function addLog(msg) {
state.logs.unshift(msg); // 最新的在最上面
if (state.logs.length > 4) state.logs.pop(); // 只保留最近4条
}
function generateEnemy(floor) {
// 每5层一个Boss
if (floor % 5 === 0) {
return {
name: "魔王·巴风特",
maxHp: 200 + floor * 80,
hp: 200 + floor * 80,
atk: 15 + floor * 5,
def: 5 + floor * 2,
gold: 100 + floor * 20,
isBoss: true
};
}
// 普通怪物随层数成长
let tier = Math.min(Math.floor((floor - 1) / 2), MONSTERS.length - 1);
let base = MONSTERS[tier];
let multiplier = 1 + ((floor - 1) * 0.15); // 每层增加15%属性
return {
name: base.name,
maxHp: Math.floor(base.baseHp * multiplier),
hp: Math.floor(base.baseHp * multiplier),
atk: Math.floor(base.baseAtk * multiplier),
def: Math.floor(base.baseDef * multiplier),
gold: Math.floor(base.gold * multiplier),
isBoss: false
};
}
async function saveProgress() {
if (state.floor > state.maxFloor) {
state.maxFloor = state.floor;
try {
await script.data.set('dungeon_max_floor', state.maxFloor);
} catch (e) {
console.error("保存最高记录失败", e);
}
}
}
async function main() {
try {
const savedFloor = await script.data.get('dungeon_max_floor', 1);
state.maxFloor = savedFloor;
} catch (e) {
console.error("读取存档失败", e);
}
addLog(`[系统] 历史最高记录: 第 ${state.maxFloor} 层`);
updateUI();
}
function updateUI() {
let elements = [];
// 1. 顶部状态栏
elements.push(ui.row([
ui.text(`第 ${state.floor} 层`, { flex: 1, color: '#FFB143', bold: true, size: 18 }),
ui.text(`金币: ${state.gold}`, { flex: 1, align: 'right', color: '#FFD700', bold: true, size: 18 })
]));
elements.push(ui.divider({ color: '#333333', height: 1 }));
// 2. 怪物区域 (如果在战斗)
if (state.inBattle) {
elements.push(ui.row([
ui.text(state.enemy.name, { flex: 1, color: state.enemy.isBoss ? '#FF453A' : '#FFFFFF', bold: true, size: 16 }),
ui.text(`攻:${state.enemy.atk} 防:${state.enemy.def}`, { align: 'right', color: '#888888', size: 12 })
]));
elements.push(ui.progress(`HP: ${state.enemy.hp}/${state.enemy.maxHp}`, (state.enemy.hp / state.enemy.maxHp) * 100, {
color: '#FF453A', background: '#1c1c1e', height: 14
}));
elements.push(ui.spacer(4));
}
// 3. 玩家区域
elements.push(ui.row([
ui.text(`生命`, { flex: 1, color: '#1a8f38', bold: true, size: 16 }),
ui.text(`攻:${state.atk} 防:${state.def} 药水:${state.potions}`, { align: 'right', color: '#aaaaaa', size: 12 })
]));
elements.push(ui.progress(`${state.hp} / ${state.maxHp}`, (state.hp / state.maxHp) * 100, {
color: '#1a8f38', background: '#1c1c1e', height: 14
}));
elements.push(ui.spacer(8));
// 4. 战斗日志区 (固定高度,避免跳动)
let logsNodes = state.logs.map((log, index) => {
let color = '#aaaaaa';
if (log.includes('[伤害]')) color = '#FF453A';
if (log.includes('[恢复]')) color = '#1a8f38';
if (log.includes('[系统]')) color = '#FFB143';
if (index === 0) color = '#FFFFFF'; // 最新一条高亮
return ui.text(log, { color: color, size: 13, lines: 1 });
});
elements.push(ui.column(logsNodes, {
background: '#0a0a0a', radius: 6, padding: 8, height: 100, gap: 4
}));
elements.push(ui.spacer(8));
// 5. 操作按钮区
if (state.isDead) {
elements.push(ui.button("重新挑战", () => resetGame(), { tone: 'primary', height: 56 }));
} else if (state.inBattle) {
elements.push(ui.row([
ui.button("攻击", () => playerAttack(), { flex: 1, tone: 'danger', disabled: state.isBusy, height: 50 }),
ui.button("喝药", () => drinkPotion(), { flex: 1, tone: 'neutral', disabled: state.isBusy || state.potions <= 0, height: 50 })
], { gap: 10 }));
} else {
elements.push(ui.button("向下探索", () => explore(), { tone: 'primary', height: 56 }));
// 升级面板
elements.push(ui.row([
ui.button("升攻(50)", () => upgrade('atk'), { flex: 1, tone: 'neutral', disabled: state.gold < 50, height: 40, size: 14 }),
ui.button("升防(50)", () => upgrade('def'), { flex: 1, tone: 'neutral', disabled: state.gold < 50, height: 40, size: 14 }),
ui.button("补血(30)", () => upgrade('hp'), { flex: 1, tone: 'neutral', disabled: state.gold < 30, height: 40, size: 14 })
], { gap: 6 }));
}
ui.render(elements);
}
// 逻辑函数
function explore() {
if (state.isBusy) return;
state.floor++;
state.enemy = generateEnemy(state.floor);
state.inBattle = true;
addLog(`[系统] 进入第 ${state.floor} 层,遭遇 ${state.enemy.name}!`);
saveProgress();
updateUI();
}
function playerAttack() {
if (state.isBusy) return;
state.isBusy = true;
// 命中与暴击判定
let isCrit = Math.random() < 0.15;
let dmg = Math.max(1, state.atk - state.enemy.def + Math.floor(Math.random() * 4));
if (isCrit) dmg = Math.floor(dmg * 2);
state.enemy.hp -= dmg;
addLog(`[伤害] 你${isCrit ? '暴击' : '攻击'}敌人,造成 ${dmg} 伤害。`);
if (script.canUse('@system.vibrator.vibrate')) system.vibration.vibrate({ mode: 'short' });
updateUI();
setTimeout(() => {
if (state.enemy.hp <= 0) {
addLog(`[系统] 击败了 ${state.enemy.name},获得 ${state.enemy.gold} 金币!`);
state.gold += state.enemy.gold;
state.inBattle = false;
state.enemy = null;
state.isBusy = false;
updateUI();
} else {
enemyAttack();
}
}, 600);
}
function enemyAttack() {
let dmg = Math.max(1, state.enemy.atk - state.def + Math.floor(Math.random() * 3));
state.hp -= dmg;
addLog(`[伤害] ${state.enemy.name} 反击,造成 ${dmg} 伤害。`);
if (script.canUse('@system.vibrator.vibrate')) system.vibration.vibrate({ mode: 'short' });
if (state.hp <= 0) {
state.hp = 0;
state.isDead = true;
state.inBattle = false;
addLog(`[系统] 你倒下了... 挑战结束。`);
if (script.canUse('@system.vibrator.vibrate')) system.vibration.vibrate({ mode: 'long' });
}
state.isBusy = false;
updateUI();
}
function drinkPotion() {
if (state.potions <= 0 || state.isBusy) return;
state.potions--;
let heal = 50;
state.hp = Math.min(state.maxHp, state.hp + heal);
addLog(`[恢复] 喝下药水,恢复 ${heal} 生命。`);
state.isBusy = true;
updateUI();
setTimeout(() => enemyAttack(), 600); // 喝药消耗回合
}
function upgrade(type) {
if (type === 'atk' && state.gold >= 50) {
state.gold -= 50;
state.atk += 3;
addLog(`[系统] 攻击力永久提升至 ${state.atk}。`);
} else if (type === 'def' && state.gold >= 50) {
state.gold -= 50;
state.def += 2;
addLog(`[系统] 防御力永久提升至 ${state.def}。`);
} else if (type === 'hp' && state.gold >= 30) {
state.gold -= 30;
state.hp = Math.min(state.maxHp, state.hp + 40);
addLog(`[恢复] 花费30金币,恢复40点生命。`);
}
updateUI();
}
function resetGame() {
state.hp = 100;
state.maxHp = 100;
state.atk = 10;
state.def = 2;
state.gold = 0;
state.potions = 2;
state.floor = 1;
state.inBattle = false;
state.enemy = null;
state.logs = ["[系统] 你重获新生,再次踏入地牢。"];
state.isBusy = false;
state.isDead = false;
updateUI();
}
return main();