Sprites with alpha and non-integer position are drawn with black frame:
Cocos 3.1:
Cocos 2.3.3:
Here is code for repro:
Cocos 3.1:
// Good sprite
cocos2d::SpriteFrame* fr = new cocos2d::SpriteFrame();
fr->initWithTextureFilename("Test_transparency1.png", cocos2d::Rect(0, 180, 142, 134));
auto p = cocos2d::Sprite::createWithSpriteFrame(fr);
p->setPosition(500, 200);
this->addChild(p);
// Bad sprite
cocos2d::SpriteFrame* fr2 = new cocos2d::SpriteFrame();
fr2->initWithTextureFilename("Test_transparency1.png", cocos2d::Rect(0, 180, 141, 134));
auto p2 = cocos2d::Sprite::createWithSpriteFrame(fr2);
p2->setPosition(500, 400);
this->addChild(p2);
Cocos 2.2.3:
// Good sprite
cocos2d::CCSpriteFrame* fr = new cocos2d::CCSpriteFrame();
fr->initWithTextureFilename("Test_transparency1.png", cocos2d::CCRect(0, 180, 142, 134));
auto p = cocos2d::CCSprite::createWithSpriteFrame(fr);
p->setPosition(ccp(500, 200));
this->addChild(p);
// Good sprite
cocos2d::CCSpriteFrame* fr2 = new cocos2d::CCSpriteFrame();
fr2->initWithTextureFilename("Test_transparency1.png", cocos2d::CCRect(0, 180, 141, 134));
auto p2 = cocos2d::CCSprite::createWithSpriteFrame(fr2);
p2->setPosition(ccp(500, 400));
this->addChild(p2);
In cocos3 Position of the sprite is calculated from midpoint and if sprite has odd size (e.g. [141, 134]) it will not fit screen pixels because midpoint will be [70.5, 67].
This will force openGL to interpolate texture using GL_LINEAR by default (GL_NEAREST solves the problem but causes other aliasing problems) and transparent pixels are blended with visible ones on the border.
Macros CC_NODE_RENDER_SUBPIXEL=0 and CC_SPRITEBATCHNODE_RENDER_SUBPIXEL=0 do not solve issue also.
Note! Image is not premultiplied. Premultiplied images do not have this issue.
il_cocos2.png (63.1 KB)
il_cocos3.png (68.6 KB)
Test_transparency1.png (10.6 KB)