Cocos2d-x V4.0 released

Cocos2d-x V4.0 released

Few questions:

  • Do you have any performance tests to compare v4 vs v3 renderer? (I am interested mainly in iOS, Android)
  • Will you close branch v3 and continue development in v4 only?

Is there any rendering performance gain on Apple products in v4 using Metal over v3 using OpenGL?
Would be interested to see any performance metrics.



Congratulations. Thanks for the hard work.

Congradulations guys! ) Thanks for all the hard work! )

Though its have some major issues about metal, like its crashing if device doesn’t support metal.
Thank you.

I saw your topic about this crash and I have tagged @zhangxm and he will have the team look.

1 Like

Wait what!?
Support Metal = No longer support OpenGL???
This wording is completely wrong. It isn’t ‘support meta’ but ‘replace opengl rendering with metal’

This fundamentally changes the supported device spectrum for cocos2dx.
The github still states ‘iOS 8+’ which is no longer the case.

The new requirements will be ‘Metal-supported iOS device: iPhone 5S or newer, iPad Air or newer’ (see

Was this confirmed anywhere until this sudden release? Even I had the understanding that opengl remained as a side-by-side renderer option???

(Just to add: we clearly understood that custom GL commands would no longer work in platform-agnostic code, but presumed this was to handle both renderers, not that GL was being fully removed.

For reference, we would lose X% users by dropping support for OpenGL-only devices meaning the metal upgrade no longer holds enough value until Apple forces a move away from OpenGL)

Congratulation to the entire team!
Everyone here appreciates how hard it is to work on such a complex project!

Thanks for this release, guys!

My Congratulation!

But could you please clarify some things:

  1. The following part of TextureCube::init function:

     backend::PixelFormat  ePixelFmt;
     unsigned char*          pData = getImageData(img, ePixelFmt);
     uint8_t *cData = nullptr;
     uint8_t *useData = pData;

getImageData(…) set ePixelFmt to AUTO value despite the img->_pixelFormat is equal RGBA8888. In result of that I catch
CCASSERT(false, "error: CubeMap texture may be incorrect, failed to convert pixel format data to RGBA8888");
in some lines later.

I set ePixelFmt to RGBA8888 forcibly and the initializing passed well.

  1. The second question touches of the RenderTexture class.
    I created custom RenderTextureCustom which based on cocos2d::RenderTexture. It supports rendering to the texture of 3D objects, and can support optionally only depth attachment if needed (without color attachment).

I have the issue on Window in the following sequence steps

first step: Rendering to FrameBuffer with only depth attachment texture;
second step: Rendering to FrameBuffer with only color attachment texture.
issue: No any color data in the color attachment texture after second step.

After some research I found that there is color attachment disabling in the backend/opengl/CommandBufferGL.cpp inside CommandBufferGL::applyRenderPassDescriptor, if color attachment is absent for FrameBuffer (first step). But there is no color attachment enabling after that which cause to the issue I mentioned.

I fixed this with following lines inside the same function:

I would appreciate if you suggest something better.

And one more question. Have you in plan to support multiple color attachments?

@nirobkuet @Guykun v3 is still available. And v4 only supports metal is known if you focus other versions such alpha, beta, rc0 …

@coulsonwang pleas take a look of @solan’s issue.

fixed in PR 20397. For AOTU pixel format it dose not need to convert to RGBA8888.

Congratulations. Thanks for your hard work. But why JSB was removed?

1 Like
  1. first step: It will create an FBO and adds a depthAttachmentTexture;
  2. second step: Since the FBO has always created in the first step, so it simply adds a colorAttachmentTexture to the FBO if you want to render it to a texture.

So why there is no color attachment enabling? Or can you provide me a demo?

I see this a little another:

RenderTexture::onBegin() call’s renderer->setRenderTarget(_renderTargetFlags, _texture2D, _depthStencilTexture, _depthStencilTexture); which exchange render->_renderPassDescriptor corresponding values.
(This allows to have one Frame buffer (with id == 1) and many others attachments combinations.)

RenderTexture_1::onBegin() -> set new depth/color/stencil values for _renderPassDescriptor

RenderTexture_1::onEnd() -> set old depth/color/stencil values for render->_renderPassDescriptor

RenderTexture_2::onBegin() -> set new depth/color/stencil values for _renderPassDescriptor

RenderTexture_2::onEnd() -> set old depth/color/stencil values for render->_renderPassDescriptor

Suppose, that there is only depthAttachmentTexture for RenderTexture_1.
Each calling of Renderer::drawXXXXCommand() will call CommandBufferGL::applyRenderPassDescriptor(). This function disable colorAttachmentTexture via

But there is no enabling it for RenderTexture_2. I mentioned how to patch this behavior in previous message.

About demo:
Common cocos2d::RenderTexture::onBegin() and onEnd() form CallbackCommand and put it to the render queue where z == 0 (There is five render queues in render engine).
This helps for cocos2d::Sprite, but not for cocos2d::Sprite3D, since MeshCommand will be put to the Opaque or Transparent render queues.

My custom RenderTextureCustom does the following:
RenderTextureCustom::onBegin() -> put CallBackCommand to Opaque queue RenderTextureCustom::clear() -> put CallBackCommand to clear depth/color/stencil to Opaque queue

RenderTextureCustom::onExit() -> put CallBackCommand to Transparent queue.

That is exactly what my class performs. Sorry I do not have any demo, but I can provide you this class if you want.

I know that cocos2d::RenderTexture does not allow to be created without colorAttachmentTexture on the one side. But as I can see low level api should be possible to handle similar cases (different attachment combinations).

Sure, I recommend:

  1. Updating this post to clarify ‘removing OpenGL support on iOS’ or ‘replace OpenGL with Metal on iOS’
  2. Updating cocos2dx v4 github readme to not say iOS8+ but to say iOS8+ & Metal supported device (with some sort of info or link to device support)

To avoid this confusion in the future.

1 Like

@solan I think it needs to specify the GL_COLOR_ATTACHEMNT0 to enable reading from/drawing to color buffer again.
Could you help to post your fix to the v4 branch?

@coulsonwang I wish I could help but I have no githab account to do pull request, I use bitbucket.
(If there some opportunities to do pull request from bitbucket account?) Or can I do it via git request-pull ?)

To save time, you can try this file.

CommandBufferGL.cpp (19.8 KB)

Copy it please to the renderer/backend/opengl/CommandBufferGL.cpp

It differs from origin only in fixing of this issue. I believe that it helps.
Of cause it will require some changes if you will decide to support multiple color attachments.

But I beg you to let me know if you think that this fix is not appropriate for some reason.

So, i download and installed v4, followed by CMake guide at cocos docs. But one thing is still unclear for me: how to create new project, f.e. for ios, with specified app name, bundle identifier and so on? Because, by default, “cmake … -GXcode” command create a bunch of pedefined projects, including cpp-tests, HelloWorld etc. Should i add new target at xcode project, fill all needed info by hands, or should i rename one of exist targets, HelloWorld f.e., alter it to satisfy my needs? And what about android projects? I need some guidance.