cocos2dx 象棋

来源:互联网 发布:linux服务器换编码 编辑:程序博客网 时间:2024/04/28 19:14

/********************************************************************  Copyright(c) 2017*  All rights reserved.**  文件名称: Chess.cpp*  简要描述:Chess**  创建日期: 2017-07-21*  作者:gongluck*  说明:**  修改日期: 2017-07-24*  作者:gongluck*  说明:******************************************************************/#include "Define.h"#include "Chess.h"USING_NS_CC;bool Chess::init(){if (!Sprite::init())return false;return true;}Chess* Chess::createChess(TAG tag, TYPE type, cocos2d::Vec2 pos){auto chess = new Chess();if (chess && chess->init()){chess->autorelease();chess->initChess(tag, type, pos);}else{delete chess;chess = NULL;}return chess;}void Chess::initChess(TAG tag, TYPE type, cocos2d::Vec2 pos){std::string picName;if (tag == TAG::RED){picName += "r";}else if (tag == TAG::BLACK){picName += "b";}else{CCLOG("initChess error : tag = %d", tag);return;}this->tag = tag;if (type < TYPE::JIANG || type > TYPE::BING){CCLOG("initChess error : type = %d", type);return;}else{picName += TypeStr[type];picName += ".png";}this->type = type;this->setDisplayFrame(SpriteFrame::create(picName,Rect(0,0,56,56)));this->setPosition(pos);this->setScale(0.75);}void Chess::InitPos(){this->runAction(MoveTo::create(1.5,Vec2(35+initPos.x*36,20+initPos.y*36)));this->currentPos = initPos;this->setVisible(true);}

/********************************************************************  Copyright(c) 2017*  All rights reserved.**  文件名称: GameStart.cpp*  简要描述:GameStart**  创建日期: 2017-07-21*  作者:gongluck*  说明:**  修改日期:*  作者:*  说明:******************************************************************/#include "Define.h"#include "GameStart.h"#include "GameScene.h"USING_NS_CC;bool GameStart::init(){if (!Layer::init())return false;auto size = Director::getInstance()->getVisibleSize();auto red = Sprite::create("chessRed.png");red->setPosition(size.width/2-100,size.height/2);addChild(red, 0, TAG::RED);auto black = Sprite::create("chessBlack.png");black->setPosition(size.width / 2 + 100, size.height / 2);addChild(black, 0, TAG::BLACK);auto listener = EventListenerTouchOneByOne::create();listener->onTouchBegan = CC_CALLBACK_2(GameStart::touchBegan, this);listener->onTouchEnded = CC_CALLBACK_2(GameStart::touchEnded, this);Director::getInstance()->getEventDispatcher()->addEventListenerWithSceneGraphPriority(listener, this);return true;}Scene* GameStart::createScene(){auto scene = Scene::create();auto layer = GameStart::create();scene->addChild(layer);return scene;}bool GameStart::touchBegan(Touch*, Event*){return true;//touchEnded}void GameStart::touchEnded(Touch* touch, Event* event){//getLocation返回的是OpenGL的坐标系,getBoundingBox返回的是父节点坐标系auto pos = touch->getLocation();//OpenGLauto red = static_cast<Sprite*>(getChildByTag(TAG::RED));auto black = static_cast<Sprite*>(getChildByTag(TAG::BLACK));auto size = Director::getInstance()->getVisibleSize();auto select = TAG::NONE;if (red->getBoundingBox().containsPoint(this->convertToNodeSpace(pos))){select = TAG::RED;red->setZOrder(red->getZOrder()+1);}else if (black->getBoundingBox().containsPoint(this->convertToNodeSpace(pos))){select = TAG::BLACK;black->setZOrder(black->getZOrder()+1);}if (select != TAG::NONE){auto moveto1 = MoveTo::create(1, size / 2);auto rotate1 = RotateBy::create(1, 360);auto spawn1 = Spawn::create(moveto1, rotate1, NULL);auto moveto2 = moveto1->clone();auto rotate2 = rotate1->reverse();auto spawn2 = Spawn::create(moveto2, rotate2, NULL);auto action1 = TargetedAction::create(red, spawn1);auto action2 = TargetedAction::create(black, spawn2);auto spawn = Spawn::create(action1, action2, NULL);auto sequence = Sequence::create(spawn,CallFunc::create([=](){Director::getInstance()->replaceScene(TransitionJumpZoom::create(2, GameScene::createScene(select)));}),NULL);runAction(sequence);}}

