Exemplo n.º 1
0
static void hue_correct_apply_threaded(int width, int height, unsigned char *rect, float *rect_float,
                                unsigned char *mask_rect, float *mask_rect_float, void *data_v)
{
	CurveMapping *curve_mapping = (CurveMapping *) data_v;
	int x, y;

	for (y = 0; y < height; y++) {
		for (x = 0; x < width; x++) {
			int pixel_index = (y * width + x) * 4;
			float pixel[3], result[3], mask[3] = {1.0f, 1.0f, 1.0f};
			float hsv[3], f;

			if (rect_float)
				copy_v3_v3(pixel, rect_float + pixel_index);
			else
				rgb_uchar_to_float(pixel, rect + pixel_index);

			rgb_to_hsv(pixel[0], pixel[1], pixel[2], hsv, hsv + 1, hsv + 2);

			/* adjust hue, scaling returned default 0.5 up to 1 */
			f = curvemapping_evaluateF(curve_mapping, 0, hsv[0]);
			hsv[0] += f - 0.5f;

			/* adjust saturation, scaling returned default 0.5 up to 1 */
			f = curvemapping_evaluateF(curve_mapping, 1, hsv[0]);
			hsv[1] *= (f * 2.0f);

			/* adjust value, scaling returned default 0.5 up to 1 */
			f = curvemapping_evaluateF(curve_mapping, 2, hsv[0]);
			hsv[2] *= (f * 2.f);

			hsv[0] = hsv[0] - floorf(hsv[0]); /* mod 1.0 */
			CLAMP(hsv[1], 0.0f, 1.0f);

			/* convert back to rgb */
			hsv_to_rgb(hsv[0], hsv[1], hsv[2], result, result + 1, result + 2);

			if (mask_rect_float)
				copy_v3_v3(mask, mask_rect_float + pixel_index);
			else if (mask_rect)
				rgb_uchar_to_float(mask, mask_rect + pixel_index);

			result[0] = pixel[0] * (1.0f - mask[0]) + result[0] * mask[0];
			result[1] = pixel[1] * (1.0f - mask[1]) + result[1] * mask[1];
			result[2] = pixel[2] * (1.0f - mask[2]) + result[2] * mask[2];

			if (rect_float)
				copy_v3_v3(rect_float + pixel_index, result);
			else
				rgb_float_to_uchar(rect + pixel_index, result);
		}
	}
}
Exemplo n.º 2
0
/* Returns color in the display space, matching ED_space_image_color_sample().
 * And here we've got recursion in the comments tips...
 */
