CoreGraphics CGImage от CGDisplayStream странные цвета - PullRequest
0 голосов
/ 15 октября 2018

В настоящее время я впервые использую API-интерфейс CoreGraphics (в основном код C ++), и я пытаюсь получить эскиз (или «снимок экрана») из CGDisplayStream, который работает нормально, за исключением цветов.

Я создаю CGDisplayStream, используя CGDisplayStreamCreate() (документация) и использую IOSurfaceRef внутри блока обработчика (см. Это) для создания CGImageRef.Вот мой код тестирования:

CVPixelBufferRef p_buffer = NULL;
CFDictionaryRef attributes = CFDictionaryCreate(NULL, NULL, NULL, 0, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks);

CVReturn ret = CVPixelBufferCreateWithIOSurface(kCFAllocatorDefault, surface, attributes, &p_buffer);

CVPixelBufferLockBaseAddress(p_buffer, kCVPixelBufferLock_ReadOnly);

void* baseAddr = CVPixelBufferGetBaseAddress(p_buffer);
size_t width = CVPixelBufferGetWidth(p_buffer);
size_t height = CVPixelBufferGetHeight(p_buffer);

CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();

CGContextRef cgContext = CGBitmapContextCreate(baseAddr, width, height, 8, CVPixelBufferGetBytesPerRow(p_buffer), colorSpace, kCGImageAlphaNoneSkipLast);

CGImageRef img = CGBitmapContextCreateImage(cgContext);

Вызов для создания CGDisplayStream выглядит следующим образом:

CGDisplayStreamCreate(CGMainDisplayID(), 1920, 1080, 'BGRA', NULL,
                     ^(CGDisplayStreamFrameStatus status, uint64_t time, IOSurfaceRef surface, CGDisplayStreamUpdateRef metadata){ //above handler snipped is in here });

Я подозреваю, что либо pixelFormat (см. Это) или CGColorSpace производит мой странный вывод, но я не уверен.Я также не знаю, что я мог сделать сейчас, кроме как слепо угадывать некоторые случайные настройки.Может быть, кто-то может дать мне подсказку?

Вот мой вывод против "реального" скриншота.

This is my output This is a

1 Ответ

0 голосов
/ 15 октября 2018

Окончательно нашел решение здесь :

Я изменил строку

CGContextRef cgContext = CGBitmapContextCreate(baseAddr, width, height, 8, CVPixelBufferGetBytesPerRow(p_buffer), colorSpace, kCGImageAlphaNoneSkipLast);

на

CGContextRef cgContext = CGBitmapContextCreate(baseAddr, width, height, 8, CVPixelBufferGetBytesPerRow(p_buffer), colorSpace, kCGBitmapByteOrder32Little | kCGImageAlphaNoneSkipFirst);

и теперь она работает нормально.

Мне до сих пор не очень понятно, почему это решение.Я предполагаю, что на данный момент требуется более глубокое знание форматов изображения и цвета.

...