cocos2d-x開發日誌10 ——貪食蛇源碼_cocos2d-x

來源:互聯網
上載者:User

簡單的遊戲開發,比較適合和我一樣的小白練手,除了遊戲結束情境,全部包含在了HelloWorldScene中,先上源碼,注釋已經比較全面,但是具體細節會陸續更新。

HelloWorldScene.h

#ifndef __HELLOWORLD_SCENE_H__#define __HELLOWORLD_SCENE_H__#include "cocos2d.h"#include "GameOverScene.h"#include <string.h>#include <stdlib.h>#include <iostream>#include <sstream>using namespace cocos2d;using namespace std;//貪食蛇移動方向typedef enum{    UP=1,    DOWN,    LEFT,    RIGHT}DIR_DEF;//蛇的頭 身體 食物 共用這個nodeclass SnakeNode:public Node{public:    int row; //行    int col; //列    int dir; //方向    DrawNode *pic;//要載入的圖片};//歡迎情境class HelloWorld : public Layer{public:    virtual bool init();//初始化函數    static Scene * createScene();//擷取歡迎畫面的scene    void menuCloseCallback(Ref * pSender);    CREATE_FUNC(HelloWorld);};//協助畫面class GameHelp: public Layer{public:    virtual bool init();    static Scene * createScene();    CREATE_FUNC(GameHelp);    void menuBackToMain(Ref * pSender);};//遊戲畫面class GameLayer : public Layer{protected:    bool pause_resume=0;//是否暫停 0為繼續,1為暫停    SnakeNode  *sHead;//貪食蛇的頭部    SnakeNode  *sFood;//食物    Vector <SnakeNode*>  allbody;//身體    //暫存起點座標 網格單位長度    int ox = 50;    int oy = 60;    int unit =20;    //獲得分數    int score = 0;public:    //初始化    virtual bool init();    static Scene * createScene();    CREATE_FUNC(GameLayer);    //遊戲邏輯    void logic01(float t);    void menuBackToMain( Ref * pSender);//返回主菜單};#endif // __HELLOWORLD_SCENE_H__

HelloWorldScene.cpp

