2048 Game body { font-family: 'avenir', sans-serif; display: flex; justify-content: center; align-items: center; height: 100vh; margin: 0; background-color: #ffffff; }
    .container {
        text-align: center;
    }
    
    h1 {
        color: #333;
        font-size: 1.5em;
        margin-bottom: 20px;
    }
    
    .grid {
        display: grid;
        grid-template-columns: repeat(4, 1fr);
        grid-template-rows: repeat(4, 1fr);
        width: 276px;
        height: 276px;
        gap: 6px;
        padding: 12px;
        background-color: #FFE2B5;
        border-radius: 10px;
    }
    
    .cell {
        width: 60px;
        height: 60px;
        display: flex;
        justify-content: center;
        align-items: center;
        background-color: #eee;
        color: #333;
        font-size: 20px;
        font-weight: bold;
        border-radius: 5px;
    }
    
    .cell.empty {
        background-color: #eee;
    }
    
    .cell.value-2 { background-color: #eee4da; color: #333; }
    .cell.value-4 { background-color: #ede0c8; color: #333; }
    .cell.value-8 { background-color: #f2b179; color: #f9f6f2; }
    .cell.value-16 { background-color: #f59563; color: #f9f6f2; }
    .cell.value-32 { background-color: #f67c5f; color: #f9f6f2; }
    .cell.value-64 { background-color: #f65e3b; color: #f9f6f2; }
    .cell.value-128 { background-color: #edcf72; color: #f9f6f2; font-size: 18px; }
    .cell.value-256 { background-color: #edcc61; color: #f9f6f2; font-size: 18px; }
    .cell.value-512 { background-color: #edc850; color: #f9f6f2; font-size: 18px; }
    .cell.value-1024 { background-color: #edc53f; color: #f9f6f2; font-size: 16px; }
    .cell.value-2048 { background-color: #edc22e; color: #f9f6f2; font-size: 16px; }
    
    .button-container {
        display: flex;
        flex-direction: column;
        align-items: center;
        margin-top: 20px;
    }
    
    .row {
        display: flex;
        margin: 3px 0;
    }
    
    button {
        width: 60px;
        height: 40px;
        margin: 3px;
        background-color: #f57c00;
        color: white;
        border: none;
        border-radius: 5px;
        font-family: 'avenir', sans-serif;
        font-size: 10px;
        cursor: pointer;
        transition: all 0.2s;
    }
    
    button:hover {
        background-color: #fb8c00;
        transform: scale(1.05);
    }
    
    .score-container {
        display: flex;
        justify-content: space-between;
        width: 276px;
        margin-bottom: 10px;
    }
    
    .score-box {
        background-color: #eee;
        padding: 10px;
        border-radius: 5px;
        font-weight: bold;
    }
</style>

2048 Game

Score: 0
Best: 0
← ↓ →
<script>
    // 游戏状态
    let grid = [
        [0, 0, 0, 0],
        [0, 0, 0, 0],
        [0, 0, 0, 0],
        [0, 0, 0, 0]
    ];
    let score = 0;
    let bestScore = localStorage.getItem('bestScore') || 0;
    document.getElementById('best-score').textContent = bestScore;

    // 初始化游戏
    function initGame() {
        createGrid();
        addRandomTile();
        addRandomTile();
        render();
    }

    // 创建网格
    function createGrid() {
        const gridElement = document.getElementById('grid');
        gridElement.innerHTML = '';
        
        for (let i = 0; i < 4; i++) {
            for (let j = 0; j < 4; j++) {
                const cell = document.createElement('div');
                cell.className = 'cell empty';
                cell.id = `cell-${i}-${j}`;
                gridElement.appendChild(cell);
            }
        }
    }

    // 添加随机方块
    function addRandomTile() {
        const emptyCells = [];
        
        for (let i = 0; i < 4; i++) {
            for (let j = 0; j < 4; j++) {
                if (grid[i][j] === 0) {
                    emptyCells.push({ row: i, col: j });
                }
            }
        }
        
        if (emptyCells.length > 0) {
            const randomCell = emptyCells[Math.floor(Math.random() * emptyCells.length)];
            // 90%概率生成2,10%概率生成4
            grid[randomCell.row][randomCell.col] = Math.random() < 0.9 ? 2 : 4;
        }
    }

    // 渲染网格
    function render() {
        for (let i = 0; i < 4; i++) {
            for (let j = 0; j < 4; j++) {
                const cell = document.getElementById(`cell-${i}-${j}`);
                const value = grid[i][j];
                
                if (value === 0) {
                    cell.textContent = '';
                    cell.className = 'cell empty';
                } else {
                    cell.textContent = value;
                    cell.className = `cell value-${value}`;
                }
            }
        }
        
        document.getElementById('score').textContent = score;
    }

    // 合并数组
    function mergeCells(row) {
        // 过滤掉0
        const filteredRow = row.filter(val => val !== 0);
        const result = [];
        
        for (let i = 0; i < filteredRow.length; i++) {
            if (i < filteredRow.length - 1 && filteredRow[i] === filteredRow[i + 1]) {
                // 合并相同的数字
                const mergedValue = filteredRow[i] * 2;
                result.push(mergedValue);
                score += mergedValue;
                i++; // 跳过下一个元素
            } else {
                result.push(filteredRow[i]);
            }
        }
        
        // 补充0到长度为4
        while (result.length < 4) {
            result.push(0);
        }
        
        return result;
    }

    // 移动逻辑
    function move(direction) {
        let moved = false;
        let newGrid = JSON.parse(JSON.stringify(grid)); // 深拷贝当前网格
        
        switch (direction) {
            case 'left':
                for (let i = 0; i < 4; i++) {
                    const originalRow = newGrid[i].slice();
                    newGrid[i] = mergeCells(newGrid[i]);
                    if (JSON.stringify(originalRow) !== JSON.stringify(newGrid[i])) {
                        moved = true;
                    }
                }
                break;
                
            case 'right':
                for (let i = 0; i < 4; i++) {
                    const originalRow = newGrid[i].slice();
                    const reversedRow = newGrid[i].slice().reverse();
                    const mergedRow = mergeCells(reversedRow).reverse();
                    newGrid[i] = mergedRow;
                    if (JSON.stringify(originalRow) !== JSON.stringify(mergedRow)) {
                        moved = true;
                    }
                }
                break;
                
            case 'up':
                for (let j = 0; j < 4; j++) {
                    const column = [newGrid[0][j], newGrid[1][j], newGrid[2][j], newGrid[3][j]];
                    const originalColumn = column.slice();
                    const mergedColumn = mergeCells(column);
                    
                    for (let i = 0; i < 4; i++) {
                        newGrid[i][j] = mergedColumn[i];
                    }
                    
                    if (JSON.stringify(originalColumn) !== JSON.stringify(mergedColumn)) {
                        moved = true;
                    }
                }
                break;
                
            case 'down':
                for (let j = 0; j < 4; j++) {
                    const column = [newGrid[0][j], newGrid[1][j], newGrid[2][j], newGrid[3][j]];
                    const originalColumn = column.slice();
                    const reversedColumn = column.slice().reverse();
                    const mergedColumn = mergeCells(reversedColumn).reverse();
                    
                    for (let i = 0; i < 4; i++) {
                        newGrid[i][j] = mergedColumn[i];
                    }
                    
                    if (JSON.stringify(originalColumn) !== JSON.stringify(mergedColumn)) {
                        moved = true;
                    }
                }
                break;
        }
        
        if (moved) {
            grid = newGrid;
            addRandomTile();
            render();
            
            // 更新最佳分数
            if (score > bestScore) {
                bestScore = score;
                localStorage.setItem('bestScore', bestScore);
                document.getElementById('best-score').textContent = bestScore;
            }
            
            // 检查游戏是否结束
            if (checkGameOver()) {
                setTimeout(() => {
                    alert('Game Over!');
                }, 100);
            }
        }
    }

    // 检查游戏是否结束
    function checkGameOver() {
        // 检查是否有空格
        for (let i = 0; i < 4; i++) {
            for (let j = 0; j < 4; j++) {
                if (grid[i][j] === 0) {
                    return false;
                }
            }
        }
        
        // 检查是否有相邻的相同数字
        for (let i = 0; i < 4; i++) {
            for (let j = 0; j < 4; j++) {
                const current = grid[i][j];
                
                // 检查右边
                if (j < 3 && current === grid[i][j + 1]) {
                    return false;
                }
                
                // 检查下面
                if (i < 3 && current === grid[i + 1][j]) {
                    return false;
                }
            }
        }
        
        return true;
    }

    // 检查是否获胜
    function checkWin() {
        for (let i = 0; i < 4; i++) {
            for (let j = 0; j < 4; j++) {
                if (grid[i][j] === 2048) {
                    setTimeout(() => {
                        alert('Congratulations! You reached 2048!');
                    }, 100);
                    return true;
                }
            }
        }
        return false;
    }

    // 事件监听
    document.getElementById('up-btn').addEventListener('click', () => move('up'));
    document.getElementById('down-btn').addEventListener('click', () => move('down'));
    document.getElementById('left-btn').addEventListener('click', () => move('left'));
    document.getElementById('right-btn').addEventListener('click', () => move('right'));

    // 键盘控制
    document.addEventListener('keydown', (e) => {
        switch (e.key) {
            case 'ArrowUp':
                move('up');
                break;
            case 'ArrowDown':
                move('down');
                break;
            case 'ArrowLeft':
                move('left');
                break;
            case 'ArrowRight':
                move('right');
                break;
        }
    });

    // 初始化游戏
    initGame();
</script>