NSBitmapImageRep to RGB с высокой эффективностью - PullRequest
2 голосов
/ 20 октября 2011

Я работаю над своим первым приложением Mac OSX Cocoa для 10.5+, где у меня есть CVImageBufferRef (захваченный с помощью QTKit), мне нужно перенести этот образ через TCP Socket в клиентское приложение. Клиентскому приложению нужны значения RGB. Вот что я сейчас делаю (мое текущее решение работает по мере необходимости, но использует много ресурсов ЦП)

CVImageBufferRef -> NSBitmapImageRep -> NSData -> затем передать NSData через сокет TCP клиентскому приложению, и на стороне клиента у меня есть следующий код для получения RGB:

UInt8 r,g,b
int width=320;
int height=240;

NSData *data; //read from TCP Socket
NSBitmapImageRep *bitmap=[[NSBitmapImageRep alloc] initWithData:data];

for (y=1;y<=height;y++) {
    for(x=1;x<=width;x++){


        NSColor *color=[bitmap colorAtX:x y:y];
        // ^^ this line is actually a culprit and uses a lot of CPU


        r=[color redComponent]*100;
        g=[color greenComponent]*100;
        b=[color blueComponent]*100;
        NSLog(@"r:%d g:%d b:%d",r,g,b);
    }
}

[bitmap release];

Если CVImageBufferRef можно преобразовать в массив значений RGB, который был бы идеальным, в противном случае мне нужно эффективное решение для преобразования NSBitmapImageRep в значения RGB.

Ответы [ 2 ]

3 голосов
/ 20 октября 2011

Если идти прямо из CVImageBufferRef, вы можете использовать CVPixelBuffer, так как он является производным от CVImageBuffer.Используйте CVPixelBufferLockBaseAddress (), а затем CVPixelBufferGetBaseAddress (), чтобы получить указатель на первый пиксель.Существует также множество других методов CVPixelBufferGet * (http://developer.apple.com/library/mac/#documentation/QuartzCore/Reference/CVPixelBufferRef/Reference/reference.html) для запроса ширины, высоты и т. Д. Для получения информации о размере передаваемых данных. И, конечно, CVPixelBufferUnlockBaseAddress (), когда-то выполненный с данными.

Если вы используете NSBitmapImageRep, я согласен с Джастином. Использование [bitmap bitmapData] вернет указатель на первый элемент. Даже без предварительного знания вы можете отправить необработанные данные, которые будут:

unsigned char *data = [bitmap bitmapData];
unsigned long size = [bitmap pixelsWide]*[bitmap pixelsHigh]*[bitmap samplesPerPixel]*sizeof(unsigned char);

Эти данныезатем будут RGB-последовательные значения, т.е. 1stRedComponent = *(data + 0), 1stGreenComponent = *(data + 1) 1stBlueComponent = *(data + 2) предоставит вам первый компонент RGB в данных, если вам нужен пиксельно-специфичный доступ вне NSBitmapImageRep

3 голосов
/ 20 октября 2011

Вы можете просто получить данные растрового изображения, используя bitmapData, и взять из них нужные вам значения пикселей. Это должно сделать во многих случаях более чем в 100 раз быстрее.

(журнал тоже должен идти)

...