bool ED_space_node_color_sample(Scene *scene, SpaceNode *snode, ARegion *ar, int mval[2], float r_col[3])
{
	const char *display_device = scene->display_settings.display_device;
	struct ColorManagedDisplay *display = IMB_colormanagement_display_get_named(display_device);
	void *lock;
	Image *ima;
	ImBuf *ibuf;
	float fx, fy, bufx, bufy;
	bool ret = false;

	if (STREQ(snode->tree_idname, ntreeType_Composite->idname) || (snode->flag & SNODE_BACKDRAW) == 0) {
		/* use viewer image for color sampling only if we're in compositor tree
		 * with backdrop enabled
		 */
		return false;
	}

	ima = BKE_image_verify_viewer(IMA_TYPE_COMPOSITE, "Viewer Node");
	ibuf = BKE_image_acquire_ibuf(ima, NULL, &lock);
	if (!ibuf) {
		return false;
	}

	/* map the mouse coords to the backdrop image space */
	bufx = ibuf->x * snode->zoom;
	bufy = ibuf->y * snode->zoom;
	fx = (bufx > 0.0f ? ((float)mval[0] - 0.5f * ar->winx - snode->xof) / bufx + 0.5f : 0.0f);
	fy = (bufy > 0.0f ? ((float)mval[1] - 0.5f * ar->winy - snode->yof) / bufy + 0.5f : 0.0f);

	if (fx >= 0.0f && fy >= 0.0f && fx < 1.0f && fy < 1.0f) {
		const float *fp;
		unsigned char *cp;
		int x = (int)(fx * ibuf->x), y = (int)(fy * ibuf->y);

		CLAMP(x, 0, ibuf->x - 1);
		CLAMP(y, 0, ibuf->y - 1);

		if (ibuf->rect_float) {
			fp = (ibuf->rect_float + (ibuf->channels) * (y * ibuf->x + x));
			/* IB_PROFILE_NONE is default but infact its linear */
			copy_v3_v3(r_col, fp);
			ret = true;
		}
		else if (ibuf->rect) {
			cp = (unsigned char *)(ibuf->rect + y * ibuf->x + x);
			rgb_uchar_to_float(r_col, cp);
			IMB_colormanagement_colorspace_to_scene_linear_v3(r_col, ibuf->rect_colorspace);
			ret = true;
		}
	}

	if (ret) {
		IMB_colormanagement_scene_linear_to_display_v3(r_col, display);
	}

	BKE_image_release_ibuf(ima, ibuf, lock);

	return ret;
}
Exemplo n.º 3
0
static void tonemapmodifier_apply_threaded_simple(int width,
                                                  int height,
                                                  unsigned char *rect,
                                                  float *rect_float,
                                                  unsigned char *mask_rect,
                                                  float *mask_rect_float,
                                                  void *data_v)
{
	AvgLogLum *avg = (AvgLogLum *)data_v;
	for (int y = 0; y < height; y++) {
		for (int x = 0; x < width; x++) {
			int pixel_index = (y * width + x) * 4;
			float input[4], output[4], mask[3] = {1.0f, 1.0f, 1.0f};
			/* Get input value. */
			if (rect_float) {
				copy_v4_v4(input, &rect_float[pixel_index]);
			}
			else {
				straight_uchar_to_premul_float(input, &rect[pixel_index]);
			}
			IMB_colormanagement_colorspace_to_scene_linear_v3(input, avg->colorspace);
			copy_v4_v4(output, input);
			/* Get mask value. */
			if (mask_rect_float) {
				copy_v3_v3(mask, mask_rect_float + pixel_index);
			}
			else if (mask_rect) {
				rgb_uchar_to_float(mask, mask_rect + pixel_index);
			}
			/* Apply correction. */
			mul_v3_fl(output, avg->al);
			float dr = output[0] + avg->tmmd->offset;
			float dg = output[1] + avg->tmmd->offset;
			float db = output[2] + avg->tmmd->offset;
			output[0] /= ((dr == 0.0f) ? 1.0f : dr);
			output[1] /= ((dg == 0.0f) ? 1.0f : dg);
			output[2] /= ((db == 0.0f) ? 1.0f : db);
			const float igm = avg->igm;
			if (igm != 0.0f) {
				output[0] = powf(max_ff(output[0], 0.0f), igm);
				output[1] = powf(max_ff(output[1], 0.0f), igm);
				output[2] = powf(max_ff(output[2], 0.0f), igm);
			}
			/* Apply mask. */
			output[0] = input[0] * (1.0f - mask[0]) + output[0] * mask[0];
			output[1] = input[1] * (1.0f - mask[1]) + output[1] * mask[1];
			output[2] = input[2] * (1.0f - mask[2]) + output[2] * mask[2];
			/* Copy result back. */
			IMB_colormanagement_scene_linear_to_colorspace_v3(output, avg->colorspace);
			if (rect_float) {
				copy_v4_v4(&rect_float[pixel_index], output);
			}
			else {
				premul_float_to_straight_uchar(&rect[pixel_index], output);
			}
		}
	}
}
Exemplo n.º 4
0
static void curves_apply_threaded(int width, int height, unsigned char *rect, float *rect_float,
                                  unsigned char *mask_rect, float *mask_rect_float, void *data_v)
{
	CurveMapping *curve_mapping = (CurveMapping *) data_v;
	int x, y;

	for (y = 0; y < height; y++) {
		for (x = 0; x < width; x++) {
			int pixel_index = (y * width + x) * 4;

			if (rect_float) {
				float *pixel = rect_float + pixel_index;
				float result[3];

				curvemapping_evaluate_premulRGBF(curve_mapping, result, pixel);

				if (mask_rect_float) {
					const float *m = mask_rect_float + pixel_index;

					pixel[0] = pixel[0] * (1.0f - m[0]) + result[0] * m[0];
					pixel[1] = pixel[1] * (1.0f - m[1]) + result[1] * m[1];
					pixel[2] = pixel[2] * (1.0f - m[2]) + result[2] * m[2];
				}
				else {
					pixel[0] = result[0];
					pixel[1] = result[1];
					pixel[2] = result[2];
				}
			}
			if (rect) {
				unsigned char *pixel = rect + pixel_index;
				float result[3], tempc[4];

				straight_uchar_to_premul_float(tempc, pixel);

				curvemapping_evaluate_premulRGBF(curve_mapping, result, tempc);

				if (mask_rect) {
					float t[3];

					rgb_uchar_to_float(t, mask_rect + pixel_index);

					tempc[0] = tempc[0] * (1.0f - t[0]) + result[0] * t[0];
					tempc[1] = tempc[1] * (1.0f - t[1]) + result[1] * t[1];
					tempc[2] = tempc[2] * (1.0f - t[2]) + result[2] * t[2];
				}
				else {
					tempc[0] = result[0];
					tempc[1] = result[1];
					tempc[2] = result[2];
				}

				premul_float_to_straight_uchar(pixel, tempc);
			}
		}
	}
}
Exemplo n.º 5
0
/* Byte equivalent of IMB_colormanagement_get_luminance(). */
unsigned char IMB_colormanagement_get_luminance_byte(const unsigned char rgb[3])
{
  float rgbf[3];
  float val;

  rgb_uchar_to_float(rgbf, rgb);
  val = dot_v3v3(imbuf_luma_coefficients, rgbf);

  return unit_float_to_uchar_clamp(val);
}
Exemplo n.º 6
0
static void whiteBalance_apply_threaded(int width, int height, unsigned char *rect, float *rect_float,
                                        unsigned char *mask_rect, float *mask_rect_float, void *data_v)
{
	int x, y;
	float multiplier[3];

	WhiteBalanceThreadData *data = (WhiteBalanceThreadData *) data_v;

	multiplier[0] = (data->white[0] != 0.0f) ? 1.0f / data->white[0] : FLT_MAX;
	multiplier[1] = (data->white[1] != 0.0f) ? 1.0f / data->white[1] : FLT_MAX;
	multiplier[2] = (data->white[2] != 0.0f) ? 1.0f / data->white[2] : FLT_MAX;

	for (y = 0; y < height; y++) {
		for (x = 0; x < width; x++) {
			int pixel_index = (y * width + x) * 4;
			float rgba[4], result[4], mask[3] = {1.0f, 1.0f, 1.0f};

			if (rect_float) {
				copy_v3_v3(rgba, rect_float + pixel_index);
			}
			else {
				straight_uchar_to_premul_float(rgba, rect + pixel_index);
			}

			copy_v4_v4(result, rgba);
#if 0
			mul_v3_v3(result, multiplier);
#else
			/* similar to division without the clipping */
			for (int i = 0; i < 3; i++) {
				result[i] = 1.0f - powf(1.0f - rgba[i], multiplier[i]);
			}
#endif

			if (mask_rect_float) {
				copy_v3_v3(mask, mask_rect_float + pixel_index);
			}
			else if (mask_rect) {
				rgb_uchar_to_float(mask, mask_rect + pixel_index);
			}

			result[0] = rgba[0] * (1.0f - mask[0]) + result[0] * mask[0];
			result[1] = rgba[1] * (1.0f - mask[1]) + result[1] * mask[1];
			result[2] = rgba[2] * (1.0f - mask[2]) + result[2] * mask[2];

			if (rect_float) {
				copy_v3_v3(rect_float + pixel_index, result);
			}
			else {
				premul_float_to_straight_uchar(rect + pixel_index, result);
			}
		}
	}
}
Exemplo n.º 7
0
/* matching ED_space_image_color_sample() */
int ED_space_node_color_sample(SpaceNode *snode, ARegion *ar, int mval[2], float r_col[3])
{
    void *lock;
    Image *ima;
    ImBuf *ibuf;
    float fx, fy, bufx, bufy;
    int ret = FALSE;

    if (STREQ(snode->tree_idname, ntreeType_Composite->idname) || (snode->flag & SNODE_BACKDRAW) == 0) {
        /* use viewer image for color sampling only if we're in compositor tree
         * with backdrop enabled
         */
        return FALSE;
    }

    ima = BKE_image_verify_viewer(IMA_TYPE_COMPOSITE, "Viewer Node");
    ibuf = BKE_image_acquire_ibuf(ima, NULL, &lock);
    if (!ibuf) {
        return FALSE;
    }

    /* map the mouse coords to the backdrop image space */
    bufx = ibuf->x * snode->zoom;
    bufy = ibuf->y * snode->zoom;
    fx = (bufx > 0.0f ? ((float)mval[0] - 0.5f * ar->winx - snode->xof) / bufx + 0.5f : 0.0f);
    fy = (bufy > 0.0f ? ((float)mval[1] - 0.5f * ar->winy - snode->yof) / bufy + 0.5f : 0.0f);

    if (fx >= 0.0f && fy >= 0.0f && fx < 1.0f && fy < 1.0f) {
        float *fp;
        unsigned char *cp;
        int x = (int)(fx * ibuf->x), y = (int)(fy * ibuf->y);

        CLAMP(x, 0, ibuf->x - 1);
        CLAMP(y, 0, ibuf->y - 1);

        if (ibuf->rect_float) {
            fp = (ibuf->rect_float + (ibuf->channels) * (y * ibuf->x + x));
            /* IB_PROFILE_NONE is default but infact its linear */
            linearrgb_to_srgb_v3_v3(r_col, fp);
            ret = TRUE;
        }
        else if (ibuf->rect) {
            cp = (unsigned char *)(ibuf->rect + y * ibuf->x + x);
            rgb_uchar_to_float(r_col, cp);
            ret = TRUE;
        }
    }

    BKE_image_release_ibuf(ima, ibuf, lock);

    return ret;
}
Exemplo n.º 8
0
/* Returns color in the display space, matching ED_space_image_color_sample(). */
bool ED_space_clip_color_sample(Scene *scene, SpaceClip *sc, ARegion *ar, int mval[2], float r_col[3])
{
	const char *display_device = scene->display_settings.display_device;
	struct ColorManagedDisplay *display = IMB_colormanagement_display_get_named(display_device);
	ImBuf *ibuf;
	float fx, fy, co[2];
	bool ret = false;

	ibuf = ED_space_clip_get_buffer(sc);
	if (!ibuf) {
		return false;
	}

	/* map the mouse coords to the backdrop image space */
	ED_clip_mouse_pos(sc, ar, mval, co);

	fx = co[0];
	fy = co[1];

	if (fx >= 0.0f && fy >= 0.0f && fx < 1.0f && fy < 1.0f) {
		const float *fp;
		unsigned char *cp;
		int x = (int)(fx * ibuf->x), y = (int)(fy * ibuf->y);

		CLAMP(x, 0, ibuf->x - 1);
		CLAMP(y, 0, ibuf->y - 1);

		if (ibuf->rect_float) {
			fp = (ibuf->rect_float + (ibuf->channels) * (y * ibuf->x + x));
			copy_v3_v3(r_col, fp);
			ret = true;
		}
		else if (ibuf->rect) {
			cp = (unsigned char *)(ibuf->rect + y * ibuf->x + x);
			rgb_uchar_to_float(r_col, cp);
			IMB_colormanagement_colorspace_to_scene_linear_v3(r_col, ibuf->rect_colorspace);
			ret = true;
		}
	}

	if (ret) {
		IMB_colormanagement_scene_linear_to_display_v3(r_col, display);
	}

	IMB_freeImBuf(ibuf);

	return ret;
}
Exemplo n.º 9
0
static void whiteBalance_apply_threaded(int width, int height, unsigned char *rect, float *rect_float,
                                        unsigned char *mask_rect, float *mask_rect_float, void *data_v)
{
	int x, y;
	float multiplier[3];

	WhiteBalanceThreadData *data = (WhiteBalanceThreadData *) data_v;

	multiplier[0] = 1.0f / data->white[0];
	multiplier[1] = 1.0f / data->white[1];
	multiplier[2] = 1.0f / data->white[2];

	for (y = 0; y < height; y++) {
		for (x = 0; x < width; x++) {
			int pixel_index = (y * width + x) * 4;
			float result[3], mask[3] = {1.0f, 1.0f, 1.0f};

			if (rect_float) {
				copy_v3_v3(result, rect_float + pixel_index);
			}
			else {
				straight_uchar_to_premul_float(result, rect + pixel_index);
				IMB_colormanagement_colorspace_to_scene_linear_v3(result, data->colorspace);
			}

			mul_v3_v3(result, multiplier);

			if (mask_rect_float)
				copy_v3_v3(mask, mask_rect_float + pixel_index);
			else if (mask_rect)
				rgb_uchar_to_float(mask, mask_rect + pixel_index);

			result[0] = result[0] * (1.0f - mask[0]) + result[0] * mask[0];
			result[1] = result[1] * (1.0f - mask[1]) + result[1] * mask[1];
			result[2] = result[2] * (1.0f - mask[2]) + result[2] * mask[2];

			if (rect_float)
				copy_v3_v3(rect_float + pixel_index, result);
			else
				IMB_colormanagement_scene_linear_to_colorspace_v3(result, data->colorspace);
			premul_float_to_straight_uchar(rect + pixel_index, result);
		}
	}
}
Exemplo n.º 10
0
/* matching ED_space_image_color_sample() */
bool ED_space_clip_color_sample(SpaceClip *sc, ARegion *ar, int mval[2], float r_col[3])
{
	ImBuf *ibuf;
	float fx, fy, co[2];
	bool ret = false;

	ibuf = ED_space_clip_get_buffer(sc);
	if (!ibuf) {
		return false;
	}

	/* map the mouse coords to the backdrop image space */
	ED_clip_mouse_pos(sc, ar, mval, co);

	fx = co[0];
	fy = co[1];

	if (fx >= 0.0f && fy >= 0.0f && fx < 1.0f && fy < 1.0f) {
		float *fp;
		unsigned char *cp;
		int x = (int)(fx * ibuf->x), y = (int)(fy * ibuf->y);

		CLAMP(x, 0, ibuf->x - 1);
		CLAMP(y, 0, ibuf->y - 1);

		if (ibuf->rect_float) {
			fp = (ibuf->rect_float + (ibuf->channels) * (y * ibuf->x + x));
			linearrgb_to_srgb_v3_v3(r_col, fp);
			ret = true;
		}
		else if (ibuf->rect) {
			cp = (unsigned char *)(ibuf->rect + y * ibuf->x + x);
			rgb_uchar_to_float(r_col, cp);
			ret = true;
		}
	}

	return ret;
}
Exemplo n.º 11
0
void IMB_saturation(ImBuf *ibuf, float sat)
{
  size_t i;
  unsigned char *rct = (unsigned char *)ibuf->rect;
  float *rct_fl = ibuf->rect_float;
  float hsv[3];

  if (rct) {
    float rgb[3];
    for (i = ((size_t)ibuf->x) * ibuf->y; i > 0; i--, rct += 4) {
      rgb_uchar_to_float(rgb, rct);
      rgb_to_hsv_v(rgb, hsv);
      hsv_to_rgb(hsv[0], hsv[1] * sat, hsv[2], rgb, rgb + 1, rgb + 2);
      rgb_float_to_uchar(rct, rgb);
    }
  }

  if (rct_fl) {
    for (i = ((size_t)ibuf->x) * ibuf->y; i > 0; i--, rct_fl += 4) {
      rgb_to_hsv_v(rct_fl, hsv);
      hsv_to_rgb(hsv[0], hsv[1] * sat, hsv[2], rct_fl, rct_fl + 1, rct_fl + 2);
    }
  }
}
Exemplo n.º 12
0
static void tonemapmodifier_apply_threaded_photoreceptor(int width,
                                                         int height,
                                                         unsigned char *rect,
                                                         float *rect_float,
                                                         unsigned char *mask_rect,
                                                         float *mask_rect_float,
                                                         void *data_v)
{
	AvgLogLum *avg = (AvgLogLum *)data_v;
	const float f = expf(-avg->tmmd->intensity);
	const float m = (avg->tmmd->contrast > 0.0f) ? avg->tmmd->contrast : (0.3f + 0.7f * powf(avg->auto_key, 1.4f));
	const float ic = 1.0f - avg->tmmd->correction, ia = 1.0f - avg->tmmd->adaptation;
	for (int y = 0; y < height; y++) {
		for (int x = 0; x < width; x++) {
			int pixel_index = (y * width + x) * 4;
			float input[4], output[4], mask[3] = {1.0f, 1.0f, 1.0f};
			/* Get input value. */
			if (rect_float) {
				copy_v4_v4(input, &rect_float[pixel_index]);
			}
			else {
				straight_uchar_to_premul_float(input, &rect[pixel_index]);
			}
			IMB_colormanagement_colorspace_to_scene_linear_v3(input, avg->colorspace);
			copy_v4_v4(output, input);
			/* Get mask value. */
			if (mask_rect_float) {
				copy_v3_v3(mask, mask_rect_float + pixel_index);
			}
			else if (mask_rect) {
				rgb_uchar_to_float(mask, mask_rect + pixel_index);
			}
			/* Apply correction. */
			const float L = IMB_colormanagement_get_luminance(output);
			float I_l = output[0] + ic * (L - output[0]);
			float I_g = avg->cav[0] + ic * (avg->lav - avg->cav[0]);
			float I_a = I_l + ia * (I_g - I_l);
			output[0] /= (output[0] + powf(f * I_a, m));
			I_l = output[1] + ic * (L - output[1]);
			I_g = avg->cav[1] + ic * (avg->lav - avg->cav[1]);
			I_a = I_l + ia * (I_g - I_l);
			output[1] /= (output[1] + powf(f * I_a, m));
			I_l = output[2] + ic * (L - output[2]);
			I_g = avg->cav[2] + ic * (avg->lav - avg->cav[2]);
			I_a = I_l + ia * (I_g - I_l);
			output[2] /= (output[2] + powf(f * I_a, m));
			/* Apply mask. */
			output[0] = input[0] * (1.0f - mask[0]) + output[0] * mask[0];
			output[1] = input[1] * (1.0f - mask[1]) + output[1] * mask[1];
			output[2] = input[2] * (1.0f - mask[2]) + output[2] * mask[2];
			/* Copy result back. */
			IMB_colormanagement_scene_linear_to_colorspace_v3(output, avg->colorspace);
			if (rect_float) {
				copy_v4_v4(&rect_float[pixel_index], output);
			}
			else {
				premul_float_to_straight_uchar(&rect[pixel_index], output);
			}
		}
	}
}
static void mloopcol_to_float(const MLoopCol *mloopcol, float r_col[3])
{
	rgb_uchar_to_float(r_col, (const unsigned char *)&mloopcol->r);
}
Exemplo n.º 14
0
/* used for both 3d view and image window */
void paint_sample_color(bContext *C, ARegion *ar, int x, int y, bool texpaint_proj, bool use_palette)
{
	Scene *scene = CTX_data_scene(C);
	Paint *paint = BKE_paint_get_active_from_context(C);
	Palette *palette = BKE_paint_palette(paint);
	PaletteColor *color;
	Brush *br = BKE_paint_brush(BKE_paint_get_active_from_context(C));
	unsigned int col;
	const unsigned char *cp;

	CLAMP(x, 0, ar->winx);
	CLAMP(y, 0, ar->winy);
	
	if (use_palette) {
		if (!palette) {
			palette = BKE_palette_add(CTX_data_main(C), "Palette");
			BKE_paint_palette_set(paint, palette);
		}

		color = BKE_palette_color_add(palette);
	}


	if (CTX_wm_view3d(C) && texpaint_proj) {
		/* first try getting a colour directly from the mesh faces if possible */
		Object *ob = OBACT;
		bool sample_success = false;

		if (ob) {
			DerivedMesh *dm = mesh_get_derived_final(scene, ob, CD_MASK_BAREMESH);

			ViewContext vc;
			const int mval[2] = {x, y};
			unsigned int faceindex;
			unsigned int totface = dm->getNumTessFaces(dm);
			MTFace *dm_mtface = dm->getTessFaceDataArray(dm, CD_MTFACE);

			DM_update_materials(dm, ob);

			if (dm_mtface) {
				view3d_set_viewcontext(C, &vc);

				view3d_operator_needs_opengl(C);

				if (imapaint_pick_face(&vc, mval, &faceindex, totface)) {
					Image *image = imapaint_face_image(dm, faceindex);

					ImBuf *ibuf = BKE_image_acquire_ibuf(image, NULL, NULL);
					if (ibuf && ibuf->rect) {
						float uv[2];
						float u, v;
						imapaint_pick_uv(scene, ob, faceindex, mval, uv);
						sample_success = true;

						u = fmodf(uv[0], 1.0f);
						v = fmodf(uv[1], 1.0f);

						if (u < 0.0f) u += 1.0f;
						if (v < 0.0f) v += 1.0f;

						u = u * ibuf->x - 0.5f;
						v = v * ibuf->y - 0.5f;

						if (ibuf->rect_float) {
							float rgba_f[4];
							bilinear_interpolation_color_wrap(ibuf, NULL, rgba_f, u, v);
							straight_to_premul_v4(rgba_f);
							if (use_palette) {
								linearrgb_to_srgb_v3_v3(color->rgb, rgba_f);
							}
							else {
								linearrgb_to_srgb_v3_v3(rgba_f, rgba_f);
								BKE_brush_color_set(scene, br, rgba_f);
							}
						}
						else {
							unsigned char rgba[4];
							bilinear_interpolation_color_wrap(ibuf, rgba, NULL, u, v);
							if (use_palette) {
								rgb_uchar_to_float(color->rgb, rgba);
							}
							else {
								float rgba_f[3];
								rgb_uchar_to_float(rgba_f, rgba);
								BKE_brush_color_set(scene, br, rgba_f);
							}
						}
					}

					BKE_image_release_ibuf(image, ibuf, NULL);
				}
			}
			dm->release(dm);
		}

		if (!sample_success) {
			glReadBuffer(GL_FRONT);
			glReadPixels(x + ar->winrct.xmin, y + ar->winrct.ymin, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, &col);
			glReadBuffer(GL_BACK);
		}
		else
			return;
	}
	else {
		glReadBuffer(GL_FRONT);
		glReadPixels(x + ar->winrct.xmin, y + ar->winrct.ymin, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, &col);
		glReadBuffer(GL_BACK);
	}
	cp = (unsigned char *)&col;
	
	if (use_palette) {
		rgb_uchar_to_float(color->rgb, cp);
	}
	else {
		float rgba_f[3];
		rgb_uchar_to_float(rgba_f, cp);
		BKE_brush_color_set(scene, br, rgba_f);
	}
}
Exemplo n.º 15
0
/* used by node view too */
void ED_image_draw_info(Scene *scene, ARegion *ar, int color_manage, int use_default_view, int channels, int x, int y,
                        const unsigned char cp[4], const float fp[4], int *zp, float *zpf)
{
	char str[256];
	float dx = 6;
	/* text colors */
	/* XXX colored text not allowed in Blender UI */
	#if 0
	unsigned char red[3] = {255, 50, 50};
	unsigned char green[3] = {0, 255, 0};
	unsigned char blue[3] = {100, 100, 255};
	#else
	unsigned char red[3] = {255, 255, 255};
	unsigned char green[3] = {255, 255, 255};
	unsigned char blue[3] = {255, 255, 255};
	#endif
	float hue = 0, sat = 0, val = 0, lum = 0, u = 0, v = 0;
	float col[4], finalcol[4];

	glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
	glEnable(GL_BLEND);

	/* noisy, high contrast make impossible to read if lower alpha is used. */
	glColor4ub(0, 0, 0, 190);
	glRecti(0.0, 0.0, BLI_rcti_size_x(&ar->winrct) + 1, 20);
	glDisable(GL_BLEND);

	BLF_size(blf_mono_font, 11, 72);

	glColor3ub(255, 255, 255);
	BLI_snprintf(str, sizeof(str), "X:%-4d  Y:%-4d |", x, y);
	// UI_DrawString(6, 6, str); // works ok but fixed width is nicer.
	BLF_position(blf_mono_font, dx, 6, 0);
	BLF_draw_ascii(blf_mono_font, str, sizeof(str));
	dx += BLF_width(blf_mono_font, str);

	if (zp) {
		glColor3ub(255, 255, 255);
		BLI_snprintf(str, sizeof(str), " Z:%-.4f |", 0.5f + 0.5f * (((float)*zp) / (float)0x7fffffff));
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);
	}
	if (zpf) {
		glColor3ub(255, 255, 255);
		BLI_snprintf(str, sizeof(str), " Z:%-.3f |", *zpf);
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);
	}

	if (channels >= 3) {
		glColor3ubv(red);
		if (fp)
			BLI_snprintf(str, sizeof(str), "  R:%-.5f", fp[0]);
		else if (cp)
			BLI_snprintf(str, sizeof(str), "  R:%-3d", cp[0]);
		else
			BLI_snprintf(str, sizeof(str), "  R:-");
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);
		
		glColor3ubv(green);
		if (fp)
			BLI_snprintf(str, sizeof(str), "  G:%-.5f", fp[1]);
		else if (cp)
			BLI_snprintf(str, sizeof(str), "  G:%-3d", cp[1]);
		else
			BLI_snprintf(str, sizeof(str), "  G:-");
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);
		
		glColor3ubv(blue);
		if (fp)
			BLI_snprintf(str, sizeof(str), "  B:%-.5f", fp[2]);
		else if (cp)
			BLI_snprintf(str, sizeof(str), "  B:%-3d", cp[2]);
		else
			BLI_snprintf(str, sizeof(str), "  B:-");
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);
		
		if (channels == 4) {
			glColor3ub(255, 255, 255);
			if (fp)
				BLI_snprintf(str, sizeof(str), "  A:%-.4f", fp[3]);
			else if (cp)
				BLI_snprintf(str, sizeof(str), "  A:%-3d", cp[3]);
			else
				BLI_snprintf(str, sizeof(str), "- ");
			BLF_position(blf_mono_font, dx, 6, 0);
			BLF_draw_ascii(blf_mono_font, str, sizeof(str));
			dx += BLF_width(blf_mono_font, str);
		}

		if (color_manage && channels == 4) {
			float pixel[4];

			if (use_default_view)
				IMB_colormanagement_pixel_to_display_space_v4(pixel, fp,  NULL, &scene->display_settings);
			else
				IMB_colormanagement_pixel_to_display_space_v4(pixel, fp,  &scene->view_settings, &scene->display_settings);

			BLI_snprintf(str, sizeof(str), "  |  CM  R:%-.4f  G:%-.4f  B:%-.4f", pixel[0], pixel[1], pixel[2]);
			BLF_position(blf_mono_font, dx, 6, 0);
			BLF_draw_ascii(blf_mono_font, str, sizeof(str));
			dx += BLF_width(blf_mono_font, str);
		}
	}
	
	/* color rectangle */
	if (channels == 1) {
		if (fp) {
			col[0] = col[1] = col[2] = fp[0];
		}
		else if (cp) {
			col[0] = col[1] = col[2] = (float)cp[0] / 255.0f;
		}
		else {
			col[0] = col[1] = col[2] = 0.0f;
		}
		col[3] = 1.0f;
	}
	else if (channels == 3) {
		if (fp) {
			copy_v3_v3(col, fp);
		}
		else if (cp) {
			rgb_uchar_to_float(col, cp);
		}
		else {
			zero_v3(col);
		}
		col[3] = 1.0f;
	}
	else if (channels == 4) {
		if (fp)
			copy_v4_v4(col, fp);
		else if (cp) {
			rgba_uchar_to_float(col, cp);
		}
		else {
			zero_v4(col);
		}
	}
	else {
		BLI_assert(0);
		zero_v4(col);
	}

	if (color_manage) {
		if (use_default_view)
			IMB_colormanagement_pixel_to_display_space_v4(finalcol, col,  NULL, &scene->display_settings);
		else
			IMB_colormanagement_pixel_to_display_space_v4(finalcol, col,  &scene->view_settings, &scene->display_settings);
	}
	else {
		copy_v4_v4(finalcol, col);
	}

	glDisable(GL_BLEND);
	glColor3fv(finalcol);
	dx += 5;
	glBegin(GL_QUADS);
	glVertex2f(dx, 3);
	glVertex2f(dx, 17);
	glVertex2f(dx + 30, 17);
	glVertex2f(dx + 30, 3);
	glEnd();

	/* draw outline */
	glColor3ub(128, 128, 128);
	glBegin(GL_LINE_LOOP);
	glVertex2f(dx, 3);
	glVertex2f(dx, 17);
	glVertex2f(dx + 30, 17);
	glVertex2f(dx + 30, 3);
	glEnd();

	dx += 35;

	glColor3ub(255, 255, 255);
	if (channels == 1) {
		if (fp) {
			rgb_to_hsv(fp[0], fp[0], fp[0], &hue, &sat, &val);
			rgb_to_yuv(fp[0], fp[0], fp[0], &lum, &u, &v);
		}
		else if (cp) {
			rgb_to_hsv((float)cp[0] / 255.0f, (float)cp[0] / 255.0f, (float)cp[0] / 255.0f, &hue, &sat, &val);
			rgb_to_yuv((float)cp[0] / 255.0f, (float)cp[0] / 255.0f, (float)cp[0] / 255.0f, &lum, &u, &v);
		}
		
		BLI_snprintf(str, sizeof(str), "V:%-.4f", val);
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);

		BLI_snprintf(str, sizeof(str), "   L:%-.4f", lum);
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);
	}
	else if (channels >= 3) {
		if (fp) {
			rgb_to_hsv(fp[0], fp[1], fp[2], &hue, &sat, &val);
			rgb_to_yuv(fp[0], fp[1], fp[2], &lum, &u, &v);
		}
		else if (cp) {
			rgb_to_hsv((float)cp[0] / 255.0f, (float)cp[1] / 255.0f, (float)cp[2] / 255.0f, &hue, &sat, &val);
			rgb_to_yuv((float)cp[0] / 255.0f, (float)cp[1] / 255.0f, (float)cp[2] / 255.0f, &lum, &u, &v);
		}

		BLI_snprintf(str, sizeof(str), "H:%-.4f", hue);
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);

		BLI_snprintf(str, sizeof(str), "  S:%-.4f", sat);
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);

		BLI_snprintf(str, sizeof(str), "  V:%-.4f", val);
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);

		BLI_snprintf(str, sizeof(str), "   L:%-.4f", lum);
		BLF_position(blf_mono_font, dx, 6, 0);
		BLF_draw_ascii(blf_mono_font, str, sizeof(str));
		dx += BLF_width(blf_mono_font, str);
	}

	(void)dx;
}
static void mloopcol_to_float(const MLoopCol *mloopcol, float col_r[3])
{
	rgb_uchar_to_float(col_r, (unsigned char *)&mloopcol->r);
}