#include #include #ifdef __GNUC__ #warning GTK_DISABLE_DEPRECATED #endif #undef GTK_DISABLE_DEPRECATED #include #include #include "fp.h" extern FP_Params Current; extern GimpDrawable *drawable, *mask; extern ReducedImage *reduced; extern gint nudgeArray[256]; gint colorSign[3][ALL_PRIMARY]= {{1,-1,-1,-1,1,1},{-1,1,-1,1,1,-1},{-1,-1,1,1,-1,1}}; void initializeFilterPacks() { gint i, j; for (i=0; i<256; i++) for (j=BY_HUE; jbpp; ReducedImage *temp=(ReducedImage *)malloc(sizeof(ReducedImage)); guchar *tempRGB, *src_row, *tempmask, *src_mask_row,R,G,B; gint i, j, whichcol, whichrow, x1, x2, y1, y2; GimpPixelRgn srcPR, srcMask; gint NoSelectionMade=TRUE; hsv *tempHSV, H, S, V; gimp_drawable_mask_bounds (drawable->drawable_id, &x1, &y1, &x2, &y2); width = x2-x1; height = y2-y1; if (width != drawable->width && height != drawable->height) NoSelectionMade=FALSE; if (Slctn==0) { x1=0; x2=drawable->width; y1=0; y2=drawable->height; } if (Slctn==2) { x1=MAX(0, x1-width/2.0); x2=MIN(drawable->width, x2+width/2.0); y1=MAX(0, y1-height/2.0); y2=MIN(drawable->height, y2+height/2.0); } width = x2-x1; height = y2-y1; if (width>height) { RW=LongerSize; RH=(float) height * (float) LongerSize/ (float) width; } else { RH=LongerSize; RW=(float)width * (float) LongerSize/ (float) height; } tempRGB = (guchar *) malloc(RW*RH*bytes); tempHSV = (hsv *) malloc(RW*RH*bytes*sizeof(hsv)); tempmask = (guchar *) malloc(RW*RH); gimp_pixel_rgn_init (&srcPR, drawable, x1, y1, width, height, FALSE, FALSE); gimp_pixel_rgn_init (&srcMask, mask, x1, y1, width, height, FALSE, FALSE); src_row = (guchar *) malloc (width*bytes); src_mask_row = (guchar *) malloc (width*bytes); for (i=0; iwidth=RW; temp->height=RH; temp->rgb=tempRGB; temp->hsv=tempHSV; temp->mask=tempmask; return temp; } /*************************************************************/ /************** The Preview Function *************************/ void fp_render_preview(GtkWidget *preview, gint changewhat, gint changewhich) { guchar *a; gint Inten, bytes=drawable->bpp; gint i, j, k, nudge, M, m, middle,JudgeBy; float partial; gint RW=reduced->width; gint RH=reduced->height; gint backupP[3], P[3], tempSat[JUDGE_BY][256]; a =(guchar *) malloc(bytes*RW); if (changewhat==SATURATION) for (k=0; k<256; k++) { for (JudgeBy=BY_HUE; JudgeByrgb[i*RW*bytes + j*bytes + 0]; backupP[1] = P[1] = (int) reduced->rgb[i*RW*bytes + j*bytes + 1]; backupP[2] = P[2] = (int) reduced->rgb[i*RW*bytes + j*bytes + 2]; m = MIN(MIN(P[0],P[1]),P[2]); M = MAX(MAX(P[0],P[1]),P[2]); middle=(M+m)/2; for (k=0; k<3; k++) if (P[k]!=m && P[k]!=M) middle=P[k]; partial = reduced->mask[i*RW+j]/255.0; for (JudgeBy=BY_HUE; JudgeByhsv[i*RW*bytes + j*bytes + JudgeBy]*255.0; /*DO SATURATION FIRST*/ if (changewhat != NONEATALL) { if (M!=m) { for (k=0; k<3; k++) if (backupP[k] == M) P[k] = MAX(P[k]+partial*Current.satAdj[JudgeBy][Inten],middle); else if (backupP[k] == m) P[k] = MIN(P[k]-partial*Current.satAdj[JudgeBy][Inten],middle); } P[0] += partial*Current.redAdj[JudgeBy][Inten]; P[1] += partial*Current.greenAdj[JudgeBy][Inten]; P[2] += partial*Current.blueAdj[JudgeBy][Inten]; } } Inten = reduced->hsv[i*RW*bytes + j*bytes + Current.ValueBy]*255.0; nudge = partial*nudgeArray[(Inten+Current.Offset)%256]; switch (changewhat) { case HUE: P[0] += colorSign[RED][changewhich] * nudge; P[1] += colorSign[GREEN][changewhich] * nudge; P[2] += colorSign[BLUE][changewhich] * nudge; break; case SATURATION: for (JudgeBy=BY_HUE; JudgeByrgb[i*RW*bytes+j*bytes+3]/255.0; a[3*j+k]=transp*a[3*j+k]+(1-transp)*fp_fake_transparency(i,j); } } gtk_preview_draw_row( GTK_PREVIEW(preview),a,0,i,RW); } free(a); gtk_widget_queue_draw (preview); } void Update_Current_FP (gint changewhat, gint changewhich) { int i, nudge; for (i=0; i<256; i++) { fp_Create_Nudge(nudgeArray); nudge=nudgeArray[(i+Current.Offset)%256]; switch (changewhat) { case HUE: Current.redAdj[Current.ValueBy][i] += colorSign[RED][changewhich] * nudge; Current.greenAdj[Current.ValueBy][i] += colorSign[GREEN][changewhich] * nudge; Current.blueAdj[Current.ValueBy][i] += colorSign[BLUE][changewhich] * nudge; break; case SATURATION: Current.satAdj[Current.ValueBy][i] += changewhich*nudge; break; case VALUE: Current.redAdj[Current.ValueBy][i] += changewhich * nudge; Current.greenAdj[Current.ValueBy][i] += changewhich * nudge; Current.blueAdj[Current.ValueBy][i] += changewhich * nudge; break; default: break; } /* switch */ } /* for */ } void fp_create_smoothness_graph (GtkWidget *preview) { guchar data[256*3]; gint nArray[256]; int i, j, toBeBlack; fp_Create_Nudge(nArray); for (i=0; i0 ) return 64; else return 196; }