2007-05-06 16:03:28 +00:00
|
|
|
|
//////////////////////////////////////
|
2008-03-03 08:00:26 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
// Name: 3d_draw.cpp
|
|
|
|
|
//////////////////////////////////////
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#ifdef __GNUG__
|
|
|
|
|
#pragma implementation
|
|
|
|
|
#pragma interface
|
|
|
|
|
#endif
|
|
|
|
|
|
|
|
|
|
#include "fctsys.h"
|
|
|
|
|
#include "trigo.h"
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#if !wxUSE_GLCANVAS
|
|
|
|
|
#error Please set wxUSE_GLCANVAS to 1 in setup.h.
|
|
|
|
|
#endif
|
|
|
|
|
|
|
|
|
|
#include "common.h"
|
|
|
|
|
#include "pcbstruct.h"
|
|
|
|
|
#include "macros.h"
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
// #include "pcbnew.h"
|
2007-05-06 16:03:28 +00:00
|
|
|
|
|
|
|
|
|
#include "3d_viewer.h"
|
|
|
|
|
#include "trackball.h"
|
|
|
|
|
|
|
|
|
|
#include "3d_struct.h"
|
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
static void Draw3D_FilledCircle( double posx, double posy,
|
|
|
|
|
double rayon, double hole_rayon, double zpos );
|
|
|
|
|
static void Draw3D_FilledSegment( double startx, double starty,
|
|
|
|
|
double endx, double endy, double width, double zpos );
|
|
|
|
|
static void Draw3D_FilledCylinder( double posx, double posy,
|
|
|
|
|
double rayon, double height, double zpos );
|
|
|
|
|
static void Draw3D_FilledSegmentWithHole( double startx,
|
|
|
|
|
double starty,
|
|
|
|
|
double endx,
|
|
|
|
|
double endy,
|
|
|
|
|
double width,
|
|
|
|
|
double holex,
|
|
|
|
|
double holey,
|
|
|
|
|
double holeradius,
|
|
|
|
|
double zpos );
|
2008-03-10 22:46:44 +00:00
|
|
|
|
static void Draw3D_ArcSegment(double startx, double starty,
|
|
|
|
|
double endx, double endy,double width, double zpos);
|
|
|
|
|
static void Draw3D_CircleSegment(double startx, double starty,
|
|
|
|
|
double endx, double endy,double width, double zpos);
|
2008-03-03 08:00:26 +00:00
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/******************************************/
|
2007-06-05 15:51:07 +00:00
|
|
|
|
void Pcb3D_GLCanvas::Redraw( bool finish )
|
2008-03-03 08:00:26 +00:00
|
|
|
|
/******************************************/
|
2007-05-06 16:03:28 +00:00
|
|
|
|
{
|
|
|
|
|
SetCurrent();
|
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
InitGL();
|
2007-05-06 16:03:28 +00:00
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
glMatrixMode( GL_MODELVIEW ); /* position viewer */
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/* transformations */
|
|
|
|
|
GLfloat mat[4][4];
|
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
// Translatory motion first, so rotations don't mess up the orientation...
|
|
|
|
|
glTranslatef( g_Draw3d_dx, g_Draw3d_dy, 0.0F );
|
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
build_rotmatrix( mat, g_Parm_3D_Visu.m_Quat );
|
|
|
|
|
glMultMatrixf( &mat[0][0] );
|
2007-06-05 12:10:51 +00:00
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
glRotatef( g_Parm_3D_Visu.m_Rot[0], 1.0, 0.0, 0.0 );
|
|
|
|
|
glRotatef( g_Parm_3D_Visu.m_Rot[1], 0.0, 1.0, 0.0 );
|
|
|
|
|
glRotatef( g_Parm_3D_Visu.m_Rot[2], 0.0, 0.0, 1.0 );
|
2007-05-06 16:03:28 +00:00
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
if( m_gllist )
|
|
|
|
|
glCallList( m_gllist );
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
m_gllist = CreateDrawGL_List();
|
2007-05-06 16:03:28 +00:00
|
|
|
|
|
|
|
|
|
// m_gllist = DisplayCubeforTest(); // Only for test
|
2008-03-03 08:00:26 +00:00
|
|
|
|
}
|
2007-05-06 16:03:28 +00:00
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
glFlush();
|
|
|
|
|
if( finish )
|
|
|
|
|
glFinish();
|
|
|
|
|
SwapBuffers();
|
2007-11-01 05:27:31 +00:00
|
|
|
|
}
|
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
|
|
|
|
|
/**********************************************/
|
2007-09-13 11:55:46 +00:00
|
|
|
|
GLuint Pcb3D_GLCanvas::CreateDrawGL_List()
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/**********************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/* Creation de la liste des elements a afficher
|
2007-11-01 05:27:31 +00:00
|
|
|
|
*/
|
2007-05-06 16:03:28 +00:00
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
GLuint gllist = glGenLists( 1 );
|
|
|
|
|
WinEDA_BasePcbFrame* pcbframe = m_Parent->m_Parent;
|
|
|
|
|
BOARD* pcb = pcbframe->m_Pcb;
|
|
|
|
|
TRACK* pt_piste;
|
|
|
|
|
int ii;
|
|
|
|
|
|
|
|
|
|
wxBusyCursor dummy;
|
|
|
|
|
|
|
|
|
|
pcb->ComputeBoundaryBox();
|
|
|
|
|
g_Parm_3D_Visu.m_BoardSettings = pcb->m_BoardSettings;
|
|
|
|
|
g_Parm_3D_Visu.m_BoardSize = pcb->m_BoundaryBox.GetSize();
|
|
|
|
|
g_Parm_3D_Visu.m_BoardPos = pcb->m_BoundaryBox.Centre();
|
|
|
|
|
g_Parm_3D_Visu.m_BoardPos.y = -g_Parm_3D_Visu.m_BoardPos.y;
|
|
|
|
|
g_Parm_3D_Visu.m_Layers = pcb->m_BoardSettings->m_CopperLayerCount;
|
|
|
|
|
g_Parm_3D_Visu.m_BoardScale = 2.0 / MAX( g_Parm_3D_Visu.m_BoardSize.x,
|
|
|
|
|
g_Parm_3D_Visu.m_BoardSize.y );
|
|
|
|
|
float epoxy_width = 1.6; // epoxy width in mm
|
|
|
|
|
g_Parm_3D_Visu.m_Epoxy_Width = epoxy_width / 2.54 * 1000
|
|
|
|
|
* g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
|
|
|
|
|
/* calcul de l'altitude de chaque couche */
|
|
|
|
|
for( ii = 0; ii < 32; ii++ )
|
|
|
|
|
{
|
|
|
|
|
if( ii < g_Parm_3D_Visu.m_Layers )
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[ii] = g_Parm_3D_Visu.m_Epoxy_Width * ii
|
|
|
|
|
/ (g_Parm_3D_Visu.m_Layers - 1);
|
|
|
|
|
else
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[ii] = g_Parm_3D_Visu.m_Epoxy_Width;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
GLfloat zpos_cu = 500 * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
GLfloat zpos_cmp = g_Parm_3D_Visu.m_Epoxy_Width + zpos_cu;
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[ADHESIVE_N_CU] = -zpos_cu * 2;
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[ADHESIVE_N_CMP] = zpos_cmp + zpos_cu;
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[SILKSCREEN_N_CU] = -zpos_cu;
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[SILKSCREEN_N_CMP] = zpos_cmp;
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[DRAW_N] = zpos_cmp + zpos_cu;
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[COMMENT_N] = zpos_cmp + zpos_cu;
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[ECO1_N] = zpos_cmp + zpos_cu;
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[ECO2_N] = zpos_cmp + zpos_cu;
|
|
|
|
|
|
|
|
|
|
glNewList( gllist, GL_COMPILE_AND_EXECUTE );
|
|
|
|
|
|
|
|
|
|
glColorMaterial( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE );
|
|
|
|
|
|
|
|
|
|
/* draw axes */
|
|
|
|
|
glEnable( GL_COLOR_MATERIAL );
|
|
|
|
|
SetGLColor( WHITE );
|
|
|
|
|
glBegin( GL_LINES );
|
|
|
|
|
glNormal3f( 0.0, 0.0, 1.0 ); // Normal is Z axis
|
|
|
|
|
glVertex3f( 0.0, 0.0, 0.0 );
|
|
|
|
|
glVertex3f( 1.0, 0.0, 0.0 ); // X axis
|
|
|
|
|
glVertex3f( 0.0, 0.0, 0.0 );
|
|
|
|
|
glVertex3f( 0.0, -1.0, 0.0 ); // Y axis
|
|
|
|
|
glNormal3f( 1.0, 0.0, 0.0 ); // Normal is Y axis
|
|
|
|
|
glVertex3f( 0.0, 0.0, 0.0 );
|
|
|
|
|
glVertex3f( 0.0, 0.0, 0.3 ); // Z axis
|
2007-05-06 16:03:28 +00:00
|
|
|
|
glEnd();
|
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
/* Draw epoxy limits (do not use, works and test in progress) */
|
2007-05-06 16:03:28 +00:00
|
|
|
|
#if 0
|
2008-03-03 08:00:26 +00:00
|
|
|
|
glEnable( GL_FOG );
|
|
|
|
|
GLfloat param;
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
// param = GL_LINEAR;
|
|
|
|
|
// glFogfv(GL_FOG_MODE, & param);
|
2008-03-03 08:00:26 +00:00
|
|
|
|
param = 0.2;
|
|
|
|
|
glFogfv( GL_FOG_DENSITY, ¶m );
|
|
|
|
|
param = g_Parm_3D_Visu.m_LayerZcoord[15];
|
|
|
|
|
glFogfv( GL_FOG_END, ¶m );
|
|
|
|
|
glBegin( GL_QUADS );
|
|
|
|
|
SetGLColor( g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[CMP_N] );
|
|
|
|
|
double sx = DataScale3D * g_Parm_3D_Visu.m_BoardSize.x / 2;
|
|
|
|
|
double sy = DataScale3D * g_Parm_3D_Visu.m_BoardSize.y / 2;
|
|
|
|
|
double zpos = g_Parm_3D_Visu.m_LayerZcoord[15];
|
|
|
|
|
glNormal3f( 0.0, 0.0, 1.0 ); // Normal is Z axis
|
|
|
|
|
sx = sy = 0.5;
|
|
|
|
|
glVertex3f( -sx, -sy, zpos );
|
|
|
|
|
glVertex3f( -sx, sy, zpos );
|
|
|
|
|
glVertex3f( sx, sy, zpos );
|
|
|
|
|
glVertex3f( sx, -sy, zpos );
|
|
|
|
|
glEnd();
|
|
|
|
|
glBegin( GL_QUADS );
|
|
|
|
|
SetGLColor( g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[COPPER_LAYER_N] );
|
|
|
|
|
glNormal3f( 0.0, 0.0, -1.0 ); // Normal is -Z axis
|
|
|
|
|
glVertex3f( -sx, -sy, 0 );
|
|
|
|
|
glVertex3f( -sx, sy, 0 );
|
|
|
|
|
glVertex3f( sx, sy, 0 );
|
|
|
|
|
glVertex3f( sx, -sy, 0 );
|
|
|
|
|
glEnd();
|
2007-05-06 16:03:28 +00:00
|
|
|
|
#endif
|
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
/* Translation du trac<61> du BOARD pour placer son centre en 0, 0 */
|
|
|
|
|
glTranslatef( -g_Parm_3D_Visu.m_BoardPos.x * g_Parm_3D_Visu.m_BoardScale,
|
|
|
|
|
-g_Parm_3D_Visu.m_BoardPos.y * g_Parm_3D_Visu.m_BoardScale,
|
|
|
|
|
0.0F );
|
|
|
|
|
|
|
|
|
|
glNormal3f( 0.0, 0.0, 1.0 ); // Normal is Z axis
|
|
|
|
|
/* Trac<61> des pistes : */
|
|
|
|
|
for( pt_piste = pcb->m_Track; pt_piste != NULL; pt_piste = (TRACK*) pt_piste->Pnext )
|
|
|
|
|
{
|
|
|
|
|
if( pt_piste->Type() == TYPEVIA )
|
|
|
|
|
Draw3D_Via( (SEGVIA*) pt_piste );
|
|
|
|
|
else
|
|
|
|
|
Draw3D_Track( pt_piste );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/* Trac<61> des edges */
|
|
|
|
|
EDA_BaseStruct* PtStruct;
|
|
|
|
|
for( PtStruct = pcb->m_Drawings; PtStruct != NULL; PtStruct = PtStruct->Pnext )
|
|
|
|
|
{
|
|
|
|
|
#define STRUCT ( (DRAWSEGMENT*) PtStruct )
|
|
|
|
|
if( PtStruct->Type() != TYPEDRAWSEGMENT )
|
|
|
|
|
continue;
|
|
|
|
|
Draw3D_DrawSegment( STRUCT );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/* trac<61> des modules */
|
|
|
|
|
MODULE* Module = (MODULE*) pcb->m_Modules;
|
|
|
|
|
for( ; Module != NULL; Module = (MODULE*) Module->Pnext )
|
|
|
|
|
{
|
|
|
|
|
Module->Draw3D( this );
|
|
|
|
|
}
|
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
glEndList();
|
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
/* Test for errors */
|
|
|
|
|
GLenum err = glGetError();
|
|
|
|
|
if( err != GL_NO_ERROR )
|
|
|
|
|
DisplayError( this, wxT( "Error in GL commands" ) );
|
|
|
|
|
return gllist;
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/************************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
void Pcb3D_GLCanvas::Draw3D_Track( TRACK* track )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/************************************************/
|
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
double zpos;
|
|
|
|
|
int layer = track->GetLayer();
|
|
|
|
|
int color = g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[layer];
|
|
|
|
|
double ox, oy, fx, fy;
|
|
|
|
|
double w;
|
|
|
|
|
|
|
|
|
|
if( color & ITEM_NOT_SHOW )
|
|
|
|
|
return;
|
|
|
|
|
if( layer == LAST_COPPER_LAYER )
|
|
|
|
|
layer = g_Parm_3D_Visu.m_Layers - 1;
|
|
|
|
|
zpos = g_Parm_3D_Visu.m_LayerZcoord[layer];
|
|
|
|
|
|
|
|
|
|
SetGLColor( color );
|
|
|
|
|
glNormal3f( 0.0, 0.0, (layer == COPPER_LAYER_N) ? -1.0 : 1.0 );
|
|
|
|
|
|
|
|
|
|
w = track->m_Width * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
ox = track->m_Start.x * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
oy = track->m_Start.y * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
fx = track->m_End.x * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
fy = track->m_End.y * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
Draw3D_FilledSegment( ox, -oy, fx, -fy, w, zpos );
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/********************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
void Pcb3D_GLCanvas::Draw3D_Via( SEGVIA* via )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*********************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/* 3D drawing for a VIA (cylinder + filled circles)
|
2007-11-01 05:27:31 +00:00
|
|
|
|
*/
|
2007-05-06 16:03:28 +00:00
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
double x, y, r, hole;
|
|
|
|
|
int layer, top_layer, bottom_layer;
|
|
|
|
|
double zpos, height;
|
|
|
|
|
int color;
|
|
|
|
|
|
|
|
|
|
r = via->m_Width * g_Parm_3D_Visu.m_BoardScale / 2;
|
|
|
|
|
hole = via->GetDrillValue();
|
|
|
|
|
hole *= g_Parm_3D_Visu.m_BoardScale / 2;
|
|
|
|
|
x = via->m_Start.x * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
y = via->m_Start.y * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
|
|
|
|
|
via->ReturnLayerPair( &top_layer, &bottom_layer );
|
|
|
|
|
|
|
|
|
|
// Drawing filled circles:
|
|
|
|
|
for( layer = bottom_layer; layer < g_Parm_3D_Visu.m_Layers; layer++ )
|
|
|
|
|
{
|
|
|
|
|
zpos = g_Parm_3D_Visu.m_LayerZcoord[layer];
|
|
|
|
|
if( layer < g_Parm_3D_Visu.m_Layers - 1 )
|
|
|
|
|
color = g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[layer];
|
|
|
|
|
else
|
|
|
|
|
color = g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[CMP_N];
|
|
|
|
|
if( color & ITEM_NOT_SHOW )
|
|
|
|
|
continue;
|
|
|
|
|
SetGLColor( color );
|
|
|
|
|
glNormal3f( 0.0, 0.0, (layer == COPPER_LAYER_N) ? -1.0 : 1.0 );
|
|
|
|
|
Draw3D_FilledCircle( x, -y, r, hole, zpos );
|
|
|
|
|
if( layer >= top_layer )
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Drawing hole:
|
|
|
|
|
SetGLColor( DARKGRAY );
|
|
|
|
|
height = g_Parm_3D_Visu.m_LayerZcoord[top_layer] - g_Parm_3D_Visu.m_LayerZcoord[bottom_layer];
|
|
|
|
|
Draw3D_FilledCylinder( x, -y, hole, height, g_Parm_3D_Visu.m_LayerZcoord[bottom_layer] );
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/*************************************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
void Pcb3D_GLCanvas::Draw3D_DrawSegment( DRAWSEGMENT* segment )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*************************************************************/
|
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
int layer;
|
|
|
|
|
double x, y, xf, yf;
|
|
|
|
|
double zpos, w;
|
|
|
|
|
int color = g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[segment->GetLayer()];
|
|
|
|
|
|
|
|
|
|
if( color & ITEM_NOT_SHOW )
|
|
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
SetGLColor( color );
|
|
|
|
|
w = segment->m_Width * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
x = segment->m_Start.x * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
y = segment->m_Start.y * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
xf = segment->m_End.x * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
yf = segment->m_End.y * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
|
|
|
|
|
if( segment->GetLayer() == EDGE_N )
|
|
|
|
|
{
|
|
|
|
|
for( layer = 0; layer < g_Parm_3D_Visu.m_Layers; layer++ )
|
|
|
|
|
{
|
|
|
|
|
glNormal3f( 0.0, 0.0, (layer == COPPER_LAYER_N) ? -1.0 : 1.0 );
|
|
|
|
|
zpos = g_Parm_3D_Visu.m_LayerZcoord[layer];
|
2008-03-11 22:48:52 +00:00
|
|
|
|
switch( segment->m_Shape )
|
2008-03-10 22:46:44 +00:00
|
|
|
|
{
|
|
|
|
|
case S_ARC:
|
|
|
|
|
Draw3D_ArcSegment( x, -y, xf, -yf, w, zpos);
|
|
|
|
|
break;
|
|
|
|
|
case S_CIRCLE:
|
|
|
|
|
Draw3D_CircleSegment( x, -y, xf, -yf, w, zpos);
|
|
|
|
|
break;
|
|
|
|
|
default :
|
|
|
|
|
Draw3D_FilledSegment( x, -y, xf, -yf, w, zpos);
|
|
|
|
|
break;
|
|
|
|
|
}
|
2008-03-03 08:00:26 +00:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
zpos = g_Parm_3D_Visu.m_LayerZcoord[segment->GetLayer()];
|
|
|
|
|
Draw3D_FilledSegment( x, -y, xf, -yf, w, zpos );
|
|
|
|
|
}
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/*********************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
void MODULE::Draw3D( Pcb3D_GLCanvas* glcanvas )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*********************************************/
|
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
D_PAD* pad = m_Pads;
|
2007-05-06 16:03:28 +00:00
|
|
|
|
|
|
|
|
|
#if 0
|
2008-03-03 08:00:26 +00:00
|
|
|
|
if( !DisplayOpt.Show_Modules_Cmp )
|
|
|
|
|
{
|
|
|
|
|
if( m_Layer == CMP_N )
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
if( !DisplayOpt.Show_Modules_Cu )
|
|
|
|
|
{
|
|
|
|
|
if( m_Layer == COPPER_LAYER_N )
|
|
|
|
|
return;
|
|
|
|
|
}
|
2007-05-06 16:03:28 +00:00
|
|
|
|
#endif
|
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
/* Draw pads */
|
|
|
|
|
glColorMaterial( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE );
|
|
|
|
|
glNormal3f( 0.0, 0.0, 1.0 ); // Normal is Z axis
|
|
|
|
|
for( ; pad != NULL; pad = (D_PAD*) pad->Pnext )
|
|
|
|
|
{
|
|
|
|
|
pad->Draw3D( glcanvas );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/* Draw module shape: 3D shape if exists (or module edge if not exists) */
|
|
|
|
|
Struct3D_Master* Struct3D = m_3D_Drawings;
|
|
|
|
|
bool As3dShape = FALSE;
|
|
|
|
|
glPushMatrix();
|
|
|
|
|
glTranslatef( m_Pos.x * g_Parm_3D_Visu.m_BoardScale,
|
|
|
|
|
-m_Pos.y * g_Parm_3D_Visu.m_BoardScale,
|
|
|
|
|
g_Parm_3D_Visu.m_LayerZcoord[m_Layer] );
|
|
|
|
|
if( m_Orient )
|
|
|
|
|
{
|
|
|
|
|
glRotatef( (double) m_Orient / 10, 0.0, 0.0, 1.0 );
|
|
|
|
|
}
|
|
|
|
|
if( m_Layer == COPPER_LAYER_N )
|
|
|
|
|
{
|
|
|
|
|
glRotatef( 180.0, 0.0, 1.0, 0.0 );
|
|
|
|
|
glRotatef( 180.0, 0.0, 0.0, 1.0 );
|
|
|
|
|
}
|
|
|
|
|
DataScale3D = g_Parm_3D_Visu.m_BoardScale * UNITS3D_TO_UNITSPCB;
|
|
|
|
|
|
|
|
|
|
for( ; Struct3D != NULL; Struct3D = (Struct3D_Master*) Struct3D->Pnext )
|
|
|
|
|
{
|
|
|
|
|
if( !Struct3D->m_Shape3DName.IsEmpty() )
|
|
|
|
|
{
|
|
|
|
|
As3dShape = TRUE;
|
|
|
|
|
Struct3D->ReadData();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
glPopMatrix();
|
|
|
|
|
|
|
|
|
|
if( !As3dShape )
|
|
|
|
|
{
|
|
|
|
|
EDA_BaseStruct* Struct = m_Drawings;
|
|
|
|
|
glNormal3f( 0.0, 0.0, 1.0 ); // Normal is Z axis
|
|
|
|
|
for( ; Struct != NULL; Struct = Struct->Pnext )
|
|
|
|
|
{
|
|
|
|
|
switch( Struct->Type() )
|
|
|
|
|
{
|
|
|
|
|
case TYPETEXTEMODULE:
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case TYPEEDGEMODULE:
|
|
|
|
|
( (EDGE_MODULE*) Struct )->Draw3D( glcanvas );
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
default:
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/***************************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
void EDGE_MODULE::Draw3D( Pcb3D_GLCanvas* glcanvas )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/***************************************************/
|
|
|
|
|
{
|
2008-03-11 22:48:52 +00:00
|
|
|
|
wxString s;
|
|
|
|
|
int dx, dy;
|
2008-03-03 08:00:26 +00:00
|
|
|
|
double scale, x, y, fx, fy, w, zpos;
|
|
|
|
|
int color = g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[m_Layer];
|
|
|
|
|
|
|
|
|
|
if( color & ITEM_NOT_SHOW )
|
|
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
SetGLColor( color );
|
|
|
|
|
glNormal3f( 0.0, 0.0, (m_Layer == COPPER_LAYER_N) ? -1.0 : 1.0 );
|
|
|
|
|
scale = g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
|
|
|
|
|
dx = m_End.x;
|
|
|
|
|
dy = m_End.y;
|
|
|
|
|
zpos = g_Parm_3D_Visu.m_LayerZcoord[m_Layer];
|
|
|
|
|
w = m_Width * g_Parm_3D_Visu.m_BoardScale;
|
2008-03-11 22:48:52 +00:00
|
|
|
|
x = m_Start.x * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
y = m_Start.y * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
fx = dx * g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
fy = dy * g_Parm_3D_Visu.m_BoardScale;
|
2008-03-03 08:00:26 +00:00
|
|
|
|
|
2008-03-11 22:48:52 +00:00
|
|
|
|
|
|
|
|
|
switch( m_Shape )
|
2008-03-03 08:00:26 +00:00
|
|
|
|
{
|
|
|
|
|
case S_SEGMENT:
|
|
|
|
|
Draw3D_FilledSegment( x, -y, fx, -fy, w, zpos );
|
2008-03-11 22:48:52 +00:00
|
|
|
|
#if 0
|
|
|
|
|
s.Printf("Draw FilledSegment: %g, %g, %g, %g, %g, %g\n",x,-y,fx,-fy,w,zpos);
|
|
|
|
|
printf( CONV_TO_UTF8( s ) );
|
|
|
|
|
#endif
|
2008-03-03 08:00:26 +00:00
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case S_CIRCLE:
|
2008-03-11 22:48:52 +00:00
|
|
|
|
Draw3D_CircleSegment( x, -y, fx, -fy, w, zpos);
|
|
|
|
|
#if 0
|
|
|
|
|
s.Printf("Draw Circle: %g, %g, %g, %g, %g, %g\n",x,-y,fx,-fy,w,zpos);
|
|
|
|
|
printf( CONV_TO_UTF8( s ) );
|
|
|
|
|
#endif
|
2008-03-03 08:00:26 +00:00
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case S_ARC:
|
2008-03-11 22:48:52 +00:00
|
|
|
|
Draw3D_ArcSegment( x, -y, fx, -fy, w, zpos);
|
|
|
|
|
#if 0
|
|
|
|
|
s.Printf("Draw Arc: %g, %g, %g, %g, %g, %g\n",x,-y,fx,-fy,w,zpos);
|
|
|
|
|
printf( CONV_TO_UTF8( s ) );
|
|
|
|
|
#endif
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
default:
|
|
|
|
|
s.Printf(wxT("Error: Shape nr %d not implemented!\n"), m_Shape);
|
|
|
|
|
printf( CONV_TO_UTF8( s ) );
|
|
|
|
|
|
|
|
|
|
break;
|
2008-03-03 08:00:26 +00:00
|
|
|
|
}
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/***********************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
void D_PAD::Draw3D( Pcb3D_GLCanvas* glcanvas )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/***********************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/* Dessin 3D des pads avec leur trou de percage
|
2007-11-01 05:27:31 +00:00
|
|
|
|
*/
|
2007-05-06 16:03:28 +00:00
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
int ii, ll, layer, nlmax;
|
|
|
|
|
int ux0, uy0,
|
|
|
|
|
dx, dx0, dy, dy0,
|
|
|
|
|
delta_cx, delta_cy,
|
|
|
|
|
xc, yc;
|
|
|
|
|
int angle, delta_angle;
|
|
|
|
|
int coord[4][2];
|
|
|
|
|
double fcoord[8][2], f_hole_coord[8][2];
|
|
|
|
|
float scale;
|
|
|
|
|
double zpos;
|
|
|
|
|
wxPoint shape_pos;
|
|
|
|
|
double x, y, r, w, hole, holeX, holeY;
|
|
|
|
|
double drillx, drilly;
|
|
|
|
|
bool Oncu, Oncmp, Both;
|
|
|
|
|
int color;
|
|
|
|
|
|
|
|
|
|
scale = g_Parm_3D_Visu.m_BoardScale;
|
|
|
|
|
holeX = (double) m_Drill.x * scale / 2;
|
|
|
|
|
holeY = (double) m_Drill.y * scale / 2;
|
|
|
|
|
hole = MIN( holeX, holeY );
|
|
|
|
|
|
|
|
|
|
/* calcul du centre des formes des pads : */
|
2007-05-06 16:03:28 +00:00
|
|
|
|
shape_pos = ReturnShapePos();
|
2008-03-03 08:00:26 +00:00
|
|
|
|
ux0 = shape_pos.x;
|
|
|
|
|
uy0 = shape_pos.y;
|
|
|
|
|
xc = ux0;
|
|
|
|
|
yc = uy0;
|
|
|
|
|
|
|
|
|
|
/* le trace depend de la rotation de l'empreinte */
|
|
|
|
|
dx = dx0 = m_Size.x >> 1;
|
|
|
|
|
dy = dy0 = m_Size.y >> 1; /* demi dim dx et dy */
|
|
|
|
|
|
|
|
|
|
angle = m_Orient;
|
|
|
|
|
drillx = m_Pos.x * scale;
|
|
|
|
|
drilly = m_Pos.y * scale;
|
|
|
|
|
/* Draw the pad hole (TODO: draw OBLONG hole) */
|
|
|
|
|
if( holeX && holeY )
|
|
|
|
|
{
|
|
|
|
|
SetGLColor( DARKGRAY );
|
|
|
|
|
Draw3D_FilledCylinder( drillx, -drilly, hole, g_Parm_3D_Visu.m_LayerZcoord[CMP_N], 0.0 );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
glNormal3f( 0.0, 0.0, 1.0 ); // Normal is Z axis
|
|
|
|
|
nlmax = g_Parm_3D_Visu.m_Layers - 1;
|
|
|
|
|
Oncu = (m_Masque_Layer & CUIVRE_LAYER) ? TRUE : FALSE;
|
|
|
|
|
Oncmp = (m_Masque_Layer & CMP_LAYER) ? TRUE : FALSE;
|
|
|
|
|
Both = Oncu && Oncmp;
|
|
|
|
|
|
|
|
|
|
switch( m_PadShape & 0x7F )
|
|
|
|
|
{
|
|
|
|
|
case PAD_CIRCLE:
|
|
|
|
|
x = xc * scale;
|
|
|
|
|
y = yc * scale;
|
|
|
|
|
r = (double) dx * scale;
|
|
|
|
|
for( layer = FIRST_COPPER_LAYER; layer <= LAST_COPPER_LAYER; layer++ )
|
|
|
|
|
{
|
|
|
|
|
if( layer && (layer == nlmax) )
|
|
|
|
|
layer = CMP_N;
|
|
|
|
|
if( (layer == CMP_N) && !Oncmp )
|
|
|
|
|
continue;
|
|
|
|
|
if( (layer == COPPER_LAYER_N) && !Oncu )
|
|
|
|
|
continue;
|
|
|
|
|
if( (layer > FIRST_COPPER_LAYER) && (layer < LAST_COPPER_LAYER) && !Both )
|
|
|
|
|
continue;
|
|
|
|
|
color = g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[layer];
|
|
|
|
|
if( color & ITEM_NOT_SHOW )
|
|
|
|
|
continue;
|
|
|
|
|
SetGLColor( color );
|
|
|
|
|
glNormal3f( 0.0, 0.0, (layer == COPPER_LAYER_N) ? -1.0 : 1.0 );
|
|
|
|
|
zpos = g_Parm_3D_Visu.m_LayerZcoord[layer];
|
|
|
|
|
Draw3D_FilledCircle( x, -y, r, hole, zpos );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case PAD_OVAL:
|
|
|
|
|
/* calcul de l'entraxe de l'ellipse */
|
|
|
|
|
if( dx > dy ) /* ellipse horizontale */
|
|
|
|
|
{
|
|
|
|
|
delta_cx = dx - dy;
|
|
|
|
|
delta_cy = 0;
|
|
|
|
|
w = m_Size.y * scale;
|
|
|
|
|
delta_angle = angle + 900;
|
|
|
|
|
}
|
|
|
|
|
else /* ellipse verticale */
|
|
|
|
|
{
|
|
|
|
|
delta_cx = 0;
|
|
|
|
|
delta_cy = dy - dx;
|
|
|
|
|
w = m_Size.x * scale;
|
|
|
|
|
delta_angle = angle;
|
|
|
|
|
}
|
|
|
|
|
RotatePoint( &delta_cx, &delta_cy, angle );
|
|
|
|
|
{
|
|
|
|
|
double ox, oy, fx, fy;
|
|
|
|
|
ox = (double) (ux0 + delta_cx) * scale;
|
|
|
|
|
oy = (double) (uy0 + delta_cy) * scale;
|
|
|
|
|
fx = (double) (ux0 - delta_cx) * scale;
|
|
|
|
|
fy = (double) (uy0 - delta_cy) * scale;
|
|
|
|
|
for( layer = FIRST_COPPER_LAYER; layer <= LAST_COPPER_LAYER; layer++ )
|
|
|
|
|
{
|
|
|
|
|
if( layer && (layer == nlmax) )
|
|
|
|
|
layer = CMP_N;
|
|
|
|
|
if( (layer == CMP_N) && !Oncmp )
|
|
|
|
|
continue;
|
|
|
|
|
if( (layer == COPPER_LAYER_N) && !Oncu )
|
|
|
|
|
continue;
|
|
|
|
|
if( (layer > FIRST_COPPER_LAYER) && (layer < LAST_COPPER_LAYER) && !Both )
|
|
|
|
|
continue;
|
|
|
|
|
color = g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[layer];
|
|
|
|
|
glNormal3f( 0.0, 0.0, (layer == COPPER_LAYER_N) ? -1.0 : 1.0 );
|
|
|
|
|
if( color & ITEM_NOT_SHOW )
|
|
|
|
|
continue;
|
|
|
|
|
SetGLColor( color );
|
|
|
|
|
zpos = g_Parm_3D_Visu.m_LayerZcoord[layer];
|
|
|
|
|
Draw3D_FilledSegmentWithHole( ox, -oy, fx, -fy, w, drillx, -drilly, hole, zpos );
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case PAD_RECT:
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
// case SPECIAL_PAD:
|
2008-03-03 08:00:26 +00:00
|
|
|
|
case PAD_TRAPEZOID:
|
|
|
|
|
{
|
|
|
|
|
int ddx, ddy;
|
|
|
|
|
ddx = m_DeltaSize.x >> 1;
|
|
|
|
|
ddy = m_DeltaSize.y >> 1; /* demi dim dx et dy */
|
|
|
|
|
|
|
|
|
|
coord[0][0] = -dx - ddy;
|
|
|
|
|
coord[0][1] = +dy + ddx;
|
|
|
|
|
|
|
|
|
|
coord[1][0] = -dx + ddy;
|
|
|
|
|
coord[1][1] = -dy - ddx;
|
|
|
|
|
|
|
|
|
|
coord[2][0] = +dx - ddy;
|
|
|
|
|
coord[2][1] = -dy + ddx;
|
|
|
|
|
|
|
|
|
|
coord[3][0] = +dx + ddy;
|
|
|
|
|
coord[3][1] = +dy - ddx;
|
|
|
|
|
|
|
|
|
|
for( ii = 0; ii < 4; ii++ )
|
|
|
|
|
{
|
|
|
|
|
RotatePoint( &coord[ii][0], &coord[ii][1], angle );
|
|
|
|
|
coord[ii][0] += ux0;
|
|
|
|
|
coord[ii][1] += uy0;
|
|
|
|
|
ll = ii * 2;
|
|
|
|
|
fcoord[ll][0] = coord[ii][0] * scale;
|
|
|
|
|
fcoord[ll][1] = coord[ii][1] * scale;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
for( ii = 0; ii < 7; ii += 2 )
|
|
|
|
|
{
|
|
|
|
|
ll = ii + 2;
|
|
|
|
|
if( ll > 7 )
|
|
|
|
|
ll -= 8;
|
|
|
|
|
fcoord[ii + 1][0] = (fcoord[ii][0] + fcoord[ll][0]) / 2;
|
|
|
|
|
fcoord[ii + 1][1] = (fcoord[ii][1] + fcoord[ll][1]) / 2;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
for( ii = 0; ii < 8; ii++ )
|
|
|
|
|
{
|
|
|
|
|
f_hole_coord[ii][0] = -hole * 0.707;
|
|
|
|
|
f_hole_coord[ii][1] = hole * 0.707;
|
|
|
|
|
RotatePoint( &f_hole_coord[ii][0], &f_hole_coord[ii][1],
|
|
|
|
|
angle - (ii * 450) );
|
|
|
|
|
f_hole_coord[ii][0] += drillx;
|
|
|
|
|
f_hole_coord[ii][1] += drilly;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
for( layer = FIRST_COPPER_LAYER; layer <= LAST_COPPER_LAYER; layer++ )
|
|
|
|
|
{
|
|
|
|
|
if( layer && (layer == nlmax) )
|
|
|
|
|
layer = CMP_N;
|
|
|
|
|
if( (layer == CMP_N) && !Oncmp )
|
|
|
|
|
continue;
|
|
|
|
|
if( (layer == COPPER_LAYER_N) && !Oncu )
|
|
|
|
|
continue;
|
|
|
|
|
if( (layer > FIRST_COPPER_LAYER) && (layer < LAST_COPPER_LAYER) && !Both )
|
|
|
|
|
continue;
|
|
|
|
|
color = g_Parm_3D_Visu.m_BoardSettings->m_LayerColor[layer];
|
|
|
|
|
glNormal3f( 0.0, 0.0, (layer == COPPER_LAYER_N) ? -1.0 : 1.0 );
|
|
|
|
|
if( color & ITEM_NOT_SHOW )
|
|
|
|
|
continue;
|
|
|
|
|
SetGLColor( color );
|
|
|
|
|
zpos = g_Parm_3D_Visu.m_LayerZcoord[layer];
|
|
|
|
|
glBegin( GL_QUAD_STRIP );
|
|
|
|
|
for( ii = 0; ii < 8; ii++ )
|
|
|
|
|
{
|
|
|
|
|
glVertex3f( f_hole_coord[ii][0], -f_hole_coord[ii][1], zpos );
|
|
|
|
|
glVertex3f( fcoord[ii][0], -fcoord[ii][1], zpos );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
glVertex3f( f_hole_coord[0][0], -f_hole_coord[0][1], zpos );
|
|
|
|
|
glVertex3f( fcoord[0][0], -fcoord[0][1], zpos );
|
|
|
|
|
glEnd();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
default:
|
|
|
|
|
break;
|
|
|
|
|
}
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
void SetGLColor( int color )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*************************/
|
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
double red, green, blue;
|
|
|
|
|
StructColors colordata = ColorRefs[color & MASKCOLOR];
|
2007-05-06 16:03:28 +00:00
|
|
|
|
|
2008-03-03 08:00:26 +00:00
|
|
|
|
red = colordata.m_Red / 255.0;
|
|
|
|
|
blue = colordata.m_Blue / 255.0;
|
|
|
|
|
green = colordata.m_Green / 255.0;
|
|
|
|
|
glColor3f( red, green, blue );
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/********************************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
static void Draw3D_FilledCircle( double posx, double posy,
|
|
|
|
|
double rayon, double hole, double zpos )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/********************************************************/
|
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
int ii, slice = 16;
|
|
|
|
|
double x, y;
|
|
|
|
|
|
|
|
|
|
glBegin( GL_QUAD_STRIP );
|
|
|
|
|
for( ii = 0; ii <= slice; ii++ )
|
|
|
|
|
{
|
|
|
|
|
x = hole;
|
|
|
|
|
y = 0.0;
|
|
|
|
|
RotatePoint( &x, &y, ii * 225 );
|
|
|
|
|
glVertex3f( x + posx, y + posy, zpos );
|
|
|
|
|
x = rayon;
|
|
|
|
|
y = 0.0;
|
|
|
|
|
RotatePoint( &x, &y, ii * 225 );
|
|
|
|
|
glVertex3f( x + posx, y + posy, zpos );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
glEnd();
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*********************************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
static void Draw3D_FilledCylinder( double posx, double posy,
|
|
|
|
|
double rayon, double height, double zpos )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*********************************************************/
|
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
int ii;
|
|
|
|
|
double x, y;
|
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
#define NB_SEGM 12
|
2008-03-03 08:00:26 +00:00
|
|
|
|
S3D_Vertex coords[4];
|
|
|
|
|
double tmp = DataScale3D;
|
|
|
|
|
|
|
|
|
|
DataScale3D = 1.0; // les coord sont deja a l'echelle pour Set_Object_Data();
|
|
|
|
|
coords[0].x = coords[1].x = posx + rayon;
|
|
|
|
|
coords[0].y = coords[1].y = posy;
|
|
|
|
|
coords[0].z = coords[3].z = zpos;
|
|
|
|
|
coords[1].z = coords[2].z = zpos + height;
|
|
|
|
|
|
|
|
|
|
for( ii = 0; ii <= NB_SEGM; ii++ )
|
|
|
|
|
{
|
|
|
|
|
x = rayon;
|
|
|
|
|
y = 0.0;
|
|
|
|
|
RotatePoint( &x, &y, ii * (3600 / NB_SEGM) );
|
|
|
|
|
coords[2].x = coords[3].x = posx + x;
|
|
|
|
|
coords[2].y = coords[3].y = posy + y;
|
|
|
|
|
Set_Object_Data( coords, 4 );
|
|
|
|
|
coords[0].x = coords[2].x;
|
|
|
|
|
coords[0].y = coords[2].y;
|
|
|
|
|
coords[1].x = coords[3].x;
|
|
|
|
|
coords[1].y = coords[3].y;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
glNormal3f( 0.0, 0.0, 1.0 ); // Normal is Z axis
|
|
|
|
|
DataScale3D = tmp;
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*****************************************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
static void Draw3D_FilledSegment( double startx, double starty,
|
|
|
|
|
double endx, double endy, double width, double zpos )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*****************************************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/* trace un polygone semblable a un segment a bouts ronds
|
2007-11-01 05:27:31 +00:00
|
|
|
|
*/
|
2007-05-06 16:03:28 +00:00
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
double dx, dy, x, y, firstx = 0, firsty = 0;
|
|
|
|
|
int ii, angle;
|
|
|
|
|
|
|
|
|
|
// on va calculer les coordonn<6E>es du segment suppos<6F> horizontal,
|
|
|
|
|
// puis tourner les cordonnes de l'angle voulu
|
|
|
|
|
|
|
|
|
|
dx = endx - startx;
|
|
|
|
|
dy = endy - starty;
|
|
|
|
|
angle = (int) ( ( atan2( dy, dx ) * 1800 / M_PI ) + 0.5 );
|
|
|
|
|
|
|
|
|
|
RotatePoint( &dx, &dy, angle ); // apres rotation: dx = longueur du segment
|
|
|
|
|
// dy = 0;
|
|
|
|
|
width /= 2;
|
|
|
|
|
|
|
|
|
|
glBegin( GL_POLYGON );
|
|
|
|
|
|
|
|
|
|
// trac<61> de l'arrondi a droite (1er demi polygone a la fin du segment)
|
|
|
|
|
for( ii = 0; ii <= 8; ii++ )
|
|
|
|
|
{
|
|
|
|
|
x = 0.0;
|
|
|
|
|
y = -width;
|
|
|
|
|
RotatePoint( &x, &y, -ii * 225 );
|
|
|
|
|
x += dx;
|
|
|
|
|
RotatePoint( &x, &y, -angle );
|
|
|
|
|
glVertex3f( startx + x, starty + y, zpos );
|
|
|
|
|
if( ii == 0 )
|
|
|
|
|
{
|
|
|
|
|
firstx = startx + x;
|
|
|
|
|
firsty = starty + y;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// trac<61> de l'arrondi a gauche (2ieme demi polygone a l'origine du segment)
|
|
|
|
|
for( ii = 0; ii <= 8; ii++ )
|
|
|
|
|
{
|
|
|
|
|
int jj = ii * 225;
|
|
|
|
|
x = 0.0;
|
|
|
|
|
y = width;
|
|
|
|
|
RotatePoint( &x, &y, -angle - jj );
|
|
|
|
|
glVertex3f( startx + x, starty + y, zpos );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
glVertex3f( firstx, firsty, zpos );
|
|
|
|
|
glEnd();
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
|
|
|
|
|
2007-11-01 05:27:31 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*****************************************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
static void Draw3D_FilledSegmentWithHole( double startx,
|
|
|
|
|
double starty,
|
|
|
|
|
double endx,
|
|
|
|
|
double endy,
|
|
|
|
|
double width,
|
|
|
|
|
double holex,
|
|
|
|
|
double holey,
|
|
|
|
|
double holeradius,
|
|
|
|
|
double zpos )
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/*****************************************************************/
|
2008-03-03 08:00:26 +00:00
|
|
|
|
|
2007-05-06 16:03:28 +00:00
|
|
|
|
/* trace un polygone semblable a un segment a bouts ronds avec trou
|
2007-11-01 05:27:31 +00:00
|
|
|
|
*/
|
2007-05-06 16:03:28 +00:00
|
|
|
|
{
|
2008-03-03 08:00:26 +00:00
|
|
|
|
double x, y, xin, yin;
|
|
|
|
|
double firstx = 0, firsty = 0, firstxin = 0, firstyin = 0;
|
|
|
|
|
int ii, angle, theta;
|
|
|
|
|
|
|
|
|
|
// on va calculer les coordonn<6E>es du segment suppos<6F> horizontal,
|
|
|
|
|
// puis tourner les cordonnes de l'angle voulu
|
|
|
|
|
// Tous des calculs se font avec startx, starty comme origine du trac<61>
|
|
|
|
|
|
|
|
|
|
endx -= startx;
|
|
|
|
|
endy -= starty;
|
|
|
|
|
holex -= startx;
|
|
|
|
|
holey -= starty;
|
|
|
|
|
angle = (int) ( ( atan2( endy, endx ) * 1800 / M_PI ) + 0.5 );
|
|
|
|
|
|
|
|
|
|
RotatePoint( &endx, &endy, angle ); // apres rotation: endx = longueur du segment
|
|
|
|
|
// endy = 0;
|
|
|
|
|
RotatePoint( &holex, &holey, angle );
|
|
|
|
|
width /= 2;
|
|
|
|
|
|
|
|
|
|
glBegin( GL_QUAD_STRIP );
|
|
|
|
|
|
|
|
|
|
// trac<61> de l'arrondi a droite (1er demi polygone a la fin du segment)
|
|
|
|
|
// autour du demi-trou de percage
|
|
|
|
|
for( ii = 0; ii <= 8; ii++ )
|
|
|
|
|
{
|
|
|
|
|
x = 0.0;
|
|
|
|
|
y = -width;
|
|
|
|
|
xin = 0.0;
|
|
|
|
|
yin = -holeradius;
|
|
|
|
|
theta = -ii * 225;
|
|
|
|
|
RotatePoint( &x, &y, theta );
|
|
|
|
|
RotatePoint( &xin, &yin, theta );
|
|
|
|
|
x += endx;
|
|
|
|
|
RotatePoint( &x, &y, -angle );
|
|
|
|
|
xin += holex;
|
|
|
|
|
RotatePoint( &xin, &yin, -angle );
|
|
|
|
|
glVertex3f( startx + xin, starty + yin, zpos );
|
|
|
|
|
glVertex3f( startx + x, starty + y, zpos );
|
|
|
|
|
if( ii == 0 ) // Memorisation du point de d<>part du trac<61>
|
|
|
|
|
{
|
|
|
|
|
firstx = startx + x;
|
|
|
|
|
firsty = starty + y;
|
|
|
|
|
firstxin = startx + xin;
|
|
|
|
|
firstyin = starty + yin;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// trac<61> de l'arrondi a gauche (2ieme demi polygone a l'origine du segment)
|
|
|
|
|
for( ii = 0; ii <= 8; ii++ )
|
|
|
|
|
{
|
|
|
|
|
theta = -ii * 225;
|
|
|
|
|
x = 0.0;
|
|
|
|
|
y = width;
|
|
|
|
|
RotatePoint( &x, &y, -angle + theta );
|
|
|
|
|
xin = 0.0;
|
|
|
|
|
yin = holeradius;
|
|
|
|
|
RotatePoint( &xin, &yin, theta );
|
|
|
|
|
xin += holex;
|
|
|
|
|
RotatePoint( &xin, &yin, -angle );
|
|
|
|
|
glVertex3f( startx + xin, starty + yin, zpos );
|
|
|
|
|
glVertex3f( startx + x, starty + y, zpos );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
glVertex3f( firstxin, firstyin, zpos );
|
|
|
|
|
glVertex3f( firstx, firsty, zpos );
|
|
|
|
|
glEnd();
|
2007-05-06 16:03:28 +00:00
|
|
|
|
}
|
2008-03-10 22:46:44 +00:00
|
|
|
|
|
|
|
|
|
/********************************************************/
|
|
|
|
|
static void Draw3D_ArcSegment(double startx, double starty,
|
|
|
|
|
double endx, double endy,double width, double zpos)
|
|
|
|
|
{
|
|
|
|
|
int ii, slice = 36;
|
|
|
|
|
double x, y, hole, rayon;
|
|
|
|
|
int angle;
|
|
|
|
|
|
|
|
|
|
angle = static_cast<int>(atan2( startx - endx, starty - endy) * 1800 / M_PI) + 900;
|
|
|
|
|
rayon = hypot(startx - endx, starty - endy) + ( width / 2);
|
|
|
|
|
hole = rayon - width;
|
|
|
|
|
|
|
|
|
|
glBegin(GL_QUAD_STRIP);
|
|
|
|
|
for ( ii = 0; ii <= slice / 4; ii++ )
|
|
|
|
|
{
|
|
|
|
|
x = hole; y = 0.0;
|
|
|
|
|
RotatePoint(&x, &y, angle + (ii * 3600 / slice));
|
|
|
|
|
glVertex3f( x + startx, y + starty, zpos);
|
|
|
|
|
x = rayon; y = 0.0;
|
|
|
|
|
RotatePoint(&x, &y, angle + (ii * 3600 / slice));
|
|
|
|
|
glVertex3f( x + startx , y + starty, zpos);
|
|
|
|
|
}
|
|
|
|
|
glEnd();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/********************************************************/
|
|
|
|
|
static void Draw3D_CircleSegment(double startx, double starty,
|
|
|
|
|
double endx, double endy,double width, double zpos)
|
|
|
|
|
{
|
|
|
|
|
int ii, slice = 36;
|
|
|
|
|
double x, y, hole, rayon;
|
|
|
|
|
|
|
|
|
|
rayon = hypot(startx - endx, starty - endy) + ( width / 2);
|
|
|
|
|
hole = rayon - width;
|
|
|
|
|
|
|
|
|
|
glBegin(GL_QUAD_STRIP);
|
|
|
|
|
for ( ii = 0; ii <= slice; ii++ )
|
|
|
|
|
{
|
|
|
|
|
x = hole; y = 0.0;
|
|
|
|
|
RotatePoint(&x, &y, ii * 3600 / slice);
|
|
|
|
|
glVertex3f( x + startx, y + starty, zpos);
|
|
|
|
|
x = rayon; y = 0.0;
|
|
|
|
|
RotatePoint(&x, &y, ii * 3600 / slice);
|
|
|
|
|
glVertex3f( x + startx , y + starty, zpos);
|
|
|
|
|
}
|
|
|
|
|
glEnd();
|
|
|
|
|
}
|