I'm building a Photo App for the iPhone using GPUImage by Brad Larson and based on the DLCImagePickerController by GoBackSpaces (which helped me learn lots of stuff so far), but I'm stuck with one of the features I want the App to have. I have two sets of cases:
Cases A: a set of cases that represent "film rolls" (Filter Cases) Cases B: a set of cases that represent "camera lenses" (Len Cases)
Within each case I have GPUImageFilterGroups. I want the user to be able to choose a filter from Cases A and then be able to apply another filter from Cases B over the same StaticPicture. So, in short, after the user chooses a filter from Cases A the StaticPicture changes according to the filter chosen, then I want to apply another filter from Cases B over that modified StaticPicture. I tried it several different ways, but I had no luck. The StaticPicture disappears after choosing a filter from Cases B. Do I need to retain something? Any help would be truly appreciated. Here is my code:
filter = [[GPUImageRGBFilter alloc] init];
lens = [[GPUImageRGBFilter alloc] init];
-(void) filterClicked:(UIButton *) sender {
for(UIView *view in self.filterScrollView.subviews){
if([view isKindOfClass:[UIButton class]]){
[(UIButton *)view setSelected:NO];
}
}
[sender setSelected:YES];
[self removeAllTargets];
selectedFilter = sender.tag;
[self setFilter:sender.tag];
[self prepareFilter];
}
-(void) lensClicked:(UIButton *) sender {
for(UIView *view in self.lensScrollView.subviews){
if([view isKindOfClass:[UIButton class]]){
[(UIButton *)view setSelected:NO];
}
}
[sender setSelected:YES];
selectedLens = sender.tag;
[self setLens:sender.tag];
[self prepareLens];
}
-(void) setFilter:(int) index {
switch (index) {
case 1:{
filter = [[GPUImageFilterGroup alloc] init];
UIImage *inputImage23 = [UIImage imageNamed:@"vignette.png"];
sourcePicture5 = [[GPUImagePicture alloc] initWithImage:inputImage23 smoothlyScaleOutput:YES];
GPUImageOverlayBlendFilter * overlay23 = [[GPUImageOverlayBlendFilter alloc] init];
[(GPUImageFilterGroup *)filter addFilter:overlay23];
[sourcePicture5 addTarget:overlay23 atTextureLocation:1];
[sourcePicture5 processImage];
UIImage *inputImage21 = [UIImage imageNamed:@"frame.png"];
sourcePicture6 = [[GPUImagePicture alloc] initWithImage:inputImage21 smoothlyScaleOutput:YES];
GPUImageNormalBlendFilter * overlay21 = [[GPUImageNormalBlendFilter alloc] init];
[(GPUImageFilterGroup *)filter addFilter:overlay21];
[sourcePicture6 addTarget:overlay21 atTextureLocation:1];
[sourcePicture6 processImage];
GPUilforddelta100 *ilford = [[GPUilforddelta100 alloc] init];
[(GPUImageFilterGroup *)filter addFilter:ilford];
[overlay23 addTarget:overlay21];
[overlay21 addTarget:ilford];
[(GPUImageFilterGroup *)filter setInitialFilters:[NSArray arrayWithObject:overlay23]];
[(GPUImageFilterGroup *)filter setTerminalFilter:ilford];
} break;
case 2: {
filter = [[GPUImageFilterGroup alloc] init];
UIImage *inputImage1 = [UIImage imageNamed:@"trixgrain.png"];
sourcePicture = [[GPUImagePicture alloc] initWithImage:inputImage1 smoothlyScaleOutput:YES];
GPUImageMultiplyBlendFilter * overlay1 = [[GPUImageMultiplyBlendFilter alloc] init];
[(GPUImageFilterGroup *)filter addFilter:overlay1];
[sourcePicture addTarget:overlay1 atTextureLocation:1];
[sourcePicture processImage];
UIImage *inputImage2 = [UIImage imageNamed:@"trixfeel.png"];
sourcePicture3 = [[GPUImagePicture alloc] initWithImage:inputImage2 smoothlyScaleOutput:YES];
GPUImageOverlayBlendFilter * overlay2 = [[GPUImageOverlayBlendFilter alloc] init];
[(GPUImageFilterGroup *)filter addFilter:overlay2];
[sourcePicture3 addTarget:overlay2 atTextureLocation:1];
[sourcePicture3 processImage];
UIImage *inputImage18 = [UIImage imageNamed:@"frame.png"];
sourcePicture2 = [[GPUImagePicture alloc] initWithImage:inputImage18 smoothlyScaleOutput:YES];
GPUImageNormalBlendFilter * overlay18 = [[GPUImageNormalBlendFilter alloc] init];
[(GPUImageFilterGroup *)filter addFilter:overlay18];
[sourcePicture2 addTarget:overlay18 atTextureLocation:1];
[sourcePicture2 processImage];
GPUTrix400 *trix400 = [[GPUTrix400 alloc] init];
[(GPUImageFilterGroup *)filter addFilter:trix400];
[overlay2 addTarget:overlay1];
[overlay1 addTarget:overlay18];
[overlay18 addTarget:trix400];
[(GPUImageFilterGroup *)filter setInitialFilters:[NSArray arrayWithObject:overlay2]];
[(GPUImageFilterGroup *)filter setTerminalFilter:trix400];
} break;
default:
filter = [[GPUImageRGBFilter alloc] init];
break;
}
}
-(void) setLens:(int) index {
switch (index) {
case 1:{
lens = [[GPUImageFilterGroup alloc] init];
UIImage *inputImage1 = [UIImage imageNamed:@"lightleak.png"];
sourcePicture = [[GPUImagePicture alloc] initWithImage:inputImage1 smoothlyScaleOutput:YES];
GPUImageOverlayBlendFilter * overlay1 = [[GPUImageOverlayBlendFilter alloc] init];
[(GPUImageFilterGroup *)lens addFilter:overlay1];
[sourcePicture addTarget:overlay1 atTextureLocation:1];
[sourcePicture processImage];
UIImage *inputImage18 = [UIImage imageNamed:@"holgaframe.png"];
sourcePicture2 = [[GPUImagePicture alloc] initWithImage:inputImage18 smoothlyScaleOutput:YES];
GPUImageNormalBlendFilter * overlay18 = [[GPUImageNormalBlendFilter alloc] init];
[(GPUImageFilterGroup *)lens addFilter:overlay18];
[sourcePicture2 addTarget:overlay18 atTextureLocation:1];
[sourcePicture2 processImage];
GPUholgaroid *holgaroid = [[GPUholgaroid alloc] init];
[(GPUImageFilterGroup *)lens addFilter:holgaroid];
[holgaroid addTarget:overlay1];
[overlay1 addTarget:overlay18];
[(GPUImageFilterGroup *)lens setInitialFilters:[NSArray arrayWithObject:holgaroid]];
[(GPUImageFilterGroup *)lens setTerminalFilter:overlay18];
} break;
case 2:{
lens = [[GPUImageFilterGroup alloc] init];
UIImage *inputImage1 = [UIImage imageNamed:@"dianafeel.png"];
sourcePicture = [[GPUImagePicture alloc] initWithImage:inputImage1 smoothlyScaleOutput:YES];
GPUImageOverlayBlendFilter * overlay1 = [[GPUImageOverlayBlendFilter alloc] init];
[(GPUImageFilterGroup *)lens addFilter:overlay1];
[sourcePicture addTarget:overlay1 atTextureLocation:1];
[sourcePicture processImage];
UIImage *inputImage18 = [UIImage imageNamed:@"dianaframe.png"];
sourcePicture2 = [[GPUImagePicture alloc] initWithImage:inputImage18 smoothlyScaleOutput:YES];
GPUImageNormalBlendFilter * overlay18 = [[GPUImageNormalBlendFilter alloc] init];
[(GPUImageFilterGroup *)lens addFilter:overlay18];
[sourcePicture2 addTarget:overlay18 atTextureLocation:1];
[sourcePicture2 processImage];
GPUdianaf *dianaf = [[GPUdianaf alloc] init];
[(GPUImageFilterGroup *)lens addFilter:dianaf];
[dianaf addTarget:overlay1];
[overlay1 addTarget:overlay18];
[(GPUImageFilterGroup *)lens setInitialFilters:[NSArray arrayWithObject:dianaf]];
[(GPUImageFilterGroup *)lens setTerminalFilter:overlay18];
} break;
default:
lens = [[GPUImageRGBFilter alloc] init];
break;
}
}
-(void) prepareFilter {
if (![UIImagePickerController isSourceTypeAvailable: UIImagePickerControllerSourceTypeCamera]) {
isStatic = YES;
}
if (!isStatic) {
[self prepareLiveFilter];
} else {
[self prepareStaticFilter];
}
}
-(void) prepareLiveFilter {
[filter removeAllTargets];
[cropFilter removeAllTargets];
[blurFilter removeAllTargets];
[stillCamera addTarget:cropFilter];
[cropFilter addTarget:filter];
if (hasBlur) {
[filter addTarget:blurFilter];
[blurFilter addTarget:self.imageView];
} else {
[filter addTarget:self.imageView];
}
//GPUImage issue with new code, do not use until further improvement
//[filter prepareForImageCapture];
}
-(void) prepareStaticFilter {
if (!staticPicture) {
[self performSelector:@selector(switchToLibrary:) withObject:nil afterDelay:3.5];
}
[stillCamera removeAllTargets];
[staticPicture removeAllTargets];
[staticPicture addTarget:filter];
if (hasBlur) {
[filter addTarget:blurFilter];
[blurFilter addTarget:self.imageView];
} else {
[filter addTarget:self.imageView];
}
GPUImageRotationMode imageViewRotationMode = kGPUImageNoRotation;
switch (staticPictureOriginalOrientation) {
case UIImageOrientationLeft:
imageViewRotationMode = kGPUImageRotateLeft;
break;
case UIImageOrientationRight:
imageViewRotationMode = kGPUImageRotateRight;
break;
case UIImageOrientationDown:
imageViewRotationMode = kGPUImageRotate180;
break;
default:
imageViewRotationMode = kGPUImageNoRotation;
break;
}
[self.imageView setInputRotation:imageViewRotationMode atIndex:0];
[staticPicture processImage];
}
-(void) prepareLens {
if (![UIImagePickerController isSourceTypeAvailable: UIImagePickerControllerSourceTypeCamera]) {
isStatic = YES;
}
if (!isStatic) {
[self prepareLiveLens];
} else {
[self prepareStaticLens];
}
}
-(void) prepareLiveLens {
[stillCamera addTarget:lens];
[lens addTarget:self.imageView];
//GPUImage issue with new code, do not use until further improvement
//[lens prepareForImageCapture];
}
-(void) prepareStaticLens {
if (!staticPicture) {
[self performSelector:@selector(switchToLibrary:) withObject:nil afterDelay:3.5];
}
[staticPicture addTarget:lens];
[lens addTarget:self.imageView];
GPUImageRotationMode imageViewRotationMode = kGPUImageNoRotation;
switch (staticPictureOriginalOrientation) {
case UIImageOrientationLeft:
imageViewRotationMode = kGPUImageRotateLeft;
break;
case UIImageOrientationRight:
imageViewRotationMode = kGPUImageRotateRight;
break;
case UIImageOrientationDown:
imageViewRotationMode = kGPUImageRotate180;
break;
default:
imageViewRotationMode = kGPUImageNoRotation;
break;
}
[self.imageView setInputRotation:imageViewRotationMode atIndex:0];
[staticPicture processImage];
}
-(void) removeAllTargets {
[filter removeAllTargets];
[lens removeAllTargets];
[sourcePicture removeAllTargets];
[sourcePicture2 removeAllTargets];
[sourcePicture3 removeAllTargets];
[stillCamera removeAllTargets];
[staticPicture removeAllTargets];
[cropFilter removeAllTargets];
[blurFilter removeAllTargets];
}
-(void) prepareForCapture {
[stillCamera.inputCamera lockForConfiguration:nil];
if(self.flashToggleButton.selected &&
[stillCamera.inputCamera hasTorch]){
[stillCamera.inputCamera setTorchMode:AVCaptureTorchModeOn];
[self performSelector:@selector(captureImage)
withObject:nil
afterDelay:0.50];
}else{
[self captureImage];
}
}
-(void)captureImage {
[lens forceProcessingAtSize:CGSizeMake (1936, 1936)];
[staticPicture addTarget:lens];
[stillCamera capturePhotoAsImageProcessedUpToFilter:lens
withCompletionHandler:^(UIImage *processed, NSError *error) {
isStatic = YES;
runOnMainQueueWithoutDeadlocking(^{
@autoreleasepool {
[stillCamera.inputCamera unlockForConfiguration];
[stillCamera stopCameraCapture];
[self removeAllTargets];
staticPicture = [[GPUImagePicture alloc] initWithImage:processed smoothlyScaleOutput:NO];
staticPictureOriginalOrientation = processed.imageOrientation;
[self prepareFilter];
[self.retakeButton setHidden:NO];
[self.photoCaptureButton setTitle:@"Done" forState:UIControlStateNormal];
[self.photoCaptureButton setImage:nil forState:UIControlStateNormal];
[self.photoCaptureButton setEnabled:YES];
if(![self.filtersToggleButton isSelected]){
[self showFilters];
}
}
});
}];
}
-(IBAction) takePhoto:(id)sender{
[self.photoCaptureButton setEnabled:NO];
if (!isStatic) {
isStatic = YES;
[self.libraryToggleButton setHidden:YES];
[self.cameraToggleButton setEnabled:NO];
[self.flashToggleButton setEnabled:NO];
[self prepareForCapture];
} else {
GPUImageOutput<GPUImageInput> *processUpTo;
if (hasBlur) {
processUpTo = blurFilter;
} else {
processUpTo = lens;
}
[staticPicture processImage];
UIImage *currentFilteredVideoFrame = [processUpTo imageFromCurrentlyProcessedOutputWithOrientation:staticPictureOriginalOrientation];
NSDictionary *info = [[NSDictionary alloc] initWithObjectsAndKeys:
UIImageJPEGRepresentation(currentFilteredVideoFrame, self.outputJPEGQuality), @"data", nil];
[self.delegate imagePickerController:self didFinishPickingMediaWithInfo:info];
}
}
-(void) dealloc {
[self removeAllTargets];
stillCamera = nil;
cropFilter = nil;
filter = nil;
blurFilter = nil;
sourcePicture = nil;
sourcePicture2 = nil;
sourcePicture3 = nil;
staticPicture = nil;
self.blurOverlayView = nil;
self.focusView = nil;
}
Thanks in advance for any explanation or help with this question from a noobie.