BradLarson / GPUImage

An open source iOS framework for GPU-based image and video processing
http://www.sunsetlakesoftware.com/2012/02/12/introducing-gpuimage-framework
BSD 3-Clause "New" or "Revised" License
20.25k stars 4.62k forks source link

support repeatable textures #975

Open bkramer opened 11 years ago

bkramer commented 11 years ago

I have a custom fragment shader that takes 2 inputs: a source image and a texture. Note that the texture is only 128 x 128 (and repeatable) while the source image may be any size.

I need a way to indicate to the GPUImage framework that the texture is repeatable, specifically set the GL_REPEAT property. To proceed I've added the following method to GPUImageOutput.m:

- (void)setRepeatableTexture
{
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
}

with that method i'm able to load an image with the following code:

UIImage *image = [UIImage imageNamed:@"texture.jpg"];
_texture = [[GPUImagePicture alloc] initWithImage:image smoothlyScaleOutput:YES];
[_texture setRepeatableTexture];

perhaps you would consider adding this method (or similar functionality) to the framework?

thanks, -b

BradLarson commented 11 years ago

Note that the above will break in many cases, because it isn't wrapped in a proper block on the image processing GCD queue. Also, the OpenGL ES context isn't set before that's enabled.

I've set edge clamping by default because that's the only supported mode for all but power-of-two-sized images, which is the vast majority of what gets fed into the framework. This would only work for a very small class of images, so its appeal would be limited. Still, there might be a way to incorporate this cleanly. Based on my recent slow progress, this might take months to add, though.

bkramer commented 11 years ago

I've restructured things a bit so that a bool property can be set during GPUImagePicture initialization. Now GPUImageOutput's initializeOutputTextureIfNeeded will safely set the property GL_REPEAT instead of GL_CLAMP_TO_EDGE for those occasions when I know I am using a repeatable texture that has power of two size.

Phando commented 9 years ago

Thanks for the thread, I wound up adding the following function to GPUImageOutput

-(void)setOutputTextureOptions:(GPUTextureOptions)outputTextureOptions
{
    _outputTextureOptions = outputTextureOptions;

    if( outputFramebuffer.texture )
    {
        glBindTexture(GL_TEXTURE_2D,  outputFramebuffer.texture);
        //_outputTextureOptions.format
        //_outputTextureOptions.internalFormat
        //_outputTextureOptions.magFilter
        //_outputTextureOptions.minFilter
        //_outputTextureOptions.type
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, _outputTextureOptions.wrapS);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, _outputTextureOptions.wrapT);
        glBindTexture(GL_TEXTURE_2D, 0);
    }
}