some changes about zones: enhanced dialog, and files reorganisation

This commit is contained in:
CHARRAS 2007-12-17 20:18:04 +00:00
parent fdb2905baf
commit 7e7a793753
23 changed files with 3668 additions and 875 deletions

41
bitmaps/fill_zone.xpm Normal file
View File

@ -0,0 +1,41 @@
/* XPM */
#ifndef XPMMAIN
extern const char *fill_zone_xpm[];
#else
const char *fill_zone_xpm[] = {
/* columns rows colors chars-per-pixel */
"16 16 15 1",
"# c #FCFEFC",
"@ c #ACBEFC",
"O c #444A5C",
"$ c #645AEC",
"X c #040204",
"o c #ECEAEC",
". c #F4F2F4",
" c None",
"+ c #C4C6CC",
"& c #6476C4",
"* c #A4A2AC",
"= c #848A9C",
"; c #646674",
"% c #8496F4",
"- c #7C7E8C",
/* pixels */
" . XX . .. .",
" oX X o o ",
" X OXX o ",
"oo oXO+X X@@ooo ",
" O+.X#.X$%@oo",
" o O+.#X..+X$%@o",
"o O+.##..+*=X$%@",
"&O+.##..+*=-;$%@",
"O+.##..+*=-;X$%@",
" X+#. +*=-;X&$%@",
" X+.+*=-;X &$%@",
" X=*=-;X &$%@",
" X;-;X &$%&",
" X;X &$% ",
" X $% ",
" $% "
};
#endif

View File

@ -4,6 +4,11 @@ Started 2007-June-11
Please add newer entries at the top, list the date and your name with Please add newer entries at the top, list the date and your name with
email address. email address.
2007-Dec-17 UPDATE Jean-Pierre Charras <jean-pierre.charras@inpg.fr>
================================================================================
+pcbnew:
some changes about zones: enhanced dialog, and files reorganisation.
2007-Dec-14 UPDATE Dick Hollenbeck <dick@softplc.com> 2007-Dec-14 UPDATE Dick Hollenbeck <dick@softplc.com>
================================================================================ ================================================================================

View File

@ -155,13 +155,16 @@ void FootprintListBox::SetSelection( unsigned index, bool State )
if( (int) index >= GetCount() ) if( (int) index >= GetCount() )
index = GetCount() - 1; index = GetCount() - 1;
if ( (index >= 0) && (GetCount() > 0) )
{
#ifndef __WXMAC__ #ifndef __WXMAC__
Select( index, State ); Select( index, State );
#endif #endif
EnsureVisible( index ); EnsureVisible( index );
#ifdef __WXMAC__ #ifdef __WXMAC__
Refresh(); Refresh();
#endif #endif
}
} }
@ -256,13 +259,16 @@ void ListBoxCmp::SetSelection( unsigned index, bool State )
if( (int) index >= GetCount() ) if( (int) index >= GetCount() )
index = GetCount() - 1; index = GetCount() - 1;
if ( (index >= 0) && (GetCount() > 0) )
{
#ifndef __WXMAC__ #ifndef __WXMAC__
Select( index, State ); Select( index, State );
#endif #endif
EnsureVisible( index ); EnsureVisible( index );
#ifdef __WXMAC__ #ifdef __WXMAC__
Refresh(); Refresh();
#endif #endif
}
} }

View File

@ -1,11 +1,11 @@
/***************************/ /****************************/
/* readschematicnetlist.cpp*/ /* readschematicnetlist.cpp */
/***************************/ /****************************/
/* convertit la netliste ORCADPCB en netliste ORCADPCB (fichier temporaire) /* Read a nelist type Eeschema or OrcadPCB2 and buid the component list
assure la raffectation des alimentations selon le format : * Manages the lines like :
( XXXXXX VALEUR|(pin1,pin2,...=newalim) ID VALEUR * ( XXXXXX VALEUR|(pin1,pin2,...=newalim) ID VALEUR
*/ */
#include "fctsys.h" #include "fctsys.h"
@ -19,347 +19,389 @@ assure la r
/* routines locales : */ /* routines locales : */
static int pin_orcad(STORECMP * CurrentCmp); static int ReadPinConnection( STORECMP* CurrentCmp );
#define BUFFER_CHAR_SIZE 1024 // Size of buffers used to store netlist datas
/************************************************/ /************************************************/
int WinEDA_CvpcbFrame::ReadSchematicNetlist() int WinEDA_CvpcbFrame::ReadSchematicNetlist()
/************************************************/ /************************************************/
{ {
int i , j , k ,l ; int i, j, k, l;
char * LibName; char* LibName;
char Line[1024]; char Line[BUFFER_CHAR_SIZE + 1];
char component_reference[80] ; /* buffer des references composants */ char component_reference[BUFFER_CHAR_SIZE + 1]; /* buffer for component reference (U1, R4...) */
char ref_schema[80] ; /* buffer de la ref schematique */ char schematic_timestamp[BUFFER_CHAR_SIZE + 1]; /* buffer for component time stamp */
char footprint_name[80] ; /* buffer des ref.lib */ char footprint_name[BUFFER_CHAR_SIZE + 1]; /* buffer for component footprint field */
char component_value[80] ; /* buffer des valeurs */ char component_value[BUFFER_CHAR_SIZE + 1]; /* buffer for component values (470K, 22nF ...) */
char *ptchar ; /* pointeur de service */ char* ptchar; /* pointeur de service */
STORECMP * Cmp; STORECMP* Cmp;
modified = 0; modified = 0;
Rjustify = 0; Rjustify = 0;
g_FlagEESchema = FALSE; g_FlagEESchema = FALSE;
/* Raz buffer et variable de gestion */ /* Raz buffer et variable de gestion */
if( g_BaseListeCmp ) FreeMemoryComponants(); if( g_BaseListeCmp )
FreeMemoryComponants();
/* Ouverture du fichier source */ /* Ouverture du fichier source */
source = wxFopen(FFileName, wxT("rt")); source = wxFopen( FFileName, wxT( "rt" ) );
if (source == 0) if( source == 0 )
{ {
wxString msg; wxString msg;
msg.Printf( _("File <%s> not found"),FFileName.GetData()); msg.Printf( _( "File <%s> not found" ), FFileName.GetData() );
DisplayError(this, msg); return(-1); DisplayError( this, msg ); return -1;
} }
/* Read the file header (must be "( { OrCAD PCB" or "({ OrCAD PCB" ) */ /* Read the file header (must be "( { OrCAD PCB" or "({ OrCAD PCB" )
/* or "# EESchema Netliste"*/ * or "# EESchema Netliste"
fgets(Line,255,source) ; */
/* test for netlist type PCB2 */ fgets( Line, 255, source );
i = strnicmp(Line,"( {",3) ; /* test for netlist type PCB2 */
if( i != 0 ) i = strnicmp( Line, "( {", 3 );
i = strnicmp(Line,"({",2) ; if( i != 0 )
if( i != 0 ) i = strnicmp( Line, "({", 2 );
{ if( i != 0 )
i = strnicmp(Line,"# EESchema",7) ; /* net type EESchema */ {
if( i == 0 ) g_FlagEESchema = TRUE; i = strnicmp( Line, "# EESchema", 7 ); /* net type EESchema */
} if( i == 0 )
g_FlagEESchema = TRUE;
}
if ( i != 0 ) if( i != 0 )
{ {
wxString msg, Lineconv = CONV_FROM_UTF8(Line); wxString msg, Lineconv = CONV_FROM_UTF8( Line );
msg.Printf( _("Unknown file format <%s>"), Lineconv.GetData()); msg.Printf( _( "Unknown file format <%s>" ), Lineconv.GetData() );
DisplayError(this, msg); DisplayError( this, msg );
fclose(source); return(-3) ; fclose( source ); return -3;
} }
SetStatusText( _("Netlist Format: EESchema"), 0); SetStatusText( _( "Netlist Format: EESchema" ), 0 );
/* Lecture de la liste */ /* Read the netlit */
for (;;) for( ; ; )
{ {
/* recherche du debut de la description d'un composant */ /* Search the beginning of a component description */
if( fgets(Line,255,source) == 0 ) break; if( fgets( Line, BUFFER_CHAR_SIZE, source ) == 0 )
break;
/* Remove blanks */ /* Remove blanks */
i = 0 ; while (Line[i] == ' ') i++ ; i = 0; while( Line[i] == ' ' )
i++;
/* elimination des lignes vides : */ /* remove empty lines : */
if (Line[i] < ' ') continue ; if( Line[i] < ' ' )
continue;
if (strnicmp(&Line[i],"{ Allowed footprints", 20 ) == 0 ) if( strnicmp( &Line[i], "{ Allowed footprints", 20 ) == 0 )
{ {
ReadFootprintFilterList(source); ReadFootprintFilterList( source );
continue; continue;
} }
if (strnicmp(&Line[i],"( ",2) != 0) continue ;
/****************************/ if( strnicmp( &Line[i], "( ", 2 ) != 0 )
/* debut description trouve */ continue;
/****************************/
/* memo ident schema */
while ( Line[i] != ' ') i++ ;
while ( Line[i] == ' ') i++ ; /* i pointe 1er caractere de l'ident schema */
j = 0 ; while ( Line[i] != ' ') ref_schema[j++] = Line[i++] ; /*******************************/
ref_schema[j] = 0 ; /* Component description found */
/*******************************/
while( Line[i] != ' ' )
i++;
/* recherche val/ref.lib */ while( Line[i] == ' ' )
while ( Line[i] == ' ') i++ ; /* i pointe la valeur du composant */ i++;
LibName = Line + i;
memset(component_reference, 0, sizeof(component_reference)); /* i points the beginning of the schematic time stamp */
memset(footprint_name, 0, sizeof(footprint_name) ) ;
memset(component_value, 0, sizeof(component_value) ) ;
memset(alim, 0, sizeof(alim) ) ;
/* lecture valeur du composant */ j = 0; while( Line[i] != ' ' )
schematic_timestamp[j++] = Line[i++];
/* recherche fin de valeur (' ') */ schematic_timestamp[j] = 0;
ptchar = strstr(&Line[i]," ") ;
if (ptchar == 0)
{
wxString msg;
msg.Printf( _("Netlist error: %s"),Line) ;
DisplayError(NULL, msg);
k = 0 ;
}
else k = ptchar - Line ;
for (j = 0 ; i < k ; i++) /* search val/ref.lib */
{ while( Line[i] == ' ' )
if ( Line[i] == SEPARATEUR ) break ; i++;
if ( j < (int)(sizeof(footprint_name)-1) )
footprint_name[j++] = Line[i] ;
}
if ( (Line[++i] == '(') && (Line[k-1] == ')' ) ) /* i points the component value */
{ LibName = Line + i;
i++ ; l = 0 ; while ( k-1 > i ) alim[l++] = Line[i++] ;
}
else i = k ; memset( schematic_timestamp, 0, sizeof(schematic_timestamp) );
memset( component_reference, 0, sizeof(component_reference) );
memset( footprint_name, 0, sizeof(footprint_name) );
memset( component_value, 0, sizeof(component_value) );
memset( alim, 0, sizeof(alim) );
/* recherche reference du composant */ /* Read value */
while(Line[i] != ' ') i++ ; /* elimination fin valeur */
while(Line[i] == ' ') i++ ; /* recherche debut reference */
/* debut reference trouv */ ptchar = strstr( &Line[i], " " ); // Search end of value field (space)
for ( k = 0 ; k < (int)(sizeof(component_reference)-1) ; i++ , k++ ) if( ptchar == 0 )
{ {
if ( Line[i] <= ' ' ) break ; wxString msg;
component_reference[k] = Line[i] ; msg.Printf( _( "Netlist error: %s" ), Line );
} DisplayError( NULL, msg );
k = 0;
}
else
k = ptchar - Line;
/* recherche valeur du composant */ for( j = 0; i < k; i++ )
while(Line[i] == ' ') i++ ; /* recherche debut valeur */ {
if( Line[i] == SEPARATEUR )
break;
if( j < (int) (sizeof(footprint_name) - 1) )
footprint_name[j++] = Line[i];
}
/* debut vraie valeur trouvee */ if( (Line[++i] == '(') && (Line[k - 1] == ')' ) )
for ( k = 0 ; k < (int)(sizeof(component_value)-1) ; i++ , k++ ) {
{ i++; l = 0; while( k - 1 > i )
if ( Line[i] <= ' ' ) break ; alim[l++] = Line[i++];
component_value[k] = Line[i] ; }
} else
i = k;
/* Search component reference */
while( Line[i] != ' ' )
i++;
/* classement du composant ,suivi de sa valeur */ /* goto end of value field */
Cmp = new STORECMP(); while( Line[i] == ' ' )
Cmp->Pnext = g_BaseListeCmp; i++;
g_BaseListeCmp = Cmp;
Cmp->m_Reference = CONV_FROM_UTF8(component_reference);
Cmp->m_Valeur = CONV_FROM_UTF8(component_value) ;
if( g_FlagEESchema ) /* Copie du nom module: */ /* goto beginning of reference */
{
if( strnicmp(LibName, "$noname", 7 ) != 0 )
{
while( *LibName > ' ' )
{
Cmp->m_Module.Append(*LibName);
LibName++;
}
}
}
/* classement du TimeStamp */
Cmp->m_TimeStamp = CONV_FROM_UTF8(ref_schema);
pin_orcad( Cmp) ; /* debut reference trouv */
for( k = 0; k < (int) (sizeof(component_reference) - 1); i++, k++ )
{
if( Line[i] <= ' ' )
break;
component_reference[k] = Line[i];
}
nbcomp++ ; /* Search component value */
} while( Line[i] == ' ' )
fclose(source); i++;
/* reclassement alpabetique : */ /** goto beginning of value */
g_BaseListeCmp = TriListeComposantss( g_BaseListeCmp, nbcomp);
return(0); for( k = 0; k < (int) (sizeof(component_value) - 1); i++, k++ )
{
if( Line[i] <= ' ' )
break;
component_value[k] = Line[i];
}
/* Store info for this component */
Cmp = new STORECMP();
Cmp->Pnext = g_BaseListeCmp;
g_BaseListeCmp = Cmp;
Cmp->m_Reference = CONV_FROM_UTF8( component_reference );
Cmp->m_Valeur = CONV_FROM_UTF8( component_value );
if( g_FlagEESchema ) /* copy footprint name: */
{
if( strnicmp( LibName, "$noname", 7 ) != 0 )
{
while( *LibName > ' ' )
{
Cmp->m_Module.Append( *LibName );
LibName++;
}
}
}
Cmp->m_TimeStamp = CONV_FROM_UTF8( schematic_timestamp );
ReadPinConnection( Cmp );
nbcomp++;
}
fclose( source );
/* Alpabetic sorting : */
g_BaseListeCmp = TriListeComposantss( g_BaseListeCmp, nbcomp );
return 0;
} }
/********************************************************/ /********************************************************/
int WinEDA_CvpcbFrame::ReadFootprintFilterList( FILE * f) int WinEDA_CvpcbFrame::ReadFootprintFilterList( FILE* f )
/********************************************************/ /********************************************************/
{ {
char Line[1024]; char Line[BUFFER_CHAR_SIZE + 1];
wxString CmpRef; wxString CmpRef;
STORECMP * Cmp = NULL; STORECMP* Cmp = NULL;
for (;;) for( ; ; )
{ {
if( fgets(Line,255,source) == 0 ) break; if( fgets( Line, BUFFER_CHAR_SIZE, source ) == 0 )
if (strnicmp(Line,"$endlist", 8 ) == 0 ) break;
{ if( strnicmp( Line, "$endlist", 8 ) == 0 )
Cmp = NULL; {
continue; Cmp = NULL;
} continue;
if (strnicmp(Line,"$endfootprintlist", 4 ) == 0 ) return 0; }
if( strnicmp( Line, "$endfootprintlist", 4 ) == 0 )
if (strnicmp(Line,"$component", 10 ) == 0 ) // New component ref found return 0;
{
CmpRef = CONV_FROM_UTF8(Line+11); if( strnicmp( Line, "$component", 10 ) == 0 ) // New component ref found
CmpRef.Trim(TRUE); CmpRef.Trim(FALSE); {
/* Search the new component in list */ CmpRef = CONV_FROM_UTF8( Line + 11 );
for ( Cmp = g_BaseListeCmp; Cmp != NULL; Cmp = Cmp->Pnext ) CmpRef.Trim( TRUE ); CmpRef.Trim( FALSE );
{ /* Search the new component in list */
if ( Cmp->m_Reference == CmpRef) break; for( Cmp = g_BaseListeCmp; Cmp != NULL; Cmp = Cmp->Pnext )
} {
} if( Cmp->m_Reference == CmpRef )
break;
else if ( Cmp ) }
{ }
wxString fp = CONV_FROM_UTF8(Line+1); else if( Cmp )
fp.Trim(FALSE); fp.Trim(TRUE); {
Cmp->m_FootprintFilter.Add(fp); wxString fp = CONV_FROM_UTF8( Line + 1 );
} fp.Trim( FALSE ); fp.Trim( TRUE );
} Cmp->m_FootprintFilter.Add( fp );
}
return 1; }
return 1;
} }
/***********************************/ /***********************************/
int pin_orcad(STORECMP * Cmp) int ReadPinConnection( STORECMP* Cmp )
/***********************************/ /***********************************/
{ {
int i , jj; int i, jj;
char numpin[9] , net[1024] ; char numpin[BUFFER_CHAR_SIZE + 1], net[BUFFER_CHAR_SIZE + 1];
char Line[1024]; char Line[BUFFER_CHAR_SIZE + 1];
STOREPIN * Pin = NULL; STOREPIN* Pin = NULL;
STOREPIN ** LastPin = & Cmp->m_Pins; STOREPIN** LastPin = &Cmp->m_Pins;
for ( ;; ) for( ; ; )
{ {
/* debut description trouv */ /* debut description trouv */
for ( ;; ) for( ; ; )
{ {
if ( fgets(Line,80,source) == 0 ) return(-1) ; if( fgets( Line, BUFFER_CHAR_SIZE, source ) == 0 )
return -1;
/* suppression des blancs en dbut de ligne */ /* remove blanks from the beginning of the line */
i = 0 ; while (Line[i] == ' ') i++ ; i = 0; while( Line[i] == ' ' )
while (Line[i] == '(') i++ ; i++;
while (Line[i] == ' ') i++ ;
/* elimination des lignes vides : */ while( Line[i] == '(' )
if (Line[i] < ' ') continue ; i++;
/* fin de description ? */ while( Line[i] == ' ' )
if (Line[i] == ')' ) return(0) ; i++;
memset( net, 0, sizeof(net) ); /* remove empty lines : */
memset( numpin, 0, sizeof(numpin) ); if( Line[i] < ' ' )
continue;
/* lecture name pin , 4 lettres */ /* fin de description ? */
for (jj = 0 ; jj < 4 ; jj++ , i++) if( Line[i] == ')' )
{ return 0;
if ( Line[i] == ' ' ) break ;
numpin[jj] = Line[i] ;
}
/* recherche affectation force de net */ memset( net, 0, sizeof(net) );
if ( reaffect(numpin,net) != 0) memset( numpin, 0, sizeof(numpin) );
{
Pin = new STOREPIN();
*LastPin = Pin; LastPin = &Pin->Pnext;
Pin->m_PinNum = CONV_FROM_UTF8(numpin);
Pin->m_PinNet = CONV_FROM_UTF8(net);
continue ;
}
/* recherche netname */ /* Read pi name , 4 letters */
while(Line[i] == ' ') i++ ; /* recherche debut reference */ for( jj = 0; jj < 4; jj++, i++ )
{
if( Line[i] == ' ' )
break;
numpin[jj] = Line[i];
}
/* debut netname trouv */ /* Search for a net attribute */
for ( jj = 0 ; jj < (int)sizeof(net)-1 ; i++ , jj++ ) if( reaffect( numpin, net ) != 0 )
{ {
if ( Line[i] <= ' ' ) break ; Pin = new STOREPIN();
net[jj] = Line[i] ; *LastPin = Pin; LastPin = &Pin->Pnext;
} Pin->m_PinNum = CONV_FROM_UTF8( numpin );
Pin->m_PinNet = CONV_FROM_UTF8( net );
continue;
}
Pin = new STOREPIN(); /* Read netname */
*LastPin = Pin; LastPin = &Pin->Pnext; while( Line[i] == ' ' )
Pin->m_PinNum = CONV_FROM_UTF8(numpin); i++;
Pin->m_PinNet = CONV_FROM_UTF8(net);
} for( jj = 0; jj < (int) sizeof(net) - 1; i++, jj++ )
} {
if( Line[i] <= ' ' )
break;
net[jj] = Line[i];
}
Pin = new STOREPIN();
*LastPin = Pin; LastPin = &Pin->Pnext;
Pin->m_PinNum = CONV_FROM_UTF8( numpin );
Pin->m_PinNet = CONV_FROM_UTF8( net );
}
}
} }
/****************************************************************/ /****************************************************************/
STORECMP * TriListeComposantss(STORECMP * BaseListe, int nbitems) STORECMP* TriListeComposantss( STORECMP* BaseListe, int nbitems )
/****************************************************************/ /****************************************************************/
/* Tri la liste des composants par ordre alphabetique et me a jour
le nouveau chainage avant/arriere /* Sort the component list( this is a linked list)
retourne un pointeur sur le 1er element de la liste * retourn the beginning of the list
*/ */
{ {
STORECMP ** bufferptr, * Item; STORECMP** bufferptr, * Item;
int ii; int ii;
if (nbitems <= 0 ) return(NULL); if( nbitems <= 0 )
bufferptr = (STORECMP**)MyZMalloc( (nbitems+2) * sizeof(STORECMP*) ); return NULL;
bufferptr = (STORECMP**) MyZMalloc( (nbitems + 2) * sizeof(STORECMP*) );
for( ii= 1, Item = BaseListe; Item != NULL; Item = Item->Pnext, ii++) for( ii = 1, Item = BaseListe; Item != NULL; Item = Item->Pnext, ii++ )
{ {
bufferptr[ii] = Item; bufferptr[ii] = Item;
} }
/* ici bufferptr[0] = NULL et bufferptr[nbitem+1] = NULL et ces 2 valeurs /* Here: bufferptr[0] = NULL and bufferptr[nbitem+1] = NULL.
representent le chainage arriere du 1er element, et le chainage avant * These 2 values are the first item back link, and the last item forward link
du dernier element */ */
qsort(bufferptr+1,nbitems,sizeof(STORECMP*), qsort( bufferptr + 1, nbitems, sizeof(STORECMP*),
(int(*)(const void*,const void*))CmpCompare) ; ( int( * ) ( const void*, const void* ) )CmpCompare );
/* Mise a jour du chainage */ /* Update linked list */
for( ii = 1; ii <= nbitems; ii++ ) for( ii = 1; ii <= nbitems; ii++ )
{ {
Item = bufferptr[ii]; Item = bufferptr[ii];
Item->m_Num = ii; Item->m_Num = ii;
Item->Pnext = bufferptr[ii+1]; Item->Pnext = bufferptr[ii + 1];
Item->Pback = bufferptr[ii-1]; Item->Pback = bufferptr[ii - 1];
} }
return(bufferptr[1]);
return bufferptr[1];
} }
/****************************************/ /****************************************/
int CmpCompare(void * mod1, void * mod2) int CmpCompare( void* mod1, void* mod2 )
/****************************************/ /****************************************/
/* /*
routine compare() pour qsort() en classement alphabetique des composants * Function compare() for qsort() : alphabetic sorting, with numbering order
*/ */
{ {
int ii; int ii;
STORECMP *pt1 , *pt2 ; STORECMP* pt1, * pt2;
pt1 = * ((STORECMP**)mod1); pt1 = *( (STORECMP**) mod1 );
pt2 = * ((STORECMP**)mod2); pt2 = *( (STORECMP**) mod2 );
//FIXME: //FIXME:
ii = StrNumICmp( (const wxChar*) pt1->m_Reference, (const wxChar*) pt2->m_Reference ); ii = StrNumICmp( (const wxChar*) pt1->m_Reference, (const wxChar*) pt2->m_Reference );
return(ii); return ii;
} }

