Common Vision Blox 15.0
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Events Friends Modules Pages
Acquisition and Streaming - Multiple Components

Some devices may be able to provide multiple pieces of data in a single data streams. For example, there could be a camera that sends two pieces of data, one being a color image and the seconds some metadata such as timestamp and location. As these two pieces of information are different but related (unlike a camera sending two data streams), these will be presented as a single Cvb::Composite object.

using namespace Cvb;
auto devices = DeviceFactory::Discover(DiscoverFlags::IgnoreVins);
auto device = DeviceFactory::Open<GenICamDevice>(devices[0].AccessToken(), AcquisitionStack::GenTL);
auto stream = device->Stream<CompositeStream>(); // default: index = 0 (1)
stream->Start();
while(true)
{
CompositePtr composite;
WaitStatus status;
std::tie(composite, status, nodeMaps) = stream->Wait(); // (2)
for (int i = 0; i < composite->ItemCount(); i++) // (3)
{
auto component = composite->ItemAt(i);
if (auto image = get_if<ImagePtr>(&component))
{
// Process image
}
else if (auto pointCloud = get_if<PointCloudPtr>(&component))
{
// Process point cloud
}
}
}
stream->Abort();
void Start() override
static std::vector< DiscoveryInformation > Discover()
static std::shared_ptr< T > Open(const String &provider, AcquisitionStack acquisitionStack=AcquisitionStack::PreferVin)
WaitStatus
std::shared_ptr< Composite > CompositePtr

using (var devices = DeviceFactory.Discover(DiscoverFlags.IgnoreVins))
{
using (var device = (GenICamDevice)DeviceFactory.Open(devices[0], AcquisitionStack.GenTL))
{
var stream = device.GetStream<CompositeStream>(0); // (1)
stream.Start();
while(true) {
WaitStatus status;
using (var composite = stream.Wait(out status)) // (2)
{
foreach (var part in composite) // (3)
{
if (part.GetType() == typeof(Image)) {
var image = Image.FromHandle(part.Handle, ShareObject.No);
// Process image
}
else if (part.GetType() == typeof(PointCloud)) {
var pointCloud = PointCloud.FromHandle(part.Handle, ShareObject.No);
// Process point cloud
}
}
}
}
stream.Abort(); // (6)
}
}
static Device Open(DiscoveryInformation info, AcquisitionStack acquisitionStack=AcquisitionStack.PreferVin)
static DiscoveryInformationList Discover()
static PointCloud FromHandle(IntPtr handle, ShareObject doShare)
cvbbool_t ShareObject(OBJ Object)
__int3264 Image

import cvb
devices = cvb.DeviceFactory.discover_from_root(cvb.DiscoverFlags.IgnoreVins)
with cvb.DeviceFactory.open(devices[0].access_token, cvb.AcquisitionStack.GenTL) as device:
stream = device.stream(cvb.CompositeStream) # default: index = 0 (1)
stream.start()
while True:
composite, status, node_maps = stream.wait() # (2)
with composite:
for part in composite: # (3)
if isinstance(part, cvb.Image):
# Process image
elif isinstance(part, cvb.PointCloud):
# Process point cloud
stream.abort() # (6)
Union[cvb.GenICamDevice, cvb.VinDevice, cvb.EmuDevice, cvb.VideoDevice, cvb.NonStreamingDevice] open(str provider, int acquisition_stack=cvb.AcquisitionStack.PreferVin)
List[cvb.DiscoveryInformation] discover_from_root(int flags=cvb.DiscoverFlags.FindAll, int time_span=300)

Note: Error handling has been omitted from the above example.

Note: In this example, we treat each component as potentially being a different type on each frame. In reality, for a specific camera model, the component type at each index should not change type (i.e. item 1 is always the image, item 2 is the metadata, etc).

  1. The device and stream are opened as normal. To ensure that all components can be received, the stream must be of type Cvb::CompositeStream.
  2. The composite is read from the stream in the same manner as a normal image.
  3. Each component of a Cvb::Composite has a specified type, Cvb::Image, Cvb::PointCloud, etc. The type of the component is checked to determine how to process it.