193 lines
8.3 KiB
C++
193 lines
8.3 KiB
C++
|
#include "stdafx.h"
|
||
|
|
||
|
#include "camera_helper.h"
|
||
|
|
||
|
//#include <format.h>
|
||
|
|
||
|
namespace {
|
||
|
namespace internal {
|
||
|
template<camera::Property property> struct property_traits {};
|
||
|
|
||
|
template<long Id>
|
||
|
struct camera_control_property_traits
|
||
|
{
|
||
|
typedef IAMCameraControl Interface;
|
||
|
static long id() { return Id; }
|
||
|
};
|
||
|
|
||
|
template<long Id>
|
||
|
struct video_proc_amp_property_traits
|
||
|
{
|
||
|
typedef IAMVideoProcAmp Interface;
|
||
|
static long id() { return Id; }
|
||
|
};
|
||
|
|
||
|
template<> struct property_traits < camera::Exposure > : public camera_control_property_traits<CameraControl_Exposure> {};
|
||
|
template<> struct property_traits < camera::Focus > : public camera_control_property_traits<CameraControl_Focus>{};
|
||
|
template<> struct property_traits < camera::Zoom > : public camera_control_property_traits<CameraControl_Zoom>{};
|
||
|
template<> struct property_traits < camera::Pan > : public camera_control_property_traits<CameraControl_Pan>{};
|
||
|
template<> struct property_traits < camera::Tilt > : public camera_control_property_traits<CameraControl_Tilt>{};
|
||
|
template<> struct property_traits < camera::Roll > : public camera_control_property_traits<CameraControl_Roll>{};
|
||
|
template<> struct property_traits < camera::Iris > : public camera_control_property_traits<CameraControl_Iris>{};
|
||
|
|
||
|
template<> struct property_traits < camera::Brightness > : public video_proc_amp_property_traits<VideoProcAmp_Brightness>{};
|
||
|
template<> struct property_traits < camera::Contrast > : public video_proc_amp_property_traits<VideoProcAmp_Contrast>{};
|
||
|
template<> struct property_traits < camera::Hue > : public video_proc_amp_property_traits<VideoProcAmp_Hue>{};
|
||
|
template<> struct property_traits < camera::Saturation > : public video_proc_amp_property_traits<VideoProcAmp_Saturation>{};
|
||
|
template<> struct property_traits < camera::Sharpness > : public video_proc_amp_property_traits<VideoProcAmp_Sharpness>{};
|
||
|
template<> struct property_traits < camera::Gamma > : public video_proc_amp_property_traits<VideoProcAmp_Gamma>{};
|
||
|
template<> struct property_traits < camera::ColorEnable > : public video_proc_amp_property_traits<VideoProcAmp_ColorEnable>{};
|
||
|
template<> struct property_traits < camera::WhiteBalance > : public video_proc_amp_property_traits<VideoProcAmp_WhiteBalance>{};
|
||
|
template<> struct property_traits < camera::BacklightCompensation > : public video_proc_amp_property_traits<VideoProcAmp_BacklightCompensation>{};
|
||
|
template<> struct property_traits < camera::Gain > : public video_proc_amp_property_traits < VideoProcAmp_Gain > {};
|
||
|
|
||
|
template<typename Interface> struct interface_traits {};
|
||
|
template<> struct interface_traits < IAMCameraControl >
|
||
|
{
|
||
|
static long auto_flag() { return CameraControl_Flags_Auto; }
|
||
|
static long manual_flag() { return CameraControl_Flags_Manual; }
|
||
|
};
|
||
|
template<> struct interface_traits<IAMVideoProcAmp>
|
||
|
{
|
||
|
static long auto_flag() { return VideoProcAmp_Flags_Auto; }
|
||
|
static long manual_flag() { return VideoProcAmp_Flags_Manual; }
|
||
|
};
|
||
|
|
||
|
template<typename Interface, typename SourcePtr>
|
||
|
bool has(long id, const SourcePtr& source_ptr) {
|
||
|
comet::com_ptr<Interface> pInterface = comet::com_cast(source_ptr);
|
||
|
if (!pInterface) return false;
|
||
|
long value, flags;
|
||
|
HRESULT hr = pInterface->Get(id, &value, &flags);
|
||
|
return SUCCEEDED(hr);
|
||
|
}
|
||
|
|
||
|
template<typename Interface, typename SourcePtr>
|
||
|
cam_prop_range get_range(long id, const SourcePtr& source_ptr) {
|
||
|
comet::com_ptr<Interface> pInterface = comet::try_cast(source_ptr);
|
||
|
cam_prop_range range;
|
||
|
long flags;
|
||
|
pInterface->GetRange(id, &range.min, &range.max, &range.step, &range.defaultValue, &flags) | comet::raise_exception;
|
||
|
range.canBeAuto = (flags & interface_traits<Interface>::auto_flag()) != 0;
|
||
|
range.canBeManual = (flags & interface_traits<Interface>::manual_flag()) != 0;
|
||
|
return range;
|
||
|
}
|
||
|
|
||
|
template<typename Interface, typename SourcePtr>
|
||
|
cam_prop_value get(long id, const SourcePtr& source_ptr) {
|
||
|
comet::com_ptr<Interface> pInterface = comet::try_cast(source_ptr);
|
||
|
cam_prop_value value;
|
||
|
long flags;
|
||
|
pInterface->Get(id, &value.value, &flags) | comet::raise_exception;
|
||
|
value.isAuto = (flags & interface_traits<Interface>::auto_flag()) != 0 || (flags & interface_traits<Interface>::manual_flag()) == 0;
|
||
|
return value;
|
||
|
}
|
||
|
|
||
|
template<typename Interface, typename SourcePtr>
|
||
|
void set(long id, const cam_prop_value& value, const SourcePtr& source_ptr) {
|
||
|
comet::com_ptr<Interface> pInterface = comet::try_cast(source_ptr);
|
||
|
long flags = value.isAuto ? interface_traits<Interface>::auto_flag() : interface_traits<Interface>::manual_flag();
|
||
|
pInterface->Set(id, value.value, flags) | comet::raise_exception;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
#define MAP_OVER_CAMERA_PROPERTIES(FUNC) \
|
||
|
FUNC(::camera::Exposure, Exposure) \
|
||
|
FUNC(::camera::Focus, Focus) \
|
||
|
FUNC(::camera::Zoom, Zoom) \
|
||
|
FUNC(::camera::Pan, Pan) \
|
||
|
FUNC(::camera::Tilt, Tilt) \
|
||
|
FUNC(::camera::Roll, Roll) \
|
||
|
FUNC(::camera::Iris, Iris) \
|
||
|
FUNC(::camera::Brightness, Brightness) \
|
||
|
FUNC(::camera::Contrast, Contrast) \
|
||
|
FUNC(::camera::Hue, Hue) \
|
||
|
FUNC(::camera::Saturation, Saturation) \
|
||
|
FUNC(::camera::Sharpness, Sharpness) \
|
||
|
FUNC(::camera::Gamma, Gamma) \
|
||
|
FUNC(::camera::ColorEnable, Color Enable) \
|
||
|
FUNC(::camera::WhiteBalance, White Balance) \
|
||
|
FUNC(::camera::BacklightCompensation, Backlight Compensation) \
|
||
|
FUNC(::camera::Gain, Gain)
|
||
|
|
||
|
|
||
|
bool camera::has(Property property) const
|
||
|
{
|
||
|
switch (property) {
|
||
|
#define CASE(PROP, NAME) case PROP: return ::internal::has<::internal::property_traits<PROP>::Interface>(::internal::property_traits<PROP>::id(), source_ptr);
|
||
|
MAP_OVER_CAMERA_PROPERTIES(CASE)
|
||
|
#undef CASE
|
||
|
default:
|
||
|
return false;
|
||
|
}
|
||
|
}
|
||
|
cam_prop_range camera::get_range(Property property) const
|
||
|
{
|
||
|
switch (property) {
|
||
|
#define CASE(PROP, NAME) case PROP: return ::internal::get_range<::internal::property_traits<PROP>::Interface>(::internal::property_traits<PROP>::id(), source_ptr);
|
||
|
MAP_OVER_CAMERA_PROPERTIES(CASE)
|
||
|
#undef CASE
|
||
|
default:
|
||
|
throw std::runtime_error("No such property: " + std::string(camera::property_name(property)));
|
||
|
}
|
||
|
}
|
||
|
cam_prop_value camera::get(Property property) const
|
||
|
{
|
||
|
switch (property) {
|
||
|
#define CASE(PROP, NAME) case PROP: return ::internal::get<::internal::property_traits<PROP>::Interface>(::internal::property_traits<PROP>::id(), source_ptr);
|
||
|
MAP_OVER_CAMERA_PROPERTIES(CASE)
|
||
|
#undef CASE
|
||
|
default:
|
||
|
throw std::runtime_error("No such property: " + std::string(camera::property_name(property)));
|
||
|
}
|
||
|
}
|
||
|
void camera::set(Property property, const cam_prop_value& value)
|
||
|
{
|
||
|
switch (property) {
|
||
|
#define CASE(PROP, NAME) case PROP: ::internal::set<::internal::property_traits<PROP>::Interface>(::internal::property_traits<PROP>::id(), value, source_ptr); break;
|
||
|
MAP_OVER_CAMERA_PROPERTIES(CASE)
|
||
|
#undef CASE
|
||
|
}
|
||
|
}
|
||
|
|
||
|
std::vector<camera::Property> camera::list_properties()
|
||
|
{
|
||
|
std::vector<camera::Property> properties;
|
||
|
properties.push_back(Exposure); // CameraControl
|
||
|
properties.push_back(Focus);
|
||
|
properties.push_back(Zoom);
|
||
|
properties.push_back(Pan);
|
||
|
properties.push_back(Tilt);
|
||
|
properties.push_back(Roll);
|
||
|
properties.push_back(Iris);
|
||
|
|
||
|
properties.push_back(Brightness);
|
||
|
properties.push_back(Contrast);
|
||
|
properties.push_back(Hue);
|
||
|
properties.push_back(Saturation);
|
||
|
properties.push_back(Sharpness);
|
||
|
properties.push_back(Gamma);
|
||
|
properties.push_back(ColorEnable);
|
||
|
properties.push_back(WhiteBalance);
|
||
|
properties.push_back(BacklightCompensation);
|
||
|
properties.push_back(Gain);
|
||
|
|
||
|
return properties;
|
||
|
//#define PROPENTRY(PROP, NAME) PROP,
|
||
|
// MAP_OVER_CAMERA_PROPERTIES(PROPENTRY)
|
||
|
//#undef PROPENTRY
|
||
|
// };
|
||
|
}
|
||
|
|
||
|
const char* camera::property_name(Property property)
|
||
|
{
|
||
|
switch (property) {
|
||
|
#define CASE(PROP, NAME) case PROP: return #NAME;
|
||
|
MAP_OVER_CAMERA_PROPERTIES(CASE)
|
||
|
#undef CASE
|
||
|
default:
|
||
|
return "UNKNOWN";
|
||
|
}
|
||
|
}
|