View File

@ -183,6 +183,7 @@
#include "../bitmaps/transistor.xpm" #include "../bitmaps/transistor.xpm"
#include "../bitmaps/kicad_icon_small.xpm" #include "../bitmaps/kicad_icon_small.xpm"
#include "../bitmaps/general_ratsnet.xpm" #include "../bitmaps/general_ratsnet.xpm"
#include "../bitmaps/fill_zone.xpm"
// Largeur du toolbar vertical // Largeur du toolbar vertical
#define VTOOLBAR_WIDTH 26 #define VTOOLBAR_WIDTH 26

View File

@ -5,7 +5,7 @@
COMMON_GLOBL wxString g_BuildVersion COMMON_GLOBL wxString g_BuildVersion
#ifdef EDA_BASE #ifdef EDA_BASE
(wxT("(2007-12-08)")) (wxT("(2007-12-17)"))
#endif #endif
; ;

View File

@ -383,7 +383,7 @@ void TreePrjItemData::Activate(WinEDA_PrjFrame* prjframe)
} }
if(count == 0) if(count == 0)
{ {
prjframe->AddFile(wxString( wxT("no kicad files found in this directory") ), id); prjframe->AddFile(wxString(_("no kicad files found in this directory")), id);
} }
/* Sort filenames by alphabetic order */ /* Sort filenames by alphabetic order */
m_Parent->SortChildren( id ); m_Parent->SortChildren( id );

View File

@ -121,9 +121,6 @@ void WinEDA_BasePcbFrame::CursorGoto( const wxPoint& aPos )
DrawPanel->MouseToCursorSchema(); DrawPanel->MouseToCursorSchema();
DrawPanel->CursorOn( &dc ); DrawPanel->CursorOn( &dc );
} }
D(printf("CursorGoto end x=%d, y=%d\n",
m_CurrentScreen->m_Curseur.x, m_CurrentScreen->m_Curseur.y );)
} }

View File

