|
|
@@ -2,7 +2,7 @@
|
|
|
* @Author: mojunshou 1637302775@qq.com
|
|
|
* @Date: 2025-03-20 15:01:09
|
|
|
* @LastEditors: mojunshou 1637302775@qq.com
|
|
|
- * @LastEditTime: 2025-04-01 15:42:00
|
|
|
+ * @LastEditTime: 2025-04-02 11:46:35
|
|
|
* @Description: 消除游戏主场景
|
|
|
*/
|
|
|
import { _decorator, Color, EventTouch, instantiate, JsonAsset, Label, Node, Prefab, randomRangeInt, Sprite, Toggle, tween, UITransform, Vec2, Vec3, Widget } from "cc";
|
|
|
@@ -13,7 +13,6 @@ import { LabelChange } from "db://oops-framework/libs/gui/label/LabelChange";
|
|
|
import { CCComp } from "db://oops-framework/module/common/CCComp";
|
|
|
import { GameEvent } from "../../common/config/GameEvent";
|
|
|
import { UIID } from "../../common/config/GameUIConfig";
|
|
|
-import { BlockItemView } from "./BlockItemView";
|
|
|
import { Button } from "cc";
|
|
|
|
|
|
const { ccclass, property } = _decorator;
|
|
|
@@ -57,7 +56,6 @@ interface GridData {
|
|
|
gridNode: Node | null // 网格节点
|
|
|
row: number, // 行
|
|
|
col: number, // 列
|
|
|
- gridColorKey: string | null,
|
|
|
type: number, // 类型--gridColorKey
|
|
|
}
|
|
|
|
|
|
@@ -82,7 +80,6 @@ interface BrickData {
|
|
|
gridConfig: Grids[],
|
|
|
deg: number,
|
|
|
brickNode: Node | null,
|
|
|
- gridColorKey: string | null,
|
|
|
brickInitPos: Vec3, // 方块初始位置
|
|
|
type: number, // 方块类型--gridColorKey
|
|
|
}
|
|
|
@@ -138,7 +135,7 @@ export class EliminateViewComp extends CCComp {
|
|
|
//游戏配置行列
|
|
|
private rows: number = 8; // 行数
|
|
|
private cols: number = 8; // 列数
|
|
|
- private itemSize: number = 82; // 格子大小
|
|
|
+ private itemSize: number = 76.25; // 格子大小
|
|
|
private brickNum: number = 3; // 砖块数量
|
|
|
|
|
|
private gameState: GameState = GameState.READY;
|
|
|
@@ -342,7 +339,6 @@ export class EliminateViewComp extends CCComp {
|
|
|
gridNode: null,
|
|
|
row: row,
|
|
|
col: column,
|
|
|
- gridColorKey: null,
|
|
|
type: 0
|
|
|
};
|
|
|
}
|
|
|
@@ -459,7 +455,6 @@ export class EliminateViewComp extends CCComp {
|
|
|
gridConfig: brickConfig['gridConfig'],
|
|
|
deg: 0,
|
|
|
brickNode: null,
|
|
|
- gridColorKey: randomIndex.toString(),
|
|
|
brickInitPos: new Vec3(),
|
|
|
rotateTag: false,
|
|
|
type: randomIndex,
|
|
|
@@ -488,6 +483,7 @@ export class EliminateViewComp extends CCComp {
|
|
|
brickData.brickInitPos = brickData.brickNode.getWorldPosition()
|
|
|
}
|
|
|
this.brickAddEvent(brickData);
|
|
|
+ //2508801946299286
|
|
|
}
|
|
|
|
|
|
|
|
|
@@ -744,7 +740,6 @@ export class EliminateViewComp extends CCComp {
|
|
|
// 放置方块到网格
|
|
|
this.editingData.gridList.forEach(grid => {
|
|
|
grid.status = CellState.FILLED;
|
|
|
- grid.gridColorKey = this.editingData.brickData!.gridColorKey;
|
|
|
grid.type = this.editingData.brickData!.type;
|
|
|
this.generateGrid(grid);
|
|
|
});
|
|
|
@@ -913,6 +908,8 @@ export class EliminateViewComp extends CCComp {
|
|
|
// 更新总分
|
|
|
this.score += score;
|
|
|
this.lab_score.string = this.score.toString();
|
|
|
+ //计算总分够一局没有,够就马上停止,展示界面
|
|
|
+
|
|
|
}
|
|
|
|
|
|
// 显示消除次数动画
|
|
|
@@ -1415,7 +1412,6 @@ export class EliminateViewComp extends CCComp {
|
|
|
gridNode: null,
|
|
|
row: gridData.row,
|
|
|
col: gridData.col,
|
|
|
- gridColorKey: gridData.gridColorKey,
|
|
|
type: gridData.type,
|
|
|
})
|
|
|
}
|
|
|
@@ -1480,9 +1476,222 @@ export class EliminateViewComp extends CCComp {
|
|
|
//自动放置
|
|
|
this.autoState = !this.autoState;
|
|
|
this.initButtonState(this.autoState);
|
|
|
+ if (this.autoState) {
|
|
|
+ this.gameState = GameState.PLAYING;
|
|
|
+ this.executeAutoPlace()
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ executeAutoPlace() {
|
|
|
+ if (!this.autoState || this.gameState !== GameState.PLAYING || this.editingFlag) {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ console.log("开始自动放置")
|
|
|
+ const bestPlacement = this.findBestPlacement()
|
|
|
+ if (!bestPlacement) {
|
|
|
+ // 所有方块都无法放置,游戏结束
|
|
|
+ this.autoState = false
|
|
|
+ this.gameOver()
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ // 执行放置
|
|
|
+ this.placeBrickAtPosition(bestPlacement)
|
|
|
+ }
|
|
|
+
|
|
|
+ findBestPlacement() {
|
|
|
+ const placements = []
|
|
|
+
|
|
|
+ // 对每个方块计算所有可能的放置位置和分数
|
|
|
+ for (let brickIndex = 0; brickIndex < this.bricksList.length; brickIndex++) {
|
|
|
+ const brickData = this.bricksList[brickIndex]
|
|
|
+
|
|
|
+ // 检查不同旋转状态
|
|
|
+ let gridConfigs = [brickData.gridConfig]
|
|
|
+ let degrees = [brickData.deg]
|
|
|
+
|
|
|
+ // 如果可旋转,计算所有旋转状态
|
|
|
+ if (brickData.rotateFlag) {
|
|
|
+ for (let i = 1; i <= 3; i++) {
|
|
|
+ const next = this.nextGridRotate(
|
|
|
+ i === 1 ? brickData.gridConfig : gridConfigs[i - 1],
|
|
|
+ i === 1 ? brickData.deg : degrees[i - 1]
|
|
|
+ )
|
|
|
+ gridConfigs.push(next.gridConfig)
|
|
|
+ degrees.push(next.deg)
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // 遍历所有网格位置
|
|
|
+ for (let rowIndex = 0; rowIndex < this.rows; rowIndex++) {
|
|
|
+ for (let columnIndex = 0; columnIndex < this.cols; columnIndex++) {
|
|
|
+ // 对每个旋转状态检查
|
|
|
+ for (let rotateIndex = 0; rotateIndex < gridConfigs.length; rotateIndex++) {
|
|
|
+ const currentGridConfig = gridConfigs[rotateIndex]
|
|
|
+ const currentDeg = degrees[rotateIndex]
|
|
|
+
|
|
|
+ // 检查是否可以放置
|
|
|
+ if (this.moveIf(rowIndex, columnIndex, currentGridConfig)) {
|
|
|
+ // 复制网格并模拟放置
|
|
|
+ const gridList = this.copyGridList()
|
|
|
+ currentGridConfig.forEach((gridConfigData) => {
|
|
|
+ const r = gridConfigData.row + rowIndex
|
|
|
+ const c = gridConfigData.column + columnIndex
|
|
|
+ gridList[r][c].status = CellState.FILLED
|
|
|
+ // gridList[r][c].gridColorKey = brickData.gridColorKey
|
|
|
+ gridList[r][c].type = brickData.type;
|
|
|
+ })
|
|
|
+
|
|
|
+ // 检查是否可以消除,计算分数
|
|
|
+ const elimination = this.gridEliminateCheck(gridList)
|
|
|
+ let score = 0
|
|
|
+
|
|
|
+ if (elimination.gridEliminateList.length > 0) {
|
|
|
+ // 计算消除得分
|
|
|
+ for (let i = 1; i <= elimination.eliminateRowNum; i++) {
|
|
|
+ score += this.cols * i
|
|
|
+ }
|
|
|
+ for (let i = 1; i <= elimination.eliminateColumnNum; i++) {
|
|
|
+ score += this.rows * i
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // 记录此放置选项
|
|
|
+ placements.push({
|
|
|
+ brickIndex,
|
|
|
+ brickData,
|
|
|
+ rowIndex,
|
|
|
+ columnIndex,
|
|
|
+ gridConfig: currentGridConfig,
|
|
|
+ deg: currentDeg,
|
|
|
+ score,
|
|
|
+ canEliminate: elimination.gridEliminateList.length > 0
|
|
|
+ })
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // 按优先级排序:最高分 > 有分数 > 没有分数但可放置
|
|
|
+ placements.sort((a, b) => {
|
|
|
+ // 首先按分数排序
|
|
|
+ if (a.score !== b.score) {
|
|
|
+ return b.score - a.score
|
|
|
+ }
|
|
|
+ // 其次按是否可消除排序
|
|
|
+ if (a.canEliminate !== b.canEliminate) {
|
|
|
+ return a.canEliminate ? -1 : 1
|
|
|
+ }
|
|
|
+ // 最后按照方块优先级排序(底部的方块优先)
|
|
|
+ return a.brickIndex - b.brickIndex
|
|
|
+ })
|
|
|
+
|
|
|
+ return placements.length > 0 ? placements[0] : null
|
|
|
+ }
|
|
|
+
|
|
|
+ // ... existing code ...
|
|
|
+
|
|
|
+ placeBrickAtPosition(placement) {
|
|
|
+ // 获取方块数据
|
|
|
+ const brickData = placement.brickData
|
|
|
+ const index = this.bricksList.findIndex(data => data === brickData)
|
|
|
+ if (index === -1) {
|
|
|
+ console.error("无法找到要放置的方块:", brickData)
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ // 从待选区移除方块
|
|
|
+ this.editingData.brickData = this.bricksList.splice(index, 1)[0]
|
|
|
+
|
|
|
+ // 如果需要旋转,执行旋转
|
|
|
+ if (brickData.deg !== placement.deg) {
|
|
|
+ // 更新方块配置和角度
|
|
|
+ brickData.gridConfig = placement.gridConfig
|
|
|
+ brickData.deg = placement.deg
|
|
|
+ // 添加旋转动画
|
|
|
+ tween(brickData.brickNode).to(0.1, { angle: placement.deg }).start()
|
|
|
+ }
|
|
|
+
|
|
|
+ // 准备网格列表
|
|
|
+ this.editingData.gridList = []
|
|
|
+ placement.gridConfig.forEach((gridConfigData: GridConfigData) => {
|
|
|
+ const r = gridConfigData.row + placement.rowIndex
|
|
|
+ const c = gridConfigData.column + placement.columnIndex
|
|
|
+ this.editingData.gridList.push(this.gridList[r][c])
|
|
|
+ })
|
|
|
+
|
|
|
+ // 计算目标位置 - 使用中间位置作为基准
|
|
|
+ let centerPos = new Vec3(0, 0, 0);
|
|
|
+ let validGridCount = 0;
|
|
|
+
|
|
|
+ // 计算所有网格的平均位置
|
|
|
+ this.editingData.gridList.forEach(grid => {
|
|
|
+ if (grid.gridNode) {
|
|
|
+ const worldPos = grid.gridNode.getWorldPosition();
|
|
|
+ centerPos.add(worldPos);
|
|
|
+ validGridCount++;
|
|
|
+ }
|
|
|
+ });
|
|
|
+
|
|
|
+ // 计算平均位置
|
|
|
+ if (validGridCount > 0) {
|
|
|
+ centerPos.x /= validGridCount;
|
|
|
+ centerPos.y /= validGridCount;
|
|
|
+ centerPos.z /= validGridCount;
|
|
|
+ } else {
|
|
|
+ // 如果没有有效网格,使用第一个网格的位置作为后备
|
|
|
+ const targetGridData = this.editingData.gridList[0];
|
|
|
+ if (targetGridData && targetGridData.gridNode) {
|
|
|
+ centerPos = targetGridData.gridNode.getWorldPosition();
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
+ // 添加到移动节点里进行移动
|
|
|
+ const originPos = brickData.brickNode.getWorldPosition()
|
|
|
+ brickData.brickNode.setParent(this.moveNode)
|
|
|
+ brickData.brickNode.setWorldPosition(originPos)
|
|
|
+
|
|
|
+ // 使用动画移动到目标位置--这里的最终放置有问题
|
|
|
+ tween(brickData.brickNode)
|
|
|
+ .to(2, { worldPosition: centerPos })
|
|
|
+ .call(() => {
|
|
|
+ // 动画完成后修改格子状态
|
|
|
+ this.editingData.gridList.forEach((gridData) => {
|
|
|
+ gridData.status = CellState.FILLED
|
|
|
+ gridData.type = this.editingData.brickData.type
|
|
|
+ this.generateGrid(gridData)
|
|
|
+ })
|
|
|
+
|
|
|
+ // 销毁方块
|
|
|
+ this.editingData.brickData.brickNode.destroy()
|
|
|
+
|
|
|
+ // 添加新方块
|
|
|
+ this.addBrick(this.editingData.brickData.index)
|
|
|
+
|
|
|
+ // 检查消除和游戏状态
|
|
|
+ this.gridEliminate().then(() => {
|
|
|
+ this.prompt(false).then((value: unknown) => {
|
|
|
+ const promptFlag = value as boolean;
|
|
|
+ if (!promptFlag) {
|
|
|
+ this.autoState = false
|
|
|
+ this.gameOver()
|
|
|
+ } else if (this.autoState) {
|
|
|
+ // 继续自动放置
|
|
|
+ this.scheduleOnce(() => {
|
|
|
+ this.executeAutoPlace()
|
|
|
+ }, 0.3)
|
|
|
+ }
|
|
|
+ this.editingFlag = false
|
|
|
+ })
|
|
|
+ })
|
|
|
+ })
|
|
|
+ .start()
|
|
|
}
|
|
|
|
|
|
+
|
|
|
//重新开始
|
|
|
private restartGame() {
|
|
|
if (this.gameState === GameState.READY) return;
|