Cocos2d iphone CoCoS2D2.0-忽略对层/精灵透明区域的触摸

Cocos2d iphone CoCoS2D2.0-忽略对层/精灵透明区域的触摸,cocos2d-iphone,Cocos2d Iphone,我有一个应用程序,我有几个层创建的PNG图像与透明度。这些层都在屏幕上彼此重叠。我需要能够忽略对层的透明区域的触摸,并且能够在用户点击层的非透明区域时检测为触摸。。。见图片 我该怎么做?谢谢。这里有一个可能的解决方案 在CCLayer上实现扩展,并提供以下方法: - (BOOL)isPixelTransparentAtLocation:(CGPoint)loc { //Convert the location to the node space CGPoint loca

我有一个应用程序,我有几个层创建的PNG图像与透明度。这些层都在屏幕上彼此重叠。我需要能够忽略对层的透明区域的触摸,并且能够在用户点击层的非透明区域时检测为触摸。。。见图片


我该怎么做?谢谢。

这里有一个可能的解决方案

在CCLayer上实现扩展,并提供以下方法:

- (BOOL)isPixelTransparentAtLocation:(CGPoint)loc 
{   
    //Convert the location to the node space
    CGPoint location = [self convertToNodeSpace:loc];

    //This is the pixel we will read and test
    UInt8 pixel[4];

    //Prepare a render texture to draw the receiver on, so you are able to read the required pixel and test it    
    CGSize screenSize = [[CCDirector sharedDirector] winSize];
    CCRenderTexture* renderTexture = [[CCRenderTexture alloc] initWithWidth:screenSize.width
                                                                     height:screenSize.height
                                                                pixelFormat:kCCTexture2DPixelFormat_RGBA8888];

    [renderTexture begin];

    //Draw the layer
    [self draw];    

    //Read the pixel
    glReadPixels((GLint)location.x,(GLint)location.y, kHITTEST_WIDTH, kHITTEST_HEIGHT, GL_RGBA, GL_UNSIGNED_BYTE, pixel);

    //Cleanup
    [renderTexture end];
    [renderTexture release];

    //Test if the pixel's alpha byte is transparent
    return (pixel[3] == 0);
}

如果Lio的解决方案不起作用,您可以在您的孩子时添加透明精灵,将其放置在非透明区域下方,大小与此非透明区域相同,并使用此新的透明精灵调整所有触摸的大小,但不使用原始精灵。

这是我的解决方案,可以满足您的要求,让我知道它是否起作用

在CCMenu上创建名为Transparent的类别 文件CCMenu+transparent.h

#import "CCMenu.h"

@interface CCMenu (Transparent)
@end
文件CCMenu+transparent.m

#import "CCMenu+Transparent.h"
#import "cocos2d.h"
@implementation CCMenu (Transparent)
-(CCMenuItem *) itemForTouch: (UITouch *) touch{
    CGPoint touchLocation = [touch locationInView: [touch view]];
    touchLocation = [[CCDirector sharedDirector] convertToGL: touchLocation];

    CCMenuItem* item;
    CCARRAY_FOREACH(children_, item){
        UInt8 data[4];

        // ignore invisible and disabled items: issue #779, #866
        if ( [item visible] && [item isEnabled] ) {
            CGPoint local = [item convertToNodeSpace:touchLocation];
            /*
             TRANSPARENCY LOGIC
             */
            //PIXEL READING 1 PIXEL AT LOCATION


            CGRect r = [item rect];
            r.origin = CGPointZero;

            if( CGRectContainsPoint( r, local ) ){
                if([NSStringFromClass(item.class) isEqualToString:NSStringFromClass([CCMenuItemImage class])]){
                    CCRenderTexture* renderTexture = [[CCRenderTexture alloc] initWithWidth:item.boundingBox.size.width * CC_CONTENT_SCALE_FACTOR()
                                                                                     height:item.boundingBox.size.height * CC_CONTENT_SCALE_FACTOR()
                                                                                pixelFormat:kCCTexture2DPixelFormat_RGBA8888];

                    [renderTexture begin];
                    [[(CCMenuItemImage *)item normalImage] draw];

                    data[3] = 1;
                    glReadPixels((GLint)local.x,(GLint)local.y, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, data);

                    [renderTexture end];
                    [renderTexture release];
                    if(data[3] == 0){
                        continue;
                    }

                }
                free(data);
                return item;
            }

        }
    }
    return nil;
}

@end
这将检查返回CCMenuItem的像素。 这里工作很好。。如果您遇到任何问题,请告诉我

-帕雷什拉特霍德
Cocos2d Lover

对我来说最有效的解决方案是使用雪碧床单。我使用TexturePacker创建雪碧床单。使用TexturePacker创建精灵图纸的步骤: 1.将所有图像(.png)文件加载到TexturePacker中。 2.选择数据格式为coco2d,选择PVR作为纹理格式。 3.将精灵工作表加载到代码中,并从精灵工作表中提取图像


可以找到详细说明。

透明层是透明的还是上面显示的图案?另外,您是否已经知道如何检测任何区域上的触摸?该图案表示透明度。是的,我知道如何检测触摸,我只是检查触摸是否在精灵内。边界框。。。我需要知道它是否在边界框内,是否是一个非透明像素。嗯,好吧,我建议只在非透明的父对象上放置一个空白的CCMenuItemImage,然后这样做。否则,您将处理大量不需要的像素代码。您希望触摸通过透明区域吗?(即,最上面的层是透明的,但您在下面的层中有一个不透明像素位于同一位置的位置对其进行触摸)是的,我希望它忽略在层的透明区域上进行的任何触摸,但如果下面有一层,并且该触摸点对应于该层上的一个不透明点,我希望下面这层被触发。你能扩展答案吗。我试着做一个“扩展”,但它真的应该是一个类别吗?此外,kHITTEST_宽度和kHITTEST_高度未定义。它们应该是1x1还是40x40?有人可以发布整个解决方案吗?您好,扩展确实是该类的一个类别。您可以创建它并立即将此方法添加为它的一部分。对于未定义的常量,可以用1个替换。