Merge from 2.5 r20991 through r21037
[blender.git] / source / blender / editors / sculpt_paint / sculpt.c
1 /*
2  * $Id: sculptmode.c 18309 2009-01-04 07:47:11Z nicholasbishop $
3  *
4  * ***** BEGIN GPL LICENSE BLOCK *****
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2
9  * of the License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software  Foundation,
18  * Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
19  *
20  * The Original Code is Copyright (C) 2006 by Nicholas Bishop
21  * All rights reserved.
22  *
23  * The Original Code is: all of this file.
24  *
25  * Contributor(s): none yet.
26  *
27  * ***** END GPL LICENSE BLOCK *****
28  *
29  * Implements the Sculpt Mode tools
30  *
31  */
32
33 #include "MEM_guardedalloc.h"
34
35 #include "BLI_arithb.h"
36 #include "BLI_blenlib.h"
37 #include "BLI_dynstr.h"
38
39 #include "DNA_armature_types.h"
40 #include "DNA_brush_types.h"
41 #include "DNA_image_types.h"
42 #include "DNA_key_types.h"
43 #include "DNA_mesh_types.h"
44 #include "DNA_meshdata_types.h"
45 #include "DNA_modifier_types.h"
46 #include "DNA_object_types.h"
47 #include "DNA_screen_types.h"
48 #include "DNA_scene_types.h"
49 #include "DNA_texture_types.h"
50 #include "DNA_view3d_types.h"
51 #include "DNA_userdef_types.h"
52 #include "DNA_color_types.h"
53
54 #include "BKE_brush.h"
55 #include "BKE_context.h"
56 #include "BKE_customdata.h"
57 #include "BKE_DerivedMesh.h"
58 #include "BKE_depsgraph.h"
59 #include "BKE_global.h"
60 #include "BKE_image.h"
61 #include "BKE_key.h"
62 #include "BKE_library.h"
63 #include "BKE_main.h"
64 #include "BKE_mesh.h"
65 #include "BKE_modifier.h"
66 #include "BKE_multires.h"
67 #include "BKE_sculpt.h"
68 #include "BKE_texture.h"
69 #include "BKE_utildefines.h"
70 #include "BKE_colortools.h"
71
72 #include "BIF_gl.h"
73 #include "BIF_glutil.h"
74
75 #include "WM_api.h"
76 #include "WM_types.h"
77 #include "ED_screen.h"
78 #include "ED_sculpt.h"
79 #include "ED_space_api.h"
80 #include "ED_util.h"
81 #include "ED_view3d.h"
82 #include "sculpt_intern.h"
83
84 #include "RNA_access.h"
85 #include "RNA_define.h"
86
87 #include "IMB_imbuf_types.h"
88
89 #include "RE_render_ext.h"
90 #include "RE_shader_ext.h" /*for multitex_ext*/
91
92 #include "GPU_draw.h"
93
94 #include <math.h>
95 #include <stdlib.h>
96 #include <string.h>
97
98 /* Number of vertices to average in order to determine the flatten distance */
99 #define FLATTEN_SAMPLE_SIZE 10
100
101 /* ===== STRUCTS =====
102  *
103  */
104
105 /* ActiveData stores an Index into the mvert array of Mesh, plus Fade, which
106    stores how far the vertex is from the brush center, scaled to the range [0,1]. */
107 typedef struct ActiveData {
108         struct ActiveData *next, *prev;
109         unsigned int Index;
110         float Fade;
111         float dist;
112 } ActiveData;
113
114 typedef enum StrokeFlags {
115         CLIP_X = 1,
116         CLIP_Y = 2,
117         CLIP_Z = 4
118 } StrokeFlags;
119
120 /* Cache stroke properties. Used because
121    RNA property lookup isn't particularly fast.
122
123    For descriptions of these settings, check the operator properties.
124 */
125 typedef struct StrokeCache {
126         /* Invariants */
127         float radius;
128         float scale[3];
129         int flag;
130         float clip_tolerance[3];
131         int initial_mouse[2];
132         float depth;
133
134         /* Variants */
135         float true_location[3];
136         float location[3];
137         float flip;
138         float pressure;
139         int mouse[2];
140
141         /* The rest is temporary storage that isn't saved as a property */
142
143         int first_time; /* Beginning of stroke may do some things special */
144
145         ViewContext vc;
146         bglMats *mats;
147
148         float *layer_disps; /* Displacements for each vertex */
149         float (*mesh_store)[3]; /* Copy of the mesh vertices' locations */
150         short (*orig_norms)[3]; /* Copy of the mesh vertices' normals */
151         float rotation; /* Texture rotation (radians) for anchored and rake modes */
152         int pixel_radius, previous_pixel_radius;
153         ListBase grab_active_verts[8]; /* The same list of verts is used throught grab stroke */
154         float grab_delta[3], grab_delta_symmetry[3];
155         float old_grab_location[3];
156         int symmetry; /* Symmetry index between 0 and 7 */
157         float view_normal[3], view_normal_symmetry[3];
158         int last_dot[2]; /* Last location of stroke application */
159         int last_rake[2]; /* Last location of updating rake rotation */
160 } StrokeCache;
161
162 typedef struct RectNode {
163         struct RectNode *next, *prev;
164         rcti r;
165 } RectNode;
166
167 /* Used to store to 2D screen coordinates of each vertex in the mesh. */
168 typedef struct ProjVert {
169         short co[2];
170         
171         /* Used to mark whether a vertex is inside a rough bounding box
172            containing the brush. */
173         char inside;
174 } ProjVert;
175
176 /* ===== OPENGL =====
177  *
178  * Simple functions to get data from the GL
179  */
180
181 /* Uses window coordinates (x,y) and depth component z to find a point in
182    modelspace */
183 static void unproject(bglMats *mats, float out[3], const short x, const short y, const float z)
184 {
185         double ux, uy, uz;
186
187         gluUnProject(x,y,z, mats->modelview, mats->projection,
188                      (GLint *)mats->viewport, &ux, &uy, &uz );
189         out[0] = ux;
190         out[1] = uy;
191         out[2] = uz;
192 }
193
194 /* Convert a point in model coordinates to 2D screen coordinates. */
195 static void projectf(bglMats *mats, const float v[3], float p[2])
196 {
197         double ux, uy, uz;
198
199         gluProject(v[0],v[1],v[2], mats->modelview, mats->projection,
200                    (GLint *)mats->viewport, &ux, &uy, &uz);
201         p[0]= ux;
202         p[1]= uy;
203 }
204
205 static void project(bglMats *mats, const float v[3], short p[2])
206 {
207         float f[2];
208         projectf(mats, v, f);
209
210         p[0]= f[0];
211         p[1]= f[1];
212 }
213
214 /* ===== Sculpting =====
215  *
216  */
217
218 /* Return modified brush size. Uses current tablet pressure (if available) to
219    shrink the brush. Skipped for grab brush because only the first mouse down
220    size is used, which is small if the user has just touched the pen to the
221    tablet */
222 static char brush_size(Sculpt *sd)
223 {
224         float size= sd->brush->size;
225         
226         if((sd->brush->sculpt_tool != SCULPT_TOOL_GRAB) && (sd->brush->flag & BRUSH_SIZE_PRESSURE))
227                 size *= sd->session->cache->pressure;
228
229         return size;
230 }
231
232 /* Return modified brush strength. Includes the direction of the brush, positive
233    values pull vertices, negative values push. Uses tablet pressure and a
234    special multiplier found experimentally to scale the strength factor. */
235 static float brush_strength(Sculpt *sd, StrokeCache *cache)
236 {
237         /* Primary strength input; square it to make lower values more sensitive */
238         float alpha = sd->brush->alpha * sd->brush->alpha;
239
240         float dir= sd->brush->flag & BRUSH_DIR_IN ? -1 : 1;
241         float pressure= 1;
242         float flip= cache->flip ? -1:1;
243         float anchored = sd->brush->flag & BRUSH_ANCHORED ? 25 : 1;
244
245         if(sd->brush->flag & BRUSH_ALPHA_PRESSURE)
246                 pressure *= cache->pressure;
247         
248         switch(sd->brush->sculpt_tool){
249         case SCULPT_TOOL_DRAW:
250         case SCULPT_TOOL_INFLATE:
251                 return alpha * dir * pressure * flip; /*XXX: not sure why? was multiplied by G.vd->grid */;
252         case SCULPT_TOOL_FLATTEN:
253         case SCULPT_TOOL_SMOOTH:
254                 return alpha * 4 * pressure;
255         case SCULPT_TOOL_PINCH:
256                 return alpha / 2 * dir * pressure * flip;
257         case SCULPT_TOOL_GRAB:
258                 return 1;
259         case SCULPT_TOOL_LAYER:
260                 return sd->brush->alpha / 50.0f * dir * pressure * flip * anchored; /*XXX: not sure why? multiplied by G.vd->grid */;
261         default:
262                 return 0;
263         }
264 }
265
266 /* For clipping against a mirror modifier */
267 static void sculpt_clip(StrokeCache *cache, float *co, const float val[3])
268 {
269         int i;
270         for(i=0; i<3; ++i) {
271                 if((cache->flag & (CLIP_X << i)) && (fabs(co[i]) <= cache->clip_tolerance[i]))
272                         co[i]= 0.0f;
273                 else
274                         co[i]= val[i];
275         }               
276 }
277
278 static void sculpt_axislock(Sculpt *sd, float *co)
279 {
280         if(sd->flags == (SCULPT_LOCK_X|SCULPT_LOCK_Y|SCULPT_LOCK_Z))
281                 return;
282
283         if(sd->session->cache->vc.v3d->twmode == V3D_MANIP_LOCAL) {
284                 float mat[3][3], imat[3][3];
285                 Mat3CpyMat4(mat, sd->session->cache->vc.obact->obmat);
286                 Mat3Inv(imat, mat);
287                 Mat3MulVecfl(mat, co);
288                 if (sd->flags & SCULPT_LOCK_X) co[0] = 0.0;
289                 if (sd->flags & SCULPT_LOCK_Y) co[1] = 0.0;
290                 if (sd->flags & SCULPT_LOCK_Z) co[2] = 0.0;             
291                 Mat3MulVecfl(imat, co);
292         } else {
293                 if (sd->flags & SCULPT_LOCK_X) co[0] = 0.0;
294                 if (sd->flags & SCULPT_LOCK_Y) co[1] = 0.0;
295                 if (sd->flags & SCULPT_LOCK_Z) co[2] = 0.0;             
296         }
297 }
298
299 static void add_norm_if(float view_vec[3], float out[3], float out_flip[3], const short no[3])
300 {
301         float fno[3] = {no[0], no[1], no[2]};
302
303         Normalize(fno);
304
305         if((Inpf(view_vec, fno)) > 0) {
306                 VecAddf(out, out, fno);
307         } else {
308                 VecAddf(out_flip, out_flip, fno); /* out_flip is used when out is {0,0,0} */
309         }
310 }
311
312 /* Currently only for the draw brush; finds average normal for all active
313    vertices */
314 static void calc_area_normal(Sculpt *sd, float out[3], const ListBase* active_verts)
315 {
316         StrokeCache *cache = sd->session->cache;
317         ActiveData *node = active_verts->first;
318         const int view = 0; /* XXX: should probably be a flag, not number: sd->brush_type==SCULPT_TOOL_DRAW ? sculptmode_brush()->view : 0; */
319         float out_flip[3];
320         float *out_dir = cache->view_normal_symmetry;
321         
322         out[0]=out[1]=out[2] = out_flip[0]=out_flip[1]=out_flip[2] = 0;
323
324         if(sd->brush->flag & BRUSH_ANCHORED) {
325                 for(; node; node = node->next)
326                         add_norm_if(out_dir, out, out_flip, cache->orig_norms[node->Index]);
327         }
328         else {
329                 for(; node; node = node->next)
330                         add_norm_if(out_dir, out, out_flip, sd->session->mvert[node->Index].no);
331         }
332
333         if (out[0]==0.0 && out[1]==0.0 && out[2]==0.0) {
334                 VECCOPY(out, out_flip);
335         }
336         
337         Normalize(out);
338
339         if(out_dir) {
340                 out[0] = out_dir[0] * view + out[0] * (10-view);
341                 out[1] = out_dir[1] * view + out[1] * (10-view);
342                 out[2] = out_dir[2] * view + out[2] * (10-view);
343         }
344         
345         Normalize(out);
346 }
347
348 static void do_draw_brush(Sculpt *sd, SculptSession *ss, const ListBase* active_verts)
349 {
350         float area_normal[3];
351         ActiveData *node= active_verts->first;
352
353         calc_area_normal(sd, area_normal, active_verts);
354         
355         sculpt_axislock(sd, area_normal);
356         
357         while(node){
358                 float *co= ss->mvert[node->Index].co;
359
360                 const float val[3]= {co[0]+area_normal[0]*ss->cache->radius*node->Fade*ss->cache->scale[0],
361                                      co[1]+area_normal[1]*ss->cache->radius*node->Fade*ss->cache->scale[1],
362                                      co[2]+area_normal[2]*ss->cache->radius*node->Fade*ss->cache->scale[2]};
363                                      
364                 sculpt_clip(ss->cache, co, val);
365                 
366                 node= node->next;
367         }
368 }
369
370 /* For the smooth brush, uses the neighboring vertices around vert to calculate
371    a smoothed location for vert. Skips corner vertices (used by only one
372    polygon.) */
373 static void neighbor_average(SculptSession *ss, float avg[3], const int vert)
374 {
375         int i, skip= -1, total=0;
376         IndexNode *node= ss->fmap[vert].first;
377         char ncount= BLI_countlist(&ss->fmap[vert]);
378         MFace *f;
379
380         avg[0] = avg[1] = avg[2] = 0;
381                 
382         /* Don't modify corner vertices */
383         if(ncount==1) {
384                 VecCopyf(avg, ss->mvert[vert].co);
385                 return;
386         }
387
388         while(node){
389                 f= &ss->mface[node->index];
390                 
391                 if(f->v4) {
392                         skip= (f->v1==vert?2:
393                                f->v2==vert?3:
394                                f->v3==vert?0:
395                                f->v4==vert?1:-1);
396                 }
397
398                 for(i=0; i<(f->v4?4:3); ++i) {
399                         if(i != skip && (ncount!=2 || BLI_countlist(&ss->fmap[(&f->v1)[i]]) <= 2)) {
400                                 VecAddf(avg, avg, ss->mvert[(&f->v1)[i]].co);
401                                 ++total;
402                         }
403                 }
404
405                 node= node->next;
406         }
407
408         if(total>0)
409                 VecMulf(avg, 1.0f / total);
410         else
411                 VecCopyf(avg, ss->mvert[vert].co);
412 }
413
414 static void do_smooth_brush(SculptSession *ss, const ListBase* active_verts)
415 {
416         ActiveData *node= active_verts->first;
417         int i;
418         
419         for(i = 0; i < 2; ++i) {
420                 while(node){
421                         float *co= ss->mvert[node->Index].co;
422                         float avg[3], val[3];
423                         
424                         neighbor_average(ss, avg, node->Index);
425                         val[0] = co[0]+(avg[0]-co[0])*node->Fade;
426                         val[1] = co[1]+(avg[1]-co[1])*node->Fade;
427                         val[2] = co[2]+(avg[2]-co[2])*node->Fade;
428                         
429                         sculpt_clip(ss->cache, co, val);
430                         node= node->next;
431                 }
432         }
433 }
434
435 static void do_pinch_brush(SculptSession *ss, const ListBase* active_verts)
436 {
437         ActiveData *node= active_verts->first;
438
439         while(node) {
440                 float *co= ss->mvert[node->Index].co;
441                 const float val[3]= {co[0]+(ss->cache->location[0]-co[0])*node->Fade,
442                                      co[1]+(ss->cache->location[1]-co[1])*node->Fade,
443                                      co[2]+(ss->cache->location[2]-co[2])*node->Fade};
444                 sculpt_clip(ss->cache, co, val);
445                 node= node->next;
446         }
447 }
448
449 static void do_grab_brush(Sculpt *sd, SculptSession *ss)
450 {
451         ActiveData *node= ss->cache->grab_active_verts[ss->cache->symmetry].first;
452         float add[3];
453         float grab_delta[3];
454         
455         VecCopyf(grab_delta, ss->cache->grab_delta_symmetry);
456         sculpt_axislock(sd, grab_delta);
457         
458         while(node) {
459                 float *co= ss->mvert[node->Index].co;
460                 
461                 VecCopyf(add, grab_delta);
462                 VecMulf(add, node->Fade);
463                 VecAddf(add, add, co);
464                 sculpt_clip(ss->cache, co, add);
465
466                 node= node->next;
467         }
468         
469 }
470
471 static void do_layer_brush(Sculpt *sd, SculptSession *ss, const ListBase *active_verts)
472 {
473         float area_normal[3];
474         ActiveData *node= active_verts->first;
475         float lim= brush_strength(sd, ss->cache);
476
477         if(sd->brush->flag & BRUSH_DIR_IN)
478                 lim = -lim;
479
480         calc_area_normal(sd, area_normal, active_verts);
481
482         while(node){
483                 float *disp= &ss->cache->layer_disps[node->Index];
484                 
485                 if((lim > 0 && *disp < lim) ||
486                    (lim < 0 && *disp > lim)) {
487                         float *co= ss->mvert[node->Index].co;
488                         float val[3];
489                         
490                         *disp+= node->Fade;
491
492                         if(lim < 0 && *disp < lim)
493                                 *disp = lim;
494                         else if(lim > 0 && *disp > lim)
495                                         *disp = lim;
496
497                         val[0] = ss->cache->mesh_store[node->Index][0]+area_normal[0] * *disp*ss->cache->scale[0];
498                         val[1] = ss->cache->mesh_store[node->Index][1]+area_normal[1] * *disp*ss->cache->scale[1];
499                         val[2] = ss->cache->mesh_store[node->Index][2]+area_normal[2] * *disp*ss->cache->scale[2];
500                         //VecMulf(val, ss->cache->radius);
501                         sculpt_clip(ss->cache, co, val);
502                 }
503
504                 node= node->next;
505         }
506 }
507
508 static void do_inflate_brush(SculptSession *ss, const ListBase *active_verts)
509 {
510         ActiveData *node= active_verts->first;
511         float add[3];
512         
513         while(node) {
514                 float *co= ss->mvert[node->Index].co;
515                 short *no= ss->mvert[node->Index].no;
516
517                 add[0]= no[0]/ 32767.0f;
518                 add[1]= no[1]/ 32767.0f;
519                 add[2]= no[2]/ 32767.0f;
520                 VecMulf(add, node->Fade * ss->cache->radius);
521                 add[0]*= ss->cache->scale[0];
522                 add[1]*= ss->cache->scale[1];
523                 add[2]*= ss->cache->scale[2];
524                 VecAddf(add, add, co);
525                 
526                 sculpt_clip(ss->cache, co, add);
527
528                 node= node->next;
529         }
530 }
531
532 static void calc_flatten_center(SculptSession *ss, ActiveData *node, float co[3])
533 {
534         ActiveData *outer[FLATTEN_SAMPLE_SIZE];
535         int i;
536         
537         for(i = 0; i < FLATTEN_SAMPLE_SIZE; ++i)
538                 outer[i] = node;
539                 
540         for(; node; node = node->next) {
541                 for(i = 0; i < FLATTEN_SAMPLE_SIZE; ++i) {
542                         if(node->dist > outer[i]->dist) {
543                                 outer[i] = node;
544                                 break;
545                         }
546                 }
547         }
548         
549         co[0] = co[1] = co[2] = 0.0f;
550         for(i = 0; i < FLATTEN_SAMPLE_SIZE; ++i)
551                 VecAddf(co, co, ss->mvert[outer[i]->Index].co);
552         VecMulf(co, 1.0f / FLATTEN_SAMPLE_SIZE);
553 }
554
555 static void do_flatten_brush(Sculpt *sd, SculptSession *ss, const ListBase *active_verts)
556 {
557         ActiveData *node= active_verts->first;
558         /* area_normal and cntr define the plane towards which vertices are squashed */
559         float area_normal[3];
560         float cntr[3];
561
562         calc_area_normal(sd, area_normal, active_verts);
563         calc_flatten_center(ss, node, cntr);
564
565         while(node){
566                 float *co= ss->mvert[node->Index].co;
567                 float p1[3], sub1[3], sub2[3], intr[3], val[3];
568                 
569                 /* Find the intersection between squash-plane and vertex (along the area normal) */
570                 VecSubf(p1, co, area_normal);
571                 VecSubf(sub1, cntr, p1);
572                 VecSubf(sub2, co, p1);
573                 VecSubf(intr, co, p1);
574                 VecMulf(intr, Inpf(area_normal, sub1) / Inpf(area_normal, sub2));
575                 VecAddf(intr, intr, p1);
576                 
577                 VecSubf(val, intr, co);
578                 VecMulf(val, node->Fade);
579                 VecAddf(val, val, co);
580                 
581                 sculpt_clip(ss->cache, co, val);
582                 
583                 node= node->next;
584         }
585 }
586
587
588 /* Uses symm to selectively flip any axis of a coordinate. */
589 static void flip_coord(float out[3], float in[3], const char symm)
590 {
591         if(symm & SCULPT_SYMM_X)
592                 out[0]= -in[0];
593         else
594                 out[0]= in[0];
595         if(symm & SCULPT_SYMM_Y)
596                 out[1]= -in[1];
597         else
598                 out[1]= in[1];
599         if(symm & SCULPT_SYMM_Z)
600                 out[2]= -in[2];
601         else
602                 out[2]= in[2];
603 }
604
605 /* Get a pixel from the texcache at (px, py) */
606 static unsigned char get_texcache_pixel(const SculptSession *ss, int px, int py)
607 {
608         unsigned *p;
609         p = ss->texcache + py * ss->texcache_side + px;
610         return ((unsigned char*)(p))[0];
611 }
612
613 static float get_texcache_pixel_bilinear(const SculptSession *ss, float u, float v)
614 {
615         int x, y, x2, y2;
616         const int tc_max = ss->texcache_side - 1;
617         float urat, vrat, uopp;
618
619         if(u < 0) u = 0;
620         else if(u >= ss->texcache_side) u = tc_max;
621         if(v < 0) v = 0;
622         else if(v >= ss->texcache_side) v = tc_max;
623
624         x = floor(u);
625         y = floor(v);
626         x2 = x + 1;
627         y2 = y + 1;
628
629         if(x2 > ss->texcache_side) x2 = tc_max;
630         if(y2 > ss->texcache_side) y2 = tc_max;
631         
632         urat = u - x;
633         vrat = v - y;
634         uopp = 1 - urat;
635                 
636         return ((get_texcache_pixel(ss, x, y) * uopp +
637                  get_texcache_pixel(ss, x2, y) * urat) * (1 - vrat) + 
638                 (get_texcache_pixel(ss, x, y2) * uopp +
639                  get_texcache_pixel(ss, x2, y2) * urat) * vrat) / 255.0;
640 }
641
642 /* Return a multiplier for brush strength on a particular vertex. */
643 static float tex_strength(Sculpt *sd, float *point, const float len)
644 {
645         SculptSession *ss= sd->session;
646         Brush *br = sd->brush;
647         float avg= 1;
648
649         if(br->texact==-1 || !br->mtex[br->texact])
650                 avg= 1;
651         else if(br->tex_mode==BRUSH_TEX_3D) {
652                 /* Get strength by feeding the vertex location directly
653                    into a texture */
654                 float jnk;
655                 const float factor= 0.01;
656                 MTex mtex;
657                 memset(&mtex,0,sizeof(MTex));
658                 mtex.tex= br->mtex[br->texact]->tex;
659                 mtex.projx= 1;
660                 mtex.projy= 2;
661                 mtex.projz= 3;
662                 VecCopyf(mtex.size, br->mtex[br->texact]->size);
663                 VecMulf(mtex.size, factor);
664                 if(!sd->texsep)
665                         mtex.size[1]= mtex.size[2]= mtex.size[0];
666                 
667                 externtex(&mtex,point,&avg,&jnk,&jnk,&jnk,&jnk);
668         }
669         else if(ss->texcache) {
670                 const float bsize= ss->cache->pixel_radius * 2;
671                 const float rot= sd->brush->rot + ss->cache->rotation;
672                 int px, py;
673                 float flip[3], point_2d[2];
674
675                 /* If the active area is being applied for symmetry, flip it
676                    across the symmetry axis in order to project it. This insures
677                    that the brush texture will be oriented correctly. */
678                 VecCopyf(flip, point);
679                 flip_coord(flip, flip, ss->cache->symmetry);
680                 projectf(ss->cache->mats, flip, point_2d);
681
682                 /* For Tile and Drag modes, get the 2D screen coordinates of the
683                    and scale them up or down to the texture size. */
684                 if(br->tex_mode==BRUSH_TEX_TILE) {
685                         const int sx= (const int)br->mtex[br->texact]->size[0];
686                         const int sy= (const int)sd->texsep ? br->mtex[br->texact]->size[1] : sx;
687                         
688                         float fx= point_2d[0];
689                         float fy= point_2d[1];
690                         
691                         float angle= atan2(fy, fx) - rot;
692                         float flen= sqrtf(fx*fx + fy*fy);
693                         
694                         if(rot<0.001 && rot>-0.001) {
695                                 px= point_2d[0];
696                                 py= point_2d[1];
697                         } else {
698                                 px= flen * cos(angle) + 2000;
699                                 py= flen * sin(angle) + 2000;
700                         }
701                         if(sx != 1)
702                                 px %= sx-1;
703                         if(sy != 1)
704                                 py %= sy-1;
705                         avg= get_texcache_pixel_bilinear(ss, ss->texcache_side*px/sx, ss->texcache_side*py/sy);
706                 } else {
707                         float fx= (point_2d[0] - ss->cache->mouse[0]) / bsize;
708                         float fy= (point_2d[1] - ss->cache->mouse[1]) / bsize;
709
710                         float angle= atan2(fy, fx) - rot;
711                         float flen= sqrtf(fx*fx + fy*fy);
712                         
713                         fx = flen * cos(angle) + 0.5;
714                         fy = flen * sin(angle) + 0.5;
715
716                         avg= get_texcache_pixel_bilinear(ss, fx * ss->texcache_side, fy * ss->texcache_side);
717                 }
718         }
719
720         avg*= brush_curve_strength(sd->brush, len, ss->cache->radius); /* Falloff curve */
721
722         return avg;
723 }
724
725 /* Mark area around the brush as damaged. projverts are marked if they are
726    inside the area and the damaged rectangle in 2D screen coordinates is 
727    added to damaged_rects. */
728 static void sculpt_add_damaged_rect(SculptSession *ss)
729 {
730         short p[2];
731         RectNode *rn= MEM_mallocN(sizeof(RectNode),"RectNode");
732         const float radius = MAX2(ss->cache->pixel_radius, ss->cache->previous_pixel_radius);
733         unsigned i;
734
735         /* Find center */
736         project(ss->cache->mats, ss->cache->location, p);
737         rn->r.xmin= p[0] - radius;
738         rn->r.ymin= p[1] - radius;
739         rn->r.xmax= p[0] + radius;
740         rn->r.ymax= p[1] + radius;
741
742         BLI_addtail(&ss->damaged_rects, rn);
743
744         /* Update insides */
745         for(i=0; i<ss->totvert; ++i) {
746                 if(!ss->projverts[i].inside) {
747                         if(ss->projverts[i].co[0] > rn->r.xmin && ss->projverts[i].co[1] > rn->r.ymin &&
748                            ss->projverts[i].co[0] < rn->r.xmax && ss->projverts[i].co[1] < rn->r.ymax) {
749                                 ss->projverts[i].inside= 1;
750                         }
751                 }
752                 // XXX: remember to fix this!
753                 // temporary pass
754                 ss->projverts[i].inside = 1;
755         }
756 }
757
758 /* Clears the depth buffer in each modified area. */
759 #if 0
760 static void sculpt_clear_damaged_areas(SculptSession *ss)
761 {
762         RectNode *rn= NULL;
763
764         for(rn = ss->damaged_rects.first; rn; rn = rn->next) {
765                 rcti clp = rn->r;
766                 rcti *win = NULL; /*XXX: &curarea->winrct; */
767                 
768                 clp.xmin += win->xmin;
769                 clp.xmax += win->xmin;
770                 clp.ymin += win->ymin;
771                 clp.ymax += win->ymin;
772                 
773                 if(clp.xmin < win->xmax && clp.xmax > win->xmin &&
774                    clp.ymin < win->ymax && clp.ymax > win->ymin) {
775                         if(clp.xmin < win->xmin) clp.xmin = win->xmin;
776                         if(clp.ymin < win->ymin) clp.ymin = win->ymin;
777                         if(clp.xmax > win->xmax) clp.xmax = win->xmax;
778                         if(clp.ymax > win->ymax) clp.ymax = win->ymax;
779
780                         glScissor(clp.xmin + 1, clp.ymin + 1,
781                                   clp.xmax - clp.xmin - 2,
782                                   clp.ymax - clp.ymin - 2);
783                 }
784                 
785                 glClear(GL_DEPTH_BUFFER_BIT);
786         }
787 }
788 #endif
789 static void do_brush_action(Sculpt *sd, StrokeCache *cache)
790 {
791         SculptSession *ss = sd->session;
792         float av_dist;
793         ListBase active_verts={0,0};
794         ListBase *grab_active_verts = &ss->cache->grab_active_verts[ss->cache->symmetry];
795         ActiveData *adata= 0;
796         float *vert;
797         Mesh *me= NULL; /*XXX: get_mesh(OBACT); */
798         const float bstrength= brush_strength(sd, cache);
799         KeyBlock *keyblock= NULL; /*XXX: ob_get_keyblock(OBACT); */
800         Brush *b = sd->brush;
801         int i;
802
803         sculpt_add_damaged_rect(ss);
804
805         /* Build a list of all vertices that are potentially within the brush's
806            area of influence. Only do this once for the grab brush. */
807         if((b->sculpt_tool != SCULPT_TOOL_GRAB) || cache->first_time) {
808                 for(i=0; i<ss->totvert; ++i) {
809                         /* Projverts.inside provides a rough bounding box */
810                         if(ss->multires || ss->projverts[i].inside) {
811                                 //vert= ss->vertexcosnos ? &ss->vertexcosnos[i*6] : a->verts[i].co;
812                                 vert= ss->mvert[i].co;
813                                 av_dist= VecLenf(ss->cache->location, vert);
814                                 if(av_dist < cache->radius) {
815                                         adata= (ActiveData*)MEM_mallocN(sizeof(ActiveData), "ActiveData");
816
817                                         adata->Index = i;
818                                         /* Fade is used to store the final strength at which the brush
819                                            should modify a particular vertex. */
820                                         adata->Fade= tex_strength(sd, vert, av_dist) * bstrength;
821                                         adata->dist = av_dist;
822
823                                         if(b->sculpt_tool == SCULPT_TOOL_GRAB && cache->first_time)
824                                                 BLI_addtail(grab_active_verts, adata);
825                                         else
826                                                 BLI_addtail(&active_verts, adata);
827                                 }
828                         }
829                 }
830         }
831
832         /* Only act if some verts are inside the brush area */
833         if(active_verts.first || (b->sculpt_tool == SCULPT_TOOL_GRAB && grab_active_verts->first)) {
834                 /* Apply one type of brush action */
835                 switch(b->sculpt_tool){
836                 case SCULPT_TOOL_DRAW:
837                         do_draw_brush(sd, ss, &active_verts);
838                         break;
839                 case SCULPT_TOOL_SMOOTH:
840                         do_smooth_brush(ss, &active_verts);
841                         break;
842                 case SCULPT_TOOL_PINCH:
843                         do_pinch_brush(ss, &active_verts);
844                         break;
845                 case SCULPT_TOOL_INFLATE:
846                         do_inflate_brush(ss, &active_verts);
847                         break;
848                 case SCULPT_TOOL_GRAB:
849                         do_grab_brush(sd, ss);
850                         break;
851                 case SCULPT_TOOL_LAYER:
852                         do_layer_brush(sd, ss, &active_verts);
853                         break;
854                 case SCULPT_TOOL_FLATTEN:
855                         do_flatten_brush(sd, ss, &active_verts);
856                         break;
857                 }
858         
859                 /* Copy the modified vertices from mesh to the active key */
860                 if(keyblock && !ss->multires) {
861                         float *co= keyblock->data;
862                         if(co) {
863                                 if(b->sculpt_tool == SCULPT_TOOL_GRAB)
864                                         adata = grab_active_verts->first;
865                                 else
866                                         adata = active_verts.first;
867
868                                 for(; adata; adata= adata->next)
869                                         if(adata->Index < keyblock->totelem)
870                                                 VecCopyf(&co[adata->Index*3], me->mvert[adata->Index].co);
871                         }
872                 }
873
874                 if(ss->vertexcosnos && !ss->multires)
875                         BLI_freelistN(&active_verts);
876                 else {
877                         if(b->sculpt_tool != SCULPT_TOOL_GRAB)
878                                 addlisttolist(&ss->damaged_verts, &active_verts);
879                 }
880         }
881 }
882
883 /* Flip all the editdata across the axis/axes specified by symm. Used to
884    calculate multiple modifications to the mesh when symmetry is enabled. */
885 static void calc_brushdata_symm(StrokeCache *cache, const char symm)
886 {
887         flip_coord(cache->location, cache->true_location, symm);
888         flip_coord(cache->view_normal_symmetry, cache->view_normal, symm);
889         flip_coord(cache->grab_delta_symmetry, cache->grab_delta, symm);
890         cache->symmetry= symm;
891 }
892
893 static void do_symmetrical_brush_actions(Sculpt *sd, StrokeCache *cache)
894 {
895         const char symm = sd->flags & 7;
896         int i;
897
898         /* Brush spacing: only apply dot if next dot is far enough away */
899         if((sd->brush->flag & BRUSH_SPACE) && !(sd->brush->flag & BRUSH_ANCHORED) && !cache->first_time) {
900                 int dx = cache->last_dot[0] - cache->mouse[0];
901                 int dy = cache->last_dot[1] - cache->mouse[1];
902                 if(sqrt(dx*dx+dy*dy) < sd->brush->spacing)
903                         return;
904         }
905         memcpy(cache->last_dot, cache->mouse, sizeof(int) * 2);
906
907         VecCopyf(cache->location, cache->true_location);
908         VecCopyf(cache->grab_delta_symmetry, cache->grab_delta);
909         cache->symmetry = 0;
910         do_brush_action(sd, cache);
911
912         for(i = 1; i <= symm; ++i) {
913                 if(symm & i && (symm != 5 || i != 3) && (symm != 6 || (i != 3 && i != 5))) {
914                         calc_brushdata_symm(cache, i);
915                         do_brush_action(sd, cache);
916                 }
917         }
918
919         cache->first_time = 0;
920 }
921
922 static void add_face_normal(vec3f *norm, MVert *mvert, const MFace* face, float *fn)
923 {
924         vec3f c= {mvert[face->v1].co[0],mvert[face->v1].co[1],mvert[face->v1].co[2]};
925         vec3f b= {mvert[face->v2].co[0],mvert[face->v2].co[1],mvert[face->v2].co[2]};
926         vec3f a= {mvert[face->v3].co[0],mvert[face->v3].co[1],mvert[face->v3].co[2]};
927         vec3f s1, s2;
928         float final[3];
929
930         VecSubf(&s1.x,&a.x,&b.x);
931         VecSubf(&s2.x,&c.x,&b.x);
932
933         final[0] = s1.y * s2.z - s1.z * s2.y;
934         final[1] = s1.z * s2.x - s1.x * s2.z;
935         final[2] = s1.x * s2.y - s1.y * s2.x;
936
937         if(fn)
938                 VecCopyf(fn, final);
939
940         norm->x+= final[0];
941         norm->y+= final[1];
942         norm->z+= final[2];
943 }
944
945 static void update_damaged_vert(SculptSession *ss, ListBase *lb)
946 {
947         ActiveData *vert;
948        
949         for(vert= lb->first; vert; vert= vert->next) {
950                 vec3f norm= {0,0,0};            
951                 IndexNode *face= ss->fmap[vert->Index].first;
952
953                 while(face){
954                         float *fn = NULL;
955                         if(ss->face_normals)
956                                 fn = &ss->face_normals[face->index*3];
957                         add_face_normal(&norm, ss->mvert, &ss->mface[face->index], fn);
958                         face= face->next;
959                 }
960                 Normalize(&norm.x);
961                 
962                 ss->mvert[vert->Index].no[0]=norm.x*32767;
963                 ss->mvert[vert->Index].no[1]=norm.y*32767;
964                 ss->mvert[vert->Index].no[2]=norm.z*32767;
965         }
966 }
967
968 static void calc_damaged_verts(SculptSession *ss)
969 {
970         int i;
971         
972         for(i=0; i<8; ++i)
973                 update_damaged_vert(ss, &ss->cache->grab_active_verts[i]);
974         update_damaged_vert(ss, &ss->damaged_verts);
975         BLI_freelistN(&ss->damaged_verts);
976         ss->damaged_verts.first = ss->damaged_verts.last = NULL;
977 }
978
979 #if 0
980 static void projverts_clear_inside(SculptSession *ss)
981 {
982         int i;
983         for(i = 0; i < ss->totvert; ++i)
984                 ss->projverts[i].inside = 0;
985 }
986 #endif
987
988 static void sculpt_update_tex(Sculpt *sd)
989 {
990         SculptSession *ss= sd->session;
991
992         if(ss->texcache) {
993                 MEM_freeN(ss->texcache);
994                 ss->texcache= NULL;
995         }
996
997         /* Need to allocate a bigger buffer for bigger brush size */
998         ss->texcache_side = sd->brush->size * 2;
999         if(!ss->texcache || ss->texcache_side > ss->texcache_actual) {
1000                 ss->texcache = brush_gen_texture_cache(sd->brush, sd->brush->size);
1001                 ss->texcache_actual = ss->texcache_side;
1002         }
1003 }
1004
1005 void sculptmode_selectbrush_menu(void)
1006 {
1007         /* XXX: I guess menus belong elsewhere too?
1008
1009         Sculpt *sd= sculpt_data();
1010         int val;
1011         
1012         pupmenu_set_active(sd->brush_type);
1013         
1014         val= pupmenu("Select Brush%t|Draw|Smooth|Pinch|Inflate|Grab|Layer|Flatten");
1015
1016         if(val>0) {
1017                 sd->brush_type= val;
1018
1019                 allqueue(REDRAWVIEW3D, 1);
1020                 allqueue(REDRAWBUTSEDIT, 1);
1021         }*/
1022 }
1023
1024 static void sculptmode_update_all_projverts(SculptSession *ss)
1025 {
1026         unsigned i;
1027
1028         if(!ss->projverts)
1029                 ss->projverts = MEM_mallocN(sizeof(ProjVert)*ss->totvert,"ProjVerts");
1030
1031         for(i=0; i<ss->totvert; ++i) {
1032                 project(ss->cache->mats, ss->vertexcosnos ? &ss->vertexcosnos[i * 6] : ss->mvert[i].co,
1033                         ss->projverts[i].co);
1034                 ss->projverts[i].inside= 0;
1035         }
1036 }
1037
1038 /* Checks whether full update mode (slower) needs to be used to work with modifiers */
1039 char sculpt_modifiers_active(Object *ob)
1040 {
1041         ModifierData *md;
1042         
1043         for(md= modifiers_getVirtualModifierList(ob); md; md= md->next) {
1044                 if(md->mode & eModifierMode_Realtime && md->type != eModifierType_Multires)
1045                         return 1;
1046         }
1047         
1048         return 0;
1049 }
1050
1051 /* Sculpt mode handles multires differently from regular meshes, but only if
1052    it's the last modifier on the stack and it is not on the first level */
1053 static struct MultiresModifierData *sculpt_multires_active(Object *ob)
1054 {
1055         ModifierData *md;
1056         
1057         for(md= modifiers_getVirtualModifierList(ob); md; md= md->next) {
1058                 if(md->type == eModifierType_Multires && !md->next) {
1059                         MultiresModifierData *mmd = (MultiresModifierData*)md;
1060                         if(mmd->lvl != 1)
1061                                 return mmd;
1062                 }
1063         }
1064
1065         return NULL;
1066 }
1067
1068 static void sculpt_update_mesh_elements(bContext *C)
1069 {
1070         SculptSession *ss = CTX_data_tool_settings(C)->sculpt->session;
1071         Object *ob = CTX_data_active_object(C);
1072         int oldtotvert = ss->totvert;
1073
1074         if((ss->multires = sculpt_multires_active(ob))) {
1075                 DerivedMesh *dm = mesh_get_derived_final(CTX_data_scene(C), ob, CD_MASK_BAREMESH);
1076                 ss->totvert = dm->getNumVerts(dm);
1077                 ss->totface = dm->getNumFaces(dm);
1078                 ss->mvert = dm->getVertDataArray(dm, CD_MVERT);
1079                 ss->mface = dm->getFaceDataArray(dm, CD_MFACE);
1080                 ss->face_normals = dm->getFaceDataArray(dm, CD_NORMAL);
1081         }
1082         else {
1083                 Mesh *me = get_mesh(ob);
1084                 ss->totvert = me->totvert;
1085                 ss->totface = me->totface;
1086                 ss->mvert = me->mvert;
1087                 ss->mface = me->mface;
1088                 ss->face_normals = NULL;
1089         }
1090
1091         if(ss->totvert != oldtotvert) {
1092                 if(ss->projverts) MEM_freeN(ss->projverts);
1093                 ss->projverts = NULL;
1094
1095                 if(ss->fmap) MEM_freeN(ss->fmap);
1096                 if(ss->fmap_mem) MEM_freeN(ss->fmap_mem);
1097                 create_vert_face_map(&ss->fmap, &ss->fmap_mem, ss->mface, ss->totvert, ss->totface);
1098                 ss->fmap_size = ss->totvert;
1099         }
1100 }
1101
1102 /* XXX: lots of drawing code (partial redraw), has to go elsewhere */
1103 #if 0
1104 void sculptmode_draw_wires(SculptSession *ss, int only_damaged)
1105 {
1106         Mesh *me = get_mesh(OBACT);
1107         int i;
1108
1109         bglPolygonOffset(1.0);
1110         glDepthMask(0);
1111         BIF_ThemeColor((OBACT==OBACT)?TH_ACTIVE:TH_SELECT);
1112
1113         for(i=0; i<me->totedge; i++) {
1114                 MEdge *med= &me->medge[i];
1115
1116                 if((!only_damaged || (ss->projverts[med->v1].inside || ss->projverts[med->v2].inside)) &&
1117                    (med->flag & ME_EDGEDRAW)) {
1118                         glDrawElements(GL_LINES, 2, GL_UNSIGNED_INT, &med->v1);
1119                 }
1120         }
1121
1122         glDepthMask(1);
1123         bglPolygonOffset(0.0);
1124 }
1125
1126 void sculptmode_draw_mesh(int only_damaged) 
1127 {
1128         int i, j, dt, drawCurrentMat = 1, matnr= -1;
1129         SculptSession *ss = sculpt_session();
1130
1131         sculpt_update_mesh_elements(ss, OBACT);
1132
1133         persp(PERSP_VIEW);
1134         mymultmatrix(OBACT->obmat);
1135         glEnable(GL_DEPTH_TEST);
1136         glEnable(GL_LIGHTING);
1137         /* XXX: GPU_set_object_materials(G.scene, OBACT, 0, NULL); */
1138         glEnable(GL_CULL_FACE);
1139
1140         glShadeModel(GL_SMOOTH);
1141
1142         glVertexPointer(3, GL_FLOAT, sizeof(MVert), &cache->mvert[0].co);
1143         glNormalPointer(GL_SHORT, sizeof(MVert), &cache->mvert[0].no);
1144
1145         dt= MIN2(G.vd->drawtype, OBACT->dt);
1146         if(dt==OB_WIRE)
1147                 glColorMask(0,0,0,0);
1148
1149         for(i=0; i<ss->totface; ++i) {
1150                 MFace *f= &ss->mface[i];
1151                 char inside= 0;
1152                 int new_matnr= f->mat_nr + 1;
1153                 
1154                 if(new_matnr != matnr)
1155                         drawCurrentMat= GPU_enable_material(matnr = new_matnr, NULL);
1156                 
1157                 /* If only_damaged!=0, only draw faces that are partially
1158                    inside the area(s) modified by the brush */
1159                 if(only_damaged) {
1160                         for(j=0; j<(f->v4?4:3); ++j) {
1161                                 if(ss->projverts[*((&f->v1)+j)].inside) {
1162                                         inside= 1;
1163                                         break;
1164                                 }
1165                         }
1166                 }
1167                 else
1168                         inside= 1;
1169                         
1170                 if(inside && drawCurrentMat)
1171                         glDrawElements(f->v4?GL_QUADS:GL_TRIANGLES, f->v4?4:3, GL_UNSIGNED_INT, &f->v1);
1172         }
1173
1174         glDisable(GL_CULL_FACE);
1175         glDisable(GL_LIGHTING);
1176         glColorMask(1,1,1,1);
1177
1178         if(dt==OB_WIRE || (OBACT->dtx & OB_DRAWWIRE))
1179                 sculptmode_draw_wires(ss, only_damaged);
1180
1181         glDisable(GL_DEPTH_TEST);
1182 }
1183 #endif
1184
1185 static int sculpt_poll(bContext *C)
1186 {
1187         return G.f & G_SCULPTMODE && CTX_wm_area(C)->spacetype == SPACE_VIEW3D &&
1188                 CTX_wm_region(C)->regiontype == RGN_TYPE_WINDOW;
1189 }
1190
1191 /*** Sculpt Cursor ***/
1192 static void draw_paint_cursor(bContext *C, int x, int y, void *customdata)
1193 {
1194         Sculpt *sd= CTX_data_tool_settings(C)->sculpt;
1195         
1196         glTranslatef((float)x, (float)y, 0.0f);
1197         
1198         glColor4ub(255, 100, 100, 128);
1199         glEnable( GL_LINE_SMOOTH );
1200         glEnable(GL_BLEND);
1201         glutil_draw_lined_arc(0.0, M_PI*2.0, sd->brush->size, 40);
1202         glDisable(GL_BLEND);
1203         glDisable( GL_LINE_SMOOTH );
1204         
1205         glTranslatef((float)-x, (float)-y, 0.0f);
1206 }
1207
1208 static void toggle_paint_cursor(bContext *C)
1209 {
1210         Sculpt *s = CTX_data_scene(C)->toolsettings->sculpt;
1211
1212         if(s->session->cursor) {
1213                 WM_paint_cursor_end(CTX_wm_manager(C), s->session->cursor);
1214                 s->session->cursor = NULL;
1215         }
1216         else {
1217                 s->session->cursor =
1218                         WM_paint_cursor_activate(CTX_wm_manager(C), sculpt_poll, draw_paint_cursor, NULL);
1219         }
1220 }
1221
1222 static void sculpt_undo_push(bContext *C, Sculpt *sd)
1223 {
1224         switch(sd->brush->sculpt_tool) {
1225         case SCULPT_TOOL_DRAW:
1226                 ED_undo_push(C, "Draw Brush"); break;
1227         case SCULPT_TOOL_SMOOTH:
1228                 ED_undo_push(C, "Smooth Brush"); break;
1229         case SCULPT_TOOL_PINCH:
1230                 ED_undo_push(C, "Pinch Brush"); break;
1231         case SCULPT_TOOL_INFLATE:
1232                 ED_undo_push(C, "Inflate Brush"); break;
1233         case SCULPT_TOOL_GRAB:
1234                 ED_undo_push(C, "Grab Brush"); break;
1235         case SCULPT_TOOL_LAYER:
1236                 ED_undo_push(C, "Layer Brush"); break;
1237         case SCULPT_TOOL_FLATTEN:
1238                 ED_undo_push(C, "Flatten Brush"); break;
1239         default:
1240                 ED_undo_push(C, "Sculpting"); break;
1241         }
1242 }
1243
1244 static int sculpt_brush_curve_preset_exec(bContext *C, wmOperator *op)
1245 {
1246         brush_curve_preset(CTX_data_scene(C)->toolsettings->sculpt->brush, RNA_enum_get(op->ptr, "mode"));
1247         return OPERATOR_FINISHED;
1248 }
1249
1250 static void SCULPT_OT_brush_curve_preset(wmOperatorType *ot)
1251 {
1252         static EnumPropertyItem prop_mode_items[] = {
1253                 {BRUSH_PRESET_SHARP, "SHARP", 0, "Sharp Curve", ""},
1254                 {BRUSH_PRESET_SMOOTH, "SMOOTH", 0, "Smooth Curve", ""},
1255                 {BRUSH_PRESET_MAX, "MAX", 0, "Max Curve", ""},
1256                 {0, NULL, 0, NULL, NULL}};
1257
1258         ot->name= "Preset";
1259         ot->idname= "SCULPT_OT_brush_curve_preset";
1260
1261         ot->exec= sculpt_brush_curve_preset_exec;
1262         ot->poll= sculpt_poll;
1263
1264         ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO;
1265
1266         RNA_def_enum(ot->srna, "mode", prop_mode_items, BRUSH_PRESET_SHARP, "Mode", "");
1267 }
1268
1269 /**** Radial control ****/
1270 static int sculpt_radial_control_invoke(bContext *C, wmOperator *op, wmEvent *event)
1271 {
1272         toggle_paint_cursor(C);
1273         brush_radial_control_invoke(op, CTX_data_scene(C)->toolsettings->sculpt->brush, 1);
1274         return WM_radial_control_invoke(C, op, event);
1275 }
1276
1277 static int sculpt_radial_control_modal(bContext *C, wmOperator *op, wmEvent *event)
1278 {
1279         int ret = WM_radial_control_modal(C, op, event);
1280         if(ret != OPERATOR_RUNNING_MODAL)
1281                 toggle_paint_cursor(C);
1282         return ret;
1283 }
1284
1285 static int sculpt_radial_control_exec(bContext *C, wmOperator *op)
1286 {
1287         return brush_radial_control_exec(op, CTX_data_scene(C)->toolsettings->sculpt->brush, 1);
1288 }
1289
1290 static void SCULPT_OT_radial_control(wmOperatorType *ot)
1291 {
1292         WM_OT_radial_control_partial(ot);
1293
1294         ot->name= "Sculpt Radial Control";
1295         ot->idname= "SCULPT_OT_radial_control";
1296
1297         ot->invoke= sculpt_radial_control_invoke;
1298         ot->modal= sculpt_radial_control_modal;
1299         ot->exec= sculpt_radial_control_exec;
1300         ot->poll= sculpt_poll;
1301
1302         ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO;
1303 }
1304
1305 /**** Operator for applying a stroke (various attributes including mouse path)
1306       using the current brush. ****/
1307
1308 static float unproject_brush_radius(SculptSession *ss, float offset)
1309 {
1310         float brush_edge[3];
1311
1312         /* In anchored mode, brush size changes with mouse loc, otherwise it's fixed using the brush radius */
1313         unproject(ss->cache->mats, brush_edge, ss->cache->initial_mouse[0] + offset,
1314                   ss->cache->initial_mouse[1], ss->cache->depth);
1315
1316         return VecLenf(ss->cache->true_location, brush_edge);
1317 }
1318
1319 static void sculpt_cache_free(StrokeCache *cache)
1320 {
1321         if(cache->layer_disps)
1322                 MEM_freeN(cache->layer_disps);
1323         if(cache->mesh_store)
1324                 MEM_freeN(cache->mesh_store);
1325         if(cache->orig_norms)
1326                 MEM_freeN(cache->orig_norms);
1327         if(cache->mats)
1328                 MEM_freeN(cache->mats);
1329         MEM_freeN(cache);
1330 }
1331
1332 /* Initialize the stroke cache invariants from operator properties */
1333 static void sculpt_update_cache_invariants(Sculpt *sd, bContext *C, wmOperator *op)
1334 {
1335         StrokeCache *cache = MEM_callocN(sizeof(StrokeCache), "stroke cache");
1336         int i;
1337
1338         sd->session->cache = cache;
1339
1340         RNA_float_get_array(op->ptr, "scale", cache->scale);
1341         cache->flag = RNA_int_get(op->ptr, "flag");
1342         RNA_float_get_array(op->ptr, "clip_tolerance", cache->clip_tolerance);
1343         RNA_int_get_array(op->ptr, "initial_mouse", cache->initial_mouse);
1344         cache->depth = RNA_float_get(op->ptr, "depth");
1345
1346         /* Truly temporary data that isn't stored in properties */
1347
1348         view3d_set_viewcontext(C, &cache->vc);
1349
1350         cache->mats = MEM_callocN(sizeof(bglMats), "sculpt bglMats");
1351         view3d_get_transformation(&cache->vc, cache->vc.obact, cache->mats);
1352
1353         sculpt_update_mesh_elements(C);
1354
1355         /* Make copies of the mesh vertex locations and normals for some tools */
1356         if(sd->brush->sculpt_tool == SCULPT_TOOL_LAYER || (sd->brush->flag & BRUSH_ANCHORED)) {
1357                 cache->layer_disps = MEM_callocN(sizeof(float) * sd->session->totvert, "layer brush displacements");
1358                 cache->mesh_store= MEM_mallocN(sizeof(float) * 3 * sd->session->totvert, "sculpt mesh vertices copy");
1359                 for(i = 0; i < sd->session->totvert; ++i)
1360                         VecCopyf(cache->mesh_store[i], sd->session->mvert[i].co);
1361
1362                 if(sd->brush->flag & BRUSH_ANCHORED) {
1363                         cache->orig_norms= MEM_mallocN(sizeof(short) * 3 * sd->session->totvert, "Sculpt orig norm");
1364                         for(i = 0; i < sd->session->totvert; ++i) {
1365                                 cache->orig_norms[i][0] = sd->session->mvert[i].no[0];
1366                                 cache->orig_norms[i][1] = sd->session->mvert[i].no[1];
1367                                 cache->orig_norms[i][2] = sd->session->mvert[i].no[2];
1368                         }
1369                 }
1370         }
1371
1372         unproject(cache->mats, cache->true_location, cache->initial_mouse[0], cache->initial_mouse[1], cache->depth);
1373         cache->radius = unproject_brush_radius(sd->session, brush_size(sd));
1374         cache->rotation = 0;
1375         cache->first_time = 1;
1376 }
1377
1378 /* Initialize the stroke cache variants from operator properties */
1379 static void sculpt_update_cache_variants(Sculpt *sd, PointerRNA *ptr)
1380 {
1381         StrokeCache *cache = sd->session->cache;
1382         float grab_location[3];
1383         int dx, dy;
1384
1385         if(!(sd->brush->flag & BRUSH_ANCHORED))
1386                 RNA_float_get_array(ptr, "location", cache->true_location);
1387         cache->flip = RNA_boolean_get(ptr, "flip");
1388         RNA_int_get_array(ptr, "mouse", cache->mouse);
1389         
1390         /* Truly temporary data that isn't stored in properties */
1391
1392         cache->previous_pixel_radius = cache->pixel_radius;
1393         cache->pixel_radius = brush_size(sd);
1394
1395         if(sd->brush->flag & BRUSH_ANCHORED) {
1396                 dx = cache->mouse[0] - cache->initial_mouse[0];
1397                 dy = cache->mouse[1] - cache->initial_mouse[1];
1398                 cache->pixel_radius = sqrt(dx*dx + dy*dy);
1399                 cache->radius = unproject_brush_radius(sd->session, cache->pixel_radius);
1400                 cache->rotation = atan2(dy, dx);
1401         }
1402         else if(sd->brush->flag & BRUSH_RAKE) {
1403                 int update;
1404
1405                 dx = cache->last_rake[0] - cache->mouse[0];
1406                 dy = cache->last_rake[1] - cache->mouse[1];
1407
1408                 update = dx*dx + dy*dy > 100;
1409
1410                 /* To prevent jitter, only update the angle if the mouse has moved over 10 pixels */
1411                 if(update && !cache->first_time)
1412                         cache->rotation = M_PI_2 + atan2(dy, dx);
1413
1414                 if(update || cache->first_time) {
1415                         cache->last_rake[0] = cache->mouse[0];
1416                         cache->last_rake[1] = cache->mouse[1];
1417                 }
1418         }
1419
1420         /* Find the grab delta */
1421         if(sd->brush->sculpt_tool == SCULPT_TOOL_GRAB) {
1422                 unproject(cache->mats, grab_location, cache->mouse[0], cache->mouse[1], cache->depth);
1423                 if(!cache->first_time)
1424                         VecSubf(cache->grab_delta, grab_location, cache->old_grab_location);
1425                 VecCopyf(cache->old_grab_location, grab_location);
1426         }
1427 }
1428
1429 /* Initialize stroke operator properties */
1430 static void sculpt_brush_stroke_init_properties(bContext *C, wmOperator *op, wmEvent *event, SculptSession *ss)
1431 {
1432         Sculpt *sd = CTX_data_tool_settings(C)->sculpt;
1433         Object *ob= CTX_data_active_object(C);
1434         ModifierData *md;
1435         ViewContext vc;
1436         float scale[3], clip_tolerance[3] = {0,0,0};
1437         int mouse[2], flag = 0;
1438
1439         /* Set scaling adjustment */
1440         scale[0] = 1.0f / ob->size[0];
1441         scale[1] = 1.0f / ob->size[1];
1442         scale[2] = 1.0f / ob->size[2];
1443         RNA_float_set_array(op->ptr, "scale", scale);
1444
1445         /* Initialize mirror modifier clipping */
1446         for(md= ob->modifiers.first; md; md= md->next) {
1447                 if(md->type==eModifierType_Mirror && (md->mode & eModifierMode_Realtime)) {
1448                         const MirrorModifierData *mmd = (MirrorModifierData*) md;
1449                         
1450                         /* Mark each axis that needs clipping along with its tolerance */
1451                         if(mmd->flag & MOD_MIR_CLIPPING) {
1452                                 flag |= CLIP_X << mmd->axis;
1453                                 if(mmd->tolerance > clip_tolerance[mmd->axis])
1454                                         clip_tolerance[mmd->axis] = mmd->tolerance;
1455                         }
1456                 }
1457         }
1458         RNA_int_set(op->ptr, "flag", flag);
1459         RNA_float_set_array(op->ptr, "clip_tolerance", clip_tolerance);
1460
1461         /* Initial mouse location */
1462         mouse[0] = event->x;
1463         mouse[1] = event->y;
1464         RNA_int_set_array(op->ptr, "initial_mouse", mouse);
1465
1466         /* Initial screen depth under the mouse */
1467         view3d_set_viewcontext(C, &vc);
1468         RNA_float_set(op->ptr, "depth", read_cached_depth(&vc, event->x, event->y));
1469
1470         sculpt_update_cache_invariants(sd, C, op);
1471 }
1472
1473 static int sculpt_brush_stroke_invoke(bContext *C, wmOperator *op, wmEvent *event)
1474 {
1475         Sculpt *sd = CTX_data_tool_settings(C)->sculpt;
1476
1477         view3d_operator_needs_opengl(C);
1478         sculpt_brush_stroke_init_properties(C, op, event, sd->session);
1479
1480         sculptmode_update_all_projverts(sd->session);
1481
1482         /* TODO: Shouldn't really have to do this at the start of every
1483            stroke, but sculpt would need some sort of notification when
1484            changes are made to the texture. */
1485         sculpt_update_tex(sd);
1486
1487         /* add modal handler */
1488         WM_event_add_modal_handler(C, &CTX_wm_window(C)->handlers, op);
1489         
1490         return OPERATOR_RUNNING_MODAL;
1491 }
1492
1493 static void sculpt_restore_mesh(Sculpt *sd)
1494 {
1495         StrokeCache *cache = sd->session->cache;
1496         int i;
1497         
1498         /* Restore the mesh before continuing with anchored stroke */
1499         if((sd->brush->flag & BRUSH_ANCHORED) && cache->mesh_store) {
1500                 for(i = 0; i < sd->session->totvert; ++i) {
1501                         VecCopyf(sd->session->mvert[i].co, cache->mesh_store[i]);
1502                         sd->session->mvert[i].no[0] = cache->orig_norms[i][0];
1503                         sd->session->mvert[i].no[1] = cache->orig_norms[i][1];
1504                         sd->session->mvert[i].no[2] = cache->orig_norms[i][2];
1505                 }
1506         }
1507 }
1508
1509 static void sculpt_post_stroke_free(SculptSession *ss)
1510 {
1511         BLI_freelistN(&ss->damaged_rects);
1512         BLI_freelistN(&ss->damaged_verts);
1513 }
1514
1515 static void sculpt_flush_update(bContext *C)
1516 {
1517         Sculpt *s = CTX_data_tool_settings(C)->sculpt;
1518         ARegion *ar = CTX_wm_region(C);
1519         MultiresModifierData *mmd = s->session->multires;
1520
1521         calc_damaged_verts(s->session);
1522
1523         if(mmd) {
1524                 if(mmd->undo_verts && mmd->undo_verts != s->session->mvert)
1525                         MEM_freeN(mmd->undo_verts);
1526                 
1527                 mmd->undo_verts = s->session->mvert;
1528                 mmd->undo_verts_tot = s->session->totvert;
1529                 multires_mark_as_modified(CTX_data_active_object(C));
1530         }
1531
1532         ED_region_tag_redraw(ar);
1533 }
1534
1535 static int sculpt_brush_stroke_modal(bContext *C, wmOperator *op, wmEvent *event)
1536 {
1537         PointerRNA itemptr;
1538         Sculpt *sd = CTX_data_tool_settings(C)->sculpt;
1539         float center[3];
1540         int mouse[2] = {event->x, event->y};
1541
1542         sculpt_update_mesh_elements(C);
1543
1544         unproject(sd->session->cache->mats, center, event->x, event->y,
1545                   read_cached_depth(&sd->session->cache->vc, event->x, event->y));
1546
1547         /* Add to stroke */
1548         RNA_collection_add(op->ptr, "stroke", &itemptr);
1549         RNA_float_set_array(&itemptr, "location", center);
1550         RNA_int_set_array(&itemptr, "mouse", mouse);
1551         RNA_boolean_set(&itemptr, "flip", event->shift);
1552         sculpt_update_cache_variants(sd, &itemptr);
1553
1554         sculpt_restore_mesh(sd);
1555         do_symmetrical_brush_actions(CTX_data_tool_settings(C)->sculpt, sd->session->cache);
1556
1557         sculpt_flush_update(C);
1558         sculpt_post_stroke_free(sd->session);
1559
1560         /* Finished */
1561         if(event->type == LEFTMOUSE && event->val == 0) {
1562                 request_depth_update(sd->session->cache->vc.rv3d);
1563
1564                 sculpt_cache_free(sd->session->cache);
1565
1566                 sculpt_undo_push(C, sd);
1567
1568                 return OPERATOR_FINISHED;
1569         }
1570
1571         return OPERATOR_RUNNING_MODAL;
1572 }
1573
1574 static int sculpt_brush_stroke_exec(bContext *C, wmOperator *op)
1575 {
1576         Sculpt *sd = CTX_data_tool_settings(C)->sculpt;
1577
1578         view3d_operator_needs_opengl(C);
1579         sculpt_update_cache_invariants(sd, C, op);
1580         sculptmode_update_all_projverts(sd->session);
1581         sculpt_update_tex(sd);
1582
1583         RNA_BEGIN(op->ptr, itemptr, "stroke") {
1584                 sculpt_update_cache_variants(sd, &itemptr);
1585
1586                 sculpt_restore_mesh(sd);
1587                 do_symmetrical_brush_actions(sd, sd->session->cache);
1588
1589                 sculpt_post_stroke_free(sd->session);
1590         }
1591         RNA_END;
1592
1593         sculpt_flush_update(C);
1594         sculpt_cache_free(sd->session->cache);
1595
1596         sculpt_undo_push(C, sd);
1597
1598         return OPERATOR_FINISHED;
1599 }
1600
1601 static void SCULPT_OT_brush_stroke(wmOperatorType *ot)
1602 {
1603         ot->flag |= OPTYPE_REGISTER;
1604
1605         /* identifiers */
1606         ot->name= "Sculpt Mode";
1607         ot->idname= "SCULPT_OT_brush_stroke";
1608         
1609         /* api callbacks */
1610         ot->invoke= sculpt_brush_stroke_invoke;
1611         ot->modal= sculpt_brush_stroke_modal;
1612         ot->exec= sculpt_brush_stroke_exec;
1613         ot->poll= sculpt_poll;
1614         
1615         /* flags (sculpt does own undo? (ton) */
1616         ot->flag= OPTYPE_REGISTER;
1617
1618         /* properties */
1619         RNA_def_collection_runtime(ot->srna, "stroke", &RNA_OperatorStrokeElement, "Stroke", "");
1620
1621         /* If the object has a scaling factor, brushes also need to be scaled
1622            to work as expected. */
1623         RNA_def_float_vector(ot->srna, "scale", 3, NULL, 0.0f, FLT_MAX, "Scale", "", 0.0f, 1000.0f);
1624
1625         RNA_def_int(ot->srna, "flag", 0, 0, INT_MAX, "flag", "", 0, INT_MAX);
1626
1627         /* For mirror modifiers */
1628         RNA_def_float_vector(ot->srna, "clip_tolerance", 3, NULL, 0.0f, FLT_MAX, "clip_tolerance", "", 0.0f, 1000.0f);
1629
1630         /* The initial 2D location of the mouse */
1631         RNA_def_int_vector(ot->srna, "initial_mouse", 2, NULL, INT_MIN, INT_MAX, "initial_mouse", "", INT_MIN, INT_MAX);
1632
1633         /* The initial screen depth of the mouse */
1634         RNA_def_float(ot->srna, "depth", 0.0f, 0.0f, FLT_MAX, "depth", "", 0.0f, FLT_MAX);
1635 }
1636
1637 /**** Toggle operator for turning sculpt mode on or off ****/
1638
1639 static int sculpt_toggle_mode(bContext *C, wmOperator *op)
1640 {
1641         ToolSettings *ts = CTX_data_tool_settings(C);
1642
1643         if(G.f & G_SCULPTMODE) {
1644                 multires_force_update(CTX_data_active_object(C));
1645
1646                 /* Leave sculptmode */
1647                 G.f &= ~G_SCULPTMODE;
1648
1649                 toggle_paint_cursor(C);
1650
1651                 sculptsession_free(ts->sculpt);
1652         }
1653         else {
1654                 MTex *mtex; // XXX: temporary
1655
1656                 /* Enter sculptmode */
1657
1658                 G.f |= G_SCULPTMODE;
1659                 
1660                 /* Create persistent sculpt mode data */
1661                 if(!ts->sculpt)
1662                         ts->sculpt = MEM_callocN(sizeof(Sculpt), "sculpt mode data");
1663
1664                 /* Create sculpt mode session data */
1665                 if(ts->sculpt->session)
1666                         MEM_freeN(ts->sculpt->session);
1667                 ts->sculpt->session = MEM_callocN(sizeof(SculptSession), "sculpt session");
1668
1669                 toggle_paint_cursor(C);
1670
1671                 /* If there's no brush, create one */
1672                 brush_check_exists(&ts->sculpt->brush);
1673
1674                 /* XXX: testing: set the brush texture to the first available one */
1675                 if(G.main->tex.first) {
1676                         Tex *tex = G.main->tex.first;
1677                         if(tex->type) {
1678                                 mtex = MEM_callocN(sizeof(MTex), "test mtex");
1679                                 ts->sculpt->brush->texact = 0;
1680                                 ts->sculpt->brush->mtex[0] = mtex;
1681                                 mtex->tex = tex;
1682                                 mtex->size[0] = mtex->size[1] = mtex->size[2] = 50;
1683                         }
1684                 }
1685         }
1686
1687         return OPERATOR_FINISHED;
1688 }
1689
1690 static void SCULPT_OT_sculptmode_toggle(wmOperatorType *ot)
1691 {
1692         /* identifiers */
1693         ot->name= "Sculpt Mode";
1694         ot->idname= "SCULPT_OT_sculptmode_toggle";
1695         
1696         /* api callbacks */
1697         ot->exec= sculpt_toggle_mode;
1698         ot->poll= ED_operator_object_active;
1699         
1700         ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO;
1701 }
1702
1703 void ED_operatortypes_sculpt()
1704 {
1705         WM_operatortype_append(SCULPT_OT_radial_control);
1706         WM_operatortype_append(SCULPT_OT_brush_stroke);
1707         WM_operatortype_append(SCULPT_OT_sculptmode_toggle);
1708         WM_operatortype_append(SCULPT_OT_brush_curve_preset);
1709 }
1710
1711 void sculpt(Sculpt *sd)
1712 {
1713 #if 0
1714         SculptSession *ss= sd->session;
1715         Object *ob= NULL; /*XXX */
1716         Mesh *me;
1717         MultiresModifierData *mmd = NULL;
1718         /* lastSigMouse is for the rake, to store the last place the mouse movement was significant */
1719         short mouse[2], mvalo[2], lastSigMouse[2],firsttime=1, mousebut;
1720         short modifier_calculations= 0;
1721         BrushAction *a = MEM_callocN(sizeof(BrushAction), "brush action");
1722         short spacing= 32000;
1723         int scissor_box[4];
1724         float offsetRot;
1725         int smooth_stroke = 0, i;
1726         int anchored, rake = 0 /* XXX: rake = ? */;
1727
1728         /* XXX: checking that sculpting is allowed
1729         if(!(G.f & G_SCULPTMODE) || G.obedit || !ob || ob->id.lib || !get_mesh(ob) || (get_mesh(ob)->totface == 0))
1730                 return;
1731         if(!(ob->lay & G.vd->lay))
1732                 error("Active object is not in this layer");
1733         if(ob_get_keyblock(ob)) {
1734                 if(!(ob->shapeflag & OB_SHAPE_LOCK)) {
1735                         error("Cannot sculpt on unlocked shape key");
1736                         return;
1737                 }
1738         }*/
1739         
1740         anchored = sd->brush->flag & BRUSH_ANCHORED;
1741         smooth_stroke = (sd->flags & SCULPT_INPUT_SMOOTH) && (sd->brush->sculpt_tool != SCULPT_TOOL_GRAB) && !anchored;
1742
1743         if(smooth_stroke)
1744                 sculpt_stroke_new(256);
1745
1746         ss->damaged_rects.first = ss->damaged_rects.last = NULL;
1747         ss->damaged_verts.first = ss->damaged_verts.last = NULL;
1748         ss->vertexcosnos = NULL;
1749
1750         mmd = sculpt_multires_active(ob);
1751
1752         /* Check that vertex users are up-to-date */
1753         if(ob != active_ob || !ss->vertex_users || ss->vertex_users_size != cache->totvert) {
1754                 sculpt_vertexusers_free(ss);
1755                 calc_vertex_users(ss);
1756                 if(ss->projverts)
1757                         MEM_freeN(ss->projverts);
1758                 ss->projverts = NULL;
1759                 active_ob= ob;
1760         }
1761                 
1762         glEnableClientState(GL_VERTEX_ARRAY);
1763         glEnableClientState(GL_NORMAL_ARRAY);
1764
1765         /*XXX:
1766         persp(PERSP_VIEW);
1767         getmouseco_areawin(mvalo);*/
1768
1769         /* Init texture
1770            FIXME: Shouldn't be doing this every time! */
1771         if(sd->tex_mode!=SCULPTREPT_3D)
1772                 sculptmode_update_tex(sd);
1773
1774         /*XXX: getmouseco_areawin(mouse); */
1775         mvalo[0]= mouse[0];
1776         mvalo[1]= mouse[1];
1777         lastSigMouse[0]=mouse[0];
1778         lastSigMouse[1]=mouse[1];
1779         mousebut = 0; /* XXX: L_MOUSE; */
1780
1781         /* If modifier_calculations is true, then extra time must be spent
1782            updating the mesh. This takes a *lot* longer, so it's worth
1783            skipping if the modifier stack is empty. */
1784         modifier_calculations= sculpt_modifiers_active(ob);
1785
1786         if(modifier_calculations)
1787                 ss->vertexcosnos= mesh_get_mapped_verts_nors(NULL, ob); /* XXX: scene = ? */
1788         sculptmode_update_all_projverts(ss);
1789
1790         /* Capture original copy */
1791         if(sd->flags & SCULPT_DRAW_FAST)
1792                 glAccum(GL_LOAD, 1);
1793
1794         /* Get original scissor box */
1795         glGetIntegerv(GL_SCISSOR_BOX, scissor_box);
1796         
1797         /* For raking, get the original angle*/
1798         offsetRot=sculpt_tex_angle(sd);
1799
1800         me = get_mesh(ob);
1801
1802         while (/*XXX:get_mbut() & mousebut*/0) {
1803                 /* XXX: getmouseco_areawin(mouse); */
1804                 /* If rake, and the mouse has moved over 10 pixels (euclidean) (prevents jitter) then get the new angle */
1805                 if (rake && (pow(lastSigMouse[0]-mouse[0],2)+pow(lastSigMouse[1]-mouse[1],2))>100){
1806                         /*Nasty looking, but just orig + new angle really*/
1807                         set_tex_angle(sd, offsetRot+180.+to_deg(atan2((float)(mouse[1]-lastSigMouse[1]),(float)(mouse[0]-lastSigMouse[0]))));
1808                         lastSigMouse[0]=mouse[0];
1809                         lastSigMouse[1]=mouse[1];
1810                 }
1811                 
1812                 if(firsttime || mouse[0]!=mvalo[0] || mouse[1]!=mvalo[1] ||
1813                    sd->brush->flag & BRUSH_AIRBRUSH) {
1814                         a->firsttime = firsttime;
1815                         firsttime= 0;
1816
1817                         if(smooth_stroke)
1818                                 sculpt_stroke_add_point(ss->stroke, mouse[0], mouse[1]);
1819
1820                         spacing+= sqrt(pow(mvalo[0]-mouse[0],2)+pow(mvalo[1]-mouse[1],2));
1821
1822                         if(modifier_calculations && !ss->vertexcosnos)
1823                                 ss->vertexcosnos= mesh_get_mapped_verts_nors(NULL, ob); /*XXX scene = ? */
1824
1825                         if(sd->brush->sculpt_tool != SCULPT_TOOL_GRAB) {
1826                                 if(anchored) {
1827                                         /* Restore the mesh before continuing with anchored stroke */
1828                                         /*if(a->mesh_store) {
1829                                                 for(i = 0; i < cache->totvert; ++i) {
1830                                                         VecCopyf(cache->mvert[i].co, &a->mesh_store[i].x);
1831                                                         cache->mvert[i].no[0] = a->orig_norms[i][0];
1832                                                         cache->mvert[i].no[1] = a->orig_norms[i][1];
1833                                                         cache->mvert[i].no[2] = a->orig_norms[i][2];
1834                                                 }
1835                                                 }*/
1836                                         
1837                                         //do_symmetrical_brush_actions(sd, a, mouse, NULL);
1838                                 }
1839                                 else {
1840                                         if(smooth_stroke) {
1841                                                 sculpt_stroke_apply(sd, ss->stroke);
1842                                         }
1843                                         else if(sd->spacing==0 || spacing>sd->spacing) {
1844                                                 //do_symmetrical_brush_actions(sd, a, mouse, NULL);
1845                                                 spacing= 0;
1846                                         }
1847                                 }
1848                         }
1849                         else {
1850                                 //do_symmetrical_brush_actions(sd, a, mouse, mvalo);
1851                                 //unproject(ss, sd->pivot, mouse[0], mouse[1], a->depth);
1852                         }
1853
1854                         if((!ss->multires && modifier_calculations) || ob_get_keyblock(ob)) {
1855                                 /* XXX: DAG_object_flush_update(G.scene, ob, OB_RECALC_DATA); */ }
1856
1857                         if(modifier_calculations || sd->brush->sculpt_tool == SCULPT_TOOL_GRAB || !(sd->flags & SCULPT_DRAW_FAST)) {
1858                                 calc_damaged_verts(ss, a);
1859                                 /*XXX: scrarea_do_windraw(curarea);
1860                                 screen_swapbuffers(); */
1861                         } else { /* Optimized drawing */
1862                                 calc_damaged_verts(ss, a);
1863
1864                                 /* Draw the stored image to the screen */
1865                                 glAccum(GL_RETURN, 1);
1866
1867                                 sculpt_clear_damaged_areas(ss);
1868                                 
1869                                 /* Draw all the polygons that are inside the modified area(s) */
1870                                 glScissor(scissor_box[0], scissor_box[1], scissor_box[2], scissor_box[3]);
1871                                 /* XXX: sculptmode_draw_mesh(1); */
1872                                 glAccum(GL_LOAD, 1);
1873
1874                                 projverts_clear_inside(ss);
1875
1876                                 /* XXX: persp(PERSP_WIN); */
1877                                 glDisable(GL_DEPTH_TEST);
1878                                 
1879                                 /* Draw cursor */
1880                                 if(sd->flags & SCULPT_TOOL_DRAW)
1881                                         fdrawXORcirc((float)mouse[0],(float)mouse[1],sd->brush->size);
1882                                 /* XXX: if(smooth_stroke)
1883                                    sculpt_stroke_draw();
1884                                 
1885                                 myswapbuffers(); */
1886                         }
1887
1888                         BLI_freelistN(&ss->damaged_rects);
1889                         ss->damaged_rects.first = ss->damaged_rects.last = NULL;
1890         
1891                         mvalo[0]= mouse[0];
1892                         mvalo[1]= mouse[1];
1893
1894                         if(ss->vertexcosnos) {
1895                                 MEM_freeN(ss->vertexcosnos);
1896                                 ss->vertexcosnos= NULL;
1897                         }
1898
1899                 }
1900                 else { /*XXX:BIF_wait_for_statechange();*/ }
1901         }
1902
1903         /* Set the rotation of the brush back to what it was before any rake */
1904         set_tex_angle(sd, offsetRot);
1905         
1906         if(smooth_stroke) {
1907                 sculpt_stroke_apply_all(sd, ss->stroke);
1908                 calc_damaged_verts(ss, a);
1909                 BLI_freelistN(&ss->damaged_rects);
1910         }
1911
1912         //if(a->layer_disps) MEM_freeN(a->layer_disps);
1913         //if(a->mesh_store) MEM_freeN(a->mesh_store);
1914         //if(a->orig_norms) MEM_freeN(a->orig_norms);
1915         for(i=0; i<8; ++i)
1916                 BLI_freelistN(&a->grab_active_verts[i]);
1917         MEM_freeN(a);
1918         sculpt_stroke_free(ss->stroke);
1919         ss->stroke = NULL;
1920
1921         if(mmd) {
1922                 if(mmd->undo_verts && mmd->undo_verts != cache->mvert)
1923                         MEM_freeN(mmd->undo_verts);
1924                 
1925                 mmd->undo_verts = cache->mvert;
1926                 mmd->undo_verts_tot = cache->totvert;
1927         }
1928
1929         //sculpt_undo_push(sd);
1930
1931         /* XXX: if(G.vd->depths) G.vd->depths->damaged= 1;
1932            allqueue(REDRAWVIEW3D, 0); */
1933 #endif
1934 }
1935
1936 /* Partial Mesh Visibility */
1937
1938 /* XXX: Partial vis. always was a mess, have to figure something out */
1939 #if 0
1940 /* mode: 0=hide outside selection, 1=hide inside selection */
1941 static void sculptmode_do_pmv(Object *ob, rcti *hb_2d, int mode)
1942 {
1943         Mesh *me= get_mesh(ob);
1944         float hidebox[6][3];
1945         vec3f plane_normals[4];
1946         float plane_ds[4];
1947         unsigned i, j;
1948         unsigned ndx_show, ndx_hide;
1949         MVert *nve;
1950         unsigned face_cnt_show= 0, face_ndx_show= 0;
1951         unsigned edge_cnt_show= 0, edge_ndx_show= 0;
1952         unsigned *old_map= NULL;
1953         const unsigned SHOW= 0, HIDE=1;
1954
1955         /* Convert hide box from 2D to 3D */
1956         unproject(hidebox[0], hb_2d->xmin, hb_2d->ymax, 1);
1957         unproject(hidebox[1], hb_2d->xmax, hb_2d->ymax, 1);
1958         unproject(hidebox[2], hb_2d->xmax, hb_2d->ymin, 1);
1959         unproject(hidebox[3], hb_2d->xmin, hb_2d->ymin, 1);
1960         unproject(hidebox[4], hb_2d->xmin, hb_2d->ymax, 0);
1961         unproject(hidebox[5], hb_2d->xmax, hb_2d->ymin, 0);
1962         
1963         /* Calculate normals for each side of hide box */
1964         CalcNormFloat(hidebox[0], hidebox[1], hidebox[4], &plane_normals[0].x);
1965         CalcNormFloat(hidebox[1], hidebox[2], hidebox[5], &plane_normals[1].x);
1966         CalcNormFloat(hidebox[2], hidebox[3], hidebox[5], &plane_normals[2].x);
1967         CalcNormFloat(hidebox[3], hidebox[0], hidebox[4], &plane_normals[3].x);
1968         
1969         /* Calculate D for each side of hide box */
1970         for(i= 0; i<4; ++i)
1971                 plane_ds[i]= hidebox[i][0]*plane_normals[i].x + hidebox[i][1]*plane_normals[i].y +
1972                         hidebox[i][2]*plane_normals[i].z;
1973         
1974         /* Add partial visibility to mesh */
1975         if(!me->pv) {
1976                 me->pv= MEM_callocN(sizeof(PartialVisibility),"PartialVisibility");
1977         } else {
1978                 old_map= MEM_callocN(sizeof(unsigned)*me->pv->totvert,"PMV oldmap");
1979                 for(i=0; i<me->pv->totvert; ++i) {
1980                         old_map[i]= me->pv->vert_map[i]<me->totvert?0:1;
1981                 }
1982                 mesh_pmv_revert(ob, me);
1983         }
1984         
1985         /* Kill sculpt data */
1986         active_ob= NULL;
1987         
1988         /* Initalize map with which verts are to be hidden */
1989         me->pv->vert_map= MEM_mallocN(sizeof(unsigned)*me->totvert, "PMV vertmap");
1990         me->pv->totvert= me->totvert;
1991         me->totvert= 0;
1992         for(i=0; i<me->pv->totvert; ++i) {
1993                 me->pv->vert_map[i]= mode ? HIDE:SHOW;
1994                 for(j=0; j<4; ++j) {
1995                         if(me->mvert[i].co[0] * plane_normals[j].x +
1996                            me->mvert[i].co[1] * plane_normals[j].y +
1997                            me->mvert[i].co[2] * plane_normals[j].z < plane_ds[j] ) {
1998                                 me->pv->vert_map[i]= mode ? SHOW:HIDE; /* Vert is outside the hide box */
1999                                 break;
2000                         }
2001                 }
2002                 if(old_map && old_map[i]) me->pv->vert_map[i]= 1;
2003                 if(!me->pv->vert_map[i]) ++me->totvert;
2004
2005         }
2006         if(old_map) MEM_freeN(old_map);
2007
2008         /* Find out how many faces to show */
2009         for(i=0; i<me->totface; ++i) {
2010                 if(!me->pv->vert_map[me->mface[i].v1] &&
2011                    !me->pv->vert_map[me->mface[i].v2] &&
2012                    !me->pv->vert_map[me->mface[i].v3]) {
2013                         if(me->mface[i].v4) {
2014                                 if(!me->pv->vert_map[me->mface[i].v4])
2015                                         ++face_cnt_show;
2016                         }
2017                         else ++face_cnt_show;
2018                 }
2019         }
2020         /* Find out how many edges to show */
2021         for(i=0; i<me->totedge; ++i) {
2022                 if(!me->pv->vert_map[me->medge[i].v1] &&
2023                    !me->pv->vert_map[me->medge[i].v2])
2024                         ++edge_cnt_show;
2025         }
2026
2027         /* Create new vert array and reset each vert's map with map[old]=new index */
2028         nve= MEM_mallocN(sizeof(MVert)*me->pv->totvert, "PMV verts");
2029         ndx_show= 0; ndx_hide= me->totvert;
2030         for(i=0; i<me->pv->totvert; ++i) {
2031                 if(me->pv->vert_map[i]) {
2032                         me->pv->vert_map[i]= ndx_hide;
2033                         nve[me->pv->vert_map[i]]= me->mvert[i];
2034                         ++ndx_hide;
2035                 } else {
2036                         me->pv->vert_map[i]= ndx_show;
2037                         nve[me->pv->vert_map[i]]= me->mvert[i];
2038                         ++ndx_show;
2039                 }
2040         }
2041         CustomData_free_layer_active(&me->vdata, CD_MVERT, me->pv->totvert);
2042         me->mvert= CustomData_add_layer(&me->vdata, CD_MVERT, CD_ASSIGN, nve, me->totvert);
2043
2044         /* Create new face array */
2045         me->pv->old_faces= me->mface;
2046         me->pv->totface= me->totface;
2047         me->mface= MEM_mallocN(sizeof(MFace)*face_cnt_show, "PMV faces");
2048         for(i=0; i<me->totface; ++i) {
2049                 MFace *pr_f= &me->pv->old_faces[i];
2050                 char show= 0;
2051
2052                 if(me->pv->vert_map[pr_f->v1] < me->totvert &&
2053                    me->pv->vert_map[pr_f->v2] < me->totvert &&
2054                    me->pv->vert_map[pr_f->v3] < me->totvert) {
2055                         if(pr_f->v4) {
2056                                 if(me->pv->vert_map[pr_f->v4] < me->totvert)
2057                                         show= 1;
2058                         }
2059                         else show= 1;
2060                 }
2061
2062                 if(show) {
2063                         MFace *cr_f= &me->mface[face_ndx_show];
2064                         *cr_f= *pr_f;
2065                         cr_f->v1= me->pv->vert_map[pr_f->v1];
2066                         cr_f->v2= me->pv->vert_map[pr_f->v2];
2067                         cr_f->v3= me->pv->vert_map[pr_f->v3];
2068                         cr_f->v4= pr_f->v4 ? me->pv->vert_map[pr_f->v4] : 0;
2069                         test_index_face(cr_f,NULL,0,pr_f->v4?4:3);
2070                         ++face_ndx_show;
2071                 }
2072         }
2073         me->totface= face_cnt_show;
2074         CustomData_set_layer(&me->fdata, CD_MFACE, me->mface);
2075
2076         /* Create new edge array */
2077         me->pv->old_edges= me->medge;
2078         me->pv->totedge= me->totedge;
2079         me->medge= MEM_mallocN(sizeof(MEdge)*edge_cnt_show, "PMV edges");
2080         me->pv->edge_map= MEM_mallocN(sizeof(int)*me->pv->totedge,"PMV edgemap");
2081         for(i=0; i<me->totedge; ++i) {
2082                 if(me->pv->vert_map[me->pv->old_edges[i].v1] < me->totvert &&
2083                    me->pv->vert_map[me->pv->old_edges[i].v2] < me->totvert) {
2084                         MEdge *cr_e= &me->medge[edge_ndx_show];
2085                         me->pv->edge_map[i]= edge_ndx_show;
2086                         *cr_e= me->pv->old_edges[i];
2087                         cr_e->v1= me->pv->vert_map[me->pv->old_edges[i].v1];
2088                         cr_e->v2= me->pv->vert_map[me->pv->old_edges[i].v2];
2089                         ++edge_ndx_show;
2090                 }
2091                 else me->pv->edge_map[i]= -1;
2092         }
2093         me->totedge= edge_cnt_show;
2094         CustomData_set_layer(&me->edata, CD_MEDGE, me->medge);
2095
2096         /* XXX: DAG_object_flush_update(G.scene, OBACT, OB_RECALC_DATA); */
2097 }
2098
2099 static rcti sculptmode_pmv_box()
2100 {
2101         /*XXX:  short down[2], mouse[2];
2102         rcti ret;
2103
2104         getmouseco_areawin(down);
2105
2106         while((get_mbut()&L_MOUSE) || (get_mbut()&R_MOUSE)) {
2107                 getmouseco_areawin(mouse);
2108
2109                 scrarea_do_windraw(curarea);
2110
2111                 persp(PERSP_WIN);
2112                 glLineWidth(2);
2113                 setlinestyle(2);
2114                 sdrawXORline(down[0],down[1],mouse[0],down[1]);
2115                 sdrawXORline(mouse[0],down[1],mouse[0],mouse[1]);
2116                 sdrawXORline(mouse[0],mouse[1],down[0],mouse[1]);
2117                 sdrawXORline(down[0],mouse[1],down[0],down[1]);
2118                 setlinestyle(0);
2119                 glLineWidth(1);
2120                 persp(PERSP_VIEW);
2121
2122                 screen_swapbuffers();
2123                 backdrawview3d(0);
2124         }
2125
2126         ret.xmin= down[0]<mouse[0]?down[0]:mouse[0];
2127         ret.ymin= down[1]<mouse[1]?down[1]:mouse[1];
2128         ret.xmax= down[0]>mouse[0]?down[0]:mouse[0];
2129         ret.ymax= down[1]>mouse[1]?down[1]:mouse[1];
2130         return ret;*/
2131 }
2132
2133 void sculptmode_pmv(int mode)
2134 {
2135         Object *ob= NULL; /*XXX: OBACT; */
2136         rcti hb_2d;
2137         
2138         if(ob_get_key(ob)) {
2139                 error("Cannot hide mesh with shape keys enabled");
2140                 return;
2141         }
2142         
2143         hb_2d= sculptmode_pmv_box(); /* Get 2D hide box */
2144         
2145         sculptmode_correct_state();
2146
2147         waitcursor(1);
2148
2149         if(hb_2d.xmax-hb_2d.xmin > 3 && hb_2d.ymax-hb_2d.ymin > 3) {
2150                 init_sculptmatrices();
2151
2152                 sculptmode_do_pmv(ob,&hb_2d,mode);
2153         }
2154         else mesh_pmv_off(ob, get_mesh(ob));
2155
2156         /*XXX: scrarea_do_windraw(curarea); */
2157
2158         waitcursor(0);
2159 }
2160 #endif