Quantcast
Channel: Блоги Intel® Developer Zone
Viewing all articles
Browse latest Browse all 106

Запись и воспроизведение последовательностей потоков в Intel® RealSense™ SDK

$
0
0

В Intel® RealSense™ SDK предусмотрена новая возможность для записи последовательности потоков с камеры на диск для дальнейшего воспроизведения. Это очень удобно для отладки и устранения проблем с камерой в приложениях.

Запись необработанных потоков цветного изображения и глубины налагает достаточно высокие требования на пропускную способность ввода-вывода дисков системы. Например, при конфигурации цветного изображения 1920 x 1080, 32 бита RGB, 30 кадров в секунду, и конфигурации канала глубины 640 х 480, 30 кадров в секунду, для записи на диск пропускная способность подсистемы ввода-вывода должна составлять около 272 МБ/с. Это значение превышает максимальную возможную скорость большинства обычных дисков и даже некоторых твердотельных накопителей.

Для решения этой проблемы в SDK реализована экспериментальная функция сжатия изображения перед записью на диск. Функция сжатия реализована на основе алгоритма H.264 (только I-кадры, постоянное значение параметра квантования) для цветного изображения и алгоритма сжатия без потерь LZO (по фамилиям разработчиков: Лемпель, Зив, Оберхумер) для канала глубины. Коэффициент сжатия составляет около 10:1 для цветного изображения и около 2:1 для канала глубины. Необходимая пропускная способность дисковой подсистемы ввода-вывода снижается до 32 МБ/с. Для использования этой функции требуется ГП Intel® Iris™ Graphics с последней версией соответствующего драйвера. Для управления функциями записи используются следующие параметры реестра:

WindowsRegistryEditorVersion 5.00
[HKEY_CURRENT_USER\SOFTWARE\Intel\RSSDK\FileRecording]
"DisableH264Compression"=dword:0
"H264_QPI"=dword:8
"DisableLZOCompression"=dword:0

По умолчанию сжатие H.264 включено для потока цветного изображения, а сжатие LZO включено для всех остальных потоков. Значение QPI алгоритма H.264 (значение параметра квантования I-кадров) задается в диапазоне от 0 (самое слабое сжатие) до 51 (самое сильное сжатие).

Важное примечание. Файл, записанный со сжатием по алгоритму H.264, можно воспроизводить только в системах с ГП IntelIrisGraphics.

В коде C++, C# или Java используйте SetFileName из экземпляра CaptureManager, чтобы задать имя файла и режим (запись или воспроизведение). 

C++    pxcStatus SetFileName(pxcCHAR *file, pxcBool record); 
C#       pxcmStatus SetFileName(String file, Boolean record); 
Java  pxcmStatus SetFileName(string file, boolean record); 

Параметры
file    Полный путь к файлу для воспроизведения или для записи.
record    При значении true устанавливается режим записи. В противном случае устанавливается режим воспроизведения.

Действия по записи последовательности в файл

  • Используйте функцию SetFileName из экземпляра CaptureManager.
  • Укажите имя файла и установите значение true для режима записи. Имена файлов устанавливаются без каких-либо ограничений. В режиме записи файл должен быть доступен для записи.
  • Измените параметры реестра, если нужно записать поток без сжатия.

Вот образец кода для записи или воспроизведения последовательностей:

       void RecordORPlayback(pxcCHAR *file, bool record) {
	   // Create a SenseManager instance
	   PXCSenseManager *sm=PXCSenseManager::CreateInstance();

	   // Set file recording or playback
	   sm->QueryCaptureManager()->SetFileName(file,record);

	   // Select the color stream
	   sm->EnableStream(PXCCapture.STREAM_TYPE_COLOR,640,480,0);

	   // Initialize and Record 300 frames
	   sm->Init();
	   for (int i=0;i<300;i++) {
	       // This function blocks until a color sample is ready
	       if (sm->AcquireFrame(true)<PXC_STATUS_NO_ERROR) break;

	       // Retrieve the sample
	       PXCCapture::Sample *sample=sm->QuerySample();

	       // Work on the image sample->color
	       ...

	       // Go fetching the next sample
	       sm->ReleaseFrame();
	   }

	   // close down
	   sm->Release();
	}   

