예제 #1
0
파일: CMP_glare.c 프로젝트: jinjoh/NOOR
static void streaks(NodeGlare* ndg, CompBuf* dst, CompBuf* src)
{
	CompBuf *bsrc, *tsrc, *tdst, *sbuf;
	int x, y, n;
	unsigned int nump=0;
	fRGB c1, c2, c3, c4;
	float a, ang = 360.f/(float)ndg->angle;

	bsrc = BTP(src, ndg->threshold, 1 << ndg->quality);
	tsrc = dupalloc_compbuf(bsrc); // sample from buffer
	tdst = alloc_compbuf(tsrc->x, tsrc->y, tsrc->type, 1); // sample to buffer
	sbuf = alloc_compbuf(tsrc->x, tsrc->y, tsrc->type, 1);  // streak sum buffer

	
	for (a=0.f; a<360.f; a+=ang) {
		const float an = (a + (float)ndg->angle_ofs)*(float)M_PI/180.f;
		const float vx = cos((double)an), vy = sin((double)an);
		for (n=0; n<ndg->iter; ++n) {
			const float p4 = pow(4.0, (double)n);
			const float vxp = vx*p4, vyp = vy*p4;
			const float wt = pow((double)ndg->fade, (double)p4);
			const float cmo = 1.f - pow((double)ndg->colmod, (double)n+1);	// colormodulation amount relative to current pass
			float* tdstcol = tdst->rect;
			for (y=0; y<tsrc->y; ++y) {
				for (x=0; x<tsrc->x; ++x, tdstcol+=4) {
					// first pass no offset, always same for every pass, exact copy,
					// otherwise results in uneven brightness, only need once
					if (n==0) qd_getPixel(tsrc, x, y, c1); else c1[0]=c1[1]=c1[2]=0;
					qd_getPixelLerp(tsrc, x + vxp,     y + vyp,     c2);
					qd_getPixelLerp(tsrc, x + vxp*2.f, y + vyp*2.f, c3);
					qd_getPixelLerp(tsrc, x + vxp*3.f, y + vyp*3.f, c4);
					// modulate color to look vaguely similar to a color spectrum
					fRGB_rgbmult(c2, 1.f, cmo, cmo);
					fRGB_rgbmult(c3, cmo, cmo, 1.f);
					fRGB_rgbmult(c4, cmo, 1.f, cmo);
					tdstcol[0] = 0.5f*(tdstcol[0] + c1[0] + wt*(c2[0] + wt*(c3[0] + wt*c4[0])));
					tdstcol[1] = 0.5f*(tdstcol[1] + c1[1] + wt*(c2[1] + wt*(c3[1] + wt*c4[1])));
					tdstcol[2] = 0.5f*(tdstcol[2] + c1[2] + wt*(c2[2] + wt*(c3[2] + wt*c4[2])));
				}
			}
			memcpy(tsrc->rect, tdst->rect, sizeof(float)*tdst->x*tdst->y*tdst->type);
		}

		addImage(sbuf, tsrc, 1.f/(float)(6 - ndg->iter));
		memset(tdst->rect, 0, tdst->x*tdst->y*tdst->type*sizeof(float));
		memcpy(tsrc->rect, bsrc->rect, bsrc->x*bsrc->y*bsrc->type*sizeof(float));
		nump++;
	}

	mixImages(dst, sbuf, 0.5f + 0.5f*ndg->mix);

	free_compbuf(tsrc);
	free_compbuf(tdst);
	free_compbuf(sbuf);
	free_compbuf(bsrc);
}
static void fill_bins(bNode *node, CompBuf* in, int* bins)
{
	float value[4];
	int ivalue=0;
	int x, y;

	/*fill bins */
	for (y=0; y<in->y; y++) {
		for (x=0; x<in->x; x++) {

			/* get the pixel */
			qd_getPixel(in, x, y, value);

			if (value[3] > 0.0f) { /* don't count transparent pixels */
				switch (node->custom1) {
					case 1: { /* all colors */
						value[0] = rgb_to_bw(value);
						value[0]=value[0]*255; /* scale to 0-255 range */
						ivalue=(int)value[0];
						break;
					}
					case 2: { /* red channel */
						value[0]=value[0]*255; /* scale to 0-255 range */
						ivalue=(int)value[0];
						break;
					}
					case 3:  { /* green channel */
						value[1]=value[1]*255; /* scale to 0-255 range */
						ivalue=(int)value[1];
						break;
					}
					case 4: /*blue channel */
					{
						value[2]=value[2]*255; /* scale to 0-255 range */
						ivalue=(int)value[2];
						break;
					}
					case 5: /* luminence */
					{
						rgb_to_yuv(value[0], value[1], value[2], &value[0], &value[1], &value[2]);
						value[0]=value[0]*255; /* scale to 0-255 range */
						ivalue=(int)value[0];
						break;
					}
				} /*end switch */

				/*clip*/
				if (ivalue<0) ivalue=0;
				if (ivalue>255) ivalue=255;

				/*put in the correct bin*/
				bins[ivalue]+=1;
			} /*end if alpha */
		}
	}
}
예제 #3
0
static float brightness_standard_deviation(bNode* node, CompBuf* in, float mean)
{
	float sum=0.0;
	int numPixels=0.0;
	int x,y;
	float value[4];

	for(x=0; x< in->x; x++) {
		for(y=0; y < in->y; y++) {
			
			/* get the pixel */
			qd_getPixel(in, x, y, value);

			if(value[3] > 0.0) { /* don't count transparent pixels */
				numPixels++;
				switch(node->custom1)
				{
				case 1:
					{
						rgb_tobw(value[0],value[1],value[2], &value[0]);
						sum+=(value[0]-mean)*(value[0]-mean);
						break;
					}
				case 2:
					{
						sum+=value[0];
						sum+=(value[0]-mean)*(value[0]-mean);
						break;
					}
				case 3:
					{
						sum+=value[1];
						sum+=(value[1]-mean)*(value[1]-mean);
						break;
					}
				case 4:
					{
						sum+=value[2];
						sum+=(value[2]-mean)*(value[2]-mean);
						break;
					}
				case 5:
					{
						rgb_to_yuv(value[0],value[1],value[2], &value[0], &value[1], &value[2]);
						sum+=(value[0]-mean)*(value[0]-mean);
						break;
					}
				}
			}
		}
	}


	return sqrt(sum/(float)(numPixels-1));
}
static float brightness_mean(bNode *node, CompBuf* in)
{
	float sum=0.0;
	int numPixels=0.0;
	int x, y;
	float value[4];

	for (x=0; x< in->x; x++) {
		for (y=0; y < in->y; y++) {
			
			/* get the pixel */
			qd_getPixel(in, x, y, value);

			if (value[3] > 0.0f) { /* don't count transparent pixels */
				numPixels++;
				switch (node->custom1) {
				case 1:
					{
						value[0] = rgb_to_bw(value);
						sum+=value[0];
						break;
					}
				case 2:
					{
						sum+=value[0];
						break;
					}
				case 3:
					{
						sum+=value[1];
						break;
					}
				case 4:
					{
						sum+=value[2];
						break;
					}
				case 5:
					{
						rgb_to_yuv(value[0], value[1], value[2], &value[0], &value[1], &value[2]);
						sum+=value[0];
						break;
					}
				}
			}
		}
	}

	return sum/numPixels;
}
예제 #5
0
파일: CMP_glare.c 프로젝트: jinjoh/NOOR
static void star4(NodeGlare* ndg, CompBuf* dst, CompBuf* src)
{
	int x, y, i, xm, xp, ym, yp;
	float c[4] = {0,0,0,0}, tc[4] = {0,0,0,0};
	CompBuf *tbuf1, *tbuf2, *tsrc;
	const float f1 = 1.f - ndg->fade, f2 = (1.f - f1)*0.5f;
	//const float t3 = ndg->threshold*3.f;
	const float sc = (float)(1 << ndg->quality);
	const float isc = 1.f/sc;

	tsrc = BTP(src, ndg->threshold, (int)sc);

	tbuf1 = dupalloc_compbuf(tsrc);
	tbuf2 = dupalloc_compbuf(tsrc);

	for (i=0; i<ndg->iter; i++) {
		// (x || x-1, y-1) to (x || x+1, y+1)
		// F
		for (y=0; y<tbuf1->y; y++) {
			ym = y - i;
			yp = y + i;
			for (x=0; x<tbuf1->x; x++) {
				xm = x - i;
				xp = x + i;
				qd_getPixel(tbuf1, x, y, c);
				fRGB_mult(c, f1);
				qd_getPixel(tbuf1, (ndg->angle ? xm : x), ym, tc);
				fRGB_madd(c, tc, f2);
				qd_getPixel(tbuf1, (ndg->angle ? xp : x), yp, tc);
				fRGB_madd(c, tc, f2);
				qd_setPixel(tbuf1, x, y, c);
			}
		}
		// B
		for (y=tbuf1->y-1; y>=0; y--) {
			ym = y - i;
			yp = y + i;
			for (x=tbuf1->x-1; x>=0; x--) {
				xm = x - i;
				xp = x + i;
				qd_getPixel(tbuf1, x, y, c);
				fRGB_mult(c, f1);
				qd_getPixel(tbuf1, (ndg->angle ? xm : x), ym, tc);
				fRGB_madd(c, tc, f2);
				qd_getPixel(tbuf1, (ndg->angle ? xp : x), yp, tc);
				fRGB_madd(c, tc, f2);
				qd_setPixel(tbuf1, x, y, c);
			}
		}
		// (x-1, y || y+1) to (x+1, y || y-1)
		// F
		for (y=0; y<tbuf2->y; y++) {
			ym = y - i;
			yp = y + i;
			for (x=0; x<tbuf2->x; x++) {
				xm = x - i;
				xp = x + i;
				qd_getPixel(tbuf2, x, y, c);
				fRGB_mult(c, f1);
				qd_getPixel(tbuf2, xm, (ndg->angle ? yp : y), tc);
				fRGB_madd(c, tc, f2);
				qd_getPixel(tbuf2, xp, (ndg->angle ? ym : y), tc);
				fRGB_madd(c, tc, f2);
				qd_setPixel(tbuf2, x, y, c);
			}
		}
		// B
		for (y=tbuf2->y-1; y>=0; y--) {
			ym = y - i;
			yp = y + i;
			for (x=tbuf2->x-1; x>=0; x--) {
				xm = x - i;
				xp = x + i;
				qd_getPixel(tbuf2, x, y, c);
				fRGB_mult(c, f1);
				qd_getPixel(tbuf2, xm, (ndg->angle ? yp : y), tc);
				fRGB_madd(c, tc, f2);
				qd_getPixel(tbuf2, xp, (ndg->angle ? ym : y), tc);
				fRGB_madd(c, tc, f2);
				qd_setPixel(tbuf2, x, y, c);
			}
		}
	}

	for (y=0; y<tbuf1->y; ++y)
		for (x=0; x<tbuf1->x; ++x) {
			unsigned int p = (x + y*tbuf1->x)*tbuf1->type;
			tbuf1->rect[p] += tbuf2->rect[p];
			tbuf1->rect[p+1] += tbuf2->rect[p+1];
			tbuf1->rect[p+2] += tbuf2->rect[p+2];
		}

	for (y=0; y<dst->y; ++y) {
		const float m = 0.5f + 0.5f*ndg->mix;
		for (x=0; x<dst->x; ++x) {
			unsigned int p = (x + y*dst->x)*dst->type;
			qd_getPixelLerp(tbuf1, x*isc, y*isc, tc);
			dst->rect[p] = src->rect[p] + m*(tc[0] - src->rect[p]);
			dst->rect[p+1] = src->rect[p+1] + m*(tc[1] - src->rect[p+1]);
			dst->rect[p+2] = src->rect[p+2] + m*(tc[2] - src->rect[p+2]);
		}
	}

	free_compbuf(tbuf1);
	free_compbuf(tbuf2);
	free_compbuf(tsrc);
}
예제 #6
0
static void do_displace(CompBuf *stackbuf, CompBuf *cbuf, CompBuf *vecbuf, float *UNUSED(veccol), CompBuf *xbuf,  CompBuf *ybuf, float *xscale, float *yscale)
{
	ImBuf *ibuf;
	int x, y;
	float p_dx, p_dy;	/* main displacement in pixel space */
	float d_dx, d_dy;
	float dxt, dyt;
	float u, v;
	float xs, ys;
	float vec[3], vecdx[3], vecdy[3];
	float col[3];
	
	ibuf= IMB_allocImBuf(cbuf->x, cbuf->y, 32, 0);
	ibuf->rect_float= cbuf->rect;
	
	for(y=0; y < stackbuf->y; y++) {
		for(x=0; x < stackbuf->x; x++) {
			/* calc pixel coordinates */
			qd_getPixel(vecbuf, x-vecbuf->xof, y-vecbuf->yof, vec);
			
			if (xbuf)
				qd_getPixel(xbuf, x-xbuf->xof, y-xbuf->yof, &xs);
			else
				xs = xscale[0];
			
			if (ybuf)
				qd_getPixel(ybuf, x-ybuf->xof, y-ybuf->yof, &ys);
			else
				ys = yscale[0];

			
			p_dx = vec[0] * xs;
			p_dy = vec[1] * ys;
			
			/* if no displacement, then just copy this pixel */
			if (fabsf(p_dx) < DISPLACE_EPSILON && fabsf(p_dy) < DISPLACE_EPSILON) {
				qd_getPixel(cbuf, x-cbuf->xof, y-cbuf->yof, col);
				qd_setPixel(stackbuf, x, y, col);
				continue;
			}
			
			/* displaced pixel in uv coords, for image sampling */
			u = (x - cbuf->xof - p_dx + 0.5f) / (float)stackbuf->x;
			v = (y - cbuf->yof - p_dy + 0.5f) / (float)stackbuf->y;
			
			
			/* calc derivatives */
			qd_getPixel(vecbuf, x-vecbuf->xof+1, y-vecbuf->yof, vecdx);
			qd_getPixel(vecbuf, x-vecbuf->xof, y-vecbuf->yof+1, vecdy);
			d_dx = vecdx[0] * xs;
			d_dy = vecdy[0] * ys;

			/* clamp derivatives to minimum displacement distance in UV space */
			dxt = p_dx - d_dx;
			dyt = p_dy - d_dy;

			dxt = signf(dxt)*maxf(fabsf(dxt), DISPLACE_EPSILON)/(float)stackbuf->x;
			dyt = signf(dyt)*maxf(fabsf(dyt), DISPLACE_EPSILON)/(float)stackbuf->y;
			
			ibuf_sample(ibuf, u, v, dxt, dyt, col);
			qd_setPixel(stackbuf, x, y, col);
		}
	}
	IMB_freeImBuf(ibuf);
	
	
/* simple method for reference, linear interpolation */
/*	
	int x, y;
	float dx, dy;
	float u, v;
	float vec[3];
	float col[3];
	
	for(y=0; y < stackbuf->y; y++) {
		for(x=0; x < stackbuf->x; x++) {
			qd_getPixel(vecbuf, x, y, vec);
			
			dx = vec[0] * (xscale[0]);
			dy = vec[1] * (yscale[0]);
			
			u = (x - dx + 0.5f) / (float)stackbuf->x;
			v = (y - dy + 0.5f) / (float)stackbuf->y;
			
			qd_getPixelLerp(cbuf, u*cbuf->x - 0.5f, v*cbuf->y - 0.5f, col);
			qd_setPixel(stackbuf, x, y, col);
		}
	}
*/
}