3

Currently I'm having problems with CCClippingNode in Cocos2D and transitions as stated here. Now Viktor (author of SpriteBuilder) gave a tip that I could mask the image with Core Graphics.

Which I now am doing, and it works. However Core Graphics uses the alpha the exact opposite for masking as Cocos2d. Is it possible to invert the alpha value of an UIImage (grayscale) on the fly?

If I want to mask a circle out of an image with Cocos I would need this mask.

Cocos Mask

but it needs to be this in core graphics.

Core Graphics

Is it possible to create the bottom image from the top image on the fly? (e.g inverting it's alpha)

Community
  • 1
  • 1
Matthijn
  • 3,126
  • 9
  • 46
  • 69

2 Answers2

0

How to convert UIImage/CGImageRef's alpha channel to mask?

Ben's answer to the linked question solves inverting alpha of given UIImage. Just delete/comment the below section of the code

for (int y = 0; y < height; y++) {
for (int x = 0; x < width; x++) {
    unsigned char val = alphaData[y*strideLength + x];
    val = 255 - val;
    alphaData[y*strideLength + x] = val;
}

PS: couldn't add comment.

Community
  • 1
  • 1
kboda
  • 43
  • 4
0

I get the answer based on this answer honors for @Tommy

CGSize size = finalImage.size;
    int width = size.width;
    int height = size.height;
    // Create a suitable RGB+alpha bitmap context in BGRA colour space
    CGColorSpaceRef colourSpace = CGColorSpaceCreateDeviceRGB();
    unsigned char *memoryPool = (unsigned char *)calloc(width*height*4, 1);
    CGContextRef context = CGBitmapContextCreate(memoryPool, width, height, 8, width * 4, colourSpace, kCGBitmapByteOrder32Big | kCGImageAlphaPremultipliedLast);
    CGColorSpaceRelease(colourSpace);

    // draw the current image to the newly created context
    CGContextDrawImage(context, CGRectMake(0, 0, width, height), [finalImage CGImage]);

    // run through every pixel, a scan line at a time...
    for(int y = 0; y < height; y++)
    {
        // get a pointer to the start of this scan line
        unsigned char *linePointer = &memoryPool[y * width * 4];

        // step through the pixels one by one...
        for(int x = 0; x < width; x++)
        {

            if(linePointer[3]){
                linePointer[3]=255-linePointer[3];
            }
            linePointer += 4;
        }
    }

    // get a CG image from the context, wrap that into a
    // UIImage
    CGImageRef cgImage = CGBitmapContextCreateImage(context);
    UIImage *returnImage = [UIImage imageWithCGImage:cgImage];

    // clean up
    CGImageRelease(cgImage);
    CGContextRelease(context);
    free(memoryPool);

    //use returnImage as you want
Community
  • 1
  • 1
ygweric
  • 1,002
  • 1
  • 7
  • 22