這世上隻有一種成功,就是能夠用自己喜歡的方式度過自己的一生!
1. 項目基本結構
+assets (項目資源的根目錄名)
-Texture (存放其他資源)
-Script (存放腳本檔案) ccc中腳本名就是元件名,大小寫敏感!
-Scene (存放遊戲場景)
2. 腳本檔案的結構
cc.Class({
extends: cc.Component,
properties: {
label: {
default: null,
type: cc.Label
},
// defaults, set visually when attaching this script to the Canvas
text: 'Hello, World!'
},
// 用于初始化
onLoad: function () {
this.label.string = this.text;
},
// called every frame
update: function (dt) {
},
});
properties :元件(挂載到場景中的節點上,提供控制節點的各種功能;這些properties可以直接在屬性檢查器中設定)
onload :頁面一加載完就執行裡面的函數代碼
update : 根據時間實時更新,更新回調
3. Prefab(預制資源)
需要重複生成的節點,我們可以将他儲存成Prefab(預制)資源,作為我們動态生成節點時使用的模闆
比如将Texture檔案夾下的一張圖檔,拖到層級管理器系統即是場景的canvas裡面,再從層級管理器拖到Texture檔案夾中就是預制資源(預制資源的圖示是個灰色正方形)啦(我也覺得這操作有點奇怪)
4. 學習ccc需要對JavaScript非常熟悉
5. 常見基礎 API
cc.moveBy("幾秒",cc.p("橫坐标","縱坐标")) 移動指定的距離
cc.moveTo("幾秒",cc.p("橫坐标","縱坐标")) 移動到目标位置
cc.easeCubicActionOut() 建立 easeCubicActionOut 緩動對象 ,就是緩慢減速的一種效果
cc.repeatForever("一個序列") 永遠地重複一個動作
node.runAction("動作序列名") 執行并傳回該執行的動作。該節點将會變成動作的目标。
this.node.addChild("節點名","層級數字"); 添加子節點
"節點名".setPosition(); 設定節點在父節點坐标系中的位置
cc.callFunc 執行回調函數
"節點名".removeFromParent 從父節點中删除該節點
cc.sequence(); 順序執行動作,建立的動作将按順序依次運作
6. Scene介紹和基本操作
Scene 每個遊戲都會用到場景切換!
Director類 遊戲導航儀,控制 初始化,場景切換,遊戲暫停繼續等等
cc.director.loadScene("場景名"); 加載一個場景
cc.director.preloadScene("場景名"); 預加載場景(比如圖檔資源比較大就可以用它預先加載)
this.node.on("事件名","函數"); 事件(事件名,function)
this.schedule(function(){},1); 類似js的setTimeout
改變一個标簽上面的文字居然是這樣的 this.timeLabel.string=4; (說好的和js差不多呢)
模拟手機遊戲的場景的canvas要改成 W:640 H: 960
7. 玩家輸入事件文法
EventTarget 事件目标是事件觸發時,分派的事件對象,Node 是最常見的事件目标, 但是其他對象也可以是事件目标
8. 關閉左下角的fps面闆,在場景腳本的檔案中 onLoad 的函數中寫以下:
cc.director.setDisplayStats(false);
=======================================================
騰訊課堂-cocos creator/cocos 2dx 入門 聽課筆記
1. 使用ts來做ccc開發建立的腳本檔案是這樣的: (代碼實作一隻扇翅膀的小鳥)
const {ccclass, property} = cc._decorator;
@ccclass
export default class NewClass extends cc.Component {
@property(cc.Label)
label: cc.Label = null;
@property(cc.Sprite)
bird0: cc.Sprite = null;
@property(cc.Sprite)
bird1: cc.Sprite = null;
@property(cc.Sprite)
bird2: cc.Sprite = null;
@property(cc.Sprite)
bird3: cc.Sprite = null;
@property(cc.Node)
birdParent: cc.Node = null;
@property
text: string = 'hello';
time: number = 0; // 距離上次切換顯示的小鳥 流失的時間
// LIFE-CYCLE CALLBACKS:
// onLoad () {}
start () {
}
update (dt: number) {
// console.log(dt);
let timeTmp = this.time + dt;
this.time = timeTmp;
if(this.time > 0.5){
if(this.bird0.node.active){
this.bird0.node.active = false;
this.bird1.node.active = true;
}else if (this.bird1.node.active){
this.bird1.node.active = false;
this.bird2.node.active = true;
}else if (this.bird2.node.active){
this.bird2.node.active = false;
this.bird3.node.active = true;
}else if (this.bird3.node.active){
this.bird3.node.active = false;
this.bird0.node.active = true;
}
this.time = 0;
}
let birdY = this.birdParent.y;
this.birdParent.y = birdY - 1;
}
}
// 重點來了,自定義枚舉
/**
* 全局變量
* const LEVEL = cc.Enum({EASY:1,HARD:2});
*/
@property({
type:LEVEL
})
enumVa = LEVEL.EASY;
2. 幀的概念是這樣的: 比如一秒60幀,說明一秒鐘畫面重新整理了60次,幀數為 1/60
3. 節點 Node 是包含 元件的
4. 代碼執行遇到return整個函數就都不執行了
5. BMfont 可以用圖檔數字來代替真實數字(不知道怎麼做的)
=============================================================
1. ccc是一個元件化的開發工具
2. Prefab: 預制體,預制資源
// 預(提前)制體
@property(cc.Prefab)//預制體類型
myPrefab:cc.Prefab=null;//需要被克隆的對象
//程式運作後加載對象
start(){
var loadobj =cc.instantiate(this.myPrefab);//将預制體克隆到場景
this.node.addChild(loadobj);//将克隆出的物體作為子物體
//設定物體位置
loadobj.setPosition(cc.p(300,-150));
//5秒之後銷毀對象
setTimeout(
function(){ //匿名方法
loadobj.destroy();
}
,5000);
}
3. ccc 的生命周期函數:
- onLoad(會在這個元件所在的場景被載入的時候觸發,執行最早的方法 隻執行一次,在場景加載後立刻執行)
- start(會在元件第一次激活前,也就是第一次執行 update 之前觸發,start 在onload 之後執行隻執行一次)
- update(遊戲開發一個關鍵是在每一幀渲染前更新物體的行為,狀态和方位。這些更新操作通常都放在 update 回調中,會在所有動畫更新前執行)(update 可以不帶參數 參數的意思是遊戲一幀執行的時間 大概為0.017秒 數值不固定)
- lateUpdate(動畫更新後進行額外操作,在update執行之後馬上執行 ,需要用到 lateUpdate 回調)
- onDestroy(當元件調用了 destroy(),會在該幀結束被統一回收,此時會調用 onDestroy 回調。執行最晚的方法,物體被銷毀之前執行)
onEnable(當元件的 enabled 屬性從 false 變為 true 時,會激活 onEnable 回調。倘若節點第一次被 建立且 enabled
為 true,則會在 onLoad 之後,start 之前被調用。腳本啟用會執行)
- onDisable(當元件的 enabled 屬性從 true 變為 false 時,會激活 onDisable 回調,腳本禁用會執行)
4. Cocos Creator 中腳本名稱就是元件的名稱,這個命名是大小寫敏感的!如果元件名稱的大小寫不正确,将無法正确通過名稱使用元件!
5. 通過學習官網demo摘星星總結開發流程:
- 找好遊戲相關資源,包括圖檔,音頻,位圖字型檔案等
- 建立遊戲場景(幾個遊戲畫面就幾個場景)(往場景添加背景,主角等)
- 給你的主角寫腳本(在 properties 中定義主角會用到的變量--想象主角會做什麼動作,如主角會一直跳,我們還可以控制他左右走,跳有高度,也有跳一次所需 時間,左右走有速度,加速度等)
properties: {
}
- 編寫主角動作代碼(主角自動執行的動作,如跳躍,為跳躍寫一個方法),既然是自動執行就可以寫在生命周期函數onload方法裡面初始化調用;控制移動的再寫一個方法,監聽我們的按鍵,設定速度之類的屬性
- 重複生成的東西就要做成預制資源,為這個預制資源建立一個腳本檔案
- 添加遊戲控制腳本,主邏輯包括計分,遊戲開始,遊戲失敗等邏輯,一般綁在場景的canvas上面
- 得分一般都是一個label标簽,再價格位圖字型,然後主邏輯腳本繼續寫得分邏輯
- 最後加入音效
=================================================
1. 在場景的canvas的屬性檢查器中找到Group點選編輯可以分組配置碰撞檢測
2. 添加實體邊緣步驟(點選節點-添加元件-實體-collider-Box)如果邊界是靜止的嗎,要在Rigidbody--type--static
3. 什麼是ccc元件化開發: 節點 + 元件1 + 元件2 + 元件3 。。。 (也就是一個節點帶着不同功能的元件)(開發一個功能,都是從元件開始的)
a: 建立一個元件類
b: new 元件類出來
c: 管理這些元件執行個體
(1): 運作場景的時候初始化:
周遊場景裡面的每個節點,
周遊節點上面的每個元件執行個體;
調用 元件執行個體.onLoad, --> 元件執行個體在加載的時候調用;
調用 元件執行個體.start -->元件執行個體在開始運作之前調用一次;
(2): 每次遊戲重新整理的時候
4. 在一個節點操作 添加我們自己定義的腳本元件原來就是 執行個體化一個類
5. 開啟實體引擎:
cc.director.getPhysicsManager().enabled = true;
開啟調試狀态/模式(給指定實體系統需要繪制哪些調試資訊):
var draw = cc.PhysicsManager.DrawBits;
cc.director.getPhysicsManager().debugDrawFlags = draw.e_shapeBit|draw.e_jointBit;
實體引擎的腳本要挂載到根節點上,然後一定要在該腳本的onload()方法中所有的動作初始化前開啟實體引擎。
6. 弧度轉角度: 角度值 = 弧度值*180 / Math.PI
7. 碰撞檢測:
- onBeginContact: 碰撞開始被調用
- onEndContact: 碰撞結束被調用
- onPreSolve: 碰撞接觸更新前調用
- onPostSolve: 碰撞接觸更新後調用
- 參數:contact 碰撞資訊 ,selfCollider 自己的碰撞器 , otherCollider 撞到的誰
8. 微信打包釋出:
- 釋出微信的話 canvas 節點上隻能選擇 Fit Width ,Fit Height 不能選
- 項目--建構釋出--釋出平台(Wechat Game),MD5 Cache 選上,裝置方向(豎屏選Portrait,橫屏選landscape),appid(自己填自己的)--建構--運作(就會打開微信開發工具)--預覽--掃描二維碼玩遊戲
- cocos creator--偏好設定--原生開發環境--wechatGame程...(選擇微信開發工具的位址exe的位置)
===============================================
1. moveBy:移動指定的距離
var jumpUp = cc.moveBy(this.jumpTimes,cc.p(0,this.jumpHeight));
2. cc.sequence: 順序執行動作,建立的動作将按順序依次運作
var seq = cc.sequence(this.jumpAction,this.maxMoveSpeed);
3. runAction: 執行并傳回該執行的動作。該節點将會變成動作的目标。
this.node.runAction(seq);
4. getComponent: 擷取節點上指定類型的元件,如果節點有附加指定類型的元件,則傳回,如果沒有則為空。
傳入參數也可以是腳本的名稱。
var HeroPlayer = require("HeroPlayer");
...
var hero = self.player.getComponent(HeroPlayer);
5. 除了微信小遊戲以外,其他類型的小遊戲 Canvas 中的Fit Height與Fit Width 一定要勾選上(為了适配)
6. cc.winSize: 為目前的遊戲視窗的大小。
7. 擷取一張圖檔的寬度:
this._width = this.groundImg.spriteFrame.getRect().width;
8. 定時器:參數是回調函數和時間
this.schedule(function(),this.move_time)
9. 寫動畫(幀動畫,例如 像素鳥的小鳥不斷煽動翅膀)
動畫編輯器--添加animation元件--建立animationClip(存儲在anim檔案夾裡面)--點選動畫編輯器的左上角編輯按鈕--屬性清單點選 add property---選擇 cc.Sprite.spriteFrame--點 “+” 号 -- 拉一幀點一次 “+” 号 -- 替換幀對應的圖檔--wrapMode選擇Loop--點選左上角的播放按鈕--儲存--關閉--建立腳本--腳本拉到屬性檢查器--動畫檔案拉到對應位置--playOnload打鈎--預覽
10. 擷取節點上指定類型的元件,如果節點有附加指定類型的元件,則傳回,如果沒有則為空。傳入參數也可以是腳本的名稱:
var pipeUp = cc.instantiate(this.pipePrefabs[0]);
pipe.getComponent('Pipe').init(0);
11. 傳回父節坐标系下的軸向對齊的包圍盒:(包圍後是以盒的左下角為中心的)
var boundingBox = node.getBoundingBox();
12. 擷取與設定本地 localstorage 的值:
cc.sys.localStorage.getItem('name');
cc.sys.localStorage.setItem('name',score);
13. 動畫效果(例如為得分文字添加小動畫):
- scaleTo 将節點大小縮放到指定的倍數
- sequence 順序執行動作,建立的動作将按順序依次運作。
var action1 = cc.scaleTo(this.scoreTime,1.1,0.6);
var action2 = cc.scaleTo(this.scoreTime,0.8,1.2);
var action3 = cc.scaleTo(this.scoreTime,1,1);
//播放形變動畫
this.curScoreText.node.runAction(cc.sequence(action1,action2,action3));
========================================
1. 任何一個節點都會有一個 cc.Node(cc.Node是場景樹中的節點對象);
2. cc.Node.rotation: 旋轉,順時針為正,數學逆時針為正;
3. cc.Node.anchor: 錨點,左下角(0,0),右上角(1,1),可以超過這個範圍;
4. 在代碼元件裡面,使用 this.node 通路這個元件執行個體挂載的節點對象;
5. cc.Node.children/childrenCount: 獲得孩子節點數組、孩子節點數量;
6. cc.Node場景樹相關方法:
- getChildByName: 通過名稱擷取節點的子節點
- new cc.Node():代碼中建立一個節點
- setPosition/getPosition: 擷取或設定節點的相對位置
- cc.find(): 友善,不通用, 消耗
7. 觸摸事件的類型:START, MOVED, ENDED(物體内彈起), CANCEL(物體外彈起);
- cc.Node.EventType.TOUCH_START
- cc.Node.EventType.TOUCH_MOVE
- cc.Node.EventType.TOUCH_END
- cc.Node.EventType.TOUCH_CANCEL
8. 監聽觸摸事件: node.on(類型, callback, target(回掉函數的this), [useCapture]);
9. 關閉觸摸事件: node.off(類型, callback, target(回掉函數的this), [useCapture]);
4. targetOff(target):移除所有的注冊事件;
5. 觸摸事件中回調函數的參數t:t.getLocation() 擷取目前觸點位置 ; t.getDelta() 擷取觸點距離上一次事件移動的距離對象,對象包含 x 和 y 屬性(也就是距離上一次觸摸變化了多少)
//在觸摸移動的事件類型中的回調函數
var delta = t.getDelta();
this.node.x += delta.x;
this.node.y += delta.y;
//以上代碼實作節點物體随着你點選移動的位置移動
6. stopPropagationImmediate: 立即停止目前事件的傳遞,事件甚至不會被分派到所連接配接的目前目标;
7. 監聽鍵盤事件:cc.SystemEvent.on(type, function, target, useCapture);監聽的時候,我們需要一個cc.SystemEvent類的執行個體,我們有一個全局的執行個體cc.systemEvent,小寫開頭(實際使用時小寫開頭的)
- cc.SystemEvent.EventType.KEY_DOWN 按鍵按下;
- cc.SystemEvent.EventType.KEY_UP 按鍵彈起;
8. 自定義事件:
- 監聽:this.node.on(“自定義事件名稱”, function, target, useCapture);
- 自派送: emit(“事件名稱”, [detail]); 隻有自己能夠收到;
- 冒泡派送: dispatchEvent(new cc.Event.EventCustom(“name”, 是否冒泡傳遞));
start: function() {
// 派發者,隻能傳遞給自己,不會向上傳遞
this.node.emit("pkg_event", {blake: "huang"});
// end
// 派送者,不隻是發給自己,發給我們這個體系;
// true/false, true向上傳遞, false不向向上傳遞
var e = new cc.Event.EventCustom("pkg_event", true);
e.detail = {blake: "huang"};
this.node.dispatchEvent(e);
},
9. ccc坐标系:
- 相對(節點)坐标系,兩種相對節點原點的方式(1) 左下角為原點, (2) 錨點為原點(AR)
- 節點坐标和螢幕坐标的互相轉換; 我們到底使用哪個?通常情況下帶AR;
// 節點坐标轉到螢幕(世界)坐标 cc.p(0, 0)
var w_pos = this.node.convertToWorldSpace(cc.p(0, 0)); // 左下角為原點的 cc.p(430, 270)
console.log(w_pos);
w_pos = this.node.convertToWorldSpaceAR(cc.p(0, 0)); // 錨點為原點 cc.p(480, 320)
console.log(w_pos);
// end
var w_pos = cc.p(480, 320);
var node_pos = this.node.convertToNodeSpace(w_pos);
console.log(node_pos); // cc.p(50, 50)
node_pos = this.node.convertToNodeSpaceAR(w_pos);
console.log(node_pos); // cc.p(0, 0)
// 擷取節點的包圍盒, 相對于父親節點坐标系下的包圍盒
var box = this.node.getBoundingBox();
console.log(box);
// 世界坐标系下的包圍盒
var w_box = this.node.getBoundingBoxToWorld();
console.log(w_box);
this.node.on(cc.Node.EventType.TOUCH_START, function(t) {
var w_pos = t.getLocation();
var pos = this.node.convertToNodeSpaceAR(w_pos);
console.log(pos);
pos = this.node.convertTouchToNodeSpaceAR(t);
console.log("====", pos);
}, this);
// 我要把目前這個sub移動到世界坐标為 900, 600;
//
// 把世界坐标轉到相對于它的父親節點的坐标
var node_pos = this.node.parent.convertToNodeSpaceAR(cc.p(900, 600));
this.node.setPosition(node_pos); // 相對于this.node.parent這個為參照物,AR為原點的坐标系
// end
// 擷取目前節點的世界坐标;
this.node.convertToWorldSpaceAR(cc.p(0, 0));
10. Action的使用:
- Action類是動作指令,我們建立Action,然後節點運作action就能夠執行Action的動作;
- Action分為兩類: (1) 瞬時就完成的ActionInstant, (2) 要一段時間後才能完成ActionIntervial;
- cc.Node runAction: 節點運作action;
-
cc.moveTo, cc.moveBy To: 目标 By: 變化
MoveTo:(x, y) → (x1, y1)
MoveBy:(x, y) → (x + x1, y + y1)
- cc.sequnce, cc.repeat, cc.repeatForever
- Action easing(緩動的方式): 加上緩動特效, cc.easeXXXXX檢視文檔設定自己想要的緩動對象
- stopAction: 停止運作action
- stopAllActions: 停止所有的action;
onLoad: function () {
// move
// var mto = cc.moveTo(1, cc.p(100, 100)); // cc.moveTo(1, x, y);
// this.node.runAction(mto);
// var mby = cc.moveBy(1, cc.p(100, 100)); // cc.moveBy(1, x, y); 變化多少
// this.node.runAction(mby);
// rotate
// var rto = cc.rotateTo(1, 180); // 旋轉到180度; rotation 180;
// this.node.runAction(rto);
// var rby = cc.rotateBy(1, 75); // 在原來的基礎上,變化75,可正,可負
// this.node.runAction(rby);
// scale
// this.node.scale = 2;
// var sto = cc.scaleTo(1, 1.1); // 到1.1倍
// this.node.runAction(sto);
// this.node.scale = 2;
// var sby = cc.scaleBy(1, 1.1); // 原來的基礎,變化1.1 * 2
// this.node.runAction(sby);
// opactify
// var fin = cc.fadeIn(1);
// this.node.opacity = 0;
// this.node.runAction(fin);
// var fout = cc.fadeOut(1);
// this.node.runAction(fout); // 物體還是在的的
// var fto = cc.fadeTo(1, 128);
// this.node.runAction(fto);
// function Action
/*var func = cc.callFunc(function() {
console.log("call Func actin!!!!!");
}.bind(this));
console.log("begin ####");
this.node.runAction(func);
console.log("end ####");*/
// 移動到 目的地,後,隐藏這個物體怎辦? // 指令清單, [Action1, A2, A3],
// seq Action
/*var m1 = cc.moveTo(1, 100, 100);
var fout = cc.fadeOut(0.5);
var seq = cc.sequence([m1, fout]);
this.node.runAction(seq);*/
// 一個節點可以同時運作多個Action, 一邊,一邊
/*var m1 = cc.moveTo(1, 100, 100);
var fout = cc.fadeOut(0.5);
this.node.runAction(fout);
this.node.runAction(m1);*/
// 不斷的放大縮小
/*var s1 = cc.scaleTo(0.8, 1.1);
var s2 = cc.scaleTo(0.8, 0.8);
var seq = cc.sequence([s1, s2]);
var rf = cc.repeatForever(seq);
this.node.runAction(rf);*/
// 勻速的飛過,傻了, 緩動
// 回彈
/*this.node.y = 0;
var m = cc.moveTo(1, 100, 0).easing(cc.easeBackOut());
this.node.runAction(m);*/
/*var r = cc.rotateBy(3, 360).easing(cc.easeCubicActionOut());
var rf = cc.repeatForever(r);
this.node.runAction(rf);
// this.node.stopAction(rf);
this.node.stopAllActions();*/
// end
// 移動了到100, 0,删除
/*var m = cc.moveTo(1, 100, 0);
var end_func = cc.callFunc(function() {
this.node.removeFromParent();
}.bind(this));
var seq = cc.sequence([m, end_func]);
this.node.runAction(seq);*/
// cc.Delay,
var d1 = cc.delayTime(3);
var fout = cc.fadeOut(0.5);
var end_func = cc.callFunc(function() {
this.node.removeFromParent();
}.bind(this))
var seq = cc.sequence([d1, fout, end_func]);
this.node.runAction(seq);
},
11. cc.Component屬性(元件類,所有元件的基類)
var my_item = require("my_item");
...
properties: {
//基本資料類型,數,bool,字元串,color,pos,size
speed: 100,
is_debug: false,
url_str: "",
color: cc.color(0,0,0,255),
pos: cc.p(0,0),
size: cc.Size(100,100)
// 系統的元件
sprite_item: {
type: cc.Sprite,
default: null, // null/[]
}
// 元件的代碼元件
custom_comp: {
type: my_item,
default: null, // null/[]
},
}
12. cc.Sprite: 配置圖檔的SIZE_MODE
- CUSTOM 大小和CCNode的大小一緻;
- RAW 原始的圖檔大小;
- TRIMMED 大小為原始圖檔大小, 顯示的内容是裁剪掉透明像素後的圖檔;
trim: 是否裁剪掉 圖檔的透明區域, 如果勾選,就會把完全透明的行和列裁掉, 做幀動畫的時候,我們一般是用原始大小不去透明 度,動畫,不至于抖動;
13. Filled模式(遊戲中道具的時間進度顯示條、個性化時間進度條案例等應用,比較常用,最好掌握)
- 配置Filled模式, 設定為Radius參數
- 配置Radius的參數模式,
- 中心: 位置坐标(0, 1小數), (0, 0)左下腳, (1, 1) 右上角 (0.5, 0.5) 中心點
- Fill Start 開始的位置: 0 ~1, 右邊中心點開始,逆時針走
- Fill Range: 填充總量(0, 1];
- FillRange為正,那麼就是逆時針,如果為負,那麼就是順時針;