# 微信小游戏性能优化指南 ## 📊 性能指标要求 ### 微信官方标准 - **启动时间**:冷启动 < 3秒,热启动 < 1秒 - **首屏渲染**:< 2秒 - **帧率**:稳定 60 FPS(低端机可降至 30 FPS) - **内存占用**:< 200 MB(iOS),< 300 MB(Android) - **包体大小**:主包 ≤ 20 MB,总包 ≤ 200 MB --- ## 🎯 关键优化点 ### 1. 包体优化 #### 代码分包策略 ```javascript // project.json 配置 { "subpackages": [ { "name": "core", "root": "subpackages/core/" }, { "name": "levels", "root": "subpackages/levels/", "lazy": true // 按需加载 } ] } ``` #### 资源压缩 - **图片**:使用 TinyPNG 或 ImageOptim 压缩,目标减少 50-70% - **音频**:MP3 格式,比特率 128kbps,单声道 - **纹理**:使用 ASTC 格式(Android)和 PVRTC(iOS) #### 代码优化 ```typescript // ❌ 避免:频繁创建对象 function spawnFruit() { const fruit = new Fruit(); // 每次new会触发GC return fruit; } // ✅ 推荐:使用对象池 const fruitPool: Fruit[] = []; function spawnFruit() { let fruit = fruitPool.pop(); if (!fruit) { fruit = new Fruit(); } fruit.reset(); return fruit; } ``` --- ### 2. 内存管理 #### 主动触发 GC ```typescript // 在合适的时机触发垃圾回收 class GameManager { onGameOver() { // 清理临时对象 this.clearEffects(); this.clearBullets(); // 微信环境触发GC if (typeof wx !== 'undefined' && wx.triggerGC) { setTimeout(() => wx.triggerGC(), 1000); } } } ``` #### 资源释放策略 ```typescript // 场景切换时释放资源 import { resources, AssetManager } from 'cc'; class ResourceManager { static releaseUnusedAssets() { // 释放未使用的资源 resources.releaseAll(); // 强制清理缓存 AssetManager.cacheManager?.clear(); } static releaseTexture(textureName: string) { const texture = resources.get(textureName); if (texture) { resources.release(textureName); texture.destroy(); // 立即销毁 } } } ``` #### 内存监控 ```typescript // 定期检查内存使用 class MemoryMonitor { private static checkInterval = 10000; // 10秒 static startMonitoring() { setInterval(() => { if (wx.getSystemInfoSync) { const info = wx.getSystemInfoSync(); const memoryMB = (info.memoryUsage || 0) / 1024 / 1024; if (memoryMB > 200) { console.warn(`[Memory] 内存警告: ${memoryMB.toFixed(1)} MB`); this.triggerCleanup(); } } }, this.checkInterval); } private static triggerCleanup() { console.log('[Memory] 执行内存清理...'); // 1. 清理特效 // 2. 清理粒子 // 3. 触发GC } } ``` --- ### 3. 渲染优化 #### 减少 Draw Calls ```typescript // ✅ 合并相同材质的Sprite // 将多个小水果合并到一个节点下,使用同一材质 // ❌ 避免:每个水果单独一个节点 fruit1.node.parent = rootNode; fruit2.node.parent = rootNode; // ✅ 推荐:使用批量渲染 const batchNode = new Node('FruitBatch'); fruit1.node.parent = batchNode; fruit2.node.parent = batchNode; batchNode.parent = rootNode; ``` #### 合批技巧 - 相同材质的Sprite放在同一父节点下 - 使用 SpriteAtlas 打包小图 - 避免动态修改材质参数 #### 降低 Overdraw ```typescript // 设置合理的渲染层级 camera.clearFlags = ClearFlag.SOLID | ClearFlag.DEPTH; // 隐藏不可见对象 node.active = false; // 完全禁用 // 而不是 node.opacity = 0; // 仍然参与渲染 ``` --- ### 4. 音频优化 #### 音频格式选择 | 类型 | 格式 | 比特率 | 声道 | 文件大小 | |------|------|--------|------|----------| | BGM | MP3 | 128kbps | 立体声 | ~2MB/分钟 | | SFX | MP3 | 96kbps | 单声道 | ~50KB/个 | | Voice | MP3 | 64kbps | 单声道 | ~30KB/个 | #### 音频管理最佳实践 ```typescript class AudioManager { // 限制同时播放的音效数量 private maxConcurrentSFX = 5; private activeSFXCount = 0; playSFX(name: string) { if (this.activeSFXCount >= this.maxConcurrentSFX) { console.warn('[Audio] 音效并发数已达上限'); return; } this.activeSFXCount++; // 播放音效... // 播放完成后递减计数 setTimeout(() => { this.activeSFXCount--; }, duration); } } ``` --- ### 5. 网络优化 #### 广告预加载 ```typescript // 在游戏启动3秒后预加载广告 setTimeout(() => { AdManager.preloadAds(); }, 3000); // 关卡结束前提前准备广告 class LevelManager { onLevelComplete() { // 提前加载插屏广告 AdManager.preloadInterstitial(); // 显示结算界面 this.showResultPanel(); } } ``` #### 数据上报优化 ```typescript // ❌ 避免:频繁上报 wx.reportAnalytics('merge', { level: 1 }); // 每次合成 // ✅ 推荐:批量上报 class AnalyticsManager { private eventQueue: any[] = []; recordMerge(level: number) { this.eventQueue.push({ event: 'merge', data: { level }, timestamp: Date.now() }); // 每10个事件或每30秒上报一次 if (this.eventQueue.length >= 10) { this.flushEvents(); } } private flushEvents() { this.eventQueue.forEach(event => { wx.reportAnalytics(event.event, event.data); }); this.eventQueue = []; } } ``` --- ## 🔧 微信开发者工具调试 ### 性能面板使用 1. 打开微信开发者工具 2. 点击「调试器」→「Performance」 3. 观察以下指标: - FPS 曲线 - 内存占用 - Draw Calls - JS 执行时间 ### 真机测试 ```bash # 1. 构建微信小游戏 cocos build --platform wechatgame --output ./build # 2. 用微信开发者工具打开 build 目录 # 3. 点击「预览」生成二维码 # 4. 用手机微信扫码,在真机上测试 ``` ### 性能问题定位 ```typescript // 添加性能埋点 class PerformanceTracker { private static marks: Map = new Map(); static mark(name: string) { this.marks.set(name, performance.now()); } static measure(name: string): number { const start = this.marks.get(name); if (!start) return 0; const duration = performance.now() - start; console.log(`[Perf] ${name}: ${duration.toFixed(2)}ms`); return duration; } } // 使用示例 PerformanceTracker.mark('levelLoadStart'); // ... 加载关卡 ... PerformanceTracker.measure('levelLoad'); ``` --- ## 📱 低端机适配 ### 检测低端设备 ```typescript class DeviceDetector { static isLowEndDevice(): boolean { if (!wx.getSystemInfoSync) return false; const info = wx.getSystemInfoSync(); // CPU核心数 ≤ 2 if (info.cpuNum <= 2) return true; // 内存 ≤ 2GB if (info.totalMemory <= 2 * 1024 * 1024 * 1024) return true; // 旧款iPhone if (info.model.includes('iPhone 6') || info.model.includes('iPhone 7')) { return true; } return false; } static applyLowEndSettings() { console.log('[Device] 应用低端机优化设置...'); // 降低目标帧率 GAME_CONFIG.targetFPS = 30; // 减少最大水果数量 GAME_CONFIG.maxFruitsOnScreen = 25; // 禁用部分特效 GAME_CONFIG.enableParticles = false; // 降低音频质量 AudioManager.getInstance().setSFXVolume(0.5); } } ``` ### 分级画质设置 ```typescript enum QualityLevel { Low, Medium, High } class QualitySettings { static apply(level: QualityLevel) { switch (level) { case QualityLevel.Low: // 低画质 this.setMaxParticles(10); this.setShadowEnabled(false); this.setAntiAliasing(false); break; case QualityLevel.Medium: // 中画质 this.setMaxParticles(30); this.setShadowEnabled(true); this.setAntiAliasing(false); break; case QualityLevel.High: // 高画质 this.setMaxParticles(50); this.setShadowEnabled(true); this.setAntiAliasing(true); break; } } } ``` --- ## 🚀 构建发布流程 ### 1. 构建前检查清单 - [ ] 移除所有 `console.log`(或使用条件编译) - [ ] 压缩所有图片和音频 - [ ] 测试广告位ID是否正确 - [ ] 验证存档系统正常 - [ ] 检查内存泄漏(长时间运行测试) ### 2. 构建命令 ```bash # Cocos Creator 命令行构建 cocos build \ --platform wechatgame \ --output ./build/wechatgame \ --debug false \ --compress true ``` ### 3. 上传到微信后台 ```bash # 使用微信开发者工具命令行上传 wechat-miniprogram auto \ --project ./build/wechatgame \ --appid wxb2b7651c561f9d53 \ --version 1.0.0 \ --desc "报恩榴莲v1.0.0" ``` ### 4. 提交审核 1. 登录微信公众平台 2. 进入「版本管理」 3. 选择刚上传的版本 4. 填写审核信息: - 游戏简介 - 分类:休闲 → 益智 - 截图:5张 gameplay 截图 5. 提交审核 --- ## 🐛 常见问题排查 ### Q1: 游戏启动慢 **原因**:资源加载过多 **解决**: - 使用分包加载 - 延迟加载非核心资源 - 压缩图片和音频 ### Q2: 内存持续增长 **原因**:对象未正确释放 **解决**: ```typescript // 确保在场景切换时清理 onDestroy() { this.node.removeAllChildren(); resources.releaseAll(); if (wx.triggerGC) wx.triggerGC(); } ``` ### Q3: 帧率不稳定 **原因**:Draw Calls 过多或逻辑太重 **解决**: - 合并相同材质的Sprite - 使用对象池 - 优化碰撞检测算法 ### Q4: 广告不显示 **原因**:广告位ID错误或未真机测试 **解决**: - 确认广告位ID已替换 - 必须在真机测试(模拟器不显示广告) - 检查网络连接 --- ## 📈 性能监控建议 ### 关键指标 ```typescript class MetricsCollector { private metrics = { fps: 0, memory: 0, drawCalls: 0, avgFrameTime: 0, }; collect() { // FPS this.metrics.fps = director.getScheduler().getFramesPerSecond(); // 内存 if (wx.getSystemInfoSync) { this.metrics.memory = wx.getSystemInfoSync().memoryUsage; } // 上报 if (this.shouldReport()) { wx.reportAnalytics('perf_metrics', this.metrics); } } } ``` ### 异常监控 ```typescript // 全局错误捕获 window.onerror = function(msg, url, line, col, error) { console.error('[Error]', msg, 'at', line, ':', col); // 上报错误 wx.reportAnalytics('js_error', { message: msg, line: line, column: col, stack: error?.stack }); return false; }; ``` --- ## ✨ 总结 ### 优化优先级 1. **P0**:包体大小(必须 ≤ 20MB 主包) 2. **P0**:内存管理(防止崩溃) 3. **P1**:帧率稳定(60 FPS) 4. **P1**:启动速度(< 3秒) 5. **P2**:Draw Calls 优化 6. **P2**:音频优化 ### 持续改进 - 每周分析性能数据 - 根据用户反馈调整难度 - A/B 测试广告频控策略 - 监控留存率和通关率 --- **最后更新**:2026-08-14 **适用版本**:Cocos Creator 3.8 + 微信小游戏