При записи отснятые изображения записываются на диск в том виде, в каком они обрабатываются приложением. Например, если приложение записывает потоки цветного изображения и глубины без выравнивания, то и записанные на диск последовательности будут без выравнивания. Если приложение выравнивает записанные каналы, то и на диск будут записаны выровненные последовательности.

Записанный файл содержит заголовок фиксированного размера со следующей структурой:

struct Header {

   pxcI32    ID;                    // PXC_UID('R','S','C','F')
   pxcI32    fileVersion;           // file version
   pxcI32    firstFrameOffset;      // The byte offset to the meta data of the first frame.
   pxcI32    nstreams;              // The number of streams.
   pxcI64    frameIndexingOffset;   // Optional frame indexing offset, zero if not available.
   PXCSession::CoordinateSystem coordinateSystem; // The coordinate system setting.
   pxcI32    reserved[26];
};  

Кадры изображения любого потока записываются последовательно после заголовка. Началом потока является тег ChunkFrameMetaData, окончанием — тег ChunkFrameData. Между ними может быть несколько кадров конфигурации, описывающих метаданные кадра изображения. Метаданные должны интерпретироваться как изменения (дельта) по сравнению с данными, указанными в заголовке файла. Это позволяет экономить размер, если некоторые метаданные являются общими для всех кадров. Структура кадра:

	struct StreamFrame {
	   ChunkFrameMetaData frame_header;

	   // in no defined order
	   ChunkImageMetaData image_meta_data;      // if any.

	  // there could be more chunks here.
	  ChunkFrameData     frame_data;
	} frames[] 

Структура ChunkFrameMetaData:

	struct ChunkFrameMetaData {
	   ChunkId   chunkId=CHUNK_FRAME_META_DATA;
	   pxcI32    chunkSize=sizeof(metaData);
	   struct {
	       pxcI32    frameNumber;  // frame number in the current stream
	       PXCCapture::StreamType streamType;
	       pxcI64    timeStamp;
	       PXCImage::Option options;
	   } metaData;
	}; 

Можно поместить ChunkImageMetaData в кадр со следующей структурой:

	struct ChunkImageMetaData {
	   ChunkId   chunkId=CHUNK_IMAGE_META_DATA;
	   pxcI32    chunkSize=sizeof(buffer)+sizeof(id);
	   pxcUID    id;  // meta data identifier
	   pxcBYTE   buffer[chunkSize-sizeof(id)];
	};  

Структура потока без сжатия:

	struct ChunkFrameDataUncompressed {
	   ChunkId   chunkId=CHUNK_FRAME_DATA;
	   pxcI32    chunkSize=sizeof(imageData);
	   struct {
	       pxcI32  pitches[PXCImage::NUM_OF_PLANES];
	       pxcBYTE plane0[pitches[0]*height];
	       ...
	       pxcBYTE planeN[pitches[PXCImage::NUM_OF_PLANES-1]*height];
	   } imageData
	};  

Структура потока со сжатием:

  struct ChunkFrameDataCompressed {

	   ChunkId   chunkId=CHUNK_FRAME_DATA;
	   pxcI32    chunkSize=sizeof(imageData);
	   struct {
	       pxcI32  pitches[PXCImage::NUM_OF_PLANES]; // pitches of uncompressed image planes.
	       enum {
	           H264=0x343632,
	           LZO=0x4f5a4c,
	       } CompressionIdentifier;
	       pxcBYTE compressed_data[];
	   } imageData
	};

