Commit 63401f3d authored by jean-pierre charras's avatar jean-pierre charras

Rework on 3D viewer (work in progress): Disable or enable layers, grid or 3D...

Rework on 3D viewer (work in progress): Disable or enable layers, grid or 3D footprint shapes should be now faster.
parent c89d52ee
...@@ -78,7 +78,11 @@ EDA_3D_CANVAS::EDA_3D_CANVAS( EDA_3D_FRAME* parent, int* attribList ) : ...@@ -78,7 +78,11 @@ EDA_3D_CANVAS::EDA_3D_CANVAS( EDA_3D_FRAME* parent, int* attribList ) :
wxFULL_REPAINT_ON_RESIZE ) wxFULL_REPAINT_ON_RESIZE )
{ {
m_init = false; m_init = false;
m_gllist = 0;
// Clear all gl list identifiers:
for( int ii = GL_ID_BEGIN; ii < GL_ID_END; ii++ )
m_glLists[ii] = 0;
// Explicitly create a new rendering context instance for this canvas. // Explicitly create a new rendering context instance for this canvas.
m_glRC = new wxGLContext( this ); m_glRC = new wxGLContext( this );
...@@ -94,12 +98,25 @@ EDA_3D_CANVAS::~EDA_3D_CANVAS() ...@@ -94,12 +98,25 @@ EDA_3D_CANVAS::~EDA_3D_CANVAS()
} }
void EDA_3D_CANVAS::ClearLists() void EDA_3D_CANVAS::ClearLists( GLuint aGlList )
{ {
if( m_gllist > 0 ) if( aGlList )
glDeleteLists( m_gllist, 1 ); {
if( m_glLists[aGlList] > 0 )
glDeleteLists( m_glLists[aGlList], 1 );
m_glLists[aGlList] = 0;
return;
}
m_gllist = 0; for( int ii = GL_ID_BEGIN; ii < GL_ID_END; ii++ )
{
if( m_glLists[ii] > 0 )
glDeleteLists( m_glLists[ii], 1 );
m_glLists[ii] = 0;
}
} }
......
...@@ -50,14 +50,29 @@ class S3D_VERTEX; ...@@ -50,14 +50,29 @@ class S3D_VERTEX;
class SEGVIA; class SEGVIA;
class D_PAD; class D_PAD;
// We are using GL lists to store layers and other items
// to draw or not
// GL_LIST_ID are the GL lists indexes in m_glLists
enum GL_LIST_ID
{
GL_ID_BEGIN = 0,
GL_ID_AXIS = GL_ID_BEGIN, // list id for 3D axis
GL_ID_GRID, // list id for 3D grid
GL_ID_BOARD, // List id for copper layers
GL_ID_TECH_LAYERS, // List id for non copper layers (masks...)
GL_ID_AUX_LAYERS, // List id for user layers (draw, eco, comment)
GL_ID_3DSHAPES_SOLID, // List id for 3D shapes, non transparent entities
GL_ID_3DSHAPES_TRANSP, // List id for 3D shapes, transparent entities
GL_ID_END
};
class EDA_3D_CANVAS : public wxGLCanvas class EDA_3D_CANVAS : public wxGLCanvas
{ {
private: private:
bool m_init; bool m_init;
GLuint m_gllist; GLuint m_glLists[GL_ID_END]; // GL lists
wxGLContext* m_glRC; wxGLContext* m_glRC;
wxRealPoint m_draw3dOffset; // offset to draw the 3 mesh. wxRealPoint m_draw3dOffset; // offset to draw the 3D mesh.
double m_ZBottom; // position of the back layer double m_ZBottom; // position of the back layer
double m_ZTop; // position of the front layer double m_ZTop; // position of the front layer
...@@ -67,7 +82,15 @@ public: ...@@ -67,7 +82,15 @@ public:
EDA_3D_FRAME* Parent() { return (EDA_3D_FRAME*)GetParent(); } EDA_3D_FRAME* Parent() { return (EDA_3D_FRAME*)GetParent(); }
void ClearLists(); BOARD* GetBoard() { return Parent()->GetBoard(); }
/**
* Function ClearLists
* Clear the display list.
* @param aGlList = the list to clear.
* if 0 (default) all lists are cleared
*/
void ClearLists( GLuint aGlList = 0 );
// Event functions: // Event functions:
void OnPaint( wxPaintEvent& event ); void OnPaint( wxPaintEvent& event );
...@@ -92,7 +115,7 @@ public: ...@@ -92,7 +115,7 @@ public:
* Prepares the parameters of the OpenGL draw list * Prepares the parameters of the OpenGL draw list
* creates the OpenGL draw list items (board, grid ... * creates the OpenGL draw list items (board, grid ...
*/ */
GLuint CreateDrawGL_List(); void CreateDrawGL_List();
void InitGL(); void InitGL();
void SetLights(); void SetLights();
void SetOffset(double aPosX, double aPosY) void SetOffset(double aPosX, double aPosY)
...@@ -104,11 +127,40 @@ public: ...@@ -104,11 +127,40 @@ public:
/** /**
* Function BuildBoard3DView * Function BuildBoard3DView
* Called by CreateDrawGL_List() * Called by CreateDrawGL_List()
* Fills the OpenGL draw list with board items draw list. * Populates the OpenGL GL_ID_BOARD draw list with board items only on copper layers.
* 3D footprint shapes, tech layers and aux layers are not on this list
*/ */
void BuildBoard3DView(); void BuildBoard3DView();
void DrawGrid( double aGriSizeMM ); /**
* Function BuildTechLayers3DView
* Called by CreateDrawGL_List()
* Populates the OpenGL GL_ID_BOARD draw list with items on tech layers
*/
void BuildTechLayers3DView();
/**
* Function BuildFootprintShape3DList
* Called by CreateDrawGL_List()
* Fills the OpenGL GL_ID_3DSHAPES_SOLID and GL_ID_3DSHAPES_TRANSP
* draw lists with 3D footprint shapes
* @param aOpaqueList is the gl list for non transparent items
* @param aTransparentList is the gl list for non transparent items,
* which need to be drawn after all other items
*/
void BuildFootprintShape3DList( GLuint aOpaqueList,
GLuint aTransparentList);
/**
* Function BuildBoard3DAuxLayers
* Called by CreateDrawGL_List()
* Fills the OpenGL GL_ID_AUX_LAYERS draw list
* with items on aux layers only
*/
void BuildBoard3DAuxLayers();
void Draw3DGrid( double aGriSizeMM );
void Draw3DAxis();
void Draw3DViaHole( SEGVIA * aVia ); void Draw3DViaHole( SEGVIA * aVia );
void Draw3DPadHole( D_PAD * aPad ); void Draw3DPadHole( D_PAD * aPad );
......
...@@ -133,11 +133,45 @@ void EDA_3D_CANVAS::Redraw() ...@@ -133,11 +133,45 @@ void EDA_3D_CANVAS::Redraw()
glRotatef( g_Parm_3D_Visu.m_Rot[1], 0.0, 1.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 ); glRotatef( g_Parm_3D_Visu.m_Rot[2], 0.0, 0.0, 1.0 );
if( m_gllist ) if( ! m_glLists[GL_ID_BOARD] || ! m_glLists[GL_ID_TECH_LAYERS] )
glCallList( m_gllist );
else
CreateDrawGL_List(); CreateDrawGL_List();
if( g_Parm_3D_Visu.GetFlag( FL_AXIS ) && m_glLists[GL_ID_AXIS] )
glCallList( m_glLists[GL_ID_AXIS] );
// move the board in order to draw it with its center at 0,0 3D coordinates
glTranslatef( -g_Parm_3D_Visu.m_BoardPos.x * g_Parm_3D_Visu.m_BiuTo3Dunits,
-g_Parm_3D_Visu.m_BoardPos.y * g_Parm_3D_Visu.m_BiuTo3Dunits,
0.0F );
glCallList( m_glLists[GL_ID_BOARD] );
glCallList( m_glLists[GL_ID_TECH_LAYERS] );
if( g_Parm_3D_Visu.GetFlag( FL_COMMENTS ) || g_Parm_3D_Visu.GetFlag( FL_COMMENTS ) )
{
if( ! m_glLists[GL_ID_AUX_LAYERS] )
CreateDrawGL_List();
glCallList( m_glLists[GL_ID_AUX_LAYERS] );
}
if( g_Parm_3D_Visu.GetFlag( FL_GRID ) && m_glLists[GL_ID_GRID] )
glCallList( m_glLists[GL_ID_GRID] );
if( g_Parm_3D_Visu.GetFlag( FL_MODULE ) )
{
if( ! m_glLists[GL_ID_3DSHAPES_SOLID] )
CreateDrawGL_List();
glCallList( m_glLists[GL_ID_3DSHAPES_SOLID] );
// This list must be drawn last, because it contains the
// transparent gl objects, which should be drawn after all
// non tyransparent objects
glCallList( m_glLists[GL_ID_3DSHAPES_TRANSP] );
}
SwapBuffers(); SwapBuffers();
} }
...@@ -198,8 +232,7 @@ static inline void SetGLTechLayersColor( LAYER_NUM aLayer ) ...@@ -198,8 +232,7 @@ static inline void SetGLTechLayersColor( LAYER_NUM aLayer )
void EDA_3D_CANVAS::BuildBoard3DView() void EDA_3D_CANVAS::BuildBoard3DView()
{ {
PCB_BASE_FRAME* pcbframe = Parent()->Parent(); BOARD* pcb = GetBoard();
BOARD* pcb = pcbframe->GetBoard();
bool realistic_mode = g_Parm_3D_Visu.IsRealisticMode(); bool realistic_mode = g_Parm_3D_Visu.IsRealisticMode();
// Number of segments to draw a circle using segments // Number of segments to draw a circle using segments
...@@ -456,14 +489,74 @@ void EDA_3D_CANVAS::BuildBoard3DView() ...@@ -456,14 +489,74 @@ void EDA_3D_CANVAS::BuildBoard3DView()
Draw3D_SolidHorizontalPolyPolygons( bufferPcbOutlines, zpos + board_thickness/2, Draw3D_SolidHorizontalPolyPolygons( bufferPcbOutlines, zpos + board_thickness/2,
board_thickness, g_Parm_3D_Visu.m_BiuTo3Dunits ); board_thickness, g_Parm_3D_Visu.m_BiuTo3Dunits );
} }
}
void EDA_3D_CANVAS::BuildTechLayers3DView()
{
BOARD* pcb = GetBoard();
// Number of segments to draw a circle using segments
const int segcountforcircle = 16;
double correctionFactor = 1.0 / cos( M_PI / (segcountforcircle * 2) );
const int segcountLowQuality = 12; // segments to draw a circle with low quality
// to reduce time calculations
// for holes and items which do not need
// a fine representation
CPOLYGONS_LIST bufferPolys;
bufferPolys.reserve( 200000 ); // Reserve for large board (tracks mainly)
CPOLYGONS_LIST allLayerHoles; // Contains through holes, calculated only once
allLayerHoles.reserve( 20000 );
CPOLYGONS_LIST bufferPcbOutlines; // stores the board main outlines
// Build a polygon from edge cut items
wxString msg;
if( ! pcb->GetBoardPolygonOutlines( bufferPcbOutlines,
allLayerHoles, &msg ) )
{
msg << wxT("\n\n") <<
_("Unable to calculate the board outlines.\n"
"Therefore use the board boundary box.");
wxMessageBox( msg );
}
CPOLYGONS_LIST bufferZonesPolys;
bufferZonesPolys.reserve( 500000 ); // Reserve for large board ( copper zones mainly )
CPOLYGONS_LIST currLayerHoles; // Contains holes for the current layer
int thickness = g_Parm_3D_Visu.GetCopperThicknessBIU();
for( TRACK* track = pcb->m_Track; track != NULL; track = track->Next() )
{
// Add via hole
if( track->Type() == PCB_VIA_T )
{
int shape = track->GetShape();
int holediameter = track->GetDrillValue();
int hole_outer_radius = (holediameter + thickness) / 2;
if( shape == VIA_THROUGH )
TransformCircleToPolygon( allLayerHoles,
track->GetStart(), hole_outer_radius,
segcountLowQuality );
}
}
// draw graphic items, on technical layers
// draw graphic items, not on copper layers
KI_POLYGON_SET brdpolysetHoles; KI_POLYGON_SET brdpolysetHoles;
allLayerHoles.ExportTo( brdpolysetHoles ); allLayerHoles.ExportTo( brdpolysetHoles );
for( LAYER_NUM layer = FIRST_NON_COPPER_LAYER; layer <= LAST_NON_COPPER_LAYER; for( LAYER_NUM layer = FIRST_NON_COPPER_LAYER; layer <= LAST_NON_COPPER_LAYER;
layer++ ) layer++ )
{ {
// Skip user layers, which are not drawn here
if( IsUserLayer( layer) )
continue;
if( !Is3DLayerEnabled( layer ) ) if( !Is3DLayerEnabled( layer ) )
continue; continue;
...@@ -481,9 +574,7 @@ void EDA_3D_CANVAS::BuildBoard3DView() ...@@ -481,9 +574,7 @@ void EDA_3D_CANVAS::BuildBoard3DView()
{ {
case PCB_LINE_T: case PCB_LINE_T:
( (DRAWSEGMENT*) item )->TransformShapeWithClearanceToPolygon( ( (DRAWSEGMENT*) item )->TransformShapeWithClearanceToPolygon(
bufferPolys, 0, bufferPolys, 0, segcountforcircle, correctionFactor );
segcountforcircle,
correctionFactor );
break; break;
case PCB_TEXT_T: case PCB_TEXT_T:
...@@ -556,10 +647,8 @@ void EDA_3D_CANVAS::BuildBoard3DView() ...@@ -556,10 +647,8 @@ void EDA_3D_CANVAS::BuildBoard3DView()
currLayerPolyset += polyset; currLayerPolyset += polyset;
} }
SetGLTechLayersColor( layer );
int thickness = g_Parm_3D_Visu.GetLayerObjectThicknessBIU( layer ); int thickness = g_Parm_3D_Visu.GetLayerObjectThicknessBIU( layer );
int zpos = g_Parm_3D_Visu.GetLayerZcoordBIU( layer ); int zpos = g_Parm_3D_Visu.GetLayerZcoordBIU( layer );
glNormal3f( 0.0, 0.0, Get3DLayer_Z_Orientation( layer ) );
if( layer == EDGE_N ) if( layer == EDGE_N )
{ {
...@@ -582,58 +671,129 @@ void EDA_3D_CANVAS::BuildBoard3DView() ...@@ -582,58 +671,129 @@ void EDA_3D_CANVAS::BuildBoard3DView()
bufferPolys.RemoveAllContours(); bufferPolys.RemoveAllContours();
bufferPolys.ImportFrom( currLayerPolyset ); bufferPolys.ImportFrom( currLayerPolyset );
SetGLTechLayersColor( layer );
glNormal3f( 0.0, 0.0, Get3DLayer_Z_Orientation( layer ) );
Draw3D_SolidHorizontalPolyPolygons( bufferPolys, zpos, Draw3D_SolidHorizontalPolyPolygons( bufferPolys, zpos,
thickness, g_Parm_3D_Visu.m_BiuTo3Dunits ); thickness, g_Parm_3D_Visu.m_BiuTo3Dunits );
} }
}
// draw modules 3D shapes /**
if( g_Parm_3D_Visu.GetFlag( FL_MODULE ) ) * Function BuildBoard3DAuxLayers
* Called by CreateDrawGL_List()
* Fills the OpenGL GL_ID_BOARD draw list with items
* on aux layers only
*/
void EDA_3D_CANVAS::BuildBoard3DAuxLayers()
{
const int segcountforcircle = 16;
double correctionFactor = 1.0 / cos( M_PI / (segcountforcircle * 2) );
BOARD* pcb = GetBoard();
CPOLYGONS_LIST bufferPolys;
bufferPolys.reserve( 5000 ); // Reserve for items not on board
for( LAYER_NUM layer = FIRST_USER_LAYER; layer <= LAST_USER_LAYER;
layer++ )
{ {
for( MODULE* module = pcb->m_Modules; module; module = module->Next() ) if( !Is3DLayerEnabled( layer ) )
module->ReadAndInsert3DComponentShape( this ); continue;
bufferPolys.RemoveAllContours();
for( BOARD_ITEM* item = pcb->m_Drawings; item; item = item->Next() )
{
if( !item->IsOnLayer( layer ) )
continue;
switch( item->Type() )
{
case PCB_LINE_T:
( (DRAWSEGMENT*) item )->TransformShapeWithClearanceToPolygon(
bufferPolys, 0, segcountforcircle, correctionFactor );
break;
case PCB_TEXT_T:
( (TEXTE_PCB*) item )->TransformShapeWithClearanceToPolygonSet(
bufferPolys, 0, segcountforcircle, correctionFactor );
break;
default:
break;
} }
} }
for( MODULE* module = pcb->m_Modules; module != NULL; module = module->Next() )
{
module->TransformPadsShapesWithClearanceToPolygon( layer,
bufferPolys,
0,
segcountforcircle,
correctionFactor );
module->TransformGraphicShapesWithClearanceToPolygonSet( layer,
bufferPolys,
0,
segcountforcircle,
correctionFactor );
}
// bufferPolys contains polygons to merge. Many overlaps .
// Calculate merged polygons and remove pads and vias holes
if( bufferPolys.GetCornersCount() == 0 )
continue;
KI_POLYGON_SET currLayerPolyset;
KI_POLYGON_SET polyset;
bufferPolys.ExportTo( polyset );
currLayerPolyset += polyset;
int thickness = g_Parm_3D_Visu.GetLayerObjectThicknessBIU( layer );
int zpos = g_Parm_3D_Visu.GetLayerZcoordBIU( layer );
// for Draw3D_SolidHorizontalPolyPolygons,
// zpos it the middle between bottom and top sides.
// However for top layers, zpos should be the bottom layer pos,
// and for bottom layers, zpos should be the top layer pos.
if( Get3DLayer_Z_Orientation( layer ) > 0 )
zpos += thickness/2;
else
zpos -= thickness/2 ;
GLuint EDA_3D_CANVAS::CreateDrawGL_List() bufferPolys.RemoveAllContours();
bufferPolys.ImportFrom( currLayerPolyset );
SetGLTechLayersColor( layer );
glNormal3f( 0.0, 0.0, Get3DLayer_Z_Orientation( layer ) );
Draw3D_SolidHorizontalPolyPolygons( bufferPolys, zpos,
thickness, g_Parm_3D_Visu.m_BiuTo3Dunits );
}
}
void EDA_3D_CANVAS::CreateDrawGL_List()
{ {
PCB_BASE_FRAME* pcbframe = Parent()->Parent(); BOARD* pcb = GetBoard();
BOARD* pcb = pcbframe->GetBoard();
wxBusyCursor dummy; wxBusyCursor dummy;
m_gllist = glGenLists( 1 );
// Build 3D board parameters: // Build 3D board parameters:
g_Parm_3D_Visu.InitSettings( pcb ); g_Parm_3D_Visu.InitSettings( pcb );
glNewList( m_gllist, GL_COMPILE_AND_EXECUTE );
glColorMaterial( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE ); glColorMaterial( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE );
// draw axis // Create axis gl list (if it is not shown, the list will be not called
if( g_Parm_3D_Visu.GetFlag( FL_AXIS ) ) Draw3DAxis();
// Create grid gl list
if( ! m_glLists[GL_ID_GRID] )
{ {
glEnable( GL_COLOR_MATERIAL ); m_glLists[GL_ID_GRID] = glGenLists( 1 );
SetGLColor( WHITE ); glNewList( m_glLists[GL_ID_GRID], GL_COMPILE );
glBegin( GL_LINES );
glNormal3f( 0.0f, 0.0f, 1.0f ); // Normal is Z axis Draw3DGrid( g_Parm_3D_Visu.m_3D_Grid );
glVertex3f( 0.0f, 0.0f, 0.0f ); glEndList();
glVertex3f( 1.0f, 0.0f, 0.0f ); // X axis
glVertex3f( 0.0f, 0.0f, 0.0f );
glVertex3f( 0.0f, -1.0f, 0.0f ); // Y axis
glNormal3f( 1.0f, 0.0f, 0.0f ); // Normal is Y axis
glVertex3f( 0.0f, 0.0f, 0.0f );
glVertex3f( 0.0f, 0.0f, 0.3f ); // Z axis
glEnd();
} }
// move the board in order to draw it with its center at 0,0 3D coordinates // Create Board full gl lists:
glTranslatef( -g_Parm_3D_Visu.m_BoardPos.x * g_Parm_3D_Visu.m_BiuTo3Dunits,
-g_Parm_3D_Visu.m_BoardPos.y * g_Parm_3D_Visu.m_BiuTo3Dunits,
0.0F );
// Draw Board:
// For testing purpose only, display calculation time to generate 3D data // For testing purpose only, display calculation time to generate 3D data
// #define PRINT_CALCULATION_TIME // #define PRINT_CALCULATION_TIME
...@@ -641,13 +801,45 @@ GLuint EDA_3D_CANVAS::CreateDrawGL_List() ...@@ -641,13 +801,45 @@ GLuint EDA_3D_CANVAS::CreateDrawGL_List()
unsigned strtime = GetRunningMicroSecs(); unsigned strtime = GetRunningMicroSecs();
#endif #endif
if( ! m_glLists[GL_ID_BOARD] )
{
m_glLists[GL_ID_BOARD] = glGenLists( 1 );
glNewList( m_glLists[GL_ID_BOARD], GL_COMPILE );
BuildBoard3DView(); BuildBoard3DView();
glEndList();
}
// Draw grid if( ! m_glLists[GL_ID_TECH_LAYERS] )
if( g_Parm_3D_Visu.GetFlag( FL_GRID ) ) {
DrawGrid( g_Parm_3D_Visu.m_3D_Grid ); m_glLists[GL_ID_TECH_LAYERS] = glGenLists( 1 );
glNewList( m_glLists[GL_ID_TECH_LAYERS], GL_COMPILE );
BuildTechLayers3DView();
glEndList();
}
if( ! m_glLists[GL_ID_AUX_LAYERS] )
{
m_glLists[GL_ID_AUX_LAYERS] = glGenLists( 1 );
glNewList( m_glLists[GL_ID_AUX_LAYERS], GL_COMPILE );
BuildBoard3DAuxLayers();
glEndList(); glEndList();
}
// draw modules 3D shapes
if( ! m_glLists[GL_ID_3DSHAPES_SOLID] && g_Parm_3D_Visu.GetFlag( FL_MODULE ) )
{
m_glLists[GL_ID_3DSHAPES_SOLID] = glGenLists( 1 );
// GL_ID_3DSHAPES_TRANSP is an auxiliary list for 3D shapes;
// Ensure it is cleared before rebuilding it
if( m_glLists[GL_ID_3DSHAPES_TRANSP] )
glDeleteLists( m_glLists[GL_ID_3DSHAPES_TRANSP], 1 );
m_glLists[GL_ID_3DSHAPES_TRANSP] = glGenLists( 1 );
BuildFootprintShape3DList( m_glLists[GL_ID_3DSHAPES_SOLID],
m_glLists[GL_ID_3DSHAPES_TRANSP] );
}
// Test for errors // Test for errors
CheckGLError(); CheckGLError();
...@@ -658,14 +850,51 @@ GLuint EDA_3D_CANVAS::CreateDrawGL_List() ...@@ -658,14 +850,51 @@ GLuint EDA_3D_CANVAS::CreateDrawGL_List()
msg.Printf( "Built data %.1f ms", (double) (endtime - strtime) / 1000 ); msg.Printf( "Built data %.1f ms", (double) (endtime - strtime) / 1000 );
Parent()->SetStatusText( msg, 0 ); Parent()->SetStatusText( msg, 0 );
#endif #endif
}
void EDA_3D_CANVAS::BuildFootprintShape3DList( GLuint aOpaqueList,
GLuint aTransparentList)
{
// aOpaqueList is the gl list for non transparent items
// aTransparentList is the gl list for non transparent items,
// which need to be drawn after all other items
BOARD* pcb = GetBoard();
glNewList( m_glLists[GL_ID_3DSHAPES_SOLID], GL_COMPILE );
for( MODULE* module = pcb->m_Modules; module; module = module->Next() )
module->ReadAndInsert3DComponentShape( this );
return m_gllist; glEndList();
} }
void EDA_3D_CANVAS::Draw3DAxis()
{
if( ! m_glLists[GL_ID_AXIS] )
{
m_glLists[GL_ID_AXIS] = glGenLists( 1 );
glNewList( m_glLists[GL_ID_AXIS], GL_COMPILE );
glEnable( GL_COLOR_MATERIAL );
SetGLColor( WHITE );
glBegin( GL_LINES );
glNormal3f( 0.0f, 0.0f, 1.0f ); // Normal is Z axis
glVertex3f( 0.0f, 0.0f, 0.0f );
glVertex3f( 1.0f, 0.0f, 0.0f ); // X axis
glVertex3f( 0.0f, 0.0f, 0.0f );
glVertex3f( 0.0f, -1.0f, 0.0f ); // Y axis
glNormal3f( 1.0f, 0.0f, 0.0f ); // Normal is Y axis
glVertex3f( 0.0f, 0.0f, 0.0f );
glVertex3f( 0.0f, 0.0f, 0.3f ); // Z axis
glEnd();
glEndList();
}
}
// draw a 3D grid: an horizontal grid (XY plane and Z = 0, // draw a 3D grid: an horizontal grid (XY plane and Z = 0,
// and a vertical grid (XZ plane and Y = 0) // and a vertical grid (XZ plane and Y = 0)
void EDA_3D_CANVAS::DrawGrid( double aGriSizeMM ) void EDA_3D_CANVAS::Draw3DGrid( double aGriSizeMM )
{ {
double zpos = 0.0; double zpos = 0.0;
EDA_COLOR_T gridcolor = DARKGRAY; // Color of grid lines EDA_COLOR_T gridcolor = DARKGRAY; // Color of grid lines
......
...@@ -45,6 +45,8 @@ static const wxString keyBgColor_Green( wxT( "BgColor_Green" ) ); ...@@ -45,6 +45,8 @@ static const wxString keyBgColor_Green( wxT( "BgColor_Green" ) );
static const wxString keyBgColor_Blue( wxT( "BgColor_Blue" ) ); static const wxString keyBgColor_Blue( wxT( "BgColor_Blue" ) );
static const wxString keyShowRealisticMode( wxT( "ShowRealisticMode" ) ); static const wxString keyShowRealisticMode( wxT( "ShowRealisticMode" ) );
static const wxString keyShowAxis( wxT( "ShowAxis" ) ); static const wxString keyShowAxis( wxT( "ShowAxis" ) );
static const wxString keyShowGrid( wxT( "ShowGrid3D" ) );
static const wxString keyShowGridSize( wxT( "Grid3DSize" ) );
static const wxString keyShowZones( wxT( "ShowZones" ) ); static const wxString keyShowZones( wxT( "ShowZones" ) );
static const wxString keyShowFootprints( wxT( "ShowFootprints" ) ); static const wxString keyShowFootprints( wxT( "ShowFootprints" ) );
static const wxString keyShowCopperThickness( wxT( "ShowCopperThickness" ) ); static const wxString keyShowCopperThickness( wxT( "ShowCopperThickness" ) );
...@@ -148,9 +150,9 @@ void EDA_3D_FRAME::GetSettings() ...@@ -148,9 +150,9 @@ void EDA_3D_FRAME::GetSettings()
{ {
EDA_BASE_FRAME::LoadSettings(); EDA_BASE_FRAME::LoadSettings();
config->Read( keyBgColor_Red, &g_Parm_3D_Visu.m_BgColor.m_Red, 0.0 ); config->Read( keyBgColor_Red, &prms.m_BgColor.m_Red, 0.0 );
config->Read( keyBgColor_Green, &g_Parm_3D_Visu.m_BgColor.m_Green, 0.0 ); config->Read( keyBgColor_Green, &prms.m_BgColor.m_Green, 0.0 );
config->Read( keyBgColor_Blue, &g_Parm_3D_Visu.m_BgColor.m_Blue, 0.0 ); config->Read( keyBgColor_Blue, &prms.m_BgColor.m_Blue, 0.0 );
bool tmp; bool tmp;
config->Read( keyShowRealisticMode, &tmp, false ); config->Read( keyShowRealisticMode, &tmp, false );
...@@ -159,6 +161,12 @@ void EDA_3D_FRAME::GetSettings() ...@@ -159,6 +161,12 @@ void EDA_3D_FRAME::GetSettings()
config->Read( keyShowAxis, &tmp, true ); config->Read( keyShowAxis, &tmp, true );
prms.SetFlag( FL_AXIS, tmp ); prms.SetFlag( FL_AXIS, tmp );
config->Read( keyShowGrid, &tmp, true );
prms.SetFlag( FL_GRID, tmp );
config->Read( keyShowGridSize, &prms.m_3D_Grid, 10.0 );
prms.SetFlag( FL_MODULE, tmp );
config->Read( keyShowFootprints, &tmp, true ); config->Read( keyShowFootprints, &tmp, true );
prms.SetFlag( FL_MODULE, tmp ); prms.SetFlag( FL_MODULE, tmp );
...@@ -201,12 +209,14 @@ void EDA_3D_FRAME::SaveSettings() ...@@ -201,12 +209,14 @@ void EDA_3D_FRAME::SaveSettings()
EDA_BASE_FRAME::SaveSettings(); EDA_BASE_FRAME::SaveSettings();
config->Write( keyBgColor_Red, g_Parm_3D_Visu.m_BgColor.m_Red );
config->Write( keyBgColor_Green, g_Parm_3D_Visu.m_BgColor.m_Green );
config->Write( keyBgColor_Blue, g_Parm_3D_Visu.m_BgColor.m_Blue );
class INFO3D_VISU& prms = g_Parm_3D_Visu; class INFO3D_VISU& prms = g_Parm_3D_Visu;
config->Write( keyBgColor_Red, prms.m_BgColor.m_Red );
config->Write( keyBgColor_Green, prms.m_BgColor.m_Green );
config->Write( keyBgColor_Blue, prms.m_BgColor.m_Blue );
config->Write( keyShowRealisticMode, prms.GetFlag( FL_USE_REALISTIC_MODE ) ); config->Write( keyShowRealisticMode, prms.GetFlag( FL_USE_REALISTIC_MODE ) );
config->Write( keyShowAxis, prms.GetFlag( FL_AXIS ) ); config->Write( keyShowAxis, prms.GetFlag( FL_AXIS ) );
config->Write( keyShowGrid, prms.GetFlag( FL_GRID ) );
config->Write( keyShowGridSize, prms.m_3D_Grid );
config->Write( keyShowFootprints, prms.GetFlag( FL_MODULE ) ); config->Write( keyShowFootprints, prms.GetFlag( FL_MODULE ) );
config->Write( keyShowCopperThickness, prms.GetFlag( FL_USE_COPPER_THICKNESS ) ); config->Write( keyShowCopperThickness, prms.GetFlag( FL_USE_COPPER_THICKNESS ) );
config->Write( keyShowZones, prms.GetFlag( FL_ZONE ) ); config->Write( keyShowZones, prms.GetFlag( FL_ZONE ) );
...@@ -364,52 +374,52 @@ void EDA_3D_FRAME::Process_Special_Functions( wxCommandEvent& event ) ...@@ -364,52 +374,52 @@ void EDA_3D_FRAME::Process_Special_Functions( wxCommandEvent& event )
case ID_MENU3D_AXIS_ONOFF: case ID_MENU3D_AXIS_ONOFF:
g_Parm_3D_Visu.SetFlag( FL_AXIS, isChecked ); g_Parm_3D_Visu.SetFlag( FL_AXIS, isChecked );
NewDisplay(); m_canvas->Refresh();
return; return;
case ID_MENU3D_MODULE_ONOFF: case ID_MENU3D_MODULE_ONOFF:
g_Parm_3D_Visu.SetFlag( FL_MODULE, isChecked ); g_Parm_3D_Visu.SetFlag( FL_MODULE, isChecked );
NewDisplay(); m_canvas->Refresh();
return; return;
case ID_MENU3D_USE_COPPER_THICKNESS: case ID_MENU3D_USE_COPPER_THICKNESS:
g_Parm_3D_Visu.SetFlag( FL_USE_COPPER_THICKNESS, isChecked ); g_Parm_3D_Visu.SetFlag( FL_USE_COPPER_THICKNESS, isChecked );
NewDisplay(); NewDisplay(GL_ID_BOARD);
return; return;
case ID_MENU3D_ZONE_ONOFF: case ID_MENU3D_ZONE_ONOFF:
g_Parm_3D_Visu.SetFlag( FL_ZONE, isChecked ); g_Parm_3D_Visu.SetFlag( FL_ZONE, isChecked );
NewDisplay(); NewDisplay(GL_ID_BOARD);
return; return;
case ID_MENU3D_ADHESIVE_ONOFF: case ID_MENU3D_ADHESIVE_ONOFF:
g_Parm_3D_Visu.SetFlag( FL_ADHESIVE, isChecked ); g_Parm_3D_Visu.SetFlag( FL_ADHESIVE, isChecked );
NewDisplay(); NewDisplay(GL_ID_TECH_LAYERS);
return; return;
case ID_MENU3D_SILKSCREEN_ONOFF: case ID_MENU3D_SILKSCREEN_ONOFF:
g_Parm_3D_Visu.SetFlag( FL_SILKSCREEN, isChecked ); g_Parm_3D_Visu.SetFlag( FL_SILKSCREEN, isChecked );
NewDisplay(); NewDisplay(GL_ID_TECH_LAYERS);
return; return;
case ID_MENU3D_SOLDER_MASK_ONOFF: case ID_MENU3D_SOLDER_MASK_ONOFF:
g_Parm_3D_Visu.SetFlag( FL_SOLDERMASK, isChecked ); g_Parm_3D_Visu.SetFlag( FL_SOLDERMASK, isChecked );
NewDisplay(); NewDisplay(GL_ID_TECH_LAYERS);
return; return;
case ID_MENU3D_SOLDER_PASTE_ONOFF: case ID_MENU3D_SOLDER_PASTE_ONOFF:
g_Parm_3D_Visu.SetFlag( FL_SOLDERPASTE, isChecked ); g_Parm_3D_Visu.SetFlag( FL_SOLDERPASTE, isChecked );
NewDisplay(); NewDisplay(GL_ID_TECH_LAYERS);
return; return;
case ID_MENU3D_COMMENTS_ONOFF: case ID_MENU3D_COMMENTS_ONOFF:
g_Parm_3D_Visu.SetFlag( FL_COMMENTS, isChecked ); g_Parm_3D_Visu.SetFlag( FL_COMMENTS, isChecked );
NewDisplay(); NewDisplay(GL_ID_AUX_LAYERS);
return; return;
case ID_MENU3D_ECO_ONOFF: case ID_MENU3D_ECO_ONOFF:
g_Parm_3D_Visu.SetFlag( FL_ECO, isChecked ); g_Parm_3D_Visu.SetFlag( FL_ECO, isChecked );
NewDisplay(); NewDisplay(GL_ID_AUX_LAYERS);
return; return;
default: default:
...@@ -434,7 +444,6 @@ void EDA_3D_FRAME::On3DGridSelection( wxCommandEvent& event ) ...@@ -434,7 +444,6 @@ void EDA_3D_FRAME::On3DGridSelection( wxCommandEvent& event )
GetMenuBar()->Check( ii, false ); GetMenuBar()->Check( ii, false );
} }
switch( id ) switch( id )
{ {
case ID_MENU3D_GRID_NOGRID: case ID_MENU3D_GRID_NOGRID:
...@@ -466,18 +475,17 @@ void EDA_3D_FRAME::On3DGridSelection( wxCommandEvent& event ) ...@@ -466,18 +475,17 @@ void EDA_3D_FRAME::On3DGridSelection( wxCommandEvent& event )
return; return;
} }
NewDisplay(); NewDisplay( GL_ID_GRID );
} }
void EDA_3D_FRAME::NewDisplay() void EDA_3D_FRAME::NewDisplay( GLuint aGlList )
{ {
m_reloadRequest = false; m_reloadRequest = false;
m_canvas->ClearLists(); m_canvas->ClearLists( aGlList );
m_canvas->CreateDrawGL_List(); m_canvas->CreateDrawGL_List();
// m_canvas->InitGL();
m_canvas->Refresh( true ); m_canvas->Refresh( true );
m_canvas->DisplayStatus(); m_canvas->DisplayStatus();
} }
...@@ -507,6 +515,9 @@ void EDA_3D_FRAME::Set3DBgColor() ...@@ -507,6 +515,9 @@ void EDA_3D_FRAME::Set3DBgColor()
newcolor = wxGetColourFromUser( this, oldcolor ); newcolor = wxGetColourFromUser( this, oldcolor );
if( ! newcolor.IsOk() ) // Happens on cancel dialog
return;
if( newcolor != oldcolor ) if( newcolor != oldcolor )
{ {
g_Parm_3D_Visu.m_BgColor.m_Red = (double) newcolor.Red() / 255.0; g_Parm_3D_Visu.m_BgColor.m_Red = (double) newcolor.Red() / 255.0;
...@@ -515,3 +526,8 @@ void EDA_3D_FRAME::Set3DBgColor() ...@@ -515,3 +526,8 @@ void EDA_3D_FRAME::Set3DBgColor()
NewDisplay(); NewDisplay();
} }
} }
BOARD* EDA_3D_FRAME::GetBoard()
{
return Parent()->GetBoard();
}
...@@ -167,13 +167,22 @@ void EDA_3D_FRAME::CreateMenuBar() ...@@ -167,13 +167,22 @@ void EDA_3D_FRAME::CreateMenuBar()
AddMenuItem( prefsMenu, gridlistMenu, ID_MENU3D_GRID, AddMenuItem( prefsMenu, gridlistMenu, ID_MENU3D_GRID,
_( "3D Grid" ), KiBitmap( grid_xpm ) ); _( "3D Grid" ), KiBitmap( grid_xpm ) );
gridlistMenu->Append( ID_MENU3D_GRID_NOGRID, _( "No 3D Grid" ), wxEmptyString, true ); gridlistMenu->Append( ID_MENU3D_GRID_NOGRID, _( "No 3D Grid" ), wxEmptyString, true );
gridlistMenu->Check( ID_MENU3D_GRID_NOGRID, true );
gridlistMenu->Append( ID_MENU3D_GRID_10_MM, _( "3D Grid 10 mm" ), wxEmptyString, true ); gridlistMenu->Append( ID_MENU3D_GRID_10_MM, _( "3D Grid 10 mm" ), wxEmptyString, true );
gridlistMenu->Append( ID_MENU3D_GRID_5_MM, _( "3D Grid 5 mm" ), wxEmptyString, true ); gridlistMenu->Append( ID_MENU3D_GRID_5_MM, _( "3D Grid 5 mm" ), wxEmptyString, true );
gridlistMenu->Append( ID_MENU3D_GRID_2P5_MM, _( "3D Grid 2.5 mm" ), wxEmptyString, true ); gridlistMenu->Append( ID_MENU3D_GRID_2P5_MM, _( "3D Grid 2.5 mm" ), wxEmptyString, true );
gridlistMenu->Append( ID_MENU3D_GRID_1_MM, _( "3D Grid 1 mm" ), wxEmptyString, true ); gridlistMenu->Append( ID_MENU3D_GRID_1_MM, _( "3D Grid 1 mm" ), wxEmptyString, true );
// If the grid is on, check the corresponding menuitem showing the grid size
if( g_Parm_3D_Visu.GetFlag( FL_GRID ) )
{
gridlistMenu->Check( ID_MENU3D_GRID_10_MM, g_Parm_3D_Visu.m_3D_Grid == 10.0 );
gridlistMenu->Check( ID_MENU3D_GRID_5_MM, g_Parm_3D_Visu.m_3D_Grid == 5.0 );
gridlistMenu->Check( ID_MENU3D_GRID_2P5_MM, g_Parm_3D_Visu.m_3D_Grid == 2.5 );
gridlistMenu->Check( ID_MENU3D_GRID_1_MM, g_Parm_3D_Visu.m_3D_Grid == 1.0 );
}
else
gridlistMenu->Check( ID_MENU3D_GRID_NOGRID, true );
prefsMenu->AppendSeparator(); prefsMenu->AppendSeparator();
AddMenuItem( prefsMenu, ID_MENU3D_SHOW_BOARD_BODY, AddMenuItem( prefsMenu, ID_MENU3D_SHOW_BOARD_BODY,
......
...@@ -78,6 +78,8 @@ public: ...@@ -78,6 +78,8 @@ public:
PCB_BASE_FRAME* Parent() { return (PCB_BASE_FRAME*)GetParent(); } PCB_BASE_FRAME* Parent() { return (PCB_BASE_FRAME*)GetParent(); }
BOARD* GetBoard();
/** /**
* Function ReloadRequest * Function ReloadRequest
* must be called when reloading data from Pcbnew is needed * must be called when reloading data from Pcbnew is needed
...@@ -93,8 +95,10 @@ public: ...@@ -93,8 +95,10 @@ public:
* Function NewDisplay * Function NewDisplay
* Rebuild the display list. * Rebuild the display list.
* must be called when 3D opengl data is modified * must be called when 3D opengl data is modified
* @param aGlList = the list to rebuild.
* if 0 (default) all lists are rebuilt
*/ */
void NewDisplay(); void NewDisplay( GLuint aGlList = 0 );
void SetDefaultFileName(const wxString &aFn) { m_defaultFileName = aFn; } void SetDefaultFileName(const wxString &aFn) { m_defaultFileName = aFn; }
const wxString &GetDefaultFileName() const { return m_defaultFileName; } const wxString &GetDefaultFileName() const { return m_defaultFileName; }
......
...@@ -74,7 +74,6 @@ enum DISPLAY3D_FLG { ...@@ -74,7 +74,6 @@ enum DISPLAY3D_FLG {
FL_LAST FL_LAST
}; };
class INFO3D_VISU class INFO3D_VISU
{ {
public: public:
......
...@@ -63,6 +63,8 @@ typedef int LAYER_NUM; ...@@ -63,6 +63,8 @@ typedef int LAYER_NUM;
#define NB_COPPER_LAYERS (LAST_COPPER_LAYER - FIRST_COPPER_LAYER + 1) #define NB_COPPER_LAYERS (LAST_COPPER_LAYER - FIRST_COPPER_LAYER + 1)
#define FIRST_NON_COPPER_LAYER 16 #define FIRST_NON_COPPER_LAYER 16
#define FIRST_TECHNICAL_LAYER 16
#define FIRST_USER_LAYER 24
#define ADHESIVE_N_BACK 16 #define ADHESIVE_N_BACK 16
#define ADHESIVE_N_FRONT 17 #define ADHESIVE_N_FRONT 17
#define SOLDERPASTE_N_BACK 18 #define SOLDERPASTE_N_BACK 18
...@@ -77,6 +79,8 @@ typedef int LAYER_NUM; ...@@ -77,6 +79,8 @@ typedef int LAYER_NUM;
#define ECO2_N 27 #define ECO2_N 27
#define EDGE_N 28 #define EDGE_N 28
#define LAST_NON_COPPER_LAYER 28 #define LAST_NON_COPPER_LAYER 28
#define LAST_TECHNICAL_LAYER 23
#define LAST_USER_LAYER 27
#define NB_PCB_LAYERS (LAST_NON_COPPER_LAYER + 1) #define NB_PCB_LAYERS (LAST_NON_COPPER_LAYER + 1)
#define UNUSED_LAYER_29 29 #define UNUSED_LAYER_29 29
#define UNUSED_LAYER_30 30 #define UNUSED_LAYER_30 30
...@@ -128,13 +132,16 @@ typedef unsigned LAYER_MSK; ...@@ -128,13 +132,16 @@ typedef unsigned LAYER_MSK;
#define ALL_CU_LAYERS 0x0000FFFF #define ALL_CU_LAYERS 0x0000FFFF
#define INTERNAL_CU_LAYERS 0x00007FFE #define INTERNAL_CU_LAYERS 0x00007FFE
#define EXTERNAL_CU_LAYERS 0x00008001 #define EXTERNAL_CU_LAYERS 0x00008001
#define FRONT_AUX_LAYERS (SILKSCREEN_LAYER_FRONT | SOLDERMASK_LAYER_FRONT \ #define FRONT_TECH_LAYERS (SILKSCREEN_LAYER_FRONT | SOLDERMASK_LAYER_FRONT \
| ADHESIVE_LAYER_FRONT | SOLDERPASTE_LAYER_FRONT) | ADHESIVE_LAYER_FRONT | SOLDERPASTE_LAYER_FRONT)
#define BACK_AUX_LAYERS (SILKSCREEN_LAYER_BACK | SOLDERMASK_LAYER_BACK \ #define BACK_TECH_LAYERS (SILKSCREEN_LAYER_BACK | SOLDERMASK_LAYER_BACK \
| ADHESIVE_LAYER_BACK | SOLDERPASTE_LAYER_BACK) | ADHESIVE_LAYER_BACK | SOLDERPASTE_LAYER_BACK)
#define ALL_AUX_LAYERS (FRONT_AUX_LAYERS | BACK_AUX_LAYERS) #define ALL_TECH_LAYERS (FRONT_TECH_LAYERS | BACK_TECH_LAYERS)
#define BACK_LAYERS (LAYER_BACK | BACK_AUX_LAYERS) #define BACK_LAYERS (LAYER_BACK | BACK_TECH_LAYERS)
#define FRONT_LAYERS (LAYER_FRONT | FRONT_AUX_LAYERS) #define FRONT_LAYERS (LAYER_FRONT | FRONT_TECH_LAYERS)
#define ALL_USER_LAYERS (DRAW_LAYER | COMMENT_LAYER |\
ECO1_LAYER | ECO2_LAYER )
#define NO_LAYERS 0x00000000 #define NO_LAYERS 0x00000000
...@@ -329,8 +336,18 @@ inline bool IsCopperLayer( LAYER_NUM aLayer ) ...@@ -329,8 +336,18 @@ inline bool IsCopperLayer( LAYER_NUM aLayer )
*/ */
inline bool IsNonCopperLayer( LAYER_NUM aLayer ) inline bool IsNonCopperLayer( LAYER_NUM aLayer )
{ {
return aLayer >= FIRST_NON_COPPER_LAYER return aLayer >= FIRST_NON_COPPER_LAYER && aLayer <= LAST_NON_COPPER_LAYER;
&& aLayer <= LAST_NON_COPPER_LAYER; }
/**
* Function IsUserLayer
* tests whether a layer is a non copper and a non tech layer
* @param aLayer = Layer to test
* @return true if aLayer is a user layer
*/
inline bool IsUserLayer( LAYER_NUM aLayer )
{
return aLayer >= FIRST_USER_LAYER && aLayer <= LAST_USER_LAYER;
} }
/* IMPORTANT: If a layer is not a front layer not necessarily is true /* IMPORTANT: If a layer is not a front layer not necessarily is true
......
...@@ -176,19 +176,19 @@ static const LAYER_MSK presets[] = ...@@ -176,19 +176,19 @@ static const LAYER_MSK presets[] =
NO_LAYERS, // shift the array index up by one, matches with "Custom". NO_LAYERS, // shift the array index up by one, matches with "Custom".
// "Two layers, parts on Front only" // "Two layers, parts on Front only"
EDGE_LAYER | LAYER_FRONT | LAYER_BACK | FRONT_AUX_LAYERS, EDGE_LAYER | LAYER_FRONT | LAYER_BACK | FRONT_TECH_LAYERS,
// "Two layers, parts on Back only", // "Two layers, parts on Back only",
EDGE_LAYER | LAYER_FRONT | LAYER_BACK | BACK_AUX_LAYERS, EDGE_LAYER | LAYER_FRONT | LAYER_BACK | BACK_TECH_LAYERS,
// "Two layers, parts on Front and Back", // "Two layers, parts on Front and Back",
EDGE_LAYER | LAYER_FRONT | LAYER_BACK | ALL_AUX_LAYERS, EDGE_LAYER | LAYER_FRONT | LAYER_BACK | ALL_TECH_LAYERS,
// "Four layers, parts on Front only" // "Four layers, parts on Front only"
EDGE_LAYER | LAYER_FRONT | LAYER_BACK | LAYER_2 | LAYER_3 | FRONT_AUX_LAYERS, EDGE_LAYER | LAYER_FRONT | LAYER_BACK | LAYER_2 | LAYER_3 | FRONT_TECH_LAYERS,
// "Four layers, parts on Front and Back" // "Four layers, parts on Front and Back"
EDGE_LAYER | LAYER_FRONT | LAYER_BACK | LAYER_2 | LAYER_3 | ALL_AUX_LAYERS, EDGE_LAYER | LAYER_FRONT | LAYER_BACK | LAYER_2 | LAYER_3 | ALL_TECH_LAYERS,
// "All layers on", // "All layers on",
ALL_LAYERS, ALL_LAYERS,
......
...@@ -246,7 +246,7 @@ void DIALOG_PLOT::OnPopUpLayers( wxCommandEvent& event ) ...@@ -246,7 +246,7 @@ void DIALOG_PLOT::OnPopUpLayers( wxCommandEvent& event )
for( i = 0; i < m_layerList.size(); i++ ) for( i = 0; i < m_layerList.size(); i++ )
{ {
LAYER_MSK layermask = GetLayerMask( m_layerList[ i ] ); LAYER_MSK layermask = GetLayerMask( m_layerList[ i ] );
if( layermask & ( ALL_CU_LAYERS | ALL_AUX_LAYERS ) ) if( layermask & ( ALL_CU_LAYERS | ALL_TECH_LAYERS ) )
m_layerCheckListBox->Check( i, true ); m_layerCheckListBox->Check( i, true );
else else
m_layerCheckListBox->Check( i, false ); m_layerCheckListBox->Check( i, false );
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment