COM: Add helper for SAFEARRAY creation
Signed-off-by: Simon Rozman <simon@rozman.si>
This commit is contained in:
parent
b0cf45a0f1
commit
f33010e6b6
@ -34,7 +34,8 @@ namespace winstd
|
||||
/// \param[in] msg Error message
|
||||
///
|
||||
com_runtime_error(_In_ error_type num, _In_ const std::string& msg) : num_runtime_error<HRESULT>(num, msg)
|
||||
{}
|
||||
{
|
||||
}
|
||||
|
||||
///
|
||||
/// Constructs an exception
|
||||
@ -43,7 +44,8 @@ namespace winstd
|
||||
/// \param[in] msg Error message
|
||||
///
|
||||
com_runtime_error(_In_ error_type num, _In_opt_z_ const char* msg = nullptr) : num_runtime_error<HRESULT>(num, msg)
|
||||
{}
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
/// @}
|
||||
@ -1460,6 +1462,58 @@ namespace winstd
|
||||
/// \addtogroup WinStdCOMHelpers
|
||||
/// @{
|
||||
|
||||
///
|
||||
/// Builds SAFEARRAY of uniform data
|
||||
///
|
||||
/// \param[in] vt Type of array element
|
||||
/// \param[in] array Pointer to data
|
||||
/// \param[in] columns Number of columns. When 1, SafeArrayCreateVector is used; when >1, SafeArrayCreate is used.
|
||||
/// \param[in] rows Number of rows
|
||||
///
|
||||
/// \return Returns SAFEARRAY
|
||||
///
|
||||
inline _Ret_notnull_ LPSAFEARRAY BuildSAFEARRAY(_In_ VARTYPE vt, _In_opt_ LPCVOID array, _In_ ULONG columns, _In_ ULONG rows)
|
||||
{
|
||||
const size_t n = columns * rows;
|
||||
if (!array && n)
|
||||
throw std::invalid_argument("array is NULL");
|
||||
|
||||
safearray sa;
|
||||
if (columns == 1) {
|
||||
// Make vector when one column only.
|
||||
sa = SafeArrayCreateVector(vt, 0, rows);
|
||||
}
|
||||
else {
|
||||
// Make 2-dimensional array when more columns.
|
||||
SAFEARRAYBOUND dim[2] = {
|
||||
{ columns, 0 },
|
||||
{ rows, 0 }
|
||||
};
|
||||
sa = SafeArrayCreate(vt, 2, dim);
|
||||
}
|
||||
if (!sa)
|
||||
throw std::bad_alloc();
|
||||
|
||||
size_t elem_size;
|
||||
switch (vt) {
|
||||
case VT_UI4:
|
||||
case VT_I4: elem_size = 4; break;
|
||||
case VT_UI2:
|
||||
case VT_I2:
|
||||
case VT_BOOL: elem_size = 2; break;
|
||||
case VT_UI1:
|
||||
case VT_I1: elem_size = 1; break;
|
||||
default: throw std::invalid_argument("unsupported type");
|
||||
};
|
||||
|
||||
{
|
||||
safearray_accessor<void> saa(sa);
|
||||
memcpy(saa.data(), array, elem_size * n);
|
||||
}
|
||||
|
||||
return sa.detach();
|
||||
}
|
||||
|
||||
///
|
||||
/// Builds VBARRAY of uniform data
|
||||
///
|
||||
@ -1476,7 +1530,7 @@ namespace winstd
|
||||
if (!array && n)
|
||||
throw std::invalid_argument("array is NULL");
|
||||
|
||||
LPSAFEARRAY sa;
|
||||
safearray sa;
|
||||
if (columns == 1) {
|
||||
// Make vector when one column only.
|
||||
sa = SafeArrayCreateVector(VT_VARIANT, 0, rows);
|
||||
@ -1536,7 +1590,7 @@ namespace winstd
|
||||
|
||||
VARIANT var;
|
||||
V_VT(&var) = VT_ARRAY | VT_VARIANT;
|
||||
V_ARRAY(&var) = sa;
|
||||
V_ARRAY(&var) = sa.detach();
|
||||
return var;
|
||||
}
|
||||
|
||||
@ -1560,7 +1614,7 @@ namespace winstd
|
||||
if (!array && rows)
|
||||
throw std::invalid_argument("array is NULL");
|
||||
|
||||
LPSAFEARRAY sa;
|
||||
safearray sa;
|
||||
if constexpr (columns == 1) {
|
||||
// Make vector when one column only.
|
||||
sa = SafeArrayCreateVector(VT_VARIANT, 0, rows);
|
||||
@ -1590,7 +1644,7 @@ namespace winstd
|
||||
|
||||
VARIANT var;
|
||||
V_VT(&var) = VT_ARRAY | VT_VARIANT;
|
||||
V_ARRAY(&var) = sa;
|
||||
V_ARRAY(&var) = sa.detach();
|
||||
return var;
|
||||
}
|
||||
|
||||
@ -1614,7 +1668,7 @@ namespace winstd
|
||||
|
||||
// Allocate.
|
||||
size_t pallete_size = sizeof(RGBQUAD) * bmh.biClrUsed;
|
||||
LPSAFEARRAY sa = SafeArrayCreateVector(VT_UI1, 0, static_cast<ULONG>(sizeof(BITMAPFILEHEADER) + sizeof(bmh) + pallete_size + bmh.biSizeImage));
|
||||
safearray sa = SafeArrayCreateVector(VT_UI1, 0, static_cast<ULONG>(sizeof(BITMAPFILEHEADER) + sizeof(bmh) + pallete_size + bmh.biSizeImage));
|
||||
if (!sa)
|
||||
throw std::bad_alloc();
|
||||
|
||||
@ -1642,7 +1696,7 @@ namespace winstd
|
||||
|
||||
VARIANT var;
|
||||
V_VT(&var) = VT_ARRAY | VT_UI1;
|
||||
V_ARRAY(&var) = sa;
|
||||
V_ARRAY(&var) = sa.detach();
|
||||
return var;
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user