Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBrecht Van Lommel <brechtvanlommel@pandora.be>2009-02-09 23:58:31 +0300
committerBrecht Van Lommel <brechtvanlommel@pandora.be>2009-02-09 23:58:31 +0300
commit283926aa2d0c6366d92a4f38e994e843b73659f6 (patch)
tree2bd35e5609efa63882ab81eab9e8009a691c5acb /source/blender/editors/mesh/editface.c
parentc02bc1ce5379356b5c17034457a59aebf6e41725 (diff)
2.5: UV Editor module porting pretty much finished now, only missing
still is mirror transform. This commits adds the remaining operators: * UV mapping operators (U key menu): cube, sphere, cylinder, etc. * Hide/Show operators. And solves most XXX's, including: * Fix bad includes and calls into space image. * Aspect ratio correction. * Create UVs if they don't exist yet on unwrap. * Assign image to UVs. * Drawing proportional edit circle.
Diffstat (limited to 'source/blender/editors/mesh/editface.c')
-rw-r--r--source/blender/editors/mesh/editface.c544
1 files changed, 0 insertions, 544 deletions
diff --git a/source/blender/editors/mesh/editface.c b/source/blender/editors/mesh/editface.c
index f2dd68973b8..6c17dff3428 100644
--- a/source/blender/editors/mesh/editface.c
+++ b/source/blender/editors/mesh/editface.c
@@ -81,27 +81,6 @@
/* own include */
#include "mesh_intern.h"
-
-/* Pupmenu codes: */
-#define UV_CUBE_MAPPING 2
-#define UV_CYL_MAPPING 3
-#define UV_SPHERE_MAPPING 4
-#define UV_BOUNDS_MAPPING 5
-#define UV_RESET_MAPPING 6
-#define UV_WINDOW_MAPPING 7
-#define UV_UNWRAP_MAPPING 8
-#define UV_CYL_EX 32
-#define UV_SPHERE_EX 34
-
-/* Some macro tricks to make pupmenu construction look nicer :-)
- Sorry, just did it for fun. */
-
-#define _STR(x) " " #x
-#define STRING(x) _STR(x)
-
-#define MENUSTRING(string, code) string " %x" STRING(code)
-#define MENUTITLE(string) string " %t|"
-
/* ***************** XXX **************** */
static int sample_backbuf_rect() {return 0;}
static int sample_backbuf() {return 0;}
@@ -139,462 +118,6 @@ int facesel_face_pick(View3D *v3d, Mesh *me, short *mval, unsigned int *index, s
return 1;
}
-/* only operates on the edit object - this is all thats needed at the moment */
-static void uv_calc_center_vector(Scene *scene, View3D *v3d, float *result, Object *ob, EditMesh *em)
-{
- float min[3], max[3], *cursx;
-
- EditFace *efa;
- switch (v3d->around)
- {
- case V3D_CENTER: /* bounding box center */
- min[0]= min[1]= min[2]= 1e20f;
- max[0]= max[1]= max[2]= -1e20f;
-
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (efa->f & SELECT) {
- DO_MINMAX(efa->v1->co, min, max);
- DO_MINMAX(efa->v2->co, min, max);
- DO_MINMAX(efa->v3->co, min, max);
- if(efa->v4) DO_MINMAX(efa->v4->co, min, max);
- }
- }
- VecMidf(result, min, max);
- break;
- case V3D_CURSOR: /*cursor center*/
- cursx= give_cursor(scene, v3d);
- /* shift to objects world */
- result[0]= cursx[0]-ob->obmat[3][0];
- result[1]= cursx[1]-ob->obmat[3][1];
- result[2]= cursx[2]-ob->obmat[3][2];
- break;
- case V3D_LOCAL: /*object center*/
- case V3D_CENTROID: /* multiple objects centers, only one object here*/
- default:
- result[0]= result[1]= result[2]= 0.0;
- break;
- }
-}
-
-static void uv_calc_map_matrix(float result[][4], RegionView3D *rv3d, Object *ob, float upangledeg, float sideangledeg, float radius)
-{
- float rotup[4][4], rotside[4][4], viewmatrix[4][4], rotobj[4][4];
- float sideangle= 0.0, upangle= 0.0;
- int k;
-
- /* get rotation of the current view matrix */
- Mat4CpyMat4(viewmatrix, rv3d->viewmat);
- /* but shifting */
- for( k= 0; k< 4; k++) viewmatrix[3][k] =0.0;
-
- /* get rotation of the current object matrix */
- Mat4CpyMat4(rotobj,ob->obmat);
- /* but shifting */
- for( k= 0; k< 4; k++) rotobj[3][k] =0.0;
-
- Mat4Clr(*rotup);
- Mat4Clr(*rotside);
-
- /* compensate front/side.. against opengl x,y,z world definition */
- /* this is "kanonen gegen spatzen", a few plus minus 1 will do here */
- /* i wanted to keep the reason here, so we're rotating*/
- sideangle= M_PI * (sideangledeg + 180.0) /180.0;
- rotside[0][0]= (float)cos(sideangle);
- rotside[0][1]= -(float)sin(sideangle);
- rotside[1][0]= (float)sin(sideangle);
- rotside[1][1]= (float)cos(sideangle);
- rotside[2][2]= 1.0f;
-
- upangle= M_PI * upangledeg /180.0;
- rotup[1][1]= (float)cos(upangle)/radius;
- rotup[1][2]= -(float)sin(upangle)/radius;
- rotup[2][1]= (float)sin(upangle)/radius;
- rotup[2][2]= (float)cos(upangle)/radius;
- rotup[0][0]= (float)1.0/radius;
-
- /* calculate transforms*/
- Mat4MulSerie(result,rotup,rotside,viewmatrix,rotobj,NULL,NULL,NULL,NULL);
-}
-
-static void uv_calc_shift_project(ARegion *ar, View3D *v3d, float *target, float *shift, float rotmat[][4], int projectionmode, float *source, float *min, float *max)
-{
- RegionView3D *rv3d= ar->regiondata;
- float pv[3];
-
- VecSubf(pv, source, shift);
- Mat4MulVecfl(rotmat, pv);
-
- switch(projectionmode) {
- case B_UVAUTO_CYLINDER:
- tubemap(pv[0], pv[1], pv[2], &target[0],&target[1]);
- /* split line is always zero */
- if (target[0] >= 1.0f) target[0] -= 1.0f;
- break;
-
- case B_UVAUTO_SPHERE:
- spheremap(pv[0], pv[1], pv[2], &target[0],&target[1]);
- /* split line is always zero */
- if (target[0] >= 1.0f) target[0] -= 1.0f;
- break;
-
- case 3: /* ortho special case for BOUNDS */
- target[0] = -pv[0];
- target[1] = pv[2];
- break;
-
- case 4:
- {
- /* very special case for FROM WINDOW */
- float pv4[4], dx, dy, x= 0.0, y= 0.0;
-
- dx= ar->winx;
- dy= ar->winy;
-
- VecCopyf(pv4, source);
- pv4[3] = 1.0;
-
- /* rotmat is the object matrix in this case */
- Mat4MulVec4fl(rotmat, pv4);
-
- /* almost project_short */
- Mat4MulVec4fl(rv3d->persmat, pv4);
- if (fabs(pv4[3]) > 0.00001) { /* avoid division by zero */
- target[0] = dx/2.0 + (dx/2.0)*pv4[0]/pv4[3];
- target[1] = dy/2.0 + (dy/2.0)*pv4[1]/pv4[3];
- }
- else {
- /* scaling is lost but give a valid result */
- target[0] = dx/2.0 + (dx/2.0)*pv4[0];
- target[1] = dy/2.0 + (dy/2.0)*pv4[1];
- }
-
- /* v3d->persmat seems to do this funky scaling */
- if(dx > dy) {
- y= (dx-dy)/2.0;
- dy = dx;
- }
- else {
- x= (dy-dx)/2.0;
- dx = dy;
- }
- target[0]= (x + target[0])/dx;
- target[1]= (y + target[1])/dy;
-
- }
- break;
-
- default:
- target[0] = 0.0;
- target[1] = 1.0;
- }
-
- /* we know the values here and may need min_max later */
- /* max requests independand from min; not fastest but safest */
- if(min) {
- min[0] = MIN2(target[0], min[0]);
- min[1] = MIN2(target[1], min[1]);
- }
- if(max) {
- max[0] = MAX2(target[0], max[0]);
- max[1] = MAX2(target[1], max[1]);
- }
-}
-
-static void correct_uv_aspect( EditMesh *em )
-{
- float aspx=1, aspy=1;
- EditFace *efa = EM_get_actFace(em, 1);
- MTFace *tface;
-
- if (efa) {
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
-// XXX image_final_aspect(tface->tpage, &aspx, &aspy);
- }
-
- if (aspx != aspy) {
-
- float scale;
-
- if (aspx > aspy) {
- scale = aspy/aspx;
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (efa->f & SELECT) {
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
- tface->uv[0][0] = ((tface->uv[0][0]-0.5)*scale)+0.5;
- tface->uv[1][0] = ((tface->uv[1][0]-0.5)*scale)+0.5;
- tface->uv[2][0] = ((tface->uv[2][0]-0.5)*scale)+0.5;
- if(efa->v4) {
- tface->uv[3][0] = ((tface->uv[3][0]-0.5)*scale)+0.5;
- }
- }
- }
- } else {
- scale = aspx/aspy;
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (efa->f & SELECT) {
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
- tface->uv[0][1] = ((tface->uv[0][1]-0.5)*scale)+0.5;
- tface->uv[1][1] = ((tface->uv[1][1]-0.5)*scale)+0.5;
- tface->uv[2][1] = ((tface->uv[2][1]-0.5)*scale)+0.5;
- if(efa->v4) {
- tface->uv[3][1] = ((tface->uv[3][1]-0.5)*scale)+0.5;
- }
- }
- }
- }
- }
-}
-
-static void default_uv(float uv[][2], float size)
-{
- int dy;
-
- if(size>1.0) size= 1.0;
-
- dy= 1.0-size;
-
- uv[0][0]= 0;
- uv[0][1]= size+dy;
-
- uv[1][0]= 0;
- uv[1][1]= dy;
-
- uv[2][0]= size;
- uv[2][1]= dy;
-
- uv[3][0]= size;
- uv[3][1]= size+dy;
-}
-
-static void calculate_uv_map(Scene *scene, ARegion *ar, View3D *v3d, EditMesh *em, unsigned short mapmode)
-{
- RegionView3D *rv3d= ar->regiondata;
- MTFace *tface;
- Object *ob;
- EditFace *efa;
- float dx, dy, rotatematrix[4][4], radius= 1.0, min[3], cent[3], max[3];
- float fac= 1.0, upangledeg= 0.0, sideangledeg= 90.0;
- int i, b, mi, n;
-
- if(scene->toolsettings->uvcalc_mapdir==1) {
- upangledeg= 90.0;
- sideangledeg= 0.0;
- } else {
- upangledeg= 0.0;
- if(scene->toolsettings->uvcalc_mapalign==1) sideangledeg= 0.0;
- else sideangledeg= 90.0;
- }
-
- /* add uvs if there not here */
- if (!EM_texFaceCheck(em)) {
- if (em && em->faces.first)
- EM_add_data_layer(em, &em->fdata, CD_MTFACE);
-
-// XXX if (G.sima && G.sima->image) /* this is a bit of a kludge, but assume they want the image on their mesh when UVs are added */
-// image_changed(G.sima, G.sima->image);
-
- if (!EM_texFaceCheck(em))
- return;
-
- /* select new UV's */
-// XX if ((G.sima && G.sima->flag & SI_SYNC_UVSEL)==0) {
-// for(efa=em->faces.first; efa; efa=efa->next) {
-// MTFace *tf= (MTFace *)CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
-// simaFaceSel_Set(efa, tf);
-// }
-
- }
-
- ob=OBACT;
-
- switch(mapmode) {
- case B_UVAUTO_BOUNDS:
- min[0]= min[1]= 10000000.0;
- max[0]= max[1]= -10000000.0;
-
- cent[0] = cent[1] = cent[2] = 0.0;
- uv_calc_map_matrix(rotatematrix, rv3d, ob, upangledeg, sideangledeg, 1.0f);
-
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (efa->f & SELECT) {
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
- uv_calc_shift_project(ar, v3d, tface->uv[0],cent,rotatematrix,3, efa->v1->co, min,max);
- uv_calc_shift_project(ar, v3d, tface->uv[1],cent,rotatematrix,3, efa->v2->co, min,max);
- uv_calc_shift_project(ar, v3d, tface->uv[2],cent,rotatematrix,3, efa->v3->co,min,max);
- if(efa->v4)
- uv_calc_shift_project(ar, v3d, tface->uv[3],cent,rotatematrix,3, efa->v4->co,min,max);
- }
- }
-
- /* rescale UV to be in 1/1 */
- dx= (max[0]-min[0]);
- dy= (max[1]-min[1]);
-
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (efa->f & SELECT) {
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
- if(efa->v4) b= 3; else b= 2;
- for(; b>=0; b--) {
- tface->uv[b][0]= ((tface->uv[b][0]-min[0])*fac)/dx;
- tface->uv[b][1]= 1.0-fac+((tface->uv[b][1]-min[1])/* *fac */)/dy;
- }
- }
- }
- break;
-
- case B_UVAUTO_WINDOW:
- cent[0] = cent[1] = cent[2] = 0.0;
- Mat4CpyMat4(rotatematrix,ob->obmat);
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (efa->f & SELECT) {
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
- uv_calc_shift_project(ar, v3d, tface->uv[0],cent,rotatematrix,4, efa->v1->co, NULL,NULL);
- uv_calc_shift_project(ar, v3d, tface->uv[1],cent,rotatematrix,4, efa->v2->co, NULL,NULL);
- uv_calc_shift_project(ar, v3d, tface->uv[2],cent,rotatematrix,4, efa->v3->co, NULL,NULL);
- if(efa->v4)
- uv_calc_shift_project(ar, v3d, tface->uv[3],cent,rotatematrix,4, efa->v4->co, NULL,NULL);
- }
- }
- break;
-
- case B_UVAUTO_RESET:
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (efa->f & SELECT) {
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
- default_uv(tface->uv, 1.0);
- }
- }
- break;
-
- case B_UVAUTO_CYLINDER:
- case B_UVAUTO_SPHERE:
- uv_calc_center_vector(scene, v3d, cent, ob, em);
-
- if(mapmode==B_UVAUTO_CYLINDER) radius = scene->toolsettings->uvcalc_radius;
-
- /* be compatible to the "old" sphere/cylinder mode */
- if (scene->toolsettings->uvcalc_mapdir== 2)
- Mat4One(rotatematrix);
- else
- uv_calc_map_matrix(rotatematrix, rv3d, ob, upangledeg,sideangledeg,radius);
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (efa->f & SELECT) {
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
- uv_calc_shift_project(ar, v3d, tface->uv[0],cent,rotatematrix,mapmode, efa->v1->co, NULL,NULL);
- uv_calc_shift_project(ar, v3d, tface->uv[1],cent,rotatematrix,mapmode, efa->v2->co, NULL,NULL);
- uv_calc_shift_project(ar, v3d, tface->uv[2],cent,rotatematrix,mapmode, efa->v3->co, NULL,NULL);
- n = 3;
- if(efa->v4) {
- uv_calc_shift_project(ar, v3d, tface->uv[3],cent,rotatematrix,mapmode, efa->v4->co, NULL,NULL);
- n=4;
- }
-
- mi = 0;
- for (i = 1; i < n; i++)
- if (tface->uv[i][0] > tface->uv[mi][0]) mi = i;
-
- for (i = 0; i < n; i++) {
- if (i != mi) {
- dx = tface->uv[mi][0] - tface->uv[i][0];
- if (dx > 0.5) tface->uv[i][0] += 1.0;
- }
- }
- }
- }
-
- break;
-
- case B_UVAUTO_CUBE:
- {
- /* choose x,y,z axis for projetion depending on the largest normal */
- /* component, but clusters all together around the center of map */
- float no[3];
- short cox, coy;
- float *loc= ob->obmat[3];
- /*MVert *mv= me->mvert;*/
- float cubesize = scene->toolsettings->uvcalc_cubesize;
-
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (efa->f & SELECT) {
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
- CalcNormFloat(efa->v1->co, efa->v2->co, efa->v3->co, no);
-
- no[0]= fabs(no[0]);
- no[1]= fabs(no[1]);
- no[2]= fabs(no[2]);
-
- cox=0; coy= 1;
- if(no[2]>=no[0] && no[2]>=no[1]);
- else if(no[1]>=no[0] && no[1]>=no[2]) coy= 2;
- else { cox= 1; coy= 2; }
-
- tface->uv[0][0]= 0.5+0.5*cubesize*(loc[cox] + efa->v1->co[cox]);
- tface->uv[0][1]= 0.5+0.5*cubesize*(loc[coy] + efa->v1->co[coy]);
- dx = floor(tface->uv[0][0]);
- dy = floor(tface->uv[0][1]);
- tface->uv[0][0] -= dx;
- tface->uv[0][1] -= dy;
- tface->uv[1][0]= 0.5+0.5*cubesize*(loc[cox] + efa->v2->co[cox]);
- tface->uv[1][1]= 0.5+0.5*cubesize*(loc[coy] + efa->v2->co[coy]);
- tface->uv[1][0] -= dx;
- tface->uv[1][1] -= dy;
- tface->uv[2][0]= 0.5+0.5*cubesize*(loc[cox] + efa->v3->co[cox]);
- tface->uv[2][1]= 0.5+0.5*cubesize*(loc[coy] + efa->v3->co[coy]);
- tface->uv[2][0] -= dx;
- tface->uv[2][1] -= dy;
- if(efa->v4) {
- tface->uv[3][0]= 0.5+0.5*cubesize*(loc[cox] + efa->v4->co[cox]);
- tface->uv[3][1]= 0.5+0.5*cubesize*(loc[coy] + efa->v4->co[coy]);
- tface->uv[3][0] -= dx;
- tface->uv[3][1] -= dy;
- }
- }
- }
- break;
- }
- default:
- if ((scene->toolsettings->uvcalc_flag & UVCALC_NO_ASPECT_CORRECT)==0)
- correct_uv_aspect(em);
- return;
- } /* end switch mapmode */
-
- /* clipping and wrapping */
- if(0) { // XXX (make it uv layer property!) G.sima && G.sima->flag & SI_CLIP_UV) {
- for (efa= em->faces.first; efa; efa= efa->next) {
- if (!(efa->f & SELECT)) continue;
- tface = CustomData_em_get(&em->fdata, efa->data, CD_MTFACE);
-
- dx= dy= 0;
- if(efa->v4) b= 3; else b= 2;
- for(; b>=0; b--) {
- while(tface->uv[b][0] + dx < 0.0) dx+= 0.5;
- while(tface->uv[b][0] + dx > 1.0) dx-= 0.5;
- while(tface->uv[b][1] + dy < 0.0) dy+= 0.5;
- while(tface->uv[b][1] + dy > 1.0) dy-= 0.5;
- }
-
- if(efa->v4) b= 3; else b= 2;
- for(; b>=0; b--) {
- tface->uv[b][0]+= dx;
- CLAMP(tface->uv[b][0], 0.0, 1.0);
-
- tface->uv[b][1]+= dy;
- CLAMP(tface->uv[b][1], 0.0, 1.0);
- }
- }
- }
-
- if ( (mapmode!=B_UVAUTO_BOUNDS) &&
- (mapmode!=B_UVAUTO_RESET) &&
- (scene->toolsettings->uvcalc_flag & UVCALC_NO_ASPECT_CORRECT)==0
- ) {
- correct_uv_aspect(em);
- }
-
-// XXX notifier object_uvs_changed(OBACT);
-
-}
-
/* last_sel, use em->act_face otherwise get the last selected face in the editselections
* at the moment, last_sel is mainly useful for gaking sure the space image dosnt flicker */
MTFace *EM_get_active_mtface(EditMesh *em, EditFace **act_efa, MCol **mcol, int sloppy)
@@ -1211,73 +734,6 @@ void face_borderselect(Scene *scene, ARegion *ar)
#endif
}
-void uv_autocalc_tface(Scene *scene, ARegion *ar, View3D *v3d, EditMesh *em)
-{
- short mode;
-#ifndef DISABLE_PYTHON
-// short i=0, has_pymenu=0; /* pymenu must be bigger then UV_*_MAPPING */
-// XXX BPyMenu *pym;
-// char menu_number[3];
-#endif
-
- /* uvmenu, will add python items */
- char uvmenu[4096]=MENUTITLE("UV Calculation")
- MENUSTRING("Unwrap", UV_UNWRAP_MAPPING) "|%l|"
-
- MENUSTRING("Cube Projection", UV_CUBE_MAPPING) "|"
- MENUSTRING("Cylinder from View", UV_CYL_MAPPING) "|"
- MENUSTRING("Sphere from View", UV_SPHERE_MAPPING) "|%l|"
-
- MENUSTRING("Project From View", UV_WINDOW_MAPPING) "|"
- MENUSTRING("Project from View (Bounds)",UV_BOUNDS_MAPPING) "|%l|"
-
- MENUSTRING("Reset", UV_RESET_MAPPING);
-#ifndef DISABLE_PYTHON
-#if 0
- XXX
- /* note that we account for the 10 previous entries with i+10: */
- for (pym = BPyMenuTable[PYMENU_UVCALCULATION]; pym; pym = pym->next, i++) {
-
- if (!has_pymenu) {
- strcat(uvmenu, "|%l");
- has_pymenu = 1;
- }
-
- strcat(uvmenu, "|");
- strcat(uvmenu, pym->name);
- strcat(uvmenu, " %x");
- sprintf(menu_number, "%d", i+10);
- strcat(uvmenu, menu_number);
- }
-#endif
-#endif
-
- mode= pupmenu(uvmenu);
-#ifndef DISABLE_PYTHON
-// if (mode >= 10) {
-// BPY_menu_do_python(PYMENU_UVCALCULATION, mode - 10);
-// return;
-// }
-#endif
- switch(mode) {
- case UV_CUBE_MAPPING:
- calculate_uv_map(scene, ar, v3d, em, B_UVAUTO_CUBE); break;
- case UV_CYL_MAPPING:
- calculate_uv_map(scene, ar, v3d, em, B_UVAUTO_CYLINDER); break;
- case UV_SPHERE_MAPPING:
- calculate_uv_map(scene, ar, v3d, em, B_UVAUTO_SPHERE); break;
- case UV_BOUNDS_MAPPING:
- calculate_uv_map(scene, ar, v3d, em, B_UVAUTO_BOUNDS); break;
- case UV_RESET_MAPPING:
- calculate_uv_map(scene, ar, v3d, em, B_UVAUTO_RESET); break;
- case UV_WINDOW_MAPPING:
- calculate_uv_map(scene, ar, v3d, em, B_UVAUTO_WINDOW); break;
- case UV_UNWRAP_MAPPING:
-// XXX unwrap_lscm(0);
- break;
- }
-}
-
/* Texture Paint */
void set_texturepaint(Scene *scene) /* toggle */