16#include "JsonStreamer.h"
21VULKAN_HPP_DEFAULT_DISPATCH_LOADER_DYNAMIC_STORAGE;
29static std::pair<vk::Format, size_t> vkColorFormatFromParams(
const rvs::Parameters& params) {
32 return {vk::Format::eG16B16R163Plane420Unorm, 6};
34 return {vk::Format::eG10X6B10X6R10X63Plane420Unorm3Pack16, 6};
36 return {vk::Format::eG8B8R83Plane420Unorm, 3};
46static std::pair<vk::Format, size_t> vkDepthFormatFromParams(
const rvs::Parameters& params) {
49 return {vk::Format::eR16Unorm, 2};
51 return {vk::Format::eR10X6UnormPack16, 2};
53 return {vk::Format::eR8Unorm, 1};
57int JsonStreamer::ReadStream::frameIndex(Clock::duration time)
const {
58 return (time / framePeriod) % frameCount;
61bool JsonStreamer::ReadStream::nextFrameReady(Clock::duration time)
const {
63 return streamedFrame != frameIndex(time);
66JsonStreamer::JsonStreamer(std::span<const uint8_t, VK_UUID_SIZE> uuid)
75void JsonStreamer::initVk(std::span<const uint8_t, VK_UUID_SIZE> uuid) {
77 VULKAN_HPP_DEFAULT_DISPATCHER.init(dl.getProcAddress<PFN_vkGetInstanceProcAddr>(
"vkGetInstanceProcAddr"));
79 constexpr auto neededInstanceExts = std::array{
80 VK_KHR_EXTERNAL_MEMORY_CAPABILITIES_EXTENSION_NAME,
81 VK_KHR_EXTERNAL_SEMAPHORE_CAPABILITIES_EXTENSION_NAME,
84 vk::ApplicationInfo ainfos(
85 "JsonStreamer", VK_MAKE_VERSION(0,0,1),
"No Engine", VK_MAKE_VERSION(0,0,0), VK_API_VERSION_1_2
88 instance = vk::createInstanceUnique(
89 vk::InstanceCreateInfo(
96 VULKAN_HPP_DEFAULT_DISPATCHER.init(*instance);
98 constexpr auto neededDeviceExts = std::array{
100 VK_KHR_EXTERNAL_MEMORY_WIN32_EXTENSION_NAME,
101 VK_KHR_EXTERNAL_SEMAPHORE_WIN32_EXTENSION_NAME,
103 VK_KHR_EXTERNAL_MEMORY_FD_EXTENSION_NAME,
104 VK_KHR_EXTERNAL_SEMAPHORE_FD_EXTENSION_NAME
109 auto phyDevs = instance->enumeratePhysicalDevices();
111 auto it = std::find_if(phyDevs.begin(), phyDevs.end(), [&](
const vk::PhysicalDevice& phy){
112 auto idProps = phy.getProperties2<vk::PhysicalDeviceProperties2, vk::PhysicalDeviceIDProperties>().get<vk::PhysicalDeviceIDProperties>();
113 return strncmp((const char*)idProps.deviceUUID.data(), (const char*)uuid.data(), VK_UUID_SIZE) == 0;
116 if(it == phyDevs.end()){
117 throw std::runtime_error(
"Could not find physical device corresponding to UUID");
121 auto props = phyDevice.getProperties();
122 std::cout <<
"Loaded streaming device : " << props.deviceName << std::endl;
124 float priority[] = { 1.f,1.0f };
126 queueFamilyIndex = 0;
127 auto queuesInfos = std::array{vk::DeviceQueueCreateInfo({}, queueFamilyIndex, 2, priority)};
129 device = phyDevice.createDeviceUnique(
130 vk::DeviceCreateInfo(
137 VULKAN_HPP_DEFAULT_DISPATCHER.init(*device);
139 queue = device->getQueue(queueFamilyIndex, 0);
140 syncQueue = device->getQueue(queueFamilyIndex, 1);
143template<
typename Closure>
144void JsonStreamer::oneTimeSubmit(Closure&& func, vk::SubmitInfo submitInfo) {
145 static thread_local vk::UniqueCommandPool commandPool;
146 static thread_local vk::UniqueFence oneTimeFence;
149 commandPool = device->createCommandPoolUnique(
150 vk::CommandPoolCreateInfo({}, queueFamilyIndex));
154 oneTimeFence = device->createFenceUnique(vk::FenceCreateInfo());
157 auto commandBuffers = device->allocateCommandBuffersUnique(
158 vk::CommandBufferAllocateInfo(
160 vk::CommandBufferLevel::ePrimary,
162 auto& cmdbuf = *commandBuffers.front();
164 cmdbuf.begin(vk::CommandBufferBeginInfo{});
168 submitInfo.setCommandBuffers(cmdbuf);
170 device->resetFences(*oneTimeFence);
172 std::scoped_lock l(queueMutex);
173 queue.submit(submitInfo, *oneTimeFence);
175 (void)device->waitForFences(*oneTimeFence, VK_TRUE, UINT64_MAX);
179void JsonStreamer::initSettings() {
180 const char* jsonPath = getenv(
"HVT_JSON_PATH");
183 std::cerr <<
"No HVT_JSON_PATH env variable set, cannot load settings" << std::endl;
184 throw HvtResult::HVT_ERROR_NOT_FOUND;
187 auto path = std::filesystem::path(jsonPath);
188 if(!std::filesystem::exists(path)) {
189 std::cerr <<
"File " << path <<
" does not exist" << std::endl;
190 throw HvtResult::HVT_ERROR_NOT_FOUND;
193 auto dir = std::filesystem::path(path).parent_path();
197 size_t numViews = config->InputCameraNames.size();
198 if(config->params_real.size() != numViews ||
199 config->depth_names.size() != numViews ||
200 config->texture_names.size() != numViews){
201 throw std::runtime_error(
"File and settings size mismatch");
205 using namespace std::chrono_literals;
206 auto framePeriod = std::chrono::nanoseconds(1s) / frameRate;
208 for(
size_t i = 0; i < numViews; i++) {
209 const auto& params = config->params_real.at(i);
210 const auto& colorFileName = config->texture_names.at(i);
211 const auto& depthFileName = config->depth_names.at(i);
213 std::filesystem::path cp(colorFileName);
214 auto colorFilePath = cp.is_absolute() ? cp : dir / cp;
216 std::filesystem::path dp(depthFileName);
217 auto depthFilePath = dp.is_absolute() ? dp : dir / dp;
220 auto colorFile = std::ifstream(colorFilePath, std::ifstream::ate | std::ifstream::binary | std::ifstream::in);
221 if(!colorFile.is_open()) {
222 throw std::runtime_error(colorFileName);
225 auto depthFile = std::ifstream(depthFilePath, std::ifstream::ate | std::ifstream::binary | std::ifstream::in);
226 if(!depthFile.is_open()) {
227 throw std::runtime_error(depthFileName);
230 auto [colorFormat, colorHalfBytesPerPixel] = vkColorFormatFromParams(params);
231 auto [depthFormat, depthBytesPerPixel] = vkDepthFormatFromParams(params);
233 size_t pixelCount = params.
getSize().width * params.
getSize().height;
235 size_t colorSize = (pixelCount * colorHalfBytesPerPixel) / 2;
236 size_t depthSize = pixelCount * depthBytesPerPixel;
238 size_t depthStride = depthSize * 3 / 2;
239 if (config->params_real[i].getDepthColorFormat() == rvs::ColorFormat::YUV400) {
240 depthStride = depthSize;
243 auto colorFileSize = colorFile.tellg();
244 auto depthFileSize = depthFile.tellg();
245 auto frameCount = colorFileSize / colorSize;
246 if(frameCount != (depthFileSize / depthStride)) {
247 throw std::runtime_error(
"Mismatching depth and color framecount");
253 HvtProjectionType ptype;
255 ptype = HvtProjectionType::HVT_PROJECTION_PERSPECTIVE;
263 ptype = HvtProjectionType::HVT_PROJECTION_EQUIRECTANGULAR;
269 throw std::runtime_error(
"Unknown projection type " + params.
getProjectionType());
277 readStreams.push_back(
279 .colorFile = std::move(colorFile),
280 .depthFile = std::move(depthFile),
281 .colorFrameStride = colorSize,
282 .colorFrameSize = colorSize,
283 .depthFrameStride = depthStride,
284 .depthFrameSize = depthSize,
286 .projectionType = ptype,
287 .intrinsics = intrinsics,
288 .extrinsics = extrinsics,
291 .colorFormat = colorFormat,
292 .depthFormat = depthFormat,
293 .framePeriod = framePeriod,
294 .frameCount = (int)frameCount
300void JsonStreamer::initVkResources() {
301 for(ReadStream& stream : readStreams) {
302 auto colorSize = stream.colorFrameSize;
303 auto depthSize = stream.depthFrameSize;
304 auto buffer = device->createBufferUnique(
305 vk::BufferCreateInfo(
308 vk::BufferUsageFlagBits::eTransferSrc,
309 vk::SharingMode::eExclusive)
312 auto reqs = device->getBufferMemoryRequirements(*buffer);
313 auto memIndex = findMemoryType(reqs.memoryTypeBits, vk::MemoryPropertyFlagBits::eHostCoherent | vk::MemoryPropertyFlagBits::eHostVisible);
315 auto memory = device->allocateMemoryUnique(
316 vk::MemoryAllocateInfo(reqs.size, memIndex));
318 device->bindBufferMemory(*buffer, *memory, 0);
319 auto mappedStagging = device->mapMemory(*memory, 0, colorSize+depthSize);
321 stream.stagingBuffer = std::move(buffer);
322 stream.stagingMemory = std::move(memory);
323 stream.stagingMapping = (
char*)mappedStagging;
327uint32_t JsonStreamer::findMemoryType(uint32_t typeFilter, vk::MemoryPropertyFlags properties)
329 vk::PhysicalDeviceMemoryProperties memProperties = phyDevice.getMemoryProperties();
330 for (uint32_t i = 0; i < memProperties.memoryTypeCount; i++) {
331 if ((typeFilter & (1 << i)) && (memProperties.memoryTypes[i].propertyFlags & properties) == properties) {
335 throw std::runtime_error(
"failed to find suitable memory type!");
338void JsonStreamer::enumerateStreamsParameters(uint32_t* streamsCount,
HvtRGBDStreamParameters* parameters)
const {
340 *streamsCount = readStreams.size();
344 if(*streamsCount != readStreams.size()){
345 throw HvtResult::HVT_ERROR_WRONG_BUFFER_SIZE;
348 for(
int i = 0;
const auto& readStream : readStreams) {
350 .
colorResolution = {(uint32_t)readStream.resolution.x, (uint32_t)readStream.resolution.y},
351 .depthResolution = {(uint32_t)readStream.resolution.x, (uint32_t)readStream.resolution.y},
353 .nearDepth = readStream.anear,
354 .farDepth = readStream.afar,
356 .colorFormat = (HvtImageFormat)readStream.colorFormat,
357 .depthFormat = (HvtImageFormat)readStream.depthFormat,
359 .slotCount = numSlots,
360 .projectionType = readStream.projectionType
362 snprintf(parameters->
name, HVT_MAX_STREAM_NAME_LENGHT,
"%s", config->InputCameraNames.at(i).c_str());
368 auto memtype = (vk::ExternalMemoryHandleTypeFlagBits)exportInfos.
memoryType;
371 if(memtype != vk::ExternalMemoryHandleTypeFlagBits::eOpaqueWin32)
373 if(memtype != vk::ExternalMemoryHandleTypeFlagBits::eOpaqueFd)
376 throw HvtResult::HVT_ERROR_UNSUPPORTED_MEMORY_TYPE;
379 auto isDepth = (bool)exportInfos.
depth;
380 auto& stream = readStreams.at(exportInfos.
streamIndex);
381 auto format = isDepth ? stream.depthFormat : stream.colorFormat;
382 auto& slots = isDepth ? stream.depthSlots : stream.colorSlots;
385 throw HvtResult::HVT_ERROR_WRONG_BUFFER_SIZE;
388 vk::ImageCreateInfo imgCreateInfo(
392 vk::Extent3D(stream.resolution.x, stream.resolution.y, 1),
395 vk::SampleCountFlagBits::e1,
396 vk::ImageTiling::eOptimal,
397 vk::ImageUsageFlagBits::eTransferDst,
398 vk::SharingMode::eExclusive,
400 vk::ImageLayout::eUndefined
403 for(
int i = 0; i < numSlots; i++) {
404 auto memoryInfos = exportInfos.
pImages[i];
406 auto imgImportInfo = vk::ExternalMemoryImageCreateInfo(memtype);
407 auto createChain = vk::StructureChain(imgCreateInfo, imgImportInfo);
409 auto image = device->createImageUnique(createChain.get<vk::ImageCreateInfo>());
410 auto reqs = device->getImageMemoryRequirements(*image);
412 auto memIndex = findMemoryType(reqs.memoryTypeBits, vk::MemoryPropertyFlagBits::eDeviceLocal);
414 assert(reqs.size == memoryInfos.size);
415 assert(reqs.alignment == memoryInfos.alignment);
417 auto memoryAllocInfo = vk::StructureChain(
418 vk::MemoryAllocateInfo(reqs.size, memIndex),
420 vk::ImportMemoryWin32HandleInfoKHR(memtype, memoryInfos.handle)
422 vk::ImportMemoryFdInfoKHR(memtype, memoryInfos.handle)
426 auto memory = device->allocateMemoryUnique(memoryAllocInfo.get<vk::MemoryAllocateInfo>());
428 device->bindImageMemory(*image, *memory, 0);
431 oneTimeSubmit([&](vk::CommandBuffer& cmd){
432 vk::ImageMemoryBarrier colorMemoryBarrier(
434 vk::AccessFlagBits::eTransferWrite,
435 vk::ImageLayout::eUndefined,
436 vk::ImageLayout::eTransferDstOptimal,
437 VK_QUEUE_FAMILY_IGNORED,
438 VK_QUEUE_FAMILY_IGNORED,
440 vk::ImageSubresourceRange(
441 vk::ImageAspectFlagBits::ePlane0 | vk::ImageAspectFlagBits::ePlane1 | vk::ImageAspectFlagBits::ePlane2,
445 vk::ImageMemoryBarrier depthMemoryBarrier(
447 vk::AccessFlagBits::eTransferWrite,
448 vk::ImageLayout::eUndefined,
449 vk::ImageLayout::eTransferDstOptimal,
450 VK_QUEUE_FAMILY_IGNORED,
451 VK_QUEUE_FAMILY_IGNORED,
453 vk::ImageSubresourceRange(
454 vk::ImageAspectFlagBits::eColor,
459 vk::PipelineStageFlagBits::eTransfer,
460 vk::PipelineStageFlagBits::eTransfer,
461 vk::DependencyFlagBits::eByRegion,
464 isDepth ? depthMemoryBarrier : colorMemoryBarrier );
467 slots.at(i) = ImageSlot{
468 .image = std::move(image),
469 .memory = std::move(memory)
472 (isDepth ? stream.importedDepth : stream.importedColor) =
true;
477 if((vk::ExternalSemaphoreHandleTypeFlagBits)exportInfos.type != vk::ExternalSemaphoreHandleTypeFlagBits::eOpaqueWin32){
479 if((vk::ExternalSemaphoreHandleTypeFlagBits)exportInfos.type != vk::ExternalSemaphoreHandleTypeFlagBits::eOpaqueFd){
481 throw HvtResult::HVT_ERROR_UNSUPPORTED_SEMAPHORE_TYPE;
484 auto sem = device->createSemaphoreUnique({});
486 device->importSemaphoreWin32HandleKHR(
487 vk::ImportSemaphoreWin32HandleInfoKHR(
490 vk::ExternalSemaphoreHandleTypeFlagBits::eOpaqueWin32,
491 exportInfos.semaphore
494 device->importSemaphoreFdKHR(
495 vk::ImportSemaphoreFdInfoKHR(
498 vk::ExternalSemaphoreHandleTypeFlagBits::eOpaqueFd,
499 exportInfos.semaphore
503 .sem = std::move(sem)
507void JsonStreamer::destroySemaphore(
Semaphore* sem)
const {
511void JsonStreamer::startStreaming() {
513 for(
auto& stream : readStreams) {
514 if(!stream.importedColor || !stream.importedDepth) {
515 throw HvtResult::HVT_ERROR_CALL_ORDER;
521 streamingThread = std::thread([&]{
528 throw HvtResult::HVT_ERROR_WRONG_BUFFER_SIZE;
531 swapPendingToReading();
533 auto imageIndex = slotReadingIndex;
536 auto& stream = readStreams.at(i);
539 desc.intrinsics = stream.intrinsics;
540 desc.imageIndex = imageIndex;
545 std::scoped_lock l(queueMutex);
555void JsonStreamer::releaseStreamsFrames(
Semaphore* waitSem) {
556 std::scoped_lock l(queueMutex);
559 vk::PipelineStageFlags stage = vk::PipelineStageFlagBits::eTopOfPipe;
569void JsonStreamer::stopStreaming() {
571 if(streamingThread.joinable()) {
572 streamingThread.join();
576JsonStreamer::~JsonStreamer() {
585void JsonStreamer::streamingLoop() {
587 auto startTime = Clock::now();
591 auto now = Clock::now();
592 auto time = now-startTime;
595 for(
auto& stream : readStreams){
596 if(stream.nextFrameReady(time)){
601 if(readyCount == readStreams.size()) {
603 oneTimeSubmit([&](vk::CommandBuffer& cmd){
604 for(
int i = 0;
auto& stream : readStreams){
605 if(stream.nextFrameReady(time)){
606 uploadFrame(cmd, i, stream, stream.frameIndex(time));
607 stream.streamedFrame = stream.frameIndex(time);
614 swapStreamingToPending();
616 std::this_thread::yield();
630void JsonStreamer::uploadFrame(vk::CommandBuffer cmd,
int streamId, ReadStream &stream,
int frame) {
631 auto colorFileOffset = frame * stream.colorFrameStride;
632 auto depthFileOffset = frame * stream.depthFrameStride;
634 stream.colorFile.seekg(colorFileOffset, std::ios_base::beg);
635 stream.depthFile.seekg(depthFileOffset, std::ios_base::beg);
638 stream.colorFile.read(stream.stagingMapping, stream.colorFrameSize);
639 stream.depthFile.read(stream.stagingMapping+stream.colorFrameSize, stream.depthFrameSize);
641 if(!stream.colorFile) {
642 std::cerr <<
"Failed to read more than " << stream.colorFile.gcount() <<
" bytes of data" << std::endl;
645 if(!stream.depthFile) {
646 std::cerr <<
"Failed to read more than " << stream.depthFile.gcount() <<
" bytes of data" << std::endl;
649 auto imageIndex = slotStreamingIndex;
651 auto& dstColorSlot = stream.colorSlots.at(imageIndex);
652 auto& dstDepthSlot = stream.depthSlots.at(imageIndex);
655 auto mainStride = (stream.colorFrameSize*2) / 3;
656 auto secondStride = mainStride / 4;
657 auto half_res = stream.resolution / 2;
660 cmd.copyBufferToImage(
661 *stream.stagingBuffer,
663 vk::ImageLayout::eTransferDstOptimal,
669 vk::ImageSubresourceLayers(
670 vk::ImageAspectFlagBits::ePlane0,
674 vk::Extent3D(stream.resolution.x, stream.resolution.y, 1)
680 vk::ImageSubresourceLayers(
681 vk::ImageAspectFlagBits::ePlane1,
685 vk::Extent3D(half_res.x, half_res.y, 1)
688 mainStride+secondStride,
691 vk::ImageSubresourceLayers(
692 vk::ImageAspectFlagBits::ePlane2,
696 vk::Extent3D(half_res.x, half_res.y, 1)
702 cmd.copyBufferToImage(
703 *stream.stagingBuffer,
705 vk::ImageLayout::eTransferDstOptimal,
706 {vk::BufferImageCopy(
707 stream.colorFrameSize,
710 vk::ImageSubresourceLayers(
711 vk::ImageAspectFlagBits::eColor,
715 vk::Extent3D(stream.resolution.x, stream.resolution.y, 1)
719void JsonStreamer::swapStreamingToPending() {
720 std::scoped_lock l(indicesMutex);
721 std::swap(slotPendingIndex, slotStreamingIndex);
722 newDataInPending =
true;
726void JsonStreamer::swapPendingToReading() {
727 std::scoped_lock l(indicesMutex);
728 if(newDataInPending) {
729 std::swap(slotPendingIndex, slotReadingIndex);
730 newDataInPending =
false;
737template<
typename Closure>
738HvtResult exceptionFirewall(Closure&& clos) {
741 }
catch(HvtResult res) {
743 }
catch(
const std::exception& e) {
744 std::cerr <<
"Catched exception at C boundary : \"" << e.what() <<
"\"" << std::endl;
745 return HvtResult::HVT_ERROR_UNKNOWN;
747 return HvtResult::HVT_ERROR_UNKNOWN;
749 return HvtResult::HVT_SUCESS;
753void checkNonNull(T ptr){
755 throw HvtResult::HVT_ERROR_INVALID_HANDLE;
769HVTAPI_ATTR HvtResult HVTAPI_CALL hvtCreateStreamingContext(
const HvtStreamingContextCreateInfo* createInfo, HvtStreamingContext* outStreamingContext) {
770 return exceptionFirewall([&]{
771 checkNonNull(createInfo);
774 throw HvtResult::HVT_ERROR_HEADER_VERSION;
778 *outStreamingContext = context->to_handle();
789HVTAPI_ATTR HvtResult HVTAPI_CALL hvtEnumerateStreamsParameters(HvtStreamingContext streamingContext, uint32_t* pStreamParameterCount,
HvtRGBDStreamParameters* pStreamParameters) {
790 return exceptionFirewall([&]{
791 auto context = JsonStreamer::check(streamingContext);
792 checkNonNull(pStreamParameterCount);
793 context->enumerateStreamsParameters(pStreamParameterCount, pStreamParameters);
803HVTAPI_ATTR HvtResult HVTAPI_CALL hvtExportStreamImages(HvtStreamingContext streamingContext,
const HvtStreamImagesExportInfo* exportInfos) {
804 return exceptionFirewall([&]{
805 auto context = JsonStreamer::check(streamingContext);
806 checkNonNull(exportInfos);
807 context->importStreamImages(*exportInfos);
818HVTAPI_ATTR HvtResult HVTAPI_CALL hvtExportSemaphore(HvtStreamingContext streamingContext,
const HvtSemaphoreExportInfo* exportInfo, HvtSemaphore* outSemaphore) {
819 return exceptionFirewall([&]{
820 auto context = JsonStreamer::check(streamingContext);
821 checkNonNull(exportInfo);
822 auto sem = context->importSemaphore(*exportInfo);
823 *outSemaphore = sem->to_handle();
833HVTAPI_ATTR HvtResult HVTAPI_CALL hvtDestroySemaphore(HvtStreamingContext streamingContext, HvtSemaphore semaphore) {
834 return exceptionFirewall([&]{
835 auto context = JsonStreamer::check(streamingContext);
836 context->destroySemaphore(Semaphore::check(semaphore));
846HVTAPI_ATTR HvtResult HVTAPI_CALL hvtStartStreaming(HvtStreamingContext streamingContext) {
847 return exceptionFirewall([&]{
848 auto context = JsonStreamer::check(streamingContext);
849 context->startStreaming();
859HVTAPI_ATTR HvtResult HVTAPI_CALL hvtAcquireStreamsFrames(HvtStreamingContext streamingContext,
const HvtAcquireStreamFramesInfo* infos) {
860 return exceptionFirewall([&]{
861 auto context = JsonStreamer::check(streamingContext);
862 context->acquireStreamsFrames(*infos);
875HVTAPI_ATTR HvtResult HVTAPI_CALL hvtReleaseStreamsFrames(HvtStreamingContext streamingContext, HvtSemaphore waitSemaphore) {
876 return exceptionFirewall([&]{
877 auto context = JsonStreamer::check(streamingContext);
878 context->releaseStreamsFrames(Semaphore::opt_check(waitSemaphore));
887HVTAPI_ATTR HvtResult HVTAPI_CALL hvtStopStreaming(HvtStreamingContext streamingContext) {
888 return exceptionFirewall([&]{
889 auto context = JsonStreamer::check(streamingContext);
890 context->stopStreaming();
899HVTAPI_ATTR HvtResult HVTAPI_CALL hvtDestroyStreamingContext(HvtStreamingContext streamingContext) {
900 return exceptionFirewall([&]{
901 auto context = JsonStreamer::check(streamingContext);
static Config loadFromFile(std::string const &filename, std::string const &dir)
int getColorBitDepth() const
std::string const & getProjectionType() const
cv::Vec3f getRotation() const
cv::Vec2f getDepthRange() const
cv::Vec2f getPrinciplePoint() const
cv::Vec2f getHorRange() const
cv::Vec2f getVerRange() const
cv::Vec3f getPosition() const
int getDepthBitDepth() const
cv::Vec2f getFocal() const
Parameters for query of the current frames infos.
HvtSemaphore signalSemaphore
HvtStreamFrameInfo * pStreamFrameInfos
Intrinsics parameters of an equirectangular projection.
Intrinsics parameters of a perspective projection.
Description of an RGBD stream.
char name[HVT_MAX_STREAM_NAME_LENGHT]
HvtExtent2D colorResolution
Export info for images of a stream.
HvtImageMemoryType memoryType
HvtStreamImageMemoryInfo * pImages
Parameters for the creation of the Streaming context.
uint8_t graphicsDeviceUUID[VK_UUID_SIZE]
Union of possible intrinsics types data.