static void gimp_ink_motion (GimpPaintCore *paint_core, GimpDrawable *drawable, GimpPaintOptions *paint_options, const GimpCoords *coords, guint32 time) { GimpInk *ink = GIMP_INK (paint_core); GimpInkOptions *options = GIMP_INK_OPTIONS (paint_options); GimpContext *context = GIMP_CONTEXT (paint_options); GimpImage *image; GimpBlob *blob_union = NULL; GimpBlob *blob_to_render; TempBuf *area; guchar col[MAX_CHANNELS]; PixelRegion blob_maskPR; image = gimp_item_get_image (GIMP_ITEM (drawable)); if (! ink->last_blob) { ink->last_blob = ink_pen_ellipse (options, coords->x, coords->y, coords->pressure, coords->xtilt, coords->ytilt, 100); if (ink->start_blob) g_free (ink->start_blob); ink->start_blob = gimp_blob_duplicate (ink->last_blob); blob_to_render = ink->last_blob; } else { GimpBlob *blob = ink_pen_ellipse (options, coords->x, coords->y, coords->pressure, coords->xtilt, coords->ytilt, coords->velocity * 100); blob_union = gimp_blob_convex_union (ink->last_blob, blob); g_free (ink->last_blob); ink->last_blob = blob; blob_to_render = blob_union; } /* Get the buffer */ ink->cur_blob = blob_to_render; area = gimp_paint_core_get_paint_area (paint_core, drawable, paint_options, coords); ink->cur_blob = NULL; if (! area) return; gimp_image_get_foreground (image, context, gimp_drawable_type (drawable), col); /* set the alpha channel */ col[paint_core->canvas_buf->bytes - 1] = OPAQUE_OPACITY; /* color the pixels */ color_pixels (temp_buf_get_data (paint_core->canvas_buf), col, area->width * area->height, area->bytes); gimp_paint_core_validate_canvas_tiles (paint_core, paint_core->canvas_buf->x, paint_core->canvas_buf->y, paint_core->canvas_buf->width, paint_core->canvas_buf->height); /* draw the blob directly to the canvas_tiles */ pixel_region_init (&blob_maskPR, paint_core->canvas_tiles, paint_core->canvas_buf->x, paint_core->canvas_buf->y, paint_core->canvas_buf->width, paint_core->canvas_buf->height, TRUE); render_blob (blob_to_render, &blob_maskPR); /* draw the canvas_buf using the just rendered canvas_tiles as mask */ pixel_region_init (&blob_maskPR, paint_core->canvas_tiles, paint_core->canvas_buf->x, paint_core->canvas_buf->y, paint_core->canvas_buf->width, paint_core->canvas_buf->height, FALSE); gimp_paint_core_paste (paint_core, &blob_maskPR, drawable, GIMP_OPACITY_OPAQUE, gimp_context_get_opacity (context), gimp_context_get_paint_mode (context), GIMP_PAINT_CONSTANT); if (blob_union) g_free (blob_union); }
void _gimp_paintbrush_motion (GimpPaintCore *paint_core, GimpDrawable *drawable, GimpPaintOptions *paint_options, gdouble opacity) { GimpBrushCore *brush_core = GIMP_BRUSH_CORE (paint_core); GimpContext *context = GIMP_CONTEXT (paint_options); GimpPressureOptions *pressure_options = paint_options->pressure_options; GimpImage *image; GimpRGB gradient_color; TempBuf *area; guchar col[MAX_CHANNELS]; GimpPaintApplicationMode paint_appl_mode; image = gimp_item_get_image (GIMP_ITEM (drawable)); opacity *= gimp_paint_options_get_fade (paint_options, image, paint_core->pixel_dist); if (opacity == 0.0) return; paint_appl_mode = paint_options->application_mode; area = gimp_paint_core_get_paint_area (paint_core, drawable, paint_options); if (! area) return; /* optionally take the color from the current gradient */ if (gimp_paint_options_get_gradient_color (paint_options, image, paint_core->cur_coords.pressure, paint_core->pixel_dist, &gradient_color)) { opacity *= gradient_color.a; gimp_rgb_get_uchar (&gradient_color, &col[RED_PIX], &col[GREEN_PIX], &col[BLUE_PIX]); col[ALPHA_PIX] = OPAQUE_OPACITY; color_pixels (temp_buf_data (area), col, area->width * area->height, area->bytes); paint_appl_mode = GIMP_PAINT_INCREMENTAL; } /* otherwise check if the brush has a pixmap and use that to color the area */ else if (brush_core->brush && brush_core->brush->pixmap) { gimp_brush_core_color_area_with_pixmap (brush_core, drawable, area, gimp_paint_options_get_brush_mode (paint_options)); paint_appl_mode = GIMP_PAINT_INCREMENTAL; } /* otherwise fill the area with the foreground color */ else { gimp_image_get_foreground (image, context, gimp_drawable_type (drawable), col); col[area->bytes - 1] = OPAQUE_OPACITY; color_pixels (temp_buf_data (area), col, area->width * area->height, area->bytes); } if (paint_core->use_pressure && pressure_options->opacity) opacity *= PRESSURE_SCALE * paint_core->cur_coords.pressure; /* finally, let the brush core paste the colored area on the canvas */ gimp_brush_core_paste_canvas (brush_core, drawable, MIN (opacity, GIMP_OPACITY_OPAQUE), gimp_context_get_opacity (context), gimp_context_get_paint_mode (context), gimp_paint_options_get_brush_mode (paint_options), paint_appl_mode); }