Coder Social home page Coder Social logo

Comments (11)

ggua5470 avatar ggua5470 commented on July 23, 2024 1

I end up using a small hack, still using GPUImage2.
Because I know the chromakey is working (i.e. detecting the green pixels and set alpha to 0), but the resulting UIImage does not have the right alpha, So I replace the green pixels in the original image with pure-green pixels, and use color masking to remove them.
This gives the "transparent" image I need to put into a UIImageView and process it further.

This hack is only good for one-time processing. For real-time processing, just use RenderView provided by GPUImage2.

Sample code below:

        //Use a ChromaKeyBlend to blend original image with a pure-green image
        let pictureInput1 = PictureInput(image:scaled)
        let filterChromakey = ChromaKeyBlend()

        //==> A trick here, use .green to replace green background, then replace it with transparent!
        //1X1 image to blend in (no need to create image of same size)
        let rect = CGRect(origin: .zero, size: CGSize(width: 1, height: 1))  //scaled.size
        UIGraphicsBeginImageContextWithOptions(rect.size, false, 0.0)
        UIColor.green.setFill()
        UIRectFill(rect)
        let greenImage = UIGraphicsGetImageFromCurrentImageContext()
        UIGraphicsEndImageContext()
        let pictureInput2 = PictureInput(image:greenImage!)
        
        pictureInput1.addTarget(filterChromakey)
        pictureInput1.processImage()
        pictureInput2.addTarget(filterChromakey)
        pictureInput2.processImage()
        
        let output = PictureOutput()
        output.imageAvailableCallback = {image in

            //replace green color to transparent
            let rawImageRef: CGImage = image.cgImage!
            let colorMasking: [CGFloat] = [0, 5, 250, 255, 0, 5]
            UIGraphicsBeginImageContextWithOptions(image.size, false, 0)
            let maskedImageRef=rawImageRef.copy(maskingColorComponents: colorMasking)
            UIGraphicsGetCurrentContext()?.translateBy(x: 0.0, y: image.size.height)
            UIGraphicsGetCurrentContext()?.scaleBy(x: 1.0, y: -1.0)
            UIGraphicsGetCurrentContext()?.draw(maskedImageRef!, in: CGRect(x: 0.0,y: 0.0,width:image.size.width,height: image.size.height))
            
            result = UIGraphicsGetImageFromCurrentImageContext()
            UIGraphicsEndImageContext();
    
        }
    
        pictureInput1 --> filterChromakey
        pictureInput2 --> filterChromakey --> output
        pictureInput1.processImage(synchronously: true)
        pictureInput2.processImage(synchronously: true)`

from gpuimage2.

BradLarson avatar BradLarson commented on July 23, 2024

Does your UIImageView support transparency? The chroma keying shader only drops the alpha channel of the resulting image in response to they keyed colors, so the RGB components are the same. If the resulting image is then placed in something that doesn't respect alpha channels, it will look like the original image.

If you instead save this image to a PNG file, does the resulting PNG file have the correct reduced alpha channel in the keyed areas?

from gpuimage2.

florianbuerger avatar florianbuerger commented on July 23, 2024

Yes, UIImageView respects the alpha channel. I double checked with an exported artwork from Sketch.

Writing the image to disk does produce the same image as the image view.

    private func process() {
        output.imageAvailableCallback = { image in
            NSOperationQueue.mainQueue().addOperationWithBlock {
                self.imageView.image = image
                if let imageData = UIImagePNGRepresentation(image) {
                    let dir = NSSearchPathForDirectoriesInDomains(.DocumentDirectory, .UserDomainMask, true).first!
                    let url = NSURL(fileURLWithPath: dir).URLByAppendingPathComponent("image.png")
                    do {
                        try imageData.writeToURL(url, options: NSDataWritingOptions())
                    } catch let error {
                        print(error)
                    }
                }
            }
        }
        picture --> filter
        filter --> renderView
        filter --> output

        picture.processImage(synchronously: true)
    }

image

I've uploaded the complete project if you want to have a look.

from gpuimage2.

ggua5470 avatar ggua5470 commented on July 23, 2024

@florianbuerger This seems not fixed yet. Any solution from you?

After chromakeying or chromakeyblend, the resulting UIImage in imageAvailableCallback() or the imageData in encodedImageAvailableCallback() with format setting to .png all lost the alpha channel, so the background is black (I used chromakeyblend to replace .green to .clear)

As @florianbuerger said, it only shows correct image with transparent background when showing the result to a RenderView (which means the chromakeying itself is working). When showing in a UIImageView, the background become black. It is similar to getting a JPEG output.

Any way to get it a UIImage with transparent background?

from gpuimage2.

florianbuerger avatar florianbuerger commented on July 23, 2024

I ended up using GPUImage version 1, which does not have that issue.

from gpuimage2.

allenkiehl avatar allenkiehl commented on July 23, 2024

Is there any solution to this? I am having same issue filters fine on live view but saved image not filtered.

from gpuimage2.

geoffhufford avatar geoffhufford commented on July 23, 2024

I posted a similar question on Stack Overflow prior to finding this issue discussion. https://stackoverflow.com/questions/52952776/gpuimage-chroma-key-export-png-file-with-alpha

I am going to try @ggua5470 workaround above, but hope someone may know the fix.

from gpuimage2.

allenkiehl avatar allenkiehl commented on July 23, 2024

@geoffhufford did the above solution work for you? I tried with no success after using thresholdSensitivity and smoothing does not give desired result. Filtering live works perfect though.

from gpuimage2.

allenkiehl avatar allenkiehl commented on July 23, 2024

@ggua5470

I end up using a small hack, still using GPUImage2.
Because I know the chromakey is working (i.e. detecting the green pixels and set alpha to 0), but the resulting UIImage does not have the right alpha, So I replace the green pixels in the original image with pure-green pixels, and use color masking to remove them.
This gives the "transparent" image I need to put into a UIImageView and process it further.

This hack is only good for one-time processing. For real-time processing, just use RenderView provided by GPUImage2.

Sample code below:

        //Use a ChromaKeyBlend to blend original image with a pure-green image
        let pictureInput1 = PictureInput(image:scaled)
        let filterChromakey = ChromaKeyBlend()

        //==> A trick here, use .green to replace green background, then replace it with transparent!
        //1X1 image to blend in (no need to create image of same size)
        let rect = CGRect(origin: .zero, size: CGSize(width: 1, height: 1))  //scaled.size
        UIGraphicsBeginImageContextWithOptions(rect.size, false, 0.0)
        UIColor.green.setFill()
        UIRectFill(rect)
        let greenImage = UIGraphicsGetImageFromCurrentImageContext()
        UIGraphicsEndImageContext()
        let pictureInput2 = PictureInput(image:greenImage!)
        
        pictureInput1.addTarget(filterChromakey)
        pictureInput1.processImage()
        pictureInput2.addTarget(filterChromakey)
        pictureInput2.processImage()
        
        let output = PictureOutput()
        output.imageAvailableCallback = {image in

            //replace green color to transparent
            let rawImageRef: CGImage = image.cgImage!
            let colorMasking: [CGFloat] = [0, 5, 250, 255, 0, 5]
            UIGraphicsBeginImageContextWithOptions(image.size, false, 0)
            let maskedImageRef=rawImageRef.copy(maskingColorComponents: colorMasking)
            UIGraphicsGetCurrentContext()?.translateBy(x: 0.0, y: image.size.height)
            UIGraphicsGetCurrentContext()?.scaleBy(x: 1.0, y: -1.0)
            UIGraphicsGetCurrentContext()?.draw(maskedImageRef!, in: CGRect(x: 0.0,y: 0.0,width:image.size.width,height: image.size.height))
            
            result = UIGraphicsGetImageFromCurrentImageContext()
            UIGraphicsEndImageContext();
    
        }
    
        pictureInput1 --> filterChromakey
        pictureInput2 --> filterChromakey --> output
        pictureInput1.processImage(synchronously: true)
        pictureInput2.processImage(synchronously: true)`

DId you get this to work with smoothing and thresholdSensitivity?

from gpuimage2.

sonvuhwg avatar sonvuhwg commented on July 23, 2024

Have you resolve the problem with UIIMageView? @florianbuerger

from gpuimage2.

florianbuerger avatar florianbuerger commented on July 23, 2024

Have you resolve the problem with UIIMageView? @florianbuerger

I did not look into further when working on this project. Seems like I reverted to using GPUImage 1 as mentioned here.

from gpuimage2.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.