2012-03-04 1 views
4

처음으로 Core Image (OS X, 10.7.3)를 실험 중이며 벽돌 벽을 실행 중입니다. 나는 이것이 내가 어리석은 일이라고 확신한다. 그리고 나에게 그것을 지적하기위한 틀을 더 잘 알고있는 누군가가 필요하다. 이 코드를 실행하는 경우CIFilter의 outputImage에 액세스하려고 시도 할 때 "인식 할 수없는 선택기"

CIImage *inputImage = [CIImage imageWithContentsOfURL:imageURL]; 
CIFilter *filter = [CIFilter filterWithName:@"CIAreaAverage" keysAndValues: 
                kCIInputImageKey, inputImage, 
                kCIInputExtentKey, [inputImage valueForKey:@"extent"], 
                nil]; 
CIImage *outputImage = (CIImage *)[filter valueForKey:@"outputImage"]; 
이, 마지막 줄 트리거

:

다음 코드를 고려 (의이 imageURL 디스크에 JPG를 가리키는 유효한 파일 URL이라고 규정하자)

0 CoreFoundation      0x00007fff96c2efc6 __exceptionPreprocess + 198 
1 libobjc.A.dylib      0x00007fff9153cd5e objc_exception_throw + 43 
2 CoreFoundation      0x00007fff96cbb2ae -[NSObject doesNotRecognizeSelector:] + 190 
3 CoreFoundation      0x00007fff96c1be73 ___forwarding___ + 371 
4 CoreFoundation      0x00007fff96c1bc88 _CF_forwarding_prep_0 + 232 
5 CoreImage       0x00007fff8f03c38d -[CIAreaAverage outputImage] + 52 
6 Foundation       0x00007fff991d8384 _NSGetUsingKeyValueGetter + 62 
7 Foundation       0x00007fff991d8339 -[NSObject(NSKeyValueCoding) valueForKey:] + 392 

이제 Core Image Filter Reference에는 CIAreaAverage가 "관심 영역의 평균 색상을 포함하는 단일 픽셀 이미지를 반환합니다."라고 명시되어 있습니다. 사실, 더 이해할 수, I 필터합니다 (valueForKey: 전화를 시도하기 전에) 디버거에서 속성을 검사 할 때 :

(lldb) po [filter attributes] 
(id) $3 = 0x00007fb3e3ef0e00 { 
    CIAttributeDescription = "Calculates the average color for the specified area in an image, returning the result in a pixel."; 
    CIAttributeFilterCategories =  (
     CICategoryReduction, 
     CICategoryVideo, 
     CICategoryStillImage, 
     CICategoryBuiltIn 
    ); 
    CIAttributeFilterDisplayName = "Area Average"; 
    CIAttributeFilterName = CIAreaAverage; 
    CIAttributeReferenceDocumentation = "http://developer.apple.com/cgi-bin/apple_ref.cgi?apple_ref=//apple_ref/doc/filter/ci/CIAreaAverage"; 
    inputExtent =  { 
     CIAttributeClass = CIVector; 
     CIAttributeDefault = "[0 0 640 80]"; 
     CIAttributeDescription = "A rectangle that specifies the subregion of the image that you want to process."; 
     CIAttributeDisplayName = Extent; 
     CIAttributeType = CIAttributeTypeRectangle; 
     CIUIParameterSet = CIUISetBasic; 
    }; 
    inputImage =  { 
     CIAttributeClass = CIImage; 
     CIAttributeDescription = "The image to process."; 
     CIAttributeDisplayName = Image; 
     CIUIParameterSet = CIUISetBasic; 
    }; 
    outputImage =  { 
     CIAttributeClass = CIImage; 
    }; 
} 

바로 outputImage을있다 - 타입 CIImage로 제공!

그래서 내가 뭘 잘못하고 있니? 필자가 보았던 모든 문서 및 자습서에서는 이 outputImage을 포함하여 속성에 액세스하는 올바른 방법임을 나타냅니다.

답변

7

나는 당신의 범위가 범인이라고 믿습니다. (그러나 그것은 이상합니다.) 익스텐트를 CIVector *로 변경하면 작동합니다.

NSURL *imageURL = [NSURL fileURLWithPath:@"/Users/david/Desktop/video.png"]; 
CIImage *inputImage = [CIImage imageWithContentsOfURL:imageURL]; 
CIFilter *filter = [CIFilter filterWithName:@"CIAreaAverage"]; 
[filter setValue:inputImage forKey:kCIInputImageKey]; 
CGRect inputExtent = [inputImage extent]; 
CIVector *extent = [CIVector vectorWithX:inputExtent.origin.x 
             Y:inputExtent.origin.y 
             Z:inputExtent.size.width 
             W:inputExtent.size.height]; 
[filter setValue:extent forKey:kCIInputExtentKey]; 
CIImage *outputImage = [filter valueForKey:@"outputImage"]; 

는 [inputImage 범위]은 CGRect를 반환하지만 분명히 CIVector *이 더 잘 작동합니다.

+0

가 흠 ... 뭔가 내가 기대 한 것 없습니다. 나는 오늘 밤 이것을 확인하고 다시 너에게 갈거야. 감사! –

+0

나는 이것이 당신을 위해 일했는지 여부를 알고 싶어합니다. – devguydavid

+0

미안하지만, 나는 잊지 않았다, 나는 방금 다른 일로 가득 찼다. (그리고 이것은 "개인 호기심"프로젝트를위한 것이다.) 나는 내가 다시 게시 할 것을 약속한다. –

0

는 여기가 iOS 앱에 CIAreaAverage 작업을 만든 방법은 다음과 같습니다

CGRect inputExtent = [self.inputImage extent]; 
CIVector *extent = [CIVector vectorWithX:inputExtent.origin.x 
             Y:inputExtent.origin.y 
             Z:inputExtent.size.width 
             W:inputExtent.size.height]; 
CIImage* inputAverage = [CIFilter filterWithName:@"CIAreaAverage" keysAndValues:@"inputImage", self.inputImage, @"inputExtent", extent, nil].outputImage; 

//CIImage* inputAverage = [self.inputImage imageByApplyingFilter:@"CIAreaMinimum" withInputParameters:@{@"inputImage" : inputImage, @"inputExtent" : extent}]; 
EAGLContext *myEAGLContext = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2]; 
NSDictionary *options = @{ kCIContextWorkingColorSpace : [NSNull null] }; 
CIContext *myContext = [CIContext contextWithEAGLContext:myEAGLContext options:options]; 

size_t rowBytes = 32 ; // ARGB has 4 components 
uint8_t byteBuffer[rowBytes]; // Buffer to render into 

[myContext render:inputAverage toBitmap:byteBuffer rowBytes:rowBytes bounds:[inputAverage extent] format:kCIFormatRGBA8 colorSpace:nil]; 

const uint8_t* pixel = &byteBuffer[0]; 
float red = pixel[0]/255.0; 
float green = pixel[1]/255.0; 
float blue = pixel[2]/255.0; 
NSLog(@"%f, %f, %f\n", red, green, blue); 


return outputImage; 
} 
@end 

출력은 다음과 같이 보일 것입니다 :

2015-05-23 15:58:20.935 CIFunHouse[2400:489913] 0.752941, 0.858824, 0.890196 
2015-05-23 15:58:20.981 CIFunHouse[2400:489913] 0.752941, 0.858824, 0.890196