Gerbview: Added support of arcs in polygons outlines. Need more tests, but works.
This commit is contained in:
parent
32dfdb4844
commit
c4b37d77bd
|
@ -3,6 +3,15 @@ KiCad ChangeLog 2009
|
|||
|
||||
Please add newer entries at the top, list the date and your name with
|
||||
email address.
|
||||
|
||||
2010-Jan-08 UPDATE Jean-Pierre Charras <jean-pierre.charras@gipsa-lab.inpg.fr>
|
||||
================================================================================
|
||||
++Gerbview
|
||||
Added support of arcs in polygons outlines.
|
||||
Needed to show copper areas in some gerber files
|
||||
Not fully tested but works better than without this support...
|
||||
|
||||
|
||||
2010-Jan-03 UPDATE Jean-Pierre Charras <jean-pierre.charras@gipsa-lab.inpg.fr>
|
||||
================================================================================
|
||||
++pcbnew
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
#endif
|
||||
|
||||
#ifndef KICAD_BUILD_VERSION
|
||||
#define KICAD_BUILD_VERSION "(2010-01-05)"
|
||||
#define KICAD_BUILD_VERSION "(2010-01-08)"
|
||||
#endif
|
||||
|
||||
#define VERSION_STABILITY "unstable"
|
||||
|
|
|
@ -166,7 +166,7 @@ void DIALOG_EESCHEMA_CONFIG::OnOkClick( wxCommandEvent& event )
|
|||
WinEDA_LibeditFrame::EnsureActiveLibExists();
|
||||
}
|
||||
|
||||
m_Parent->SaveProjectFile( this );
|
||||
m_Parent->SaveProjectFile( this, false );
|
||||
EndModal( wxID_OK );
|
||||
}
|
||||
|
||||
|
|
|
@ -43,7 +43,7 @@ void WinEDA_SchematicFrame::Process_Config( wxCommandEvent& event )
|
|||
break;
|
||||
|
||||
case ID_CONFIG_SAVE:
|
||||
SaveProjectFile( this );
|
||||
SaveProjectFile( this, false );
|
||||
break;
|
||||
|
||||
case ID_CONFIG_READ:
|
||||
|
@ -316,16 +316,18 @@ bool WinEDA_SchematicFrame::LoadProjectFile( const wxString& CfgFileName,
|
|||
/*
|
||||
* Save the Kicad project file (*.pro) settings specific to EESchema.
|
||||
*/
|
||||
void WinEDA_SchematicFrame::SaveProjectFile( wxWindow* displayframe )
|
||||
void WinEDA_SchematicFrame::SaveProjectFile( wxWindow* displayframe, bool askoverwrite )
|
||||
{
|
||||
wxFileName fn;
|
||||
|
||||
fn = g_RootSheet->m_AssociatedScreen->m_FileName /*ConfigFileName*/;
|
||||
fn.SetExt( ProjectFileExtension );
|
||||
|
||||
int options = wxFD_SAVE;
|
||||
if( askoverwrite )
|
||||
options |= wxFD_OVERWRITE_PROMPT;
|
||||
wxFileDialog dlg( this, _( "Save Project Settings" ), wxGetCwd(),
|
||||
fn.GetFullName(), ProjectFileWildcard,
|
||||
wxFD_SAVE | wxFD_OVERWRITE_PROMPT );
|
||||
fn.GetFullName(), ProjectFileWildcard, options );
|
||||
|
||||
if( dlg.ShowModal() == wxID_CANCEL )
|
||||
return;
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,51 @@
|
|||
*
|
||||
%FSLAX35Y35*%
|
||||
%MOMM*%
|
||||
%ADD10C,0.085000*%
|
||||
%ADD11C,1.000000*%
|
||||
%IPPOS*%
|
||||
%LNl2p*%
|
||||
%LPD*%
|
||||
%SRX1Y1I0J0*%
|
||||
G01*
|
||||
G75*
|
||||
G36*
|
||||
X-824649Y824737D02*
|
||||
X-824642Y824746D01*
|
||||
X-824637Y824748D01*
|
||||
X-600285Y824596D01*
|
||||
G02X-596337Y813997I0J-6035D01*
|
||||
G01X-596759Y813502D01*
|
||||
X-599070Y812402D01*
|
||||
X-599079Y812403D01*
|
||||
X-600633Y812842D01*
|
||||
G03X-591714Y760887I-18257J-29877D01*
|
||||
G01X-589396Y761987D01*
|
||||
X-587850Y761553D01*
|
||||
G03X-543350Y814584I18275J29851D01*
|
||||
G02X-538846Y824554I4504J3968D01*
|
||||
G01X-387906Y824445D01*
|
||||
X-387901Y824439D01*
|
||||
X-387898Y718310D01*
|
||||
X-387892Y718296D01*
|
||||
X-387887Y718290D01*
|
||||
X-337968Y678268D01*
|
||||
X-337966Y678263D01*
|
||||
X-337746Y625972D01*
|
||||
G02X-347743Y621473I-6001J-23D01*
|
||||
G03X-394478Y621365I-23307J-26119D01*
|
||||
G02X-402955Y621809I-4016J4477D01*
|
||||
G01X-407368Y626784D01*
|
||||
X-409076Y628288D01*
|
||||
G02X-406164Y638849I3817J4630D01*
|
||||
G03X-421754Y706900I-5285J34600D01*
|
||||
G01X-699601D01*
|
||||
G03X-766967Y720229I-35002J0D01*
|
||||
G02X-771614Y718929I-2844J1211D01*
|
||||
G03X-817118Y687087I-10523J-33398D01*
|
||||
G03X-817151Y685566I34972J-1522D01*
|
||||
G01X-823562D01*
|
||||
X-824649Y824737D01*
|
||||
G37*
|
||||
|
||||
M02*
|
|
@ -19,15 +19,11 @@ bool WinEDA_GerberFrame::Clear_Pcb( bool query )
|
|||
if( GetBoard() == NULL )
|
||||
return FALSE;
|
||||
|
||||
if( query )
|
||||
{
|
||||
if( GetBoard()->m_Drawings || GetBoard()->m_Track
|
||||
|| GetBoard()->m_Zone )
|
||||
if( query && GetScreen()->IsModify() )
|
||||
{
|
||||
if( !IsOK( this, _( "Current data will be lost?" ) ) )
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
GetBoard()->m_Drawings.DeleteAll();
|
||||
|
||||
|
|
|
@ -115,7 +115,6 @@ bool WinEDA_GerberFrame::Read_GERBER_File( const wxString& GERBER_FullFileName,
|
|||
char* text;
|
||||
int layer; /* current layer used in gerbview */
|
||||
GERBER* gerber;
|
||||
wxPoint pos;
|
||||
int error = 0;
|
||||
|
||||
layer = GetScreen()->m_Active_Layer;
|
||||
|
@ -201,7 +200,7 @@ bool WinEDA_GerberFrame::Read_GERBER_File( const wxString& GERBER_FullFileName,
|
|||
|
||||
case 'X':
|
||||
case 'Y': /* Move or draw command */
|
||||
pos = gerber->ReadXYCoord( text );
|
||||
gerber->m_CurrentPos = gerber->ReadXYCoord( text );
|
||||
if( *text == '*' ) // command like X12550Y19250*
|
||||
{
|
||||
gerber->Execute_DCODE_Command( this, text,
|
||||
|
@ -211,7 +210,7 @@ bool WinEDA_GerberFrame::Read_GERBER_File( const wxString& GERBER_FullFileName,
|
|||
|
||||
case 'I':
|
||||
case 'J': /* Auxiliary Move command */
|
||||
pos = gerber->ReadIJCoord( text );
|
||||
gerber->m_IJPos = gerber->ReadIJCoord( text );
|
||||
break;
|
||||
|
||||
case '%':
|
||||
|
|
|
@ -9,8 +9,11 @@
|
|||
#include "macros.h"
|
||||
#include "gerbview.h"
|
||||
#include "pcbplot.h"
|
||||
#include "trigo.h"
|
||||
#include "protos.h"
|
||||
|
||||
#include <math.h>
|
||||
|
||||
#define IsNumber( x ) ( ( ( (x) >= '0' ) && ( (x) <='9' ) ) \
|
||||
|| ( (x) == '-' ) || ( (x) == '+' ) || ( (x) == '.' ) )
|
||||
|
||||
|
@ -373,13 +376,143 @@ static void fillArcTRACK( TRACK* aTrack, int Dcode_index, int aLayer,
|
|||
}
|
||||
|
||||
|
||||
/**
|
||||
* Function fillArcPOLY
|
||||
* creates an arc G code when found in poly outlines.
|
||||
* <p>
|
||||
* if multiquadrant == true : arc can be 0 to 360 degrees
|
||||
* and \a rel_center is the center coordinate relative to start point.
|
||||
* <p>
|
||||
* if multiquadrant == false arc can be only 0 to 90 deg,
|
||||
* and only in the same quadrant :
|
||||
* <ul>
|
||||
* <li> absolute angle 0 to 90 (quadrant 1) or
|
||||
* <li> absolute angle 90 to 180 (quadrant 2) or
|
||||
* <li> absolute angle 180 to 270 (quadrant 3) or
|
||||
* <li> absolute angle 270 to 0 (quadrant 4)
|
||||
* </ul><p>
|
||||
* @param aPcb is the board.
|
||||
* @param aLayer is the layer index to set into the TRACK
|
||||
* @param aStart is the starting point
|
||||
* @param aEnd is the ending point
|
||||
* @param rel_center is the center coordinate relative to start point,
|
||||
* given in ABSOLUTE VALUE and the sign of values x et y de rel_center
|
||||
* must be calculated from the previously given constraint: arc only in the
|
||||
* same quadrant.
|
||||
* @param aDiameter The diameter of the round flash
|
||||
* @param aWidth is the pen width.
|
||||
* @param isDark True if flash is positive and should use a drawing
|
||||
* color other than the background color, else use the background color
|
||||
* when drawing so that an erasure happens.
|
||||
* @return a pointer to the first segment created
|
||||
*/
|
||||
static SEGZONE * fillArcPOLY( BOARD * aPcb, int aLayer,
|
||||
const wxPoint& aStart, const wxPoint& aEnd,
|
||||
const wxPoint& rel_center,
|
||||
bool clockwise, bool multiquadrant, bool isDark )
|
||||
{
|
||||
/* in order to calculate arc parameters, we use fillArcTRACK
|
||||
* so we muse create a dummy track and use its geometric parmeters
|
||||
*/
|
||||
static TRACK dummyTrack(NULL);
|
||||
SEGZONE * firstSegment = NULL;
|
||||
|
||||
fillArcTRACK( &dummyTrack, 0, aLayer,
|
||||
aStart, aEnd,
|
||||
rel_center, 0,
|
||||
clockwise, multiquadrant, isDark );
|
||||
|
||||
// dummyTrack has right geometric parameters, and has its Y coordinates negated (to match the pcbnew Y axis).
|
||||
// Approximate arc by 36 segments per 360 degree
|
||||
const int increment_angle = 360/36;
|
||||
|
||||
wxPoint center;
|
||||
center.x = dummyTrack.m_Param;
|
||||
center.y = dummyTrack.GetSubNet();
|
||||
|
||||
// Calculate relative coordinates;
|
||||
wxPoint start = dummyTrack.m_Start - center;
|
||||
wxPoint end = dummyTrack.m_End - center;
|
||||
|
||||
/* Calculate angle arc
|
||||
* angle is here clockwise because Y axis is reversed
|
||||
*/
|
||||
double start_angle =
|
||||
atan2( (double)start.y, (double)start.x );
|
||||
start_angle = 180 * start_angle / M_PI;
|
||||
double end_angle =
|
||||
atan2( (double)end.y , (double)end.x );
|
||||
end_angle = 180 * end_angle / M_PI;
|
||||
double angle = start_angle - end_angle;
|
||||
|
||||
// D( printf( " >>>> st %d,%d angle %f, end %d,%d angle %f delta %f\n",
|
||||
// start.x, start.y, start_angle, end.x, end.y, end_angle, angle ) );
|
||||
if( !clockwise )
|
||||
{
|
||||
EXCHG(start, end);
|
||||
D( printf( " >>>> reverse arc\n") );
|
||||
}
|
||||
|
||||
// Normalize angle
|
||||
while ( angle > 360.0 )
|
||||
angle -= 360.0;
|
||||
while ( angle < 0.0 )
|
||||
angle += 360.0;
|
||||
|
||||
int count = (int) (angle / increment_angle );
|
||||
if( count <= 0 )
|
||||
count = 1;
|
||||
// D( printf( " >>>> angle %f, cnt %d sens %d\n", angle, count, clockwise ) );
|
||||
|
||||
// calculate segments
|
||||
wxPoint start_arc = start;
|
||||
for( int ii = 1; ii <= count; ii++ )
|
||||
{
|
||||
wxPoint end_arc = start;
|
||||
int rot = 10 * ii * increment_angle; // rot is in 0.1 deg
|
||||
if( ii < count )
|
||||
{
|
||||
if( clockwise )
|
||||
RotatePoint(&end_arc, rot);
|
||||
else
|
||||
RotatePoint(&end_arc, -rot);
|
||||
}
|
||||
else
|
||||
end_arc = end;
|
||||
SEGZONE * edge_poly = new SEGZONE( aPcb );
|
||||
if( firstSegment == NULL )
|
||||
firstSegment = edge_poly;
|
||||
aPcb->m_Zone.Append( edge_poly );
|
||||
// D( printf( " >> Add arc %d rot %d, edge poly item %d,%d to %d,%d\n",
|
||||
// ii, rot, start_arc.x, start_arc.y,end_arc.x, end_arc.y ); )
|
||||
|
||||
edge_poly->SetLayer( aLayer );
|
||||
edge_poly->m_Width = 1;
|
||||
|
||||
edge_poly->m_Start = start_arc + center;
|
||||
edge_poly->m_End = end_arc + center;
|
||||
|
||||
// the first track of each polygon has a netcode of zero,
|
||||
// otherwise one.
|
||||
// set netcode to 1. the calling function is responsible
|
||||
// to set the first point to 0
|
||||
edge_poly->SetNet( 1 );
|
||||
if( !isDark )
|
||||
{
|
||||
edge_poly->m_Flags |= DRAW_ERASED;
|
||||
}
|
||||
start_arc = end_arc;
|
||||
}
|
||||
|
||||
return firstSegment;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/* These routines read the text string point from Text.
|
||||
* After use, advanced Text the beginning of the sequence unread
|
||||
*/
|
||||
|
||||
|
||||
/* Returns the current coord pointed to by Text (XnnnnYmmmm)
|
||||
*/
|
||||
wxPoint GERBER::ReadXYCoord( char*& Text )
|
||||
{
|
||||
wxPoint pos = m_CurrentPos;
|
||||
|
@ -748,12 +881,12 @@ bool GERBER::Execute_G_Command( char*& text, int G_commande )
|
|||
break;
|
||||
|
||||
case GC_SPECIFY_ABSOLUES_COORD:
|
||||
m_Relative = false; // false = absolute Coord, RUE = relative
|
||||
m_Relative = false; // false = absolute Coord, true = relative
|
||||
// Coord
|
||||
break;
|
||||
|
||||
case GC_SPECIFY_RELATIVEES_COORD:
|
||||
m_Relative = true; // false = absolute Coord, RUE = relative
|
||||
m_Relative = true; // false = absolute Coord, true = relative
|
||||
// Coord
|
||||
break;
|
||||
|
||||
|
@ -888,15 +1021,33 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
|
|||
|
||||
if( m_PolygonFillMode ) // Enter a polygon description:
|
||||
{
|
||||
SEGZONE* edge_poly;
|
||||
switch( D_commande )
|
||||
{
|
||||
case 1: // code D01 Draw line, exposure ON
|
||||
m_Exposure = true;
|
||||
|
||||
SEGZONE* edge_poly;
|
||||
switch( m_Iterpolation )
|
||||
{
|
||||
case GERB_INTERPOL_ARC_NEG:
|
||||
case GERB_INTERPOL_ARC_POS:
|
||||
D( printf( "Add arc poly %d,%d to %d,%d fill %d interpol %d 360_enb %d\n",
|
||||
m_PreviousPos.x, m_PreviousPos.y, m_CurrentPos.x,
|
||||
m_CurrentPos.y, m_PolygonFillModeState, m_Iterpolation, m_360Arc_enbl ); )
|
||||
edge_poly = fillArcPOLY( pcb, activeLayer, m_PreviousPos,
|
||||
m_CurrentPos, m_IJPos,
|
||||
( m_Iterpolation == GERB_INTERPOL_ARC_NEG ) ?
|
||||
false : true, m_360Arc_enbl,
|
||||
!(m_LayerNegative ^ m_ImageNegative) );
|
||||
edge_poly->SetNet( m_PolygonFillModeState );
|
||||
break;
|
||||
|
||||
default:
|
||||
edge_poly = new SEGZONE( pcb );
|
||||
pcb->m_Zone.Append( edge_poly );
|
||||
D( printf( "R:%p\n", edge_poly ); )
|
||||
D( printf( "Add poly edge %d,%d to %d,%d fill %d\n",
|
||||
m_PreviousPos.x, m_PreviousPos.y,
|
||||
m_CurrentPos.x, m_CurrentPos.y, m_Iterpolation ); )
|
||||
|
||||
edge_poly->SetLayer( activeLayer );
|
||||
edge_poly->m_Width = 1;
|
||||
|
@ -918,6 +1069,8 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
|
|||
edge_poly->m_Flags |= DRAW_ERASED;
|
||||
D( printf( "\nm_Flags=0x%08X\n", edge_poly->m_Flags ); )
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
m_PreviousPos = m_CurrentPos;
|
||||
m_PolygonFillModeState = 1;
|
||||
|
|
|
@ -89,7 +89,7 @@ public:
|
|||
void GeneralControle( wxDC* DC, wxPoint MousePositionInPixels );
|
||||
|
||||
PARAM_CFG_ARRAY& GetProjectFileParameters( void );
|
||||
void SaveProjectFile( wxWindow* displayframe );
|
||||
void SaveProjectFile( wxWindow* displayframe, bool askoverwrite = true );
|
||||
bool LoadProjectFile( const wxString& CfgFileName, bool ForceRereadConfig );
|
||||
|
||||
PARAM_CFG_ARRAY& GetConfigurationSettings( void );
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
///////////////////////////////////////////////////////////////////////////
|
||||
// C++ code generated with wxFormBuilder (version Dec 29 2008)
|
||||
// C++ code generated with wxFormBuilder (version Apr 16 2008)
|
||||
// http://www.wxformbuilder.org/
|
||||
//
|
||||
// PLEASE DO "NOT" EDIT THIS FILE!
|
||||
|
@ -50,6 +50,7 @@ DIALOG_LAYERS_SETUP_BASE::DIALOG_LAYERS_SETUP_BASE( wxWindow* parent, wxWindowID
|
|||
bCaptionsSizer = new wxBoxSizer( wxHORIZONTAL );
|
||||
|
||||
m_TitlePanel = new wxPanel( this, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxRAISED_BORDER|wxTAB_TRAVERSAL );
|
||||
m_TitlePanel->SetForegroundColour( wxSystemSettings::GetColour( wxSYS_COLOUR_CAPTIONTEXT ) );
|
||||
m_TitlePanel->SetBackgroundColour( wxSystemSettings::GetColour( wxSYS_COLOUR_ACTIVECAPTION ) );
|
||||
|
||||
bCaptionsSizer->Add( m_TitlePanel, 1, wxEXPAND, 5 );
|
||||
|
|
|
@ -245,7 +245,7 @@
|
|||
<property name="bg">wxSYS_COLOUR_ACTIVECAPTION</property>
|
||||
<property name="context_help"></property>
|
||||
<property name="enabled">1</property>
|
||||
<property name="fg"></property>
|
||||
<property name="fg">wxSYS_COLOUR_CAPTIONTEXT</property>
|
||||
<property name="font"></property>
|
||||
<property name="hidden">0</property>
|
||||
<property name="id">wxID_ANY</property>
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
///////////////////////////////////////////////////////////////////////////
|
||||
// C++ code generated with wxFormBuilder (version Dec 29 2008)
|
||||
// C++ code generated with wxFormBuilder (version Apr 16 2008)
|
||||
// http://www.wxformbuilder.org/
|
||||
//
|
||||
// PLEASE DO "NOT" EDIT THIS FILE!
|
||||
|
|
Loading…
Reference in New Issue