Search code examples
cocos2d-xcocos2d-x-3.0

The Cocos2D/Cocos2d-x internal implementation of drawDot in CCDrawNode/DrawNode


for an OpenGL ES issue, I am tracing the Cocos2D 3.1.0 source code. I focus on drawDot in CCDrawNode, here is the internal implementation:

-(void)drawDot:(CGPoint)pos radius:(CGFloat)radius color:(CCColor *)color;
{
    GLKVector4 color4 = Premultiply(color.glkVector4);

    GLKVector2 zero2 = GLKVector2Make(0, 0);

    CCRenderBuffer buffer = [self bufferVertexes:4 andTriangleCount:2];
    CCRenderBufferSetVertex(buffer, 0, (CCVertex){GLKVector4Make(pos.x - radius, pos.y - radius, 0, 1), GLKVector2Make(-1, -1), zero2, color4});
    CCRenderBufferSetVertex(buffer, 1, (CCVertex){GLKVector4Make(pos.x - radius, pos.y + radius, 0, 1), GLKVector2Make(-1,  1), zero2, color4});
    CCRenderBufferSetVertex(buffer, 2, (CCVertex){GLKVector4Make(pos.x + radius, pos.y + radius, 0, 1), GLKVector2Make( 1,  1), zero2, color4});
    CCRenderBufferSetVertex(buffer, 3, (CCVertex){GLKVector4Make(pos.x + radius, pos.y - radius, 0, 1), GLKVector2Make( 1, -1), zero2, color4});

    CCRenderBufferSetTriangle(buffer, 0, 0, 1, 2);
    CCRenderBufferSetTriangle(buffer, 1, 0, 2, 3);
}

I remember that drawDot allows us to draw a circle with the radius. In my knowledge of drawing circle with OpenGL, we use many triangles to form a circle, algorithm would be like http://slabode.exofire.net/circle_draw.shtml. Somebody please kindly explain why Cocos2D just uses 2 triangles? Or it is not just 2 triangles, I just miss something?

For reference, Cocos2d-x code is:

void DrawNode::drawDot(const Vec2 &pos, float radius, const Color4F &color)
{
    unsigned int vertex_count = 2*3;
    ensureCapacity(vertex_count);

    V2F_C4B_T2F a = {Vec2(pos.x - radius, pos.y - radius), Color4B(color), Tex2F(-1.0, -1.0) };
    V2F_C4B_T2F b = {Vec2(pos.x - radius, pos.y + radius), Color4B(color), Tex2F(-1.0,  1.0) };
    V2F_C4B_T2F c = {Vec2(pos.x + radius, pos.y + radius), Color4B(color), Tex2F( 1.0,  1.0) };
    V2F_C4B_T2F d = {Vec2(pos.x + radius, pos.y - radius), Color4B(color), Tex2F( 1.0, -1.0) };

    V2F_C4B_T2F_Triangle *triangles = (V2F_C4B_T2F_Triangle *)(_buffer + _bufferCount);
    V2F_C4B_T2F_Triangle triangle0 = {a, b, c};
    V2F_C4B_T2F_Triangle triangle1 = {a, c, d};
    triangles[0] = triangle0;
    triangles[1] = triangle1;

    _bufferCount += vertex_count;

    _dirty = true;
}

Thanks


Solution

  • drawDot just uses 2 triangles for drawing a dot(circle). But it also uses a specific fragment shader for drawing a circle.

    https://github.com/cocos2d/cocos2d-iphone/blob/v3.1/cocos2d/CCDrawNode.m#L43

    gl_FragColor = cc_FragColor*smoothstep(0.0, length(fwidth(cc_FragTexCoord1)), 1.0 - length(cc_FragTexCoord1));
    

    For further reference: http://people.freedesktop.org/~idr/OpenGL_tutorials/03-fragment-intro.html