/********************************************************************  Copyright(c) 2017*  All rights reserved.**  文件名称: GameScene.cpp*  简要描述:GameScene**  创建日期: 2017-07-21*  作者:gongluck*  说明:**  修改日期: 2017-07-24*  作者: gongluck*  说明:******************************************************************/#include "Define.h"#include "Chess.h"#include "GameScene.h"USING_NS_CC;bool GameScene::init(){if (!Layer::init())return false;return true;}Scene* GameScene::createScene(TAG tag){auto scene = Scene::create();auto layer = GameScene::createGame(tag);scene->addChild(layer);return scene;}GameScene* GameScene::createGame(TAG tag){auto layer = new GameScene();if (layer && layer->init()){layer->autorelease();layer->initGame(tag);}else{delete layer;layer = NULL;}return layer;}void GameScene::initGame(TAG Tag){this->tag = Tag;auto size = Director::getInstance()->getVisibleSize();auto background = Sprite::create("background.png");background->setScale(size.height / background->getContentSize().height);background->setPosition(background->getBoundingBox().size.width/2,size.height /2);addChild(background);auto floor = Sprite::create("floor.jpg");floor->setScaleX((size.width - background->getBoundingBox().size.width) / floor->getContentSize().width);floor->setScaleY(size.height / floor->getContentSize().height);floor->setPosition(size.width - floor->getBoundingBox().size.width / 2, size.height / 2);addChild(floor);auto mNew = MenuItemImage::create("new.jpg", "new.jpg",CC_CALLBACK_1(GameScene::menuNew,this));auto mReg = MenuItemImage::create("regret.jpg", "regret.jpg", CC_CALLBACK_1(GameScene::menuRegret, this));auto menu = Menu::create(mNew, mReg, NULL);menu->alignItemsVertically();menu->setPosition(floor->getPosition());addChild(menu);srand(time(NULL));int i = 0;for (int tag = TAG::RED; tag <= TAG::BLACK; ++tag)//先创建红色棋子{chesses[i] = Chess::createChess((TAG)tag, TYPE::JIANG, Vec2(rand() % HEIGHT, rand() % HEIGHT));chesses[i]->setInitPos(Point(4, tag == Tag ? 0:9));addChild(chesses[i]);++i;int flag = 0;for (int times = 0; times < 2; ++times,++flag){chesses[i] = Chess::createChess((TAG)tag, TYPE::SHI, Vec2(rand() % HEIGHT, rand() % HEIGHT));chesses[i]->setInitPos(Point(3+flag*2,tag==Tag?0:9));addChild(chesses[i]);++i;chesses[i] = Chess::createChess((TAG)tag, TYPE::XIANG, Vec2(rand() % HEIGHT, rand() % HEIGHT));chesses[i]->setInitPos(Point(2 + flag * 4, tag == Tag ? 0 : 9));addChild(chesses[i]);++i;chesses[i] = Chess::createChess((TAG)tag, TYPE::MA, Vec2(rand() % HEIGHT, rand() % HEIGHT));chesses[i]->setInitPos(Point(1 + flag * 6, tag == Tag ? 0 : 9));addChild(chesses[i]);++i;chesses[i] = Chess::createChess((TAG)tag, TYPE::CHE, Vec2(rand() % HEIGHT, rand() % HEIGHT));chesses[i]->setInitPos(Point(0 + flag * 8, tag == Tag ? 0 : 9));addChild(chesses[i]);++i;chesses[i] = Chess::createChess((TAG)tag, TYPE::PAO, Vec2(rand() % HEIGHT, rand() % HEIGHT));chesses[i]->setInitPos(Point(1+flag*6,tag==Tag?2:7));addChild(chesses[i]);++i;}flag = 0;for (int times = 0; times < 5; ++times,++flag){chesses[i] = Chess::createChess((TAG)tag, TYPE::BING, Vec2(rand() % HEIGHT, rand() % HEIGHT));chesses[i]->setInitPos(Point(0+flag*2,tag==Tag?3:6));addChild(chesses[i]);++i;}}auto listener = EventListenerTouchOneByOne::create();listener->onTouchBegan = CC_CALLBACK_2(GameScene::touchBegan, this);Director::getInstance()->getEventDispatcher()->addEventListenerWithSceneGraphPriority(listener, this);selected = Sprite::create("selected.png");selected->setScale(0.75);selected->setVisible(false);addChild(selected);selectIndex = -1;for (auto& i : pane){for (auto &j : i){j = -1;}}win = Sprite::create("yingjiemian.png");win->setPosition(size / 2);addChild(win);win->setVisible(false);}void GameScene::menuNew(cocos2d::Ref*){Point pos;int index = 0;for (auto i : chesses){i->InitPos();pos = i->getInitPos();pane[(int)pos.x][(int)pos.y] = index;++index;}selected->setVisible(false);selectIndex = -1;turn = tag;steps.clear();}void GameScene::menuRegret(cocos2d::Ref*){if (steps.size() > 0){Step step = steps.back();Point from = step.from;Point to = step.to;chesses[pane[(int)to.x][(int)to.y]]->runAction(MoveTo::create(0.1, Vec2(35 + from.x * 36, 20 + from.y * 36)));chesses[pane[(int)to.x][(int)to.y]]->setPos(from);pane[(int)from.x][(int)from.y] = pane[(int)to.x][(int)to.y];pane[(int)to.x][(int)to.y] = step.killnum;if (step.killnum != -1)chesses[step.killnum]->setVisible(true);steps.pop_back();selected->setVisible(false);selectIndex = -1;turn = turn == TAG::RED ? TAG::BLACK : TAG::RED;}}bool GameScene::touchBegan(cocos2d::Touch* touch, cocos2d::Event*){auto touchPos = touch->getLocation();//OpenGLint x = (touchPos.x - 35 + 18) / 36;int y = (touchPos.y - 20 + 18) / 36;CCLOG("x=%d,y=%d", x, y);if (x<0 || x>9 || y<0 || y>10)return false;moveChess(selectIndex, Point(x, y));return false;}bool GameScene::moveChess(int index, Point pos){if (pane[(int)pos.x][(int)pos.y] != -1 && chesses[pane[(int)pos.x][(int)pos.y]]->getTag() == turn)//点中棋子是我方{selected->setVisible(true);selected->setPosition(35 + 36 * pos.x, 20 + 36 * pos.y);selectIndex = pane[(int)pos.x][(int)pos.y];return false;//没有移动}else{if (index == -1)return false;if (moveChessFromTo(chesses[index]->getType(), chesses[index]->getPos(), pos)){selected->setVisible(false);selectIndex = -1;turn = turn == TAG::RED ? TAG::BLACK : TAG::RED;}}}bool GameScene::moveChessFromTo(TYPE type, cocos2d::Point from, cocos2d::Point to){int x1 = from.x;int x2 = to.x;int y1 = from.y;int y2 = to.y;int d_x = abs(x1 - x2);int d_y = abs(y1 - y2);bool res = false;int num = 0;Step step;switch (type){case TYPE::JIANG:if (x2 < 3 || x2 >5 || (y2 > 2 && y2 <7) || d_x>1 || d_y > 1 || (x1 != x2 && y1 != y2))res = false;elseres = true;break;case TYPE::SHI:if (d_x != 1 || d_y != 1 || x2 < 3 || x2 >5 || (y2 > 2 && y2 <7))res = false;else res = true;break;case TYPE::XIANG:if (d_x != 2 || d_y != 2 || (y1 <= 4 && y2>4) || (y1 > 4 && y2 <= 4) || pane[(x1 + x2) / 2][(y1 + y2) / 2] != -1)res = false;elseres = true;break;case TYPE::MA:if (d_x == 2 && d_y == 1){if (pane[(x1 + x2) / 2][y1] != -1)res = false;elseres = true;}else if (d_y == 2 && d_x == 1){if (pane[x1][(y1 + y2) / 2] != -1)res = false;elseres = true;}elseres = false;break;case TYPE::CHE:if (d_x > 0 && d_y > 0)res = false;res = true;if (d_x == 0){auto min = y1 < y2 ? y1 : y2;auto max = y1 > y2 ? y1 : y2;for (int temp = min+1; temp < max; ++temp){if (pane[x1][temp] != -1)res = false;}}else if (d_y == 0){auto min = x1 < x2 ? x1 : x2;auto max = x1 > x2 ? x1 : x2;for (int temp = min+1; temp < max; ++temp){if (pane[temp][y1] != -1)res = false;}}break;case TYPE::PAO:num = 0;if (d_x == 0){auto min = y1 < y2 ? y1 : y2;auto max = y1 > y2 ? y1 : y2;for (int temp = min + 1; temp < max; ++temp){if (pane[x1][temp] != -1)++num;}if ((num == 0 && pane[x2][y2] == -1) || (num == 1 && pane[x2][y2] != -1 && chesses[pane[x2][y2]]->getTag() != turn))res = true;}else if (d_y == 0){auto min = x1 < x2 ? x1 : x2;auto max = x1 > x2 ? x1 : x2;for (int temp = min + 1; temp < max; ++temp){if (pane[temp][y1] != -1)++num;}if ((num == 0 && pane[x2][y2] == -1) || (num == 1 && pane[x2][y2] != -1 && chesses[pane[x2][y2]]->getTag() != turn))res = true;}elseres = false;break;case TYPE::BING:if (d_y == 0 && d_x == 1 && ((chesses[pane[x1][y1]]->getTag() == tag && y1>4) || (chesses[pane[x1][y1]]->getTag() != tag && y1<5)))res = true;else if (d_x == 0 && d_y == 1){if ((chesses[pane[x1][y1]]->getTag() == tag && y2 > y1) || (chesses[pane[x1][y1]]->getTag() != tag && y2 < y1))res = true;else res = false;}elseres = false;break;default:res = false;break;}if (res){step.from = from;step.to = to;step.killnum = -1;chesses[pane[(int)from.x][(int)from.y]]->runAction(MoveTo::create(0.5, Vec2(35 + x2 * 36, 20 + y2 * 36)));chesses[pane[(int)from.x][(int)from.y]]->setPos(to);if (pane[(int)to.x][(int)to.y] != -1){step.killnum = pane[(int)to.x][(int)to.y];chesses[pane[(int)to.x][(int)to.y]]->setVisible(false);if (chesses[pane[(int)to.x][(int)to.y]]->getType() == TYPE::JIANG){win->setVisible(true);scheduleOnce(schedule_selector(GameScene::winCall), 2.0f);}}steps.push_back(step);pane[(int)to.x][(int)to.y] = pane[(int)from.x][(int)from.y];pane[(int)from.x][(int)from.y] = -1;}return res;}void GameScene::winCall(float dt){win->setVisible(false);}

https://github.com/gongluck93/GameChineseChess.git