变色精灵Cocos2d

时间:2012-02-29 02:10:11

标签: animation colors cocos2d-iphone

我需要我的精灵过渡到一种颜色到另一种颜色然后......就像蓝色色调然后是绿色然后是紫色,但我找不到任何好的动作,我想知道,我应该使用动画吗?或者是否有针对此的合并行动?

3 个答案:

答案 0 :(得分:11)

你可以使用CCTintTo动作来改变精灵的颜色

[sprite runAction:[CCTintTo actionWithDuration:2 red:255 green:0 blue:0]];

答案 1 :(得分:4)

因为我看到几个关于更换精灵中的像素颜色的问题,我没有看到任何好的解决方案(所有解决方案只有颜色,并且没有一个能够改变颜色数组而不强迫你创建多个构建你想要的最终图像的图像层,即:一层用于平底锅,另一层用于展示,另一层用于衬衫,另一层用于头发颜色......它继续 - 请注意它们确实具有使用准确性等优点梯度)

我的解决方案允许您更改颜色数组,这意味着您可以使用已知颜色的单个图像(您不希望此图层中有任何渐变,只有您知道其值的颜色 - PS这仅适用于您想要的颜色要改变,其他像素可以有你想要的任何颜色) 如果您需要在您更改的颜色上使用渐变,请创建仅包含阴影的附加图像,并将其作为精灵的子项。

另外请注意,我对cocos2d / x(3天)非常新,并且此代码是为cocos2dx编写的,但可以轻松移植到cocos2d。

另请注意,我没有在iOS上测试它,我不确定Android官方gcc有多强大,它如何处理我分配_srcC和_dstC的方式,但同样,这很容易移植。

所以这就是:

cocos2d::CCSprite * spriteWithReplacedColors( const char * imgfilename, cocos2d::ccColor3B * srcColors, cocos2d::ccColor3B * dstColors, int numColors )
{
    CCSprite *theSprite = NULL;

    CCImage *theImage = new CCImage;
    if( theImage->initWithImageFile( imgfilename ) )
    {
        //make a color array which is easier to work with
        unsigned long _srcC [ numColors ];
        unsigned long _dstC [ numColors ];
        for( int c=0; c<numColors; c++ )
        {
            _srcC[c] = (srcColors[c].r << 0) | (srcColors[c].g << 8) | (srcColors[0].b << 16);
            _dstC[c] = (dstColors[c].r << 0) | (dstColors[c].g << 8) | (dstColors[0].b << 16);
        }

        unsigned char * rawData = theImage->getData();
        int width = theImage->getWidth();
        int height = theImage->getHeight();

        //replace the colors need replacing
        unsigned int * b = (unsigned int *) rawData;
        for( int pixel=0; pixel<width*height; pixel++ )
        {
            register unsigned int p = *b;
            for( int c=0; c<numColors; c++ )
            {
                if( (p&0x00FFFFFF) == _srcC[c] ) 
                {
                    *b = (p&0xFF000000) | _dstC[c];
                    break;
                } 
           }
            b++;
        }

        CCTexture2D *theTexture = new CCTexture2D();
        if( theTexture->initWithData(rawData, kCCTexture2DPixelFormat_RGBA8888, width, height, CCSizeMake(width, height)) )
        {
            theSprite = CCSprite::spriteWithTexture(theTexture);
        }
        theTexture->release();
    }
    theImage->release();

    return theSprite;
}

使用它只需执行以下操作:

ccColor3B src[] = { ccc3( 255,255,255 ), ccc3( 0, 0, 255 ) };
ccColor3B dst[] = { ccc3( 77,255,77 ), ccc3( 255, 0 0 ) };
//will change all whites to greens, and all blues to reds. 
CCSprite * pSprite =  spriteWithReplacedColors( "character_template.png", src, dst, sizeof(src)/sizeof(src[0]) );

当然,如果你需要速度,你会为精灵创建一个扩展,创建一个像素着色器,它在渲染时加速;)

顺便说一下:在某些情况下,这种解决方案可能会在边缘上造成一些假象,因此您可以创建一个大图像并将其缩小,让GL最小化人工制品。 您还可以使用黑色轮廓创建“修复”图层,以隐藏文物并将其放在顶部等。 还要确保不要在图像的其余部分使用这些“关键”颜色,而不希望像素发生变化。 还要记住,alpha通道没有改变的事实,如果你只使用纯红色/绿色/蓝色的基本图像,你也可以优化这个功能,以自动消除边缘上的所有人工制品(并避免在许多例如,需要额外的阴影层)和其他很酷的东西(将几个图像复用到一个位图中 - 记得调色板动画吗?)

享受;)

答案 2 :(得分:1)

如果有人想要cocos2d-x这就是代码:

somesprite->runAction(TintTo::create(float duration, Color3b &color));