Модуль записи RealSense™ SDK добавит кадр конфигурации в файл. Кадр конфигурации может содержать любые произвольные данные, заданные посредством идентификатора фрагмента и размера фрагмента. Порядок данных фрагмента в файле не имеет значения, но есть общее правило: если между двумя фрагментами существуют зависимости, то зависимый фрагмент должен находиться в файле после фрагмента, от которого он зависит. Структура ChunkData:

	struct ChunkData {
	   enum ChunkId {
	       CHUNK_DEVICEINFO       =   1,
	       CHUNK_STREAMINFO       =   2,
	       CHUNK_PROPERTIES       =   3,
	       CHUNK_PROFILES         =   4,
	       CHUNK_SERIALIZEABLE    =   5,
	       CHUNK_FRAME_META_DATA  =   6,
	       CHUNK_FRAME_DATA       =   7,
	       CHUNK_IMAGE_META_DATA  =   8,
	       CHUNK_FRAME_INDEXING   =   9,
	   }chunkId;               // The chunk identifier
	   pxcI32    chunkSize;             // The chunk size in bytes-8.
	   pxcBYTE   chunkData[chunkSize];  // The chunk data buffer
	} chunks[]; 

Некоторые кадры конфигурации, которые должны быть в файлах:

  • CHUNK_DEVICEINFO — информация об устройстве 
  • CHUNK_STREAMINFO — информация о потоке 
  • CHUNK_PROPERTIES — свойства устройства
  • CHUNK_PROFILES — профили потока
  • CHUNK_SERIALIZEABLE — калибровка устройства
  • CHUNK_FRAME_INDEXING — индексирование кадров

Действия по воспроизведению записанного файла последовательности

  • Используйте функцию SetFileName из экземпляра CaptureManager. 
  • Укажите имя файла в формате rssdk и установите значение false для режима записи.

Для воспроизведения файла SDK сразу же создает экземпляр Capture (с помощью функции QueryCapture), чтобы приложение могло опрашивать возможности записанного содержимого. Можно настроить воспроизведение файлов в SDK следующим образом.

Функция

Значение по умолчанию

Описание                                                                          

SetPause

false

Если задано значение true, при воспроизведении возвращается одна и та же выборка текущего кадра.

SetRealtime

true

Если задано значение true, при воспроизведении возвращается выборка текущего кадра на момент его демонстрации (согласно отметке времени выборки). Если задано значение false, при воспроизведении сразу же возвращается выборка.

Выберите pause=true и realtime=false, если нужно с точностью найти какие-либо данные кадра при воспроизведении. Вот образец кода с демонстрацией использования SetRealtime и SetPause:

// Create a SenseManager instance

	PXCSenseManager* sm = PXCSenseManager::CreateInstance();

	// Set file playback name
	sm->QueryCaptureManager()->SetFileName(filename, false);

	// Enable stream and Initialize
	sm->EnableStream(PXCCapture::STREAM_TYPE_COLOR, 0, 0);
	sm->Init();

	// Set realtime=false and pause=true
	sm->QueryCaptureManager()->SetRealtime(false);
	sm->QueryCaptureManager()->SetPause(true);

	// Streaming loop
	for (int i = 0; i < nframes; i+=3) {

	   // Set to work on every 3rd frame of data
	   sm->QueryCaptureManager()->SetFrameByIndex(i);
	   sm->FlushFrame();

	   // Ready for the frame to be ready
	   pxcStatus sts = sm->AcquireFrame(true);
	   if (sts < PXC_STATUS_NO_ERROR) break;

	   // Retrieve the sample and work on it. The image is in sample->color.
	   PXCCapture::Sample* sample = sm->QuerySample();
	   ....

	   // Resume processing the next frame
	   sm->ReleaseFrame();
	}

	// Clean up
	sm->Release();  

Итак, как описано в этой статье, новая функция Intel® RealSense™ SDK дает разработчикам возможность встраивать код для записи последовательностей с камеры на диск со сжатием и для воспроизведения записанных файлов. Это очень удобно для отладки и устранения неполадок в приложениях.


Viewing all articles
Browse latest Browse all 106

Trending Articles