#include "HelloWorldScene.h"#define START_TAG 10#define HELP_TAG 11#define EXIT_TAG 12#define MAINMENU_TAG 13#define UP_TAG 14#define DOWN_TAG 15#define LEFT_TAG 16#define RIGHT_TAG 17#define PAUSE_TAG 18#define SCORE_TAG 19#define MENU_TAG 20USING_NS_CC;using namespace cocos2d;//************************************************************************////**                                                                    **////**                              歡迎介面                               **////**                                                                    **////************************************************************************////歡迎介面方法Scene * HelloWorld::createScene(){    Scene * scene = Scene::create();    HelloWorld * layer = HelloWorld::create();    scene-> addChild(layer);    return scene;}//歡迎介面初始化方法bool HelloWorld::init(){    if (!Layer::init())        return false;    //遊戲名稱標籤    auto label = Label::createWithTTF("SNAKE", "fonts/Marker Felt.ttf", 50);    label->setColor(Color3B(0,120,100));    label->setPosition(Director::getInstance()->getWinSize().width/2,                       Director::getInstance()->getWinSize().height/2+                       label->getContentSize().height*1.5);    this->addChild(label);    //開始 按鈕    auto start = Label::createWithTTF("Start Game", "fonts/Marker Felt.ttf", 24);    start->setColor(Color3B(0,255,0));    auto start_button = MenuItemLabel::create(start,CC_CALLBACK_1(HelloWorld::menuCloseCallback, this));    start_button->setPositionY(start->getPositionY()+start_button->getContentSize().height*1.5);    start_button->setTag(START_TAG);    //協助 按鈕    auto help = Label::createWithTTF("Help", "fonts/Marker Felt.ttf", 24);    help->setColor(Color3B(0,0,255));    auto help_button = MenuItemLabel::create(help,CC_CALLBACK_1(HelloWorld::menuCloseCallback, this));    help_button->setTag(HELP_TAG);    //退出 按鈕    auto exit = Label::createWithTTF("Exit", "fonts/Marker Felt.ttf", 24);    exit->setColor(Color3B(200,0,200));    auto exit_button = MenuItemLabel::create(exit,CC_CALLBACK_1(HelloWorld::menuCloseCallback, this));    exit_button->setPositionY(start->getPositionY()-exit_button->getContentSize().height*1.5);    exit_button->setTag(EXIT_TAG);    //建立菜單    auto menu = Menu::create(start_button,help_button,exit_button,NULL);    this->addChild(menu);    return true;}//歡迎介面菜單回呼函數void HelloWorld::menuCloseCallback(Ref * pSender){    switch (((MenuItemLabel*)pSender)->getTag()) {        case START_TAG:{            auto scene = GameLayer::createScene();            Director::getInstance()->replaceScene(scene);            break;        }        case HELP_TAG:{            auto scene = GameHelp::createScene();            Director::getInstance()->replaceScene(scene);            break;        }        case EXIT_TAG:            Director::getInstance()->end();#if (CC_TARGET_PLATFORM == CC_PLATFORM_IOS)            exit(0);#endif            break;        default:            break;    }}//************************************************************************////**                                                                    **////**                              協助介面                                **////**                                                                    **////************************************************************************////協助畫面方法Scene * GameHelp::createScene(){    auto scene = Scene::create();    auto layer = GameHelp::create();    scene-> addChild(layer);    return scene;}//協助畫面初始化方法bool GameHelp::init(){    if (!Layer::init())        return false;    //協助文字    auto label = Label::createWithTTF("DO NOT TELL ME YOU CAN'T DO THIS ,YOU FOOL!", "fonts/Marker Felt.ttf", 24);    label->setColor(Color3B(200,70,200));    label->setPosition(Director::getInstance()->getWinSize().width/2,                       Director::getInstance()->getWinSize().height/2+50);    this->addChild(label);    //返回主菜單 按鈕    auto MainMenu = Label::createWithTTF("Main Menu", "fonts/Marker Felt.ttf", 24);    MainMenu->setColor(Color3B(0,200,200));    auto MainMenu_button = MenuItemLabel::create(MainMenu,CC_CALLBACK_1(GameHelp::menuBackToMain, this));    MainMenu_button->setPositionY(MainMenu_button->getPositionY()-50);    MainMenu_button->setTag(EXIT_TAG);    //建立菜單    auto menu = Menu::create(MainMenu_button,NULL);    this->addChild(menu);    return true;}//協助畫面菜單回調方法void GameHelp::menuBackToMain(Ref * pSender){    auto scene = HelloWorld::createScene();    Director::getInstance()->replaceScene(scene);}//************************************************************************////**                                                                    **////**                              遊戲介面                                **////**                                                                    **////************************************************************************////遊戲介面方法Scene * GameLayer:: createScene(){    auto scene = Scene::create();    auto layer = GameLayer::create();    scene->addChild(layer);    return scene;}bool GameLayer::init(){    if (!Layer::init())        return false;    //返回主菜單 按鍵    auto MainMenu = Label::createWithTTF("Main Menu", "fonts/Marker Felt.ttf", 24);    MainMenu->setColor(Color3B(0,200,200));    auto MainMenu_button = MenuItemLabel::create(MainMenu,CC_CALLBACK_1(GameLayer::menuBackToMain, this));    MainMenu_button->setTag(0);    MainMenu_button->setPosition(Director::getInstance()->getWinSize().width*0.3,                                -Director::getInstance()->getWinSize().height*0.3);    //暫停 按鍵    auto pause = Label::createWithTTF("PAUSE", "fonts/Marker Felt.ttf", 24);    pause->setColor(Color3B(255,100,100));    auto pause_button = MenuItemLabel::create(pause,CC_CALLBACK_1(GameLayer::menuBackToMain, this));    pause_button->setTag(PAUSE_TAG);    pause_button->setPosition(Director::getInstance()->getWinSize().width*0.3,                           -Director::getInstance()->getWinSize().height*0.3+140);    //向上 按鍵    auto up = Label::createWithTTF("UP", "fonts/Marker Felt.ttf", 24);    up->setColor(Color3B(0,255,0));    auto up_button = MenuItemLabel::create(up,CC_CALLBACK_1(GameLayer::menuBackToMain, this));    up_button->setTag(UP_TAG);    up_button->setPosition(Director::getInstance()->getWinSize().width*0.3,                        -Director::getInstance()->getWinSize().height*0.3+100);    //向下 按鍵    auto down = Label::createWithTTF("DOWN", "fonts/Marker Felt.ttf", 24);    down->setColor(Color3B(0,255,0));    auto down_button = MenuItemLabel::create(down,CC_CALLBACK_1(GameLayer::menuBackToMain, this));   down_button->setTag(DOWN_TAG);    down_button->setPosition(Director::getInstance()->getWinSize().width*0.3,                           -Director::getInstance()->getWinSize().height*0.3+40);    //向左 按鍵    auto left = Label::createWithTTF("LEFT", "fonts/Marker Felt.ttf", 24);    left->setColor(Color3B(0,255,0));    auto left_button = MenuItemLabel::create(left,CC_CALLBACK_1(GameLayer::menuBackToMain, this));    left_button->setTag(LEFT_TAG);    left_button->setPosition(Director::getInstance()->getWinSize().width*0.3-30,                             -Director::getInstance()->getWinSize().height*0.3+70);    //向右 按鍵    auto right = Label::createWithTTF("RIGHT", "fonts/Marker Felt.ttf", 24);    right->setColor(Color3B(0,255,0));    auto right_button = MenuItemLabel::create(right,CC_CALLBACK_1(GameLayer::menuBackToMain, this));    right_button->setTag(RIGHT_TAG);    right_button->setPosition(Director::getInstance()->getWinSize().width*0.3+30,                             -Director::getInstance()->getWinSize().height*0.3+70);    //建立菜單    auto menu = Menu::create(MainMenu_button,up_button,left_button,down_button,right_button,pause_button,NULL);    this->addChild(menu);    menu->setTag(MENU_TAG);    //顯示分數    char a[3] ;    stringstream stream;    stream << score;    stream >> a;    auto score_label = Label::createWithTTF (a, "fonts/Marker Felt.ttf", 40);    score_label->setPosition(Director::getInstance()->getWinSize().width*0.8,                              Director::getInstance()->getWinSize().height*0.8);    score_label->setTag(SCORE_TAG);    this->addChild(score_label);    //設定網格    for(int i=0; i<11; i++){        for(int j=0; j<11 ;j++){            auto head1 = DrawNode::create();            head1->drawDot(Point(0,0), 1, Color4F(1, 1, 1, 0.5));            head1->setPosition(Vec2(ox+unit*i, oy+unit*j));            this->addChild(head1,4);        }    }    //初始化蛇頭    sHead = new SnakeNode();    sHead->row = arc4random()%10;    sHead->col = arc4random()%10;    sHead->dir = arc4random()%4+1;    CCLOG("%d %d",sHead->row,sHead->col);    sHead->pic = DrawNode::create();    sHead->pic->drawSolidRect(Point(0,0),Point(unit,unit),Color4F(1, 0, 0, 0.8));    sHead->pic->setPosition(Vec2(ox+sHead->col*unit,oy+sHead->row*unit));    this->addChild(sHead->pic,2);    //初始化食物    sFood = new SnakeNode;    sFood->row = arc4random()%10;    sFood->col = arc4random()%10;    sFood->pic = DrawNode::create();    sFood->pic->drawSolidRect(Point(0,0),Point(unit,unit), Color4F(1,1,1,1));    sFood->pic->setPosition(Vec2(ox+sFood->col*unit,oy+sFood->row*unit));    this->addChild(sFood->pic,2);    //初始化身體    //allbody.reserve(1);    //執行計畫任務   this->schedule(schedule_selector(GameLayer::logic01), 0.8);    return true;}//遊戲介面菜單回調方法void GameLayer::menuBackToMain( Ref * pSender){    auto p = (MenuItemLabel*)pSender;    switch (p->getTag()) {        case 0:{            auto scene = HelloWorld::createScene();            Director::getInstance()->replaceScene(scene);            break;        }        case UP_TAG:{            if(sHead->dir!=DIR_DEF::DOWN)            sHead->dir = DIR_DEF::UP;            break;        }        case DOWN_TAG:{            if(sHead->dir!=DIR_DEF::UP)            sHead->dir = DIR_DEF::DOWN;            break;        }        case LEFT_TAG:{            if(sHead->dir!=DIR_DEF::RIGHT)            sHead->dir = DIR_DEF::LEFT;            break;        }        case RIGHT_TAG:{            if(sHead->dir!=DIR_DEF::LEFT)            sHead->dir = DIR_DEF::RIGHT;            break;        }        case PAUSE_TAG:{            if(pause_resume == 0){                pause_resume = 1;                unschedule(schedule_selector(GameLayer::logic01));                MenuItemLabel* l = (MenuItemLabel*)this->getChildByTag(MENU_TAG)-> getChildByTag(PAUSE_TAG);                l->setString("RESUME");            }            else{                //Director::getInstance()->resume();                pause_resume = 0;                schedule(schedule_selector(GameLayer::logic01), 0.8);                MenuItemLabel * l = (MenuItemLabel*)this->getChildByTag(MENU_TAG)->getChildByTag(PAUSE_TAG);                l->setString("PAUSE");            }            break;        }        default:            break;    }}//計劃任務void GameLayer::logic01(float t){    //移動身體    for (int i = allbody.size()-1; i>=0; i--) {        SnakeNode * sn = allbody.at(i);        if (i>0) {            auto snpre = allbody.at(i-1);            sn->dir = snpre->dir;            sn->row = snpre->row;            sn->col = snpre->col;        }        //移動第一個節點        else if (i==0) {            sn->dir = sHead->dir;            sn->row = sHead->row;            sn->col = sHead->col;        }    }    //移動蛇頭    switch (sHead->dir) {        case DIR_DEF::UP:{            sHead->row++;            if(sHead->row >= 10)            sHead->row = 0;            break;        }        case DIR_DEF::DOWN:{            sHead->row--;            if(sHead->row < 0)                sHead->row = 9;            break;        }        case DIR_DEF::LEFT:{            sHead->col--;            if(sHead->col < 0)                sHead->col = 9;            break;        }        case DIR_DEF::RIGHT:{            sHead->col++;            if(sHead->col >= 10)                sHead->col = 0;            break;        }    }    //頭結點重設映像位置    sHead->pic->setPosition(Vec2(ox+sHead->col*unit,oy+sHead->row*unit));    //碰撞檢測    if(sHead->row==sFood->row && sHead->col==sFood->col){        score ++;        char a[3] ;        stringstream stream;        stream << score;        stream >> a;        auto l =(Label *)this->getChildByTag(SCORE_TAG);        l->setString(a);        //食物消失        while(1){            bool flag = true;            sFood->row = rand()%10;            sFood->col = rand()%10;            for (int i=0; i<allbody.size(); i++) {                if(allbody.at(i)->row==sFood->row && allbody.at(i)->col==sFood->col)                    flag = false;            }            if(flag == true) break;        }        sFood->pic->setPosition(Vec2(ox+sFood->col*unit,oy+sFood->row*unit));        //添加身體到集合        SnakeNode  * sn;        sn = new SnakeNode;        SnakeNode  *lastNode;        if (allbody.size()>0)            lastNode = allbody.at(allbody.size()-1);        else            lastNode = sHead;        switch (lastNode->dir) {            case DIR_DEF::UP:                sn->row = lastNode->row-1;                sn->col = lastNode->col;                break;            case DIR_DEF::DOWN:                sn->row = lastNode->row+1;                sn->col = lastNode->col;                break;            case DIR_DEF::LEFT:                sn->row = lastNode->row;                sn->col = lastNode->col+1;                break;            case DIR_DEF::RIGHT:                sn->row = lastNode->row;                sn->col = lastNode->col-1;                break;        }        sn->dir = lastNode->dir;        this->allbody.pushBack(sn);        sn->pic = DrawNode::create();        sn->pic->drawSolidRect(Point(0,0),Point(unit,unit),Color4F(0, 1, 0, 0.8));        sn->pic->setPosition(Vec2(ox+sn->col*unit,oy+sn->row*unit));        this->addChild(sn->pic);    }    //重設身體位置    for (int i = 0; i<allbody.size(); i++) {        allbody.at(i)->pic->setPosition(Vec2(ox+allbody.at(i)->col*unit,oy+allbody.at(i)->row*unit));    }    //game over 判定    for (int i=0; i<allbody.size(); i++)        if(allbody.at(i)->row==sHead->row && allbody.at(i)->col==sHead->col){            auto scene = GameOver::createScene();            Director::getInstance()->replaceScene(scene);        }}

