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:
Diffstat (limited to 'source/blender/src/drawobject.c')
-rw-r--r--source/blender/src/drawobject.c5555
1 files changed, 0 insertions, 5555 deletions
diff --git a/source/blender/src/drawobject.c b/source/blender/src/drawobject.c
deleted file mode 100644
index db2225f4823..00000000000
--- a/source/blender/src/drawobject.c
+++ /dev/null
@@ -1,5555 +0,0 @@
-/**
- * $Id$
- *
- * ***** BEGIN GPL/BL DUAL LICENSE BLOCK *****
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version. The Blender
- * Foundation also sells licenses for use in proprietary software under
- * the Blender License. See http://www.blender.org/BL/ for information
- * about this.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
- *
- * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
- * All rights reserved.
- *
- * The Original Code is: all of this file.
- *
- * Contributor(s): none yet.
- *
- * ***** END GPL/BL DUAL LICENSE BLOCK *****
- */
-
-#include <string.h>
-#include <math.h>
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#include "MEM_guardedalloc.h"
-
-#include "BMF_Api.h"
-
-#include "IMB_imbuf.h"
-
-
-#include "MTC_matrixops.h"
-
-#include "DNA_armature_types.h"
-#include "DNA_camera_types.h"
-#include "DNA_curve_types.h"
-#include "DNA_constraint_types.h" // for drawing constraint
-#include "DNA_effect_types.h"
-#include "DNA_ipo_types.h"
-#include "DNA_lamp_types.h"
-#include "DNA_lattice_types.h"
-#include "DNA_material_types.h"
-#include "DNA_mesh_types.h"
-#include "DNA_meshdata_types.h"
-#include "DNA_meta_types.h"
-#include "DNA_modifier_types.h"
-#include "DNA_object_types.h"
-#include "DNA_object_force.h"
-#include "DNA_particle_types.h"
-#include "DNA_space_types.h"
-#include "DNA_scene_types.h"
-#include "DNA_screen_types.h"
-#include "DNA_userdef_types.h"
-#include "DNA_view3d_types.h"
-#include "DNA_world_types.h"
-// FSPARTICLE
-#include "DNA_object_fluidsim.h"
-
-#include "BLI_blenlib.h"
-#include "BLI_arithb.h"
-#include "BLI_editVert.h"
-#include "BLI_edgehash.h"
-#include "BLI_rand.h"
-
-#include "BKE_utildefines.h"
-#include "BKE_curve.h"
-#include "BKE_constraint.h" // for the get_constraint_target function
-#include "BKE_DerivedMesh.h"
-#include "BKE_displist.h"
-#include "BKE_effect.h"
-#include "BKE_font.h"
-#include "BKE_global.h"
-#include "BKE_image.h"
-#include "BKE_ipo.h"
-#include "BKE_key.h"
-#include "BKE_lattice.h"
-#include "BKE_mesh.h"
-#include "BKE_material.h"
-#include "BKE_mball.h"
-#include "BKE_modifier.h"
-#include "BKE_object.h"
-#include "BKE_anim.h" //for the where_on_path function
-#include "BKE_particle.h"
-#include "BKE_utildefines.h"
-#ifdef WITH_VERSE
-#include "BKE_verse.h"
-#endif
-
-#include "BIF_editarmature.h"
-#include "BIF_editdeform.h"
-#include "BIF_editmesh.h"
-#include "BIF_editparticle.h"
-#include "BIF_glutil.h"
-#include "BIF_gl.h"
-#include "BIF_glutil.h"
-#include "BIF_mywindow.h"
-#include "BIF_resources.h"
-#include "BIF_retopo.h"
-#include "BIF_screen.h"
-#include "BIF_space.h"
-#include "BIF_toolbox.h"
-
-#include "BDR_drawmesh.h"
-#include "BDR_drawobject.h"
-#include "BDR_editobject.h"
-#include "BDR_sculptmode.h"
-#include "BDR_vpaint.h"
-
-#include "BSE_drawview.h"
-#include "BSE_node.h"
-#include "BSE_trans_types.h"
-#include "BSE_view.h"
-
-#include "blendef.h"
-#include "mydevice.h"
-#include "nla.h"
-
-#include "BKE_deform.h"
-
-/* pretty stupid */
-/* extern Lattice *editLatt; already in BKE_lattice.h */
-/* editcurve.c */
-extern ListBase editNurb;
-/* editmball.c */
-extern ListBase editelems;
-
-static void draw_bounding_volume(Object *ob);
-
-static void drawcube_size(float size);
-static void drawcircle_size(float size);
-static void draw_empty_sphere(float size);
-static void draw_empty_cone(float size);
-
-/* ************* Setting OpenGL Material ************ */
-
-// Materials start counting at # one....
-#define MAXMATBUF (MAXMAT + 1)
-static float matbuf[MAXMATBUF][2][4];
-static int totmat_gl= 0;
-
-int set_gl_material(int nr)
-{
- static int last_gl_matnr= -1;
- static int last_ret_val= 1;
-
- /* prevent index to use un-initialized array items */
- if(nr>totmat_gl) nr= totmat_gl;
-
- if(nr<0) {
- last_gl_matnr= -1;
- last_ret_val= 1;
- }
- else if(nr<MAXMATBUF && nr!=last_gl_matnr) {
- glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, matbuf[nr][0]);
- glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, matbuf[nr][1]);
- last_gl_matnr = nr;
- last_ret_val= matbuf[nr][0][3]!=0.0;
-
- /* matbuf alpha: 0.0 = skip draw, 1.0 = no blending, else blend */
- if(matbuf[nr][0][3]!= 0.0 && matbuf[nr][0][3]!= 1.0) {
- glEnable(GL_BLEND);
- }
- else
- glDisable(GL_BLEND);
-
- }
-
- return last_ret_val;
-}
-
-/* returns 1: when there's alpha needed to be drawn in a 2nd pass */
-int init_gl_materials(Object *ob, int check_alpha)
-{
- extern Material defmaterial; // render module abuse...
- Material *ma;
- int a, has_alpha= 0;
-
- if(ob->totcol==0) {
- matbuf[0][0][0]= defmaterial.r;
- matbuf[0][0][1]= defmaterial.g;
- matbuf[0][0][2]= defmaterial.b;
- matbuf[0][0][3]= 1.0;
-
- matbuf[0][1][0]= defmaterial.specr;
- matbuf[0][1][1]= defmaterial.specg;
- matbuf[0][1][2]= defmaterial.specb;
- matbuf[0][1][3]= 1.0;
-
- /* do material 1 too, for displists! */
- QUATCOPY(matbuf[1][0], matbuf[0][0]);
- QUATCOPY(matbuf[1][1], matbuf[0][1]);
- }
-
- for(a=1; a<=ob->totcol; a++) {
- ma= give_current_material(ob, a);
- ma= editnode_get_active_material(ma);
- if(ma==NULL) ma= &defmaterial;
-
- if(a<MAXMATBUF) {
- if (ma->mode & MA_SHLESS) {
- matbuf[a][0][0]= 2*ma->r;
- matbuf[a][0][1]= 2*ma->g;
- matbuf[a][0][2]= 2*ma->b;
- } else {
- matbuf[a][0][0]= (ma->ref+ma->emit)*ma->r;
- matbuf[a][0][1]= (ma->ref+ma->emit)*ma->g;
- matbuf[a][0][2]= (ma->ref+ma->emit)*ma->b;
- }
-
- /* draw transparent, not in pick-select, nor editmode */
- if(check_alpha && !(G.f & G_PICKSEL) && (ob->dtx & OB_DRAWTRANSP) && !(G.obedit && G.obedit->data==ob->data)) {
- if(G.vd->transp) { // drawing the transparent pass
- if(ma->alpha==1.0) matbuf[a][0][3]= 0.0; // means skip solid
- else matbuf[a][0][3]= ma->alpha;
- }
- else { // normal pass
- if(ma->alpha==1.0) matbuf[a][0][3]= 1.0;
- else {
- matbuf[a][0][3]= 0.0; // means skip transparent
- has_alpha= 1; // return value, to indicate adding to after-draw queue
- }
- }
- }
- else
- matbuf[a][0][3]= 1.0;
-
- if (!(ma->mode & MA_SHLESS)) {
- matbuf[a][1][0]= ma->spec*ma->specr;
- matbuf[a][1][1]= ma->spec*ma->specg;
- matbuf[a][1][2]= ma->spec*ma->specb;
- matbuf[a][1][3]= 1.0;
- }
- }
- }
-
- totmat_gl= ob->totcol;
- set_gl_material(-1); // signal for static variable
- return has_alpha;
-}
-
-
- /***/
-static unsigned int colortab[24]=
- {0x0, 0xFF88FF, 0xFFBBFF,
- 0x403000, 0xFFFF88, 0xFFFFBB,
- 0x104040, 0x66CCCC, 0x77CCCC,
- 0x104010, 0x55BB55, 0x66FF66,
- 0xFFFFFF
-};
-
-
-static float cube[8][3] = {
- {-1.0, -1.0, -1.0},
- {-1.0, -1.0, 1.0},
- {-1.0, 1.0, 1.0},
- {-1.0, 1.0, -1.0},
- { 1.0, -1.0, -1.0},
- { 1.0, -1.0, 1.0},
- { 1.0, 1.0, 1.0},
- { 1.0, 1.0, -1.0},
-};
-
-/* ----------------- OpenGL Circle Drawing - Tables for Optimised Drawing Speed ------------------ */
-/* 32 values of sin function (still same result!) */
-static float sinval[32] = {
- 0.00000000,
- 0.20129852,
- 0.39435585,
- 0.57126821,
- 0.72479278,
- 0.84864425,
- 0.93775213,
- 0.98846832,
- 0.99871650,
- 0.96807711,
- 0.89780453,
- 0.79077573,
- 0.65137248,
- 0.48530196,
- 0.29936312,
- 0.10116832,
- -0.10116832,
- -0.29936312,
- -0.48530196,
- -0.65137248,
- -0.79077573,
- -0.89780453,
- -0.96807711,
- -0.99871650,
- -0.98846832,
- -0.93775213,
- -0.84864425,
- -0.72479278,
- -0.57126821,
- -0.39435585,
- -0.20129852,
- 0.00000000
-};
-
-/* 32 values of cos function (still same result!) */
-static float cosval[32] ={
- 1.00000000,
- 0.97952994,
- 0.91895781,
- 0.82076344,
- 0.68896691,
- 0.52896401,
- 0.34730525,
- 0.15142777,
- -0.05064916,
- -0.25065253,
- -0.44039415,
- -0.61210598,
- -0.75875812,
- -0.87434661,
- -0.95413925,
- -0.99486932,
- -0.99486932,
- -0.95413925,
- -0.87434661,
- -0.75875812,
- -0.61210598,
- -0.44039415,
- -0.25065253,
- -0.05064916,
- 0.15142777,
- 0.34730525,
- 0.52896401,
- 0.68896691,
- 0.82076344,
- 0.91895781,
- 0.97952994,
- 1.00000000
-};
-
-/* flag is same as for draw_object */
-void drawaxes(float size, int flag, char drawtype)
-{
- int axis;
- float v1[3]= {0.0, 0.0, 0.0};
- float v2[3]= {0.0, 0.0, 0.0};
- float v3[3]= {0.0, 0.0, 0.0};
-
- switch(drawtype) {
-
- case OB_PLAINAXES:
- for (axis=0; axis<3; axis++) {
- float v1[3]= {0.0, 0.0, 0.0};
- float v2[3]= {0.0, 0.0, 0.0};
-
- glBegin(GL_LINES);
-
- v1[axis]= size;
- v2[axis]= -size;
- glVertex3fv(v1);
- glVertex3fv(v2);
-
- glEnd();
- }
- break;
- case OB_SINGLE_ARROW:
-
- glBegin(GL_LINES);
- /* in positive z direction only */
- v1[2]= size;
- glVertex3fv(v1);
- glVertex3fv(v2);
- glEnd();
-
- /* square pyramid */
- glBegin(GL_TRIANGLES);
-
- v2[0]= size*0.035; v2[1] = size*0.035;
- v3[0]= size*-0.035; v3[1] = size*0.035;
- v2[2]= v3[2]= size*0.75;
-
- for (axis=0; axis<4; axis++) {
- if (axis % 2 == 1) {
- v2[0] *= -1;
- v3[1] *= -1;
- } else {
- v2[1] *= -1;
- v3[0] *= -1;
- }
-
- glVertex3fv(v1);
- glVertex3fv(v2);
- glVertex3fv(v3);
-
- }
- glEnd();
-
- break;
- case OB_CUBE:
- drawcube_size(size);
- break;
-
- case OB_CIRCLE:
- drawcircle_size(size);
- break;
-
- case OB_EMPTY_SPHERE:
- draw_empty_sphere(size);
- break;
-
- case OB_EMPTY_CONE:
- draw_empty_cone(size);
- break;
-
- case OB_ARROWS:
- default:
- for (axis=0; axis<3; axis++) {
- float v1[3]= {0.0, 0.0, 0.0};
- float v2[3]= {0.0, 0.0, 0.0};
- int arrow_axis= (axis==0)?1:0;
-
- glBegin(GL_LINES);
-
- v2[axis]= size;
- glVertex3fv(v1);
- glVertex3fv(v2);
-
- v1[axis]= size*0.8;
- v1[arrow_axis]= -size*0.125;
- glVertex3fv(v1);
- glVertex3fv(v2);
-
- v1[arrow_axis]= size*0.125;
- glVertex3fv(v1);
- glVertex3fv(v2);
-
- glEnd();
-
- v2[axis]+= size*0.125;
- glRasterPos3fv(v2);
-
- // patch for 3d cards crashing on glSelect for text drawing (IBM)
- if((flag & DRAW_PICKING) == 0) {
- if (axis==0)
- BMF_DrawString(G.font, "x");
- else if (axis==1)
- BMF_DrawString(G.font, "y");
- else
- BMF_DrawString(G.font, "z");
- }
- }
- break;
- }
-}
-
-/* circle for object centers, special_color is for library or ob users */
-static void drawcentercircle(float *vec, int selstate, int special_color)
-{
- View3D *v3d= G.vd;
- float size;
-
- size= v3d->persmat[0][3]*vec[0]+ v3d->persmat[1][3]*vec[1]+ v3d->persmat[2][3]*vec[2]+ v3d->persmat[3][3];
- size*= v3d->pixsize*((float)U.obcenter_dia*0.5f);
-
- /* using gldepthfunc guarantees that it does write z values, but not checks for it, so centers remain visible independt order of drawing */
- if(v3d->zbuf) glDepthFunc(GL_ALWAYS);
- glEnable(GL_BLEND);
-
- if(special_color) {
-#ifdef WITH_VERSE
- if (selstate==VERSE) glColor4ub(0x00, 0xFF, 0x00, 155);
- else if (selstate==ACTIVE || selstate==SELECT) glColor4ub(0x88, 0xFF, 0xFF, 155);
-#else
- if (selstate==ACTIVE || selstate==SELECT) glColor4ub(0x88, 0xFF, 0xFF, 155);
-#endif
-
- else glColor4ub(0x55, 0xCC, 0xCC, 155);
- }
- else {
- if (selstate == ACTIVE) BIF_ThemeColorShadeAlpha(TH_ACTIVE, 0, -80);
- else if (selstate == SELECT) BIF_ThemeColorShadeAlpha(TH_SELECT, 0, -80);
- else if (selstate == DESELECT) BIF_ThemeColorShadeAlpha(TH_TRANSFORM, 0, -80);
- }
- drawcircball(GL_POLYGON, vec, size, v3d->viewinv);
-
- BIF_ThemeColorShadeAlpha(TH_WIRE, 0, -30);
- drawcircball(GL_LINE_LOOP, vec, size, v3d->viewinv);
-
- glDisable(GL_BLEND);
- if(v3d->zbuf) glDepthFunc(GL_LEQUAL);
-}
-
-
-void drawsolidcube(float size)
-{
- float n[3];
-
- glPushMatrix();
- glScalef(size, size, size);
-
- n[0]=0; n[1]=0; n[2]=0;
- glBegin(GL_QUADS);
- n[0]= -1.0;
- glNormal3fv(n);
- glVertex3fv(cube[0]); glVertex3fv(cube[1]); glVertex3fv(cube[2]); glVertex3fv(cube[3]);
- n[0]=0;
- glEnd();
-
- glBegin(GL_QUADS);
- n[1]= -1.0;
- glNormal3fv(n);
- glVertex3fv(cube[0]); glVertex3fv(cube[4]); glVertex3fv(cube[5]); glVertex3fv(cube[1]);
- n[1]=0;
- glEnd();
-
- glBegin(GL_QUADS);
- n[0]= 1.0;
- glNormal3fv(n);
- glVertex3fv(cube[4]); glVertex3fv(cube[7]); glVertex3fv(cube[6]); glVertex3fv(cube[5]);
- n[0]=0;
- glEnd();
-
- glBegin(GL_QUADS);
- n[1]= 1.0;
- glNormal3fv(n);
- glVertex3fv(cube[7]); glVertex3fv(cube[3]); glVertex3fv(cube[2]); glVertex3fv(cube[6]);
- n[1]=0;
- glEnd();
-
- glBegin(GL_QUADS);
- n[2]= 1.0;
- glNormal3fv(n);
- glVertex3fv(cube[1]); glVertex3fv(cube[5]); glVertex3fv(cube[6]); glVertex3fv(cube[2]);
- n[2]=0;
- glEnd();
-
- glBegin(GL_QUADS);
- n[2]= -1.0;
- glNormal3fv(n);
- glVertex3fv(cube[7]); glVertex3fv(cube[4]); glVertex3fv(cube[0]); glVertex3fv(cube[3]);
- glEnd();
-
- glPopMatrix();
-}
-
-static void drawcube(void)
-{
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(cube[0]); glVertex3fv(cube[1]);glVertex3fv(cube[2]); glVertex3fv(cube[3]);
- glVertex3fv(cube[0]); glVertex3fv(cube[4]);glVertex3fv(cube[5]); glVertex3fv(cube[6]);
- glVertex3fv(cube[7]); glVertex3fv(cube[4]);
- glEnd();
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(cube[1]); glVertex3fv(cube[5]);
- glEnd();
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(cube[2]); glVertex3fv(cube[6]);
- glEnd();
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(cube[3]); glVertex3fv(cube[7]);
- glEnd();
-}
-
-/* draws a cube on given the scaling of the cube, assuming that
- * all required matrices have been set (used for drawing empties)
- */
-static void drawcube_size(float size)
-{
- glBegin(GL_LINE_STRIP);
- glVertex3f(-size,-size,-size); glVertex3f(-size,-size,size);glVertex3f(-size,size,size); glVertex3f(-size,size,-size);
- glVertex3f(-size,-size,-size); glVertex3f(size,-size,-size);glVertex3f(size,-size,size); glVertex3f(size,size,size);
- glVertex3f(size,size,-size); glVertex3f(size,-size,-size);
- glEnd();
-
- glBegin(GL_LINE_STRIP);
- glVertex3f(-size,-size,size); glVertex3f(size,-size,size);
- glEnd();
-
- glBegin(GL_LINE_STRIP);
- glVertex3f(-size,size,size); glVertex3f(size,size,size);
- glEnd();
-
- glBegin(GL_LINE_STRIP);
- glVertex3f(-size,size,-size); glVertex3f(size,size,-size);
- glEnd();
-}
-
-/* this is an unused (old) cube-drawing function based on a given size */
-#if 0
-static void drawcube_size(float *size)
-{
-
- glPushMatrix();
- glScalef(size[0], size[1], size[2]);
-
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(cube[0]); glVertex3fv(cube[1]);glVertex3fv(cube[2]); glVertex3fv(cube[3]);
- glVertex3fv(cube[0]); glVertex3fv(cube[4]);glVertex3fv(cube[5]); glVertex3fv(cube[6]);
- glVertex3fv(cube[7]); glVertex3fv(cube[4]);
- glEnd();
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(cube[1]); glVertex3fv(cube[5]);
- glEnd();
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(cube[2]); glVertex3fv(cube[6]);
- glEnd();
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(cube[3]); glVertex3fv(cube[7]);
- glEnd();
-
- glPopMatrix();
-}
-#endif
-
-static void drawshadbuflimits(Lamp *la, float mat[][4])
-{
- float sta[3], end[3], lavec[3];
-
- lavec[0]= -mat[2][0];
- lavec[1]= -mat[2][1];
- lavec[2]= -mat[2][2];
- Normalize(lavec);
-
- sta[0]= mat[3][0]+ la->clipsta*lavec[0];
- sta[1]= mat[3][1]+ la->clipsta*lavec[1];
- sta[2]= mat[3][2]+ la->clipsta*lavec[2];
-
- end[0]= mat[3][0]+ la->clipend*lavec[0];
- end[1]= mat[3][1]+ la->clipend*lavec[1];
- end[2]= mat[3][2]+ la->clipend*lavec[2];
-
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(sta);
- glVertex3fv(end);
- glEnd();
-
- glPointSize(3.0);
- bglBegin(GL_POINTS);
- bglVertex3fv(sta);
- bglVertex3fv(end);
- bglEnd();
- glPointSize(1.0);
-}
-
-
-
-static void spotvolume(float *lvec, float *vvec, float inp)
-{
- /* camera is at 0,0,0 */
- float temp[3],plane[3],mat1[3][3],mat2[3][3],mat3[3][3],mat4[3][3],q[4],co,si,angle;
-
- Normalize(lvec);
- Normalize(vvec); /* is this the correct vector ? */
-
- Crossf(temp,vvec,lvec); /* equation for a plane through vvec en lvec */
- Crossf(plane,lvec,temp); /* a plane perpendicular to this, parrallel with lvec */
-
- Normalize(plane);
-
- /* now we've got two equations: one of a cone and one of a plane, but we have
- three unknowns. We remove one unkown by rotating the plane to z=0 (the plane normal) */
-
- /* rotate around cross product vector of (0,0,1) and plane normal, dot product degrees */
- /* according definition, we derive cross product is (plane[1],-plane[0],0), en cos = plane[2]);*/
-
- /* translating this comment to english didnt really help me understanding the math! :-) (ton) */
-
- q[1] = plane[1] ;
- q[2] = -plane[0] ;
- q[3] = 0 ;
- Normalize(&q[1]);
-
- angle = saacos(plane[2])/2.0;
- co = cos(angle);
- si = sqrt(1-co*co);
-
- q[0] = co;
- q[1] *= si;
- q[2] *= si;
- q[3] = 0;
-
- QuatToMat3(q,mat1);
-
- /* rotate lamp vector now over acos(inp) degrees */
-
- vvec[0] = lvec[0] ;
- vvec[1] = lvec[1] ;
- vvec[2] = lvec[2] ;
-
- Mat3One(mat2);
- co = inp;
- si = sqrt(1-inp*inp);
-
- mat2[0][0] = co;
- mat2[1][0] = -si;
- mat2[0][1] = si;
- mat2[1][1] = co;
- Mat3MulMat3(mat3,mat2,mat1);
-
- mat2[1][0] = si;
- mat2[0][1] = -si;
- Mat3MulMat3(mat4,mat2,mat1);
- Mat3Transp(mat1);
-
- Mat3MulMat3(mat2,mat1,mat3);
- Mat3MulVecfl(mat2,lvec);
- Mat3MulMat3(mat2,mat1,mat4);
- Mat3MulVecfl(mat2,vvec);
-
- return;
-}
-
-static void drawlamp(Object *ob)
-{
- Lamp *la;
- View3D *v3d= G.vd;
- float vec[3], lvec[3], vvec[3], circrad, x,y,z;
- float pixsize, lampsize;
- float imat[4][4], curcol[4];
- char col[4];
-
- la= ob->data;
-
- /* we first draw only the screen aligned & fixed scale stuff */
- glPushMatrix();
- myloadmatrix(G.vd->viewmat);
-
- /* lets calculate the scale: */
- pixsize= v3d->persmat[0][3]*ob->obmat[3][0]+ v3d->persmat[1][3]*ob->obmat[3][1]+ v3d->persmat[2][3]*ob->obmat[3][2]+ v3d->persmat[3][3];
- pixsize*= v3d->pixsize;
- lampsize= pixsize*((float)U.obcenter_dia*0.5f);
-
- /* and view aligned matrix: */
- Mat4CpyMat4(imat, G.vd->viewinv);
- Normalize(imat[0]);
- Normalize(imat[1]);
-
- /* for AA effects */
- glGetFloatv(GL_CURRENT_COLOR, curcol);
- curcol[3]= 0.6;
- glColor4fv(curcol);
-
- if(ob->id.us>1) {
- if (ob==OBACT || (ob->flag & SELECT)) glColor4ub(0x88, 0xFF, 0xFF, 155);
- else glColor4ub(0x77, 0xCC, 0xCC, 155);
- }
-
- /* Inner Circle */
- VECCOPY(vec, ob->obmat[3]);
- glEnable(GL_BLEND);
- drawcircball(GL_LINE_LOOP, vec, lampsize, imat);
- glDisable(GL_BLEND);
- drawcircball(GL_POLYGON, vec, lampsize, imat);
-
- /* restore */
- if(ob->id.us>1)
- glColor4fv(curcol);
-
- /* Outer circle */
- circrad = 3.0f*lampsize;
- drawcircball(GL_LINE_LOOP, vec, circrad, imat);
-
- setlinestyle(3);
-
- /* draw dashed outer circle if shadow is on. remember some lamps can't have certain shadows! */
- if (la->type!=LA_HEMI) {
- if ((la->mode & LA_SHAD_RAY) ||
- ((la->mode & LA_SHAD_BUF) && (la->type==LA_SPOT)) )
- {
- drawcircball(GL_LINE_LOOP, vec, circrad + 3.0f*pixsize, imat);
- }
- }
-
- /* draw the pretty sun rays */
- if(la->type==LA_SUN) {
- float v1[3], v2[3], mat[3][3];
- short axis;
-
- /* setup a 45 degree rotation matrix */
- VecRotToMat3(imat[2], M_PI/4.0f, mat);
-
- /* vectors */
- VECCOPY(v1, imat[0]);
- VecMulf(v1, circrad*1.2f);
- VECCOPY(v2, imat[0]);
- VecMulf(v2, circrad*2.5f);
-
- /* center */
- glTranslatef(vec[0], vec[1], vec[2]);
-
- setlinestyle(3);
-
- glBegin(GL_LINES);
- for (axis=0; axis<8; axis++) {
- glVertex3fv(v1);
- glVertex3fv(v2);
- Mat3MulVecfl(mat, v1);
- Mat3MulVecfl(mat, v2);
- }
- glEnd();
-
- glTranslatef(-vec[0], -vec[1], -vec[2]);
-
- }
-
- if (la->type==LA_LOCAL) {
- if(la->mode & LA_SPHERE) {
- drawcircball(GL_LINE_LOOP, vec, la->dist, imat);
- }
- /* yafray: for photonlight also draw lightcone as for spot */
- }
-
- glPopMatrix(); /* back in object space */
- vec[0]= vec[1]= vec[2]= 0.0f;
-
- if ((la->type==LA_SPOT) || (la->type==LA_YF_PHOTON)) {
- lvec[0]=lvec[1]= 0.0;
- lvec[2] = 1.0;
- x = G.vd->persmat[0][2];
- y = G.vd->persmat[1][2];
- z = G.vd->persmat[2][2];
- vvec[0]= x*ob->obmat[0][0] + y*ob->obmat[0][1] + z*ob->obmat[0][2];
- vvec[1]= x*ob->obmat[1][0] + y*ob->obmat[1][1] + z*ob->obmat[1][2];
- vvec[2]= x*ob->obmat[2][0] + y*ob->obmat[2][1] + z*ob->obmat[2][2];
-
- y = cos( M_PI*la->spotsize/360.0 );
- spotvolume(lvec, vvec, y);
- x = -la->dist;
- lvec[0] *= x ;
- lvec[1] *= x ;
- lvec[2] *= x;
- vvec[0] *= x ;
- vvec[1] *= x ;
- vvec[2] *= x;
-
- /* draw the angled sides of the cone */
- glBegin(GL_LINE_STRIP);
- glVertex3fv(vvec);
- glVertex3fv(vec);
- glVertex3fv(lvec);
- glEnd();
-
- z = x*sqrt(1.0 - y*y);
- x *= y;
-
- /* draw the circle/square at the end of the cone */
- glTranslatef(0.0, 0.0 , x);
- if(la->mode & LA_SQUARE) {
- vvec[0]= fabs(z);
- vvec[1]= fabs(z);
- vvec[2]= 0.0;
- glBegin(GL_LINE_LOOP);
- glVertex3fv(vvec);
- vvec[1]= -fabs(z);
- glVertex3fv(vvec);
- vvec[0]= -fabs(z);
- glVertex3fv(vvec);
- vvec[1]= fabs(z);
- glVertex3fv(vvec);
- glEnd();
- }
- else circ(0.0, 0.0, fabs(z));
-
- /* draw the circle/square representing spotbl */
- if(la->type==LA_SPOT) {
- float spotblcirc = fabs(z)*(1 - pow(la->spotblend, 2));
- /* make sure the line is always visible - prevent it from reaching the outer border (or 0)
- * values are kinda arbitrary - just what seemed to work well */
- if (spotblcirc == 0) spotblcirc = 0.15;
- else if (spotblcirc == fabs(z)) spotblcirc = fabs(z) - 0.07;
- circ(0.0, 0.0, spotblcirc);
- }
-
- }
- else if ELEM(la->type, LA_HEMI, LA_SUN) {
-
- /* draw the line from the circle along the dist */
- glBegin(GL_LINE_STRIP);
- vec[2] = -circrad;
- glVertex3fv(vec);
- vec[2]= -la->dist;
- glVertex3fv(vec);
- glEnd();
-
- if(la->type==LA_HEMI) {
- /* draw the hemisphere curves */
- short axis, steps, dir;
- float outdist, zdist, mul;
- vec[0]=vec[1]=vec[2]= 0.0;
- outdist = 0.14; mul = 1.4; dir = 1;
-
- setlinestyle(4);
- /* loop over the 4 compass points, and draw each arc as a LINE_STRIP */
- for (axis=0; axis<4; axis++) {
- float v[3]= {0.0, 0.0, 0.0};
- zdist = 0.02;
-
- glBegin(GL_LINE_STRIP);
-
- for (steps=0; steps<6; steps++) {
- if (axis == 0 || axis == 1) { /* x axis up, x axis down */
- /* make the arcs start at the edge of the energy circle */
- if (steps == 0) v[0] = dir*circrad;
- else v[0] = v[0] + dir*(steps*outdist);
- } else if (axis == 2 || axis == 3) { /* y axis up, y axis down */
- /* make the arcs start at the edge of the energy circle */
- if (steps == 0) v[1] = dir*circrad;
- else v[1] = v[1] + dir*(steps*outdist);
- }
-
- v[2] = v[2] - steps*zdist;
-
- glVertex3fv(v);
-
- zdist = zdist * mul;
- }
-
- glEnd();
- /* flip the direction */
- dir = -dir;
- }
- }
- } else if(la->type==LA_AREA) {
- setlinestyle(3);
- if(la->area_shape==LA_AREA_SQUARE)
- fdrawbox(-la->area_size*0.5, -la->area_size*0.5, la->area_size*0.5, la->area_size*0.5);
- else if(la->area_shape==LA_AREA_RECT)
- fdrawbox(-la->area_size*0.5, -la->area_sizey*0.5, la->area_size*0.5, la->area_sizey*0.5);
-
- glBegin(GL_LINE_STRIP);
- glVertex3f(0.0,0.0,-circrad);
- glVertex3f(0.0,0.0,-la->dist);
- glEnd();
- }
-
- /* and back to viewspace */
- myloadmatrix(G.vd->viewmat);
- VECCOPY(vec, ob->obmat[3]);
-
- setlinestyle(0);
-
- if(la->type==LA_SPOT && (la->mode & LA_SHAD_BUF) ) {
- drawshadbuflimits(la, ob->obmat);
- }
-
- BIF_GetThemeColor4ubv(TH_LAMP, col);
- glColor4ub(col[0], col[1], col[2], col[3]);
-
- glEnable(GL_BLEND);
-
- if (vec[2]>0) vec[2] -= circrad;
- else vec[2] += circrad;
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(vec);
- vec[2]= 0;
- glVertex3fv(vec);
- glEnd();
-
- glPointSize(2.0);
- glBegin(GL_POINTS);
- glVertex3fv(vec);
- glEnd();
- glPointSize(1.0);
-
- glDisable(GL_BLEND);
-
- /* restore for drawing extra stuff */
- glColor3fv(curcol);
-
-}
-
-static void draw_limit_line(float sta, float end, unsigned int col)
-{
- glBegin(GL_LINES);
- glVertex3f(0.0, 0.0, -sta);
- glVertex3f(0.0, 0.0, -end);
- glEnd();
-
- glPointSize(3.0);
- glBegin(GL_POINTS);
- cpack(col);
- glVertex3f(0.0, 0.0, -sta);
- glVertex3f(0.0, 0.0, -end);
- glEnd();
- glPointSize(1.0);
-}
-
-
-/* yafray: draw camera focus point (cross, similar to aqsis code in tuhopuu) */
-/* qdn: now also enabled for Blender to set focus point for defocus composit node */
-static void draw_focus_cross(float dist, float size)
-{
- glBegin(GL_LINES);
- glVertex3f(-size, 0.f, -dist);
- glVertex3f(size, 0.f, -dist);
- glVertex3f(0.f, -size, -dist);
- glVertex3f(0.f, size, -dist);
- glEnd();
-}
-
-/* flag similar to draw_object() */
-static void drawcamera(Object *ob, int flag)
-{
- /* a standing up pyramid with (0,0,0) as top */
- Camera *cam;
- World *wrld;
- float vec[8][4], tmat[4][4], fac, facx, facy, depth;
- int i;
-
- cam= ob->data;
-
- glDisable(GL_LIGHTING);
- glDisable(GL_CULL_FACE);
-
- if(G.vd->persp>=2 && cam->type==CAM_ORTHO && ob==G.vd->camera) {
- facx= 0.5*cam->ortho_scale*1.28;
- facy= 0.5*cam->ortho_scale*1.024;
- depth= -cam->clipsta-0.1;
- }
- else {
- fac= cam->drawsize;
- if(G.vd->persp>=2 && ob==G.vd->camera) fac= cam->clipsta+0.1; /* that way it's always visible */
-
- depth= - fac*cam->lens/16.0;
- facx= fac*1.28;
- facy= fac*1.024;
- }
-
- vec[0][0]= 0.0; vec[0][1]= 0.0; vec[0][2]= 0.001; /* GLBUG: for picking at iris Entry (well thats old!) */
- vec[1][0]= facx; vec[1][1]= facy; vec[1][2]= depth;
- vec[2][0]= facx; vec[2][1]= -facy; vec[2][2]= depth;
- vec[3][0]= -facx; vec[3][1]= -facy; vec[3][2]= depth;
- vec[4][0]= -facx; vec[4][1]= facy; vec[4][2]= depth;
-
- glBegin(GL_LINE_LOOP);
- glVertex3fv(vec[1]);
- glVertex3fv(vec[2]);
- glVertex3fv(vec[3]);
- glVertex3fv(vec[4]);
- glEnd();
-
-
- if(G.vd->persp>=2 && ob==G.vd->camera) return;
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(vec[2]);
- glVertex3fv(vec[0]);
- glVertex3fv(vec[1]);
- glVertex3fv(vec[4]);
- glVertex3fv(vec[0]);
- glVertex3fv(vec[3]);
- glEnd();
-
-
- /* arrow on top */
- vec[0][2]= depth;
-
-
- /* draw an outline arrow for inactive cameras and filled
- * for active cameras. We actually draw both outline+filled
- * for active cameras so the wire can be seen side-on */
- for (i=0;i<2;i++) {
- if (i==0) glBegin(GL_LINE_LOOP);
- else if (i==1 && (ob == G.vd->camera)) glBegin(GL_TRIANGLES);
- else break;
-
- vec[0][0]= -0.7*cam->drawsize;
- vec[0][1]= 1.1*cam->drawsize;
- glVertex3fv(vec[0]);
-
- vec[0][0]= 0.0;
- vec[0][1]= 1.8*cam->drawsize;
- glVertex3fv(vec[0]);
-
- vec[0][0]= 0.7*cam->drawsize;
- vec[0][1]= 1.1*cam->drawsize;
- glVertex3fv(vec[0]);
-
- glEnd();
- }
-
- if(flag==0) {
- if(cam->flag & (CAM_SHOWLIMITS+CAM_SHOWMIST)) {
- myloadmatrix(G.vd->viewmat);
- Mat4CpyMat4(vec, ob->obmat);
- Mat4Ortho(vec);
- mymultmatrix(vec);
-
- MTC_Mat4SwapMat4(G.vd->persmat, tmat);
- mygetsingmatrix(G.vd->persmat);
-
- if(cam->flag & CAM_SHOWLIMITS) {
- draw_limit_line(cam->clipsta, cam->clipend, 0x77FFFF);
- /* qdn: was yafray only, now also enabled for Blender to be used with defocus composit node */
- draw_focus_cross(dof_camera(ob), cam->drawsize);
- }
-
- wrld= G.scene->world;
- if(cam->flag & CAM_SHOWMIST)
- if(wrld) draw_limit_line(wrld->miststa, wrld->miststa+wrld->mistdist, 0xFFFFFF);
-
- MTC_Mat4SwapMat4(G.vd->persmat, tmat);
- }
- }
-}
-
-static void lattice_draw_verts(Lattice *lt, DispList *dl, short sel)
-{
- BPoint *bp = lt->def;
- float *co = dl?dl->verts:NULL;
- int u, v, w;
-
- BIF_ThemeColor(sel?TH_VERTEX_SELECT:TH_VERTEX);
- glPointSize(BIF_GetThemeValuef(TH_VERTEX_SIZE));
- bglBegin(GL_POINTS);
-
- for(w=0; w<lt->pntsw; w++) {
- int wxt = (w==0 || w==lt->pntsw-1);
- for(v=0; v<lt->pntsv; v++) {
- int vxt = (v==0 || v==lt->pntsv-1);
- for(u=0; u<lt->pntsu; u++, bp++, co+=3) {
- int uxt = (u==0 || u==lt->pntsu-1);
- if(!(lt->flag & LT_OUTSIDE) || uxt || vxt || wxt) {
- if(bp->hide==0) {
- if((bp->f1 & SELECT)==sel) {
- bglVertex3fv(dl?co:bp->vec);
- }
- }
- }
- }
- }
- }
-
- glPointSize(1.0);
- bglEnd();
-}
-
-void lattice_foreachScreenVert(void (*func)(void *userData, BPoint *bp, int x, int y), void *userData)
-{
- int i, N = editLatt->pntsu*editLatt->pntsv*editLatt->pntsw;
- DispList *dl = find_displist(&G.obedit->disp, DL_VERTS);
- float *co = dl?dl->verts:NULL;
- BPoint *bp = editLatt->def;
- float pmat[4][4], vmat[4][4];
- short s[2];
-
- view3d_get_object_project_mat(curarea, G.obedit, pmat, vmat);
-
- for (i=0; i<N; i++, bp++, co+=3) {
- if (bp->hide==0) {
- view3d_project_short_clip(curarea, dl?co:bp->vec, s, pmat, vmat);
- func(userData, bp, s[0], s[1]);
- }
- }
-}
-
-static void drawlattice__point(Lattice *lt, DispList *dl, int u, int v, int w, int use_wcol)
-{
- int index = ((w*lt->pntsv + v)*lt->pntsu) + u;
-
- if(use_wcol) {
- float col[3];
- MDeformWeight *mdw= get_defweight (lt->dvert+index, use_wcol-1);
-
- weight_to_rgb(mdw?mdw->weight:0.0f, col, col+1, col+2);
- glColor3fv(col);
- }
-
- if (dl) {
- glVertex3fv(&dl->verts[index*3]);
- } else {
- glVertex3fv(lt->def[index].vec);
- }
-}
-
-/* lattice color is hardcoded, now also shows weightgroup values in edit mode */
-static void drawlattice(Object *ob)
-{
- Lattice *lt;
- DispList *dl;
- int u, v, w;
- int use_wcol= 0;
-
- lt= (ob==G.obedit)?editLatt:ob->data;
- dl= find_displist(&ob->disp, DL_VERTS);
- if(ob==G.obedit) {
- cpack(0x004000);
-
- if(ob->defbase.first && lt->dvert) {
- use_wcol= ob->actdef;
- glShadeModel(GL_SMOOTH);
- }
- }
-
- glBegin(GL_LINES);
- for(w=0; w<lt->pntsw; w++) {
- int wxt = (w==0 || w==lt->pntsw-1);
- for(v=0; v<lt->pntsv; v++) {
- int vxt = (v==0 || v==lt->pntsv-1);
- for(u=0; u<lt->pntsu; u++) {
- int uxt = (u==0 || u==lt->pntsu-1);
-
- if(w && ((uxt || vxt) || !(lt->flag & LT_OUTSIDE))) {
- drawlattice__point(lt, dl, u, v, w-1, use_wcol);
- drawlattice__point(lt, dl, u, v, w, use_wcol);
- }
- if(v && ((uxt || wxt) || !(lt->flag & LT_OUTSIDE))) {
- drawlattice__point(lt, dl, u, v-1, w, use_wcol);
- drawlattice__point(lt, dl, u, v, w, use_wcol);
- }
- if(u && ((vxt || wxt) || !(lt->flag & LT_OUTSIDE))) {
- drawlattice__point(lt, dl, u-1, v, w, use_wcol);
- drawlattice__point(lt, dl, u, v, w, use_wcol);
- }
- }
- }
- }
- glEnd();
-
- /* restoration for weight colors */
- if(use_wcol)
- glShadeModel(GL_FLAT);
-
- if(ob==G.obedit) {
- if(G.vd->zbuf) glDisable(GL_DEPTH_TEST);
-
- lattice_draw_verts(lt, dl, 0);
- lattice_draw_verts(lt, dl, 1);
-
- if(G.vd->zbuf) glEnable(GL_DEPTH_TEST);
- }
-}
-
-/* ***************** ******************** */
-
-static void mesh_foreachScreenVert__mapFunc(void *userData, int index, float *co, float *no_f, short *no_s)
-{
- struct { void (*func)(void *userData, EditVert *eve, int x, int y, int index); void *userData; int clipVerts; float pmat[4][4], vmat[4][4]; } *data = userData;
- EditVert *eve = EM_get_vert_for_index(index);
- short s[2];
-
- if (eve->h==0) {
- if (data->clipVerts) {
- view3d_project_short_clip(curarea, co, s, data->pmat, data->vmat);
- } else {
- view3d_project_short_noclip(curarea, co, s, data->pmat);
- }
-
- data->func(data->userData, eve, s[0], s[1], index);
- }
-}
-void mesh_foreachScreenVert(void (*func)(void *userData, EditVert *eve, int x, int y, int index), void *userData, int clipVerts)
-{
- struct { void (*func)(void *userData, EditVert *eve, int x, int y, int index); void *userData; int clipVerts; float pmat[4][4], vmat[4][4]; } data;
- DerivedMesh *dm = editmesh_get_derived_cage(CD_MASK_BAREMESH);
-
- data.func = func;
- data.userData = userData;
- data.clipVerts = clipVerts;
-
- view3d_get_object_project_mat(curarea, G.obedit, data.pmat, data.vmat);
-
- EM_init_index_arrays(1, 0, 0);
- dm->foreachMappedVert(dm, mesh_foreachScreenVert__mapFunc, &data);
- EM_free_index_arrays();
-
- dm->release(dm);
-}
-
-static void mesh_foreachScreenEdge__mapFunc(void *userData, int index, float *v0co, float *v1co)
-{
- struct { void (*func)(void *userData, EditEdge *eed, int x0, int y0, int x1, int y1, int index); void *userData; int clipVerts; float pmat[4][4], vmat[4][4]; } *data = userData;
- EditEdge *eed = EM_get_edge_for_index(index);
- short s[2][2];
-
- if (eed->h==0) {
- if (data->clipVerts==1) {
- view3d_project_short_clip(curarea, v0co, s[0], data->pmat, data->vmat);
- view3d_project_short_clip(curarea, v1co, s[1], data->pmat, data->vmat);
- } else {
- view3d_project_short_noclip(curarea, v0co, s[0], data->pmat);
- view3d_project_short_noclip(curarea, v1co, s[1], data->pmat);
-
- if (data->clipVerts==2) {
- if (!(s[0][0]>=0 && s[0][1]>= 0 && s[0][0]<curarea->winx && s[0][1]<curarea->winy))
- if (!(s[1][0]>=0 && s[1][1]>= 0 && s[1][0]<curarea->winx && s[1][1]<curarea->winy))
- return;
- }
- }
-
- data->func(data->userData, eed, s[0][0], s[0][1], s[1][0], s[1][1], index);
- }
-}
-void mesh_foreachScreenEdge(void (*func)(void *userData, EditEdge *eed, int x0, int y0, int x1, int y1, int index), void *userData, int clipVerts)
-{
- struct { void (*func)(void *userData, EditEdge *eed, int x0, int y0, int x1, int y1, int index); void *userData; int clipVerts; float pmat[4][4], vmat[4][4]; } data;
- DerivedMesh *dm = editmesh_get_derived_cage(CD_MASK_BAREMESH);
-
- data.func = func;
- data.userData = userData;
- data.clipVerts = clipVerts;
-
- view3d_get_object_project_mat(curarea, G.obedit, data.pmat, data.vmat);
-
- EM_init_index_arrays(0, 1, 0);
- dm->foreachMappedEdge(dm, mesh_foreachScreenEdge__mapFunc, &data);
- EM_free_index_arrays();
-
- dm->release(dm);
-}
-
-static void mesh_foreachScreenFace__mapFunc(void *userData, int index, float *cent, float *no)
-{
- struct { void (*func)(void *userData, EditFace *efa, int x, int y, int index); void *userData; float pmat[4][4], vmat[4][4]; } *data = userData;
- EditFace *efa = EM_get_face_for_index(index);
- short s[2];
-
- if (efa && efa->h==0 && efa->fgonf!=EM_FGON) {
- view3d_project_short_clip(curarea, cent, s, data->pmat, data->vmat);
-
- data->func(data->userData, efa, s[0], s[1], index);
- }
-}
-void mesh_foreachScreenFace(void (*func)(void *userData, EditFace *efa, int x, int y, int index), void *userData)
-{
- struct { void (*func)(void *userData, EditFace *efa, int x, int y, int index); void *userData; float pmat[4][4], vmat[4][4]; } data;
- DerivedMesh *dm = editmesh_get_derived_cage(CD_MASK_BAREMESH);
-
- data.func = func;
- data.userData = userData;
-
- view3d_get_object_project_mat(curarea, G.obedit, data.pmat, data.vmat);
-
- EM_init_index_arrays(0, 0, 1);
- dm->foreachMappedFaceCenter(dm, mesh_foreachScreenFace__mapFunc, &data);
- EM_free_index_arrays();
-
- dm->release(dm);
-}
-
-void nurbs_foreachScreenVert(void (*func)(void *userData, Nurb *nu, BPoint *bp, BezTriple *bezt, int beztindex, int x, int y), void *userData)
-{
- float pmat[4][4], vmat[4][4];
- short s[2];
- Nurb *nu;
- int i;
-
- view3d_get_object_project_mat(curarea, G.obedit, pmat, vmat);
-
- for (nu= editNurb.first; nu; nu=nu->next) {
- if((nu->type & 7)==CU_BEZIER) {
- for (i=0; i<nu->pntsu; i++) {
- BezTriple *bezt = &nu->bezt[i];
-
- if(bezt->hide==0) {
- if (G.f & G_HIDDENHANDLES) {
- view3d_project_short_clip(curarea, bezt->vec[1], s, pmat, vmat);
- if (s[0] != IS_CLIPPED)
- func(userData, nu, NULL, bezt, 1, s[0], s[1]);
- } else {
- view3d_project_short_clip(curarea, bezt->vec[0], s, pmat, vmat);
- if (s[0] != IS_CLIPPED)
- func(userData, nu, NULL, bezt, 0, s[0], s[1]);
- view3d_project_short_clip(curarea, bezt->vec[1], s, pmat, vmat);
- if (s[0] != IS_CLIPPED)
- func(userData, nu, NULL, bezt, 1, s[0], s[1]);
- view3d_project_short_clip(curarea, bezt->vec[2], s, pmat, vmat);
- if (s[0] != IS_CLIPPED)
- func(userData, nu, NULL, bezt, 2, s[0], s[1]);
- }
- }
- }
- }
- else {
- for (i=0; i<nu->pntsu*nu->pntsv; i++) {
- BPoint *bp = &nu->bp[i];
-
- if(bp->hide==0) {
- view3d_project_short_clip(curarea, bp->vec, s, pmat, vmat);
- func(userData, nu, bp, NULL, -1, s[0], s[1]);
- }
- }
- }
- }
-}
-
-/* ************** DRAW MESH ****************** */
-
-/* First section is all the "simple" draw routines,
- * ones that just pass some sort of primitive to GL,
- * with perhaps various options to control lighting,
- * color, etc.
- *
- * These routines should not have user interface related
- * logic!!!
- */
-
-static void draw_dm_face_normals__mapFunc(void *userData, int index, float *cent, float *no)
-{
- EditFace *efa = EM_get_face_for_index(index);
-
- if (efa->h==0 && efa->fgonf!=EM_FGON) {
- glVertex3fv(cent);
- glVertex3f( cent[0] + no[0]*G.scene->editbutsize,
- cent[1] + no[1]*G.scene->editbutsize,
- cent[2] + no[2]*G.scene->editbutsize);
- }
-}
-static void draw_dm_face_normals(DerivedMesh *dm) {
- glBegin(GL_LINES);
- dm->foreachMappedFaceCenter(dm, draw_dm_face_normals__mapFunc, 0);
- glEnd();
-}
-
-static void draw_dm_face_centers__mapFunc(void *userData, int index, float *cent, float *no)
-{
- EditFace *efa = EM_get_face_for_index(index);
- int sel = *((int*) userData);
-
- if (efa->h==0 && efa->fgonf!=EM_FGON && (efa->f&SELECT)==sel) {
- bglVertex3fv(cent);
- }
-}
-static void draw_dm_face_centers(DerivedMesh *dm, int sel)
-{
- bglBegin(GL_POINTS);
- dm->foreachMappedFaceCenter(dm, draw_dm_face_centers__mapFunc, &sel);
- bglEnd();
-}
-
-static void draw_dm_vert_normals__mapFunc(void *userData, int index, float *co, float *no_f, short *no_s)
-{
- EditVert *eve = EM_get_vert_for_index(index);
-
- if (eve->h==0) {
- glVertex3fv(co);
-
- if (no_f) {
- glVertex3f( co[0] + no_f[0]*G.scene->editbutsize,
- co[1] + no_f[1]*G.scene->editbutsize,
- co[2] + no_f[2]*G.scene->editbutsize);
- } else {
- glVertex3f( co[0] + no_s[0]*G.scene->editbutsize/32767.0f,
- co[1] + no_s[1]*G.scene->editbutsize/32767.0f,
- co[2] + no_s[2]*G.scene->editbutsize/32767.0f);
- }
- }
-}
-static void draw_dm_vert_normals(DerivedMesh *dm) {
- glBegin(GL_LINES);
- dm->foreachMappedVert(dm, draw_dm_vert_normals__mapFunc, NULL);
- glEnd();
-}
-
- /* Draw verts with color set based on selection */
-static void draw_dm_verts__mapFunc(void *userData, int index, float *co, float *no_f, short *no_s)
-{
- struct { int sel; EditVert *eve_act; } * data = userData;
- EditVert *eve = EM_get_vert_for_index(index);
-
- if (eve->h==0 && (eve->f&SELECT)==data->sel) {
- /* draw active larger - need to stop/start point drawing for this :/ */
- if (eve==data->eve_act) {
- float size = BIF_GetThemeValuef(TH_VERTEX_SIZE);
- BIF_ThemeColor4(TH_EDITMESH_ACTIVE);
-
- bglEnd();
-
- glPointSize(size);
- bglBegin(GL_POINTS);
- bglVertex3fv(co);
- bglEnd();
-
- BIF_ThemeColor4(TH_VERTEX_SELECT);
- glPointSize(size);
- bglBegin(GL_POINTS);
- } else {
- bglVertex3fv(co);
- }
- }
-}
-static void draw_dm_verts(DerivedMesh *dm, int sel, EditVert *eve_act)
-{
- struct { int sel; EditVert *eve_act; } data;
- data.sel = sel;
- data.eve_act = eve_act;
-
- bglBegin(GL_POINTS);
- dm->foreachMappedVert(dm, draw_dm_verts__mapFunc, &data);
- bglEnd();
-}
-
- /* Draw edges with color set based on selection */
-static int draw_dm_edges_sel__setDrawOptions(void *userData, int index)
-{
- EditEdge *eed = EM_get_edge_for_index(index);
- //unsigned char **cols = userData, *col;
- struct { unsigned char *baseCol, *selCol, *actCol; EditEdge *eed_act; } * data = userData;
- unsigned char *col;
-
- if (eed->h==0) {
- if (eed==data->eed_act) {
- glColor4ubv(data->actCol);
- } else {
- if (eed->f&SELECT) {
- col = data->selCol;
- } else {
- col = data->baseCol;
- }
- /* no alpha, this is used so a transparent color can disable drawing unselected edges in editmode */
- if (col[3]==0) return 0;
-
- glColor4ubv(col);
- }
- return 1;
- } else {
- return 0;
- }
-}
-static void draw_dm_edges_sel(DerivedMesh *dm, unsigned char *baseCol, unsigned char *selCol, unsigned char *actCol, EditEdge *eed_act)
-{
- struct { unsigned char *baseCol, *selCol, *actCol; EditEdge *eed_act; } data;
-
- data.baseCol = baseCol;
- data.selCol = selCol;
- data.actCol = actCol;
- data.eed_act = eed_act;
- dm->drawMappedEdges(dm, draw_dm_edges_sel__setDrawOptions, &data);
-}
-
- /* Draw edges */
-static int draw_dm_edges__setDrawOptions(void *userData, int index)
-{
- return EM_get_edge_for_index(index)->h==0;
-}
-static void draw_dm_edges(DerivedMesh *dm)
-{
- dm->drawMappedEdges(dm, draw_dm_edges__setDrawOptions, NULL);
-}
-
- /* Draw edges with color interpolated based on selection */
-static int draw_dm_edges_sel_interp__setDrawOptions(void *userData, int index)
-{
- return EM_get_edge_for_index(index)->h==0;
-}
-static void draw_dm_edges_sel_interp__setDrawInterpOptions(void *userData, int index, float t)
-{
- EditEdge *eed = EM_get_edge_for_index(index);
- unsigned char **cols = userData;
- unsigned char *col0 = cols[(eed->v1->f&SELECT)?1:0];
- unsigned char *col1 = cols[(eed->v2->f&SELECT)?1:0];
-
- glColor4ub( col0[0] + (col1[0]-col0[0])*t,
- col0[1] + (col1[1]-col0[1])*t,
- col0[2] + (col1[2]-col0[2])*t,
- col0[3] + (col1[3]-col0[3])*t);
-}
-static void draw_dm_edges_sel_interp(DerivedMesh *dm, unsigned char *baseCol, unsigned char *selCol)
-{
- unsigned char *cols[2];
- cols[0] = baseCol;
- cols[1] = selCol;
- dm->drawMappedEdgesInterp(dm, draw_dm_edges_sel_interp__setDrawOptions, draw_dm_edges_sel_interp__setDrawInterpOptions, cols);
-}
-
- /* Draw only seam edges */
-static int draw_dm_edges_seams__setDrawOptions(void *userData, int index)
-{
- EditEdge *eed = EM_get_edge_for_index(index);
-
- return (eed->h==0 && eed->seam);
-}
-static void draw_dm_edges_seams(DerivedMesh *dm)
-{
- dm->drawMappedEdges(dm, draw_dm_edges_seams__setDrawOptions, NULL);
-}
-
- /* Draw only sharp edges */
-static int draw_dm_edges_sharp__setDrawOptions(void *userData, int index)
-{
- EditEdge *eed = EM_get_edge_for_index(index);
-
- return (eed->h==0 && eed->sharp);
-}
-static void draw_dm_edges_sharp(DerivedMesh *dm)
-{
- dm->drawMappedEdges(dm, draw_dm_edges_sharp__setDrawOptions, NULL);
-}
-
-
- /* Draw faces with color set based on selection
- * return 2 for the active face so it renders with stipple enabled */
-static int draw_dm_faces_sel__setDrawOptions(void *userData, int index, int *drawSmooth_r)
-{
- struct { unsigned char *cols[3]; EditFace *efa_act; } * data = userData;
- EditFace *efa = EM_get_face_for_index(index);
- unsigned char *col;
-
- if (efa->h==0) {
- if (efa == data->efa_act) {
- glColor4ubv(data->cols[2]);
- return 2; /* stipple */
- } else {
- col = data->cols[(efa->f&SELECT)?1:0];
- if (col[3]==0) return 0;
- glColor4ubv(col);
- return 1;
- }
- }
- return 0;
-}
-
-/* also draws the active face */
-static void draw_dm_faces_sel(DerivedMesh *dm, unsigned char *baseCol, unsigned char *selCol, unsigned char *actCol, EditFace *efa_act)
-{
- struct { unsigned char *cols[3]; EditFace *efa_act; } data;
- data.cols[0] = baseCol;
- data.cols[1] = selCol;
- data.cols[2] = actCol;
- data.efa_act = efa_act;
-
- dm->drawMappedFaces(dm, draw_dm_faces_sel__setDrawOptions, &data, 0);
-}
-
-static int draw_dm_creases__setDrawOptions(void *userData, int index)
-{
- EditEdge *eed = EM_get_edge_for_index(index);
-
- if (eed->h==0 && eed->crease!=0.0) {
- BIF_ThemeColorBlend(TH_WIRE, TH_EDGE_SELECT, eed->crease);
- return 1;
- } else {
- return 0;
- }
-}
-static void draw_dm_creases(DerivedMesh *dm)
-{
- glLineWidth(3.0);
- dm->drawMappedEdges(dm, draw_dm_creases__setDrawOptions, NULL);
- glLineWidth(1.0);
-}
-
-/* Second section of routines: Combine first sets to form fancy
- * drawing routines (for example rendering twice to get overlays).
- *
- * Also includes routines that are basic drawing but are too
- * specialized to be split out (like drawing creases or measurements).
- */
-
-/* EditMesh drawing routines*/
-
-static void draw_em_fancy_verts(EditMesh *em, DerivedMesh *cageDM, EditVert *eve_act)
-{
- int sel;
-
- if(G.vd->zbuf) glDepthMask(0); // disable write in zbuffer, zbuf select
-
- for (sel=0; sel<2; sel++) {
- char col[4], fcol[4];
- int pass;
-
- BIF_GetThemeColor3ubv(sel?TH_VERTEX_SELECT:TH_VERTEX, col);
- BIF_GetThemeColor3ubv(sel?TH_FACE_DOT:TH_WIRE, fcol);
-
- for (pass=0; pass<2; pass++) {
- float size = BIF_GetThemeValuef(TH_VERTEX_SIZE);
- float fsize = BIF_GetThemeValuef(TH_FACEDOT_SIZE);
-
- if (pass==0) {
- if(G.vd->zbuf && !(G.vd->flag&V3D_ZBUF_SELECT)) {
- glDisable(GL_DEPTH_TEST);
-
- glEnable(GL_BLEND);
- } else {
- continue;
- }
-
- size = (size>2.1?size/2.0:size);
- fsize = (fsize>2.1?fsize/2.0:fsize);
- col[3] = fcol[3] = 100;
- } else {
- col[3] = fcol[3] = 255;
- }
-
- if(G.scene->selectmode & SCE_SELECT_VERTEX) {
- glPointSize(size);
- glColor4ubv((GLubyte *)col);
- draw_dm_verts(cageDM, sel, eve_act);
- }
-
- if( CHECK_OB_DRAWFACEDOT(G.scene, G.vd, G.obedit->dt) ) {
- glPointSize(fsize);
- glColor4ubv((GLubyte *)fcol);
- draw_dm_face_centers(cageDM, sel);
- }
-
- if (pass==0) {
- glDisable(GL_BLEND);
- glEnable(GL_DEPTH_TEST);
- }
- }
- }
-
- if(G.vd->zbuf) glDepthMask(1);
- glPointSize(1.0);
-}
-
-static void draw_em_fancy_edges(DerivedMesh *cageDM, short sel_only, EditEdge *eed_act)
-{
- int pass;
- unsigned char wireCol[4], selCol[4], actCol[4];
-
- /* since this function does transparant... */
- BIF_GetThemeColor3ubv(TH_EDGE_SELECT, (char *)selCol);
- BIF_GetThemeColor3ubv(TH_WIRE, (char *)wireCol);
- BIF_GetThemeColor3ubv(TH_EDITMESH_ACTIVE, (char *)actCol);
-
- /* when sel only is used, dont render wire, only selected, this is used for
- * textured draw mode when the 'edges' option is disabled */
- if (sel_only)
- wireCol[3] = 0;
-
- for (pass=0; pass<2; pass++) {
- /* show wires in transparant when no zbuf clipping for select */
- if (pass==0) {
- if (G.vd->zbuf && (G.vd->flag & V3D_ZBUF_SELECT)==0) {
- glEnable(GL_BLEND);
- glDisable(GL_DEPTH_TEST);
- selCol[3] = 85;
- if (!sel_only) wireCol[3] = 85;
- } else {
- continue;
- }
- } else {
- selCol[3] = 255;
- if (!sel_only) wireCol[3] = 255;
- }
-
- if(G.scene->selectmode == SCE_SELECT_FACE) {
- draw_dm_edges_sel(cageDM, wireCol, selCol, actCol, eed_act);
- }
- else if( (G.f & G_DRAWEDGES) || (G.scene->selectmode & SCE_SELECT_EDGE) ) {
- if(cageDM->drawMappedEdgesInterp && (G.scene->selectmode & SCE_SELECT_VERTEX)) {
- glShadeModel(GL_SMOOTH);
- draw_dm_edges_sel_interp(cageDM, wireCol, selCol);
- glShadeModel(GL_FLAT);
- } else {
- draw_dm_edges_sel(cageDM, wireCol, selCol, actCol, eed_act);
- }
- }
- else {
- if (!sel_only) {
- glColor4ubv(wireCol);
- draw_dm_edges(cageDM);
- }
- }
-
- if (pass==0) {
- glDisable(GL_BLEND);
- glEnable(GL_DEPTH_TEST);
- }
- }
-}
-
-#ifdef WITH_VERSE
-/*
- * draw some debug info about verse mesh (vertex indexes,
- * face indexes, status of )
- */
-static void draw_verse_debug(Object *ob, EditMesh *em)
-{
- struct EditVert *eve=NULL;
- struct EditFace *efa=NULL;
- float v1[3], v2[3], v3[3], v4[3], fvec[3], col[3];
- char val[32];
-
- if(G.vd->zbuf && (G.vd->flag & V3D_ZBUF_SELECT)==0)
- glDisable(GL_DEPTH_TEST);
-
- if(G.vd->zbuf) bglPolygonOffset(5.0);
-
- BIF_GetThemeColor3fv(TH_TEXT, col);
- /* make color a bit more red */
- if(col[0]> 0.5) {col[1]*=0.7; col[2]*= 0.7;}
- else col[0]= col[0]*0.7 + 0.3;
- glColor3fv(col);
-
- /* draw IDs of verse vertexes */
- for(eve = em->verts.first; eve; eve = eve->next) {
- if(eve->vvert) {
- VecLerpf(fvec, ob->loc, eve->co, 1.1);
- glRasterPos3f(fvec[0], fvec[1], fvec[2]);
-
- sprintf(val, "%d", ((VerseVert*)eve->vvert)->id);
- BMF_DrawString(G.fonts, val);
- }
- }
-
- /* draw IDs of verse faces */
- for(efa = em->faces.first; efa; efa = efa->next) {
- if(efa->vface) {
- VECCOPY(v1, efa->v1->co);
- VECCOPY(v2, efa->v2->co);
- VECCOPY(v3, efa->v3->co);
- if(efa->v4) {
- VECCOPY(v4, efa->v4->co);
- glRasterPos3f(0.25*(v1[0]+v2[0]+v3[0]+v4[0]),
- 0.25*(v1[1]+v2[1]+v3[1]+v4[1]),
- 0.25*(v1[2]+v2[2]+v3[2]+v4[2]));
- }
- else {
- glRasterPos3f((v1[0]+v2[0]+v3[0])/3,
- (v1[1]+v2[1]+v3[1])/3,
- (v1[2]+v2[2]+v3[2])/3);
- }
-
- sprintf(val, "%d", ((VerseFace*)efa->vface)->id);
- BMF_DrawString(G.fonts, val);
-
- }
- }
-
- if(G.vd->zbuf) {
- glEnable(GL_DEPTH_TEST);
- bglPolygonOffset(0.0);
- }
-}
-#endif
-
-static void draw_em_measure_stats(Object *ob, EditMesh *em)
-{
- EditEdge *eed;
- EditFace *efa;
- float v1[3], v2[3], v3[3], v4[3];
- float fvec[3];
- char val[32]; /* Stores the measurement display text here */
- char conv_float[5]; /* Use a float conversion matching the grid size */
- float area, col[3]; /* area of the face, color of the text to draw */
-
- /* make the precission of the pronted value proportionate to the gridsize */
- if ((G.vd->grid) < 0.01)
- strcpy(conv_float, "%.6f");
- else if ((G.vd->grid) < 0.1)
- strcpy(conv_float, "%.5f");
- else if ((G.vd->grid) < 1.0)
- strcpy(conv_float, "%.4f");
- else if ((G.vd->grid) < 10.0)
- strcpy(conv_float, "%.3f");
- else
- strcpy(conv_float, "%.2f");
-
-
- if(G.vd->zbuf && (G.vd->flag & V3D_ZBUF_SELECT)==0)
- glDisable(GL_DEPTH_TEST);
-
- if(G.vd->zbuf) bglPolygonOffset(5.0);
-
- if(G.f & G_DRAW_EDGELEN) {
- BIF_GetThemeColor3fv(TH_TEXT, col);
- /* make color a bit more red */
- if(col[0]> 0.5) {col[1]*=0.7; col[2]*= 0.7;}
- else col[0]= col[0]*0.7 + 0.3;
- glColor3fv(col);
-
- for(eed= em->edges.first; eed; eed= eed->next) {
- /* draw non fgon edges, or selected edges, or edges next to selected verts while draging */
- if((eed->h != EM_FGON) && ((eed->f & SELECT) || (G.moving && ((eed->v1->f & SELECT) || (eed->v2->f & SELECT)) ))) {
- VECCOPY(v1, eed->v1->co);
- VECCOPY(v2, eed->v2->co);
-
- glRasterPos3f( 0.5*(v1[0]+v2[0]), 0.5*(v1[1]+v2[1]), 0.5*(v1[2]+v2[2]));
-
- if(G.vd->flag & V3D_GLOBAL_STATS) {
- Mat4MulVecfl(ob->obmat, v1);
- Mat4MulVecfl(ob->obmat, v2);
- }
-
- sprintf(val, conv_float, VecLenf(v1, v2));
- BMF_DrawString( G.fonts, val);
- }
- }
- }
-
- if(G.f & G_DRAW_FACEAREA) {
- extern int faceselectedOR(EditFace *efa, int flag); // editmesh.h shouldn't be in this file... ok for now?
-
- BIF_GetThemeColor3fv(TH_TEXT, col);
- /* make color a bit more green */
- if(col[1]> 0.5) {col[0]*=0.7; col[2]*= 0.7;}
- else col[1]= col[1]*0.7 + 0.3;
- glColor3fv(col);
-
- for(efa= em->faces.first; efa; efa= efa->next) {
- if((efa->f & SELECT) || (G.moving && faceselectedOR(efa, SELECT)) ) {
- VECCOPY(v1, efa->v1->co);
- VECCOPY(v2, efa->v2->co);
- VECCOPY(v3, efa->v3->co);
- if (efa->v4) {
- VECCOPY(v4, efa->v4->co);
- }
- if(G.vd->flag & V3D_GLOBAL_STATS) {
- Mat4MulVecfl(ob->obmat, v1);
- Mat4MulVecfl(ob->obmat, v2);
- Mat4MulVecfl(ob->obmat, v3);
- if (efa->v4) Mat4MulVecfl(ob->obmat, v4);
- }
-
- if (efa->v4)
- area= AreaQ3Dfl(v1, v2, v3, v4);
- else
- area = AreaT3Dfl(v1, v2, v3);
-
- sprintf(val, conv_float, area);
- glRasterPos3fv(efa->cent);
- BMF_DrawString( G.fonts, val);
- }
- }
- }
-
- if(G.f & G_DRAW_EDGEANG) {
- EditEdge *e1, *e2, *e3, *e4;
-
- BIF_GetThemeColor3fv(TH_TEXT, col);
- /* make color a bit more blue */
- if(col[2]> 0.5) {col[0]*=0.7; col[1]*= 0.7;}
- else col[2]= col[2]*0.7 + 0.3;
- glColor3fv(col);
-
- for(efa= em->faces.first; efa; efa= efa->next) {
- VECCOPY(v1, efa->v1->co);
- VECCOPY(v2, efa->v2->co);
- VECCOPY(v3, efa->v3->co);
- if(efa->v4) {
- VECCOPY(v4, efa->v4->co);
- }
- else {
- VECCOPY(v4, v3);
- }
- if(G.vd->flag & V3D_GLOBAL_STATS) {
- Mat4MulVecfl(ob->obmat, v1);
- Mat4MulVecfl(ob->obmat, v2);
- Mat4MulVecfl(ob->obmat, v3);
- if (efa->v4) Mat4MulVecfl(ob->obmat, v4);
- }
-
- e1= efa->e1;
- e2= efa->e2;
- e3= efa->e3;
- if(efa->e4) e4= efa->e4; else e4= e3;
-
- /* Calculate the angles */
-
- if( (e4->f & e1->f & SELECT) || (G.moving && (efa->v1->f & SELECT)) ) {
- /* Vec 1 */
- sprintf(val,"%.3f", VecAngle3(v4, v1, v2));
- VecLerpf(fvec, efa->cent, efa->v1->co, 0.8);
- glRasterPos3fv(fvec);
- BMF_DrawString( G.fonts, val);
- }
- if( (e1->f & e2->f & SELECT) || (G.moving && (efa->v2->f & SELECT)) ) {
- /* Vec 2 */
- sprintf(val,"%.3f", VecAngle3(v1, v2, v3));
- VecLerpf(fvec, efa->cent, efa->v2->co, 0.8);
- glRasterPos3fv(fvec);
- BMF_DrawString( G.fonts, val);
- }
- if( (e2->f & e3->f & SELECT) || (G.moving && (efa->v3->f & SELECT)) ) {
- /* Vec 3 */
- if(efa->v4)
- sprintf(val,"%.3f", VecAngle3(v2, v3, v4));
- else
- sprintf(val,"%.3f", VecAngle3(v2, v3, v1));
- VecLerpf(fvec, efa->cent, efa->v3->co, 0.8);
- glRasterPos3fv(fvec);
- BMF_DrawString( G.fonts, val);
- }
- /* Vec 4 */
- if(efa->v4) {
- if( (e3->f & e4->f & SELECT) || (G.moving && (efa->v4->f & SELECT)) ) {
- sprintf(val,"%.3f", VecAngle3(v3, v4, v1));
- VecLerpf(fvec, efa->cent, efa->v4->co, 0.8);
- glRasterPos3fv(fvec);
- BMF_DrawString( G.fonts, val);
- }
- }
- }
- }
-
- if(G.vd->zbuf) {
- glEnable(GL_DEPTH_TEST);
- bglPolygonOffset(0.0);
- }
-}
-
-static int draw_em_fancy__setFaceOpts(void *userData, int index, int *drawSmooth_r)
-{
- EditFace *efa = EM_get_face_for_index(index);
-
- if (efa->h==0) {
- set_gl_material(efa->mat_nr+1);
- return 1;
- } else {
- return 0;
- }
-}
-static void draw_em_fancy(Object *ob, EditMesh *em, DerivedMesh *cageDM, DerivedMesh *finalDM, int dt)
-{
- Mesh *me = ob->data;
- EditFace *efa_act = NULL;
- EditEdge *eed_act = NULL;
- EditVert *eve_act = NULL;
-
- if (G.editMesh->selected.last) {
- EditSelection *ese = G.editMesh->selected.last;
- if ( ese->type == EDITFACE ) {
- efa_act = (EditFace *)ese->data;
- } else if ( ese->type == EDITEDGE ) {
- eed_act = (EditEdge *)ese->data;
- } else if ( ese->type == EDITVERT ) {
- eve_act = (EditVert *)ese->data;
- }
- }
-
- EM_init_index_arrays(1, 1, 1);
-
- if(dt>OB_WIRE) {
- if( CHECK_OB_DRAWTEXTURE(G.vd, dt) ) {
- draw_mesh_textured(ob, finalDM, 0);
- } else {
- glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, me->flag & ME_TWOSIDED);
-
- glEnable(GL_LIGHTING);
- glFrontFace((ob->transflag&OB_NEG_SCALE)?GL_CW:GL_CCW);
-
- finalDM->drawMappedFaces(finalDM, draw_em_fancy__setFaceOpts, 0, 0);
-
- glFrontFace(GL_CCW);
- glDisable(GL_LIGHTING);
- }
-
- // Setup for drawing wire over, disable zbuffer
- // write to show selected edge wires better
- BIF_ThemeColor(TH_WIRE);
-
- bglPolygonOffset(1.0);
- glDepthMask(0);
- }
- else {
- if (cageDM!=finalDM) {
- BIF_ThemeColorBlend(TH_WIRE, TH_BACK, 0.7);
- finalDM->drawEdges(finalDM, 1);
- }
- }
-
- if((G.f & (G_DRAWFACES)) || FACESEL_PAINT_TEST) { /* transp faces */
- unsigned char col1[4], col2[4], col3[4];
-
- BIF_GetThemeColor4ubv(TH_FACE, (char *)col1);
- BIF_GetThemeColor4ubv(TH_FACE_SELECT, (char *)col2);
- BIF_GetThemeColor4ubv(TH_EDITMESH_ACTIVE, (char *)col3);
-
- glEnable(GL_BLEND);
- glDepthMask(0); // disable write in zbuffer, needed for nice transp
-
- /* dont draw unselected faces, only selected, this is MUCH nicer when texturing */
- if CHECK_OB_DRAWTEXTURE(G.vd, dt)
- col1[3] = 0;
-
- draw_dm_faces_sel(cageDM, col1, col2, col3, efa_act);
-
- glDisable(GL_BLEND);
- glDepthMask(1); // restore write in zbuffer
- } else if (efa_act) {
- /* even if draw faces is off it would be nice to draw the stipple face
- * Make all other faces zero alpha except for the active
- * */
- unsigned char col1[4], col2[4], col3[4];
- col1[3] = col2[3] = 0; /* dont draw */
- BIF_GetThemeColor4ubv(TH_EDITMESH_ACTIVE, (char *)col3);
-
- glEnable(GL_BLEND);
- glDepthMask(0); // disable write in zbuffer, needed for nice transp
-
- draw_dm_faces_sel(cageDM, col1, col2, col3, efa_act);
-
- glDisable(GL_BLEND);
- glDepthMask(1); // restore write in zbuffer
-
- }
-
- /* here starts all fancy draw-extra over */
- if((G.f & G_DRAWEDGES)==0 && CHECK_OB_DRAWTEXTURE(G.vd, dt)) {
- /* we are drawing textures and 'G_DRAWEDGES' is disabled, dont draw any edges */
-
- /* only draw selected edges otherwise there is no way of telling if a face is selected */
- draw_em_fancy_edges(cageDM, 1, eed_act);
-
- } else {
- if(G.f & G_DRAWSEAMS) {
- BIF_ThemeColor(TH_EDGE_SEAM);
- glLineWidth(2);
-
- draw_dm_edges_seams(cageDM);
-
- glColor3ub(0,0,0);
- glLineWidth(1);
- }
-
- if(G.f & G_DRAWSHARP) {
- BIF_ThemeColor(TH_EDGE_SHARP);
- glLineWidth(2);
-
- draw_dm_edges_sharp(cageDM);
-
- glColor3ub(0,0,0);
- glLineWidth(1);
- }
-
- if(G.f & G_DRAWCREASES) {
- draw_dm_creases(cageDM);
- }
-
- draw_em_fancy_edges(cageDM, 0, eed_act);
- }
- if(ob==G.obedit) {
- retopo_matrix_update(G.vd);
-
- draw_em_fancy_verts(em, cageDM, eve_act);
-
- if(G.f & G_DRAWNORMALS) {
- BIF_ThemeColor(TH_NORMAL);
- draw_dm_face_normals(cageDM);
- }
- if(G.f & G_DRAW_VNORMALS) {
- BIF_ThemeColor(TH_NORMAL);
- draw_dm_vert_normals(cageDM);
- }
-
- if(G.f & (G_DRAW_EDGELEN|G_DRAW_FACEAREA|G_DRAW_EDGEANG))
- draw_em_measure_stats(ob, em);
-#ifdef WITH_VERSE
- if(em->vnode && (G.f & G_DRAW_VERSE_DEBUG))
- draw_verse_debug(ob, em);
-#endif
- }
-
- if(dt>OB_WIRE) {
- glDepthMask(1);
- bglPolygonOffset(0.0);
- }
-
- EM_free_index_arrays();
-}
-
-/* Mesh drawing routines */
-
-static void draw_mesh_object_outline(Object *ob, DerivedMesh *dm)
-{
-
- if(G.vd->transp==0) { // not when we draw the transparent pass
- glLineWidth(2.0);
- glDepthMask(0);
-
- /* if transparent, we cannot draw the edges for solid select... edges have no material info.
- drawFacesSolid() doesn't draw the transparent faces */
- if(ob->dtx & OB_DRAWTRANSP) {
- glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
- dm->drawFacesSolid(dm, set_gl_material);
- glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
- }
- else {
- dm->drawEdges(dm, 0);
- }
-
- glLineWidth(1.0);
- glDepthMask(1);
- }
-}
-
-static int wpaint__setSolidDrawOptions(void *userData, int index, int *drawSmooth_r)
-{
- *drawSmooth_r = 1;
- return 1;
-}
-
-static void draw_mesh_fancy(Base *base, int dt, int flag)
-{
- Object *ob= base->object;
- Mesh *me = ob->data;
- Material *ma= give_current_material(ob, 1);
- int hasHaloMat = (ma && (ma->mode&MA_HALO));
- int draw_wire = ob->dtx&OB_DRAWWIRE;
- int totvert, totedge, totface;
- DispList *dl;
- DerivedMesh *dm= mesh_get_derived_final(ob, get_viewedit_datamask());
-
- if(!dm)
- return;
-
-#ifdef WITH_VERSE
- if(me->vnode) {
- struct VNode *vnode = (VNode*)me->vnode;
- struct VLayer *vert_vlayer = find_verse_layer_type((VGeomData*)vnode->data, VERTEX_LAYER);
- struct VLayer *face_vlayer = find_verse_layer_type((VGeomData*)vnode->data, POLYGON_LAYER);
-
- if(vert_vlayer) totvert = vert_vlayer->dl.da.count;
- else totvert = 0;
- totedge = 0; /* total count of edge needn't to be zero, but verse doesn't know edges */
- if(face_vlayer) totface = face_vlayer->dl.da.count;
- else totface = 0;
- }
- else {
- totvert = dm->getNumVerts(dm);
- totedge = dm->getNumEdges(dm);
- totface = dm->getNumFaces(dm);
- }
-#else
- totvert = dm->getNumVerts(dm);
- totedge = dm->getNumEdges(dm);
- totface = dm->getNumFaces(dm);
-#endif
-
- /* vertexpaint, faceselect wants this, but it doesnt work for shaded? */
- if(dt!=OB_SHADED)
- glFrontFace((ob->transflag&OB_NEG_SCALE)?GL_CW:GL_CCW);
-
- // Unwanted combination.
- if (ob==OBACT && FACESEL_PAINT_TEST) draw_wire = 0;
-
- if(dt==OB_BOUNDBOX) {
- draw_bounding_volume(ob);
- }
- else if(hasHaloMat || (totface==0 && totedge==0)) {
- glPointSize(1.5);
- dm->drawVerts(dm);
- glPointSize(1.0);
- }
- else if(dt==OB_WIRE || totface==0) {
- draw_wire = 1;
- }
- else if( (ob==OBACT && (G.f & G_TEXTUREPAINT || FACESEL_PAINT_TEST)) ||
- CHECK_OB_DRAWTEXTURE(G.vd, dt))
- {
- int faceselect= (ob==OBACT && FACESEL_PAINT_TEST);
-
- if ((G.vd->flag&V3D_SELECT_OUTLINE) && (base->flag&SELECT) && !(G.f&G_PICKSEL || FACESEL_PAINT_TEST) && !draw_wire) {
- draw_mesh_object_outline(ob, dm);
- }
-
- draw_mesh_textured(ob, dm, faceselect);
-
- if(!faceselect) {
- if(base->flag & SELECT)
- BIF_ThemeColor((ob==OBACT)?TH_ACTIVE:TH_SELECT);
- else
- BIF_ThemeColor(TH_WIRE);
-
- dm->drawLooseEdges(dm);
- }
- }
- else if(dt==OB_SOLID ) {
-
- if ((G.vd->flag&V3D_SELECT_OUTLINE) && (base->flag&SELECT) && !draw_wire) {
- draw_mesh_object_outline(ob, dm);
- }
-
- glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, me->flag & ME_TWOSIDED );
-
- glEnable(GL_LIGHTING);
- glFrontFace((ob->transflag&OB_NEG_SCALE)?GL_CW:GL_CCW);
-
- dm->drawFacesSolid(dm, set_gl_material);
-
- glFrontFace(GL_CCW);
- glDisable(GL_LIGHTING);
-
- if(base->flag & SELECT) {
- BIF_ThemeColor((ob==OBACT)?TH_ACTIVE:TH_SELECT);
- } else {
- BIF_ThemeColor(TH_WIRE);
- }
- dm->drawLooseEdges(dm);
- }
- else if(dt==OB_SHADED) {
- int do_draw= 1; /* to resolve all G.f settings below... */
-
- if(ob==OBACT) {
- do_draw= 0;
- if( (G.f & G_WEIGHTPAINT)) {
- set_gl_material(0); /* enforce defmaterial settings */
-
- /* but set default spec */
- glColorMaterial(GL_FRONT_AND_BACK, GL_SPECULAR);
- glEnable(GL_COLOR_MATERIAL); /* according manpages needed */
- glColor3ub(120, 120, 120);
- glDisable(GL_COLOR_MATERIAL);
- /* diffuse */
- glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE);
- glEnable(GL_LIGHTING);
- glEnable(GL_COLOR_MATERIAL);
-
- dm->drawMappedFaces(dm, wpaint__setSolidDrawOptions, me->mface, 1);
- glDisable(GL_COLOR_MATERIAL);
- glDisable(GL_LIGHTING);
- }
- else if((G.f & (G_VERTEXPAINT+G_TEXTUREPAINT)) && me->mcol) {
- dm->drawMappedFaces(dm, wpaint__setSolidDrawOptions, NULL, 1);
- }
- else if(G.f & (G_VERTEXPAINT+G_TEXTUREPAINT)) {
- glColor3f(1.0f, 1.0f, 1.0f);
- dm->drawMappedFaces(dm, wpaint__setSolidDrawOptions, NULL, 0);
- }
- else do_draw= 1;
- }
- if(do_draw) {
- dl = ob->disp.first;
- if (!dl || !dl->col1) {
- /* release and reload derivedmesh because it might be freed in
- shadeDispList due to a different datamask */
- dm->release(dm);
- shadeDispList(base);
- dl = find_displist(&ob->disp, DL_VERTCOL);
- dm= mesh_get_derived_final(ob, get_viewedit_datamask());
- }
-
- if ((G.vd->flag&V3D_SELECT_OUTLINE) && (base->flag&SELECT) && !draw_wire) {
- draw_mesh_object_outline(ob, dm);
- }
-
- /* False for dupliframe objects */
- if (dl) {
- unsigned int *obCol1 = dl->col1;
- unsigned int *obCol2 = dl->col2;
-
- dm->drawFacesColored(dm, me->flag&ME_TWOSIDED, (unsigned char*) obCol1, (unsigned char*) obCol2);
- }
-
- if(base->flag & SELECT) {
- BIF_ThemeColor((ob==OBACT)?TH_ACTIVE:TH_SELECT);
- } else {
- BIF_ThemeColor(TH_WIRE);
- }
- dm->drawLooseEdges(dm);
- }
- }
-
- /* set default draw color back for wire or for draw-extra later on */
- if (dt!=OB_WIRE) {
- if(base->flag & SELECT) {
- if(ob==OBACT && ob->flag & OB_FROMGROUP)
- BIF_ThemeColor(TH_GROUP_ACTIVE);
- else if(ob->flag & OB_FROMGROUP)
- BIF_ThemeColorShade(TH_GROUP_ACTIVE, -16);
- else if(flag!=DRAW_CONSTCOLOR)
- BIF_ThemeColor((ob==OBACT)?TH_ACTIVE:TH_SELECT);
- else
- glColor3ub(80,80,80);
- } else {
- if (ob->flag & OB_FROMGROUP)
- BIF_ThemeColor(TH_GROUP);
- else {
- if(ob->dtx & OB_DRAWWIRE && flag==DRAW_CONSTCOLOR)
- glColor3ub(80,80,80);
- else
- BIF_ThemeColor(TH_WIRE);
- }
- }
- }
- if (draw_wire) {
- /* If drawing wire and drawtype is not OB_WIRE then we are
- * overlaying the wires.
- */
-
- if (dt!=OB_WIRE) {
- bglPolygonOffset(1.0);
- glDepthMask(0); // disable write in zbuffer, selected edge wires show better
- }
-
- dm->drawEdges(dm, (dt==OB_WIRE || totface==0));
-
- if (dt!=OB_WIRE) {
- glDepthMask(1);
- bglPolygonOffset(0.0);
- }
- }
-
- dm->release(dm);
-}
-
-/* returns 1 if nothing was drawn, for detecting to draw an object center */
-static int draw_mesh_object(Base *base, int dt, int flag)
-{
- Object *ob= base->object;
- Mesh *me= ob->data;
- int has_alpha= 0, drawlinked= 0, retval= 0;
-
- if(G.obedit && ob!=G.obedit && ob->data==G.obedit->data) {
- if(ob_get_key(ob));
- else drawlinked= 1;
- }
-
- if(ob==G.obedit || drawlinked) {
- DerivedMesh *finalDM, *cageDM;
-
- if (G.obedit!=ob)
- finalDM = cageDM = editmesh_get_derived_base();
- else
- cageDM = editmesh_get_derived_cage_and_final(&finalDM,
- get_viewedit_datamask());
-
- if(dt>OB_WIRE) init_gl_materials(ob, 0); // no transp in editmode, the fancy draw over goes bad then
- draw_em_fancy(ob, G.editMesh, cageDM, finalDM, dt);
-
- if (G.obedit!=ob && finalDM)
- finalDM->release(finalDM);
- }
- else if(!G.obedit && (G.f & G_SCULPTMODE) &&(G.scene->sculptdata.flags & SCULPT_DRAW_FAST) &&
- OBACT==ob && !sculpt_modifiers_active(ob)) {
- sculptmode_draw_mesh(0);
- }
- else {
- /* don't create boundbox here with mesh_get_bb(), the derived system will make it, puts deformed bb's OK */
- if(me->totface<=4 || boundbox_clip(ob->obmat, (ob->bb)? ob->bb: me->bb)) {
- if(dt==OB_SOLID) has_alpha= init_gl_materials(ob, (base->flag & OB_FROMDUPLI)==0);
- draw_mesh_fancy(base, dt, flag);
-
- if(me->totvert==0) retval= 1;
- }
- }
-
- /* init_gl_materials did the proper checking if this is needed */
- if(has_alpha) add_view3d_after(G.vd, base, V3D_TRANSP);
-
- return retval;
-}
-
-/* ************** DRAW DISPLIST ****************** */
-
-static int draw_index_wire= 1;
-static int index3_nors_incr= 1;
-
-/* returns 1 when nothing was drawn */
-static int drawDispListwire(ListBase *dlbase)
-{
- DispList *dl;
- int parts, nr;
- float *data;
-
- if(dlbase==NULL) return 1;
-
- glDisableClientState(GL_NORMAL_ARRAY);
- glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
-
- for(dl= dlbase->first; dl; dl= dl->next) {
- if(dl->parts==0 || dl->nr==0)
- continue;
-
- data= dl->verts;
-
- switch(dl->type) {
- case DL_SEGM:
-
- glVertexPointer(3, GL_FLOAT, 0, data);
-
- for(parts=0; parts<dl->parts; parts++)
- glDrawArrays(GL_LINE_STRIP, parts*dl->nr, dl->nr);
-
- break;
- case DL_POLY:
-
- glVertexPointer(3, GL_FLOAT, 0, data);
-
- for(parts=0; parts<dl->parts; parts++)
- glDrawArrays(GL_LINE_LOOP, parts*dl->nr, dl->nr);
-
- break;
- case DL_SURF:
-
- glVertexPointer(3, GL_FLOAT, 0, data);
-
- for(parts=0; parts<dl->parts; parts++) {
- if(dl->flag & DL_CYCL_U)
- glDrawArrays(GL_LINE_LOOP, parts*dl->nr, dl->nr);
- else
- glDrawArrays(GL_LINE_STRIP, parts*dl->nr, dl->nr);
- }
-
- for(nr=0; nr<dl->nr; nr++) {
- int ofs= 3*dl->nr;
-
- data= ( dl->verts )+3*nr;
- parts= dl->parts;
-
- if(dl->flag & DL_CYCL_V) glBegin(GL_LINE_LOOP);
- else glBegin(GL_LINE_STRIP);
-
- while(parts--) {
- glVertex3fv(data);
- data+=ofs;
- }
- glEnd();
-
- /* (ton) this code crashes for me when resolv is 86 or higher... no clue */
-// glVertexPointer(3, GL_FLOAT, sizeof(float)*3*dl->nr, data + 3*nr);
-// if(dl->flag & DL_CYCL_V)
-// glDrawArrays(GL_LINE_LOOP, 0, dl->parts);
-// else
-// glDrawArrays(GL_LINE_STRIP, 0, dl->parts);
- }
- break;
-
- case DL_INDEX3:
- if(draw_index_wire) {
- glVertexPointer(3, GL_FLOAT, 0, dl->verts);
- glDrawElements(GL_TRIANGLES, 3*dl->parts, GL_UNSIGNED_INT, dl->index);
- }
- break;
-
- case DL_INDEX4:
- if(draw_index_wire) {
- glVertexPointer(3, GL_FLOAT, 0, dl->verts);
- glDrawElements(GL_QUADS, 4*dl->parts, GL_UNSIGNED_INT, dl->index);
- }
- break;
- }
- }
-
- glEnableClientState(GL_NORMAL_ARRAY);
- glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
-
- return 0;
-}
-
-static void drawDispListsolid(ListBase *lb, Object *ob)
-{
- DispList *dl;
- float *data, curcol[4];
- float *ndata;
-
- if(lb==NULL) return;
-
- /* for drawing wire */
- glGetFloatv(GL_CURRENT_COLOR, curcol);
-
- glEnable(GL_LIGHTING);
-
- if(ob->transflag & OB_NEG_SCALE) glFrontFace(GL_CW);
- else glFrontFace(GL_CCW);
-
- if(ob->type==OB_MBALL) { // mball always smooth shaded
- glShadeModel(GL_SMOOTH);
- }
-
- dl= lb->first;
- while(dl) {
- data= dl->verts;
- ndata= dl->nors;
-
- switch(dl->type) {
- case DL_SEGM:
- if(ob->type==OB_SURF) {
- int nr;
-
- glDisable(GL_LIGHTING);
- glColor3fv(curcol);
-
- // glVertexPointer(3, GL_FLOAT, 0, dl->verts);
- // glDrawArrays(GL_LINE_STRIP, 0, dl->nr);
-
- glBegin(GL_LINE_STRIP);
- for(nr= dl->nr; nr; nr--, data+=3)
- glVertex3fv(data);
- glEnd();
-
- glEnable(GL_LIGHTING);
- }
- break;
- case DL_POLY:
- if(ob->type==OB_SURF) {
- int nr;
-
- BIF_ThemeColor(TH_WIRE);
- glDisable(GL_LIGHTING);
-
- /* for some reason glDrawArrays crashes here in half of the platforms (not osx) */
- //glVertexPointer(3, GL_FLOAT, 0, dl->verts);
- //glDrawArrays(GL_LINE_LOOP, 0, dl->nr);
-
- glBegin(GL_LINE_LOOP);
- for(nr= dl->nr; nr; nr--, data+=3)
- glVertex3fv(data);
- glEnd();
-
- glEnable(GL_LIGHTING);
- break;
- }
- case DL_SURF:
-
- if(dl->index) {
- set_gl_material(dl->col+1);
-
- if(dl->rt & CU_SMOOTH) glShadeModel(GL_SMOOTH);
- else glShadeModel(GL_FLAT);
-
- glVertexPointer(3, GL_FLOAT, 0, dl->verts);
- glNormalPointer(GL_FLOAT, 0, dl->nors);
- glDrawElements(GL_QUADS, 4*dl->totindex, GL_UNSIGNED_INT, dl->index);
- }
- break;
-
- case DL_INDEX3:
-
- set_gl_material(dl->col+1);
-
- glVertexPointer(3, GL_FLOAT, 0, dl->verts);
-
- /* voor polys only one normal needed */
- if(index3_nors_incr==0) {
- glDisableClientState(GL_NORMAL_ARRAY);
- glNormal3fv(ndata);
- }
- else
- glNormalPointer(GL_FLOAT, 0, dl->nors);
-
- glDrawElements(GL_TRIANGLES, 3*dl->parts, GL_UNSIGNED_INT, dl->index);
-
- if(index3_nors_incr==0)
- glEnableClientState(GL_NORMAL_ARRAY);
-
- break;
-
- case DL_INDEX4:
-
- set_gl_material(dl->col+1);
-
- glVertexPointer(3, GL_FLOAT, 0, dl->verts);
- glNormalPointer(GL_FLOAT, 0, dl->nors);
- glDrawElements(GL_QUADS, 4*dl->parts, GL_UNSIGNED_INT, dl->index);
-
- break;
- }
- dl= dl->next;
- }
-
- glShadeModel(GL_FLAT);
- glDisable(GL_LIGHTING);
- glFrontFace(GL_CCW);
-}
-
-static void drawDispListshaded(ListBase *lb, Object *ob)
-{
- DispList *dl, *dlob;
- unsigned int *cdata;
-
- if(lb==NULL) return;
-
- glShadeModel(GL_SMOOTH);
- glDisableClientState(GL_NORMAL_ARRAY);
- glEnableClientState(GL_COLOR_ARRAY);
-
- dl= lb->first;
- dlob= ob->disp.first;
- while(dl && dlob) {
-
- cdata= dlob->col1;
- if(cdata==NULL) break;
-
- switch(dl->type) {
- case DL_SURF:
- if(dl->index) {
- glVertexPointer(3, GL_FLOAT, 0, dl->verts);
- glColorPointer(4, GL_UNSIGNED_BYTE, 0, cdata);
- glDrawElements(GL_QUADS, 4*dl->totindex, GL_UNSIGNED_INT, dl->index);
- }
- break;
-
- case DL_INDEX3:
-
- glVertexPointer(3, GL_FLOAT, 0, dl->verts);
- glColorPointer(4, GL_UNSIGNED_BYTE, 0, cdata);
- glDrawElements(GL_TRIANGLES, 3*dl->parts, GL_UNSIGNED_INT, dl->index);
- break;
-
- case DL_INDEX4:
-
- glVertexPointer(3, GL_FLOAT, 0, dl->verts);
- glColorPointer(4, GL_UNSIGNED_BYTE, 0, cdata);
- glDrawElements(GL_QUADS, 4*dl->parts, GL_UNSIGNED_INT, dl->index);
- break;
- }
-
- dl= dl->next;
- dlob= dlob->next;
- }
-
- glShadeModel(GL_FLAT);
- glEnableClientState(GL_NORMAL_ARRAY);
- glDisableClientState(GL_COLOR_ARRAY);
-}
-
-/* returns 1 when nothing was drawn */
-static int drawDispList(Base *base, int dt)
-{
- Object *ob= base->object;
- ListBase *lb=0;
- DispList *dl;
- Curve *cu;
- int solid, retval= 0;
-
- solid= (dt > OB_WIRE);
-
- switch(ob->type) {
- case OB_FONT:
- case OB_CURVE:
- cu= ob->data;
-
- lb= &cu->disp;
-
- if(solid) {
- dl= lb->first;
- if(dl==NULL) return 1;
-
- if(dl->nors==0) addnormalsDispList(ob, lb);
- index3_nors_incr= 0;
-
- if( displist_has_faces(lb)==0) {
- draw_index_wire= 0;
- drawDispListwire(lb);
- draw_index_wire= 1;
- }
- else {
- if(dt==OB_SHADED) {
- if(ob->disp.first==0) shadeDispList(base);
- drawDispListshaded(lb, ob);
- }
- else {
- init_gl_materials(ob, 0);
- glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, 0);
- drawDispListsolid(lb, ob);
- }
- if(ob==G.obedit && cu->bevobj==NULL && cu->taperobj==NULL) {
- cpack(0);
- draw_index_wire= 0;
- drawDispListwire(lb);
- draw_index_wire= 1;
- }
- }
- index3_nors_incr= 1;
- }
- else {
- draw_index_wire= 0;
- retval= drawDispListwire(lb);
- draw_index_wire= 1;
- }
- break;
- case OB_SURF:
-
- lb= &((Curve *)ob->data)->disp;
-
- if(solid) {
- dl= lb->first;
- if(dl==NULL) return 1;
-
- if(dl->nors==NULL) addnormalsDispList(ob, lb);
-
- if(dt==OB_SHADED) {
- if(ob->disp.first==NULL) shadeDispList(base);
- drawDispListshaded(lb, ob);
- }
- else {
- init_gl_materials(ob, 0);
- glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, 0);
-
- drawDispListsolid(lb, ob);
- }
- }
- else {
- retval= drawDispListwire(lb);
- }
- break;
- case OB_MBALL:
-
- if( is_basis_mball(ob)) {
- lb= &ob->disp;
- if(lb->first==NULL) makeDispListMBall(ob);
- if(lb->first==NULL) return 1;
-
- if(solid) {
-
- if(dt==OB_SHADED) {
- dl= lb->first;
- if(dl && dl->col1==0) shadeDispList(base);
- drawDispListshaded(lb, ob);
- }
- else {
- init_gl_materials(ob, 0);
- glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, 0);
-
- drawDispListsolid(lb, ob);
- }
- }
- else{
- /* MetaBalls use DL_INDEX4 type of DispList */
- retval= drawDispListwire(lb);
- }
- }
- break;
- }
-
- return retval;
-}
-
-/* ******************************** */
-
-
-static void draw_particle_system(Base *base, PartEff *paf)
-{
- Object *ob= base->object;
- Particle *pa;
- float ptime, ctime, vec[3], vec1[3], mat[4][4];
- int a, totpart;
-
- pa= paf->keys;
- // FSPARTICLE always rebuild fluid particle system upon change...
- if( (pa==NULL)
- || ( (ob->fluidsimFlag & OB_FLUIDSIM_ENABLE) && (ob->fluidsimSettings) && (ob->fluidsimSettings->type == OB_FLUIDSIM_PARTICLE))
- ) {
- build_particle_system(ob);
- pa= paf->keys;
- if(pa==NULL) return;
- }
-
- myloadmatrix(G.vd->viewmat);
- /* flag abuse... but I need working code too now. This feature doesnt work for per frame animated objects */
- if( (base->flag & OB_FROMDUPLI) && (ob->flag & OB_FROMGROUP) ) {
- Mat4MulMat4(mat, paf->imat, ob->obmat);
- mymultmatrix(mat);
- }
-
- if(ob->ipoflag & OB_OFFS_PARTICLE) ptime= ob->sf;
- else ptime= 0.0;
- ctime= bsystem_time(ob, (float)(G.scene->r.cfra), ptime);
-
- glPointSize(1.0);
-
- if(paf->stype==PAF_VECT) glBegin(GL_LINES);
- else glBegin(GL_POINTS);
-
- totpart= (paf->disp*paf->totpart)/100;
- for(a=0; a<totpart; a++, pa+=paf->totkey) {
-
- if(ctime > pa->time) {
- if(ctime < pa->time+pa->lifetime) {
-
- if(paf->stype==PAF_VECT) {
- where_is_particle(paf, pa, ctime, vec);
- where_is_particle(paf, pa, ctime+1.0, vec1);
-
- glVertex3fv(vec);
- glVertex3fv(vec1);
- }
- else {
- where_is_particle(paf, pa, ctime, vec);
-
- glVertex3fv(vec);
- }
- }
- }
- }
- glEnd();
-
- myloadmatrix(G.vd->viewmat);
- mymultmatrix(ob->obmat); // bring back local matrix for dtx
-}
-
-static void draw_static_particle_system(Object *ob, PartEff *paf, int dt)
-{
- Particle *pa;
- float ctime, mtime, vec[3], veco[3];
- int a, use_norm=0, totpart;
-
- pa= paf->keys;
- // FSPARTICLE always rebuild upon change...
- if( (pa==NULL)
- || ( (ob->fluidsimFlag & OB_FLUIDSIM_ENABLE) && (ob->fluidsimSettings) && (ob->fluidsimSettings->type == OB_FLUIDSIM_PARTICLE))
- ) {
- build_particle_system(ob);
- pa= paf->keys;
- if(pa==NULL) return;
- }
-
- if(paf->stype==PAF_VECT) {
- if(dt>OB_WIRE) {
-
- /* shaded/texture mode: we still draw solid, so have to set materials */
- if(dt>OB_SOLID) init_gl_materials(ob, 0);
-
- glEnable(GL_LIGHTING);
- set_gl_material(paf->omat);
- use_norm= 1;
- }
- }
- else {
- glPointSize(1.0);
- glBegin(GL_POINTS);
- }
-
- totpart= (paf->disp*paf->totpart)/100;
- for(a=0; a<totpart; a++, pa+=paf->totkey) {
-
- if(paf->stype==PAF_VECT) {
-
- glBegin(GL_LINE_STRIP);
- where_is_particle(paf, pa, pa->time, veco);
-
- mtime= pa->time+pa->lifetime+paf->staticstep;
- for(ctime= pa->time+paf->staticstep; ctime<mtime; ctime+=paf->staticstep) {
-
- where_is_particle(paf, pa, ctime, vec);
-
- if(use_norm) {
- float no[3];
- VECSUB(no, vec, veco);
- glNormal3fv(no);
- }
- glVertex3fv(veco);
- VECCOPY(veco, vec);
- }
-
- glVertex3fv(veco);
- glEnd();
- }
- else {
- mtime= pa->time+pa->lifetime+paf->staticstep-1;
- for(ctime= pa->time; ctime<mtime; ctime+=paf->staticstep) {
- where_is_particle(paf, pa, ctime, vec);
- glVertex3fv(vec);
- }
- }
- }
- if(paf->stype==PAF_VECT) {
- glDisable(GL_LIGHTING);
- }
- else {
- glEnd();
- }
-
-}
-
-/* unified drawing of all new particle systems draw types except dupli ob & group */
-/* mostly tries to use vertex arrays for speed */
-
-/* 1. check that everything is ok & updated */
-/* 2. start initialising things */
-/* 3. initialize according to draw type */
-/* 4. allocate drawing data arrays */
-/* 5. start filling the arrays */
-/* 6. draw the arrays */
-/* 7. clean up */
-static void draw_new_particle_system(Base *base, ParticleSystem *psys)
-{
- View3D *v3d= G.vd;
- Object *ob=base->object;
- ParticleSystemModifierData *psmd;
- ParticleSettings *part;
- ParticleData *pars, *pa;
- ParticleKey state, *states=0;
- ParticleCacheKey *cache=0;
- Material *ma;
- Object *bb_ob=0;
- float vel[3], vec[3], vec2[3], imat[4][4], onevec[3]={0.0f,0.0f,0.0f}, bb_center[3];
- float timestep, pixsize=1.0, pa_size, pa_time, r_tilt;
- float cfra=bsystem_time(ob,(float)CFRA,0.0);
- float *vdata=0, *vedata=0, *cdata=0, *ndata=0, *vd=0, *ved=0, *cd=0, *nd=0, xvec[3], yvec[3], zvec[3];
- int a, k, k_max=0, totpart, totpoint=0, draw_as, path_nbr=0;
- int path_possible=0, keys_possible=0, draw_keys=0, totchild=0;
- int select=ob->flag&SELECT;
- GLint polygonmode[2];
- char val[32];
-
-/* 1. */
- if(psys==0)
- return;
-
- part=psys->part;
- pars=psys->particles;
-
- if(part==0 || !psys_check_enabled(ob, psys))
- return;
-
- if(pars==0) return;
-
- if(!G.obedit && psys_in_edit_mode(psys)
- && psys->flag & PSYS_HAIR_DONE && part->draw_as==PART_DRAW_PATH)
- return;
-
- if(part->draw_as==PART_DRAW_NOT) return;
-
-/* 2. */
- if(part->phystype==PART_PHYS_KEYED){
- if(psys->flag & PSYS_FIRST_KEYED){
- if(psys->flag&PSYS_KEYED){
- select=psys_count_keyed_targets(ob,psys);
- if(psys->totkeyed==0)
- return;
- }
- }
- else
- return;
- }
-
- if(select){
- select=0;
- if(psys_get_current(ob)==psys)
- select=1;
- }
-
- psys->flag|=PSYS_DRAWING;
-
- if(!psys->childcache)
- totchild=0;
- else
- totchild=psys->totchild*part->disp/100;
-
- ma= give_current_material(ob,part->omat);
-
- if(select)
- cpack(0xFFFFFF);
- else if(part->draw&PART_DRAW_MAT_COL)
- glColor3f(ma->r,ma->g,ma->b);
- else
- cpack(0);
-
- psmd= psys_get_modifier(ob,psys);
-
- timestep= psys_get_timestep(part);
-
- myloadmatrix(G.vd->viewmat);
-
- if( (base->flag & OB_FROMDUPLI) && (ob->flag & OB_FROMGROUP) ) {
- float mat[4][4];
- Mat4MulMat4(mat, psys->imat, ob->obmat);
- mymultmatrix(mat);
- }
-
- totpart=psys->totpart;
- draw_as=part->draw_as;
-
- if(part->flag&PART_ABS_TIME && part->ipo){
- calc_ipo(part->ipo, cfra);
- execute_ipo((ID *)part, part->ipo);
- }
-
- if(part->flag&PART_GLOB_TIME)
- cfra=bsystem_time(0,(float)CFRA,0.0);
-
- if(psys->pathcache){
- path_possible=1;
- keys_possible=1;
- }
- if(draw_as==PART_DRAW_PATH && path_possible==0)
- draw_as=PART_DRAW_DOT;
-
- if(draw_as!=PART_DRAW_PATH && keys_possible && part->draw&PART_DRAW_KEYS){
- path_nbr=part->keys_step;
- draw_keys=1;
- }
-
-/* 3. */
- switch(draw_as){
- case PART_DRAW_DOT:
- if(part->draw_size)
- glPointSize(part->draw_size);
- else
- glPointSize(2.0); /* default dot size */
- break;
- case PART_DRAW_CIRC:
- /* calculate view aligned matrix: */
- Mat4CpyMat4(imat, G.vd->viewinv);
- Normalize(imat[0]);
- Normalize(imat[1]);
- /* no break! */
- case PART_DRAW_CROSS:
- case PART_DRAW_AXIS:
- /* lets calculate the scale: */
- pixsize= v3d->persmat[0][3]*ob->obmat[3][0]+ v3d->persmat[1][3]*ob->obmat[3][1]+ v3d->persmat[2][3]*ob->obmat[3][2]+ v3d->persmat[3][3];
- pixsize*= v3d->pixsize;
- if(part->draw_size==0.0)
- pixsize*=2.0;
- else
- pixsize*=part->draw_size;
- break;
- case PART_DRAW_OB:
- if(part->dup_ob==0)
- draw_as=PART_DRAW_DOT;
- else
- draw_as=0;
- break;
- case PART_DRAW_GR:
- if(part->dup_group==0)
- draw_as=PART_DRAW_DOT;
- else
- draw_as=0;
- break;
- case PART_DRAW_BB:
- if(G.vd->camera==0 && part->bb_ob==0){
- error("Billboards need an active camera or a target object!");
-
- draw_as=part->draw_as=PART_DRAW_DOT;
-
- if(part->draw_size)
- glPointSize(part->draw_size);
- else
- glPointSize(2.0); /* default dot size */
- }
- else if(part->bb_ob)
- bb_ob=part->bb_ob;
- else
- bb_ob=G.vd->camera;
-
- if(part->bb_align<PART_BB_VIEW)
- onevec[part->bb_align]=1.0f;
- break;
- case PART_DRAW_PATH:
- break;
- }
- if(part->draw & PART_DRAW_SIZE && part->draw_as!=PART_DRAW_CIRC){
- Mat4CpyMat4(imat, G.vd->viewinv);
- Normalize(imat[0]);
- Normalize(imat[1]);
- }
-
-/* 4. */
- if(draw_as && draw_as!=PART_DRAW_PATH){
- if(draw_as!=PART_DRAW_CIRC){
- switch(draw_as){
- case PART_DRAW_AXIS:
- cdata=MEM_callocN((totpart+totchild)*(path_nbr+1)*6*3*sizeof(float), "particle_cdata");
- /* no break! */
- case PART_DRAW_CROSS:
- vdata=MEM_callocN((totpart+totchild)*(path_nbr+1)*6*3*sizeof(float), "particle_vdata");
- break;
- case PART_DRAW_LINE:
- vdata=MEM_callocN((totpart+totchild)*(path_nbr+1)*2*3*sizeof(float), "particle_vdata");
- break;
- case PART_DRAW_BB:
- vdata=MEM_callocN((totpart+totchild)*(path_nbr+1)*4*3*sizeof(float), "particle_vdata");
- ndata=MEM_callocN((totpart+totchild)*(path_nbr+1)*4*3*sizeof(float), "particle_vdata");
- break;
- default:
- vdata=MEM_callocN((totpart+totchild)*(path_nbr+1)*3*sizeof(float), "particle_vdata");
- }
- }
-
- if(part->draw&PART_DRAW_VEL && draw_as!=PART_DRAW_LINE)
- vedata=MEM_callocN((totpart+totchild)*2*3*(path_nbr+1)*sizeof(float), "particle_vedata");
-
- vd=vdata;
- ved=vedata;
- cd=cdata;
- nd=ndata;
-
- psys->lattice=psys_get_lattice(ob,psys);
- }
-
- if(draw_as){
-/* 5. */
- for(a=0,pa=pars; a<totpart+totchild; a++, pa++){
- if(a<totpart){
- if(totchild && (part->draw&PART_DRAW_PARENT)==0) continue;
- if(pa->flag & PARS_NO_DISP || pa->flag & PARS_UNEXIST) continue;
-
- pa_time=(cfra-pa->time)/pa->lifetime;
-
- if((part->flag&PART_ABS_TIME)==0 && part->ipo){
- calc_ipo(part->ipo, 100*pa_time);
- execute_ipo((ID *)part, part->ipo);
- }
-
- pa_size=pa->size;
-
- r_tilt=1.0f+pa->r_ave[0];
-
- if(path_nbr){
- cache=psys->pathcache[a];
- k_max=(int)(cache->steps);
- }
- }
- else{
- ChildParticle *cpa= &psys->child[a-totpart];
-
- pa_time=psys_get_child_time(psys,cpa,cfra);
-
- if((part->flag&PART_ABS_TIME)==0 && part->ipo){
- calc_ipo(part->ipo, 100*pa_time);
- execute_ipo((ID *)part, part->ipo);
- }
-
- pa_size=psys_get_child_size(psys,cpa,cfra,0);
-
- r_tilt=2.0f*cpa->rand[2];
- if(path_nbr){
- cache=psys->childcache[a-totpart];
- k_max=(int)(cache->steps);
- }
- }
-
- if(draw_as!=PART_DRAW_PATH){
- int next_pa=0;
- for(k=0; k<=path_nbr; k++){
- if(draw_keys){
- state.time=(float)k/(float)path_nbr;
- psys_get_particle_on_path(ob,psys,a,&state,1);
- }
- else if(path_nbr){
- if(k<=k_max){
- VECCOPY(state.co,(cache+k)->co);
- VECCOPY(state.vel,(cache+k)->vel);
- QUATCOPY(state.rot,(cache+k)->rot);
- }
- else
- continue;
- }
- else{
- state.time=cfra;
- if(psys_get_particle_state(ob,psys,a,&state,0)==0){
- next_pa=1;
- break;
- }
- }
-
- switch(draw_as){
- case PART_DRAW_DOT:
- if(vd){
- VECCOPY(vd,state.co) vd+=3;
- }
- break;
- case PART_DRAW_CROSS:
- case PART_DRAW_AXIS:
- vec[0]=2.0f*pixsize;
- vec[1]=vec[2]=0.0;
- QuatMulVecf(state.rot,vec);
- if(draw_as==PART_DRAW_AXIS){
- cd[1]=cd[2]=cd[4]=cd[5]=0.0;
- cd[0]=cd[3]=1.0;
- cd[6]=cd[8]=cd[9]=cd[11]=0.0;
- cd[7]=cd[10]=1.0;
- cd[13]=cd[12]=cd[15]=cd[16]=0.0;
- cd[14]=cd[17]=1.0;
- cd+=18;
-
- VECCOPY(vec2,state.co);
- }
- else VECSUB(vec2,state.co,vec);
-
- VECADD(vec,state.co,vec);
- VECCOPY(vd,vec); vd+=3;
- VECCOPY(vd,vec2); vd+=3;
-
- vec[1]=2.0f*pixsize;
- vec[0]=vec[2]=0.0;
- QuatMulVecf(state.rot,vec);
- if(draw_as==PART_DRAW_AXIS){
- VECCOPY(vec2,state.co);
- }
- else VECSUB(vec2,state.co,vec);
-
- VECADD(vec,state.co,vec);
- VECCOPY(vd,vec); vd+=3;
- VECCOPY(vd,vec2); vd+=3;
-
- vec[2]=2.0f*pixsize;
- vec[0]=vec[1]=0.0;
- QuatMulVecf(state.rot,vec);
- if(draw_as==PART_DRAW_AXIS){
- VECCOPY(vec2,state.co);
- }
- else VECSUB(vec2,state.co,vec);
-
- VECADD(vec,state.co,vec);
-
- VECCOPY(vd,vec); vd+=3;
- VECCOPY(vd,vec2); vd+=3;
- break;
- case PART_DRAW_LINE:
- VECCOPY(vec,state.vel);
- Normalize(vec);
- if(part->draw & PART_DRAW_VEL_LENGTH)
- VecMulf(vec,VecLength(state.vel));
- VECADDFAC(vd,state.co,vec,-part->draw_line[0]); vd+=3;
- VECADDFAC(vd,state.co,vec,part->draw_line[1]); vd+=3;
- break;
- case PART_DRAW_CIRC:
- drawcircball(GL_LINE_LOOP, state.co, pixsize, imat);
- break;
- case PART_DRAW_BB:
- if(part->draw&PART_DRAW_BB_LOCK && part->bb_align==PART_BB_VIEW){
- VECCOPY(xvec,bb_ob->obmat[0]);
- Normalize(xvec);
- VECCOPY(yvec,bb_ob->obmat[1]);
- Normalize(yvec);
- VECCOPY(zvec,bb_ob->obmat[2]);
- Normalize(zvec);
- }
- else if(part->bb_align==PART_BB_VEL){
- float temp[3];
- VECCOPY(temp,state.vel);
- Normalize(temp);
- VECSUB(zvec,bb_ob->obmat[3],state.co);
- if(part->draw&PART_DRAW_BB_LOCK){
- float fac=-Inpf(zvec,temp);
- VECADDFAC(zvec,zvec,temp,fac);
- }
- Normalize(zvec);
- Crossf(xvec,temp,zvec);
- Normalize(xvec);
- Crossf(yvec,zvec,xvec);
- }
- else{
- VECSUB(zvec,bb_ob->obmat[3],state.co);
- if(part->draw&PART_DRAW_BB_LOCK)
- zvec[part->bb_align]=0.0f;
- Normalize(zvec);
-
- if(part->bb_align<PART_BB_VIEW)
- Crossf(xvec,onevec,zvec);
- else
- Crossf(xvec,bb_ob->obmat[1],zvec);
- Normalize(xvec);
- Crossf(yvec,zvec,xvec);
- }
-
- VECCOPY(vec,xvec);
- VECCOPY(vec2,yvec);
-
- VecMulf(xvec,cos(part->bb_tilt*(1.0f-part->bb_rand_tilt*r_tilt)*(float)M_PI));
- VecMulf(vec2,sin(part->bb_tilt*(1.0f-part->bb_rand_tilt*r_tilt)*(float)M_PI));
- VECADD(xvec,xvec,vec2);
-
- VecMulf(yvec,cos(part->bb_tilt*(1.0f-part->bb_rand_tilt*r_tilt)*(float)M_PI));
- VecMulf(vec,-sin(part->bb_tilt*(1.0f-part->bb_rand_tilt*r_tilt)*(float)M_PI));
- VECADD(yvec,yvec,vec);
-
- VecMulf(xvec,pa_size);
- VecMulf(yvec,pa_size);
-
- VECADDFAC(bb_center,state.co,xvec,part->bb_offset[0]);
- VECADDFAC(bb_center,bb_center,yvec,part->bb_offset[1]);
-
- VECADD(vd,bb_center,xvec);
- VECADD(vd,vd,yvec); vd+=3;
-
- VECSUB(vd,bb_center,xvec);
- VECADD(vd,vd,yvec); vd+=3;
-
- VECSUB(vd,bb_center,xvec);
- VECSUB(vd,vd,yvec); vd+=3;
-
- VECADD(vd,bb_center,xvec);
- VECSUB(vd,vd,yvec); vd+=3;
-
- VECCOPY(nd, zvec); nd+=3;
- VECCOPY(nd, zvec); nd+=3;
- VECCOPY(nd, zvec); nd+=3;
- VECCOPY(nd, zvec); nd+=3;
- break;
- }
-
- if(vedata){
- VECCOPY(ved,state.co);
- ved+=3;
- VECCOPY(vel,state.vel);
- VecMulf(vel,timestep);
- VECADD(ved,state.co,vel);
- ved+=3;
- }
-
- if(part->draw & PART_DRAW_SIZE){
- setlinestyle(3);
- drawcircball(GL_LINE_LOOP, state.co, pa_size, imat);
- setlinestyle(0);
- }
-
- totpoint++;
- }
- if(next_pa)
- continue;
- if(part->draw&PART_DRAW_NUM){
- /* in path drawing state.co is the end point */
- glRasterPos3f(state.co[0], state.co[1], state.co[2]);
- sprintf(val," %i",a);
- BMF_DrawString(G.font, val);
- }
- }
- }
-/* 6. */
-
- glGetIntegerv(GL_POLYGON_MODE, polygonmode);
- glDisableClientState(GL_NORMAL_ARRAY);
-
- if(draw_as != PART_DRAW_CIRC){
- if(draw_as==PART_DRAW_PATH){
- ParticleCacheKey **cache, *path;
- float *cd2=0,*cdata2=0;
-
- glEnableClientState(GL_VERTEX_ARRAY);
- glEnableClientState(GL_NORMAL_ARRAY);
- glEnable(GL_LIGHTING);
-
- if(part->draw&PART_DRAW_MAT_COL) {
- glEnableClientState(GL_COLOR_ARRAY);
- glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE);
- glEnable(GL_COLOR_MATERIAL);
- }
-
- if(totchild && (part->draw&PART_DRAW_PARENT)==0)
- totpart=0;
-
- cache=psys->pathcache;
- for(a=0, pa=psys->particles; a<totpart; a++, pa++){
- path=cache[a];
- glVertexPointer(3, GL_FLOAT, sizeof(ParticleCacheKey), path->co);
- glNormalPointer(GL_FLOAT, sizeof(ParticleCacheKey), path->vel);
- if(part->draw&PART_DRAW_MAT_COL)
- glColorPointer(3, GL_FLOAT, sizeof(ParticleCacheKey), path->col);
- glDrawArrays(GL_LINE_STRIP, 0, path->steps + 1);
- }
-
- cache=psys->childcache;
- for(a=0; a<totchild; a++){
- path=cache[a];
- glVertexPointer(3, GL_FLOAT, sizeof(ParticleCacheKey), path->co);
- glNormalPointer(GL_FLOAT, sizeof(ParticleCacheKey), path->vel);
- if(part->draw&PART_DRAW_MAT_COL)
- glColorPointer(3, GL_FLOAT, sizeof(ParticleCacheKey), path->col);
- glDrawArrays(GL_LINE_STRIP, 0, path->steps + 1);
- }
-
- if(part->draw&PART_DRAW_MAT_COL) {
- glDisable(GL_COLOR_ARRAY);
- glDisable(GL_COLOR_MATERIAL);
- }
-
- if(cdata2)
- MEM_freeN(cdata2);
- cd2=cdata2=0;
-
- glLineWidth(1.0f);
-
- /* draw particle edit mode key points*/
- }
-
- if(draw_as!=PART_DRAW_PATH){
- glDisableClientState(GL_COLOR_ARRAY);
-
- if(vdata){
- glEnableClientState(GL_VERTEX_ARRAY);
- glVertexPointer(3, GL_FLOAT, 0, vdata);
- }
- else
- glDisableClientState(GL_VERTEX_ARRAY);
-
- if(ndata && MIN2(G.vd->drawtype, ob->dt)>OB_WIRE){
- glEnableClientState(GL_NORMAL_ARRAY);
- glNormalPointer(GL_FLOAT, 0, ndata);
- glEnable(GL_LIGHTING);
- }
- else{
- glDisableClientState(GL_NORMAL_ARRAY);
- glDisable(GL_LIGHTING);
- }
-
- switch(draw_as){
- case PART_DRAW_AXIS:
- case PART_DRAW_CROSS:
- if(cdata){
- glEnableClientState(GL_COLOR_ARRAY);
- glColorPointer(3, GL_FLOAT, 0, cdata);
- }
- glDrawArrays(GL_LINES, 0, 6*totpoint);
- break;
- case PART_DRAW_LINE:
- glDrawArrays(GL_LINES, 0, 2*totpoint);
- break;
- case PART_DRAW_BB:
- if(MIN2(G.vd->drawtype, ob->dt)<=OB_WIRE)
- glPolygonMode(GL_FRONT_AND_BACK,GL_LINE);
-
- glDrawArrays(GL_QUADS, 0, 4*totpoint);
- break;
- default:
- glDrawArrays(GL_POINTS, 0, totpoint);
- break;
- }
- }
-
- }
- if(vedata){
- glDisableClientState(GL_COLOR_ARRAY);
- cpack(0xC0C0C0);
-
- glEnableClientState(GL_VERTEX_ARRAY);
- glVertexPointer(3, GL_FLOAT, 0, vedata);
-
- glDrawArrays(GL_LINES, 0, 2*totpoint);
- }
-
- glPolygonMode(GL_FRONT, polygonmode[0]);
- glPolygonMode(GL_BACK, polygonmode[1]);
- }
-
-/* 7. */
-
- glDisable(GL_LIGHTING);
- glDisableClientState(GL_COLOR_ARRAY);
- glEnableClientState(GL_NORMAL_ARRAY);
- glEnable(GL_DEPTH_TEST);
-
- if(states)
- MEM_freeN(states);
- if(vdata)
- MEM_freeN(vdata);
- if(vedata)
- MEM_freeN(vedata);
- if(cdata)
- MEM_freeN(cdata);
- if(ndata)
- MEM_freeN(ndata);
-
- psys->flag &= ~PSYS_DRAWING;
-
- if(psys->lattice){
- end_latt_deform();
- psys->lattice=0;
- }
-
- myloadmatrix(G.vd->viewmat);
- mymultmatrix(ob->obmat); // bring back local matrix for dtx
-}
-
-static void draw_particle_edit(Object *ob, ParticleSystem *psys)
-{
- ParticleEdit *edit = psys->edit;
- ParticleData *pa;
- ParticleCacheKey **path;
- ParticleEditKey *key;
- ParticleEditSettings *pset = PE_settings();
- int i, k, totpart = psys->totpart, totchild=0, timed = pset->draw_timed;
- char nosel[4], sel[4];
- float sel_col[3];
- float nosel_col[3];
- char val[32];
-
- if(psys->pathcache==0){
- PE_hide_keys_time(psys,CFRA);
- psys_cache_paths(ob,psys,CFRA,0);
- }
-
- if(pset->flag & PE_SHOW_CHILD && psys->part->draw_as == PART_DRAW_PATH) {
- if(psys->childcache==0)
- psys_cache_child_paths(ob, psys, CFRA, 0);
- }
- else if(psys->childcache)
- free_child_path_cache(psys);
-
- if((G.vd->flag & V3D_ZBUF_SELECT)==0)
- glDisable(GL_DEPTH_TEST);
-
- myloadmatrix(G.vd->viewmat);
-
- BIF_GetThemeColor3ubv(TH_VERTEX_SELECT, sel);
- BIF_GetThemeColor3ubv(TH_VERTEX, nosel);
- sel_col[0]=(float)sel[0]/255.0f;
- sel_col[1]=(float)sel[1]/255.0f;
- sel_col[2]=(float)sel[2]/255.0f;
- nosel_col[0]=(float)nosel[0]/255.0f;
- nosel_col[1]=(float)nosel[1]/255.0f;
- nosel_col[2]=(float)nosel[2]/255.0f;
-
- if(psys->childcache)
- totchild = psys->totchildcache;
-
- /* draw paths */
- glEnableClientState(GL_VERTEX_ARRAY);
- glEnableClientState(GL_NORMAL_ARRAY);
- glEnableClientState(GL_COLOR_ARRAY);
- if(timed)
- glEnable(GL_BLEND);
-
- if(pset->brushtype == PE_BRUSH_WEIGHT){
- glLineWidth(2.0f);
- glEnableClientState(GL_COLOR_ARRAY);
- glDisable(GL_LIGHTING);
- }
-
- glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE);
- glEnable(GL_COLOR_MATERIAL);
-
- for(i=0, pa=psys->particles, path = psys->pathcache; i<totpart; i++, pa++, path++){
- glVertexPointer(3, GL_FLOAT, sizeof(ParticleCacheKey), (*path)->co);
- glNormalPointer(GL_FLOAT, sizeof(ParticleCacheKey), (*path)->vel);
- glColorPointer(3, GL_FLOAT, sizeof(ParticleCacheKey), (*path)->col);
-
- glDrawArrays(GL_LINE_STRIP, 0, (int)(*path)->steps + 1);
- }
-
- glEnable(GL_LIGHTING);
-
- for(i=0, path=psys->childcache; i<totchild; i++,path++){
- glVertexPointer(3, GL_FLOAT, sizeof(ParticleCacheKey), (*path)->co);
- glNormalPointer(GL_FLOAT, sizeof(ParticleCacheKey), (*path)->vel);
- glColorPointer(3, GL_FLOAT, sizeof(ParticleCacheKey), (*path)->col);
-
- glDrawArrays(GL_LINE_STRIP, 0, (int)(*path)->steps + 1);
- }
-
- glDisable(GL_COLOR_MATERIAL);
-
- /* draw edit vertices */
- if(G.scene->selectmode!=SCE_SELECT_PATH){
- glDisableClientState(GL_NORMAL_ARRAY);
- glEnableClientState(GL_COLOR_ARRAY);
- glDisable(GL_LIGHTING);
- glPointSize(4.0f);
-
- if(G.scene->selectmode==SCE_SELECT_POINT){
- float *cd=0,*cdata=0;
- cd=cdata=MEM_callocN(edit->totkeys*(timed?4:3)*sizeof(float), "particle edit color data");
-
- for(i=0, pa=psys->particles; i<totpart; i++, pa++){
- for(k=0, key=edit->keys[i]; k<pa->totkey; k++, key++){
- if(key->flag&PEK_SELECT){
- VECCOPY(cd,sel_col);
- }
- else{
- VECCOPY(cd,nosel_col);
- }
- if(timed)
- *(cd+3) = (key->flag&PEK_HIDE)?0.0f:1.0f;
- cd += (timed?4:3);
- }
- }
- cd=cdata;
- for(i=0, pa=psys->particles; i<totpart; i++, pa++){
- if((pa->flag & PARS_HIDE)==0){
- glVertexPointer(3, GL_FLOAT, sizeof(ParticleEditKey), edit->keys[i]->world_co);
- glColorPointer((timed?4:3), GL_FLOAT, (timed?4:3)*sizeof(float), cd);
- glDrawArrays(GL_POINTS, 0, pa->totkey);
- }
- cd += (timed?4:3) * pa->totkey;
-
- if(pset->flag&PE_SHOW_TIME && (pa->flag&PARS_HIDE)==0){
- for(k=0, key=edit->keys[i]+k; k<pa->totkey; k++, key++){
- if(key->flag & PEK_HIDE) continue;
-
- glRasterPos3fv(key->world_co);
- sprintf(val," %.1f",*key->time);
- BMF_DrawString(G.font, val);
- }
- }
- }
- if(cdata)
- MEM_freeN(cdata);
- cd=cdata=0;
- }
- else if(G.scene->selectmode == SCE_SELECT_END){
- for(i=0, pa=psys->particles; i<totpart; i++, pa++){
- if((pa->flag & PARS_HIDE)==0){
- key = edit->keys[i] + pa->totkey - 1;
- if(key->flag & PEK_SELECT)
- glColor3fv(sel_col);
- else
- glColor3fv(nosel_col);
- /* has to be like this.. otherwise selection won't work, have try glArrayElement later..*/
- glBegin(GL_POINTS);
- glVertex3fv(key->world_co);
- glEnd();
-
- if(pset->flag & PE_SHOW_TIME){
- glRasterPos3fv(key->world_co);
- sprintf(val," %.1f",*key->time);
- BMF_DrawString(G.font, val);
- }
- }
- }
- }
- }
-
- glDisable(GL_BLEND);
- glDisable(GL_LIGHTING);
- glDisableClientState(GL_COLOR_ARRAY);
- glEnableClientState(GL_NORMAL_ARRAY);
- glEnable(GL_DEPTH_TEST);
- glLineWidth(1.0f);
-
- mymultmatrix(ob->obmat); // bring back local matrix for dtx
-}
-
-unsigned int nurbcol[8]= {
- 0, 0x9090, 0x409030, 0x603080, 0, 0x40fff0, 0x40c033, 0xA090F0 };
-
-static void tekenhandlesN(Nurb *nu, short sel)
-{
- BezTriple *bezt;
- float *fp;
- unsigned int *col;
- int a;
-
- if(nu->hide || (G.f & G_HIDDENHANDLES)) return;
-
- glBegin(GL_LINES);
-
- if( (nu->type & 7)==1) {
- if(sel) col= nurbcol+4;
- else col= nurbcol;
-
- bezt= nu->bezt;
- a= nu->pntsu;
- while(a--) {
- if(bezt->hide==0) {
- if( (bezt->f2 & SELECT)==sel) {
- fp= bezt->vec[0];
-
- cpack(col[bezt->h1]);
- glVertex3fv(fp);
- glVertex3fv(fp+3);
-
- cpack(col[bezt->h2]);
- glVertex3fv(fp+3);
- glVertex3fv(fp+6);
- }
- else if( (bezt->f1 & SELECT)==sel) {
- fp= bezt->vec[0];
-
- cpack(col[bezt->h1]);
- glVertex3fv(fp);
- glVertex3fv(fp+3);
- }
- else if( (bezt->f3 & SELECT)==sel) {
- fp= bezt->vec[1];
-
- cpack(col[bezt->h2]);
- glVertex3fv(fp);
- glVertex3fv(fp+3);
- }
- }
- bezt++;
- }
- }
- glEnd();
-}
-
-static void tekenvertsN(Nurb *nu, short sel)
-{
- BezTriple *bezt;
- BPoint *bp;
- float size;
- int a;
-
- if(nu->hide) return;
-
- if(sel) BIF_ThemeColor(TH_VERTEX_SELECT);
- else BIF_ThemeColor(TH_VERTEX);
-
- size= BIF_GetThemeValuef(TH_VERTEX_SIZE);
- glPointSize(size);
-
- bglBegin(GL_POINTS);
-
- if((nu->type & 7)==1) {
-
- bezt= nu->bezt;
- a= nu->pntsu;
- while(a--) {
- if(bezt->hide==0) {
- if (G.f & G_HIDDENHANDLES) {
- if((bezt->f2 & SELECT)==sel) bglVertex3fv(bezt->vec[1]);
- } else {
- if((bezt->f1 & SELECT)==sel) bglVertex3fv(bezt->vec[0]);
- if((bezt->f2 & SELECT)==sel) bglVertex3fv(bezt->vec[1]);
- if((bezt->f3 & SELECT)==sel) bglVertex3fv(bezt->vec[2]);
- }
- }
- bezt++;
- }
- }
- else {
- bp= nu->bp;
- a= nu->pntsu*nu->pntsv;
- while(a--) {
- if(bp->hide==0) {
- if((bp->f1 & SELECT)==sel) bglVertex3fv(bp->vec);
- }
- bp++;
- }
- }
-
- bglEnd();
- glPointSize(1.0);
-}
-
-static void draw_editnurb(Object *ob, Nurb *nurb, int sel)
-{
- Nurb *nu;
- BPoint *bp, *bp1;
- int a, b, ofs;
-
- nu= nurb;
- while(nu) {
- if(nu->hide==0) {
- switch(nu->type & 7) {
- case CU_POLY:
- cpack(nurbcol[3]);
- bp= nu->bp;
- for(b=0; b<nu->pntsv; b++) {
- if(nu->flagu & 1) glBegin(GL_LINE_LOOP);
- else glBegin(GL_LINE_STRIP);
-
- for(a=0; a<nu->pntsu; a++, bp++) {
- glVertex3fv(bp->vec);
- }
-
- glEnd();
- }
- break;
- case CU_NURBS:
-
- bp= nu->bp;
- for(b=0; b<nu->pntsv; b++) {
- bp1= bp;
- bp++;
- for(a=nu->pntsu-1; a>0; a--, bp++) {
- if(bp->hide==0 && bp1->hide==0) {
- if(sel) {
- if( (bp->f1 & SELECT) && ( bp1->f1 & SELECT ) ) {
- cpack(nurbcol[5]);
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(bp->vec);
- glVertex3fv(bp1->vec);
- glEnd();
- }
- }
- else {
- if( (bp->f1 & SELECT) && ( bp1->f1 & SELECT) );
- else {
- cpack(nurbcol[1]);
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(bp->vec);
- glVertex3fv(bp1->vec);
- glEnd();
- }
- }
- }
- bp1= bp;
- }
- }
- if(nu->pntsv > 1) { /* surface */
-
- ofs= nu->pntsu;
- for(b=0; b<nu->pntsu; b++) {
- bp1= nu->bp+b;
- bp= bp1+ofs;
- for(a=nu->pntsv-1; a>0; a--, bp+=ofs) {
- if(bp->hide==0 && bp1->hide==0) {
- if(sel) {
- if( (bp->f1 & SELECT) && ( bp1->f1 & SELECT) ) {
- cpack(nurbcol[7]);
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(bp->vec);
- glVertex3fv(bp1->vec);
- glEnd();
- }
- }
- else {
- if( (bp->f1 & SELECT) && ( bp1->f1 & SELECT) );
- else {
- cpack(nurbcol[3]);
-
- glBegin(GL_LINE_STRIP);
- glVertex3fv(bp->vec);
- glVertex3fv(bp1->vec);
- glEnd();
- }
- }
- }
- bp1= bp;
- }
- }
-
- }
- break;
- }
- }
- nu= nu->next;
- }
-}
-
-static void drawnurb(Base *base, Nurb *nurb, int dt)
-{
- Object *ob= base->object;
- Curve *cu = ob->data;
- Nurb *nu;
- BevList *bl;
-
- retopo_matrix_update(G.vd);
-
- /* DispList */
- BIF_ThemeColor(TH_WIRE);
- drawDispList(base, dt);
-
- if(G.vd->zbuf) glDisable(GL_DEPTH_TEST);
-
- /* first non-selected handles */
- for(nu=nurb; nu; nu=nu->next) {
- if((nu->type & 7)==CU_BEZIER) {
- tekenhandlesN(nu, 0);
- }
- }
- draw_editnurb(ob, nurb, 0);
- draw_editnurb(ob, nurb, 1);
- /* selected handles */
- for(nu=nurb; nu; nu=nu->next) {
- if((nu->type & 7)==1) tekenhandlesN(nu, 1);
- tekenvertsN(nu, 0);
- }
-
- if(G.vd->zbuf) glEnable(GL_DEPTH_TEST);
-
- /* direction vectors for 3d curve paths
- when at its lowest, dont render normals */
- if(cu->flag & CU_3D && G.scene->editbutsize > 0.0015) {
- BIF_ThemeColor(TH_WIRE);
- for (bl=cu->bev.first,nu=nurb; nu && bl; bl=bl->next,nu=nu->next) {
- BevPoint *bevp= (BevPoint *)(bl+1);
- int nr= bl->nr;
- int skip= nu->resolu/16;
- float fac;
-
- while (nr-->0) { /* accounts for empty bevel lists */
- float ox,oy,oz; // Offset perpendicular to the curve
- float dx,dy,dz; // Delta along the curve
-
- fac = calc_curve_subdiv_radius(cu, nu, (bl->nr - nr)) * G.scene->editbutsize;
-
- ox = fac*bevp->mat[0][0];
- oy = fac*bevp->mat[0][1];
- oz = fac*bevp->mat[0][2];
-
- dx = fac*bevp->mat[2][0];
- dy = fac*bevp->mat[2][1];
- dz = fac*bevp->mat[2][2];
-
- glBegin(GL_LINE_STRIP);
- glVertex3f(bevp->x - ox - dx, bevp->y - oy - dy, bevp->z - oz - dz);
- glVertex3f(bevp->x, bevp->y, bevp->z);
- glVertex3f(bevp->x + ox - dx, bevp->y + oy - dy, bevp->z + oz - dz);
- glEnd();
-
- bevp += skip+1;
- nr -= skip;
- }
- }
- }
-
- if(G.vd->zbuf) glDisable(GL_DEPTH_TEST);
-
- for(nu=nurb; nu; nu=nu->next) {
- tekenvertsN(nu, 1);
- }
-
- if(G.vd->zbuf) glEnable(GL_DEPTH_TEST);
-}
-
-/* draw a sphere for use as an empty drawtype */
-static void draw_empty_sphere (float size)
-{
- float cent=0;
- GLUquadricObj *qobj = gluNewQuadric();
- gluQuadricDrawStyle(qobj, GLU_SILHOUETTE);
-
- glPushMatrix();
- glTranslatef(cent, cent, cent);
- glScalef(size, size, size);
- gluSphere(qobj, 1.0, 8, 5);
-
- glPopMatrix();
-
- gluDeleteQuadric(qobj);
-}
-
-/* draw a cone for use as an empty drawtype */
-static void draw_empty_cone (float size)
-{
- float cent=0;
- float radius;
- GLUquadricObj *qobj = gluNewQuadric();
- gluQuadricDrawStyle(qobj, GLU_SILHOUETTE);
-
-
- glPushMatrix();
-
- radius = size;
- glTranslatef(cent,cent, cent);
- glScalef(radius, 2.0*size, radius);
- glRotatef(-90., 1.0, 0.0, 0.0);
- gluCylinder(qobj, 1.0, 0.0, 1.0, 8, 1);
-
- glPopMatrix();
-
- gluDeleteQuadric(qobj);
-}
-
-/* draw points on curve speed handles */
-static void curve_draw_speed(Object *ob)
-{
- Curve *cu= ob->data;
- IpoCurve *icu;
- BezTriple *bezt;
- float loc[4], dir[3];
- int a;
-
- if(cu->ipo==NULL)
- return;
-
- icu= cu->ipo->curve.first;
- if(icu==NULL || icu->totvert<2)
- return;
-
- glPointSize( BIF_GetThemeValuef(TH_VERTEX_SIZE) );
- bglBegin(GL_POINTS);
-
- for(a=0, bezt= icu->bezt; a<icu->totvert; a++, bezt++) {
- if( where_on_path(ob, bezt->vec[1][1], loc, dir)) {
- BIF_ThemeColor((bezt->f2 & SELECT) && ob==OBACT?TH_VERTEX_SELECT:TH_VERTEX);
- bglVertex3fv(loc);
- }
- }
-
- glPointSize(1.0);
- bglEnd();
-}
-
-
-static void tekentextcurs(void)
-{
- cpack(0);
-
- set_inverted_drawing(1);
- glBegin(GL_QUADS);
- glVertex2fv(G.textcurs[0]);
- glVertex2fv(G.textcurs[1]);
- glVertex2fv(G.textcurs[2]);
- glVertex2fv(G.textcurs[3]);
- glEnd();
- set_inverted_drawing(0);
-}
-
-static void drawspiral(float *cent, float rad, float tmat[][4], int start)
-{
- float vec[3], vx[3], vy[3];
- int a, tot=32;
- char inverse=0;
-
- if (start < 0) {
- inverse = 1;
- start *= -1;
- }
-
- VECCOPY(vx, tmat[0]);
- VECCOPY(vy, tmat[1]);
- VecMulf(vx, rad);
- VecMulf(vy, rad);
-
- VECCOPY(vec, cent);
-
- if (inverse==0) {
- for(a=0; a<tot; a++) {
- if (a+start>31)
- start=-a + 1;
- glBegin(GL_LINES);
- glVertex3fv(vec);
- vec[0]= cent[0] + *(sinval+a+start) * (vx[0] * (float)a/(float)tot) + *(cosval+a+start) * (vy[0] * (float)a/(float)tot);
- vec[1]= cent[1] + *(sinval+a+start) * (vx[1] * (float)a/(float)tot) + *(cosval+a+start) * (vy[1] * (float)a/(float)tot);
- vec[2]= cent[2] + *(sinval+a+start) * (vx[2] * (float)a/(float)tot) + *(cosval+a+start) * (vy[2] * (float)a/(float)tot);
- glVertex3fv(vec);
- glEnd();
- }
- }
- else {
- a=0;
- vec[0]= cent[0] + *(sinval+a+start) * (vx[0] * (float)(-a+31)/(float)tot) + *(cosval+a+start) * (vy[0] * (float)(-a+31)/(float)tot);
- vec[1]= cent[1] + *(sinval+a+start) * (vx[1] * (float)(-a+31)/(float)tot) + *(cosval+a+start) * (vy[1] * (float)(-a+31)/(float)tot);
- vec[2]= cent[2] + *(sinval+a+start) * (vx[2] * (float)(-a+31)/(float)tot) + *(cosval+a+start) * (vy[2] * (float)(-a+31)/(float)tot);
- for(a=0; a<tot; a++) {
- if (a+start>31)
- start=-a + 1;
- glBegin(GL_LINES);
- glVertex3fv(vec);
- vec[0]= cent[0] + *(sinval+a+start) * (vx[0] * (float)(-a+31)/(float)tot) + *(cosval+a+start) * (vy[0] * (float)(-a+31)/(float)tot);
- vec[1]= cent[1] + *(sinval+a+start) * (vx[1] * (float)(-a+31)/(float)tot) + *(cosval+a+start) * (vy[1] * (float)(-a+31)/(float)tot);
- vec[2]= cent[2] + *(sinval+a+start) * (vx[2] * (float)(-a+31)/(float)tot) + *(cosval+a+start) * (vy[2] * (float)(-a+31)/(float)tot);
- glVertex3fv(vec);
- glEnd();
- }
- }
-}
-
-/* draws a circle on x-z plane given the scaling of the circle, assuming that
- * all required matrices have been set (used for drawing empties)
- */
-static void drawcircle_size(float size)
-{
- float x, y;
- short degrees;
-
- glBegin(GL_LINE_LOOP);
-
- /* coordinates are: cos(degrees*11.25)=x, sin(degrees*11.25)=y, 0.0f=z */
- for (degrees=0; degrees<32; degrees++) {
- x= *(cosval + degrees);
- y= *(sinval + degrees);
-
- glVertex3f(x*size, 0.0f, y*size);
- }
-
- glEnd();
-
-}
-
-void drawcircball(int mode, float *cent, float rad, float tmat[][4])
-{
- float vec[3], vx[3], vy[3];
- int a, tot=32;
-
- VECCOPY(vx, tmat[0]);
- VECCOPY(vy, tmat[1]);
- VecMulf(vx, rad);
- VecMulf(vy, rad);
-
- glBegin(mode);
- for(a=0; a<tot; a++) {
- vec[0]= cent[0] + *(sinval+a) * vx[0] + *(cosval+a) * vy[0];
- vec[1]= cent[1] + *(sinval+a) * vx[1] + *(cosval+a) * vy[1];
- vec[2]= cent[2] + *(sinval+a) * vx[2] + *(cosval+a) * vy[2];
- glVertex3fv(vec);
- }
- glEnd();
-}
-/* needs fixing if non-identity matrice used */
-static void drawtube(float *vec, float radius, float height, float tmat[][4])
-{
- float cur[3];
- drawcircball(GL_LINE_LOOP, vec, radius, tmat);
-
- VecCopyf(cur,vec);
- cur[2]+=height;
-
- drawcircball(GL_LINE_LOOP, cur, radius, tmat);
-
- glBegin(GL_LINES);
- glVertex3f(vec[0]+radius,vec[1],vec[2]);
- glVertex3f(cur[0]+radius,cur[1],cur[2]);
- glVertex3f(vec[0]-radius,vec[1],vec[2]);
- glVertex3f(cur[0]-radius,cur[1],cur[2]);
- glVertex3f(vec[0],vec[1]+radius,vec[2]);
- glVertex3f(cur[0],cur[1]+radius,cur[2]);
- glVertex3f(vec[0],vec[1]-radius,vec[2]);
- glVertex3f(cur[0],cur[1]-radius,cur[2]);
- glEnd();
-}
-/* needs fixing if non-identity matrice used */
-static void drawcone(float *vec, float radius, float height, float tmat[][4])
-{
- float cur[3];
-
- VecCopyf(cur,vec);
- cur[2]+=height;
-
- drawcircball(GL_LINE_LOOP, cur, radius, tmat);
-
- glBegin(GL_LINES);
- glVertex3f(vec[0],vec[1],vec[2]);
- glVertex3f(cur[0]+radius,cur[1],cur[2]);
- glVertex3f(vec[0],vec[1],vec[2]);
- glVertex3f(cur[0]-radius,cur[1],cur[2]);
- glVertex3f(vec[0],vec[1],vec[2]);
- glVertex3f(cur[0],cur[1]+radius,cur[2]);
- glVertex3f(vec[0],vec[1],vec[2]);
- glVertex3f(cur[0],cur[1]-radius,cur[2]);
- glEnd();
-}
-/* return 1 if nothing was drawn */
-static int drawmball(Base *base, int dt)
-{
- Object *ob= base->object;
- MetaBall *mb;
- MetaElem *ml;
- float imat[4][4], tmat[4][4];
- int code= 1;
-
- mb= ob->data;
-
- if(ob==G.obedit) {
- BIF_ThemeColor(TH_WIRE);
- if((G.f & G_PICKSEL)==0 ) drawDispList(base, dt);
- ml= editelems.first;
- }
- else {
- if((base->flag & OB_FROMDUPLI)==0)
- drawDispList(base, dt);
- ml= mb->elems.first;
- }
-
- if(ml==NULL) return 1;
-
- /* in case solid draw, reset wire colors */
- if(ob!=G.obedit && (ob->flag & SELECT)) {
- if(ob==OBACT) BIF_ThemeColor(TH_ACTIVE);
- else BIF_ThemeColor(TH_SELECT);
- }
- else BIF_ThemeColor(TH_WIRE);
-
- mygetmatrix(tmat);
- Mat4Invert(imat, tmat);
- Normalize(imat[0]);
- Normalize(imat[1]);
-
- while(ml) {
-
- /* draw radius */
- if(ob==G.obedit) {
- if((ml->flag & SELECT) && (ml->flag & MB_SCALE_RAD)) cpack(0xA0A0F0);
- else cpack(0x3030A0);
-
- if(G.f & G_PICKSEL) {
- ml->selcol1= code;
- glLoadName(code++);
- }
- }
- drawcircball(GL_LINE_LOOP, &(ml->x), ml->rad, imat);
-
- /* draw stiffness */
- if(ob==G.obedit) {
- if((ml->flag & SELECT) && !(ml->flag & MB_SCALE_RAD)) cpack(0xA0F0A0);
- else cpack(0x30A030);
-
- if(G.f & G_PICKSEL) {
- ml->selcol2= code;
- glLoadName(code++);
- }
- drawcircball(GL_LINE_LOOP, &(ml->x), ml->rad*atan(ml->s)/M_PI_2, imat);
- }
-
- ml= ml->next;
- }
- return 0;
-}
-
-static void draw_forcefield(Object *ob)
-{
- PartDeflect *pd= ob->pd;
- float imat[4][4], tmat[4][4];
- float vec[3]= {0.0, 0.0, 0.0};
- int curcol;
- float size;
-
- if(ob!=G.obedit && (ob->flag & SELECT)) {
- if(ob==OBACT) curcol= TH_ACTIVE;
- else curcol= TH_SELECT;
- }
- else curcol= TH_WIRE;
-
- /* scale size of circle etc with the empty drawsize */
- if (ob->type == OB_EMPTY) size = ob->empty_drawsize;
- else size = 1.0;
-
- /* calculus here, is reused in PFIELD_FORCE */
- mygetmatrix(tmat);
- Mat4Invert(imat, tmat);
-// Normalize(imat[0]); // we don't do this because field doesnt scale either... apart from wind!
-// Normalize(imat[1]);
-
- if (pd->forcefield == PFIELD_WIND) {
- float force_val;
-
- Mat4One(tmat);
- BIF_ThemeColorBlend(curcol, TH_BACK, 0.5);
-
- if (has_ipo_code(ob->ipo, OB_PD_FSTR))
- force_val = IPO_GetFloatValue(ob->ipo, OB_PD_FSTR, G.scene->r.cfra);
- else
- force_val = pd->f_strength;
- force_val*= 0.1;
- drawcircball(GL_LINE_LOOP, vec, size, tmat);
- vec[2]= 0.5*force_val;
- drawcircball(GL_LINE_LOOP, vec, size, tmat);
- vec[2]= 1.0*force_val;
- drawcircball(GL_LINE_LOOP, vec, size, tmat);
- vec[2]= 1.5*force_val;
- drawcircball(GL_LINE_LOOP, vec, size, tmat);
-
- }
- else if (pd->forcefield == PFIELD_FORCE) {
- float ffall_val;
-
- if (has_ipo_code(ob->ipo, OB_PD_FFALL))
- ffall_val = IPO_GetFloatValue(ob->ipo, OB_PD_FFALL, G.scene->r.cfra);
- else
- ffall_val = pd->f_power;
-
- BIF_ThemeColorBlend(curcol, TH_BACK, 0.5);
- drawcircball(GL_LINE_LOOP, vec, size, imat);
- BIF_ThemeColorBlend(curcol, TH_BACK, 0.9 - 0.4 / pow(1.5, (double)ffall_val));
- drawcircball(GL_LINE_LOOP, vec, size*1.5, imat);
- BIF_ThemeColorBlend(curcol, TH_BACK, 0.9 - 0.4 / pow(2.0, (double)ffall_val));
- drawcircball(GL_LINE_LOOP, vec, size*2.0, imat);
- }
- else if (pd->forcefield == PFIELD_VORTEX) {
- float ffall_val, force_val;
-
- Mat4One(tmat);
- if (has_ipo_code(ob->ipo, OB_PD_FFALL))
- ffall_val = IPO_GetFloatValue(ob->ipo, OB_PD_FFALL, G.scene->r.cfra);
- else
- ffall_val = pd->f_power;
-
- if (has_ipo_code(ob->ipo, OB_PD_FSTR))
- force_val = IPO_GetFloatValue(ob->ipo, OB_PD_FSTR, G.scene->r.cfra);
- else
- force_val = pd->f_strength;
-
- BIF_ThemeColorBlend(curcol, TH_BACK, 0.7);
- if (force_val < 0) {
- drawspiral(vec, size*1.0, tmat, 1);
- drawspiral(vec, size*1.0, tmat, 16);
- }
- else {
- drawspiral(vec, size*1.0, tmat, -1);
- drawspiral(vec, size*1.0, tmat, -16);
- }
- }
- else if (pd->forcefield == PFIELD_GUIDE && ob->type==OB_CURVE) {
- Curve *cu= ob->data;
- if((cu->flag & CU_PATH) && cu->path && cu->path->data) {
- float mindist, guidevec1[4], guidevec2[3];
-
- if (has_ipo_code(ob->ipo, OB_PD_FSTR))
- mindist = IPO_GetFloatValue(ob->ipo, OB_PD_FSTR, G.scene->r.cfra);
- else
- mindist = pd->f_strength;
-
- /*path end*/
- setlinestyle(3);
- where_on_path(ob, 1.0f, guidevec1, guidevec2);
- BIF_ThemeColorBlend(curcol, TH_BACK, 0.5);
- drawcircball(GL_LINE_LOOP, guidevec1, mindist, imat);
-
- /*path beginning*/
- setlinestyle(0);
- where_on_path(ob, 0.0f, guidevec1, guidevec2);
- BIF_ThemeColorBlend(curcol, TH_BACK, 0.5);
- drawcircball(GL_LINE_LOOP, guidevec1, mindist, imat);
-
- VECCOPY(vec, guidevec1); /* max center */
- }
- }
-
- setlinestyle(3);
- BIF_ThemeColorBlend(curcol, TH_BACK, 0.5);
-
- if(pd->falloff==PFIELD_FALL_SPHERE){
- /* as last, guide curve alters it */
- if(pd->flag & PFIELD_USEMAX)
- drawcircball(GL_LINE_LOOP, vec, pd->maxdist, imat);
-
- if(pd->flag & PFIELD_USEMIN)
- drawcircball(GL_LINE_LOOP, vec, pd->mindist, imat);
- }
- else if(pd->falloff==PFIELD_FALL_TUBE){
- float radius,distance;
-
- Mat4One(tmat);
-
- vec[0]=vec[1]=0.0f;
- radius=(pd->flag&PFIELD_USEMAXR)?pd->maxrad:1.0f;
- distance=(pd->flag&PFIELD_USEMAX)?pd->maxdist:0.0f;
- vec[2]=distance;
- distance=(pd->flag&PFIELD_POSZ)?-distance:-2.0f*distance;
-
- if(pd->flag & (PFIELD_USEMAX|PFIELD_USEMAXR))
- drawtube(vec,radius,distance,tmat);
-
- radius=(pd->flag&PFIELD_USEMINR)?pd->minrad:1.0f;
- distance=(pd->flag&PFIELD_USEMIN)?pd->mindist:0.0f;
- vec[2]=distance;
- distance=(pd->flag&PFIELD_POSZ)?-distance:-2.0f*distance;
-
- if(pd->flag & (PFIELD_USEMIN|PFIELD_USEMINR))
- drawtube(vec,radius,distance,tmat);
- }
- else if(pd->falloff==PFIELD_FALL_CONE){
- float radius,distance;
-
- Mat4One(tmat);
-
- radius=(pd->flag&PFIELD_USEMAXR)?pd->maxrad:1.0f;
- radius*=(float)M_PI/180.0f;
- distance=(pd->flag&PFIELD_USEMAX)?pd->maxdist:0.0f;
-
- if(pd->flag & (PFIELD_USEMAX|PFIELD_USEMAXR)){
- drawcone(vec,distance*sin(radius),distance*cos(radius),tmat);
- if((pd->flag & PFIELD_POSZ)==0)
- drawcone(vec,distance*sin(radius),-distance*cos(radius),tmat);
- }
-
- radius=(pd->flag&PFIELD_USEMINR)?pd->minrad:1.0f;
- radius*=(float)M_PI/180.0f;
- distance=(pd->flag&PFIELD_USEMIN)?pd->mindist:0.0f;
-
- if(pd->flag & (PFIELD_USEMIN|PFIELD_USEMINR)){
- drawcone(vec,distance*sin(radius),distance*cos(radius),tmat);
- if((pd->flag & PFIELD_POSZ)==0)
- drawcone(vec,distance*sin(radius),-distance*cos(radius),tmat);
- }
- }
- setlinestyle(0);
-}
-
-static void draw_box(float vec[8][3])
-{
- glBegin(GL_LINE_STRIP);
- glVertex3fv(vec[0]); glVertex3fv(vec[1]);glVertex3fv(vec[2]); glVertex3fv(vec[3]);
- glVertex3fv(vec[0]); glVertex3fv(vec[4]);glVertex3fv(vec[5]); glVertex3fv(vec[6]);
- glVertex3fv(vec[7]); glVertex3fv(vec[4]);
- glEnd();
-
- glBegin(GL_LINES);
- glVertex3fv(vec[1]); glVertex3fv(vec[5]);
- glVertex3fv(vec[2]); glVertex3fv(vec[6]);
- glVertex3fv(vec[3]); glVertex3fv(vec[7]);
- glEnd();
-}
-
-/* uses boundbox, function used by Ketsji */
-void get_local_bounds(Object *ob, float *center, float *size)
-{
- BoundBox *bb= object_get_boundbox(ob);
-
- if(bb==NULL) {
- center[0]= center[1]= center[2]= 0.0;
- VECCOPY(size, ob->size);
- }
- else {
- size[0]= 0.5*fabs(bb->vec[0][0] - bb->vec[4][0]);
- size[1]= 0.5*fabs(bb->vec[0][1] - bb->vec[2][1]);
- size[2]= 0.5*fabs(bb->vec[0][2] - bb->vec[1][2]);
-
- center[0]= (bb->vec[0][0] + bb->vec[4][0])/2.0;
- center[1]= (bb->vec[0][1] + bb->vec[2][1])/2.0;
- center[2]= (bb->vec[0][2] + bb->vec[1][2])/2.0;
- }
-}
-
-
-
-static void draw_bb_quadric(BoundBox *bb, short type)
-{
- float size[3], cent[3];
- GLUquadricObj *qobj = gluNewQuadric();
-
- gluQuadricDrawStyle(qobj, GLU_SILHOUETTE);
-
- size[0]= 0.5*fabs(bb->vec[0][0] - bb->vec[4][0]);
- size[1]= 0.5*fabs(bb->vec[0][1] - bb->vec[2][1]);
- size[2]= 0.5*fabs(bb->vec[0][2] - bb->vec[1][2]);
-
- cent[0]= (bb->vec[0][0] + bb->vec[4][0])/2.0;
- cent[1]= (bb->vec[0][1] + bb->vec[2][1])/2.0;
- cent[2]= (bb->vec[0][2] + bb->vec[1][2])/2.0;
-
- glPushMatrix();
- if(type==OB_BOUND_SPHERE) {
- glTranslatef(cent[0], cent[1], cent[2]);
- glScalef(size[0], size[1], size[2]);
- gluSphere(qobj, 1.0, 8, 5);
- }
- else if(type==OB_BOUND_CYLINDER) {
- float radius = size[0] > size[1] ? size[0] : size[1];
- glTranslatef(cent[0], cent[1], cent[2]-size[2]);
- glScalef(radius, radius, 2.0*size[2]);
- gluCylinder(qobj, 1.0, 1.0, 1.0, 8, 1);
- }
- else if(type==OB_BOUND_CONE) {
- float radius = size[0] > size[1] ? size[0] : size[1];
- glTranslatef(cent[0], cent[2]-size[2], cent[1]);
- glScalef(radius, 2.0*size[2], radius);
- glRotatef(-90., 1.0, 0.0, 0.0);
- gluCylinder(qobj, 1.0, 0.0, 1.0, 8, 1);
- }
- glPopMatrix();
-
- gluDeleteQuadric(qobj);
-}
-
-static void draw_bounding_volume(Object *ob)
-{
- BoundBox *bb=0;
-
- if(ob->type==OB_MESH) {
- bb= mesh_get_bb(ob);
- }
- else if ELEM3(ob->type, OB_CURVE, OB_SURF, OB_FONT) {
- bb= ( (Curve *)ob->data )->bb;
- }
- else if(ob->type==OB_MBALL) {
- bb= ob->bb;
- if(bb==0) {
- makeDispListMBall(ob);
- bb= ob->bb;
- }
- }
- else {
- drawcube();
- return;
- }
-
- if(bb==0) return;
-
- if(ob->boundtype==OB_BOUND_BOX) draw_box(bb->vec);
- else draw_bb_quadric(bb, ob->boundtype);
-
-}
-
-static void drawtexspace(Object *ob)
-{
- float vec[8][3], loc[3], size[3];
-
- if(ob->type==OB_MESH) {
- mesh_get_texspace(ob->data, loc, NULL, size);
- }
- else if ELEM3(ob->type, OB_CURVE, OB_SURF, OB_FONT) {
- Curve *cu= ob->data;
- VECCOPY(size, cu->size);
- VECCOPY(loc, cu->loc);
- }
- else if(ob->type==OB_MBALL) {
- MetaBall *mb= ob->data;
- VECCOPY(size, mb->size);
- VECCOPY(loc, mb->loc);
- }
- else return;
-
- vec[0][0]=vec[1][0]=vec[2][0]=vec[3][0]= loc[0]-size[0];
- vec[4][0]=vec[5][0]=vec[6][0]=vec[7][0]= loc[0]+size[0];
-
- vec[0][1]=vec[1][1]=vec[4][1]=vec[5][1]= loc[1]-size[1];
- vec[2][1]=vec[3][1]=vec[6][1]=vec[7][1]= loc[1]+size[1];
-
- vec[0][2]=vec[3][2]=vec[4][2]=vec[7][2]= loc[2]-size[2];
- vec[1][2]=vec[2][2]=vec[5][2]=vec[6][2]= loc[2]+size[2];
-
- setlinestyle(2);
-
- draw_box(vec);
-
- setlinestyle(0);
-}
-
-/* draws wire outline */
-static void drawSolidSelect(Base *base)
-{
- Object *ob= base->object;
-
- glLineWidth(2.0);
- glDepthMask(0);
-
- if(ELEM3(ob->type, OB_FONT,OB_CURVE, OB_SURF)) {
- Curve *cu = ob->data;
- if (displist_has_faces(&cu->disp) && boundbox_clip(ob->obmat, cu->bb)) {
- draw_index_wire= 0;
- drawDispListwire(&cu->disp);
- draw_index_wire= 1;
- }
- } else if (ob->type==OB_MBALL) {
- if((base->flag & OB_FROMDUPLI)==0)
- drawDispListwire(&ob->disp);
- }
- else if(ob->type==OB_ARMATURE) {
- if(!(ob->flag & OB_POSEMODE)) {
- draw_armature(base, OB_WIRE);
- }
- }
-
- glLineWidth(1.0);
- glDepthMask(1);
-}
-
-static void drawWireExtra(Object *ob)
-{
- if(ob!=G.obedit && (ob->flag & SELECT)) {
- if(ob==OBACT) {
- if(ob->flag & OB_FROMGROUP) BIF_ThemeColor(TH_GROUP_ACTIVE);
- else BIF_ThemeColor(TH_ACTIVE);
- }
- else if(ob->flag & OB_FROMGROUP)
- BIF_ThemeColorShade(TH_GROUP_ACTIVE, -16);
- else
- BIF_ThemeColor(TH_SELECT);
- }
- else {
- if(ob->flag & OB_FROMGROUP)
- BIF_ThemeColor(TH_GROUP);
- else {
- if(ob->dtx & OB_DRAWWIRE) {
- glColor3ub(80,80,80);
- } else {
- BIF_ThemeColor(TH_WIRE);
- }
- }
- }
-
- bglPolygonOffset(1.0);
- glDepthMask(0); // disable write in zbuffer, selected edge wires show better
-
- if (ELEM3(ob->type, OB_FONT, OB_CURVE, OB_SURF)) {
- Curve *cu = ob->data;
- if (boundbox_clip(ob->obmat, cu->bb)) {
- if (ob->type==OB_CURVE)
- draw_index_wire= 0;
- drawDispListwire(&cu->disp);
- if (ob->type==OB_CURVE)
- draw_index_wire= 1;
- }
- } else if (ob->type==OB_MBALL) {
- drawDispListwire(&ob->disp);
- }
-
- glDepthMask(1);
- bglPolygonOffset(0.0);
-}
-
-/* should be called in view space */
-static void draw_hooks(Object *ob)
-{
- ModifierData *md;
- float vec[3];
-
- for (md=ob->modifiers.first; md; md=md->next) {
- if (md->type==eModifierType_Hook) {
- HookModifierData *hmd = (HookModifierData*) md;
-
- VecMat4MulVecfl(vec, ob->obmat, hmd->cent);
-
- if(hmd->object) {
- setlinestyle(3);
- glBegin(GL_LINES);
- glVertex3fv(hmd->object->obmat[3]);
- glVertex3fv(vec);
- glEnd();
- setlinestyle(0);
- }
-
- glPointSize(3.0);
- bglBegin(GL_POINTS);
- bglVertex3fv(vec);
- bglEnd();
- glPointSize(1.0);
- }
- }
-}
-
-
-//<rcruiz>
-void drawRBpivot(bRigidBodyJointConstraint *data){
- float radsPerDeg = 6.283185307179586232f / 360.f;
- int axis;
- float v1[3]= {data->pivX, data->pivY, data->pivZ};
- float eu[3]= {radsPerDeg*data->axX, radsPerDeg*data->axY, radsPerDeg*data->axZ};
-
-
-
- float mat[4][4];
- EulToMat4(eu,mat);
- glLineWidth (4.0f);
- setlinestyle(2);
- for (axis=0; axis<3; axis++) {
- float dir[3] = {0,0,0};
- float v[3]= {data->pivX, data->pivY, data->pivZ};
-
- dir[axis] = 1.f;
- glBegin(GL_LINES);
- Mat4MulVecfl(mat,dir);
- v[0] += dir[0];
- v[1] += dir[1];
- v[2] += dir[2];
- glVertex3fv(v1);
- glVertex3fv(v);
- glEnd();
- glRasterPos3fv(v);
- if (axis==0)
- BMF_DrawString(G.font, "px");
- else if (axis==1)
- BMF_DrawString(G.font, "py");
- else
- BMF_DrawString(G.font, "pz");
- }
- glLineWidth (1.0f);
- setlinestyle(0);
-}
-
-/* flag can be DRAW_PICKING and/or DRAW_CONSTCOLOR */
-void draw_object(Base *base, int flag)
-{
- static int warning_recursive= 0;
- Object *ob;
- Curve *cu;
- float cfraont;
- float vec1[3], vec2[3];
- unsigned int col=0;
- int sel, drawtype, colindex= 0, ipoflag;
- int i, selstart, selend, empty_object=0;
- short dt, dtx, zbufoff= 0;
-
- /* only once set now, will be removed too, should become a global standard */
- glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-
- ob= base->object;
-
- if (ob!=G.obedit) {
- if (ob->restrictflag & OB_RESTRICT_VIEW)
- return;
- }
-
- /* xray delay? */
- if((flag & DRAW_PICKING)==0 && (base->flag & OB_FROMDUPLI)==0) {
- /* don't do xray in particle mode, need the z-buffer */
- if(!(G.f & G_PARTICLEEDIT)) {
- /* xray and transp are set when it is drawing the 2nd/3rd pass */
- if(!G.vd->xray && !G.vd->transp && (ob->dtx & OB_DRAWXRAY)) {
- add_view3d_after(G.vd, base, V3D_XRAY);
- return;
- }
- }
- }
-
- /* draw keys? */
- if(base==(G.scene->basact) || (base->flag & (SELECT+BA_WAS_SEL))) {
- if(flag==0 && warning_recursive==0 && ob!=G.obedit) {
- if(ob->ipo && ob->ipo->showkey && (ob->ipoflag & OB_DRAWKEY)) {
- ListBase elems;
- CfraElem *ce;
- float temp[7][3];
-
- warning_recursive= 1;
-
- elems.first= elems.last= 0;
- make_cfra_list(ob->ipo, &elems);
-
- cfraont= (G.scene->r.cfra);
- drawtype= G.vd->drawtype;
- if(drawtype>OB_WIRE) G.vd->drawtype= OB_WIRE;
- sel= base->flag;
- memcpy(temp, &ob->loc, 7*3*sizeof(float));
-
- ipoflag= ob->ipoflag;
- ob->ipoflag &= ~OB_OFFS_OB;
-
- set_no_parent_ipo(1);
- disable_speed_curve(1);
-
- if ((ob->ipoflag & OB_DRAWKEYSEL)==0) {
- ce= elems.first;
- while(ce) {
- if(!ce->sel) {
- (G.scene->r.cfra)= ce->cfra/G.scene->r.framelen;
-
- base->flag= 0;
-
- where_is_object_time(ob, (G.scene->r.cfra));
- draw_object(base, 0);
- }
- ce= ce->next;
- }
- }
-
- ce= elems.first;
- while(ce) {
- if(ce->sel) {
- (G.scene->r.cfra)= ce->cfra/G.scene->r.framelen;
-
- base->flag= SELECT;
-
- where_is_object_time(ob, (G.scene->r.cfra));
- draw_object(base, 0);
- }
- ce= ce->next;
- }
-
- set_no_parent_ipo(0);
- disable_speed_curve(0);
-
- base->flag= sel;
- ob->ipoflag= ipoflag;
-
- /* restore icu->curval */
- (G.scene->r.cfra)= cfraont;
-
- memcpy(&ob->loc, temp, 7*3*sizeof(float));
- where_is_object(ob);
- G.vd->drawtype= drawtype;
-
- BLI_freelistN(&elems);
-
- warning_recursive= 0;
- }
- }
- }
-
- /* patch? children objects with a timeoffs change the parents. How to solve! */
- /* if( ((int)ob->ctime) != F_(G.scene->r.cfra)) where_is_object(ob); */
-
- mymultmatrix(ob->obmat);
-
- /* which wire color */
- if((flag & DRAW_CONSTCOLOR) == 0) {
- project_short(ob->obmat[3], &base->sx);
-
- if((G.moving & G_TRANSFORM_OBJ) && (base->flag & (SELECT+BA_WAS_SEL))) BIF_ThemeColor(TH_TRANSFORM);
- else {
-
- if(ob->type==OB_LAMP) BIF_ThemeColor(TH_LAMP);
- else BIF_ThemeColor(TH_WIRE);
-
- if((G.scene->basact)==base) {
- if(base->flag & (SELECT+BA_WAS_SEL)) BIF_ThemeColor(TH_ACTIVE);
- }
- else {
- if(base->flag & (SELECT+BA_WAS_SEL)) BIF_ThemeColor(TH_SELECT);
- }
-
- // no theme yet
- if(ob->id.lib) {
- if(base->flag & (SELECT+BA_WAS_SEL)) colindex = 4;
- else colindex = 3;
- }
- else if(warning_recursive==1) {
- if(base->flag & (SELECT+BA_WAS_SEL)) {
- if(G.scene->basact==base) colindex = 8;
- else colindex= 7;
- }
- else colindex = 6;
- }
- else if(ob->flag & OB_FROMGROUP) {
- if(base->flag & (SELECT+BA_WAS_SEL)) {
- if(G.scene->basact==base) BIF_ThemeColor(TH_GROUP_ACTIVE);
- else BIF_ThemeColorShade(TH_GROUP_ACTIVE, -16);
- }
- else BIF_ThemeColor(TH_GROUP);
- colindex= 0;
- }
-
- }
-
- if(colindex) {
- col= colortab[colindex];
- cpack(col);
- }
- }
-
- /* maximum drawtype */
- dt= MIN2(G.vd->drawtype, ob->dt);
- if(G.vd->zbuf==0 && dt>OB_WIRE) dt= OB_WIRE;
- dtx= 0;
-
- /* faceselect exception: also draw solid when dt==wire, except in editmode */
- if(ob==OBACT && (G.f & (G_VERTEXPAINT+G_TEXTUREPAINT+G_WEIGHTPAINT))) {
- if(ob->type==OB_MESH) {
-
- if(ob==G.obedit);
- else {
- dt= OB_SHADED;
-
- glClearDepth(1.0); glClear(GL_DEPTH_BUFFER_BIT);
- glEnable(GL_DEPTH_TEST);
- if(dt<OB_SOLID) zbufoff= 1;
- }
- }
- else {
- if(dt<OB_SOLID) {
- dt= OB_SOLID;
- glClearDepth(1.); glClear(GL_DEPTH_BUFFER_BIT);
- glEnable(GL_DEPTH_TEST);
- zbufoff= 1;
- }
- }
- }
-
- /* draw-extra supported for boundbox drawmode too */
- if(dt>=OB_BOUNDBOX ) {
-
- dtx= ob->dtx;
- if(G.obedit==ob) {
- // the only 2 extra drawtypes alowed in editmode
- dtx= dtx & (OB_DRAWWIRE|OB_TEXSPACE);
- }
-
- if(G.f & G_DRAW_EXT) {
- if(ob->type==OB_EMPTY || ob->type==OB_CAMERA || ob->type==OB_LAMP) dt= OB_WIRE;
- }
- }
-
- /* draw outline for selected solid objects, mesh does itself */
- if((G.vd->flag & V3D_SELECT_OUTLINE) && ob->type!=OB_MESH) {
- if(dt>OB_WIRE && dt<OB_TEXTURE && ob!=G.obedit) {
- if (!(ob->dtx&OB_DRAWWIRE) && (ob->flag&SELECT) && !(flag&DRAW_PICKING)) {
- drawSolidSelect(base);
- }
- }
- }
-
- switch( ob->type) {
- case OB_MESH:
- if (!(base->flag&OB_RADIO)) {
- empty_object= draw_mesh_object(base, dt, flag);
- if(flag!=DRAW_CONSTCOLOR) dtx &= ~OB_DRAWWIRE; // mesh draws wire itself
-
- if(G.obedit!=ob && warning_recursive==0) {
- PartEff *paf = give_parteff(ob);
-
- if(paf) {
- if(col || (ob->flag & SELECT)) cpack(0xFFFFFF); /* for visibility, also while wpaint */
- if(paf->flag & PAF_STATIC) draw_static_particle_system(ob, paf, dt);
- else if((flag & DRAW_PICKING) == 0) draw_particle_system(base, paf); // selection errors happen to easy
- if(col) cpack(col);
- }
- }
- }
-
- break;
- case OB_FONT:
- cu= ob->data;
- if (cu->disp.first==NULL) makeDispListCurveTypes(ob, 0);
- if(ob==G.obedit) {
- tekentextcurs();
-
- if (cu->flag & CU_FAST) {
- cpack(0xFFFFFF);
- set_inverted_drawing(1);
- drawDispList(base, OB_WIRE);
- set_inverted_drawing(0);
- } else {
- drawDispList(base, dt);
- }
-
- if (cu->linewidth != 0.0) {
- cpack(0xff44ff);
- BIF_ThemeColor(TH_WIRE);
- VECCOPY(vec1, ob->orig);
- VECCOPY(vec2, ob->orig);
- vec1[0] += cu->linewidth;
- vec2[0] += cu->linewidth;
- vec1[1] += cu->linedist * cu->fsize;
- vec2[1] -= cu->lines * cu->linedist * cu->fsize;
- setlinestyle(3);
- glBegin(GL_LINE_STRIP);
- glVertex2fv(vec1);
- glVertex2fv(vec2);
- glEnd();
- setlinestyle(0);
- }
-
- setlinestyle(3);
- for (i=0; i<cu->totbox; i++) {
- if (cu->tb[i].w != 0.0) {
- if (i == (cu->actbox-1))
- BIF_ThemeColor(TH_ACTIVE);
- else
- BIF_ThemeColor(TH_WIRE);
- vec1[0] = cu->tb[i].x;
- vec1[1] = cu->tb[i].y + cu->fsize;
- vec1[2] = 0.001;
- glBegin(GL_LINE_STRIP);
- glVertex3fv(vec1);
- vec1[0] += cu->tb[i].w;
- glVertex3fv(vec1);
- vec1[1] -= cu->tb[i].h;
- glVertex3fv(vec1);
- vec1[0] -= cu->tb[i].w;
- glVertex3fv(vec1);
- vec1[1] += cu->tb[i].h;
- glVertex3fv(vec1);
- glEnd();
- }
- }
- setlinestyle(0);
-
-
- if (getselection(&selstart, &selend) && selboxes) {
- float selboxw;
-
- cpack(0xffffff);
- set_inverted_drawing(1);
- for (i=0; i<(selend-selstart+1); i++) {
- SelBox *sb = &(selboxes[i]);
-
- if (i<(selend-selstart)) {
- if (selboxes[i+1].y == sb->y)
- selboxw= selboxes[i+1].x - sb->x;
- else
- selboxw= sb->w;
- }
- else {
- selboxw= sb->w;
- }
- glBegin(GL_QUADS);
- glVertex3f(sb->x, sb->y, 0.001);
- glVertex3f(sb->x+selboxw, sb->y, 0.001);
- glVertex3f(sb->x+selboxw, sb->y+sb->h, 0.001);
- glVertex3f(sb->x, sb->y+sb->h, 0.001);
- glEnd();
- }
- set_inverted_drawing(0);
- }
- }
- else if(dt==OB_BOUNDBOX)
- draw_bounding_volume(ob);
- else if(boundbox_clip(ob->obmat, cu->bb))
- empty_object= drawDispList(base, dt);
-
- break;
- case OB_CURVE:
- case OB_SURF:
- cu= ob->data;
- /* still needed for curves hidden in other layers. depgraph doesnt handle that yet */
- if (cu->disp.first==NULL) makeDispListCurveTypes(ob, 0);
-
- if(ob==G.obedit) {
- drawnurb(base, editNurb.first, dt);
- }
- else if(dt==OB_BOUNDBOX)
- draw_bounding_volume(ob);
- else if(boundbox_clip(ob->obmat, cu->bb)) {
- empty_object= drawDispList(base, dt);
-
- if(cu->path)
- curve_draw_speed(ob);
- }
- break;
- case OB_MBALL:
- if(ob==G.obedit)
- drawmball(base, dt);
- else if(dt==OB_BOUNDBOX)
- draw_bounding_volume(ob);
- else
- empty_object= drawmball(base, dt);
- break;
- case OB_EMPTY:
- drawaxes(ob->empty_drawsize, flag, ob->empty_drawtype);
- break;
- case OB_LAMP:
- drawlamp(ob);
- if(dtx || (base->flag & SELECT)) mymultmatrix(ob->obmat);
- break;
- case OB_CAMERA:
- drawcamera(ob, flag);
- break;
- case OB_LATTICE:
- drawlattice(ob);
- break;
- case OB_ARMATURE:
- if(dt>OB_WIRE) set_gl_material(0); // we use defmaterial
- empty_object= draw_armature(base, dt);
- break;
- default:
- drawaxes(1.0, flag, OB_ARROWS);
- }
- if(ob->pd && ob->pd->forcefield) draw_forcefield(ob);
-
- /* code for new particle system */
- if(warning_recursive==0 && (flag & DRAW_PICKING)==0 && ob!=G.obedit){
- glDepthMask(GL_FALSE);
- if(col || (ob->flag & SELECT)) cpack(0xFFFFFF); /* for visibility, also while wpaint */
- if(ob->particlesystem.first) {
- ParticleSystem *psys;
-
- for(psys=ob->particlesystem.first; psys; psys=psys->next)
- draw_new_particle_system(base, psys);
-
- if(G.f & G_PARTICLEEDIT && ob==OBACT) {
- psys= PE_get_current(ob);
- if(psys && !G.obedit && psys_in_edit_mode(psys))
- draw_particle_edit(ob, psys);
- }
- }
- if(col) cpack(col);
- glDepthMask(GL_TRUE);
- }
-
- {
- bConstraint *con;
- for(con=ob->constraints.first; con; con= con->next)
- {
- if(con->type==CONSTRAINT_TYPE_RIGIDBODYJOINT)
- {
- bRigidBodyJointConstraint *data = (bRigidBodyJointConstraint*)con->data;
- if(data->flag&CONSTRAINT_DRAW_PIVOT)
- drawRBpivot(data);
- }
- }
- }
-
- /* draw extra: after normal draw because of makeDispList */
- if(dtx) {
- if(G.f & G_SIMULATION);
- else if(dtx & OB_AXIS) {
- drawaxes(1.0f, flag, OB_ARROWS);
- }
- if(dtx & OB_BOUNDBOX) draw_bounding_volume(ob);
- if(dtx & OB_TEXSPACE) drawtexspace(ob);
- if(dtx & OB_DRAWNAME) {
- /* patch for several 3d cards (IBM mostly) that crash on glSelect with text drawing */
- /* but, we also dont draw names for sets or duplicators */
- if(flag == 0) {
- glRasterPos3f(0.0, 0.0, 0.0);
-
- BMF_DrawString(G.font, " ");
- BMF_DrawString(G.font, ob->id.name+2);
- }
- }
- /*if(dtx & OB_DRAWIMAGE) drawDispListwire(&ob->disp);*/
- if((dtx & OB_DRAWWIRE) && dt>=OB_SOLID) drawWireExtra(ob);
- }
-
- if(dt<OB_SHADED) {
- if((ob->gameflag & OB_ACTOR) && (ob->gameflag & OB_DYNAMIC)) {
- float tmat[4][4], imat[4][4], vec[3];
-
- vec[0]= vec[1]= vec[2]= 0.0;
- mygetmatrix(tmat);
- Mat4Invert(imat, tmat);
-
- setlinestyle(2);
- drawcircball(GL_LINE_LOOP, vec, ob->inertia, imat);
- setlinestyle(0);
- }
- }
-
- myloadmatrix(G.vd->viewmat);
-
- if(zbufoff) glDisable(GL_DEPTH_TEST);
-
- if(warning_recursive) return;
- if(base->flag & (OB_FROMDUPLI|OB_RADIO)) return;
- if(G.f & G_SIMULATION) return;
-
- /* object centers, need to be drawn in viewmat space for speed, but OK for picking select */
- if(ob!=OBACT || (G.f & (G_VERTEXPAINT|G_TEXTUREPAINT|G_WEIGHTPAINT))==0) {
- int do_draw_center= -1; /* defines below are zero or positive... */
-
- if((G.scene->basact)==base)
- do_draw_center= ACTIVE;
- else if(base->flag & SELECT)
- do_draw_center= SELECT;
- else if(empty_object || (G.vd->flag & V3D_DRAW_CENTERS))
- do_draw_center= DESELECT;
-
- if(do_draw_center != -1) {
- if(flag & DRAW_PICKING) {
- /* draw a single point for opengl selection */
- glBegin(GL_POINTS);
- glVertex3fv(ob->obmat[3]);
- glEnd();
- }
- else if((flag & DRAW_CONSTCOLOR)==0) {
- /* we don't draw centers for duplicators and sets */
-#ifdef WITH_VERSE
- if(ob->vnode)
- drawcentercircle(ob->obmat[3], VERSE, 1);
- else
-#endif
- drawcentercircle(ob->obmat[3], do_draw_center, ob->id.lib || ob->id.us>1);
- }
- }
- }
-
- /* not for sets, duplicators or picking */
- if(flag==0 && (!(G.vd->flag & V3D_HIDE_HELPLINES))) {
- ListBase *list;
-
- /* draw hook center and offset line */
- if(ob!=G.obedit) draw_hooks(ob);
-
- /* help lines and so */
- if(ob!=G.obedit && ob->parent && (ob->parent->lay & G.vd->lay)) {
- setlinestyle(3);
- glBegin(GL_LINES);
- glVertex3fv(ob->obmat[3]);
- glVertex3fv(ob->orig);
- glEnd();
- setlinestyle(0);
- }
-
- /* Drawing the constraint lines */
- list = &ob->constraints;
- if (list) {
- bConstraint *curcon;
- bConstraintOb *cob;
- char col[4], col2[4];
-
- BIF_GetThemeColor3ubv(TH_GRID, col);
- make_axis_color(col, col2, 'z');
- glColor3ubv((GLubyte *)col2);
-
- cob= constraints_make_evalob(ob, NULL, CONSTRAINT_OBTYPE_OBJECT);
-
- for (curcon = list->first; curcon; curcon=curcon->next) {
- bConstraintTypeInfo *cti= constraint_get_typeinfo(curcon);
- ListBase targets = {NULL, NULL};
- bConstraintTarget *ct;
-
- if ((curcon->flag & CONSTRAINT_EXPAND) && (cti) && (cti->get_constraint_targets)) {
- cti->get_constraint_targets(curcon, &targets);
-
- for (ct= targets.first; ct; ct= ct->next) {
- /* calculate target's matrix */
- if (cti->get_target_matrix)
- cti->get_target_matrix(curcon, cob, ct, bsystem_time(ob, (float)(G.scene->r.cfra), ob->sf));
- else
- Mat4One(ct->matrix);
-
- setlinestyle(3);
- glBegin(GL_LINES);
- glVertex3fv(ct->matrix[3]);
- glVertex3fv(ob->obmat[3]);
- glEnd();
- setlinestyle(0);
- }
-
- if (cti->flush_constraint_targets)
- cti->flush_constraint_targets(curcon, &targets, 1);
- }
- }
-
- constraints_clear_evalob(cob);
- }
- }
-
- free_old_images();
-}
-
-void draw_object_ext(Base *base)
-{
-
- if(G.vd==NULL || base==NULL) return;
-
- if(G.vd->drawtype > OB_WIRE) {
- G.vd->zbuf= 1;
- glEnable(GL_DEPTH_TEST);
- }
-
- G.f |= G_DRAW_EXT;
-
- glDrawBuffer(GL_FRONT);
- persp(PERSP_VIEW);
-
- if(G.vd->flag & V3D_CLIPPING)
- view3d_set_clipping(G.vd);
-
- draw_object(base, 0);
-
- if(G.vd->flag & V3D_CLIPPING)
- view3d_clr_clipping();
-
- G.f &= ~G_DRAW_EXT;
-
- bglFlush(); /* reveil frontbuffer drawing */
- glDrawBuffer(GL_BACK);
-
- if(G.vd->zbuf) {
- G.vd->zbuf= 0;
- glDisable(GL_DEPTH_TEST);
- }
- curarea->win_swap= WIN_FRONT_OK;
-}
-
-/* ***************** BACKBUF SEL (BBS) ********* */
-
-static void bbs_mesh_verts__mapFunc(void *userData, int index, float *co, float *no_f, short *no_s)
-{
- int offset = (long) userData;
- EditVert *eve = EM_get_vert_for_index(index);
-
- if (eve->h==0) {
- set_framebuffer_index_color(offset+index);
- bglVertex3fv(co);
- }
-}
-static int bbs_mesh_verts(DerivedMesh *dm, int offset)
-{
- glPointSize( BIF_GetThemeValuef(TH_VERTEX_SIZE) );
- bglBegin(GL_POINTS);
- dm->foreachMappedVert(dm, bbs_mesh_verts__mapFunc, (void*)(long) offset);
- bglEnd();
- glPointSize(1.0);
-
- return offset + G.totvert;
-}
-
-static int bbs_mesh_wire__setDrawOptions(void *userData, int index)
-{
- int offset = (long) userData;
- EditEdge *eed = EM_get_edge_for_index(index);
-
- if (eed->h==0) {
- set_framebuffer_index_color(offset+index);
- return 1;
- } else {
- return 0;
- }
-}
-static int bbs_mesh_wire(DerivedMesh *dm, int offset)
-{
- dm->drawMappedEdges(dm, bbs_mesh_wire__setDrawOptions, (void*)(long) offset);
-
- return offset + G.totedge;
-}
-
-static int bbs_mesh_solid__setSolidDrawOptions(void *userData, int index, int *drawSmooth_r)
-{
- if (EM_get_face_for_index(index)->h==0) {
- if (userData) {
- set_framebuffer_index_color(index+1);
- }
- return 1;
- } else {
- return 0;
- }
-}
-
-static void bbs_mesh_solid__drawCenter(void *userData, int index, float *cent, float *no)
-{
- EditFace *efa = EM_get_face_for_index(index);
-
- if (efa->h==0 && efa->fgonf!=EM_FGON) {
- set_framebuffer_index_color(index+1);
-
- bglVertex3fv(cent);
- }
-}
-
-/* two options, facecolors or black */
-static int bbs_mesh_solid_EM(DerivedMesh *dm, int facecol)
-{
- cpack(0);
-
- if (facecol) {
- dm->drawMappedFaces(dm, bbs_mesh_solid__setSolidDrawOptions, (void*)(long) 1, 0);
-
- if( CHECK_OB_DRAWFACEDOT(G.scene, G.vd, G.obedit->dt) ) {
- glPointSize(BIF_GetThemeValuef(TH_FACEDOT_SIZE));
-
- bglBegin(GL_POINTS);
- dm->foreachMappedFaceCenter(dm, bbs_mesh_solid__drawCenter, NULL);
- bglEnd();
- }
-
- return 1+G.totface;
- } else {
- dm->drawMappedFaces(dm, bbs_mesh_solid__setSolidDrawOptions, (void*) 0, 0);
- return 1;
- }
-}
-
-static int bbs_mesh_solid__setDrawOpts(void *userData, int index, int *drawSmooth_r)
-{
- Mesh *me = userData;
-
- if (!(me->mface[index].flag&ME_HIDE)) {
- set_framebuffer_index_color(index+1);
- return 1;
- } else {
- return 0;
- }
-}
-
-static int bbs_mesh_wire__setDrawOpts(void *userData, int index)
-{
- struct { Mesh *me; EdgeHash *eh; int offset; } *data = userData;
- MEdge *med = data->me->medge + index;
- unsigned long flags = (long)BLI_edgehash_lookup(data->eh, med->v1, med->v2);
-
- if (flags & 1) {
- set_framebuffer_index_color(data->offset+index);
- return 1;
- } else
- return 0;
-}
-
-/* TODO remove this - since face select mode now only works with painting */
-static void bbs_mesh_solid(Object *ob)
-{
- DerivedMesh *dm = mesh_get_derived_final(ob, get_viewedit_datamask());
- Mesh *me = (Mesh*)ob->data;
-
- glColor3ub(0, 0, 0);
- dm->drawMappedFaces(dm, bbs_mesh_solid__setDrawOpts, me, 0);
-
- /* draw edges for seam marking in faceselect mode, but not when painting,
- so that painting doesn't get interrupted on an edge */
- if ((G.f & G_FACESELECT) && !(G.f & (G_VERTEXPAINT|G_TEXTUREPAINT|G_WEIGHTPAINT))) {
- struct { Mesh *me; EdgeHash *eh; int offset; } userData;
-
- userData.me = me;
- userData.eh = get_tface_mesh_marked_edge_info(me);
- userData.offset = userData.me->totface+1;
-
- bglPolygonOffset(1.0);
- dm->drawMappedEdges(dm, bbs_mesh_wire__setDrawOpts, (void*)&userData);
- bglPolygonOffset(0.0);
-
- BLI_edgehash_free(userData.eh, NULL);
- }
-
- dm->release(dm);
-}
-
-void draw_object_backbufsel(Object *ob)
-{
-
- mymultmatrix(ob->obmat);
-
- glClearDepth(1.0); glClear(GL_DEPTH_BUFFER_BIT);
- glEnable(GL_DEPTH_TEST);
-
- switch( ob->type) {
- case OB_MESH:
- if(ob==G.obedit) {
- DerivedMesh *dm = editmesh_get_derived_cage(CD_MASK_BAREMESH);
-
- EM_init_index_arrays(1, 1, 1);
-
- em_solidoffs= bbs_mesh_solid_EM(dm, G.scene->selectmode & SCE_SELECT_FACE);
-
- bglPolygonOffset(1.0);
-
- // we draw edges always, for loop (select) tools
- em_wireoffs= bbs_mesh_wire(dm, em_solidoffs);
-
- // we draw verts if vert select mode or if in transform (for snap).
- if(G.scene->selectmode & SCE_SELECT_VERTEX || G.moving & G_TRANSFORM_EDIT)
- em_vertoffs= bbs_mesh_verts(dm, em_wireoffs);
- else em_vertoffs= em_wireoffs;
-
- bglPolygonOffset(0.0);
-
- dm->release(dm);
-
- EM_free_index_arrays();
- }
- else bbs_mesh_solid(ob);
-
- break;
- case OB_CURVE:
- case OB_SURF:
- break;
- }
-
- myloadmatrix(G.vd->viewmat);
-}
-
-
-/* ************* draw object instances for bones, for example ****************** */
-/* assumes all matrices/etc set OK */
-
-/* helper function for drawing object instances - meshes */
-static void draw_object_mesh_instance(Object *ob, int dt, int outline)
-{
- DerivedMesh *dm=NULL, *edm=NULL;
-
- if(G.obedit && ob->data==G.obedit->data)
- edm= editmesh_get_derived_base();
- else
- dm = mesh_get_derived_final(ob, CD_MASK_BAREMESH);
-
- if(dt<=OB_WIRE) {
- if(dm)
- dm->drawEdges(dm, 1);
- else if(edm)
- edm->drawEdges(edm, 1);
- }
- else {
- if(outline)
- draw_mesh_object_outline(ob, dm?dm:edm);
-
- if(dm)
- init_gl_materials(ob, 0);
- else {
- glEnable(GL_COLOR_MATERIAL);
- BIF_ThemeColor(TH_BONE_SOLID);
- glDisable(GL_COLOR_MATERIAL);
- }
-
- glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, 0);
- glFrontFace((ob->transflag&OB_NEG_SCALE)?GL_CW:GL_CCW);
- glEnable(GL_LIGHTING);
-
- if(dm)
- dm->drawFacesSolid(dm, set_gl_material);
- else if(edm)
- edm->drawMappedFaces(edm, NULL, NULL, 0);
-
- glDisable(GL_LIGHTING);
- }
-
- if(edm) edm->release(edm);
- if(dm) dm->release(dm);
-}
-
-void draw_object_instance(Object *ob, int dt, int outline)
-{
- if (ob == NULL)
- return;
-
- switch (ob->type) {
- case OB_MESH:
- draw_object_mesh_instance(ob, dt, outline);
- break;
- case OB_EMPTY:
- drawaxes(ob->empty_drawsize, 0, ob->empty_drawtype);
- break;
- }
-}