-
Notifications
You must be signed in to change notification settings - Fork 1.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
CCClippingNode with CCLabelTTF - problem with CCRenderTexture #926
Comments
#913 is a problem with RenderTextures and Effects as well. |
There have been some change like 4b62c1a |
No - seeing exactly the same problem with v3.2.1 I suspect the issue discussed in #936 could be a major part of the problem, but no idea why just CCLabelTTF is failing compared to other node types used as the stencil. |
This is still broken in v3.3 |
This is also breaking using a CCNodeColor as a stencil. In my case, both the stencil node and clipping node are inside a CCEffectNode. |
Finally looked into this, and I have no idea how it ever worked before. O_o CCClippingNode replaces shaders on everything that it uses for a mask, and it's really making the assumption that everything is being shaded like a regular sprite (texture alpha*sprite alpha). This is the way it has always worked, and I think my eyes nearly popped out of my head when I first saw the code for it. (What? You can't do that!) Unfortunately since GLES 2 doesn't support alpha testing there really is no other option. Depending on if a label is styled or not it uses different texture formats to save memory (RGBA vs just alpha). Alpha-only labels need a special shader to render them, and I'm guessing that is what doesn't work. We may have changed the rules for creating alpha only labels? I dunno. Try setting the fontColor property to something other than white. That's the easiest way to force an RGBA label texture. I'll dig a bit more on this. Maybe there is some sketchy shader hack I can do to make it work better. Unfortunately the whole thing has always been based on sketchy shader hacks. |
In my case (not using a label - see #913), I tried swapping in a regular sprite for the CCNodeColor that I was using for a stencil, but no luck. Which makes me think this might be related to the clipping occurring inside of a CCEffectNode instead of alpha testing... I've been poking around a bit in CCClippingNode.m and CCEffectNode.m and wondering if CCEffectNode is somehow overriding the stencil buffer? |
Hi @slembcke Thanks for looking into this. I now remember seeing that shader replacement code in CCClippingNode when I was trying to work out how it worked and being 'concerned' that it was a bit of a brutal hack. Forcing a full colour texture for the CCLabelTTF doesn't help in my case. The image in the original comment shows the problem: the clip node with the label as the stencil is working when added to the scene normally (the 'TESTING TEXT' in the middle of the screen) but not when used in the RenderTexture begin/visit/end getUIImage -> sprite onto screen path that draws the second block at the bottom left. But that path does work for a normal sprite. So what change can there be in the begin/visit/end path of the CCRenderTexture vs the standard draw path? [retested on 3.3.5 from latest develop branch and still the same] This code replacing the 'setupClippingNodeTest' method in CCRendererTest in the tests project demonstrates the issue: // Test CCClippingNode.
} |
So I've finally worked out what is going wrong here! @slembcke - you were spot on with those shader shenanigans: that's the root cause of it. The reason it was broken for CCLabelTTF was that in the visit method of the label it does a lazy update of the texture if anything has changed: which it will have in my example having been just created... As part of the update texture code it resets the shader - thus wiping out the change the CCClippingNode made. So to make it work I've had to force it to build the texture before the visit call to the clip node. Asking the label for the content size is enough (there is no explicit method for it) and that has fixed it. Interestingly it works with or without a full colour texture: somehow the stencil render path/shader override must be able to handle the A8 texture in the basic labels (default r/g/b being 1 if not in the texture?). So to change the code above to work simply insert this above the [parent beginWithClear... line CGSize cs = stencil.contentSize; // Forces the CCLabelTTF to update the texture and thus set the shader and it works. I can't immediately see that there is any sensible solution to problems like this but maybe a big chunk of warning in the CCClippingNode documentation for when people hit problems would be helpful. |
Hi,
Summary: Doing a 'direct' render of a CCRenderTexture when the node to be rendered is a CClippingNode with a stencil defined by a CCLabelTTF fails. Other stencil node types work, and adding the render texture to the scene makes it render properly. This usage worked fine on 3.0 but failed when I updated to 3.1.
I posted this on the forums: https://forum.cocos2d-swift.org/t/problem-with-ccclippingnode-with-cclabelttf-as-stencil-into-ccrendertexture/14689 which shows how to reproduce the issue
I've recreated the problem in a fork of the 3.1 code:
https://github.com/richardgroves/cocos2d-iphone
The change made to the CCRendererTest:
richardgroves@2007790
The image here shows the result: The text shown is the render path where the CCRenderTexture is added to the scene, the solid block of colour is where it is renderer in the setup code with [begin] [visit] [end] with a text label stencil.
The text was updated successfully, but these errors were encountered: