Fix G key (playBestSolution never awaited async bestSolution), add menu exit
- playBestSolution() called bestSolution() (now async, hits the server)
without await/async — got a Promise object back, .moves was undefined,
autoPlayStep() bailed on its first tick. G silently did nothing.
- No way back to the menu from gameplay — add 🏠 HUD button + M key,
cancels any in-flight search/autoplay before switching screens.
- settings-save button now shows "Сохраняю…" and disables itself during
the request — previously gave no feedback while the fetch was in
flight, looked like a dead button even though it worked (confirmed via
server logs/DB — the save itself was never broken).
This commit is contained in:
+25
-3
@@ -13,6 +13,8 @@
|
||||
canvas { border: 3px solid #e94560; border-radius: 12px; box-shadow: 0 0 20px rgba(233,69,96,0.4); }
|
||||
#hud { display: flex; gap: 20px; color: #e94560; font-size: 16px; font-weight: bold; }
|
||||
#hud span { background: rgba(233,69,96,0.1); padding: 8px 16px; border-radius: 20px; border: 1px solid rgba(233,69,96,0.3); }
|
||||
#menu-btn { cursor: pointer; }
|
||||
#menu-btn:hover { background: rgba(233,69,96,0.25) !important; }
|
||||
#controls { color: #aaa; font-size: 13px; }
|
||||
kbd { background: #1a1a2e; border: 1px solid #e94560; border-radius: 4px; padding: 2px 6px; color: #e94560; }
|
||||
#solve-overlay { position: fixed; inset: 0; background: rgba(10,10,21,0.75); display: flex; justify-content: center; align-items: center; z-index: 10; }
|
||||
@@ -124,6 +126,7 @@
|
||||
<span id="level-name">Уровень 1</span>
|
||||
<span id="box-count">📦 0/0</span>
|
||||
<span id="moves-count">👣 0</span>
|
||||
<span id="menu-btn" title="В меню">🏠</span>
|
||||
</div>
|
||||
<div id="controls">
|
||||
<kbd>← → ↑ ↓</kbd> или <kbd>WASD</kbd> — движение
|
||||
@@ -131,7 +134,8 @@
|
||||
<kbd>P</kbd> — пред.
|
||||
<kbd>R</kbd> — рестарт
|
||||
<kbd>F</kbd> — автопоиск (<kbd>Esc</kbd> — отмена)
|
||||
<kbd>G</kbd> — лучшее сохранённое решение
|
||||
<kbd>G</kbd> — лучшее сохранённое решение
|
||||
<kbd>M</kbd> — в меню
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -1722,9 +1726,9 @@ function autoPlayStep() {
|
||||
tryMove(dx, dy);
|
||||
}
|
||||
|
||||
function playBestSolution() {
|
||||
async function playBestSolution() {
|
||||
if (autoSolveActive || levelComplete || solveState || playerMoving || boxes.some(b => b.moving)) return;
|
||||
const best = bestSolution(LEVELS[currentLevel].name);
|
||||
const best = await bestSolution(LEVELS[currentLevel].name);
|
||||
if (!best) { alert('Нет сохранённых решений для этого уровня — сначала пройди его (F или руками)'); return; }
|
||||
startFlatPlayback(best.moves);
|
||||
}
|
||||
@@ -2080,6 +2084,7 @@ window.addEventListener('keydown', e => {
|
||||
if (key === 'p') { currentLevel=(currentLevel-1+LEVELS.length)%LEVELS.length; loadLevel(currentLevel); e.preventDefault(); return; }
|
||||
if (key === 'f') { startAutoSolve(); e.preventDefault(); return; }
|
||||
if (key === 'g') { playBestSolution(); e.preventDefault(); return; }
|
||||
if (key === 'm') { backToMenu(); e.preventDefault(); return; }
|
||||
|
||||
// Стрелки и WASD
|
||||
if (['arrowup','arrowdown','arrowleft','arrowright','w','a','s','d'].includes(key)) {
|
||||
@@ -2149,14 +2154,31 @@ document.getElementById('start-begin').addEventListener('click', () => {
|
||||
});
|
||||
document.getElementById('end-menu').addEventListener('click', () => showScreen('screen-menu'));
|
||||
|
||||
// Выход в меню из игры — гасим поиск/автопроигрывание, если шли, иначе
|
||||
// они продолжат тикать в фоне за скрытым экраном.
|
||||
function backToMenu() {
|
||||
if (solveState) cancelAutoSolve();
|
||||
autoSolveActive = false;
|
||||
autoPlayMoves = null;
|
||||
showScreen('screen-menu');
|
||||
}
|
||||
document.getElementById('menu-btn').addEventListener('click', backToMenu);
|
||||
|
||||
document.getElementById('settings-save').addEventListener('click', async () => {
|
||||
const name = document.getElementById('settings-name-input').value.trim();
|
||||
if (!name) return;
|
||||
const btn = document.getElementById('settings-save');
|
||||
btn.disabled = true;
|
||||
const originalText = btn.textContent;
|
||||
btn.textContent = 'Сохраняю…';
|
||||
try {
|
||||
await apiPost('set_name', { name });
|
||||
showScreen(settingsReturnTo === null ? 'screen-menu' : settingsReturnTo);
|
||||
} catch {
|
||||
alert('Не удалось сохранить имя — сервер недоступен');
|
||||
} finally {
|
||||
btn.disabled = false;
|
||||
btn.textContent = originalText;
|
||||
}
|
||||
});
|
||||
document.getElementById('settings-name-input').addEventListener('keydown', e => {
|
||||
|
||||
Reference in New Issue
Block a user