Exemple #1
0
void BallMap::actionEndCallback(CCNode *node)
{
    BallSprite *ball = (BallSprite *)node;
    ball->set_isMoving(false);
    m_matrix[ball->getRow() * (int)m_size.width + ball->getCol()] = NULL;
    ball->removeFromParent();
}
Exemple #2
0
void BallMap::removeBall()
{
    // make sequence remove
    m_isAnimationing = true;
    
    std::list<BallSprite *>::iterator itList;
    for (itList = m_readyRemoveList.begin(); itList != m_readyRemoveList.end(); itList++)
    {
        BallSprite *ball = dynamic_cast<BallSprite*>(*itList);
        
        if (!ball)
        {
            continue;
        }
    
        if (ball->getIsNeedRemove())
        {
            m_isNeedFillVacancies = true;//需要掉落
            m_isNeedCheckSelf = true;
            
            explodeBall(ball);
        }
    }
    m_readyRemoveList.clear();
}
void GameScene_Box2D::delTouchedBalls() {
    
    std::vector<BallSprite*>::iterator tempIterator;
    std::vector<BallSprite*> tmpbollArray;
    
    std::vector<std::vector<BallSprite*>::iterator> deleteIteratorArray;
    
    for( tempIterator = _bollArray.begin(); tempIterator != _bollArray.end(); tempIterator++ ) {
        BallSprite *ball = (BallSprite *)*tempIterator;
        if (ball->getDeleteState()==BallSprite::deleteState::kDelete) {
            _delballPos.push_back(ball->getPosition());
           // _world->DestroyBody(ball->getB2Body());
            ball->deleteParticle(_particleSystem,_particleGroup);
            ball->removeFromParent();
        }
        else {
            tmpbollArray.push_back(ball);
        }
    }
    
    _bollArray.clear();
    for (auto nodelball = tmpbollArray.begin(); nodelball != tmpbollArray.end(); nodelball++) {
        BallSprite *ball = (BallSprite *)*nodelball;
        _bollArray.push_back(ball);
    }
    
}
BallSprite *BallSprite::createBallSprite(Node *parent ,b2World *world, const std::string& filename)
{
    BallSprite* pInstance = BallSprite::create();
    
    //Texture2D *texture = Director::getInstance()->getTextureCache()->addImage(filename);
    
    pInstance->setTexture(filename);
    
   
    // shape.m_radius = sptite->getContentSize().width / PTM_RATIO; // 形状の大きさ
   
    /**
     *
     剛体は次の手順で作成する。剛体とは物理エンジンの影響をうけることが出来る物質のこと
     
     1. 位置・減衰率などで剛体を定義する。
     2. 剛体を作成するためにワールドを使用する。
     3. 図形・摩擦・密度などから装備を定義する。
     4. 剛体から装備を作成する。
     */
    b2Body* body; // 剛体。rigid body。
    b2BodyDef bodyDef; // 剛体の定義
    b2CircleShape shape; // 装備の形状
    float radius = getBallRadius();
    shape.m_radius = radius/ PTM_RATIO;;
    b2FixtureDef fixtureDef; // 装備の形状定義
    
    
    // 1. 位置・減衰率などで剛体を定義する。
    bodyDef.type = b2_dynamicBody;
    //bodyDef.position.Set((winSize.width / 2) / PTM_RATIO, (winSize.height) / PTM_RATIO);
    bodyDef.userData = pInstance; // 画像をこの剛体に紐付ける
    
    // 2. 剛体を作成するためにワールドを使用する。
    body = world->CreateBody(&bodyDef);
    
    fixtureDef.shape = &shape; // 形状を紐付ける
    fixtureDef.density = 1; // 密度
    fixtureDef.friction = 0.9; // 摩擦
    
    // 4. 剛体から装備を作成する。
    body->CreateFixture(&fixtureDef);
    
    /** PhysicsSpriteに各種情報をセットする */
    //parent->addChild(pInstance);
    pInstance->setB2Body(body);
    pInstance->setPTMRatio(PTM_RATIO);

    
    parent->addChild(pInstance);
    
    return pInstance;
}
void GameScene::updateBall() {
	if (!isTouched) {
		return;
	}

	for (int i = 0; i < m_activeballs->count(); i++) {
		BallSprite* ball =
				dynamic_cast<BallSprite*>(m_activeballs->objectAtIndex(i));
		if (!ball)
			return;

		CCPoint ballPoint = ball->getPosition();
		float vx = ball->getVelocityX();
		float vy = ball->getVelocityY();

		// ボールの移動
//	    CCLOG("# updateBall1 #ball position X: %f, Y: %f",
//	          ball->getPositionX(), ball->getPositionY());
		ball->setPosition(ccp(ball->getPositionX() + vx,
				ball->getPositionY() + vy));
//	    CCLOG("# updateBall2 #ball position X: %f, Y: %f",
//	          ball->getPositionX(), ball->getPositionY());

		if (ballPoint.y < 0) {
			//ユーザーがボールを奈落に落とした
			onBallLost(ball);
			return;
		}
		//壁との衝突判定
		ball->bounceBall(g_visibleSize);
	}
}
Exemple #6
0
//インスタンス生成
BallSprite* BallSprite::create(BallType type, bool visible)
{
    BallSprite *pRet = new BallSprite();
    if (pRet && pRet->init(type, visible))
    {
        pRet->autorelease();
        return pRet;
    }
    else
    {
        delete pRet;
        pRet = nullptr;
        return nullptr;
    }
}
BallSprite* BallSprite::create(GameLayer * game, int type, CCPoint position) {
    /*
     Create sprite with image file name.
     
     Args:
       pszFileName: char *, string of file name
     
     Returns:
       BallSprite *
     */
    BallSprite *sprite = new BallSprite(game, type, position);
    if (sprite) {
        sprite->initBall();
        sprite->autorelease();
        return sprite;
    }
    CC_SAFE_DELETE(sprite);
    return NULL;
}
void GameScene::updateBlocks() {
	for (int i = 0; i < m_activeballs->count(); i++) {
		BallSprite* ball =
				dynamic_cast<BallSprite*>(m_activeballs->objectAtIndex(i));
		if (!ball)
			return;

		CCRect ballRect = ball->boundingBox();

		CCObject* jt = NULL;
		CCArray* blocksToDelete = new CCArray;

		CCARRAY_FOREACH(m_blocks, jt) {
			CCSprite* block = dynamic_cast<CCSprite*>(jt);
			//            CCLOG("updateGame target.x: %f, target.y: %f, tag: %d",target->getContentSize().width, target->getContentSize().height, target->getTag());
			CCRect blockRect = block->boundingBox();

			//衝突判定
			if (ballRect.intersectsRect(blockRect)) {
				// ボールは跳ね返す
				ball->bounceBall(blockRect, kTagBlock);

				blocksToDelete->addObject(block);

				//スコア加算
				m_score += 100;
				showScore();

				//確率に従ってボーナスアイテムを生成する
				makeItem(block);
			}
		}

		// 当たったブロックを消す
		CCARRAY_FOREACH(blocksToDelete, jt) {
			CCSprite *block = dynamic_cast<CCSprite*>(jt);
			m_blocks->removeObject(block);
			this->removeChild(block, true);

			m_blocksDestroyed++;
		}
BallSprite *GameScene_Box2D::createSprite(Vec2 &pos, Vec2 &velocity){
    std::random_device rd;
    std::mt19937 mt(rd());
    std::uniform_real_distribution<double> intval(0,3);
    
    int val = (int)intval(mt);
    __String *filename;
    BallSprite::ballType type;
    
    switch (val) {
        case 0:
            filename = String::create("ball.png");
            type = BallSprite::ballType::kRed;
            break;
        case 1:
            filename = String::create("pur_ball.png");
            type = BallSprite::ballType::kPurple;
            break;
        case 2:
            filename = String::create("blue_ball.png");
            type = BallSprite::ballType::kBrue;
            break;
        case 3:
            filename = String::create("yellow_ball.png");
            type = BallSprite::ballType::kYellow;
            break;
        default:
            filename = String::create("ball.png");
            type = BallSprite::ballType::kBrue;
            break;
    }
    
    //BallSprite *ball = BallSprite::createBallSprite(this, _world, filename->getCString());
    BallSprite *ball = BallSprite::createParticleSprite(this, _world, _particleSystem, _particleGroup, filename->getCString());
    //ball->setPosition(pos);
    ball->setParticlePpos(_particleSystem, _particleGroup, pos.x, pos.y, velocity.x, velocity.y);
    ball->setTag(spriteType::kBall);
    ball->setBallType(type);
    _bollArray.push_back(ball);
    return ball;
}
void GameScene::setBall() {
	//ボールをバー上に配置する
	if (m_balls->count() <= 0) {
		return;
	}
	BallSprite* ball = dynamic_cast<BallSprite*>(m_balls->objectAtIndex(0));
	CCNode *bar = this->getChildByTag(kTagBar);
//	CCRect rect = bar->boundingBox();
	ball->setPosition(
			ccp(bar->getPositionX(), bar->getPositionY() + bar->getContentSize().height + 10));
//    CCLOG("# setBall #bar.width: %f, height: %f",
//          bar->getContentSize().width, bar->getContentSize().height);
//    CCLOG("# setBall #bar position X: %f, Y: %f",
//          bar->getPositionX(), bar->getPositionY());
//	ball->setPosition(
//			ccp(bar->getPositionX() + bar->getContentSize().width / 2, bar->getPositionY() + bar->getContentSize().height));
	this->addChild(ball);

	m_balls->removeObjectAtIndex(0);
	m_activeballs->addObject(ball);
}
Exemple #11
0
void BallMap::createAndDropBall(int row, int col)
{
    CCSize size = CCDirector::sharedDirector()->getWinSize();
    
    BallSprite *ball = BallSprite::create(row, col);
    
    // create animation
    CCPoint endPosition = positionOfItem(ball);
    CCPoint startPosition = CCPoint(endPosition.x, endPosition.y + size.height / 2);
    ball->setPosition(startPosition);
    float speed = startPosition.y / (2.0 * size.height);
    ball->runAction(CCSequence::create(
                    CCMoveTo::create(speed, endPosition),
                                       CCCallFuncN::create(this, callfuncN_selector(BallMap::setBallNoMoving)),
                                       NULL));
    
    // add to BatchNode
    m_joyPad->get_spriteNode()->addChild(ball);

    m_matrix[row * (int)m_size.width + col] = ball;

}
BallSprite *GameScene_Chipmunk::createSprite(Vec2 &pos){
    std::random_device rd;
    std::mt19937 mt(rd());
    std::uniform_real_distribution<double> intval(0,3);
    
    int val = (int)intval(mt);
    __String *filename;
    BallSprite::ballType type;
    
    switch (val) {
        case 0:
            filename = String::create("ball.png");
            type = BallSprite::ballType::kRed;
            break;
        case 1:
            filename = String::create("pur_ball.png");
            type = BallSprite::ballType::kPurple;
            break;
        case 2:
            filename = String::create("blue_ball.png");
            type = BallSprite::ballType::kBrue;
            break;
        case 3:
            filename = String::create("yellow_ball.png");
            type = BallSprite::ballType::kYellow;
            break;
        default:
            filename = String::create("ball.png");
            type = BallSprite::ballType::kBrue;
            break;
    }
    
    BallSprite *ball = BallSprite::createBallSprite(this, filename->getCString());
    ball->setCenter(pos);
    ball->setTag(spriteType::kBall);
    ball->setBallType(type);
    _bollArray.push_back(ball);
    return ball;
}
Exemple #13
0
BallSprite *BallMap::BallOfPoint(CCPoint *point)
{
    BallSprite *Ball = NULL;
    CCRect rect = CCRect(0, 0, 0, 0);
    
    for (int i = 0; i < m_size.height * m_size.width; i++)
    {
        Ball = m_matrix[i];
        if (Ball)
        {
            rect.origin.x = Ball->getPositionX() - (Ball->getContentSize().width / 2);
            rect.origin.y = Ball->getPositionY() - (Ball->getContentSize().height / 2);
            rect.size = Ball->getContentSize();
            
            if (rect.containsPoint(*point))
            {
                return Ball;
            }
        }
    }
    
    return NULL;
}
Exemple #14
0
void BallMap::update(float dt)
{
    // check if animationing
    if (m_isAnimationing) {
        // init with false
        m_isAnimationing = false;
        for (int i = 0; i < m_size.height * m_size.width; i++)
        {
            BallSprite *ball = m_matrix[i];
            
            if (ball && ball->get_isMoving())
            {
                m_isAnimationing = true;
                break;
            }
        }
    }
    
    // if Ball is moving, ignore use touch event
    m_isTouchEnable = !m_isAnimationing;
    
    if (!m_isAnimationing)
    {
        if (m_isNeedFillVacancies)
        {
            //爆炸效果结束后才掉落新寿司,增强打击感
            fillVacancies();
            m_isNeedFillVacancies = false;
        } else
        {
            if (m_isNeedCheckSelf)
            {
                checkAndRemoveChain();
            }
        }
    }
}
void GameScene_Chipmunk::delTouchedBalls() {
    
    std::vector<BallSprite*>::iterator tempIterator;
    std::vector<BallSprite*> tmpbollArray;
    
    std::vector<std::vector<BallSprite*>::iterator> deleteIteratorArray;
    for( tempIterator = _bollArray.begin(); tempIterator != _bollArray.end(); tempIterator++ ) {
         BallSprite *ball = (BallSprite *)*tempIterator;
        if (ball->getDeleteState()==BallSprite::deleteState::kDelete) {
            _delballPos.push_back(ball->getPosition());
            ball->removeFromParent();
        }
        else {
            tmpbollArray.push_back(ball);
        }
    }
    
    _bollArray.clear();
    for (auto nodelball = tmpbollArray.begin(); nodelball != tmpbollArray.end(); nodelball++) {
        BallSprite *ball = (BallSprite *)*nodelball;
        _bollArray.push_back(ball);
    }
    
}
//指定方向のボールと同じ色かチェックする
bool GameLayer::isSameBallType(BallSprite::PositionIndex current, Direction direction)
{
    //全てのボールのBallTypeを取得
    auto allBalls = getAllBalls();
    
    if (direction == Direction::x)
    {
        if (current.x + 1 > BALL_NUM_X)
            //列が存在しない場合は抜ける
            return false;
    }
    else
    {
        if (current.y + 1 > BALL_NUM_Y)
            //行が存在しない場合は抜ける
            return false;
    }
    
    //現在のボールを取得
    int currentTag = BallSprite::generateTag(BallSprite::PositionIndex(current.x, current.y));
    BallSprite* currentBall = allBalls.at(currentTag);
    
    //次のボールを取得
    int nextTag;
    if (direction == Direction::x)
        nextTag = BallSprite::generateTag(BallSprite::PositionIndex(current.x + 1, current.y));
    else
        nextTag = BallSprite::generateTag(BallSprite::PositionIndex(current.x, current.y + 1));
    auto nextBall = allBalls.at(nextTag);
    
    if (currentBall->getBallType() == nextBall->getBallType())
        //次のボールが同じBallTypeである
        return true;
    
    return false;
}
void GameScene::onBallLost(CCNode* sender) {
	if (UserSettings::getSESetting())
		SimpleAudioEngine::sharedEngine()->playEffect(MP3_BALLLOST);

	BallSprite *ball = dynamic_cast<BallSprite*>(sender);
	if (ball->getIsItem3()) {
		this->removeChild(ball, true);
		m_activeballs->removeObject(ball);
		if (m_activeballs->count() == 0) {
			isTouched = false;
		}
		return;
	}

	cancelTimers();

	//奈落に落ちたボールを削除
	this->removeChild(ball, true);
	m_activeballs->removeObject(ball);

	int remain = this->getBallRemain() - 1;
	this->setBallRemain(remain);

	showBallRemain();

	if (m_activeballs->count() == 0) {
		isTouched = false;
	}

	//ゲームオーバー判定
	if (remain <= 0) {
		this->gameOver();
		return;
	}
	setBall();
}
void GameScene_Box2D::onContactPostSolve(PhysicsContact& contact, const PhysicsContactPostSolve& solve)
{
    auto node1 = contact.getShapeA()->getBody()->getNode();
    auto node2 = contact.getShapeB()->getBody()->getNode();
    if (node1->getTag()== spriteType::kFloor && node2->getTag()== spriteType::kBall) {
        BallSprite *ball = (BallSprite *)node2;
        bool ball_state_none    = (ball->getBallContState() == BallSprite::ballContactState::kNone);
        if (ball_state_none) {
            ball->setBallContState(BallSprite::ballContactState::kFloorContact);
        }
        
    }
    else if (node2->getTag()== spriteType::kFloor && node1->getTag()== spriteType::kBall) {
        BallSprite *ball = (BallSprite *)node1;
        bool ball_state_none    = (ball->getBallContState() == BallSprite::ballContactState::kNone);
        ball->setBallContState(BallSprite::ballContactState::kFloorContact);
        if (ball_state_none) {
            ball->setBallContState(BallSprite::ballContactState::kFloorContact);
        }
    }
    else if (node2->getTag()== spriteType::kBall && node1->getTag()== spriteType::kBall) {
        BallSprite *ball1 = (BallSprite *)node1;
        BallSprite *ball2 = (BallSprite *)node2;
        bool ball1_state_floor   = (ball1->getBallContState() == BallSprite::ballContactState::kFloorContact);
        bool ball2_state_floor   = (ball2->getBallContState() == BallSprite::ballContactState::kFloorContact);
        bool ball1_state_none    = (ball1->getBallContState() == BallSprite::ballContactState::kNone);
        bool ball2_state_none    = (ball2->getBallContState() == BallSprite::ballContactState::kNone);
        bool ball1_state_second  = (ball1->getBallContState() == BallSprite::ballContactState::kSecondContact);
        bool ball2_state_second  = (ball2->getBallContState() == BallSprite::ballContactState::kSecondContact);
        
        if (ball1_state_none || ball2_state_floor) {
            ball1->setBallContState(BallSprite::ballContactState::kSecondContact);
        }
        else if (ball1_state_floor || ball2_state_none) {
            ball2->setBallContState(BallSprite::ballContactState::kSecondContact);
        }
        else if (ball1_state_none || ball2_state_second) {
            ball1->setBallContState(BallSprite::ballContactState::kSecondContact);
        }
        else if (ball2_state_none || ball1_state_second) {
            ball2->setBallContState(BallSprite::ballContactState::kSecondContact);
        }
        
    }
    
}
Exemple #19
0
void BallMap::getRowChain(BallSprite *ball, std::list<BallSprite *> &chainList)
{
    chainList.push_back(ball);// add first Ball
    
    int neighborRow = ball->getRow() - 1;
    while (neighborRow >= 0)
    {
        BallSprite *neighborBall = m_matrix[neighborRow * (int)m_size.width + ball->getCol()];
        if (neighborBall
            && (neighborBall->getImgIndex() == ball->getImgIndex())
            && (!neighborBall->getIsNeedRemove() || !ball->getIsNeedRemove())
            && !neighborBall->getIgnoreCheck())
        {
            chainList.push_back(neighborBall);
            neighborRow--;
        }
        else
        {
            break;
        }
    }
    
    neighborRow = ball->getRow() + 1;
    while (neighborRow < m_size.height)
    {
        BallSprite *neighborBall = m_matrix[neighborRow * (int)m_size.width + ball->getCol()];
        if (neighborBall
            && (neighborBall->getImgIndex() == ball->getImgIndex())
            && (!neighborBall->getIsNeedRemove() || !ball->getIsNeedRemove())
            && !neighborBall->getIgnoreCheck())
        {
            chainList.push_back(neighborBall);
            neighborRow++;
        }
        else
        {
            break;
        }
    }
}
BallSprite *BallSprite::createParticleSprite(Node *parent ,b2World *world, b2ParticleSystem *particleSystem, b2ParticleGroup *particleGroup,const std::string& filename) {
    
    BallSprite* pInstance = (BallSprite *)Sprite::create();
    //BallSprite* pInstance = BallSprite::createBallSprite(parent,world,filename);
    pInstance->setTexture(filename);
    parent->addChild(pInstance);
    
    // 描画用ノードの作成
    DrawNode* draw = DrawNode::create();
    draw->setPosition(Vec2(0, 0));
    pInstance->addChild(draw);
    
    /* 円の描画 */
    draw->drawDot(Vec2(pInstance->getBallRadius()/2, pInstance->getBallRadius()/2), // 中心
                  pInstance->getBallRadius(),                        // 半径
                  Color4F(1, 0.5f, 0, 200)                  // 色
                  );
    
    
    particleSystem->SetRadius(getBallRadius()*1.2/PTM_RATIO);
    
    b2ParticleDef particleDef;
    
    //パーティクルの寿命
    //particleDef.lifetime = 2.0f;
    
    //particleDef.flags = b2_dynamicBody;
    particleDef.flags = b2_waterParticle;
    particleDef.flags |= b2_destructionListenerParticle;
    particleDef.color = b2ParticleColor(100,150,255,255);
    //particleDef.velocity.y = -100;
    
    //グループへのポインタを渡しておく事でそのグループ内で管理する事ができる。
    particleDef.group = particleGroup;
    particleDef.flags = b2_waterParticle;
    
   
    //void** userdata = particleSystem->GetUserDataBuffer();
    particleDef.userData = pInstance;
    particleSystem->CreateParticle(particleDef);
    
    return pInstance;

}
Exemple #21
0
BallSprite* BallSprite::createWithNumber(kBallNumber number)
{
    BallSprite *ballSprite = new BallSprite();
    ballSprite->setNumber(number);
    if(ballSprite && ballSprite->initWithFile(PNG_BALL))
    {
        //ボールの数字をラベルとして付ける
        const char* numberString = CCString::createWithFormat("%d", number)->getCString();
        LabelBMFont* numberLabel = CCLabelBMFont::create(numberString, FONT_NUMBER);
        numberLabel->setPosition(Point(ballSprite->getContentSize().width / 2,ballSprite->getContentSize().height / 2));
        numberLabel->setScale(1.8);
        ballSprite->addChild(numberLabel, kZOrderNumber, kTagNumber);
        
        //ボールのメモリを自動消去
        ballSprite->autorelease();
        
        //作ったSpriteを返す
        return ballSprite;
    } else {
        CC_SAFE_DELETE(ballSprite);
        return nullptr;
    }
}
Exemple #22
0
/*
bool BallMap::ccTouchBegan(CCTouch *touch, CCEvent *unused)
{
    m_srcBall = NULL;
    m_destBall = NULL;
    if (m_isTouchEnable) {
        auto location = touch->getLocation();
        m_srcBall = BallOfPoint(&location);
    }
    return m_isTouchEnable;
}

void BallMap::ccTouchMoved(CCTouch *touch, CCEvent *unused)
{
    if (!m_srcBall || !m_isTouchEnable) {
        return;
    }
    
    int row = m_srcBall->getRow();
    int col = m_srcBall->getCol();
    
    auto location = touch->getLocation();
    auto halfBallWidth = m_srcBall->getContentSize().width / 2;
    auto halfBallHeight = m_srcBall->getContentSize().height / 2;
    
    auto  upRect = CCRect(m_srcBall->getPositionX() - halfBallWidth,
                        m_srcBall->getPositionY() + halfBallHeight,
                        m_srcBall->getContentSize().width,
                        m_srcBall->getContentSize().height);
    
    if (upRect.containsPoint(location)) {
        row++;
        if (row < m_height) {
            m_destBall = m_matrix[row * m_width + col];
        }
        m_movingVertical = true;
        swapBallAndCheck();
        return;
    }
    
    auto  downRect = CCRect(m_srcBall->getPositionX() - halfBallWidth,
                        m_srcBall->getPositionY() - (halfBallHeight * 3),
                        m_srcBall->getContentSize().width,
                        m_srcBall->getContentSize().height);
    
    if (downRect.containsPoint(location)) {
        row--;
        if (row >= 0) {
            m_destBall = m_matrix[row * m_width + col];
        }
        m_movingVertical = true;
        swapBallAndCheck();
        return;
    }
    
    auto  leftRect = CCRect(m_srcBall->getPositionX() - (halfBallWidth * 3),
                          m_srcBall->getPositionY() - halfBallHeight,
                          m_srcBall->getContentSize().width,
                          m_srcBall->getContentSize().height);
    
    if (leftRect.containsPoint(location)) {
        col--;
        if (col >= 0) {
            m_destBall = m_matrix[row * m_width + col];
        }
        m_movingVertical = false;
        swapBallAndCheck();
        return;
    }
    
    auto  rightRect = CCRect(m_srcBall->getPositionX() + halfBallWidth,
                          m_srcBall->getPositionY() - halfBallHeight,
                          m_srcBall->getContentSize().width,
                          m_srcBall->getContentSize().height);
    
    if (rightRect.containsPoint(location)) {
        col++;
        if (col < m_width) {
            m_destBall = m_matrix[row * m_width + col];
        }
        m_movingVertical = false;
        swapBallAndCheck();
        return;
    }
    
    // not a useful movement
}

void BallMap::swapBallAndCheck()
{
    m_isAnimationing = true;
    m_isTouchEnable = false;
    if (!m_srcBall || !m_destBall)
    {
        m_movingVertical = true;
        return;
    }
    
    CCPoint posOfSrc = m_srcBall->getPosition();
    CCPoint posOfDest = m_destBall->getPosition();
    float time = 0.2;
    
    // 1.swap in matrix
    this->swapBall(m_srcBall, m_destBall);
    
    // 2.check for remove able
    std::list<BallSprite *> colChainListOfFirst;
    getColChain(m_srcBall, colChainListOfFirst);
    
    std::list<BallSprite *> rowChainListOfFirst;
    getRowChain(m_srcBall, rowChainListOfFirst);
    
    std::list<BallSprite *> colChainListOfSecond;
    getColChain(m_destBall, colChainListOfSecond);
    
    std::list<BallSprite *> rowChainListOfSecond;
    getRowChain(m_destBall, rowChainListOfSecond);
    
    if (colChainListOfFirst.size() >= 3
        || rowChainListOfFirst.size() >= 3
        || colChainListOfSecond.size() >= 3
        || rowChainListOfSecond.size() >= 3) {
        // just swap
        m_srcBall->runAction(CCMoveTo::create(time, posOfDest));
        m_destBall->runAction(CCMoveTo::create(time, posOfSrc));
        return;
    }
    
    // 3.no chain, swap back
    this->swapBall(m_srcBall, m_destBall);
    
    m_srcBall->runAction(CCSequence::create(
                                      CCMoveTo::create(time, posOfDest),
                                      CCMoveTo::create(time, posOfSrc),
                                      NULL));
    m_destBall->runAction(CCSequence::create(
                                      CCMoveTo::create(time, posOfSrc),
                                      CCMoveTo::create(time, posOfDest),
                                      NULL));
}
*/
bool BallMap::swapBall(BallSprite* src, BallSprite* dest)
{
    m_srcBall = src;
    m_destBall = dest;
    
    m_matrix[m_srcBall->getRow() * (int)m_size.width + m_srcBall->getCol()] = m_destBall;
    m_matrix[m_destBall->getRow() * (int)m_size.width + m_destBall->getCol()] = m_srcBall;
    
    int tmpRow = m_srcBall->getRow();
    int tmpCol = m_srcBall->getCol();
    
    m_srcBall->setRow(m_destBall->getRow());
    m_srcBall->setCol(m_destBall->getCol());
    
    m_destBall->setRow(tmpRow);
    m_destBall->setCol(tmpCol);
    
    // 2.check for remove able
    std::list<BallSprite *> colChainListOfFirst;
    this->getColChain(m_srcBall, colChainListOfFirst);
    
    std::list<BallSprite *> rowChainListOfFirst;
    this->getRowChain(m_srcBall, rowChainListOfFirst);
    
    std::list<BallSprite *> colChainListOfSecond;
    this->getColChain(m_destBall, colChainListOfSecond);
    
    std::list<BallSprite *> rowChainListOfSecond;
    this->getRowChain(m_destBall, rowChainListOfSecond);
    
    if (colChainListOfFirst.size() >= 3
        || rowChainListOfFirst.size() >= 3
        || colChainListOfSecond.size() >= 3
        || rowChainListOfSecond.size() >= 3)
    {
        // just swap
        BallSprite* ball = NULL;
        
        std::list<BallSprite*> longerList;
        std::list<BallSprite*> newList;
        
        if (colChainListOfFirst.size()>=3)
        {
            longerList.merge(colChainListOfFirst);
        }
        if (rowChainListOfFirst.size()>=3)
        {
            longerList.merge(rowChainListOfFirst);
        }
        // 4消产生特殊元素
        if (longerList.size() > 3)
        {
            m_srcBall->setIgnoreCheck(true);
            m_srcBall->setIsNeedRemove(false);
            m_srcBall->setDisplayMode(DISPLAY_MODE_FOUR);
        }
        
        if (colChainListOfSecond.size()>=3)
        {
            longerList.merge(colChainListOfSecond);
            newList.merge(colChainListOfSecond);
        }
        if (rowChainListOfSecond.size()>=3)
        {
            longerList.merge(rowChainListOfSecond);
            newList.merge(rowChainListOfSecond);
        }
        // 4消产生特殊元素
        if (newList.size() > 3)
        {
            m_destBall->setIgnoreCheck(true);
            m_destBall->setIsNeedRemove(false);
            m_destBall->setDisplayMode(DISPLAY_MODE_FOUR);
        }
        
        for (std::list<BallSprite *>::iterator itList = longerList.begin(); itList != longerList.end(); itList++)
        {
            ball = dynamic_cast<BallSprite*>(*itList);
            
            if (!ball)
            {
                continue;
            }
            markRemove(ball);
        }
    
    // 3.消除标记了的寿司
        if (longerList.size() >=3 )
        {
            m_readyRemoveList = longerList;
        }
        
        ball->runAction(CCSequence::create(CCDelayTime::create(0.2f), CCCallFunc::create(this, callfunc_selector(BallMap::removeBall)), NULL));
        
        return true;
    }
    
    m_matrix[m_srcBall->getRow() * (int)m_size.width + m_srcBall->getCol()] = m_destBall;
    m_matrix[m_destBall->getRow() * (int)m_size.width + m_destBall->getCol()] = m_srcBall;
    
    tmpRow = m_srcBall->getRow();
    tmpCol = m_srcBall->getCol();
    
    m_srcBall->setRow(m_destBall->getRow());
    m_srcBall->setCol(m_destBall->getCol());
    
    m_destBall->setRow(tmpRow);
    m_destBall->setCol(tmpCol);
    
    return false;
}
//全ボールに対してボールの並びをチェックする
void GameLayer::checkedBall(BallSprite::PositionIndex current, Direction direction)
{
    //全てのボールのBallTypeを取得
    auto allBalls = getAllBalls();
    
    //検索するタグの生成
    int tag = BallSprite::generateTag(BallSprite::PositionIndex(current.x, current.y));
    BallSprite* ball = allBalls.at(tag);
    
    //指定方向のチェック済みフラグを取得
    bool checked;
    if (direction == Direction::x)
        checked = ball->getCheckedX();
    else
        checked = ball->getCheckedY();
    
    if (!checked)
    {
        int num = 0;
        
        while (true)
        {
            //検索位置を取得
            BallSprite::PositionIndex searchPosition;
            if (direction == Direction::x)
                searchPosition = BallSprite::PositionIndex(current.x + num, current.y);
            else
                searchPosition = BallSprite::PositionIndex(current.x, current.y + num);
            
            //次のボールと同じballTypeかチェックする
            if (isSameBallType(searchPosition, direction))
            {
                //次のボールと同じballType
                int nextTag = BallSprite::generateTag(searchPosition);
                auto nextBall = allBalls.at(nextTag);
                
                //チェックしたボールのチェック済みフラグを立てる
                if (direction == Direction::x)
                    nextBall->setCheckedX(true);
                else
                    nextBall->setCheckedY(true);
                
                num++;
            }
            else
            {
                //次のボールが異なるballType
                
                if (num >= 2)
                {
                    int removedNo = 0;
                    
                    //消去するボールのカウント
                    if (_removeNumbers.size() <= _chainNumber)
                    {
                        //配列が存在しない場合は追加する
                        std::map<BallSprite::BallType, int> removeNumber;
                        _removeNumbers.push_back(removeNumber);
                    }
                    _removeNumbers[_chainNumber][ball->getBallType()] += num + 1;
                    
                    //すでにRemovedNoがあるものが存在するかチェック
                    for (int i = 0; i <= num; i++)
                    {
                    BallSprite::PositionIndex linedPosition;
                        if (direction == Direction::x)
                            linedPosition = BallSprite::PositionIndex(current.x + i, current.y);
                        else
                            linedPosition = BallSprite::PositionIndex(current.x, current.y + i);
                        
                        int linedBallTag = BallSprite::generateTag(linedPosition);
                        auto linedBall = allBalls.at(linedBallTag);
                        if (linedBall->getRemovedNo() > 0)
                        {
                            //すでにRemovedNoがあるものが存在するので、removedNoを取得し次の処理を行う
                            removedNo = linedBall->getRemovedNo();
                            break;
                        }
                    }
                    
                    //消去する順番のカウントアップ
                    if (removedNo == 0)
                        removedNo = ++_maxRemovedNo;
                    
                    //3個以上並んでいた場合は、reomvedNoをセットする
                    for (int i = 0; i <= num; i++)
                    {
                        BallSprite::PositionIndex linedPosition;
                        if (direction == Direction::x)
                            linedPosition = BallSprite::PositionIndex(current.x + i, current.y);
                        else
                            linedPosition = BallSprite::PositionIndex(current.x, current.y + i);
                        
                        int linedBallTag = BallSprite::generateTag(linedPosition);
                        auto linedBall = allBalls.at(linedBallTag);
                        linedBall->setRemovedNo(removedNo);
                    }
                }
                
                break;
            }
        };
        
        //指定方向をチェック済みとする
        if (direction == Direction::x)
            ball->setCheckedX(true);
        else
            ball->setCheckedY(true);
    }
}
Exemple #24
0
void BallMap::checkAndRemoveChain()
{
    BallSprite *ball;
    // 1. reset ingnore flag
    for (int i = 0; i < m_size.height * m_size.width; i++)
    {
        ball = m_matrix[i];
        if (!ball) {
            continue;
        }
        ball->setIgnoreCheck(false);
    }
    
    // 2. check chain
    std::list<BallSprite *> longerList;
    
    for (int i = 0; i < m_size.height * m_size.width; i++)
    {
        ball = m_matrix[i];
        if (!ball)
        {
            continue;
        }
        
        if (ball->getIsNeedRemove())
        {
            continue;// 已标记过的跳过检查
        }
        if (ball->getIgnoreCheck())
        {
//            continue;// 新变化的特殊寿司,不消除
        }
        
        // start count chain
        std::list<BallSprite *> colChainList;
        getColChain(ball, colChainList);
        
        if (colChainList.size() >= 3)
        {
            longerList.merge(colChainList);
        }
        
        std::list<BallSprite *> rowChainList;
        getRowChain(ball, rowChainList);
        
        if (rowChainList.size() >= 3)
        {
            longerList.merge(rowChainList);
        }

        if (longerList.size() < 3)
        {
            m_isNeedCheckSelf = false;
            
            TwoBallPos towBall = this->selfCheckHaveMore();

            if (isPointEqual(towBall.srcPos, towBall.destPos))
            {
                this->removeAllBall(true);
            }
            
            continue;// 小于3个不消除
        }
        
        std::list<BallSprite *>::iterator itList;
        
//        longerList.sort();  //sort the list
//        longerList.erase( unique( longerList.begin(), longerList.end() ), longerList.end());//Remove duplicate list values
        
        for (itList = longerList.begin(); itList != longerList.end(); itList++)
        {
            ball = dynamic_cast<BallSprite*>(*itList);
            
            if (!ball)
            {
                continue;
            }
        
            markRemove(ball);
        }
        
        // 如何是自由掉落产生的4消, 取最后一个变化为特殊寿司
        if (longerList.size() > 3)
        {
            ball->setIgnoreCheck(true);
            ball->setIsNeedRemove(false);
            ball->setDisplayMode(DISPLAY_MODE_FOUR);
        }
    }
    
    if (longerList.size() >= 3)
    {
        m_readyRemoveList = longerList;
    }
    // 3.消除标记了的寿司
    removeBall();
}
Exemple #25
0
void BallMap::fillVacancies()
{
    // reset moving direction flag
//    m_movingVertical = true;
    m_isAnimationing = true;
    
    CCSize size = CCDirector::sharedDirector()->getWinSize();
    
    int *colEmptyInfo = (int *)malloc(sizeof(int) * m_size.width);
    memset((void *)colEmptyInfo, 0, sizeof(int) * m_size.width);
    
    // 1. drop exist Ball
    BallSprite *ball = NULL;
    for (int col = 0; col < m_size.width; col++) {
        int removedBallOfCol = 0;
        // from buttom to top
        for (int row = 0; row < m_size.height; row++)
        {
            ball = m_matrix[row * (int)m_size.width + col];
            
            if (NULL == ball)
            {
                removedBallOfCol++;
            }
            else
            {
                if (removedBallOfCol > 0)
                {
                    // evey item have its own drop distance
                    int newRow = row - removedBallOfCol;
                    // switch in matrix
                    m_matrix[newRow * (int)m_size.width + col] = ball;
                    m_matrix[row * (int)m_size.width + col] = NULL;
                    
                    // set the new row to item
                    ball->setRow(newRow);

                    // move to new position
                    CCPoint startPosition = ball->getPosition();
                    CCPoint endPosition = positionOfItem(ball);

                    float speed = (startPosition.y - endPosition.y) / size.height;
                    
                    ball->set_isMoving(true);
//                    ball->stopAllActions();// must stop pre drop action
                    ball->runAction(CCSequence::create(
                                    CCMoveTo::create(speed, endPosition),
                                                       CCCallFuncN::create(this, callfuncN_selector(BallMap::setBallNoMoving)),
                                                       NULL));
                }
            }
        }
        
        // record empty info
        colEmptyInfo[col] = removedBallOfCol;
    }
    
    // 2. create new item and drop down.
    for (int col = 0; col < m_size.width; col++)
    {
        for (int row = m_size.height - colEmptyInfo[col]; row < m_size.height; row++)
        {
            createAndDropBall(row, col);
        }
    }
    
    free(colEmptyInfo);
    colEmptyInfo = NULL;
    
}
Exemple #26
0
TwoBallPos BallMap::selfCheckHaveMore()
{
    TwoBallPos point_ab;
    point_ab.srcPos = CCPointZero;
    point_ab.destPos = CCPointZero;
    
    //    bool flag = false;
    for (int row = 0; row != m_size.height; ++row)
    {
        for (int col = 0; col != m_size.width; ++col)
        {
            BallSprite* aSprite = BallOfRC(col, row);
            
            if ( aSprite && (aSprite->getDisplayMode() == DISPLAY_MODE_FIVE || aSprite->getDisplayMode() == DISPLAY_MODE_SKILL))
            {
                point_ab.srcPos = ccp(aSprite->getCol(), aSprite->getRow());
            }
            
            //竖向是否有1 2情况的可移动消除 v 1 2
            if (aSprite->getRow() - 1 >= 0)
            {
                BallSprite* bSprite = BallOfRC(col, row - 1);
                if ( bSprite && aSprite->getImgIndex() == bSprite->getImgIndex())
                {
                    /*
                     (x, y-2)
                     (x-1, y-1)     (x, y-1)    (x+1, y-1)
                     (x-1, y    )    (x, y    )   (x+1, y     )
                     (x-1, y+1)    (x, y+1)    (x+1, y+1)
                     (x, y+2)
                     */
                    {
                        BallSprite* cSprite = BallOfRC(col, row + 2);
                        if (cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row+1);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col-1, row+1);
                        if (cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row+1);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col+1, row+1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row+1);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col, row-3);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row-2);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col-1, row-2);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row-2);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col+1, row-2);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row-2);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                }
            }
            //v 1 3
            if (aSprite->getRow()-2 >= 0)
            {
                BallSprite* bSprite = BallOfRC(col, row-2);
                if ( bSprite && aSprite->getImgIndex() == bSprite->getImgIndex())
                {
                    {
                        BallSprite* cSprite = BallOfRC(col, row+1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row-1);
                            point_ab.srcPos = ccp(bSprite->getCol(), bSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col, row-3);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row-1);
                            point_ab.srcPos = ccp(aSprite->getCol(), aSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col-1, row-1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row-1);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                            
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col+1, row-1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col, row-1);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                }
            }
            // h 1 2
            if (aSprite->getCol()+1 < m_size.width)
            {
                BallSprite* bSprite = BallOfRC(col+1, row);
                if ( bSprite && aSprite->getImgIndex() == bSprite->getImgIndex())
                {
                    {
                        BallSprite* cSprite = BallOfRC(col-2, row);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col -1, row);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col-1, row-1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col -1, row);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col-1, row+1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col -1, row);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col+3, row);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col + 2, row);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col+2, row-1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col + 2, row);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col+2, row+1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col + 2, row);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                }
            }
            //h 13
            if (aSprite->getCol()+2 < m_size.width)
            {
                BallSprite* bSprite = BallOfRC(col+2, row);
                if ( bSprite && aSprite->getImgIndex() == bSprite->getImgIndex())
                {
                    {
                        BallSprite* cSprite = BallOfRC(col+3, row);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col + 1, row);
                            point_ab.srcPos = ccp(aSprite->getCol(), aSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col-1, row);
                        if (cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col + 1, row);
                            point_ab.srcPos = ccp(bSprite->getCol(), bSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col+1, row-1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col + 1, row);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                    {
                        BallSprite* cSprite = BallOfRC(col+1, row+1);
                        if ( cSprite && cSprite->getImgIndex() == aSprite->getImgIndex())
                        {
                            BallSprite* temp = BallOfRC(col + 1, row);
                            point_ab.srcPos = ccp(cSprite->getCol(), cSprite->getRow());
                            point_ab.destPos = ccp(temp->getCol(), temp->getRow());
                            return point_ab;
                        }
                    }
                }
            }
        }
    }
    return point_ab;
}