@ -650,8 +650,86 @@ EQUIPOT* BOARD::FindNet( int anetcode ) const
} }
/* Two sort functions used in BOARD::ReturnSortedNetnamesList */
// Sort nets by name
int s_SortByNames(const void * ptr1, const void * ptr2)
{
EQUIPOT* item1 = * (EQUIPOT**) ptr1;
EQUIPOT* item2 = * (EQUIPOT**) ptr2;
return item1->m_Netname.CmpNoCase(item2->m_Netname);
}
// Sort nets by decreasing pad count
int s_SortByNodes(const void * ptr1, const void * ptr2)
{
EQUIPOT* item1 = * (EQUIPOT**) ptr1;
EQUIPOT* item2 = * (EQUIPOT**) ptr2;
if ( (item1->m_NbNodes - item2->m_NbNodes) != 0 )
return - (item1->m_NbNodes - item2->m_NbNodes);
return item1->m_Netname.CmpNoCase(item2->m_Netname);
}
/**
* Function ReturnSortedNetnamesList
* searches for a net with the given netcode.
* @param aNames An array string to fill with net names.
* @param aSort_Type : NO_SORT = no sort, ALPHA_SORT = sort by alphabetic order, PAD_CNT_SORT = sort by active pads count.
* @return int - net names count.
*/
int BOARD::ReturnSortedNetnamesList( wxArrayString & aNames, const int aSort_Type)
{
int NetCount = 0;
int ii;
EQUIPOT* net;
/* count items to list and sort */
for( net = m_Equipots; net; net=net->Next() )
{
if ( net->m_Netname.IsEmpty() ) continue;
NetCount++;
}
if ( NetCount == 0 ) return 0;
/* Build the list */
EQUIPOT* * net_ptr_list = (EQUIPOT* *) MyMalloc( NetCount * sizeof(* net_ptr_list) );
for( ii = 0, net = m_Equipots; net; net=net->Next() )
{
if ( net->m_Netname.IsEmpty() ) continue;
net_ptr_list[ii] = net;
ii++;
}
/* sort the list */
switch ( aSort_Type )
{
case NO_SORT : break;
case ALPHA_SORT :
qsort (net_ptr_list, NetCount, sizeof(EQUIPOT*), s_SortByNames);
break;
case PAD_CNT_SORT:
qsort (net_ptr_list, NetCount, sizeof(EQUIPOT*), s_SortByNodes);
break;
}
/* fill the given list */
for( ii = 0; ii < NetCount; ii++ )
{
net = net_ptr_list[ii];
aNames.Add(net->m_Netname);
}
MyFree(net_ptr_list);
return NetCount;
}
/************************************/
bool BOARD::Save( FILE* aFile ) const bool BOARD::Save( FILE* aFile ) const
/************************************/
{ {
bool rc = false; bool rc = false;
BOARD_ITEM* item; BOARD_ITEM* item;

View File

@ -48,8 +48,7 @@ public:
CHEVELU* m_Ratsnest; // Rastnest list CHEVELU* m_Ratsnest; // Rastnest list
CHEVELU* m_LocalRatsnest; // Rastnest list used while moving a footprint CHEVELU* m_LocalRatsnest; // Rastnest list used while moving a footprint
EDGE_ZONE* m_CurrentLimitZone; /* pointeur sur la liste des segments EDGE_ZONE* m_CurrentLimitZone; /* zone contour currently in progress */
* de delimitation de la zone en cours de trace */
BOARD( EDA_BaseStruct* StructFather, WinEDA_BasePcbFrame* frame ); BOARD( EDA_BaseStruct* StructFather, WinEDA_BasePcbFrame* frame );
~BOARD(); ~BOARD();
@ -175,6 +174,20 @@ public:
*/ */
EQUIPOT* FindNet( int aNetcode ) const; EQUIPOT* FindNet( int aNetcode ) const;
/**
* Function ReturnSortedNetnamesList
* searches for a net with the given netcode.
* @param aNames An array string to fill with net names.
* @param aSort_Type : NO_SORT = no sort, ALPHA_SORT = sort by alphabetic order, PAD_CNT_SORT = sort by active pads count.
* @return int - net names count.
*/
enum netname_sort_type {
NO_SORT,
ALPHA_SORT,
PAD_CNT_SORT
};
int ReturnSortedNetnamesList( wxArrayString & aNames, const int aSort_Type);
/** /**
* Function Save * Function Save

View File

@ -0,0 +1,453 @@
/////////////////////////////////////////////////////////////////////////////
// Name: zones.cpp
// Purpose:
// Author: jean-pierre Charras
// Modified by:
// Created: 25/01/2006 11:35:19
// RCS-ID:
// Copyright: GNU License
// Licence: GNU License
/////////////////////////////////////////////////////////////////////////////
// Generated by DialogBlocks (unregistered), 25/01/2006 11:35:19
#if defined (__GNUG__) && !defined (NO_GCC_PRAGMA)
#pragma implementation "zones.h"
#endif
// For compilers that support precompilation, includes "wx/wx.h".
#include "wx/wxprec.h"
#ifdef __BORLANDC__
#pragma hdrstop
#endif
#ifndef WX_PRECOMP
#include "wx/wx.h"
#endif
////@begin includes
////@end includes
#include "dialog_zones_by_polygon.h"
////@begin XPM images
////@end XPM images
/*!
* WinEDA_ZoneFrame type definition
*/
IMPLEMENT_DYNAMIC_CLASS( WinEDA_ZoneFrame, wxDialog )
/*!
* WinEDA_ZoneFrame event table definition
*/
BEGIN_EVENT_TABLE( WinEDA_ZoneFrame, wxDialog )
////@begin WinEDA_ZoneFrame event table entries
EVT_BUTTON( ID_BUTTON, WinEDA_ZoneFrame::ExecFillZone )
EVT_BUTTON( wxID_CANCEL, WinEDA_ZoneFrame::OnCancelClick )
EVT_RADIOBOX( ID_NET_SORTING_OPTION, WinEDA_ZoneFrame::OnNetSortingOptionSelected )
////@end WinEDA_ZoneFrame event table entries
END_EVENT_TABLE()
/*!
* WinEDA_ZoneFrame constructors
*/
WinEDA_ZoneFrame::WinEDA_ZoneFrame()
{
}
WinEDA_ZoneFrame::WinEDA_ZoneFrame( WinEDA_PcbFrame* parent,
wxWindowID id,
const wxString& caption,
const wxPoint& pos,
const wxSize& size,
long style )
{
m_Parent = parent;
Create( parent, id, caption, pos, size, style );
}
/*!
* WinEDA_ZoneFrame creator
*/
bool WinEDA_ZoneFrame::Create( wxWindow* parent,
wxWindowID id,
const wxString& caption,
const wxPoint& pos,
const wxSize& size,
long style )
{
////@begin WinEDA_ZoneFrame member initialisation
m_GridCtrl = NULL;
m_ClearanceValueTitle = NULL;
m_ZoneClearanceCtrl = NULL;
m_FillOpt = NULL;
m_OrientEdgesOpt = NULL;
m_NetSortingOption = NULL;
m_ListNetNameSelection = NULL;
m_LayerSelectionCtrl = NULL;
////@end WinEDA_ZoneFrame member initialisation
////@begin WinEDA_ZoneFrame creation
SetExtraStyle(wxWS_EX_BLOCK_EVENTS);
wxDialog::Create( parent, id, caption, pos, size, style );
CreateControls();
if (GetSizer())
{
GetSizer()->SetSizeHints(this);
}
Centre();
////@end WinEDA_ZoneFrame creation
return true;
}
/*!
* Control creation for WinEDA_ZoneFrame
*/
void WinEDA_ZoneFrame::CreateControls()
{
SetFont( *g_DialogFont );
////@begin WinEDA_ZoneFrame content construction
// Generated by DialogBlocks, 17/12/2007 20:46:19 (unregistered)
WinEDA_ZoneFrame* itemDialog1 = this;
wxBoxSizer* itemBoxSizer2 = new wxBoxSizer(wxVERTICAL);
itemDialog1->SetSizer(itemBoxSizer2);
wxBoxSizer* itemBoxSizer3 = new wxBoxSizer(wxHORIZONTAL);
itemBoxSizer2->Add(itemBoxSizer3, 0, wxALIGN_CENTER_HORIZONTAL|wxALL, 5);
wxBoxSizer* itemBoxSizer4 = new wxBoxSizer(wxVERTICAL);
itemBoxSizer3->Add(itemBoxSizer4, 0, wxGROW|wxALL, 5);
wxArrayString m_GridCtrlStrings;
m_GridCtrlStrings.Add(_("0.00000"));
m_GridCtrlStrings.Add(_("0.00000"));
m_GridCtrlStrings.Add(_("0.00000"));
m_GridCtrlStrings.Add(_("0.00000"));
m_GridCtrl = new wxRadioBox( itemDialog1, ID_RADIOBOX3, _("Grid Size for Filling:"), wxDefaultPosition, wxDefaultSize, m_GridCtrlStrings, 1, wxRA_SPECIFY_COLS );
m_GridCtrl->SetSelection(0);
itemBoxSizer4->Add(m_GridCtrl, 0, wxGROW|wxALL, 5);
m_ClearanceValueTitle = new wxStaticText( itemDialog1, wxID_STATIC, _("Zone clearance value (mm):"), wxDefaultPosition, wxDefaultSize, 0 );
itemBoxSizer4->Add(m_ClearanceValueTitle, 0, wxALIGN_LEFT|wxLEFT|wxRIGHT|wxTOP|wxADJUST_MINSIZE, 5);
m_ZoneClearanceCtrl = new wxTextCtrl( itemDialog1, ID_TEXTCTRL1, _T(""), wxDefaultPosition, wxDefaultSize, 0 );
itemBoxSizer4->Add(m_ZoneClearanceCtrl, 0, wxGROW|wxLEFT|wxRIGHT|wxBOTTOM, 5);
itemBoxSizer3->Add(5, 5, 0, wxGROW|wxALL, 5);
wxBoxSizer* itemBoxSizer9 = new wxBoxSizer(wxVERTICAL);
itemBoxSizer3->Add(itemBoxSizer9, 0, wxGROW|wxALL, 5);
wxArrayString m_FillOptStrings;
m_FillOptStrings.Add(_("Include Pads"));
m_FillOptStrings.Add(_("Thermal"));
m_FillOptStrings.Add(_("Exclude Pads"));
m_FillOpt = new wxRadioBox( itemDialog1, ID_RADIOBOX4, _("Pad options:"), wxDefaultPosition, wxDefaultSize, m_FillOptStrings, 1, wxRA_SPECIFY_COLS );
m_FillOpt->SetSelection(0);
itemBoxSizer9->Add(m_FillOpt, 0, wxGROW|wxALL, 5);
wxArrayString m_OrientEdgesOptStrings;
m_OrientEdgesOptStrings.Add(_("Any"));
m_OrientEdgesOptStrings.Add(_("H , V and 45 deg"));
m_OrientEdgesOpt = new wxRadioBox( itemDialog1, ID_RADIOBOX5, _("Zone edges orient:"), wxDefaultPosition, wxDefaultSize, m_OrientEdgesOptStrings, 1, wxRA_SPECIFY_COLS );
m_OrientEdgesOpt->SetSelection(0);
itemBoxSizer9->Add(m_OrientEdgesOpt, 0, wxGROW|wxALL, 5);
itemBoxSizer3->Add(5, 5, 0, wxGROW|wxALL, 5);
wxBoxSizer* itemBoxSizer13 = new wxBoxSizer(wxVERTICAL);
itemBoxSizer3->Add(itemBoxSizer13, 0, wxGROW|wxALL, 5);
wxButton* itemButton14 = new wxButton( itemDialog1, ID_BUTTON, _("Fill"), wxDefaultPosition, wxDefaultSize, 0 );
itemButton14->SetDefault();
itemButton14->SetForegroundColour(wxColour(204, 0, 0));
itemBoxSizer13->Add(itemButton14, 0, wxGROW|wxALL, 5);
wxButton* itemButton15 = new wxButton( itemDialog1, wxID_CANCEL, _("&Cancel"), wxDefaultPosition, wxDefaultSize, 0 );
itemButton15->SetForegroundColour(wxColour(0, 0, 255));
itemBoxSizer13->Add(itemButton15, 0, wxGROW|wxALL, 5);
itemBoxSizer13->Add(5, 5, 1, wxGROW|wxALL, 5);
wxArrayString m_NetSortingOptionStrings;
m_NetSortingOptionStrings.Add(_("Alphabetic"));
m_NetSortingOptionStrings.Add(_("Advanced"));
m_NetSortingOption = new wxRadioBox( itemDialog1, ID_NET_SORTING_OPTION, _("Net sorting:"), wxDefaultPosition, wxDefaultSize, m_NetSortingOptionStrings, 1, wxRA_SPECIFY_COLS );
m_NetSortingOption->SetSelection(0);
itemBoxSizer13->Add(m_NetSortingOption, 0, wxGROW|wxALL, 5);
wxBoxSizer* itemBoxSizer18 = new wxBoxSizer(wxVERTICAL);
itemBoxSizer2->Add(itemBoxSizer18, 0, wxGROW|wxALL, 5);
wxStaticText* itemStaticText19 = new wxStaticText( itemDialog1, wxID_STATIC, _("Net:"), wxDefaultPosition, wxDefaultSize, 0 );
itemBoxSizer18->Add(itemStaticText19, 0, wxALIGN_LEFT|wxLEFT|wxRIGHT|wxTOP, 5);
wxArrayString m_ListNetNameSelectionStrings;
m_ListNetNameSelection = new wxListBox( itemDialog1, ID_NETNAME_SELECTION, wxDefaultPosition, wxDefaultSize, m_ListNetNameSelectionStrings, wxLB_SINGLE|wxSUNKEN_BORDER );
itemBoxSizer18->Add(m_ListNetNameSelection, 0, wxGROW|wxLEFT|wxRIGHT|wxBOTTOM, 5);
wxStaticText* itemStaticText21 = new wxStaticText( itemDialog1, wxID_LAYER_SELECTION, _("Layer:"), wxDefaultPosition, wxDefaultSize, 0 );
itemBoxSizer18->Add(itemStaticText21, 0, wxALIGN_LEFT|wxLEFT|wxRIGHT|wxTOP, 5);
wxArrayString m_LayerSelectionCtrlStrings;
m_LayerSelectionCtrl = new wxListBox( itemDialog1, ID_LAYER_CHOICE, wxDefaultPosition, wxDefaultSize, m_LayerSelectionCtrlStrings, wxLB_SINGLE );
itemBoxSizer18->Add(m_LayerSelectionCtrl, 0, wxGROW|wxALL, 5);
// Set validators
m_NetSortingOption->SetValidator( wxGenericValidator(& s_NetSortingOpt) );
////@end WinEDA_ZoneFrame content construction
wxString title = _( "Zone clearance value:" ) + ReturnUnitSymbol( g_UnitMetric );
m_ClearanceValueTitle->SetLabel( title );
title = _( "Grid :" ) + ReturnUnitSymbol( g_UnitMetric );;
m_GridCtrl->SetLabel( title );
if( g_DesignSettings.m_ZoneClearence == 0 )
g_DesignSettings.m_ZoneClearence = g_DesignSettings.m_TrackClearence;
title = ReturnStringFromValue( g_UnitMetric,
g_DesignSettings.m_ZoneClearence,
m_Parent->m_InternalUnits );
m_ZoneClearanceCtrl->SetValue( title );
if( Zone_45_Only )
m_OrientEdgesOpt->SetSelection( 1 );
static const int GridList[4] = { 50, 100, 250, 500 };
int selection = 0;
for( unsigned ii = 0; ii < (unsigned) m_GridCtrl->GetCount(); ii++ )
{
wxString msg = ReturnStringFromValue( g_UnitMetric,
GridList[ii],
m_Parent->m_InternalUnits );
m_GridCtrl->SetString( ii, msg );
if( g_GridRoutingSize == GridList[ii] )
selection = ii;
}
// Initialise options
m_GridCtrl->SetSelection( selection );
if( Zone_Exclude_Pads )
{
if( s_Zone_Create_Thermal_Relief )
m_FillOpt->SetSelection( 1 );
else
m_FillOpt->SetSelection( 2 );
}
m_NetSortingOption->SetSelection(s_NetSortingOpt == 0 ? : 1 );
int layer_cnt = g_DesignSettings.m_CopperLayerCount;
for( int ii = 0; ii < g_DesignSettings.m_CopperLayerCount; ii++ )
{
wxString msg;
int layer_number;
if( layer_cnt == 0 || ii < layer_cnt - 1 )
layer_number = ii;
else if( ii == layer_cnt - 1 )
layer_number = LAYER_CMP_N;
m_LayerId[ii] = layer_number;
msg = ReturnPcbLayerName( layer_number ).Trim();
m_LayerSelectionCtrl->InsertItems( 1, &msg, ii );
if( m_Parent->GetScreen()->m_Active_Layer == layer_number )
m_LayerSelectionCtrl->SetSelection( ii );
}
wxArrayString ListNetName;
m_Parent->m_Pcb->ReturnSortedNetnamesList( ListNetName,
s_NetSortingOpt == 0 ? BOARD::ALPHA_SORT : BOARD::PAD_CNT_SORT );
m_ListNetNameSelection->InsertItems( ListNetName, 0 );
// Select net:
if( g_HightLigth_NetCode > 0 )
{
EQUIPOT* equipot = m_Parent->m_Pcb->FindNet( g_HightLigth_NetCode );
if( equipot ) // Search net in list and select it
{
for( unsigned ii = 0; ii < ListNetName.GetCount(); ii++ )
{
if( ListNetName[ii] == equipot->m_Netname )
{
m_ListNetNameSelection->SetSelection( ii );
break;
}
}
}
}
}
/*!
* Should we show tooltips?
*/
bool WinEDA_ZoneFrame::ShowToolTips()
{
return true;
}
/*!
* Get bitmap resources
*/
wxBitmap WinEDA_ZoneFrame::GetBitmapResource( const wxString& name )
{
// Bitmap retrieval
////@begin WinEDA_ZoneFrame bitmap retrieval
wxUnusedVar(name);
return wxNullBitmap;
////@end WinEDA_ZoneFrame bitmap retrieval
}
/*!
* Get icon resources
*/
wxIcon WinEDA_ZoneFrame::GetIconResource( const wxString& name )
{
// Icon retrieval
////@begin WinEDA_ZoneFrame icon retrieval
wxUnusedVar(name);
return wxNullIcon;
////@end WinEDA_ZoneFrame icon retrieval
}
/*!
* wxEVT_COMMAND_BUTTON_CLICKED event handler for wxID_CANCEL
*/
void WinEDA_ZoneFrame::OnCancelClick( wxCommandEvent& event )
{
////@begin wxEVT_COMMAND_BUTTON_CLICKED event handler for wxID_CANCEL in WinEDA_ZoneFrame.
// Before editing this code, remove the block markers.
event.Skip();
////@end wxEVT_COMMAND_BUTTON_CLICKED event handler for wxID_CANCEL in WinEDA_ZoneFrame.
}
/*!
* wxEVT_COMMAND_BUTTON_CLICKED event handler for ID_BUTTON2
*/
/***********************************************************/
void WinEDA_ZoneFrame::ExecFillZone( wxCommandEvent& event )
/***********************************************************/
{
switch( m_FillOpt->GetSelection() )
{
case 0:
Zone_Exclude_Pads = FALSE;
s_Zone_Create_Thermal_Relief = FALSE;
break;
case 1:
Zone_Exclude_Pads = TRUE;
s_Zone_Create_Thermal_Relief = TRUE;
break;
case 2:
Zone_Exclude_Pads = TRUE;
s_Zone_Create_Thermal_Relief = FALSE;
break;
}
switch( m_GridCtrl->GetSelection() )
{
case 0:
g_GridRoutingSize = 50;
break;
case 1:
g_GridRoutingSize = 100;
break;
case 2:
g_GridRoutingSize = 250;
break;
case 3:
g_GridRoutingSize = 500;
break;
}
wxString txtvalue = m_ZoneClearanceCtrl->GetValue();
g_DesignSettings.m_ZoneClearence =
ReturnValueFromString( g_UnitMetric, txtvalue, m_Parent->m_InternalUnits );
if( m_OrientEdgesOpt->GetSelection() == 0 )
Zone_45_Only = FALSE;
else
Zone_45_Only = TRUE;
/* Get the layer selection for this zone */
int ii = m_LayerSelectionCtrl->GetSelection();
if( ii < 0 )
{
DisplayError( this, _( "Error : you must choose a layer" ) );
return;
}
s_Zone_Layer = m_LayerId[ii];
/* Get the net name selection for this zone */
ii = m_ListNetNameSelection->GetSelection();
if( ii < 0 )
{
DisplayError( this, _( "Error : you must choose a net name" ) );
return;
}
wxString net_name = m_ListNetNameSelection->GetString( ii );
/* Search net_code for this net */
EQUIPOT* net;
s_NetcodeSelection = 0;
for( net = m_Parent->m_Pcb->m_Equipots; net; net = net->Next() )
{
if( net->m_Netname == net_name )
{
s_NetcodeSelection = net->GetNet();
break;
}
}
EndModal( 0 );
}
/*!
* wxEVT_COMMAND_RADIOBOX_SELECTED event handler for ID_NET_SORTING_OPTION
*/
void WinEDA_ZoneFrame::OnNetSortingOptionSelected( wxCommandEvent& event )
{
wxArrayString ListNetName;
s_NetSortingOpt = m_NetSortingOption->GetSelection();
m_Parent->m_Pcb->ReturnSortedNetnamesList( ListNetName,
s_NetSortingOpt == 0 ? BOARD::ALPHA_SORT : BOARD::PAD_CNT_SORT );
m_ListNetNameSelection->Clear();
m_ListNetNameSelection->InsertItems( ListNetName, 0 );
}

View File

@ -0,0 +1,130 @@
/////////////////////////////////////////////////////////////////////////////
// Name: dialog_zones_by_polygon.h
// Purpose:
// Author: jean-pierre Charras
// Modified by:
// Created: 25/01/2006 11:35:19
// RCS-ID:
// Copyright: GNU License
// Licence:
/////////////////////////////////////////////////////////////////////////////
// Generated by DialogBlocks (unregistered), 25/01/2006 11:35:19
#ifndef DIALOG_ZONES_H_
#define DIALOG_ZONES_H_
#if defined(__GNUG__) && !defined(NO_GCC_PRAGMA)
#pragma interface "dialog_zones_by_polygon.h"
#endif
/*!
* Includes
*/
////@begin includes
#include "wx/valgen.h"
////@end includes
/*!
* Forward declarations
*/
////@begin forward declarations
////@end forward declarations
/*!
* Control identifiers
*/
////@begin control identifiers
#define ID_DIALOG 10000
#define ID_RADIOBOX3 10003
#define ID_TEXTCTRL1 10007
#define ID_RADIOBOX4 10008
#define ID_RADIOBOX5 10009
#define ID_BUTTON 10010
#define ID_NET_SORTING_OPTION 10005
#define ID_NETNAME_SELECTION 10001
#define wxID_LAYER_SELECTION 10004
#define ID_LAYER_CHOICE 10002
#define SYMBOL_WINEDA_ZONEFRAME_STYLE wxCAPTION|wxSYSTEM_MENU|wxCLOSE_BOX|MAYBE_RESIZE_BORDER
#define SYMBOL_WINEDA_ZONEFRAME_TITLE _("Fill Zones Options")
#define SYMBOL_WINEDA_ZONEFRAME_IDNAME ID_DIALOG
#define SYMBOL_WINEDA_ZONEFRAME_SIZE wxSize(400, 300)
#define SYMBOL_WINEDA_ZONEFRAME_POSITION wxDefaultPosition
////@end control identifiers
/*!
* Compatibility
*/
#ifndef wxCLOSE_BOX
#define wxCLOSE_BOX 0x1000
#endif
/*!
* WinEDA_ZoneFrame class declaration
*/
class WinEDA_ZoneFrame: public wxDialog
{
DECLARE_DYNAMIC_CLASS( WinEDA_ZoneFrame )
DECLARE_EVENT_TABLE()
public:
/// Constructors
WinEDA_ZoneFrame( );
WinEDA_ZoneFrame( WinEDA_PcbFrame* parent, wxWindowID id = SYMBOL_WINEDA_ZONEFRAME_IDNAME, const wxString& caption = SYMBOL_WINEDA_ZONEFRAME_TITLE, const wxPoint& pos = SYMBOL_WINEDA_ZONEFRAME_POSITION, const wxSize& size = SYMBOL_WINEDA_ZONEFRAME_SIZE, long style = SYMBOL_WINEDA_ZONEFRAME_STYLE );
/// Creation
bool Create( wxWindow* parent, wxWindowID id = SYMBOL_WINEDA_ZONEFRAME_IDNAME, const wxString& caption = SYMBOL_WINEDA_ZONEFRAME_TITLE, const wxPoint& pos = SYMBOL_WINEDA_ZONEFRAME_POSITION, const wxSize& size = SYMBOL_WINEDA_ZONEFRAME_SIZE, long style = SYMBOL_WINEDA_ZONEFRAME_STYLE );
/// Creates the controls and sizers
void CreateControls();
////@begin WinEDA_ZoneFrame event handler declarations
/// wxEVT_COMMAND_BUTTON_CLICKED event handler for ID_BUTTON
void ExecFillZone( wxCommandEvent& event );
/// wxEVT_COMMAND_BUTTON_CLICKED event handler for wxID_CANCEL
void OnCancelClick( wxCommandEvent& event );
/// wxEVT_COMMAND_RADIOBOX_SELECTED event handler for ID_NET_SORTING_OPTION
void OnNetSortingOptionSelected( wxCommandEvent& event );
////@end WinEDA_ZoneFrame event handler declarations
////@begin WinEDA_ZoneFrame member function declarations
/// Retrieves bitmap resources
wxBitmap GetBitmapResource( const wxString& name );
/// Retrieves icon resources
wxIcon GetIconResource( const wxString& name );
////@end WinEDA_ZoneFrame member function declarations
/// Should we show tooltips?
static bool ShowToolTips();
////@begin WinEDA_ZoneFrame member variables
wxRadioBox* m_GridCtrl;
wxStaticText* m_ClearanceValueTitle;
wxTextCtrl* m_ZoneClearanceCtrl;
wxRadioBox* m_FillOpt;
wxRadioBox* m_OrientEdgesOpt;
wxRadioBox* m_NetSortingOption;
wxListBox* m_ListNetNameSelection;
wxListBox* m_LayerSelectionCtrl;
////@end WinEDA_ZoneFrame member variables
WinEDA_PcbFrame * m_Parent;
int m_LayerId[LAYER_COUNT]; // Handle the real layer number from layer name position in m_LayerSelectionCtrl
};
#endif // DIALOG_ZONES_H_

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,612 @@
/* filling_zone_algorithm:
Algos used to fill a zone defined by a polygon and a filling starting point
*/
#include "fctsys.h"
#include "gr_basic.h"
#include "common.h"
#include "pcbnew.h"
#include "autorout.h"
#include "cell.h"
#include "trigo.h"
#include "protos.h"
/* Local functions */
static void Genere_Segments_Zone( WinEDA_PcbFrame* frame, wxDC* DC, int net_code );
/* Local variables */
static bool Zone_Debug = FALSE;
static unsigned long s_TimeStamp; /* Time stamp common to all segments relative to the new created zone */
/****************************************************************************************/
void Build_Zone( WinEDA_PcbFrame* frame, wxDC* DC, int net_code,
bool Zone_Exclude_Pads, bool Zone_Create_Thermal_Relief )
/****************************************************************************************/
/** Function Build_Zone()
* Init the zone filling
* If a zone edge is found, it is used.
* Otherwise the whole board is filled by the zone
* The zone edge is a frontier, and can be complex. So non filled zones can be achieved
* The zone is put on the active layer
* If a net is hightlighted, the zone will be attached to this net
* The filling start from a starting point.
* If a net is selected, all tracks attached to this net are also starting points
*/
{
int ii, jj;
EDGE_ZONE* PtLim;
int lp_tmp, lay_tmp_TOP, lay_tmp_BOTTOM;
int save_isol = g_DesignSettings.m_TrackClearence;
wxPoint ZoneStartFill;
wxString msg;
PCB_SCREEN * Screen = frame->GetScreen();
BOARD * Pcb = frame->m_Pcb;
g_DesignSettings.m_TrackClearence = g_DesignSettings.m_ZoneClearence;
s_TimeStamp = time( NULL );
// calculate the fixed step of the routing matrix as 5 mils or more
E_scale = g_GridRoutingSize / 50;
if( g_GridRoutingSize < 1 )
g_GridRoutingSize = 1;
// calculate the Ncols and Nrows, size of the routing matrix
ComputeMatriceSize( frame, g_GridRoutingSize );
// Determine the cell pointed to by the mouse
ZoneStartFill.x = ( Screen->m_Curseur.x - Pcb->m_BoundaryBox.m_Pos.x +
(g_GridRoutingSize / 2) ) / g_GridRoutingSize;
ZoneStartFill.y = ( Screen->m_Curseur.y - Pcb->m_BoundaryBox.m_Pos.y +
(g_GridRoutingSize / 2) ) / g_GridRoutingSize;
if( ZoneStartFill.x < 0 )
ZoneStartFill.x = 0;
if( ZoneStartFill.x >= Ncols )
ZoneStartFill.x = Ncols - 1;
if( ZoneStartFill.y < 0 )
ZoneStartFill.y = 0;
if( ZoneStartFill.y >= Nrows )
ZoneStartFill.y = Nrows - 1;
// create the routing matrix in autorout.h's eda_global BOARDHEAD Board
Nb_Sides = ONE_SIDE;
if( Board.InitBoard() < 0 )
{
DisplayError( frame, wxT( "Mo memory for creating zones" ) );
return;
}
msg.Printf( wxT( "%d" ), Ncols );
Affiche_1_Parametre( frame, 1, wxT( "Cols" ), msg, GREEN );
msg.Printf( wxT( "%d" ), Nrows );
Affiche_1_Parametre( frame, 7, wxT( "Lines" ), msg, GREEN );
msg.Printf( wxT( "%d" ), Board.m_MemSize / 1024 );
Affiche_1_Parametre( frame, 14, wxT( "Mem(Ko)" ), msg, CYAN );
lay_tmp_BOTTOM = Route_Layer_BOTTOM;
lay_tmp_TOP = Route_Layer_TOP;
Route_Layer_BOTTOM = Route_Layer_TOP = Screen->m_Active_Layer;
lp_tmp = g_DesignSettings.m_CurrentTrackWidth;
g_DesignSettings.m_CurrentTrackWidth = g_GridRoutingSize;
/* Create the starting point for thz zone:
* The starting point and all the tracks are suitable "starting points" */
TRACK* pt_segm = Pcb->m_Track;
for( ; pt_segm != NULL; pt_segm = pt_segm->Next() )
{
if( g_HightLigth_NetCode != pt_segm->GetNet() )
continue;
if( pt_segm->GetLayer() != Screen->m_Active_Layer )
continue;
if( pt_segm->Type() != TYPETRACK )
continue;
TraceSegmentPcb( Pcb, pt_segm, CELL_is_FRIEND, 0, WRITE_CELL );
}
// trace the pcb edges (pcb contour) into the routing matrix
Route_Layer_BOTTOM = Route_Layer_TOP = EDGE_N;
PlaceCells( Pcb, -1, 0 );
Route_Layer_BOTTOM = Route_Layer_TOP = Screen->m_Active_Layer;
// trace the zone edges into the routing matrix
for( PtLim = Pcb->m_CurrentLimitZone; PtLim; PtLim=PtLim->Next() )
{
int ux0, uy0, ux1, uy1;
ux0 = PtLim->m_Start.x - Pcb->m_BoundaryBox.m_Pos.x;
uy0 = PtLim->m_Start.y - Pcb->m_BoundaryBox.m_Pos.y;
ux1 = PtLim->m_End.x - Pcb->m_BoundaryBox.m_Pos.x;
uy1 = PtLim->m_End.y - Pcb->m_BoundaryBox.m_Pos.y;
TraceLignePcb( ux0, uy0, ux1, uy1, -1, HOLE | CELL_is_EDGE, WRITE_CELL );
}
OrCell( ZoneStartFill.y, ZoneStartFill.x, BOTTOM, CELL_is_ZONE );
// mark the cells forming part of the zone
ii = 1; jj = 1;
while( ii )
{
msg.Printf( wxT( "%d" ), jj++ );
Affiche_1_Parametre( frame, 50, wxT( "Iter." ), msg, CYAN );
ii = Propagation( frame );
}
// selection of the suitable cells for the points of anchoring of the zone
for( ii = 0; ii < Nrows; ii++ )
{
for( jj = 0; jj < Ncols; jj++ )
{
long cell = GetCell( ii, jj, BOTTOM );
if( (cell & CELL_is_ZONE) )
{
if( (cell & CELL_is_FRIEND) == 0 )
AndCell( ii, jj, BOTTOM, (BoardCell) ~(CELL_is_FRIEND | CELL_is_ZONE) );
}
}
}
// now, all the cell candidates are marked
// place all the obstacles into the matrix, such as (pads, tracks, vias,
// pcb edges or segments)
ii = 0;
if( Zone_Exclude_Pads )
ii = FORCE_PADS;
Affiche_1_Parametre( frame, 42, wxT( "GenZone" ), wxEmptyString, RED );
PlaceCells( Pcb, g_HightLigth_NetCode, ii );
Affiche_1_Parametre( frame, -1, wxEmptyString, _( "Ok" ), RED );
/* Create zone limits on the routing matrix
* (colud be deleted by PlaceCells()) : */
for( PtLim = Pcb->m_CurrentLimitZone; PtLim; PtLim = PtLim->Next() )
{
int ux0, uy0, ux1, uy1;
ux0 = PtLim->m_Start.x - Pcb->m_BoundaryBox.m_Pos.x;
uy0 = PtLim->m_Start.y - Pcb->m_BoundaryBox.m_Pos.y;
ux1 = PtLim->m_End.x - Pcb->m_BoundaryBox.m_Pos.x;
uy1 = PtLim->m_End.y - Pcb->m_BoundaryBox.m_Pos.y;
TraceLignePcb( ux0, uy0, ux1, uy1, -1, HOLE | CELL_is_EDGE, WRITE_CELL );
}
/* Init the starting point for zone filling : this is the mouse position
* (could be deleted by PlaceCells()) : */
OrCell( ZoneStartFill.y, ZoneStartFill.x, BOTTOM, CELL_is_ZONE );
if( Zone_Debug )
DisplayBoard( frame->DrawPanel, DC );
/* Filling the cells of the matrix (tjis is the zone building)*/
ii = 1; jj = 1;
while( ii )
{
msg.Printf( wxT( "%d" ), jj++ );
Affiche_1_Parametre( frame, 50, wxT( "Iter." ), msg, CYAN );
ii = Propagation( frame );
}
if( Zone_Debug )
DisplayBoard( frame->DrawPanel, DC );
/* Convert the matrix information (cells) to segments which are actually the zone */
if( g_HightLigth_NetCode < 0 )
Genere_Segments_Zone( frame, DC, 0 );
else
Genere_Segments_Zone( frame, DC, g_HightLigth_NetCode );
/* Create the thermal reliefs */
g_DesignSettings.m_CurrentTrackWidth = lp_tmp;
if( Zone_Exclude_Pads && Zone_Create_Thermal_Relief )
frame->Genere_Pad_Connexion( DC, Screen->m_Active_Layer );
g_DesignSettings.m_TrackClearence = save_isol;
// free the memory
Board.UnInitBoard();
// restore original values unchanged
Route_Layer_TOP = lay_tmp_TOP;
Route_Layer_BOTTOM = lay_tmp_BOTTOM;
}
/*******************************************************************************/
static void Genere_Segments_Zone( WinEDA_PcbFrame* frame, wxDC* DC, int net_code )
/*******************************************************************************/
/** Function Genere_Segments_Zone()
* Create the zone segments from the routing matrix structure
* Algorithm:
* Search for consecutive cells (flagged "zone") , and create segments
* from the first cell to the last cell in the matrix
* 2 searchs are made
* 1 - From left to right and create horizontal zone segments
* 2 - From top to bottom, and create vertical zone segmùents
* @param net_code = net_code common to all segment zone created
* @param DC = current device context
* @param frame = current WinEDA_PcbFrame
* global: parameter TimeStamp: time stamp common to all segment zone created
*/
{
int row, col;
long current_cell, old_cell;
int ux0 = 0, uy0 = 0, ux1 = 0, uy1 = 0;
int Xmin = frame->m_Pcb->m_BoundaryBox.m_Pos.x;
int Ymin = frame->m_Pcb->m_BoundaryBox.m_Pos.y;
SEGZONE* pt_track;
int layer = frame->GetScreen()->m_Active_Layer;
int nbsegm = 0;
wxString msg;
/* balayage Gauche-> droite */
Affiche_1_Parametre( frame, 64, wxT( "Segm H" ), wxT( "0" ), BROWN );
for( row = 0; row < Nrows; row++ )
{
old_cell = 0;
uy0 = uy1 = (row * g_GridRoutingSize) + Ymin;
for( col = 0; col < Ncols; col++ )
{
current_cell = GetCell( row, col, BOTTOM ) & CELL_is_ZONE;
if( current_cell ) /* ce point doit faire partie d'un segment */
{
ux1 = (col * g_GridRoutingSize) + Xmin;
if( old_cell == 0 )
ux0 = ux1;
}
if( !current_cell || (col == Ncols - 1) ) /* peut etre fin d'un segment */
{
if( (old_cell) && (ux0 != ux1) )
{
/* un segment avait debute de longueur > 0 */
pt_track = new SEGZONE( frame->m_Pcb );
pt_track->SetLayer( layer );
pt_track->SetNet( net_code );
pt_track->m_Width = g_GridRoutingSize;
pt_track->m_Start.x = ux0;
pt_track->m_Start.y = uy0;
pt_track->m_End.x = ux1;
pt_track->m_End.y = uy1;
pt_track->m_TimeStamp = s_TimeStamp;
pt_track->Insert( frame->m_Pcb, NULL );
pt_track->Draw( frame->DrawPanel, DC, GR_OR );
nbsegm++;
}
}
old_cell = current_cell;
}
msg.Printf( wxT( "%d" ), nbsegm );
Affiche_1_Parametre( frame, -1, wxEmptyString, msg, BROWN );
}
Affiche_1_Parametre( frame, 72, wxT( "Segm V" ), wxT( "0" ), BROWN );
for( col = 0; col < Ncols; col++ )
{
old_cell = 0;
ux0 = ux1 = (col * g_GridRoutingSize) + Xmin;
for( row = 0; row < Nrows; row++ )
{
current_cell = GetCell( row, col, BOTTOM ) & CELL_is_ZONE;
if( current_cell ) /* ce point doit faire partie d'un segment */
{
uy1 = (row * g_GridRoutingSize) + Ymin;
if( old_cell == 0 )
uy0 = uy1;
}
if( !current_cell || (row == Nrows - 1) ) /* peut etre fin d'un segment */
{
if( (old_cell) && (uy0 != uy1) )
{
/* un segment avait debute de longueur > 0 */
pt_track = new SEGZONE( frame->m_Pcb );
pt_track->SetLayer( layer );
pt_track->m_Width = g_GridRoutingSize;
pt_track->SetNet( net_code );
pt_track->m_Start.x = ux0;
pt_track->m_Start.y = uy0;
pt_track->m_End.x = ux1;
pt_track->m_End.y = uy1;
pt_track->m_TimeStamp = s_TimeStamp;
pt_track->Insert( frame->m_Pcb, NULL );
pt_track->Draw( frame->DrawPanel, DC, GR_OR );
nbsegm++;
}
}
old_cell = current_cell;
}
msg.Printf( wxT( "%d" ), nbsegm );
Affiche_1_Parametre( frame, -1, wxEmptyString, msg, BROWN );
}
}
/********************************************/
int Propagation( WinEDA_PcbFrame* frame )
/********************************************/
/** Function Propagation()
* An important function to calculate zones
* Uses the routing matrix to fill the cells within the zone
* Search and mark cells within the zone, and agree with DRC options.
* Requirements:
* Start from an initial point, to fill zone
* The zone must have no "copper island"
* Algorithm:
* If the current cell has a neightbour flagged as "cell in the zone", it
* become a cell in the zone
* The first point in the zone is the starting point
* 4 searches within the matrix are made:
* 1 - Left to right and top to bottom
* 2 - Right to left and top to bottom
* 3 - bottom to top and Right to left
* 4 - bottom to top and Left to right
* Given the current cell, for each search, we consider the 2 neightbour cells
* the previous cell on the same line and the previous cell on the same column.
*
* This funtion can request some iterations
* Iterations are made until no cell is added to the zone.
* @return: added cells count (i.e. which the attribute CELL_is_ZONE is set)
*/
{
int row, col, nn;
long current_cell, old_cell_H;
int long* pt_cell_V;
int nbpoints = 0;
#define NO_CELL_ZONE (HOLE | CELL_is_EDGE | CELL_is_ZONE)
wxString msg;
Affiche_1_Parametre( frame, 57, wxT( "Detect" ), msg, CYAN );
Affiche_1_Parametre( frame, -1, wxEmptyString, wxT( "1" ), CYAN );
// Alloc memory to handle 1 line or 1 colunmn on the routing matrix
nn = MAX( Nrows, Ncols ) * sizeof(*pt_cell_V);
pt_cell_V = (long*) MyMalloc( nn );
/* search 1 : from left to right and top to bottom */
memset( pt_cell_V, 0, nn );
for( row = 0; row < Nrows; row++ )
{
old_cell_H = 0;
for( col = 0; col < Ncols; col++ )
{
current_cell = GetCell( row, col, BOTTOM ) & NO_CELL_ZONE;
if( current_cell == 0 ) /* a free cell is found */
{
if( (old_cell_H & CELL_is_ZONE)
|| (pt_cell_V[col] & CELL_is_ZONE) )
{
OrCell( row, col, BOTTOM, CELL_is_ZONE );
current_cell = CELL_is_ZONE;
nbpoints++;
}
}
pt_cell_V[col] = old_cell_H = current_cell;
}
}
/* search 2 : from right to left and top to bottom */
Affiche_1_Parametre( frame, -1, wxEmptyString, wxT( "2" ), CYAN );
memset( pt_cell_V, 0, nn );
for( row = 0; row < Nrows; row++ )
{
old_cell_H = 0;
for( col = Ncols - 1; col >= 0; col-- )
{
current_cell = GetCell( row, col, BOTTOM ) & NO_CELL_ZONE;
if( current_cell == 0 ) /* a free cell is found */
{
if( (old_cell_H & CELL_is_ZONE)
|| (pt_cell_V[col] & CELL_is_ZONE) )
{
OrCell( row, col, BOTTOM, CELL_is_ZONE );
current_cell = CELL_is_ZONE;
nbpoints++;
}
}
pt_cell_V[col] = old_cell_H = current_cell;
}
}
/* search 3 : from bottom to top and right to left balayage */
Affiche_1_Parametre( frame, -1, wxEmptyString, wxT( "3" ), CYAN );
memset( pt_cell_V, 0, nn );
for( col = Ncols - 1; col >= 0; col-- )
{
old_cell_H = 0;
for( row = Nrows - 1; row >= 0; row-- )
{
current_cell = GetCell( row, col, BOTTOM ) & NO_CELL_ZONE;
if( current_cell == 0 ) /* a free cell is found */
{
if( (old_cell_H & CELL_is_ZONE)
|| (pt_cell_V[row] & CELL_is_ZONE) )
{
OrCell( row, col, BOTTOM, CELL_is_ZONE );
current_cell = CELL_is_ZONE;
nbpoints++;
}
}
pt_cell_V[row] = old_cell_H = current_cell;
}
}
/* search 4 : from bottom to top and left to right */
Affiche_1_Parametre( frame, -1, wxEmptyString, wxT( "4" ), CYAN );
memset( pt_cell_V, 0, nn );
for( col = 0; col < Ncols; col++ )
{
old_cell_H = 0;
for( row = Nrows - 1; row >= 0; row-- )
{
current_cell = GetCell( row, col, BOTTOM ) & NO_CELL_ZONE;
if( current_cell == 0 ) /* a free cell is found */
{
if( (old_cell_H & CELL_is_ZONE)
|| (pt_cell_V[row] & CELL_is_ZONE) )
{
OrCell( row, col, BOTTOM, CELL_is_ZONE );
current_cell = CELL_is_ZONE;
nbpoints++;
}
}
pt_cell_V[row] = old_cell_H = current_cell;
}
}
MyFree( pt_cell_V );
return nbpoints;
}
/*****************************************************************************/
bool WinEDA_PcbFrame::Genere_Pad_Connexion( wxDC* DC, int layer )
/*****************************************************************************/
/* Create the thermal relief for each pad in the zone:
* this is 4 small segments from the pad to the zone
*/
{
int ii, jj, Npads;
D_PAD* pt_pad;
LISTE_PAD* pt_liste_pad;
TRACK* pt_track, * loctrack;
int angle;
int cX, cY, dx, dy;
int sommet[4][2];
wxString msg;
if( m_Pcb->m_Zone == NULL )
return FALSE; /* error: no zone */
if( m_Pcb->m_Zone->m_TimeStamp != s_TimeStamp ) /* error: this is not the new zone */
return FALSE;
/* Count the pads, i.e. the thermal relief to create count, and displays it */
Affiche_1_Parametre( this, 50, wxT( "NPads" ), wxT( " " ), CYAN );
pt_liste_pad = (LISTE_PAD*) m_Pcb->m_Pads;
for( ii = 0, Npads = 0; ii < m_Pcb->m_NbPads; ii++, pt_liste_pad++ )
{
pt_pad = *pt_liste_pad;
/* Search pads relative to the selected net code */
if( pt_pad->GetNet() != g_HightLigth_NetCode )
continue;
/* Is the pad on the active layer ? */
if( (pt_pad->m_Masque_Layer & g_TabOneLayerMask[layer]) == 0 )
continue;
Npads++;
}
msg.Printf( wxT( "%d" ), Npads );
Affiche_1_Parametre( this, -1, wxEmptyString, msg, CYAN );
/* Create the thermal reliefs */
Affiche_1_Parametre( this, 57, wxT( "Pads" ), wxT( " " ), CYAN );
pt_liste_pad = (LISTE_PAD*) m_Pcb->m_Pads;
for( ii = 0, Npads = 0; ii < m_Pcb->m_NbPads; ii++, pt_liste_pad++ )
{
pt_pad = *pt_liste_pad;
/* Search pads relative to the selected net code */
if( pt_pad->GetNet() != g_HightLigth_NetCode )
continue;
/* Is the pad on the active layer ? */
if( (pt_pad->m_Masque_Layer & g_TabOneLayerMask[layer]) == 0 )
continue;
/* Create the theram relief for the current pad */
Npads++;
msg.Printf( wxT( "%d" ), Npads );
Affiche_1_Parametre( this, -1, wxEmptyString, msg, CYAN );
cX = pt_pad->GetPosition().x;
cY = pt_pad->GetPosition().y;
dx = pt_pad->m_Size.x / 2;
dy = pt_pad->m_Size.y / 2;
dx += g_DesignSettings.m_TrackClearence + g_GridRoutingSize;
dy += g_DesignSettings.m_TrackClearence + g_GridRoutingSize;
if( pt_pad->m_PadShape == TRAPEZE )
{
dx += abs( pt_pad->m_DeltaSize.y ) / 2;
dy += abs( pt_pad->m_DeltaSize.x ) / 2;
}
/* calculate the 4 segment coordintes (starting from the pad centre cX,cY) */
sommet[0][0] = 0; sommet[0][1] = -dy;
sommet[1][0] = -dx; sommet[1][1] = 0;
sommet[2][0] = 0; sommet[2][1] = dy;
sommet[3][0] = dx; sommet[3][1] = 0;
angle = pt_pad->m_Orient;
for( jj = 0; jj < 4; jj++ )
{
RotatePoint( &sommet[jj][0], &sommet[jj][1], angle );
pt_track = new SEGZONE( m_Pcb );
pt_track->SetLayer( layer );
pt_track->m_Width = g_DesignSettings.m_CurrentTrackWidth;
pt_track->SetNet( g_HightLigth_NetCode );
pt_track->start = pt_pad;
pt_track->m_Start.x = cX; pt_track->m_Start.y = cY;
pt_track->m_End.x = cX + sommet[jj][0];
pt_track->m_End.y = cY + sommet[jj][1];
pt_track->m_TimeStamp = s_TimeStamp;
/* Test if the segment is allowed */
if( BAD_DRC==m_drc->DrcBlind( pt_track, m_Pcb->m_Track ) )
{
delete pt_track;
continue;
}
/* Search for a zone segment */
loctrack = Locate_Zone( m_Pcb->m_Zone, pt_track->m_End, layer );
if( (loctrack == NULL) || (loctrack->m_TimeStamp != s_TimeStamp) )
{
delete pt_track;
continue;
}
pt_track->Insert( m_Pcb, NULL );
pt_track->Draw( DrawPanel, DC, GR_OR );
}
}
return TRUE;
}

View File

@ -1,12 +1,18 @@
EXTRALIBS = ../common/common.a EXTRALIBS = ../common/common.a
EXTRACPPFLAGS += -DPCBNEW -fno-strict-aliasing -I./ -Ibitmaps -I../include -I../share -I../pcbnew -I../3d-viewer EXTRACPPFLAGS += -DPCBNEW -fno-strict-aliasing -I./ -Ibitmaps -I../include -I../share\
-I../pcbnew -I../3d-viewer -I../polygon
#COMMON = pcbnew.h struct.h class_pad.h class_module.h class_text_mod.h \ #COMMON = pcbnew.h struct.h class_pad.h class_module.h class_text_mod.h \
# class_edge_mod.h class_equipot.h # class_edge_mod.h class_equipot.h
LIBVIEWER3D = ../3d-viewer/3d-viewer.a LIBVIEWER3D = ../3d-viewer/3d-viewer.a
ZONE_FILES = zones_by_polygon.o
#ZONE_FILES = zones.o
OBJECTS= $(TARGET).o classpcb.o\ OBJECTS= $(TARGET).o classpcb.o\
$(ZONE_FILES)\
filling_zone_algorithm.o\
lay2plot.o\ lay2plot.o\
modedit_undo_redo.o\ modedit_undo_redo.o\
block_module_editor.o\ block_module_editor.o\
@ -86,7 +92,7 @@ OBJECTS= $(TARGET).o classpcb.o\
autorout.o solve.o\ autorout.o solve.o\
work.o queue.o \ work.o queue.o \
board.o dist.o graphpcb.o \ board.o dist.o graphpcb.o \
zones.o undelete.o \ undelete.o \
copy_track.o\ copy_track.o\
move_or_drag_track.o\ move_or_drag_track.o\
ioascii.o \ ioascii.o \
@ -109,6 +115,10 @@ OBJECTS= $(TARGET).o classpcb.o\
hotkeys.o \ hotkeys.o \
collectors.o collectors.o
PolyLine.o: ../polygon/PolyLine.cpp ../polygon/PolyLine.h $(COMMON)
$(CXX) -c $(EDACPPFLAGS) -o $@ ../polygon/$*.cpp
setpage.o: ../share/setpage.cpp setpage.o: ../share/setpage.cpp
$(CXX) -c $(EDACPPFLAGS) -o $@ ../share/$*.cpp $(CXX) -c $(EDACPPFLAGS) -o $@ ../share/$*.cpp
@ -277,6 +287,9 @@ graphpcb.o: graphpcb.cpp cell.h autorout.h $(COMMON)
zones.o: zones.cpp cell.h $(COMMON) zones.o: zones.cpp cell.h $(COMMON)
zones_by_polygon.o: zones_by_polygon.cpp dialog_zones_by_polygon.cpp dialog_zones_by_polygon.h $(COMMON)
undelete.o: undelete.cpp $(COMMON) undelete.o: undelete.cpp $(COMMON)
move_or_drag_track.o: move_or_drag_track.cpp $(COMMON) move_or_drag_track.o: move_or_drag_track.cpp $(COMMON)

View File

@ -355,7 +355,8 @@ bool WinEDA_PcbFrame::OnRightClick( const wxPoint& aMousePos, wxMenu* aPopMenu )
case ID_PCB_ZONES_BUTT: case ID_PCB_ZONES_BUTT:
{ {
bool add_separator = FALSE; bool add_separator = FALSE;
aPopMenu->Append( ID_POPUP_PCB_FILL_ZONE, _( "Fill zone" ) ); ADD_MENUITEM( aPopMenu, ID_POPUP_PCB_FILL_ZONE,
_( "Fill zone" ), fill_zone_xpm );
if( item if( item
&& ( (item->Type() == TYPEPAD) && ( (item->Type() == TYPEPAD)

View File

@ -43,10 +43,6 @@ bool WinEDA_App::OnInit()
return false; return false;
} }
/* Add image handlers for screen hardcopy */
wxImage::AddHandler( new wxPNGHandler );
wxImage::AddHandler( new wxJPEGHandler );
ScreenPcb = new PCB_SCREEN( PCB_FRAME ); ScreenPcb = new PCB_SCREEN( PCB_FRAME );
GetSettings(); GetSettings();

View File

@ -35,19 +35,22 @@
////@begin XPM images ////@begin XPM images
////@end XPM images ////@end XPM images
/* Imported functions */
void Build_Zone( WinEDA_PcbFrame* frame, wxDC* DC, int net_code,
bool Zone_Exclude_Pads, bool Zone_Create_Thermal_Relief );
/* Local functions */ /* Local functions */
static void Display_Zone_Netname( WinEDA_PcbFrame* frame ); static void Display_Zone_Netname( WinEDA_PcbFrame* frame );
static void Exit_Zones( WinEDA_DrawPanel* Panel, wxDC* DC ); static void Exit_Zones( WinEDA_DrawPanel* Panel, wxDC* DC );
static void Show_Zone_Edge_While_MoveMouse( WinEDA_DrawPanel* panel, wxDC* DC, bool erase ); static void Show_Zone_Edge_While_MoveMouse( WinEDA_DrawPanel* panel, wxDC* DC, bool erase );
static void Genere_Segments_Zone( WinEDA_PcbFrame* frame, wxDC* DC, int net_code );
/* Local variables */ /* Local variables */
static bool Zone_Debug = FALSE;
static bool Zone_45_Only = FALSE; static bool Zone_45_Only = FALSE;
static bool Zone_Exclude_Pads = TRUE; static bool Zone_Exclude_Pads = TRUE;
static bool s_Zone_Create_Thermal_Relief = TRUE; static bool s_Zone_Create_Thermal_Relief = TRUE;
/* Time stamp comon to all segments relative to the new created zone */ /* Time stamp common to all segments relative to the new created zone */
static unsigned long s_TimeStamp; static unsigned long s_TimeStamp;
/*! /*!
@ -616,7 +619,7 @@ static void Exit_Zones( WinEDA_DrawPanel* Panel, wxDC* DC )
{ {
Panel->ManageCurseur( Panel, DC, 0 ); Panel->ManageCurseur( Panel, DC, 0 );
} }
pcbframe->DelLimitesZone( DC, FALSE ); pcbframe->DelLimitesZone( DC, TRUE );
} }
Panel->ManageCurseur = NULL; Panel->ManageCurseur = NULL;
@ -819,11 +822,7 @@ void WinEDA_PcbFrame::Fill_Zone( wxDC* DC )
* If a net is selected, all tracks attached to this net are also starting points * If a net is selected, all tracks attached to this net are also starting points
*/ */
{ {
int ii, jj;
EDGE_ZONE* PtLim;
int lp_tmp, lay_tmp_TOP, lay_tmp_BOTTOM;
EQUIPOT* pt_equipot; EQUIPOT* pt_equipot;
int save_isol = g_DesignSettings.m_TrackClearence;
wxPoint ZoneStartFill; wxPoint ZoneStartFill;
wxString msg; wxString msg;
@ -837,19 +836,18 @@ void WinEDA_PcbFrame::Fill_Zone( wxDC* DC )
DrawPanel->m_IgnoreMouseEvents = TRUE; DrawPanel->m_IgnoreMouseEvents = TRUE;
WinEDA_ZoneFrame* frame = new WinEDA_ZoneFrame( this ); WinEDA_ZoneFrame* frame = new WinEDA_ZoneFrame( this );
ii = frame->ShowModal(); int abrd = frame->ShowModal();
frame->Destroy(); frame->Destroy();
DrawPanel->MouseToCursorSchema(); DrawPanel->MouseToCursorSchema();
DrawPanel->m_IgnoreMouseEvents = FALSE; DrawPanel->m_IgnoreMouseEvents = FALSE;
if( ii ) if( abrd )
return; return;
g_DesignSettings.m_TrackClearence = g_DesignSettings.m_ZoneClearence;
// set all the EDGE_ZONEs to the currently active layer and redraw them // set all the EDGE_ZONEs to the currently active layer and redraw them
// on that layer. // on that layer.
PtLim = m_Pcb->m_CurrentLimitZone; EDGE_ZONE* PtLim = m_Pcb->m_CurrentLimitZone;
for( ; PtLim != NULL; PtLim = PtLim->Next() ) for( ; PtLim != NULL; PtLim = PtLim->Next() )
{ {
Trace_DrawSegmentPcb( DrawPanel, DC, PtLim, GR_XOR ); Trace_DrawSegmentPcb( DrawPanel, DC, PtLim, GR_XOR );
@ -857,61 +855,7 @@ void WinEDA_PcbFrame::Fill_Zone( wxDC* DC )
Trace_DrawSegmentPcb( DrawPanel, DC, PtLim, GR_XOR ); Trace_DrawSegmentPcb( DrawPanel, DC, PtLim, GR_XOR );
} }
s_TimeStamp = time( NULL ); /* Show the NetName */
// calculate the fixed step of the routing matrix as 5 mils or more
E_scale = g_GridRoutingSize / 50;
if( g_GridRoutingSize < 1 )
g_GridRoutingSize = 1;
// calculate the Ncols and Nrows, size of the routing matrix
ComputeMatriceSize( this, g_GridRoutingSize );
// Determine the cell pointed to by the mouse
ZoneStartFill.x = ( GetScreen()->m_Curseur.x - m_Pcb->m_BoundaryBox.m_Pos.x +
(g_GridRoutingSize / 2) ) / g_GridRoutingSize;
ZoneStartFill.y = ( GetScreen()->m_Curseur.y - m_Pcb->m_BoundaryBox.m_Pos.y +
(g_GridRoutingSize / 2) ) / g_GridRoutingSize;
if( ZoneStartFill.x < 0 )
ZoneStartFill.x = 0;
if( ZoneStartFill.x >= Ncols )
ZoneStartFill.x = Ncols - 1;
if( ZoneStartFill.y < 0 )
ZoneStartFill.y = 0;
if( ZoneStartFill.y >= Nrows )
ZoneStartFill.y = Nrows - 1;
// create the routing matrix in autorout.h's eda_global BOARDHEAD Board
Nb_Sides = ONE_SIDE;
if( Board.InitBoard() < 0 )
{
DisplayError( this, wxT( "Mo memory for creating zones" ) );
return;
}
msg.Printf( wxT( "%d" ), Ncols );
Affiche_1_Parametre( this, 1, wxT( "Cols" ), msg, GREEN );
msg.Printf( wxT( "%d" ), Nrows );
Affiche_1_Parametre( this, 7, wxT( "Lines" ), msg, GREEN );
msg.Printf( wxT( "%d" ), Board.m_MemSize / 1024 );
Affiche_1_Parametre( this, 14, wxT( "Mem(Ko)" ), msg, CYAN );
lay_tmp_BOTTOM = Route_Layer_BOTTOM;
lay_tmp_TOP = Route_Layer_TOP;
Route_Layer_BOTTOM = Route_Layer_TOP = GetScreen()->m_Active_Layer;
lp_tmp = g_DesignSettings.m_CurrentTrackWidth;
g_DesignSettings.m_CurrentTrackWidth = g_GridRoutingSize;
/* Shos the NetName */
if( g_HightLigth_NetCode > 0 ) if( g_HightLigth_NetCode > 0 )
{ {
pt_equipot = m_Pcb->FindNet( g_HightLigth_NetCode ); pt_equipot = m_Pcb->FindNet( g_HightLigth_NetCode );
@ -928,510 +872,7 @@ void WinEDA_PcbFrame::Fill_Zone( wxDC* DC )
Affiche_1_Parametre( this, 22, _( "NetName" ), msg, RED ); Affiche_1_Parametre( this, 22, _( "NetName" ), msg, RED );
/* Create the starting point for thz zone: Build_Zone( this, DC, g_HightLigth_NetCode, Zone_Exclude_Pads, s_Zone_Create_Thermal_Relief );
* The starting point and all the tracks are suitable "starting points" */
TRACK* pt_segm = m_Pcb->m_Track;
for( ; pt_segm != NULL; pt_segm = pt_segm->Next() )
{
if( g_HightLigth_NetCode != pt_segm->GetNet() )
continue;
if( pt_segm->GetLayer() != GetScreen()->m_Active_Layer )
continue;
if( pt_segm->Type() != TYPETRACK )
continue;
TraceSegmentPcb( m_Pcb, pt_segm, CELL_is_FRIEND, 0, WRITE_CELL );
}
// trace the pcb edges (pcb contour) into the routing matrix
Route_Layer_BOTTOM = Route_Layer_TOP = EDGE_N;
PlaceCells( m_Pcb, -1, 0 );
Route_Layer_BOTTOM = Route_Layer_TOP = GetScreen()->m_Active_Layer;
// trace the zone edges into the routing matrix
for( PtLim = m_Pcb->m_CurrentLimitZone; PtLim; PtLim=PtLim->Next() )
{
int ux0, uy0, ux1, uy1;
ux0 = PtLim->m_Start.x - m_Pcb->m_BoundaryBox.m_Pos.x;
uy0 = PtLim->m_Start.y - m_Pcb->m_BoundaryBox.m_Pos.y;
ux1 = PtLim->m_End.x - m_Pcb->m_BoundaryBox.m_Pos.x;
uy1 = PtLim->m_End.y - m_Pcb->m_BoundaryBox.m_Pos.y;
TraceLignePcb( ux0, uy0, ux1, uy1, -1, HOLE | CELL_is_EDGE, WRITE_CELL );
}
OrCell( ZoneStartFill.y, ZoneStartFill.x, BOTTOM, CELL_is_ZONE );
// mark the cells forming part of the zone
ii = 1; jj = 1;
while( ii )
{
msg.Printf( wxT( "%d" ), jj++ );
Affiche_1_Parametre( this, 50, wxT( "Iter." ), msg, CYAN );
ii = Propagation( this );
}
// selection of the suitable cells for the points of anchoring of the zone
for( ii = 0; ii < Nrows; ii++ )
{
for( jj = 0; jj < Ncols; jj++ )
{
long cell = GetCell( ii, jj, BOTTOM );
if( (cell & CELL_is_ZONE) )
{
if( (cell & CELL_is_FRIEND) == 0 )
AndCell( ii, jj, BOTTOM, (BoardCell) ~(CELL_is_FRIEND | CELL_is_ZONE) );
}
}
}
// now, all the cell candidates are marked
// place all the obstacles into the matrix, such as (pads, tracks, vias,
// pcb edges or segments)
ii = 0;
if( Zone_Exclude_Pads )
ii = FORCE_PADS;
Affiche_1_Parametre( this, 42, wxT( "GenZone" ), wxEmptyString, RED );
PlaceCells( m_Pcb, g_HightLigth_NetCode, ii );
Affiche_1_Parametre( this, -1, wxEmptyString, _( "Ok" ), RED );
/* Create zone limits on the routing matrix
* (colud be deleted by PlaceCells()) : */
for( PtLim = m_Pcb->m_CurrentLimitZone; PtLim; PtLim = PtLim->Next() )
{
int ux0, uy0, ux1, uy1;
ux0 = PtLim->m_Start.x - m_Pcb->m_BoundaryBox.m_Pos.x;
uy0 = PtLim->m_Start.y - m_Pcb->m_BoundaryBox.m_Pos.y;
ux1 = PtLim->m_End.x - m_Pcb->m_BoundaryBox.m_Pos.x;
uy1 = PtLim->m_End.y - m_Pcb->m_BoundaryBox.m_Pos.y;
TraceLignePcb( ux0, uy0, ux1, uy1, -1, HOLE | CELL_is_EDGE, WRITE_CELL );
}
/* Init the starting point for zone filling : this is the mouse position
* (could be deleted by PlaceCells()) : */
OrCell( ZoneStartFill.y, ZoneStartFill.x, BOTTOM, CELL_is_ZONE );
if( Zone_Debug )
DisplayBoard( DrawPanel, DC );
/* Filling the cells of the matrix (tjis is the zone building)*/
ii = 1; jj = 1;
while( ii )
{
msg.Printf( wxT( "%d" ), jj++ );
Affiche_1_Parametre( this, 50, wxT( "Iter." ), msg, CYAN );
ii = Propagation( this );
}
if( Zone_Debug )
DisplayBoard( DrawPanel, DC );
/* Convert the matrix information (cells) to segments which are actually the zone */
if( g_HightLigth_NetCode < 0 )
Genere_Segments_Zone( this, DC, 0 );
else
Genere_Segments_Zone( this, DC, g_HightLigth_NetCode );
/* Create the thermal reliefs */
g_DesignSettings.m_CurrentTrackWidth = lp_tmp;
if( Zone_Exclude_Pads && s_Zone_Create_Thermal_Relief )
Genere_Pad_Connexion( DC, GetScreen()->m_Active_Layer );
g_DesignSettings.m_TrackClearence = save_isol;
GetScreen()->SetModify(); GetScreen()->SetModify();
// free the memory
Board.UnInitBoard();
// restore original values unchanged
Route_Layer_TOP = lay_tmp_TOP;
Route_Layer_BOTTOM = lay_tmp_BOTTOM;
}
/*******************************************************************************/
static void Genere_Segments_Zone( WinEDA_PcbFrame* frame, wxDC* DC, int net_code )
/*******************************************************************************/
/** Function Genere_Segments_Zone()
* Create the zone segments from the routing matrix structure
* Algorithm:
* Search for consecutive cells (flagged "zone") , and create segments
* from the first cell to the last cell in the matrix
* 2 searchs are made
* 1 - From left to right and create horizontal zone segments
* 2 - From top to bottom, and create vertical zone segmùents
* @param net_code = net_code common to all segment zone created
* @param DC = current device context
* @param frame = current WinEDA_PcbFrame
* global: parameter TimeStamp: time stamp common to all segment zone created
*/
{
int row, col;
long current_cell, old_cell;
int ux0 = 0, uy0 = 0, ux1 = 0, uy1 = 0;
int Xmin = frame->m_Pcb->m_BoundaryBox.m_Pos.x;
int Ymin = frame->m_Pcb->m_BoundaryBox.m_Pos.y;
SEGZONE* pt_track;
int layer = frame->GetScreen()->m_Active_Layer;
int nbsegm = 0;
wxString msg;
/* balayage Gauche-> droite */
Affiche_1_Parametre( frame, 64, wxT( "Segm H" ), wxT( "0" ), BROWN );
for( row = 0; row < Nrows; row++ )
{
old_cell = 0;
uy0 = uy1 = (row * g_GridRoutingSize) + Ymin;
for( col = 0; col < Ncols; col++ )
{
current_cell = GetCell( row, col, BOTTOM ) & CELL_is_ZONE;
if( current_cell ) /* ce point doit faire partie d'un segment */
{
ux1 = (col * g_GridRoutingSize) + Xmin;
if( old_cell == 0 )
ux0 = ux1;
}
if( !current_cell || (col == Ncols - 1) ) /* peut etre fin d'un segment */
{
if( (old_cell) && (ux0 != ux1) )
{
/* un segment avait debute de longueur > 0 */
pt_track = new SEGZONE( frame->m_Pcb );
pt_track->SetLayer( layer );
pt_track->SetNet( net_code );
pt_track->m_Width = g_GridRoutingSize;
pt_track->m_Start.x = ux0;
pt_track->m_Start.y = uy0;
pt_track->m_End.x = ux1;
pt_track->m_End.y = uy1;
pt_track->m_TimeStamp = s_TimeStamp;
pt_track->Insert( frame->m_Pcb, NULL );
pt_track->Draw( frame->DrawPanel, DC, GR_OR );
nbsegm++;
}
}
old_cell = current_cell;
}
msg.Printf( wxT( "%d" ), nbsegm );
Affiche_1_Parametre( frame, -1, wxEmptyString, msg, BROWN );
}
Affiche_1_Parametre( frame, 72, wxT( "Segm V" ), wxT( "0" ), BROWN );
for( col = 0; col < Ncols; col++ )
{
old_cell = 0;
ux0 = ux1 = (col * g_GridRoutingSize) + Xmin;
for( row = 0; row < Nrows; row++ )
{
current_cell = GetCell( row, col, BOTTOM ) & CELL_is_ZONE;
if( current_cell ) /* ce point doit faire partie d'un segment */
{
uy1 = (row * g_GridRoutingSize) + Ymin;
if( old_cell == 0 )
uy0 = uy1;
}
if( !current_cell || (row == Nrows - 1) ) /* peut etre fin d'un segment */
{
if( (old_cell) && (uy0 != uy1) )
{
/* un segment avait debute de longueur > 0 */
pt_track = new SEGZONE( frame->m_Pcb );
pt_track->SetLayer( layer );
pt_track->m_Width = g_GridRoutingSize;
pt_track->SetNet( net_code );
pt_track->m_Start.x = ux0;
pt_track->m_Start.y = uy0;
pt_track->m_End.x = ux1;
pt_track->m_End.y = uy1;
pt_track->m_TimeStamp = s_TimeStamp;
pt_track->Insert( frame->m_Pcb, NULL );
pt_track->Draw( frame->DrawPanel, DC, GR_OR );
nbsegm++;
}
}
old_cell = current_cell;
}
msg.Printf( wxT( "%d" ), nbsegm );
Affiche_1_Parametre( frame, -1, wxEmptyString, msg, BROWN );
}
}
/********************************************/
int Propagation( WinEDA_PcbFrame* frame )
/********************************************/
/** Function Propagation()
* An important function to calculate zones
* Uses the routing matrix to fill the cells within the zone
* Search and mark cells within the zone, and agree with DRC options.
* Requirements:
* Start from an initial point, to fill zone
* The zone must have no "copper island"
* Algorithm:
* If the current cell has a neightbour flagged as "cell in the zone", it
* become a cell in the zone
* The first point in the zone is the starting point
* 4 searches within the matrix are made:
* 1 - Left to right and top to bottom
* 2 - Right to left and top to bottom
* 3 - bottom to top and Right to left
* 4 - bottom to top and Left to right
* Given the current cell, for each search, we consider the 2 neightbour cells
* the previous cell on the same line and the previous cell on the same column.
*
* This funtion can request some iterations
* Iterations are made until no cell is added to the zone.
* @return: added cells count (i.e. which the attribute CELL_is_ZONE is set)
*/
{
int row, col, nn;
long current_cell, old_cell_H;
int long* pt_cell_V;
int nbpoints = 0;
#define NO_CELL_ZONE (HOLE | CELL_is_EDGE | CELL_is_ZONE)
wxString msg;
Affiche_1_Parametre( frame, 57, wxT( "Detect" ), msg, CYAN );
Affiche_1_Parametre( frame, -1, wxEmptyString, wxT( "1" ), CYAN );
// Alloc memory to handle 1 line or 1 colunmn on the routing matrix
nn = MAX( Nrows, Ncols ) * sizeof(*pt_cell_V);
pt_cell_V = (long*) MyMalloc( nn );
/* search 1 : from left to right and top to bottom */
memset( pt_cell_V, 0, nn );
for( row = 0; row < Nrows; row++ )
{
old_cell_H = 0;
for( col = 0; col < Ncols; col++ )
{
current_cell = GetCell( row, col, BOTTOM ) & NO_CELL_ZONE;
if( current_cell == 0 ) /* a free cell is found */
{
if( (old_cell_H & CELL_is_ZONE)
|| (pt_cell_V[col] & CELL_is_ZONE) )
{
OrCell( row, col, BOTTOM, CELL_is_ZONE );
current_cell = CELL_is_ZONE;
nbpoints++;
}
}
pt_cell_V[col] = old_cell_H = current_cell;
}
}
/* search 2 : from right to left and top to bottom */
Affiche_1_Parametre( frame, -1, wxEmptyString, wxT( "2" ), CYAN );
memset( pt_cell_V, 0, nn );
for( row = 0; row < Nrows; row++ )
{
old_cell_H = 0;
for( col = Ncols - 1; col >= 0; col-- )
{
current_cell = GetCell( row, col, BOTTOM ) & NO_CELL_ZONE;
if( current_cell == 0 ) /* a free cell is found */
{
if( (old_cell_H & CELL_is_ZONE)
|| (pt_cell_V[col] & CELL_is_ZONE) )
{
OrCell( row, col, BOTTOM, CELL_is_ZONE );
current_cell = CELL_is_ZONE;
nbpoints++;
}
}
pt_cell_V[col] = old_cell_H = current_cell;
}
}
/* search 3 : from bottom to top and right to left balayage */
Affiche_1_Parametre( frame, -1, wxEmptyString, wxT( "3" ), CYAN );
memset( pt_cell_V, 0, nn );
for( col = Ncols - 1; col >= 0; col-- )
{
old_cell_H = 0;
for( row = Nrows - 1; row >= 0; row-- )
{
current_cell = GetCell( row, col, BOTTOM ) & NO_CELL_ZONE;
if( current_cell == 0 ) /* a free cell is found */
{
if( (old_cell_H & CELL_is_ZONE)
|| (pt_cell_V[row] & CELL_is_ZONE) )
{
OrCell( row, col, BOTTOM, CELL_is_ZONE );
current_cell = CELL_is_ZONE;
nbpoints++;
}
}
pt_cell_V[row] = old_cell_H = current_cell;
}
}
/* search 4 : from bottom to top and left to right */
Affiche_1_Parametre( frame, -1, wxEmptyString, wxT( "4" ), CYAN );
memset( pt_cell_V, 0, nn );
for( col = 0; col < Ncols; col++ )
{
old_cell_H = 0;
for( row = Nrows - 1; row >= 0; row-- )
{
current_cell = GetCell( row, col, BOTTOM ) & NO_CELL_ZONE;
if( current_cell == 0 ) /* a free cell is found */
{
if( (old_cell_H & CELL_is_ZONE)
|| (pt_cell_V[row] & CELL_is_ZONE) )
{
OrCell( row, col, BOTTOM, CELL_is_ZONE );
current_cell = CELL_is_ZONE;
nbpoints++;
}
}
pt_cell_V[row] = old_cell_H = current_cell;
}
}
MyFree( pt_cell_V );
return nbpoints;
}
/*****************************************************************************/
bool WinEDA_PcbFrame::Genere_Pad_Connexion( wxDC* DC, int layer )
/*****************************************************************************/
/* Create the thermal relief for each pad in the zone:
* this is 4 small segments from the pad to the zone
*/
{
int ii, jj, Npads;
D_PAD* pt_pad;
LISTE_PAD* pt_liste_pad;
TRACK* pt_track, * loctrack;
int angle;
int cX, cY, dx, dy;
int sommet[4][2];
wxString msg;
if( m_Pcb->m_Zone == NULL )
return FALSE; /* error: no zone */
if( m_Pcb->m_Zone->m_TimeStamp != s_TimeStamp ) /* error: this is not the new zone */
return FALSE;
/* Count the pads, i.e. the thermal relief to create count, and displays it */
Affiche_1_Parametre( this, 50, wxT( "NPads" ), wxT( " " ), CYAN );
pt_liste_pad = (LISTE_PAD*) m_Pcb->m_Pads;
for( ii = 0, Npads = 0; ii < m_Pcb->m_NbPads; ii++, pt_liste_pad++ )
{
pt_pad = *pt_liste_pad;
/* Search pads relative to the selected net code */
if( pt_pad->GetNet() != g_HightLigth_NetCode )
continue;
/* Is the pad on the active layer ? */
if( (pt_pad->m_Masque_Layer & g_TabOneLayerMask[layer]) == 0 )
continue;
Npads++;
}
msg.Printf( wxT( "%d" ), Npads );
Affiche_1_Parametre( this, -1, wxEmptyString, msg, CYAN );
/* Create the thermal reliefs */
Affiche_1_Parametre( this, 57, wxT( "Pads" ), wxT( " " ), CYAN );
pt_liste_pad = (LISTE_PAD*) m_Pcb->m_Pads;
for( ii = 0, Npads = 0; ii < m_Pcb->m_NbPads; ii++, pt_liste_pad++ )
{
pt_pad = *pt_liste_pad;
/* Search pads relative to the selected net code */
if( pt_pad->GetNet() != g_HightLigth_NetCode )
continue;
/* Is the pad on the active layer ? */
if( (pt_pad->m_Masque_Layer & g_TabOneLayerMask[layer]) == 0 )
continue;
/* Create the theram relief for the current pad */
Npads++;
msg.Printf( wxT( "%d" ), Npads );
Affiche_1_Parametre( this, -1, wxEmptyString, msg, CYAN );
cX = pt_pad->GetPosition().x;
cY = pt_pad->GetPosition().y;
dx = pt_pad->m_Size.x / 2;
dy = pt_pad->m_Size.y / 2;
dx += g_DesignSettings.m_TrackClearence + g_GridRoutingSize;
dy += g_DesignSettings.m_TrackClearence + g_GridRoutingSize;
if( pt_pad->m_PadShape == TRAPEZE )
{
dx += abs( pt_pad->m_DeltaSize.y ) / 2;
dy += abs( pt_pad->m_DeltaSize.x ) / 2;
}
/* calculate the 4 segment coordintes (starting from the pad centre cX,cY) */
sommet[0][0] = 0; sommet[0][1] = -dy;
sommet[1][0] = -dx; sommet[1][1] = 0;
sommet[2][0] = 0; sommet[2][1] = dy;
sommet[3][0] = dx; sommet[3][1] = 0;
angle = pt_pad->m_Orient;
for( jj = 0; jj < 4; jj++ )
{
RotatePoint( &sommet[jj][0], &sommet[jj][1], angle );
pt_track = new SEGZONE( m_Pcb );
pt_track->SetLayer( layer );
pt_track->m_Width = g_DesignSettings.m_CurrentTrackWidth;
pt_track->SetNet( g_HightLigth_NetCode );
pt_track->start = pt_pad;
pt_track->m_Start.x = cX; pt_track->m_Start.y = cY;
pt_track->m_End.x = cX + sommet[jj][0];
pt_track->m_End.y = cY + sommet[jj][1];
pt_track->m_TimeStamp = s_TimeStamp;
/* Test if the segment is allowed */
if( BAD_DRC==m_drc->DrcBlind( pt_track, m_Pcb->m_Track ) )
{
delete pt_track;
continue;
}
/* Search for a zone segment */
loctrack = Locate_Zone( m_Pcb->m_Zone, pt_track->m_End, layer );
if( (loctrack == NULL) || (loctrack->m_TimeStamp != s_TimeStamp) )
{
delete pt_track;
continue;
}
pt_track->Insert( m_Pcb, NULL );
pt_track->Draw( DrawPanel, DC, GR_OR );
}
}
return TRUE;
} }

View File

@ -49,18 +49,17 @@
////@begin control identifiers ////@begin control identifiers
#define ID_DIALOG 10000 #define ID_DIALOG 10000
// #define SYMBOL_WINEDA_ZONEFRAME_STYLE wxCAPTION|wxRESIZE_BORDER|wxSYSTEM_MENU|wxSTAY_ON_TOP|wxCLOSE_BOX
#define SYMBOL_WINEDA_ZONEFRAME_STYLE wxCAPTION|wxSYSTEM_MENU|wxCLOSE_BOX|MAYBE_RESIZE_BORDER
#define SYMBOL_WINEDA_ZONEFRAME_TITLE _("Fill Zones Options")
#define SYMBOL_WINEDA_ZONEFRAME_IDNAME ID_DIALOG
#define SYMBOL_WINEDA_ZONEFRAME_SIZE wxSize(400, 300)
#define SYMBOL_WINEDA_ZONEFRAME_POSITION wxDefaultPosition
#define ID_RADIOBOX 10001 #define ID_RADIOBOX 10001
#define ID_TEXTCTRL 10006 #define ID_TEXTCTRL 10006
#define ID_RADIOBOX1 10004 #define ID_RADIOBOX1 10004
#define ID_RADIOBOX2 10005 #define ID_RADIOBOX2 10005
#define ID_FILL_ZONE 10002 #define ID_FILL_ZONE 10002
#define ID_SET_OPTIONS_ZONE 10003 #define ID_SET_OPTIONS_ZONE 10003
#define SYMBOL_WINEDA_ZONEFRAME_STYLE wxCAPTION|wxSYSTEM_MENU|wxCLOSE_BOX|MAYBE_RESIZE_BORDER
#define SYMBOL_WINEDA_ZONEFRAME_TITLE _("Fill Zones Options")
#define SYMBOL_WINEDA_ZONEFRAME_IDNAME ID_DIALOG
#define SYMBOL_WINEDA_ZONEFRAME_SIZE wxSize(400, 300)
#define SYMBOL_WINEDA_ZONEFRAME_POSITION wxDefaultPosition
////@end control identifiers ////@end control identifiers
/*! /*!

582
pcbnew/zones_by_polygon.cpp Normal file
View File

@ -0,0 +1,582 @@
/////////////////////////////////////////////////////////////////////////////
// Name: zones_by_polygon.cpp
// Purpose:
// Author: jean-pierre Charras
// Modified by:
// Created: 25/01/2006 11:35:19
// RCS-ID:
// Copyright: GNU License
// Licence: GNU License
/////////////////////////////////////////////////////////////////////////////
// Generated by DialogBlocks (unregistered), 25/01/2006 11:35:19
#if defined (__GNUG__) && !defined (NO_GCC_PRAGMA)
#pragma implementation "dialog_zones_by_polygon.h"
#endif
#include "fctsys.h"
#include "gr_basic.h"
#include "common.h"
#include "pcbnew.h"
#include "autorout.h"
#include "cell.h"
#include "trigo.h"
#include "protos.h"
// For compilers that support precompilation, includes "wx/wx.h".
#include "wx/wxprec.h"
#ifdef __BORLANDC__
#pragma hdrstop
#endif
#ifndef WX_PRECOMP
#include "wx/wx.h"
#endif
////@begin includes
////@end includes
////@begin XPM images
////@end XPM images
/* Imported functions */
void Build_Zone( WinEDA_PcbFrame* frame, wxDC* DC, int net_code,
bool Zone_Exclude_Pads, bool Zone_Create_Thermal_Relief );
/* Local functions */
static void Display_Zone_Netname( WinEDA_PcbFrame* frame );
static void Exit_Zones( WinEDA_DrawPanel* Panel, wxDC* DC );
static void Show_Zone_Edge_While_MoveMouse( WinEDA_DrawPanel* panel, wxDC* DC, bool erase );
/* Local variables */
static bool Zone_45_Only = FALSE;
static bool Zone_Exclude_Pads = TRUE;
static bool s_Zone_Create_Thermal_Relief = TRUE;
static int s_Zone_Layer; // Layer used to put the current zone
static int s_NetcodeSelection; // Net code selection for the current zone
static int s_NetSortingOpt; // For the net list: sort option (by alphabetic order or bay pad count order
#define ZONE_NET_SORT_OPTION_KEY wxT("Zone_NetSort_Opt")
#include "dialog_zones_by_polygon.cpp"
/**************************************************************/
void WinEDA_PcbFrame::Edit_Zone_Width( wxDC* DC, SEGZONE* aZone )
/**************************************************************/
/* Edite (change la largeur des segments) la zone Zone.
* La zone est constituee des segments zones de meme TimeStamp
*/
{
bool modify = FALSE;
double f_new_width;
int w_tmp;
wxString Line;
wxString Msg( _( "New zone segment width: " ) );
if( aZone == NULL )
return;
f_new_width = To_User_Unit( g_UnitMetric, aZone->m_Width, GetScreen()->GetInternalUnits() );
Line.Printf( wxT( "%.4f" ), f_new_width );
Msg += g_UnitMetric ? wxT( "(mm)" ) : wxT( "(\")" );
if( Get_Message( Msg, Line, this ) != 0 )
return;
w_tmp = g_DesignSettings.m_CurrentTrackWidth;
Line.ToDouble( &f_new_width );
g_DesignSettings.m_CurrentTrackWidth = From_User_Unit( g_UnitMetric,
f_new_width, GetScreen(
)->GetInternalUnits() );
for( SEGZONE* zone = m_Pcb->m_Zone; zone; zone = zone->Next() )
{
if( zone->m_TimeStamp == aZone->m_TimeStamp )
{
modify = TRUE;
Edit_TrackSegm_Width( DC, zone );
}
}
g_DesignSettings.m_CurrentTrackWidth = w_tmp;
if( modify )
{
GetScreen()->SetModify();
DrawPanel->Refresh();
}
}
/**********************************************************/
void WinEDA_PcbFrame::Delete_Zone( wxDC* DC, SEGZONE* aZone )
/**********************************************************/
/* Remove the zone which include the segment aZone.
* A zone is a group of segments which have the same TimeStamp
*/
{
if( aZone == NULL )
return;
int nb_segm = 0;
bool modify = FALSE;
unsigned long TimeStamp = aZone->m_TimeStamp; // Save reference time stamp (aZone will be deleted)
SEGZONE* next;
for( SEGZONE* zone = m_Pcb->m_Zone; zone != NULL; zone = next )
{
next = zone->Next();
if( zone->m_TimeStamp == TimeStamp )
{
modify = TRUE;
/* Erase segment from screen */
Trace_Une_Piste( DrawPanel, DC, zone, nb_segm, GR_XOR );
/* remove item from linked list and free memory */
zone->DeleteStructure();
}
}
if( modify )
{
GetScreen()->SetModify();
GetScreen()->SetRefreshReq();
}
}
/*****************************************************************************/
EDGE_ZONE* WinEDA_PcbFrame::Del_SegmEdgeZone( wxDC* DC, EDGE_ZONE* edge_zone )
/*****************************************************************************/
/* Routine d'effacement du segment de limite zone en cours de trace */
{
EDGE_ZONE* segm;
if( m_Pcb->m_CurrentLimitZone )
segm = m_Pcb->m_CurrentLimitZone;
else
segm = edge_zone;
if( segm == NULL )
return NULL;
Trace_DrawSegmentPcb( DrawPanel, DC, segm, GR_XOR );
m_Pcb->m_CurrentLimitZone = segm->Next();
delete segm;
segm = m_Pcb->m_CurrentLimitZone;
SetCurItem( segm );
if( segm )
{
segm->Pback = NULL;
if( DrawPanel->ManageCurseur )
DrawPanel->ManageCurseur( DrawPanel, DC, TRUE );
}
else
{
DrawPanel->ManageCurseur = NULL;
DrawPanel->ForceCloseManageCurseur = NULL;
SetCurItem( NULL );
}
return segm;
}
/*********************************************/
void WinEDA_PcbFrame::CaptureNetName( wxDC* DC )
/*********************************************/
/* routine permettant de capturer le nom net net (netcode) d'un pad
* ou d'une piste pour l'utiliser comme netcode de zone
*/
{
D_PAD* pt_pad = 0;
TRACK* adrpiste;
MODULE* Module;
int masquelayer = g_TabOneLayerMask[GetScreen()->m_Active_Layer];
int netcode;
netcode = -1;
MsgPanel->EraseMsgBox();
adrpiste = Locate_Pistes( m_Pcb->m_Track, masquelayer, CURSEUR_OFF_GRILLE );
if( adrpiste == NULL )
{
pt_pad = Locate_Any_Pad( m_Pcb, CURSEUR_OFF_GRILLE );
if( pt_pad ) /* Verif qu'il est bien sur la couche active */
{
Module = (MODULE*) pt_pad->m_Parent;
pt_pad = Locate_Pads( Module, g_TabOneLayerMask[GetScreen()->m_Active_Layer],
CURSEUR_OFF_GRILLE );
}
if( pt_pad )
{
pt_pad->Display_Infos( this );
netcode = pt_pad->GetNet();
}
}
else
{
adrpiste->Display_Infos( this );
netcode = adrpiste->GetNet();
}
// Mise en surbrillance du net
if( g_HightLigt_Status )
Hight_Light( DC );
g_HightLigth_NetCode = netcode;
if( g_HightLigth_NetCode >= 0 )
{
Hight_Light( DC );
}
/* Affichage du net selectionne pour la zone a tracer */
Display_Zone_Netname( this );
}
/*******************************************************/
static void Display_Zone_Netname( WinEDA_PcbFrame* frame )
/*******************************************************/
/*
* Affiche le net_code et le nom de net couramment selectionne
*/
{
EQUIPOT* pt_equipot;
wxString line;
pt_equipot = frame->m_Pcb->m_Equipots;
if( g_HightLigth_NetCode > 0 )
{
for( ; pt_equipot != NULL; pt_equipot = (EQUIPOT*) pt_equipot->Pnext )
{
if( pt_equipot->GetNet() == g_HightLigth_NetCode )
break;
}
if( pt_equipot )
{
line.Printf( wxT( "Zone: Net[%d] <%s>" ), g_HightLigth_NetCode,
pt_equipot->m_Netname.GetData() );
}
else
line.Printf( wxT( "Zone: NetCode[%d], Equipot not found" ),
g_HightLigth_NetCode );
}
line = _( "Zone: No net selected" );
frame->Affiche_Message( line );
}
/********************************************************/
static void Exit_Zones( WinEDA_DrawPanel* Panel, wxDC* DC )
/********************************************************/
/**
* Function Exit_Zones
* cancels the Begin_Zone state if at least one EDGE_ZONE has been created.
*/
{
WinEDA_PcbFrame* pcbframe = (WinEDA_PcbFrame*) Panel->m_Parent;
if( pcbframe->m_Pcb->m_CurrentLimitZone )
{
if( Panel->ManageCurseur ) // trace in progress
{
Panel->ManageCurseur( Panel, DC, 0 );
}
pcbframe->DelLimitesZone( DC, TRUE );
}
Panel->ManageCurseur = NULL;
Panel->ForceCloseManageCurseur = NULL;
pcbframe->SetCurItem( NULL );
}
/**************************************************************/
void WinEDA_BasePcbFrame::DelLimitesZone( wxDC* DC, bool Redraw )
/**************************************************************/
{
EDGE_ZONE* segment;
EDGE_ZONE* next;
if( m_Pcb->m_CurrentLimitZone == NULL )
return;
if( !IsOK( this, _( "Delete Current Zone Edges" ) ) )
return;
// erase the old zone border, one segment at a time
for( segment = m_Pcb->m_CurrentLimitZone; segment; segment = next )
{
next = segment->Next();
if( Redraw && DC )
Trace_DrawSegmentPcb( DrawPanel, DC, segment, GR_XOR );
delete segment;
}
m_Pcb->m_CurrentLimitZone = NULL;
SetCurItem( NULL );
}
/**
* Function Begin_Zone
* either initializes the first segment of a new zone, or adds an
* intermediate segment.
*/
EDGE_ZONE* WinEDA_PcbFrame::Begin_Zone()
{
EDGE_ZONE* oldedge;
EDGE_ZONE* newedge = NULL;
oldedge = m_Pcb->m_CurrentLimitZone;
// if first segment
if( (m_Pcb->m_CurrentLimitZone == NULL ) /* debut reel du trace */
|| (DrawPanel->ManageCurseur == NULL) ) /* reprise d'un trace complementaire */
{
newedge = new EDGE_ZONE( m_Pcb );
newedge->m_Flags = IS_NEW | STARTPOINT | IS_MOVED;
newedge->m_Start = newedge->m_End = GetScreen()->m_Curseur;
newedge->SetLayer( GetScreen()->m_Active_Layer );
// link into list:
newedge->Pnext = oldedge;
if( oldedge )
oldedge->Pback = newedge;
m_Pcb->m_CurrentLimitZone = newedge;
DrawPanel->ManageCurseur = Show_Zone_Edge_While_MoveMouse;
DrawPanel->ForceCloseManageCurseur = Exit_Zones;
}
// edge in progress:
else /* piste en cours : les coord du point d'arrivee ont ete mises
* a jour par la routine Show_Zone_Edge_While_MoveMouse*/
{
if( oldedge->m_Start != oldedge->m_End )
{
oldedge->m_Flags &= ~(IS_NEW | IS_MOVED);
newedge = new EDGE_ZONE( oldedge );
newedge->m_Flags = IS_NEW | IS_MOVED;
newedge->m_Start = newedge->m_End = oldedge->m_End;
newedge->SetLayer( GetScreen()->m_Active_Layer );
// link into list:
newedge->Pnext = oldedge;
oldedge->Pback = newedge;
m_Pcb->m_CurrentLimitZone = newedge;
}
}
return newedge;
}
/*********************************************/
void WinEDA_PcbFrame::End_Zone( wxDC* DC )
/*********************************************/
/*
* Routine de fin de trace d'une zone (succession de segments)
*/
{
EDGE_ZONE* edge;
if( m_Pcb->m_CurrentLimitZone )
{
Begin_Zone();
/* le dernier point genere est de longueur tj nulle donc inutile. */
/* il sera raccorde au point de depart */
edge = m_Pcb->m_CurrentLimitZone;
edge->m_Flags &= ~(IS_NEW | IS_MOVED);
while( edge && edge->Next() )
{
edge = edge->Next();
if( edge->m_Flags & STARTPOINT )
break;
edge->m_Flags &= ~(IS_NEW | IS_MOVED);
}
if( edge )
{
edge->m_Flags &= ~(IS_NEW | IS_MOVED);
m_Pcb->m_CurrentLimitZone->m_End = edge->m_Start;
}
Trace_DrawSegmentPcb( DrawPanel, DC, m_Pcb->m_CurrentLimitZone, GR_XOR );
}
DrawPanel->ManageCurseur = NULL;
DrawPanel->ForceCloseManageCurseur = NULL;
}
/******************************************************************************************/
static void Show_Zone_Edge_While_MoveMouse( WinEDA_DrawPanel* panel, wxDC* DC, bool erase )
/******************************************************************************************/
/* redessin du contour de la piste lors des deplacements de la souris
*/
{
EDGE_ZONE* edge;
EDGE_ZONE* currentEdge;
WinEDA_PcbFrame* pcbframe = (WinEDA_PcbFrame*) panel->m_Parent;
if( pcbframe->m_Pcb->m_CurrentLimitZone == NULL )
return;
/* efface ancienne position si elle a ete deja dessinee */
if( erase )
{
edge = pcbframe->m_Pcb->m_CurrentLimitZone;
// for( ; edge; edge = edge->Next() )
{
Trace_DrawSegmentPcb( panel, DC, edge, GR_XOR );
}
}
/* mise a jour de la couche */
for( edge = pcbframe->m_Pcb->m_CurrentLimitZone; edge; edge = edge->Next() )
{
edge->SetLayer( pcbframe->GetScreen()->m_Active_Layer );
}
/* dessin de la nouvelle piste : mise a jour du point d'arrivee */
currentEdge = pcbframe->m_Pcb->m_CurrentLimitZone;
if( Zone_45_Only )
{
// Calcul de l'extremite de la piste pour orientations permises:
// horiz,vertical ou 45 degre
currentEdge->m_End = pcbframe->GetScreen()->m_Curseur;
Calcule_Coord_Extremite_45( currentEdge->m_Start.x, currentEdge->m_Start.y,
&currentEdge->m_End.x, &currentEdge->m_End.y );
}
else /* ici l'angle d'inclinaison est quelconque */
{
currentEdge->m_End = pcbframe->GetScreen()->m_Curseur;
}
// for( ; currentEdge; currentEdge = currentEdge->Next() )
{
Trace_DrawSegmentPcb( panel, DC, currentEdge, GR_XOR );
}
}
/**********************************************/
void WinEDA_PcbFrame::Fill_Zone( wxDC* DC )
/**********************************************/
/** Function Fill_Zone()
* Init the zone filling
* If a zone edge is found, it is used.
* Otherwise the whole board is filled by the zone
* The zone edge is a frontier, and can be complex. So non filled zones can be achieved
* The zone is put on the active layer
* If a net is hightlighted, the zone will be attached to this net
* The filling start from a starting point.
* If a net is selected, all tracks attached to this net are also starting points
*/
{
EQUIPOT* pt_equipot;
wxPoint ZoneStartFill;
wxString msg;
MsgPanel->EraseMsgBox();
if( m_Pcb->ComputeBoundaryBox() == FALSE )
{
DisplayError( this, wxT( "Board is empty!" ), 10 );
return;
}
if( m_Parent && m_Parent->m_EDA_Config )
{
s_NetSortingOpt = m_Parent->m_EDA_Config->Read( ZONE_NET_SORT_OPTION_KEY, (long) BOARD::PAD_CNT_SORT );
}
int NetSortingOptImg = s_NetSortingOpt;
DrawPanel->m_IgnoreMouseEvents = TRUE;
WinEDA_ZoneFrame* frame = new WinEDA_ZoneFrame( this );
int abrd = frame->ShowModal();
frame->Destroy();
DrawPanel->MouseToCursorSchema();
DrawPanel->m_IgnoreMouseEvents = FALSE;
if( (NetSortingOptImg != s_NetSortingOpt ) && m_Parent && m_Parent->m_EDA_Config )
{
m_Parent->m_EDA_Config->Write( ZONE_NET_SORT_OPTION_KEY, (long) s_NetSortingOpt );
}
if( abrd )
return;
// set all the EDGE_ZONEs to the currently active layer and redraw them
// on that layer.
GetScreen()->m_Active_Layer = s_Zone_Layer;
EDGE_ZONE* PtLim = m_Pcb->m_CurrentLimitZone;
for( ; PtLim != NULL; PtLim = PtLim->Next() )
{
Trace_DrawSegmentPcb( DrawPanel, DC, PtLim, GR_XOR );
PtLim->SetLayer( s_Zone_Layer );
Trace_DrawSegmentPcb( DrawPanel, DC, PtLim, GR_XOR );
}
/* Show the NetName */
if( (g_HightLigth_NetCode > 0) && (g_HightLigth_NetCode != s_NetcodeSelection) )
{
Hight_Light( DC );
g_HightLigth_NetCode = s_NetcodeSelection;
Hight_Light( DC );
}
g_HightLigth_NetCode = s_NetcodeSelection;
if( g_HightLigth_NetCode > 0 )
{
pt_equipot = m_Pcb->FindNet( g_HightLigth_NetCode );
if( pt_equipot == NULL )
{
if( g_HightLigth_NetCode > 0 )
DisplayError( this, wxT( "Unable to find Net name" ) );
}
else
msg = pt_equipot->m_Netname;
}
else
msg = _( "No Net" );
Affiche_1_Parametre( this, 22, _( "NetName" ), msg, RED );
Build_Zone( this, DC, g_HightLigth_NetCode, Zone_Exclude_Pads, s_Zone_Create_Thermal_Relief );
GetScreen()->SetModify();
}

View File

@ -25,8 +25,17 @@
#define abs(x) (((x) >=0) ? (x) : (-(x))) #define abs(x) (((x) >=0) ? (x) : (-(x)))
#endif #endif
#ifndef min
#define min(x,y) (((x) <= (y)) ? (x) : (y))
#endif
#ifndef max
#define max(x,y) (((x) >= (y)) ? (x) : (y))
#endif
#define TRACE printf #define TRACE printf
#define ASSERT(x) // todo : change to DEBUG, under wxWidgets #define ASSERT(x) // todo : change to wxASSERT, under wxWidgets
#endif // ifndef DEFS_MACROS_H #endif // ifndef DEFS_MACROS_H

View File

@ -7,10 +7,14 @@ COMMON =
OBJECTS= \ OBJECTS= \
GenericPolygonClipperLibrary.o \ GenericPolygonClipperLibrary.o \
php_polygon.o\ php_polygon.o\
php_polygon_vertex.o php_polygon_vertex.o\
PolyLine.o\
math_for_graphics.o
GenericPolygonClipperLibrary.o: GenericPolygonClipperLibrary.cpp GenericPolygonClipperLibrary.h GenericPolygonClipperLibrary.o: GenericPolygonClipperLibrary.cpp GenericPolygonClipperLibrary.h
php_polygon.o: php_polygon.cpp php_polygon.h php_polygon_vertex.h defs-macros.h php_polygon.o: php_polygon.cpp php_polygon.h php_polygon_vertex.h defs-macros.h
#polygon1.o: polygon1.cpp polyarea.h vectmatr.h #polygon1.o: polygon1.cpp polyarea.h vectmatr.h
math_for_graphics.o: math_for_graphics.cpp math_for_graphics.h

View File

@ -584,10 +584,7 @@ void WinEDA_DrawFrame::OnZoom( int zoom_type )
* replacé au centre de l'ecran * replacé au centre de l'ecran
*/ */
{ {
D(printf("OnZoom x=%d, y=%d\n", if( DrawPanel == NULL )
m_CurrentScreen->m_Curseur.x, m_CurrentScreen->m_Curseur.y );)
if( DrawPanel == NULL )
return; return;
bool move_mouse_cursor = FALSE; bool move_mouse_cursor = FALSE;