GameOverScene.h

////  GameOverScene.h//  snakegame////  Created by jiumiao on 15/8/9.////#ifndef __snakegame__GameOverScene__#define __snakegame__GameOverScene__#include <stdio.h>#include "cocos2d.h"#include "HelloWorldScene.h"USING_NS_CC;class GameOver : public Layer{public:    bool init();//初始化函數    static Scene * createScene();//擷取歡迎畫面的scene    void menuCloseCallback(Ref * pSender);    CREATE_FUNC(GameOver);};#endif /* defined(__snakegame__GameOverScene__) */

GameOverScene.cpp

////  GameOverScene.cpp//  snakegame////  Created by jiumiao on 15/8/9.////#include "GameOverScene.h"//初始化函數bool GameOver:: init(){    if(!Layer::init())        return false;    //Game Over    auto label = Label::createWithTTF("Game Over", "fonts/Marker Felt.ttf", 50);    label->setColor(Color3B(255,120,100));    label->setPosition(Director::getInstance()->getWinSize().width/2,                       Director::getInstance()->getWinSize().height/2+                       label->getContentSize().height*1.5);    this->addChild(label);    //返回遊戲 按鈕    auto tryagain = Label::createWithTTF("Try Again", "fonts/Marker Felt.ttf", 24);    tryagain->setColor(Color3B(0,200,200));    auto tryagain_button = MenuItemLabel::create(tryagain,CC_CALLBACK_1(GameOver::menuCloseCallback, this));    tryagain_button->setPositionY(tryagain_button->getPositionY()-50);    tryagain_button->setTag(20);    auto menu = Menu::create(tryagain_button,NULL);    this->addChild(menu);    return true;}//擷取結束畫面Scene * GameOver::createScene(){    auto scene = Scene::create();    auto layer = GameOver::create();    scene-> addChild(layer);    return scene;}void GameOver::menuCloseCallback(Ref * pSender){    auto scene = GameLayer::createScene();    Director::getInstance()->replaceScene(scene);}

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.