Merge branch 'blender2.7'
[blender.git] / source / blender / editors / sculpt_paint / paint_image.c
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * along with this program; if not, write to the Free Software Foundation,
15  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
16  *
17  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
18  * All rights reserved.
19  *
20  * The Original Code is: some of this file.
21  *
22  * Contributor(s): Jens Ole Wund (bjornmose), Campbell Barton (ideasman42)
23  *
24  * ***** END GPL LICENSE BLOCK *****
25  */
26
27 /** \file blender/editors/sculpt_paint/paint_image.c
28  *  \ingroup edsculpt
29  *  \brief Functions to paint images in 2D and 3D.
30  */
31
32 #include <float.h>
33 #include <string.h>
34 #include <stdio.h>
35 #include <math.h>
36
37 #include "MEM_guardedalloc.h"
38
39 #include "BLI_math.h"
40 #include "BLI_blenlib.h"
41 #include "BLI_utildefines.h"
42
43 #include "BLT_translation.h"
44
45 #include "IMB_imbuf.h"
46 #include "IMB_imbuf_types.h"
47
48 #include "DNA_brush_types.h"
49 #include "DNA_mesh_types.h"
50 #include "DNA_node_types.h"
51 #include "DNA_object_types.h"
52
53 #include "BKE_colorband.h"
54 #include "BKE_context.h"
55 #include "BKE_brush.h"
56 #include "BKE_main.h"
57 #include "BKE_material.h"
58 #include "BKE_mesh.h"
59 #include "BKE_node.h"
60 #include "BKE_paint.h"
61 #include "BKE_undo_system.h"
62
63
64 #include "DEG_depsgraph.h"
65
66 #include "UI_interface.h"
67 #include "UI_view2d.h"
68
69 #include "ED_image.h"
70 #include "ED_object.h"
71 #include "ED_paint.h"
72 #include "ED_screen.h"
73 #include "ED_view3d.h"
74
75 #include "WM_api.h"
76 #include "WM_types.h"
77 #include "WM_message.h"
78 #include "WM_toolsystem.h"
79
80 #include "RNA_access.h"
81 #include "RNA_define.h"
82
83 #include "GPU_draw.h"
84 #include "GPU_immediate.h"
85 #include "GPU_state.h"
86
87
88 #include "IMB_colormanagement.h"
89
90 #include "paint_intern.h"
91
92 /* this is a static resource for non-globality,
93  * Maybe it should be exposed as part of the
94  * paint operation, but for now just give a public interface */
95 static ImagePaintPartialRedraw imapaintpartial = {0, 0, 0, 0, 0};
96
97 ImagePaintPartialRedraw *get_imapaintpartial(void)
98 {
99         return &imapaintpartial;
100 }
101
102 void set_imapaintpartial(struct ImagePaintPartialRedraw *ippr)
103 {
104         imapaintpartial = *ippr;
105 }
106
107 /* Imagepaint Partial Redraw & Dirty Region */
108
109 void ED_imapaint_clear_partial_redraw(void)
110 {
111         memset(&imapaintpartial, 0, sizeof(imapaintpartial));
112 }
113
114 void imapaint_region_tiles(ImBuf *ibuf, int x, int y, int w, int h, int *tx, int *ty, int *tw, int *th)
115 {
116         int srcx = 0, srcy = 0;
117
118         IMB_rectclip(ibuf, NULL, &x, &y, &srcx, &srcy, &w, &h);
119
120         *tw = ((x + w - 1) >> IMAPAINT_TILE_BITS);
121         *th = ((y + h - 1) >> IMAPAINT_TILE_BITS);
122         *tx = (x >> IMAPAINT_TILE_BITS);
123         *ty = (y >> IMAPAINT_TILE_BITS);
124 }
125
126 void ED_imapaint_dirty_region(Image *ima, ImBuf *ibuf, int x, int y, int w, int h, bool find_old)
127 {
128         ImBuf *tmpibuf = NULL;
129         int tilex, tiley, tilew, tileh, tx, ty;
130         int srcx = 0, srcy = 0;
131
132         IMB_rectclip(ibuf, NULL, &x, &y, &srcx, &srcy, &w, &h);
133
134         if (w == 0 || h == 0)
135                 return;
136
137         if (!imapaintpartial.enabled) {
138                 imapaintpartial.x1 = x;
139                 imapaintpartial.y1 = y;
140                 imapaintpartial.x2 = x + w;
141                 imapaintpartial.y2 = y + h;
142                 imapaintpartial.enabled = 1;
143         }
144         else {
145                 imapaintpartial.x1 = min_ii(imapaintpartial.x1, x);
146                 imapaintpartial.y1 = min_ii(imapaintpartial.y1, y);
147                 imapaintpartial.x2 = max_ii(imapaintpartial.x2, x + w);
148                 imapaintpartial.y2 = max_ii(imapaintpartial.y2, y + h);
149         }
150
151         imapaint_region_tiles(ibuf, x, y, w, h, &tilex, &tiley, &tilew, &tileh);
152
153         ListBase *undo_tiles = ED_image_undo_get_tiles();
154
155         for (ty = tiley; ty <= tileh; ty++)
156                 for (tx = tilex; tx <= tilew; tx++)
157                         image_undo_push_tile(undo_tiles, ima, ibuf, &tmpibuf, tx, ty, NULL, NULL, false, find_old);
158
159         ibuf->userflags |= IB_BITMAPDIRTY;
160
161         if (tmpibuf)
162                 IMB_freeImBuf(tmpibuf);
163 }
164
165 void imapaint_image_update(SpaceImage *sima, Image *image, ImBuf *ibuf, short texpaint)
166 {
167         if (imapaintpartial.x1 != imapaintpartial.x2 &&
168             imapaintpartial.y1 != imapaintpartial.y2)
169         {
170                 IMB_partial_display_buffer_update_delayed(
171                         ibuf, imapaintpartial.x1, imapaintpartial.y1,
172                         imapaintpartial.x2, imapaintpartial.y2);
173         }
174
175         if (ibuf->mipmap[0])
176                 ibuf->userflags |= IB_MIPMAP_INVALID;
177
178         /* todo: should set_tpage create ->rect? */
179         if (texpaint || (sima && sima->lock)) {
180                 int w = imapaintpartial.x2 - imapaintpartial.x1;
181                 int h = imapaintpartial.y2 - imapaintpartial.y1;
182                 if (w && h) {
183                         /* Testing with partial update in uv editor too */
184                         GPU_paint_update_image(image, (sima ? &sima->iuser : NULL), imapaintpartial.x1, imapaintpartial.y1, w, h);
185                 }
186         }
187 }
188
189 /* paint blur kernels. Projective painting enforces use of a 2x2 kernel due to lagging */
190 BlurKernel *paint_new_blur_kernel(Brush *br, bool proj)
191 {
192         int i, j;
193         BlurKernel *kernel = MEM_mallocN(sizeof(BlurKernel), "blur kernel");
194         float radius;
195         int side;
196         eBlurKernelType type = br->blur_mode;
197
198         if (proj) {
199                 radius = 0.5f;
200
201                 side = kernel->side = 2;
202                 kernel->side_squared = kernel->side * kernel->side;
203                 kernel->wdata = MEM_mallocN(sizeof(float) * kernel->side_squared, "blur kernel data");
204                 kernel->pixel_len = radius;
205         }
206         else {
207                 if (br->blur_kernel_radius <= 0)
208                         br->blur_kernel_radius = 1;
209
210                 radius = br->blur_kernel_radius;
211
212                 side = kernel->side = radius * 2 + 1;
213                 kernel->side_squared = kernel->side * kernel->side;
214                 kernel->wdata = MEM_mallocN(sizeof(float) * kernel->side_squared, "blur kernel data");
215                 kernel->pixel_len = br->blur_kernel_radius;
216         }
217
218         switch (type) {
219                 case KERNEL_BOX:
220                         for (i = 0; i < kernel->side_squared; i++)
221                                 kernel->wdata[i] = 1.0;
222                         break;
223
224                 case KERNEL_GAUSSIAN:
225                 {
226                         /* at 3.0 standard deviations distance, kernel is about zero */
227                         float standard_dev = radius / 3.0f;
228
229                         /* make the necessary adjustment to the value for use in the normal distribution formula */
230                         standard_dev = -standard_dev * standard_dev * 2;
231
232                         for (i = 0; i < side; i++) {
233                                 for (j = 0; j < side; j++) {
234                                         float idist = radius - i;
235                                         float jdist = radius - j;
236                                         float value = exp((idist * idist + jdist * jdist) / standard_dev);
237
238                                         kernel->wdata[i + j * side] = value;
239                                 }
240                         }
241
242                         break;
243                 }
244
245                 default:
246                         printf("unidentified kernel type, aborting\n");
247                         MEM_freeN(kernel->wdata);
248                         MEM_freeN(kernel);
249                         return NULL;
250         }
251
252         return kernel;
253 }
254
255 void paint_delete_blur_kernel(BlurKernel *kernel)
256 {
257         if (kernel->wdata)
258                 MEM_freeN(kernel->wdata);
259 }
260
261 /************************ image paint poll ************************/
262
263 static Brush *image_paint_brush(bContext *C)
264 {
265         Scene *scene = CTX_data_scene(C);
266         ToolSettings *settings = scene->toolsettings;
267
268         return BKE_paint_brush(&settings->imapaint.paint);
269 }
270
271 static bool image_paint_poll_ex(bContext *C, bool check_tool)
272 {
273         Object *obact;
274
275         if (!image_paint_brush(C))
276                 return 0;
277
278         obact = CTX_data_active_object(C);
279         if ((obact && obact->mode & OB_MODE_TEXTURE_PAINT) && CTX_wm_region_view3d(C)) {
280                 if (!check_tool || WM_toolsystem_active_tool_is_brush(C)) {
281                         return 1;
282                 }
283         }
284         else {
285                 SpaceImage *sima = CTX_wm_space_image(C);
286
287                 if (sima) {
288                         ARegion *ar = CTX_wm_region(C);
289
290                         if ((sima->mode == SI_MODE_PAINT) && ar->regiontype == RGN_TYPE_WINDOW) {
291                                 return 1;
292                         }
293                 }
294         }
295
296         return 0;
297 }
298
299 static bool image_paint_poll(bContext *C)
300 {
301         return image_paint_poll_ex(C, true);
302 }
303
304 static bool image_paint_poll_ignore_tool(bContext *C)
305 {
306         return image_paint_poll_ex(C, false);
307 }
308
309 static bool image_paint_2d_clone_poll(bContext *C)
310 {
311         Brush *brush = image_paint_brush(C);
312
313         if (!CTX_wm_region_view3d(C) && image_paint_poll(C))
314                 if (brush && (brush->imagepaint_tool == PAINT_TOOL_CLONE))
315                         if (brush->clone.image)
316                                 return 1;
317
318         return 0;
319 }
320
321 /************************ paint operator ************************/
322 typedef enum eTexPaintMode {
323         PAINT_MODE_2D,
324         PAINT_MODE_3D_PROJECT
325 } eTexPaintMode;
326
327 typedef struct PaintOperation {
328         eTexPaintMode mode;
329
330         void *custom_paint;
331
332         float prevmouse[2];
333         float startmouse[2];
334         double starttime;
335
336         void *cursor;
337         ViewContext vc;
338 } PaintOperation;
339
340 bool paint_use_opacity_masking(Brush *brush)
341 {
342         return ((brush->flag & BRUSH_AIRBRUSH) ||
343                 (brush->flag & BRUSH_DRAG_DOT) ||
344                 (brush->flag & BRUSH_ANCHORED) ||
345                 (brush->imagepaint_tool == PAINT_TOOL_SMEAR) ||
346                 (brush->imagepaint_tool == PAINT_TOOL_SOFTEN) ||
347                 (brush->imagepaint_tool == PAINT_TOOL_FILL) ||
348                 (brush->flag & BRUSH_USE_GRADIENT) ||
349                 (brush->mtex.tex &&
350                  !ELEM(brush->mtex.brush_map_mode, MTEX_MAP_MODE_TILED, MTEX_MAP_MODE_STENCIL, MTEX_MAP_MODE_3D)) ?
351                 false : true);
352 }
353
354 void paint_brush_color_get(
355         struct Scene *scene, struct Brush *br, bool color_correction, bool invert, float distance,
356         float pressure, float color[3], struct ColorManagedDisplay *display)
357 {
358         if (invert)
359                 copy_v3_v3(color, BKE_brush_secondary_color_get(scene, br));
360         else {
361                 if (br->flag & BRUSH_USE_GRADIENT) {
362                         float color_gr[4];
363                         switch (br->gradient_stroke_mode) {
364                                 case BRUSH_GRADIENT_PRESSURE:
365                                         BKE_colorband_evaluate(br->gradient, pressure, color_gr);
366                                         break;
367                                 case BRUSH_GRADIENT_SPACING_REPEAT:
368                                 {
369                                         float coord = fmod(distance / br->gradient_spacing, 1.0);
370                                         BKE_colorband_evaluate(br->gradient, coord, color_gr);
371                                         break;
372                                 }
373                                 case BRUSH_GRADIENT_SPACING_CLAMP:
374                                 {
375                                         BKE_colorband_evaluate(br->gradient, distance / br->gradient_spacing, color_gr);
376                                         break;
377                                 }
378                         }
379                         copy_v3_v3(color, color_gr);
380                 }
381                 else
382                         copy_v3_v3(color, BKE_brush_color_get(scene, br));
383         }
384         if (color_correction)
385                 IMB_colormanagement_display_to_scene_linear_v3(color, display);
386 }
387
388 void paint_brush_init_tex(Brush *brush)
389 {
390         /* init mtex nodes */
391         if (brush) {
392                 MTex *mtex = &brush->mtex;
393                 if (mtex->tex && mtex->tex->nodetree) {
394                         /* has internal flag to detect it only does it once */
395                         ntreeTexBeginExecTree(mtex->tex->nodetree);
396                 }
397                 mtex = &brush->mask_mtex;
398                 if (mtex->tex && mtex->tex->nodetree) {
399                         ntreeTexBeginExecTree(mtex->tex->nodetree);
400                 }
401         }
402 }
403
404 void paint_brush_exit_tex(Brush *brush)
405 {
406         if (brush) {
407                 MTex *mtex = &brush->mtex;
408                 if (mtex->tex && mtex->tex->nodetree)
409                         ntreeTexEndExecTree(mtex->tex->nodetree->execdata);
410                 mtex = &brush->mask_mtex;
411                 if (mtex->tex && mtex->tex->nodetree)
412                         ntreeTexEndExecTree(mtex->tex->nodetree->execdata);
413         }
414 }
415
416 static void gradient_draw_line(bContext *UNUSED(C), int x, int y, void *customdata)
417 {
418         PaintOperation *pop = (PaintOperation *)customdata;
419
420         if (pop) {
421                 GPU_line_smooth(true);
422                 GPU_blend(true);
423
424                 GPUVertFormat *format = immVertexFormat();
425                 uint pos = GPU_vertformat_attr_add(format, "pos", GPU_COMP_I32, 2, GPU_FETCH_INT_TO_FLOAT);
426
427                 immBindBuiltinProgram(GPU_SHADER_2D_UNIFORM_COLOR);
428
429                 GPU_line_width(4.0);
430                 immUniformColor4ub(0, 0, 0, 255);
431
432                 immBegin(GPU_PRIM_LINES, 2);
433                 immVertex2i(pos, x, y);
434                 immVertex2i(pos, pop->startmouse[0], pop->startmouse[1]);
435                 immEnd();
436
437                 GPU_line_width(2.0);
438                 immUniformColor4ub(255, 255, 255, 255);
439
440                 immBegin(GPU_PRIM_LINES, 2);
441                 immVertex2i(pos, x, y);
442                 immVertex2i(pos, pop->startmouse[0], pop->startmouse[1]);
443                 immEnd();
444
445                 immUnbindProgram();
446
447                 GPU_blend(false);
448                 GPU_line_smooth(false);
449         }
450 }
451
452
453 static PaintOperation *texture_paint_init(bContext *C, wmOperator *op, const float mouse[2])
454 {
455         Scene *scene = CTX_data_scene(C);
456         ToolSettings *settings = scene->toolsettings;
457         PaintOperation *pop = MEM_callocN(sizeof(PaintOperation), "PaintOperation"); /* caller frees */
458         Brush *brush = BKE_paint_brush(&settings->imapaint.paint);
459         int mode = RNA_enum_get(op->ptr, "mode");
460         ED_view3d_viewcontext_init(C, &pop->vc);
461
462         copy_v2_v2(pop->prevmouse, mouse);
463         copy_v2_v2(pop->startmouse, mouse);
464
465         /* initialize from context */
466         if (CTX_wm_region_view3d(C)) {
467                 ViewLayer *view_layer = CTX_data_view_layer(C);
468                 Object *ob = OBACT(view_layer);
469                 bool uvs, mat, tex, stencil;
470                 if (!BKE_paint_proj_mesh_data_check(scene, ob, &uvs, &mat, &tex, &stencil)) {
471                         BKE_paint_data_warning(op->reports, uvs, mat, tex, stencil);
472                         MEM_freeN(pop);
473                         WM_event_add_notifier(C, NC_SCENE | ND_TOOLSETTINGS, NULL);
474                         return NULL;
475                 }
476                 pop->mode = PAINT_MODE_3D_PROJECT;
477                 pop->custom_paint = paint_proj_new_stroke(C, ob, mouse, mode);
478         }
479         else {
480                 pop->mode = PAINT_MODE_2D;
481                 pop->custom_paint = paint_2d_new_stroke(C, op, mode);
482         }
483
484         if (!pop->custom_paint) {
485                 MEM_freeN(pop);
486                 return NULL;
487         }
488
489         if ((brush->imagepaint_tool == PAINT_TOOL_FILL) && (brush->flag & BRUSH_USE_GRADIENT)) {
490                 pop->cursor = WM_paint_cursor_activate(
491                         CTX_wm_manager(C),
492                         SPACE_TYPE_ANY, RGN_TYPE_ANY,
493                         image_paint_poll, gradient_draw_line,
494                         pop);
495         }
496
497         settings->imapaint.flag |= IMAGEPAINT_DRAWING;
498         ED_image_undo_push_begin(op->type->name);
499
500         return pop;
501 }
502
503 static void paint_stroke_update_step(bContext *C, struct PaintStroke *stroke, PointerRNA *itemptr)
504 {
505         PaintOperation *pop = paint_stroke_mode_data(stroke);
506         Scene *scene = CTX_data_scene(C);
507         ToolSettings *toolsettings = CTX_data_tool_settings(C);
508         UnifiedPaintSettings *ups = &toolsettings->unified_paint_settings;
509         Brush *brush = BKE_paint_brush(&toolsettings->imapaint.paint);
510
511         float alphafac = (brush->flag & BRUSH_ACCUMULATE) ? ups->overlap_factor : 1.0f;
512
513         /* initial brush values. Maybe it should be considered moving these to stroke system */
514         float startalpha = BKE_brush_alpha_get(scene, brush);
515
516         float mouse[2];
517         float pressure;
518         float size;
519         float distance = paint_stroke_distance_get(stroke);
520         int eraser;
521
522         RNA_float_get_array(itemptr, "mouse", mouse);
523         pressure = RNA_float_get(itemptr, "pressure");
524         eraser = RNA_boolean_get(itemptr, "pen_flip");
525         size = max_ff(1.0f, RNA_float_get(itemptr, "size"));
526
527         /* stroking with fill tool only acts on stroke end */
528         if (brush->imagepaint_tool == PAINT_TOOL_FILL) {
529                 copy_v2_v2(pop->prevmouse, mouse);
530                 return;
531         }
532
533         if (BKE_brush_use_alpha_pressure(scene, brush))
534                 BKE_brush_alpha_set(scene, brush, max_ff(0.0f, startalpha * pressure * alphafac));
535         else
536                 BKE_brush_alpha_set(scene, brush, max_ff(0.0f, startalpha * alphafac));
537
538         if ((brush->flag & BRUSH_DRAG_DOT) || (brush->flag & BRUSH_ANCHORED)) {
539                 UndoStack *ustack = CTX_wm_manager(C)->undo_stack;
540                 ED_image_undo_restore(ustack->step_init);
541         }
542
543         if (pop->mode == PAINT_MODE_3D_PROJECT) {
544                 paint_proj_stroke(C, pop->custom_paint, pop->prevmouse, mouse, eraser, pressure, distance, size);
545         }
546         else {
547                 paint_2d_stroke(pop->custom_paint, pop->prevmouse, mouse, eraser, pressure, distance, size);
548         }
549
550         copy_v2_v2(pop->prevmouse, mouse);
551
552         /* restore brush values */
553         BKE_brush_alpha_set(scene, brush, startalpha);
554 }
555
556 static void paint_stroke_redraw(const bContext *C, struct PaintStroke *stroke, bool final)
557 {
558         PaintOperation *pop = paint_stroke_mode_data(stroke);
559
560         if (pop->mode == PAINT_MODE_3D_PROJECT) {
561                 paint_proj_redraw(C, pop->custom_paint, final);
562         }
563         else {
564                 paint_2d_redraw(C, pop->custom_paint, final);
565         }
566 }
567
568 static void paint_stroke_done(const bContext *C, struct PaintStroke *stroke)
569 {
570         Scene *scene = CTX_data_scene(C);
571         ToolSettings *toolsettings = scene->toolsettings;
572         PaintOperation *pop = paint_stroke_mode_data(stroke);
573         Brush *brush = BKE_paint_brush(&toolsettings->imapaint.paint);
574
575         toolsettings->imapaint.flag &= ~IMAGEPAINT_DRAWING;
576
577         if (brush->imagepaint_tool == PAINT_TOOL_FILL) {
578                 if (brush->flag & BRUSH_USE_GRADIENT) {
579                         if (pop->mode == PAINT_MODE_2D) {
580                                 paint_2d_gradient_fill(C, brush, pop->startmouse, pop->prevmouse, pop->custom_paint);
581                         }
582                         else {
583                                 paint_proj_stroke(
584                                         C, pop->custom_paint, pop->startmouse, pop->prevmouse, paint_stroke_flipped(stroke),
585                                         1.0, 0.0, BKE_brush_size_get(scene, brush));
586                                 /* two redraws, one for GPU update, one for notification */
587                                 paint_proj_redraw(C, pop->custom_paint, false);
588                                 paint_proj_redraw(C, pop->custom_paint, true);
589                         }
590                 }
591                 else {
592                         if (pop->mode == PAINT_MODE_2D) {
593                                 float color[3];
594
595                                 srgb_to_linearrgb_v3_v3(color, BKE_brush_color_get(scene, brush));
596                                 paint_2d_bucket_fill(C, color, brush, pop->prevmouse, pop->custom_paint);
597                         }
598                         else {
599                                 paint_proj_stroke(
600                                         C, pop->custom_paint, pop->startmouse, pop->prevmouse, paint_stroke_flipped(stroke),
601                                         1.0, 0.0, BKE_brush_size_get(scene, brush));
602                                 /* two redraws, one for GPU update, one for notification */
603                                 paint_proj_redraw(C, pop->custom_paint, false);
604                                 paint_proj_redraw(C, pop->custom_paint, true);
605                         }
606                 }
607         }
608         if (pop->mode == PAINT_MODE_3D_PROJECT) {
609                 paint_proj_stroke_done(pop->custom_paint);
610         }
611         else {
612                 paint_2d_stroke_done(pop->custom_paint);
613         }
614
615         if (pop->cursor) {
616                 WM_paint_cursor_end(CTX_wm_manager(C), pop->cursor);
617         }
618
619         ED_image_undo_push_end();
620
621         /* duplicate warning, see texpaint_init */
622 #if 0
623         if (pop->s.warnmultifile)
624                 BKE_reportf(op->reports, RPT_WARNING, "Image requires 4 color channels to paint: %s", pop->s.warnmultifile);
625         if (pop->s.warnpackedfile)
626                 BKE_reportf(op->reports, RPT_WARNING, "Packed MultiLayer files cannot be painted: %s", pop->s.warnpackedfile);
627 #endif
628         MEM_freeN(pop);
629 }
630
631 static bool paint_stroke_test_start(bContext *C, wmOperator *op, const float mouse[2])
632 {
633         PaintOperation *pop;
634
635         /* TODO Should avoid putting this here. Instead, last position should be requested
636          * from stroke system. */
637
638         if (!(pop = texture_paint_init(C, op, mouse))) {
639                 return false;
640         }
641
642         paint_stroke_set_mode_data(op->customdata, pop);
643
644         return true;
645 }
646
647
648 static int paint_invoke(bContext *C, wmOperator *op, const wmEvent *event)
649 {
650         int retval;
651
652         op->customdata = paint_stroke_new(
653                 C, op, NULL, paint_stroke_test_start,
654                 paint_stroke_update_step,
655                 paint_stroke_redraw,
656                 paint_stroke_done, event->type);
657
658         if ((retval = op->type->modal(C, op, event)) == OPERATOR_FINISHED) {
659                 paint_stroke_data_free(op);
660                 return OPERATOR_FINISHED;
661         }
662         /* add modal handler */
663         WM_event_add_modal_handler(C, op);
664
665         OPERATOR_RETVAL_CHECK(retval);
666         BLI_assert(retval == OPERATOR_RUNNING_MODAL);
667
668         return OPERATOR_RUNNING_MODAL;
669 }
670
671 static int paint_exec(bContext *C, wmOperator *op)
672 {
673         PropertyRNA *strokeprop;
674         PointerRNA firstpoint;
675         float mouse[2];
676
677         strokeprop = RNA_struct_find_property(op->ptr, "stroke");
678
679         if (!RNA_property_collection_lookup_int(op->ptr, strokeprop, 0, &firstpoint))
680                 return OPERATOR_CANCELLED;
681
682         RNA_float_get_array(&firstpoint, "mouse", mouse);
683
684         op->customdata = paint_stroke_new(
685                 C, op, NULL, paint_stroke_test_start,
686                 paint_stroke_update_step,
687                 paint_stroke_redraw,
688                 paint_stroke_done, 0);
689         /* frees op->customdata */
690         return paint_stroke_exec(C, op);
691 }
692
693 void PAINT_OT_image_paint(wmOperatorType *ot)
694 {
695         /* identifiers */
696         ot->name = "Image Paint";
697         ot->idname = "PAINT_OT_image_paint";
698         ot->description = "Paint a stroke into the image";
699
700         /* api callbacks */
701         ot->invoke = paint_invoke;
702         ot->modal = paint_stroke_modal;
703         ot->exec = paint_exec;
704         ot->poll = image_paint_poll;
705         ot->cancel = paint_stroke_cancel;
706
707         /* flags */
708         ot->flag = OPTYPE_BLOCKING;
709
710         paint_stroke_operator_properties(ot);
711 }
712
713
714 int get_imapaint_zoom(bContext *C, float *zoomx, float *zoomy)
715 {
716         RegionView3D *rv3d = CTX_wm_region_view3d(C);
717
718         if (!rv3d) {
719                 SpaceImage *sima = CTX_wm_space_image(C);
720
721                 if (sima->mode == SI_MODE_PAINT) {
722                         ARegion *ar = CTX_wm_region(C);
723                         ED_space_image_get_zoom(sima, ar, zoomx, zoomy);
724
725                         return 1;
726                 }
727         }
728
729         *zoomx = *zoomy = 1;
730
731         return 0;
732 }
733
734 /************************ cursor drawing *******************************/
735
736 static void toggle_paint_cursor(bContext *C, int enable)
737 {
738         wmWindowManager *wm = CTX_wm_manager(C);
739         Scene *scene = CTX_data_scene(C);
740         ToolSettings *settings = scene->toolsettings;
741
742         if (settings->imapaint.paintcursor && !enable) {
743                 WM_paint_cursor_end(wm, settings->imapaint.paintcursor);
744                 settings->imapaint.paintcursor = NULL;
745                 paint_cursor_delete_textures();
746         }
747         else if (enable)
748                 paint_cursor_start(C, image_paint_poll);
749 }
750
751 /* enable the paint cursor if it isn't already.
752  *
753  * purpose is to make sure the paint cursor is shown if paint
754  * mode is enabled in the image editor. the paint poll will
755  * ensure that the cursor is hidden when not in paint mode */
756 void ED_space_image_paint_update(Main *bmain, wmWindowManager *wm, Scene *scene)
757 {
758         ToolSettings *settings = scene->toolsettings;
759         ImagePaintSettings *imapaint = &settings->imapaint;
760         bool enabled = false;
761
762         for (wmWindow *win = wm->windows.first; win; win = win->next) {
763                 bScreen *screen = WM_window_get_active_screen(win);
764
765                 for (ScrArea *sa = screen->areabase.first; sa; sa = sa->next) {
766                         if (sa->spacetype == SPACE_IMAGE) {
767                                 if (((SpaceImage *)sa->spacedata.first)->mode == SI_MODE_PAINT) {
768                                         enabled = true;
769                                 }
770                         }
771                 }
772         }
773
774         if (enabled) {
775                 BKE_paint_init(bmain, scene, PAINT_MODE_TEXTURE_2D, PAINT_CURSOR_TEXTURE_PAINT);
776
777                 paint_cursor_start_explicit(&imapaint->paint, wm, image_paint_poll);
778         }
779         else {
780                 paint_cursor_delete_textures();
781         }
782 }
783
784 /************************ grab clone operator ************************/
785
786 typedef struct GrabClone {
787         float startoffset[2];
788         int startx, starty;
789 } GrabClone;
790
791 static void grab_clone_apply(bContext *C, wmOperator *op)
792 {
793         Brush *brush = image_paint_brush(C);
794         float delta[2];
795
796         RNA_float_get_array(op->ptr, "delta", delta);
797         add_v2_v2(brush->clone.offset, delta);
798         ED_region_tag_redraw(CTX_wm_region(C));
799 }
800
801 static int grab_clone_exec(bContext *C, wmOperator *op)
802 {
803         grab_clone_apply(C, op);
804
805         return OPERATOR_FINISHED;
806 }
807
808 static int grab_clone_invoke(bContext *C, wmOperator *op, const wmEvent *event)
809 {
810         Brush *brush = image_paint_brush(C);
811         GrabClone *cmv;
812
813         cmv = MEM_callocN(sizeof(GrabClone), "GrabClone");
814         copy_v2_v2(cmv->startoffset, brush->clone.offset);
815         cmv->startx = event->x;
816         cmv->starty = event->y;
817         op->customdata = cmv;
818
819         WM_event_add_modal_handler(C, op);
820
821         return OPERATOR_RUNNING_MODAL;
822 }
823
824 static int grab_clone_modal(bContext *C, wmOperator *op, const wmEvent *event)
825 {
826         Brush *brush = image_paint_brush(C);
827         ARegion *ar = CTX_wm_region(C);
828         GrabClone *cmv = op->customdata;
829         float startfx, startfy, fx, fy, delta[2];
830         int xmin = ar->winrct.xmin, ymin = ar->winrct.ymin;
831
832         switch (event->type) {
833                 case LEFTMOUSE:
834                 case MIDDLEMOUSE:
835                 case RIGHTMOUSE: // XXX hardcoded
836                         MEM_freeN(op->customdata);
837                         return OPERATOR_FINISHED;
838                 case MOUSEMOVE:
839                         /* mouse moved, so move the clone image */
840                         UI_view2d_region_to_view(&ar->v2d, cmv->startx - xmin, cmv->starty - ymin, &startfx, &startfy);
841                         UI_view2d_region_to_view(&ar->v2d, event->x - xmin, event->y - ymin, &fx, &fy);
842
843                         delta[0] = fx - startfx;
844                         delta[1] = fy - startfy;
845                         RNA_float_set_array(op->ptr, "delta", delta);
846
847                         copy_v2_v2(brush->clone.offset, cmv->startoffset);
848
849                         grab_clone_apply(C, op);
850                         break;
851         }
852
853         return OPERATOR_RUNNING_MODAL;
854 }
855
856 static void grab_clone_cancel(bContext *UNUSED(C), wmOperator *op)
857 {
858         MEM_freeN(op->customdata);
859 }
860
861 void PAINT_OT_grab_clone(wmOperatorType *ot)
862 {
863         /* identifiers */
864         ot->name = "Grab Clone";
865         ot->idname = "PAINT_OT_grab_clone";
866         ot->description = "Move the clone source image";
867
868         /* api callbacks */
869         ot->exec = grab_clone_exec;
870         ot->invoke = grab_clone_invoke;
871         ot->modal = grab_clone_modal;
872         ot->cancel = grab_clone_cancel;
873         ot->poll = image_paint_2d_clone_poll;
874
875         /* flags */
876         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO | OPTYPE_BLOCKING;
877
878         /* properties */
879         RNA_def_float_vector(ot->srna, "delta", 2, NULL, -FLT_MAX, FLT_MAX, "Delta", "Delta offset of clone image in 0.0..1.0 coordinates", -1.0f, 1.0f);
880 }
881
882 /******************** sample color operator ********************/
883 typedef struct {
884         bool show_cursor;
885         short event_type;
886         float initcolor[3];
887         bool sample_palette;
888 }       SampleColorData;
889
890
891 static void sample_color_update_header(SampleColorData *data, bContext *C)
892 {
893         char msg[UI_MAX_DRAW_STR];
894         ScrArea *sa = CTX_wm_area(C);
895
896         if (sa) {
897                 BLI_snprintf(
898                         msg, sizeof(msg),
899                         IFACE_("Sample color for %s"),
900                         !data->sample_palette ?
901                         IFACE_("Brush. Use Left Click to sample for palette instead") :
902                         IFACE_("Palette. Use Left Click to sample more colors"));
903                 ED_workspace_status_text(C, msg);
904         }
905 }
906
907 static int sample_color_exec(bContext *C, wmOperator *op)
908 {
909         Paint *paint = BKE_paint_get_active_from_context(C);
910         Brush *brush = BKE_paint_brush(paint);
911         ePaintMode mode = BKE_paintmode_get_active_from_context(C);
912         ARegion *ar = CTX_wm_region(C);
913         wmWindow *win = CTX_wm_window(C);
914         const bool show_cursor = ((paint->flags & PAINT_SHOW_BRUSH) != 0);
915         int location[2];
916         paint->flags &= ~PAINT_SHOW_BRUSH;
917
918         /* force redraw without cursor */
919         WM_paint_cursor_tag_redraw(win, ar);
920         WM_redraw_windows(C);
921
922         RNA_int_get_array(op->ptr, "location", location);
923         const bool use_palette = RNA_boolean_get(op->ptr, "palette");
924         const bool use_sample_texture = (mode == PAINT_MODE_TEXTURE_3D) && !RNA_boolean_get(op->ptr, "merged");
925
926         paint_sample_color(C, ar, location[0], location[1], use_sample_texture, use_palette);
927
928         if (show_cursor) {
929                 paint->flags |= PAINT_SHOW_BRUSH;
930         }
931
932         WM_event_add_notifier(C, NC_BRUSH | NA_EDITED, brush);
933
934         return OPERATOR_FINISHED;
935 }
936
937 static int sample_color_invoke(bContext *C, wmOperator *op, const wmEvent *event)
938 {
939         Scene *scene = CTX_data_scene(C);
940         Paint *paint = BKE_paint_get_active_from_context(C);
941         Brush *brush = BKE_paint_brush(paint);
942         SampleColorData *data = MEM_mallocN(sizeof(SampleColorData), "sample color custom data");
943         ARegion *ar = CTX_wm_region(C);
944         wmWindow *win = CTX_wm_window(C);
945
946         data->event_type = event->type;
947         data->show_cursor = ((paint->flags & PAINT_SHOW_BRUSH) != 0);
948         copy_v3_v3(data->initcolor, BKE_brush_color_get(scene, brush));
949         data->sample_palette = false;
950         op->customdata = data;
951         paint->flags &= ~PAINT_SHOW_BRUSH;
952
953         sample_color_update_header(data, C);
954
955         WM_event_add_modal_handler(C, op);
956
957         /* force redraw without cursor */
958         WM_paint_cursor_tag_redraw(win, ar);
959         WM_redraw_windows(C);
960
961         RNA_int_set_array(op->ptr, "location", event->mval);
962
963         ePaintMode mode = BKE_paintmode_get_active_from_context(C);
964         const bool use_sample_texture = (mode == PAINT_MODE_TEXTURE_3D) && !RNA_boolean_get(op->ptr, "merged");
965
966         paint_sample_color(C, ar, event->mval[0], event->mval[1], use_sample_texture, false);
967         WM_cursor_modal_set(win, BC_EYEDROPPER_CURSOR);
968
969         WM_event_add_notifier(C, NC_BRUSH | NA_EDITED, brush);
970
971         return OPERATOR_RUNNING_MODAL;
972 }
973
974 static int sample_color_modal(bContext *C, wmOperator *op, const wmEvent *event)
975 {
976         Scene *scene = CTX_data_scene(C);
977         SampleColorData *data = op->customdata;
978         Paint *paint = BKE_paint_get_active_from_context(C);
979         Brush *brush = BKE_paint_brush(paint);
980
981         if ((event->type == data->event_type) && (event->val == KM_RELEASE)) {
982                 if (data->show_cursor) {
983                         paint->flags |= PAINT_SHOW_BRUSH;
984                 }
985
986                 if (data->sample_palette) {
987                         BKE_brush_color_set(scene, brush, data->initcolor);
988                         RNA_boolean_set(op->ptr, "palette", true);
989                 }
990                 WM_cursor_modal_restore(CTX_wm_window(C));
991                 MEM_freeN(data);
992                 ED_workspace_status_text(C, NULL);
993
994                 return OPERATOR_FINISHED;
995         }
996
997         ePaintMode mode = BKE_paintmode_get_active_from_context(C);
998         const bool use_sample_texture = (mode == PAINT_MODE_TEXTURE_3D) && !RNA_boolean_get(op->ptr, "merged");
999
1000         switch (event->type) {
1001                 case MOUSEMOVE:
1002                 {
1003                         ARegion *ar = CTX_wm_region(C);
1004                         RNA_int_set_array(op->ptr, "location", event->mval);
1005                         paint_sample_color(C, ar, event->mval[0], event->mval[1], use_sample_texture, false);
1006                         WM_event_add_notifier(C, NC_BRUSH | NA_EDITED, brush);
1007                         break;
1008                 }
1009
1010                 case LEFTMOUSE:
1011                         if (event->val == KM_PRESS) {
1012                                 ARegion *ar = CTX_wm_region(C);
1013                                 RNA_int_set_array(op->ptr, "location", event->mval);
1014                                 paint_sample_color(C, ar, event->mval[0], event->mval[1], use_sample_texture, true);
1015                                 if (!data->sample_palette) {
1016                                         data->sample_palette = true;
1017                                         sample_color_update_header(data, C);
1018                                 }
1019                                 WM_event_add_notifier(C, NC_BRUSH | NA_EDITED, brush);
1020                         }
1021                         break;
1022         }
1023
1024         return OPERATOR_RUNNING_MODAL;
1025 }
1026
1027 static bool sample_color_poll(bContext *C)
1028 {
1029         return (image_paint_poll_ignore_tool(C) || vertex_paint_poll_ignore_tool(C));
1030 }
1031
1032 void PAINT_OT_sample_color(wmOperatorType *ot)
1033 {
1034         /* identifiers */
1035         ot->name = "Sample Color";
1036         ot->idname = "PAINT_OT_sample_color";
1037         ot->description = "Use the mouse to sample a color in the image";
1038
1039         /* api callbacks */
1040         ot->exec = sample_color_exec;
1041         ot->invoke = sample_color_invoke;
1042         ot->modal = sample_color_modal;
1043         ot->poll = sample_color_poll;
1044
1045         /* flags */
1046         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1047
1048         /* properties */
1049         PropertyRNA *prop;
1050
1051         prop = RNA_def_int_vector(ot->srna, "location", 2, NULL, 0, INT_MAX, "Location", "", 0, 16384);
1052         RNA_def_property_flag(prop, PROP_SKIP_SAVE | PROP_HIDDEN);
1053
1054         RNA_def_boolean(ot->srna, "merged", 0, "Sample Merged", "Sample the output display color");
1055         RNA_def_boolean(ot->srna, "palette", 0, "Add to Palette", "");
1056 }
1057
1058 /******************** texture paint toggle operator ********************/
1059
1060 static bool texture_paint_toggle_poll(bContext *C)
1061 {
1062         Object *ob = CTX_data_active_object(C);
1063         if (ob == NULL || ob->type != OB_MESH)
1064                 return 0;
1065         if (!ob->data || ID_IS_LINKED(ob->data))
1066                 return 0;
1067         if (CTX_data_edit_object(C))
1068                 return 0;
1069
1070         return 1;
1071 }
1072
1073 static int texture_paint_toggle_exec(bContext *C, wmOperator *op)
1074 {
1075         struct wmMsgBus *mbus = CTX_wm_message_bus(C);
1076         Main *bmain = CTX_data_main(C);
1077         Scene *scene = CTX_data_scene(C);
1078         Object *ob = CTX_data_active_object(C);
1079         const int mode_flag = OB_MODE_TEXTURE_PAINT;
1080         const bool is_mode_set = (ob->mode & mode_flag) != 0;
1081
1082         if (!is_mode_set) {
1083                 if (!ED_object_mode_compat_set(C, ob, mode_flag, op->reports)) {
1084                         return OPERATOR_CANCELLED;
1085                 }
1086         }
1087
1088         if (ob->mode & mode_flag) {
1089                 ob->mode &= ~mode_flag;
1090
1091                 if (U.glreslimit != 0)
1092                         GPU_free_images(bmain);
1093                 GPU_paint_set_mipmap(bmain, 1);
1094
1095                 toggle_paint_cursor(C, 0);
1096         }
1097         else {
1098                 bScreen *sc;
1099                 Image *ima = NULL;
1100                 ImagePaintSettings *imapaint = &scene->toolsettings->imapaint;
1101
1102                 /* This has to stay here to regenerate the texture paint
1103                  * cache in case we are loading a file */
1104                 BKE_texpaint_slots_refresh_object(scene, ob);
1105
1106                 BKE_paint_proj_mesh_data_check(scene, ob, NULL, NULL, NULL, NULL);
1107
1108                 /* entering paint mode also sets image to editors */
1109                 if (imapaint->mode == IMAGEPAINT_MODE_MATERIAL) {
1110                         /* set the current material active paint slot on image editor */
1111                         Material *ma = give_current_material(ob, ob->actcol);
1112
1113                         if (ma && ma->texpaintslot)
1114                                 ima = ma->texpaintslot[ma->paint_active_slot].ima;
1115                 }
1116                 else if (imapaint->mode == IMAGEPAINT_MODE_IMAGE) {
1117                         ima = imapaint->canvas;
1118                 }
1119
1120                 if (ima) {
1121                         for (sc = bmain->screen.first; sc; sc = sc->id.next) {
1122                                 ScrArea *sa;
1123                                 for (sa = sc->areabase.first; sa; sa = sa->next) {
1124                                         SpaceLink *sl;
1125                                         for (sl = sa->spacedata.first; sl; sl = sl->next) {
1126                                                 if (sl->spacetype == SPACE_IMAGE) {
1127                                                         SpaceImage *sima = (SpaceImage *)sl;
1128
1129                                                         if (!sima->pin) {
1130                                                                 Object *obedit = CTX_data_edit_object(C);
1131                                                                 ED_space_image_set(bmain, sima, scene, obedit, ima);
1132                                                         }
1133                                                 }
1134                                         }
1135                                 }
1136                         }
1137                 }
1138
1139                 ob->mode |= mode_flag;
1140
1141                 BKE_paint_init(bmain, scene, PAINT_MODE_TEXTURE_3D, PAINT_CURSOR_TEXTURE_PAINT);
1142
1143                 BKE_paint_toolslots_brush_validate(bmain, &imapaint->paint);
1144
1145                 if (U.glreslimit != 0)
1146                         GPU_free_images(bmain);
1147                 GPU_paint_set_mipmap(bmain, 0);
1148
1149                 toggle_paint_cursor(C, 1);
1150         }
1151
1152         Mesh *me = BKE_mesh_from_object(ob);
1153         BLI_assert(me != NULL);
1154         DEG_id_tag_update(&me->id, ID_RECALC_COPY_ON_WRITE);
1155
1156         WM_event_add_notifier(C, NC_SCENE | ND_MODE, scene);
1157
1158         WM_msg_publish_rna_prop(mbus, &ob->id, ob, Object, mode);
1159
1160         WM_toolsystem_update_from_context_view3d(C);
1161
1162         return OPERATOR_FINISHED;
1163 }
1164
1165 void PAINT_OT_texture_paint_toggle(wmOperatorType *ot)
1166 {
1167         /* identifiers */
1168         ot->name = "Texture Paint Toggle";
1169         ot->idname = "PAINT_OT_texture_paint_toggle";
1170         ot->description = "Toggle texture paint mode in 3D view";
1171
1172         /* api callbacks */
1173         ot->exec = texture_paint_toggle_exec;
1174         ot->poll = texture_paint_toggle_poll;
1175
1176         /* flags */
1177         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO | OPTYPE_USE_EVAL_DATA;
1178 }
1179
1180
1181 static int brush_colors_flip_exec(bContext *C, wmOperator *UNUSED(op))
1182 {
1183         Scene *scene = CTX_data_scene(C);
1184         UnifiedPaintSettings *ups = &scene->toolsettings->unified_paint_settings;
1185
1186         ViewLayer *view_layer = CTX_data_view_layer(C);
1187         Paint *paint = BKE_paint_get_active(scene, view_layer);
1188         Brush *br = BKE_paint_brush(paint);
1189
1190         if (ups->flag & UNIFIED_PAINT_COLOR) {
1191                 swap_v3_v3(ups->rgb, ups->secondary_rgb);
1192         }
1193         else if (br) {
1194                 swap_v3_v3(br->rgb, br->secondary_rgb);
1195         }
1196         WM_event_add_notifier(C, NC_BRUSH | NA_EDITED, br);
1197
1198         return OPERATOR_FINISHED;
1199 }
1200
1201 static bool brush_colors_flip_poll(bContext *C)
1202 {
1203         if (image_paint_poll(C)) {
1204                 Brush *br = image_paint_brush(C);
1205                 if (br->imagepaint_tool == PAINT_TOOL_DRAW)
1206                         return true;
1207         }
1208         else {
1209                 Object *ob = CTX_data_active_object(C);
1210                 if (ob != NULL) {
1211                         if (ob->mode & (OB_MODE_VERTEX_PAINT | OB_MODE_TEXTURE_PAINT)) {
1212                                 return true;
1213                         }
1214                 }
1215         }
1216         return false;
1217 }
1218
1219 void PAINT_OT_brush_colors_flip(wmOperatorType *ot)
1220 {
1221         /* identifiers */
1222         ot->name = "Brush Colors Flip";
1223         ot->idname = "PAINT_OT_brush_colors_flip";
1224         ot->description = "Toggle foreground and background brush colors";
1225
1226         /* api callbacks */
1227         ot->exec = brush_colors_flip_exec;
1228         ot->poll = brush_colors_flip_poll;
1229
1230         /* flags */
1231         ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
1232 }
1233
1234
1235 void ED_imapaint_bucket_fill(struct bContext *C, float color[3], wmOperator *op)
1236 {
1237         wmWindowManager *wm = CTX_wm_manager(C);
1238         SpaceImage *sima = CTX_wm_space_image(C);
1239         Image *ima = sima->image;
1240
1241         BKE_undosys_step_push_init_with_type(wm->undo_stack, C, op->type->name, BKE_UNDOSYS_TYPE_IMAGE);
1242
1243         ED_image_undo_push_begin(op->type->name);
1244
1245         paint_2d_bucket_fill(C, color, NULL, NULL, NULL);
1246
1247         BKE_undosys_step_push(wm->undo_stack, C, op->type->name);
1248
1249         DEG_id_tag_update(&ima->id, 0);
1250 }
1251
1252
1253 static bool texture_paint_poll(bContext *C)
1254 {
1255         if (texture_paint_toggle_poll(C))
1256                 if (CTX_data_active_object(C)->mode & OB_MODE_TEXTURE_PAINT)
1257                         return 1;
1258
1259         return 0;
1260 }
1261
1262 bool image_texture_paint_poll(bContext *C)
1263 {
1264         return (texture_paint_poll(C) || image_paint_poll(C));
1265 }
1266
1267 bool facemask_paint_poll(bContext *C)
1268 {
1269         return BKE_paint_select_face_test(CTX_data_active_object(C));
1270 }
1271
1272 bool vert_paint_poll(bContext *C)
1273 {
1274         return BKE_paint_select_vert_test(CTX_data_active_object(C));
1275 }
1276
1277 bool mask_paint_poll(bContext *C)
1278 {
1279         return BKE_paint_select_elem_test(CTX_data_active_object(C));
1280 }