-
Notifications
You must be signed in to change notification settings - Fork 0
API‐Arithmetic
Namespace: acl::arithmetic (CPP) / acl::neon::arithmetic (NEON)
Per-pixel sum of two images dst = src1 + src2; input operand types and output type are decoupled (AT / BT → DT).
Tier: Starter+
Channels: 1ch / 3ch / 4ch
Inplace: supported (dst == src1 or dst == src2)
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
AT, BT, DT (CPP) |
{uint8_t, uint16_t, float} |
— |
T (NEON) |
{uint8_t, uint16_t} |
NEON-only |
Variant entry points (CPP):
| Entry point | Purpose |
|---|---|
addImg |
Sum of two images, no saturation |
addImgClamp |
Sum of two images, result clamped to [minValue, maxValue]
|
add_Imgs |
N-image accumulation (srcImages[0] + srcImages[1] + …) |
add_ImgsClamp |
N-image accumulation + clamp |
add_ImgsManual |
N-image accumulation with manually specified intermediate accumulation type ACC_T
|
add_ImgsManualClamp |
N-image accumulation + manual ACC_T + clamp |
template<class AT, class BT, class DT>
int addImg(
const AT* src1Image, const BT* src2Image, DT* dstImage,
int width, int height, int cn = 1,
int src1Stride = 0, int src2Stride = 0, int dstStride = 0);
template<class AT, class BT, class DT>
int addImgClamp(
const AT* src1Image, const BT* src2Image, DT* dstImage,
int width, int height, int cn,
int src1Stride, int src2Stride, int dstStride,
DT minValue, DT maxValue);
template<class ST, class DT>
int add_Imgs(
const ST* const* srcImages, int srcNum, DT* dstImage,
int width, int height, int cn = 1,
int srcStride = 0, int dstStride = 0);| Parameter | Type | Meaning | Default |
|---|---|---|---|
src1Image, src2Image
|
const AT*, const BT*
|
Inputs | non-null |
dstImage |
DT* |
Output | non-null |
width, height
|
int |
Image size | > 0 |
cn |
int |
Channel count | 1 |
*Stride |
int |
Bytes per row |
0 = auto |
minValue, maxValue
|
DT |
(clamp variant only) output upper/lower bounds | — |
template<class T>
int addImg(
const T* src1, const T* src2, T* dstImage,
int width, int height, int cn = 1,
int src1Stride = 0, int src2Stride = 0, int dstStride = 0);NEON provides only
addImgitself (single template acrossuint8_t/float, etc., same type for both inputs and output); variants such as N-image accumulation, clamp, and manual ACC_T are via the CPP version.
uint8_t a[1920*1080], b[1920*1080], dstImage[1920*1080];
// Sum of two images (u8)
acl::neon::arithmetic::addImg(a, b, dstImage, 1920, 1080);
// Saturating clamp to [0, 200] (CPP)
acl::arithmetic::addImgClamp<uint8_t, uint8_t, uint8_t>(
a, b, dstImage, 1920, 1080, 1, 0, 0, 0,
/*minValue=*/0, /*maxValue=*/200);
// Accumulate 10 images into u16 to avoid u8 overflow
const uint8_t* imgs[10] = { /* ... */ };
uint16_t acc[1920*1080];
acl::arithmetic::add_Imgs<uint8_t, uint16_t>(
imgs, 10, acc, 1920, 1080);Per-pixel absolute difference of two images dst = |src1 - src2|.
Tier: Starter+
Channels: any
Inplace: supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
ST1 |
uint8_t, uint16_t, float |
— |
ST2 |
uint8_t, uint16_t, float |
— |
DT |
uint8_t, uint16_t, float |
— |
template<class T>
int absDiff(
const T* src1, const T* src2, T* dstImage,
int width, int height, int cn,
int src1Stride = 0, int src2Stride = 0, int dstStride = 0);Available as both
acl::arithmetic::absDiff(CPP) andacl::neon::arithmetic::absDiff(NEON) — identical signature, different namespace. NEON path supportsuint8_t/float/double;uint16_tfalls through to scalar.
uint8_t a[1920*1080], b[1920*1080], diff[1920*1080];
// Frame differencing (motion detection)
acl::neon::arithmetic::absDiff<uint8_t>(a, b, diff, 1920, 1080, 1);Weighted sum dst = alpha*src1 + beta*src2 + gamma. Typical uses: image transitions, exposure fusion.
Tier: Starter+
Channels: 1ch / 3ch / 4ch
Inplace: supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
T |
uint8_t, uint16_t, float |
— |
template<class ST1, class ST2, class DT>
int addWeighted(
const ST1* src1, const ST2* src2, DT* dstImage,
int width, int height, int cn,
int src1Stride, int src2Stride, int dstStride,
double alpha, double beta, double gamma);template<class T>
int addWeighted(
const T* src1, const T* src2, T* dstImage,
int width, int height,
int cn = 1,
int src1Stride = 0, int src2Stride = 0, int dstStride = 0,
double alpha = 1.0, double beta = 1.0, double gamma = 0.0);uint8_t a[1920*1080*3], b[1920*1080*3], dstImage[1920*1080*3];
// 50% blend: dstImage = 0.5 * a + 0.5 * b
acl::neon::arithmetic::addWeighted(
a, b, dstImage, 1920, 1080, 3, 0, 0, 0, 0.5, 0.5, 0.0);Alpha blending C = alpha * A + (1 - alpha) * B.
Tier: Starter+
Channels: 1ch (the width*cn parameter is in bytes)
Inplace: supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
ST1 |
uint8_t, uint16_t, float |
— |
ST2 |
uint8_t, uint16_t, float |
— |
DT |
uint8_t, uint16_t, float |
— |
template<class T>
int alphaImgFusion(
const T* A, const T* B, T* C,
int width, int height,
int AStride, int BStride, int CStride,
float alpha);| Parameter | Type | Meaning | Default |
|---|---|---|---|
A, B
|
const T* |
The two input images | non-null |
C |
T* |
Output blended image | non-null |
AStride, BStride, CStride
|
int |
Bytes per row |
0 = auto |
alpha |
float |
Weight of A, [0, 1]
|
— |
Per-pixel multiplication C = A * B. When saturateCast = true the result saturates to the CT type (e.g. uint8_t is clamped to [0, 255]).
Tier: Starter+
Channels: 1ch / 3ch / 4ch
Inplace: supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
AT, BT, CT (CPP) |
{uint8_t, uint16_t, float} |
— |
T (NEON) |
{uint8_t, uint16_t} |
NEON-only |
template<class AT, class BT, class CT>
int mul(
const AT* A, const BT* B, CT* C,
int width, int height, int cn,
int AStride, int BStride, int CStride,
bool saturateCast = false);template<class T>
int mul(
const T* A, const T* B, T* C,
int width, int height, int cn,
int AStride, int BStride, int CStride,
bool saturateCast = false);NEON requires
AT == BT == CT(i.e.T); for heterogeneous types, use the CPP version.
Fixed-threshold binarization / truncation.
Tier: Starter+
Channels: 1ch
Inplace: supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
T |
uint8_t, uint16_t, float |
— |
ThreshMode: THRESH_BINARY / THRESH_BINARY_INV / THRESH_TRUNC / THRESH_TOZERO / THRESH_TOZERO_INV / THRESH_OTSU (u8 only) |
template<class ST, class DT>
int threshold(
const ST* srcImage, DT* dstImage,
int width, int height,
ST threshold,
DT maxVal = 255, DT minVal = 0,
int srcStride = 0, int dstStride = 0,
acl::ThreshMode tm = acl::ThreshMode::THRESH_BINARY);
THRESH_OTSUmode automatically computes the optimal threshold (the passed-inthresholdparameter is ignored); onlyuint8_t/uint16_tare supported.
template<class T>
int threshold(
const T* srcImage, T* dstImage,
int width, int height,
T threshold,
T maxVal = 255, T minVal = 0,
int srcStride = 0, int dstStride = 0,
acl::ThreshMode tm = acl::ThreshMode::THRESH_BINARY);uint8_t gray[1920*1080], bin[1920*1080];
// Fixed-threshold binarization
acl::neon::arithmetic::threshold<uint8_t>(
gray, bin, 1920, 1080, /*threshold=*/128,
/*maxVal=*/255, /*minVal=*/0, 0, 0,
acl::ThreshMode::THRESH_BINARY);
// Otsu automatic threshold (CPP only)
acl::arithmetic::threshold<uint8_t, uint8_t>(
gray, bin, 1920, 1080, /*threshold=*/0,
/*maxVal=*/255, /*minVal=*/0, 0, 0,
acl::ThreshMode::THRESH_OTSU); // threshold parameter is ignoredAdaptive threshold — each pixel's threshold = local_mean(src, blockSize) - C (or Gaussian-weighted mean).
Tier: Pro+
Channels: 1ch
Inplace: not supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
T |
uint8_t, uint16_t, float |
— |
Method: ADAPTIVE_THRESH_MEAN_C / ADAPTIVE_THRESH_GAUSSIAN_C
|
template<class T>
int adaptiveThreshold(
const T* srcImage, T* dstImage,
int width, int height,
int srcStride, int dstStride,
T maxVal,
int blockSize,
double C,
acl::AdaptiveThreshMethod am = acl::AdaptiveThreshMethod::ADAPTIVE_THRESH_MEAN_C);| Parameter | Type | Meaning | Default |
|---|---|---|---|
srcImage, dstImage
|
const T* / T*
|
input / output | non-null |
width, height
|
int |
Image size | > 0 |
srcStride, dstStride
|
int |
Bytes per row |
0 = auto |
maxVal |
T |
Output value for pixels above threshold | typically 255
|
blockSize |
int |
Local window size (must be odd and ≥ 3) | typically 11 / 25
|
C |
double |
Threshold adjustment constant | typically 2 ~ 10
|
am |
acl::AdaptiveThreshMethod |
ADAPTIVE_THRESH_MEAN_C / ADAPTIVE_THRESH_GAUSSIAN_C
|
MEAN_C |
template<class T>
int adaptiveThreshold(
const T* srcImage, T* dstImage,
int width, int height,
int srcStride, int dstStride,
T maxVal,
int blockSize,
double C,
acl::AdaptiveThreshMethod am = acl::AdaptiveThreshMethod::ADAPTIVE_THRESH_MEAN_C);Bitwise operations AND / NOT / XOR.
Tier: Starter+
Channels: 1ch / 3ch / 4ch
Inplace: supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
T (CPP) |
{uint8_t, uint16_t} |
— |
T (NEON) |
uint8_t |
NEON-only |
No
bitwiseOrentry point (OR can be composed as NOT + AND + NOT; the current version does not provide it separately).
// AND
template<class T>
int bitwiseAnd(
const T* src1, const T* src2, T* dstImage,
int width, int height, int cn,
int src1Stride = 0, int src2Stride = 0, int dstStride = 0);
// NOT
template<class T>
int bitwiseNot(
const T* srcImage, T* dstImage,
int width, int height, int cn,
int srcStride = 0, int dstStride = 0);
// XOR
template<class T>
int bitwiseXor(
const T* src1, const T* src2, T* dstImage,
int width, int height, int cn,
int src1Stride = 0, int src2Stride = 0, int dstStride = 0);Lookup-table transform dst[i] = table[src[i]]. Commonly used for gamma correction, color mapping, curve adjustments.
Tier: Starter+
Channels: 1ch / 3ch / 4ch
Inplace: supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
ST ∈ {uint8_t}, DT ∈ {uint8_t, uint16_t, float} (CPP) |
tested combinations | — |
T (NEON) |
uint8_t |
NEON-only |
template<class ST, class DT>
int lut(
const ST* srcImage, DT* dstImage,
const DT* table,
int width, int height,
int srcStride = 0, int dstStride = 0);
tablelength must cover all possible values ofST(uint8_t→ 256 entries,uint16_t→ 65536 entries).
int lut(
const uint8_t* srcImage, uint8_t* dstImage,
const uint8_t* table,
int width, int height,
int cn = 1,
int srcStride = 0, int dstStride = 0);The NEON version additionally supports multi-channel (applies the same 256-entry table to all channels).
uint8_t srcImage[1920*1080*3], dstImage[1920*1080*3];
// Gamma 2.2 LUT
uint8_t gamma_lut[256];
for (int i = 0; i < 256; ++i)
gamma_lut[i] = (uint8_t)(std::pow(i / 255.0, 1.0 / 2.2) * 255.0);
// 3-channel gamma correction (NEON)
acl::neon::arithmetic::lut(srcImage, dstImage, gamma_lut, 1920, 1080, 3);Scalar multiplication + offset + absolute value + convert to u8: dst = saturate_cast<u8>(|alpha*src + beta|).
Tier: Starter+
Channels: 1ch / 3ch / 4ch
Inplace: supported (requires ST == uint8_t)
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
ST |
uint8_t, int16_t, uint16_t, float |
output fixed to uint8_t
|
template<class ST>
int convertScaleAbs(
const ST* srcImage, uint8_t* dstImage,
int width, int height, int cn,
int srcStride, int dstStride,
double alpha, double beta);Typical pairing: visualize a
int16_tgradient from Sobel / Scharr by callingconvertScaleAbs<int16_t>.
Range check: if each channel simultaneously satisfies low[c] ≤ src[c] ≤ high[c], output 255, otherwise 0. Commonly used for HSV color segmentation.
Tier: Starter+
Channels: input 1ch / 3ch / 4ch (per-channel evaluation), output 1ch binary mask
Inplace: not supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
T |
uint8_t, uint16_t, float |
— |
template<class T>
int inRange(
const T* srcImage, uint8_t* dstImage,
int width, int height, int cn,
int srcStride, int dstStride,
const T* low, const T* high);| Parameter | Type | Meaning |
|---|---|---|
srcImage |
const T* |
Input image (multi-channel, interleaved) |
dstImage |
uint8_t* |
Output 1ch binary mask |
low, high
|
const T* |
Upper/lower-bound arrays of length cn
|
uint8_t hsv[1920*1080*3], mask[1920*1080];
// Extract red: H∈[0,10] S∈[100,255] V∈[100,255]
uint8_t low[3] = {0, 100, 100};
uint8_t high[3] = {10, 255, 255};
acl::neon::arithmetic::inRange(hsv, mask, 1920, 1080, 3, 0, 0, low, high);Normalization — linearly map pixel values to the target range.
Tier: Starter+
Channels: 1ch
Inplace: supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
T |
uint8_t, uint16_t, float |
— |
NormType: NORM_MINMAX (maps to [alpha, beta]) |
template<class T>
int normalize(
const T* srcImage, T* dstImage,
int width, int height,
int srcStride, int dstStride,
acl::NormType nt = acl::NormType::NORM_MINMAX,
double alpha = 0.0, double beta = 255.0);| Parameter | Type | Meaning | Default |
|---|---|---|---|
srcImage, dstImage
|
const T* / T*
|
input / output | non-null |
width, height
|
int |
Image size | > 0 |
srcStride, dstStride
|
int |
Bytes per row | required (0 = auto) |
nt |
acl::NormType |
Normalization mode | NORM_MINMAX |
alpha |
double |
Target lower bound | 0.0 |
beta |
double |
Target upper bound (for NORM_MINMAX only) |
255.0 |
2×2 pixel-block linear transform: the caller provides a 2×2 coefficient matrix [[v00, v01], [v10, v11]], applied to each 2×2 pixel block; commonly used for Bayer color correction, etc.
Tier: Business
Channels: 1ch (input is interpreted in a 2×2 block structure)
Inplace: not supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
T |
uint8_t, uint16_t, float |
— |
DT |
uint8_t, uint16_t, float |
— |
template<class T, class DT>
int linearTransform2x2(
const T* srcImage, T* dstImage,
int width, int height,
int srcStride, int dstStride,
int minValue, int maxValue,
const DT& v00, const DT& v01, const DT& v10, const DT& v11);| Parameter | Type | Meaning |
|---|---|---|
minValue, maxValue
|
int |
Output clamp upper/lower bounds |
v00, v01, v10, v11
|
DT |
2×2 matrix coefficients |
Compute phase angle and magnitude from Sobel / Scharr gradients (dx, dy).
Tier: Pro+
Channels: 1ch
Inplace: not supported
Types:
| Template parameter | Allowed types | Constraint |
|---|---|---|
GT (CPP) |
{int16_t, int32_t} (template also accepts float) |
— |
T (NEON) |
int16_t |
NEON-only |
// Phase angle (radians or degrees)
template<class GT>
int phase(
const GT* dx, const GT* dy, float* angle,
int width, int height,
int dxStride, int dyStride, int angleStride,
bool angleInDegrees = true);
// Magnitude (L2 norm)
template<class GT>
int magnitude(
const GT* dx, const GT* dy, float* mag,
int width, int height,
int dxStride, int dyStride, int magStride);
GT∈{short, int, float}. Output is fixed tofloat.
int magnitude(
const short* dx, const short* dy, float* mag,
int width, int height,
int dxStride, int dyStride, int magStride);
int phase(
const short* dx, const short* dy, float* angle,
int width, int height,
int dxStride, int dyStride, int angleStride,
bool angleInDegrees = true);Typical pairing:
sobel3x3<short>outputs ashortgradient that feeds directly into NEONmagnitude / phase.
uint8_t srcImage[1920*1080];
short dx[1920*1080], dy[1920*1080];
float mag[1920*1080], angle[1920*1080];
// Sobel → gradient magnitude + phase
acl::neon::filter::sobel3x3<uint8_t, short>(srcImage, dx, dy, 1920, 1080);
acl::neon::arithmetic::magnitude(dx, dy, mag, 1920, 1080, 0, 0, 0);
acl::neon::arithmetic::phase(dx, dy, angle, 1920, 1080, 0, 0, 0, /*degrees=*/true);