先看效果:点击碰个超大西瓜 或者搜索即可
一、项目简介
《合成大西瓜》是近几年非常火爆的休闲物理合成小游戏,玩法简单、节奏轻松、用户粘性高,非常适合做成微信小游戏。游戏核心逻辑为:点击屏幕生成水果、水果自由下落、同类水果碰撞合并升级、逐步合成更大水果,最终合成大西瓜得分,顶部堆满即游戏结束。
本文基于 Cocos Creator + TypeScript 从零完整实现可上线的微信小游戏版本,包含物理配置、水果生成、碰撞合并、计分系统、游戏结束判定、边界限制、防BUG处理、微信打包发布全套流程,无冗余内容,可直接落地开发。
二、开发环境与项目基础配置
1. 开发环境
引擎版本:Cocos Creator 3.x 系列通用
开发语言:TypeScript
运行平台:微信小游戏
核心技术:2D 物理引擎、碰撞检测、节点复用、触屏事件、游戏逻辑帧控
2. 项目初始化设置
新建 2D 空白项目,设置画布分辨率为微信小游戏标准竖屏尺寸,适配所有手机机型。
开启 2D 物理引擎:项目设置中开启物理2D模块,设置合理重力参数,保证水果下落手感真实、不漂浮、不卡顿。
统一项目资源结构,分为脚本、预制体、场景、音频资源,保证代码结构清晰、易维护、易二次开发。
三、游戏整体设计思路
1. 核心玩法逻辑
玩家点击屏幕任意位置,在对应横坐标生成随机低级水果;水果受重力自由下落,与底部或其他水果堆叠;两个相同等级水果发生碰撞时自动合并为高一级水果,并增加对应分数;当水果堆积超过顶部警戒线,判定游戏结束。
2. 游戏核心模块拆解
触屏生成模块、物理下落模块、碰撞合并模块、分数统计模块、游戏判负模块、游戏重启模块。
四、场景结构搭建
整个游戏场景结构极简,全部节点各司其职,无多余层级:
1. 边界墙体:左右底部静态碰撞体,防止水果飞出屏幕
2. 警戒线节点:用于判定水果是否溢出、触发游戏结束
3. 水果根节点:统一管理所有动态生成的水果
4. UI 层:分数显示、结束弹窗
5. 生成点位:控制水果生成高度
所有边界碰撞体设置为静态刚体,保证物理世界稳定,不会出现穿透、卡空、穿模问题。
五、水果预制体与物理参数配置
水果预制体是整个游戏的核心载体,每一个水果都是独立的物理物体。
预制体挂载:精灵组件、2D刚体、圆形碰撞体、水果逻辑脚本。
刚体设置为动态刚体,开启碰撞监听,禁止旋转,保证水果下落姿态端正。
碰撞体根据水果等级动态适配半径,保证大小水果碰撞精准无误。
设置轻微摩擦力与回弹值,模拟真实堆叠效果,不会过于僵硬或过于弹跳。
游戏设置完整水果等级链:从最小葡萄逐级升级,最终合成终极大西瓜,每一级对应不同尺寸、分数、贴图规格。
六、核心代码实现(完整可运行)
1. 水果配置常量
统一管理所有水果等级、分数、缩放大小,方便后期改数值、改皮肤、改难度。
const FRUIT_CONFIG = [
{ id: 1, score: 10, scale: 0.3 },
{ id: 2, score: 20, scale: 0.38 },
{ id: 3, score: 30, scale: 0.46 },
{ id: 4, score: 40, scale: 0.54 },
{ id: 5, score: 50, scale: 0.62 },
{ id: 6, score: 60, scale: 0.7 },
{ id: 7, score: 70, scale: 0.78 },
{ id: 8, score: 80, scale: 0.86 },
{ id: 9, score: 90, scale: 0.94 },
{ id: 10, score: 100, scale: 1.0 },
{ id: 11, score: 500, scale: 1.2 }
]
2. 水果逻辑脚本(碰撞合并核心)
脚本负责水果初始化、碰撞监听、同等级合并、防重复合并BUG处理。
import { _decorator, Component, Node, RigidBody2D, PhysicsCircleCollider2D, Contact2DType, IPhysics2DContact } from 'cc';
const { ccclass, property } = _decorator;
@ccclass('Fruit')
export class Fruit extends Component {
public fruitId: number = 1;
private isMerging: boolean = false;
onLoad() {
this.node.on(Contact2DType.BEGIN_CONTACT, this.onContact, this);
}
init(id: number) {
this.fruitId = id;
const cfg = FRUIT_CONFIG[id – 1];
this.node.setScale(cfg.scale, cfg.scale);
const collider = this.getComponent(PhysicsCircleCollider2D);
collider.radius = 45 * cfg.scale;
}
private onContact(contact: IPhysics2DContact, self, other) {
if (this.isMerging) return;
const otherFruit = other.node.getComponent(Fruit);
if (!otherFruit) return;
if (otherFruit.fruitId === this.fruitId) {
this.isMerging = true;
otherFruit.isMerging = true;
this.merge(otherFruit);
}
}
private merge(other: Fruit) {
const pos = this.node.position.clone().lerp(other.node.position, 0.5);
const nextId = this.fruitId + 1;
GameMain.ins.addScore(FRUIT_CONFIG[this.fruitId – 1].score);
GameMain.ins.spawnFruit(pos, nextId);
this.node.destroy();
other.node.destroy();
}
}
3. 游戏主控制脚本
负责触屏生成水果、随机等级、分数更新、游戏结束判定、重启游戏逻辑。
import { _decorator, Component, Node, Prefab, instantiate, Label, input, Input, EventTouch, Vec3 } from 'cc';
const { ccclass, property } = _decorator;
@ccclass('GameMain')
export class GameMain extends Component {
public static ins: GameMain = null;
@property(Prefab) fruitPrefab: Prefab = null;
@property(Node) fruitRoot: Node = null;
@property(Node) deadLine: Node = null;
@property(Label) scoreLabel: Label = null;
@property(Node) gameOverUI: Node = null;
private score: number = 0;
private isOver: boolean = false;
onLoad() {
GameMain.ins = this;
input.on(Input.EventTouchEnd, this.onTouch, this);
}
private onTouch(e: EventTouch) {
if (this.isOver) return;
const pos = e.getUILocation();
const x = Math.max(-320, Math.min(320, pos.x – this.node.position.x));
this.spawnFruit(new Vec3(x, 500, 0), this.getRandomId());
}
private getRandomId() {
return Math.floor(Math.random() * 5) + 1;
}
spawnFruit(pos: Vec3, id: number) {
const fruit = instantiate(this.fruitPrefab);
fruit.setParent(this.fruitRoot);
fruit.setPosition(pos);
fruit.getComponent(Fruit).init(id);
}
addScore(num: number) {
this.score += num;
this.scoreLabel.string = "分数:" + this.score;
}
update() {
if (this.isOver) return;
for (let f of this.fruitRoot.children) {
if (f.position.y > this.deadLine.position.y) {
this.gameOver();
break;
}
}
}
gameOver() {
this.isOver = true;
this.gameOverUI.active = true;
}
restart() {
this.fruitRoot.destroyAllChildren();
this.score = 0;
this.scoreLabel.string = "分数:0";
this.isOver = false;
this.gameOverUI.active = false;
}
}
七、核心BUG优化与手感优化方案
1. 防止多次合并BUG
原生物理碰撞会一帧触发多次碰撞,导致两个水果重复合成、错乱生成。解决方案:增加合并锁状态,正在合并的水果不再响应碰撞,彻底杜绝叠合BUG。
2. 水果穿透、卡穿模问题
边界全部使用静态碰撞体,水果动态刚体开启连续碰撞检测,保证高速下落不会穿墙。
3. 边界限位优化
点击生成水果时强制限制 X 轴范围,避免玩家点屏幕两侧生成超出可视区域的水果,保证游戏体验规整。
4. 游戏结束判定精准度
逐帧检测所有水果坐标,只要任意一颗水果溢出警戒线立刻结束游戏,还原原版游戏规则。
八、微信小游戏打包发布流程
1. 构建发布面板选择「微信小游戏」平台,设置竖屏适配、关闭多余模块,压缩纹理资源。
2. 构建完成后导出微信工程,使用微信开发者工具打开项目。
3. 校验项目配置、AppID、基础库版本,修复少量平台适配差异。
4. 真机调试流畅无误后,即可上传提交审核,正式上线。
九、项目可扩展功能(进阶优化)
1. 接入微信激励广告,实现复活、加倍得分功能
2. 本地存储最高分记录
3. 合成特效、粒子动画、合成音效
4. 连击加分、难度递增机制
5. 道具系统:清屏、降层、消除单个水果
十、总结
本文完整实现了商业级可上线的《合成大西瓜》微信小游戏,基于 Cocos Creator 原生2D物理系统,逻辑简洁、性能稳定、无明显BUG,完全对标原版游戏手感与玩法。整套代码结构清晰、低耦合、易扩展






