import { reshape, refreshLinks } from "./RainbowCut"; import { RAINBOW_SHAPES } from "./RainbowRules"; import { RocketCut } from "./RocketRules"; /** 不调用消除入口:不推进机关、计数、彩虹能量,也不生成替代方块。 */ export function applyRocketCut(map: any, block: any, cut: RocketCut): void { const origin = block.rocketOrigin || block.node.uuid; const x = block.posX, y = block.posY; if (!cut.fragments.length) { block.allBlocks.forEach(p => { const cell = map.mapBlocksWall[x + p.x][y + p.y].getComponent("MapBlock"); if (cell.block_Id === block.node.uuid) { cell.block_Id = ""; cell.nowColor = -1; } }); map.blocks.splice(map.blocks.indexOf(block.node), 1); block.node.active = false; block.node.removeFromParent(); block.node.destroy(); } else { const first = cut.fragments[0]; const upper = block.type === 1 && block.block_Info.node?.getComponent("Block"); const template = cc.instantiate(map.Block_Array[first.shape]); const floors = block.node.children.filter(node => node.getComponent("Floor")).map(node => ({ node, x: Math.round((node.x + 65) / 120), y: Math.round((node.y - 60) / 120), time: node.getComponent("Floor").time })); // 只有普通块及其普通地板/问号覆盖允许分裂,因此没有钥匙等附件归属转移。 const info = cut.fragments.length > 1 ? JSON.parse(JSON.stringify(block.block_Info)) : null; if (info) { const question = block.node.getChildByName("question"); if (question) info.questionTime = question.getComponent("Question").time; floors.forEach(floor => { if (!RAINBOW_SHAPES[first.shape].some(p => p.x + first.offset.x === floor.x && p.y + first.offset.y === floor.y)) { floor.node.active = false; floor.node.removeFromParent(); floor.node.destroy(); } }); } if (upper) { upper.posX = x; upper.posY = y; } reshape(map, block, first, template, false); block.rocketOrigin = origin; if (upper) { reshape(map, upper, first, template, true); const offset = upper.getStackingPos(); upper.node.setPosition(block.node.x + offset.x, block.node.y + offset.y); upper.stacking = cc.v2(offset.x, offset.y); upper.startPos = upper.node.position.clone(); } template.destroy(); for (const fragment of cut.fragments.slice(1)) { const node = cc.instantiate(map.Block_Array[fragment.shape]); const cell = map.mapBlocksWall[x + fragment.offset.x][y + fragment.offset.y]; node.parent = map.node; node.setPosition(cell.x + 65, cell.y - 60); const ids = map.blocks.map(n => Number(n.getComponent("Block").blockId) || 0); const extra = node.getComponent("Block"); extra.init({ ...info, id: Math.max(0, ...ids) + 1, block: fragment.shape, position: { x: node.x, y: node.y } }, null, null, null, null); extra.rocketOrigin = origin; node.children.forEach(child => { const floor = child.getComponent("Floor"); if (!floor) return; const px = Math.round((child.x + 65) / 120), py = Math.round((child.y - 60) / 120); const old = floors.find(p => p.x === px + fragment.offset.x && p.y === py + fragment.offset.y); floor.init(old.time, extra.posX + px, extra.posY + py); }); map.blocks.push(node); extra.cmupdate(); } refreshLinks(map, upper ? [block, upper] : [block]); block.cmupdate(); } map.blockNum = map.blocks.length; }