1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69
|
/**
* @brief Add src2 on src1 using src2 alpha channel (transparency).
*
* @code
* foreach(c=channels)
* dst[I,c] = src1[I,c]*(1-(src2[I,alpha]/255)) + src2[I,c]*(src2[I,alpha]/255)
* end
* @endcode
*
* @param src1 The first source array (background image, 3 or 4 channels)
* @param src2 The second source array (transparent image, 4 channels minimum)
* @param dst The destination array (merge image, 3 or 4 channels).
* @note This function only works with IPL_DEPTH_8U image for the moment.
*/
void x7sAddAlphaLayer_3C4C8U(const IplImage *src1, const IplImage *src2, IplImage *dst)
{
uint8_t *p_im1, *p_im2,*end,*p_dst;
int nChan_im1, nChan_dst, c;
float tmp, ratio;
//Set the pointers.
p_im1 = (uint8_t*)src1->imageData;
p_im2 = (uint8_t*)src2->imageData;
p_dst = (uint8_t*)dst->imageData;
end = p_im2 + src2->imageSize; //4 Channels (Include Alpha)
nChan_im1 = src1->nChannels;
nChan_dst = dst->nChannels;
//loop by 2 pixels
while(p_im2<end)
{
//Compute the ratio for this pixel.
ratio=(float)(p_im2[3]/255.f);
//Chan 0
c=0;
tmp=((float)(p_im1[c]))*(1-ratio) + ((float)(p_im2[c]))*(ratio);
p_dst[c]=(uint8_t)(tmp+0.5f);
//Chan 1
c=1;
tmp=((float)(p_im1[c]))*(1-ratio) + ((float)(p_im2[c]))*(ratio);
p_dst[c]=(uint8_t)(tmp+0.5f);
//Chan 2
c=2;
tmp=((float)(p_im1[c]))*(1-ratio) + ((float)(p_im2[c]))*(ratio);
p_dst[c]=(uint8_t)(tmp+0.5f);
//Chan Alpha
if(nChan_dst==4)
{
if(nChan_im1!=4) p_dst[3]=255;
else p_dst[3]=p_im1[3];
}
//Jump to next pixel
p_im1+=nChan_im1;
p_im2+=4;
p_dst+=nChan_dst;
}
} |
Partager