Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
K
kicad-source-mirror
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Commits
Open sidebar
Elphel
kicad-source-mirror
Commits
b992af3e
Commit
b992af3e
authored
Sep 28, 2010
by
jean-pierre charras
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Gerbview code redesign
parent
3ae0df15
Changes
39
Show whitespace changes
Inline
Side-by-side
Showing
39 changed files
with
2357 additions
and
2300 deletions
+2357
-2300
CHANGELOG.txt
CHANGELOG.txt
+19
-1
gr_basic.cpp
common/gr_basic.cpp
+36
-20
CMakeLists.txt
gerbview/CMakeLists.txt
+2
-1
block.cpp
gerbview/block.cpp
+65
-186
class_GERBER.cpp
gerbview/class_GERBER.cpp
+190
-0
class_gerber_draw_item.cpp
gerbview/class_gerber_draw_item.cpp
+426
-0
class_gerber_draw_item.h
gerbview/class_gerber_draw_item.h
+183
-0
dcode.cpp
gerbview/dcode.cpp
+319
-262
dcode.h
gerbview/dcode.h
+278
-0
deltrack.cpp
gerbview/deltrack.cpp
+11
-63
dummy_functions.cpp
gerbview/dummy_functions.cpp
+1
-1
edit.cpp
gerbview/edit.cpp
+5
-23
export_to_pcbnew.cpp
gerbview/export_to_pcbnew.cpp
+25
-30
aperture-circle-flash-with_hole.gbr
...iew/gerber_test_files/aperture-circle-flash-with_hole.gbr
+27
-0
aperture-obround-flash-with_hole.gbr
...ew/gerber_test_files/aperture-obround-flash-with_hole.gbr
+27
-0
test-aperture-polygon-flash.gbr
gerbview/gerber_test_files/test-aperture-polygon-flash.gbr
+27
-0
test-aperture-rectangle-flash-with_hole.gbr
...er_test_files/test-aperture-rectangle-flash-with_hole.gbr
+27
-0
gerberframe.cpp
gerbview/gerberframe.cpp
+78
-106
gerbview.h
gerbview/gerbview.h
+2
-230
gerbview_config.h
gerbview/gerbview_config.h
+1
-1
gerbview_id.h
gerbview/gerbview_id.h
+2
-0
hotkeys.cpp
gerbview/hotkeys.cpp
+2
-2
hotkeys.h
gerbview/hotkeys.h
+1
-1
initpcb.cpp
gerbview/initpcb.cpp
+9
-24
lay2plot.cpp
gerbview/lay2plot.cpp
+0
-37
locate.cpp
gerbview/locate.cpp
+0
-442
onrightclick.cpp
gerbview/onrightclick.cpp
+1
-20
options.cpp
gerbview/options.cpp
+2
-14
protos.h
gerbview/protos.h
+0
-11
readgerb.cpp
gerbview/readgerb.cpp
+1
-11
rs274d.cpp
gerbview/rs274d.cpp
+442
-506
rs274x.cpp
gerbview/rs274x.cpp
+1
-1
toolbars_gerber.cpp
gerbview/toolbars_gerber.cpp
+104
-4
tracepcb.cpp
gerbview/tracepcb.cpp
+30
-273
wxGerberFrame.h
gerbview/wxGerberFrame.h
+0
-11
base_struct.h
include/base_struct.h
+5
-0
class_board_item.h
include/class_board_item.h
+4
-7
gr_basic.h
include/gr_basic.h
+4
-6
class_board_item.cpp
pcbnew/class_board_item.cpp
+0
-6
No files found.
CHANGELOG.txt
View file @
b992af3e
...
...
@@ -4,6 +4,24 @@ KiCad ChangeLog 2010
Please add newer entries at the top, list the date and your name with
email address.
2010-jul-27, UPDATE Jean-Pierre Charras <jean-pierre.charras@gipsa-lab.inpg.fr>
================================================================================
++gerbview:
Important changes:
graphic functions rewritten.
graphics items are now specific to gerbview (added a GERBER_DRAW_ITEM class)
and do not use tracks from pcbnew.
The way used to draw them is also new.
Apertures are now correctly drawn for round, oval and rectangular shapes
(with or without holes)
Aperture definition type Polygon is not yet handle.
Polygons are correctly drawn.
TODO:
Draw functions for aperture definition type Polygon.
Draw functions for aperture macros.
Work in progress.
2010-Aug-9 UPDATE Dick Hollenbeck <dick@softplc.com>
================================================================================
++CMakeModules:
...
...
@@ -67,7 +85,7 @@ email address.
2010-jul-27, UPDATE Jean-Pierre Charras <jean-pierre.charras@gipsa-lab.inpg.fr>
================================================================================
++all:
Updated boost to version 1.4
3
Updated boost to version 1.4
4
Added boost::polygon (experimental)
++pcbnew:
Added experimental zone fill calculations with boost::polygon
...
...
common/gr_basic.cpp
View file @
b992af3e
...
...
@@ -58,6 +58,10 @@ int g_DrawBgColor = WHITE;
void
ClipAndDrawFilledPoly
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
wxPoint
Points
[],
int
n
);
#endif
static
void
GRSCircle
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
r
,
int
width
,
int
Color
);
static
void
GRSFilledCircle
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
r
,
int
width
,
int
Color
,
int
BgColor
);
extern
BASE_SCREEN
*
ActiveScreen
;
...
...
@@ -1333,6 +1337,26 @@ void GRCircle( EDA_Rect* ClipBox, wxDC* DC, int x, int y, int r, int Color )
GRSCircle
(
ClipBox
,
DC
,
cx
,
cy
,
radius
,
0
,
Color
);
}
/*
* Draw a circle in object space.
*/
void
GRCircle
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
r
,
int
width
,
int
Color
)
{
r
=
ZoomValue
(
r
);
width
=
ZoomValue
(
width
);
GRSCircle
(
ClipBox
,
DC
,
GRMapX
(
x
),
GRMapY
(
y
),
r
,
width
,
Color
);
}
/*
* Draw a circle in object space.
*/
void
GRCircle
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
wxPoint
aPos
,
int
aRadius
,
int
aWidth
,
int
aColor
)
{
aRadius
=
ZoomValue
(
aRadius
);
aWidth
=
ZoomValue
(
aWidth
);
GRSCircle
(
aClipBox
,
aDC
,
GRMapX
(
aPos
.
x
),
GRMapY
(
aPos
.
y
),
aRadius
,
aWidth
,
aColor
);
}
/*
* Draw a filled circle, in object space.
...
...
@@ -1346,6 +1370,14 @@ void GRFilledCircle( EDA_Rect* ClipBox, wxDC* DC, int x, int y, int r,
Color
,
BgColor
);
}
/*
* Draw a filled circle, in object space.
*/
void
GRFilledCircle
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
wxPoint
aPos
,
int
aRadius
,
int
aColor
)
{
aRadius
=
ZoomValue
(
aRadius
);
GRSFilledCircle
(
aClipBox
,
aDC
,
GRMapX
(
aPos
.
x
),
GRMapY
(
aPos
.
y
),
aRadius
,
0
,
aColor
,
aColor
);
}
/*
* Draw a filled circle, in drawing space.
...
...
@@ -1377,22 +1409,6 @@ void GRSFilledCircle( EDA_Rect* ClipBox, wxDC* DC, int x, int y, int r,
}
/*
* Draw a circle in object space.
*/
void
GRCircle
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
r
,
int
width
,
int
Color
)
{
r
=
ZoomValue
(
r
);
width
=
ZoomValue
(
width
);
GRSCircle
(
ClipBox
,
DC
,
GRMapX
(
x
),
GRMapY
(
y
),
r
,
width
,
Color
);
}
/*
* Draw a circle in drawing space.
...
...
gerbview/CMakeLists.txt
View file @
b992af3e
...
...
@@ -15,6 +15,8 @@ include_directories(${CMAKE_CURRENT_SOURCE_DIR}
###
set
(
GERBVIEW_SRCS
block.cpp
class_GERBER.cpp
class_gerber_draw_item.cpp
class_gerbview_layer_widget.cpp
controle.cpp
dcode.cpp
...
...
@@ -32,7 +34,6 @@ set(GERBVIEW_SRCS
gerbview.cpp
hotkeys.cpp
initpcb.cpp
lay2plot.cpp
locate.cpp
menubar.cpp
onrightclick.cpp
...
...
gerbview/block.cpp
View file @
b992af3e
...
...
@@ -2,6 +2,30 @@
/* Block operations: displacement, rotation, deletion ... */
/**********************************************************/
/*
* This program source code file is part of KICAD, a free EDA CAD application.
*
* Copyright (C) 1992-2010 <Jean-Pierre Charras>
* Copyright (C) 1992-2010 Kicad Developers, see change_log.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, you may find one here:
* http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* or you may search the http://www.gnu.org website for the version 2 license,
* or you may write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "fctsys.h"
#include "gr_basic.h"
...
...
@@ -11,6 +35,7 @@
#include "confirm.h"
#include "gerbview.h"
#include "class_gerber_draw_item.h"
#include "protos.h"
...
...
@@ -21,7 +46,7 @@ static void DrawMovingBlockOutlines( WinEDA_DrawPanel* panel,
wxDC
*
DC
,
bool
erase
);
static
TRACK
*
IsSegmentInBox
(
BLOCK_SELECTOR
&
blocklocate
,
TRACK
*
PtSeg
m
);
static
bool
IsGbrItemInBox
(
BLOCK_SELECTOR
&
aBlocklocate
,
GERBER_DRAW_ITEM
*
aIte
m
);
/* Return the block command (BLOCK_MOVE, BLOCK_COPY...) corresponding to
...
...
@@ -168,21 +193,10 @@ int WinEDA_GerberFrame::HandleBlockEnd( wxDC* DC )
Block_Delete
(
DC
);
break
;
case
BLOCK_MIRROR_X
:
/* Mirror*/
GetScreen
()
->
m_BlockLocate
.
m_State
=
STATE_BLOCK_STOP
;
DrawPanel
->
ManageCurseur
(
DrawPanel
,
DC
,
FALSE
);
Block_Mirror_X
(
DC
);
break
;
case
BLOCK_MIRROR_X
:
/* Mirror, unused*/
case
BLOCK_ROTATE
:
/* Unused */
break
;
case
BLOCK_FLIP
:
/* Flip, unused */
break
;
case
BLOCK_SAVE
:
/* Save (not used)*/
break
;
case
BLOCK_PASTE
:
break
;
...
...
@@ -273,28 +287,14 @@ void WinEDA_GerberFrame::Block_Delete( wxDC* DC )
GetScreen
()
->
m_BlockLocate
.
Normalize
();
GetScreen
()
->
SetCurItem
(
NULL
);
TRACK
*
pt_segm
,
*
NextS
;
for
(
pt_segm
=
m_Pcb
->
m_Track
;
pt_segm
!=
NULL
;
pt_segm
=
NextS
)
{
NextS
=
pt_segm
->
Next
();
if
(
IsSegmentInBox
(
GetScreen
()
->
m_BlockLocate
,
pt_segm
)
)
{
/* the track here is good to be cleared */
pt_segm
->
Draw
(
DrawPanel
,
DC
,
GR_XOR
);
pt_segm
->
DeleteStructure
();
}
}
/* Erasing areas. */
for
(
pt_segm
=
m_Pcb
->
m_Zone
;
pt_segm
!=
NULL
;
pt_segm
=
NextS
)
{
NextS
=
pt_segm
->
Next
();
if
(
IsSegmentInBox
(
GetScreen
()
->
m_BlockLocate
,
pt_segm
)
)
BOARD_ITEM
*
item
=
GetBoard
()
->
m_Drawings
;
BOARD_ITEM
*
nextitem
;
for
(
;
item
;
item
=
nextitem
)
{
/* The track here is good to be cleared. */
pt_segm
->
Draw
(
DrawPanel
,
DC
,
GR_XOR
)
;
pt_segm
->
DeleteStructure
();
}
nextitem
=
item
->
Next
();
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
if
(
IsGbrItemInBox
(
GetScreen
()
->
m_BlockLocate
,
gerb_item
)
)
gerb_item
->
DeleteStructure
();
}
Refresh
();
...
...
@@ -320,106 +320,13 @@ void WinEDA_GerberFrame::Block_Move( wxDC* DC )
/* Calculate displacement vectors. */
delta
=
GetScreen
()
->
m_BlockLocate
.
m_MoveVector
;
/* Move
the Track segment
s in block */
TRACK
*
track
=
m_Pcb
->
m_Track
;
while
(
track
)
/* Move
item
s in block */
BOARD_ITEM
*
item
=
GetBoard
()
->
m_Drawings
;
for
(
;
item
;
item
=
item
->
Next
()
)
{
if
(
IsSegmentInBox
(
GetScreen
()
->
m_BlockLocate
,
track
)
)
{
m_Pcb
->
m_Status_Pcb
=
0
;
track
->
Draw
(
DrawPanel
,
DC
,
GR_XOR
);
// erase the display
track
->
m_Start
+=
delta
;
track
->
m_End
+=
delta
;
// the two parameters are used in gerbview to store center
// coordinates for arcs. Move this center.
track
->
m_Param
+=
delta
.
x
;
track
->
SetSubNet
(
track
->
GetSubNet
()
+
delta
.
y
);
track
->
Draw
(
DrawPanel
,
DC
,
GR_OR
);
// redraw the moved track
}
track
=
track
->
Next
();
}
/* Move the Zone segments in block */
SEGZONE
*
zsegment
=
m_Pcb
->
m_Zone
;
while
(
zsegment
)
{
if
(
IsSegmentInBox
(
GetScreen
()
->
m_BlockLocate
,
zsegment
)
)
{
zsegment
->
Draw
(
DrawPanel
,
DC
,
GR_XOR
);
// erase the display
zsegment
->
m_Start
+=
delta
;
zsegment
->
m_End
+=
delta
;
// the two parameters are used in gerbview to store center
// coordinates for arcs. Move this center
zsegment
->
m_Param
+=
delta
.
x
;
zsegment
->
SetSubNet
(
zsegment
->
GetSubNet
()
+
delta
.
y
);
zsegment
->
Draw
(
DrawPanel
,
DC
,
GR_OR
);
// redraw the moved zone
// segment
}
zsegment
=
zsegment
->
Next
();
}
DrawPanel
->
Refresh
(
TRUE
);
}
/*
* Function to mirror items in the current selected block
*/
void
WinEDA_GerberFrame
::
Block_Mirror_X
(
wxDC
*
DC
)
{
int
xoffset
=
0
;
wxPoint
oldpos
;
oldpos
=
GetScreen
()
->
m_Curseur
;
DrawPanel
->
ManageCurseur
=
NULL
;
GetScreen
()
->
m_Curseur
=
oldpos
;
DrawPanel
->
MouseToCursorSchema
();
GetScreen
()
->
SetModify
();
GetScreen
()
->
m_BlockLocate
.
Normalize
();
/* Calculate offset to mirror track points from block edges */
xoffset
=
GetScreen
()
->
m_BlockLocate
.
m_Pos
.
x
+
GetScreen
()
->
m_BlockLocate
.
m_Pos
.
x
+
GetScreen
()
->
m_BlockLocate
.
m_Size
.
x
;
/* Move the Track segments in block */
for
(
TRACK
*
track
=
m_Pcb
->
m_Track
;
track
;
track
=
track
->
Next
()
)
{
if
(
IsSegmentInBox
(
GetScreen
()
->
m_BlockLocate
,
track
)
)
{
m_Pcb
->
m_Status_Pcb
=
0
;
track
->
Draw
(
DrawPanel
,
DC
,
GR_XOR
);
// erase the display
track
->
m_Start
.
x
=
xoffset
-
track
->
m_Start
.
x
;
track
->
m_End
.
x
=
xoffset
-
track
->
m_End
.
x
;
// the two parameters are used in gerbview to store center
// coordinates for arcs. Move this center
track
->
m_Param
=
xoffset
-
track
->
m_Param
;
track
->
Draw
(
DrawPanel
,
DC
,
GR_OR
);
// redraw the moved track
}
}
/* Move the Zone segments in block */
for
(
SEGZONE
*
zsegment
=
m_Pcb
->
m_Zone
;
zsegment
;
zsegment
=
zsegment
->
Next
()
)
{
if
(
IsSegmentInBox
(
GetScreen
()
->
m_BlockLocate
,
zsegment
)
)
{
zsegment
->
Draw
(
DrawPanel
,
DC
,
GR_XOR
);
// erase the display
zsegment
->
m_Start
.
x
=
xoffset
-
zsegment
->
m_Start
.
x
;
zsegment
->
m_End
.
x
=
xoffset
-
zsegment
->
m_End
.
x
;
// the two parameters are used in gerbview to store center
// coordinates for arcs. Move this center
zsegment
->
m_Param
=
xoffset
-
zsegment
->
m_Param
;
zsegment
->
Draw
(
DrawPanel
,
DC
,
GR_OR
);
// redraw the moved zone
// segment
}
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
if
(
IsGbrItemInBox
(
GetScreen
()
->
m_BlockLocate
,
gerb_item
)
)
gerb_item
->
Move
(
delta
);
}
DrawPanel
->
Refresh
(
TRUE
);
...
...
@@ -444,62 +351,34 @@ void WinEDA_GerberFrame::Block_Duplicate( wxDC* DC )
delta
=
GetScreen
()
->
m_BlockLocate
.
m_MoveVector
;
/* Copy
selected track segments and move the new track its new location
*/
TRACK
*
track
=
m_Pcb
->
m_Track
;
while
(
track
)
/* Copy
items in block
*/
BOARD_ITEM
*
item
=
GetBoard
()
->
m_Drawings
;
for
(
;
item
;
item
=
item
->
Next
()
)
{
TRACK
*
next_track
=
track
->
Next
()
;
if
(
Is
SegmentInBox
(
GetScreen
()
->
m_BlockLocate
,
track
)
)
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
if
(
Is
GbrItemInBox
(
GetScreen
()
->
m_BlockLocate
,
gerb_item
)
)
{
/* this track segment must be duplicated */
m_Pcb
->
m_Status_Pcb
=
0
;
TRACK
*
new_track
=
track
->
Copy
();
m_Pcb
->
Add
(
new_track
);
new_track
->
m_Start
+=
delta
;
new_track
->
m_End
+=
delta
;
new_track
->
Draw
(
DrawPanel
,
DC
,
GR_OR
);
// draw the new created
// segment
/* this item must be duplicated */
BOARD_ITEM
*
new_item
=
gerb_item
->
Copy
();
new_item
->
Move
(
delta
);
GetBoard
()
->
m_Drawings
.
PushFront
(
new_item
);
}
track
=
next_track
;
}
/* Copy the Zone segments and move the new segment to its new location */
SEGZONE
*
zsegment
=
m_Pcb
->
m_Zone
;
while
(
zsegment
)
{
SEGZONE
*
next_zsegment
=
zsegment
->
Next
();
if
(
IsSegmentInBox
(
GetScreen
()
->
m_BlockLocate
,
zsegment
)
)
{
/* this zone segment must be duplicated */
SEGZONE
*
new_zsegment
=
(
SEGZONE
*
)
zsegment
->
Copy
();
m_Pcb
->
Add
(
new_zsegment
);
new_zsegment
->
m_Start
+=
delta
;
new_zsegment
->
m_End
+=
delta
;
new_zsegment
->
Draw
(
DrawPanel
,
DC
,
GR_OR
);
// draw the new created
// segment
}
zsegment
=
next_zsegment
;
}
DrawPanel
->
Refresh
();
}
/* Test if the structure PtStruct is listed in the block selects
* Returns whether PtSegm
* NULL if not
/* Test if the structure PtStruct is inside the block
* Returns true or false
*/
static
TRACK
*
IsSegmentInBox
(
BLOCK_SELECTOR
&
blocklocate
,
TRACK
*
PtSeg
m
)
bool
IsGbrItemInBox
(
BLOCK_SELECTOR
&
aBlocklocate
,
GERBER_DRAW_ITEM
*
aIte
m
)
{
if
(
blocklocate
.
Inside
(
PtSegm
->
m_Start
.
x
,
PtSegm
->
m_Start
.
y
)
)
return
PtSegm
;
if
(
aBlocklocate
.
Inside
(
aItem
->
m_Start
)
)
return
true
;
if
(
blocklocate
.
Inside
(
PtSegm
->
m_End
.
x
,
PtSegm
->
m_End
.
y
)
)
return
PtSegm
;
if
(
aBlocklocate
.
Inside
(
aItem
->
m_End
)
)
return
true
;
return
NULL
;
return
false
;
}
gerbview/class_GERBER.cpp
0 → 100644
View file @
b992af3e
/** @file class_GERBER.cpp
* a GERBER class handle for a given layer info about used D_CODES and how the layer is drawn
*/
/*
* This program source code file is part of KICAD, a free EDA CAD application.
*
* Copyright (C) 1992-2010 <Jean-Pierre Charras>
* Copyright (C) 1992-2010 Kicad Developers, see change_log.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, you may find one here:
* http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* or you may search the http://www.gnu.org website for the version 2 license,
* or you may write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "fctsys.h"
#include "common.h"
#include "class_drawpanel.h"
#include "confirm.h"
#include "macros.h"
#include "gerbview.h"
/* Format Gerber: NOTES:
* Tools and D_CODES
* tool number (identification of shapes)
* 1 to 999
*
* D_CODES:
* D01 ... D9 = action codes:
* D01 = activating light (lower pen) when di placement
* D02 = light extinction (lift pen) when di placement
* D03 Flash
* D09 = VAPE Flash
* D10 ... = Indentification Tool (Opening)
*
* For tools:
* DCode min = D10
* DCode max = 999
*/
GERBER
::
GERBER
(
int
aLayer
)
{
m_Layer
=
aLayer
;
// Layer Number
m_Selected_Tool
=
FIRST_DCODE
;
ResetDefaultValues
();
for
(
unsigned
ii
=
0
;
ii
<
DIM
(
m_Aperture_List
);
ii
++
)
m_Aperture_List
[
ii
]
=
0
;
m_Pcb
=
0
;
}
GERBER
::~
GERBER
()
{
for
(
unsigned
ii
=
0
;
ii
<
DIM
(
m_Aperture_List
);
ii
++
)
{
delete
m_Aperture_List
[
ii
];
// m_Aperture_List[ii] = NULL;
}
delete
m_Pcb
;
}
D_CODE
*
GERBER
::
GetDCODE
(
int
aDCODE
,
bool
create
)
{
unsigned
ndx
=
aDCODE
-
FIRST_DCODE
;
if
(
ndx
<
(
unsigned
)
DIM
(
m_Aperture_List
)
)
{
// lazily create the D_CODE if it does not exist.
if
(
create
)
{
if
(
m_Aperture_List
[
ndx
]
==
NULL
)
m_Aperture_List
[
ndx
]
=
new
D_CODE
(
ndx
+
FIRST_DCODE
);
}
return
m_Aperture_List
[
ndx
];
}
return
NULL
;
}
APERTURE_MACRO
*
GERBER
::
FindApertureMacro
(
const
APERTURE_MACRO
&
aLookup
)
{
APERTURE_MACRO_SET
::
iterator
iter
=
m_aperture_macros
.
find
(
aLookup
);
if
(
iter
!=
m_aperture_macros
.
end
()
)
{
APERTURE_MACRO
*
pam
=
(
APERTURE_MACRO
*
)
&
(
*
iter
);
return
pam
;
}
return
NULL
;
// not found
}
void
GERBER
::
ResetDefaultValues
()
{
m_FileName
.
Empty
();
m_Name
=
wxT
(
"no name"
);
// Layer name
m_LayerNegative
=
FALSE
;
// TRUE = Negative Layer
m_ImageNegative
=
FALSE
;
// TRUE = Negative image
m_GerbMetric
=
FALSE
;
// FALSE = Inches, TRUE = metric
m_Relative
=
FALSE
;
// FALSE = absolute Coord, RUE =
// relative Coord
m_NoTrailingZeros
=
FALSE
;
// True: trailing zeros deleted
m_MirorA
=
FALSE
;
// True: miror / axe A (X)
m_MirorB
=
FALSE
;
// True: miror / axe B (Y)
m_Has_DCode
=
FALSE
;
// TRUE = DCodes in file (FALSE = no
// DCode->
// separate DCode file
m_Offset
.
x
=
m_Offset
.
y
=
0
;
// Coord Offset
m_FmtScale
.
x
=
m_FmtScale
.
y
=
g_Default_GERBER_Format
%
10
;
m_FmtLen
.
x
=
m_FmtLen
.
y
=
m_FmtScale
.
x
+
(
g_Default_GERBER_Format
/
10
);
m_LayerScale
.
x
=
m_LayerScale
.
y
=
1.0
;
// scale (X and Y) this
// layer
m_Rotation
=
0
;
m_Iterpolation
=
GERB_INTERPOL_LINEAR_1X
;
// Linear, 90 arc, Circ.
m_360Arc_enbl
=
FALSE
;
// 360 deg circular
// interpolation disable
m_Current_Tool
=
0
;
// Current Tool (Dcode)
// number selected
m_CommandState
=
0
;
// gives tate of the
// stacking order analysis
m_CurrentPos
.
x
=
m_CurrentPos
.
y
=
0
;
// current specified coord
// for plot
m_PreviousPos
.
x
=
m_PreviousPos
.
y
=
0
;
// old current specified
// coord for plot
m_IJPos
.
x
=
m_IJPos
.
y
=
0
;
// current centre coord for
// plot arcs & circles
m_Current_File
=
NULL
;
// File to read
m_FilesPtr
=
0
;
m_Transform
[
0
][
0
]
=
m_Transform
[
1
][
1
]
=
1
;
m_Transform
[
0
][
1
]
=
m_Transform
[
1
][
0
]
=
0
;
// Rotation/mirror = Normal
m_PolygonFillMode
=
FALSE
;
m_PolygonFillModeState
=
0
;
}
int
GERBER
::
ReturnUsedDcodeNumber
()
{
int
count
=
0
;
for
(
unsigned
ii
=
0
;
ii
<
DIM
(
m_Aperture_List
);
ii
++
)
{
if
(
m_Aperture_List
[
ii
]
)
if
(
m_Aperture_List
[
ii
]
->
m_InUse
||
m_Aperture_List
[
ii
]
->
m_Defined
)
++
count
;
}
return
count
;
}
void
GERBER
::
InitToolTable
()
{
for
(
int
count
=
0
;
count
<
TOOLS_MAX_COUNT
;
count
++
)
{
if
(
m_Aperture_List
[
count
]
==
NULL
)
continue
;
m_Aperture_List
[
count
]
->
m_Num_Dcode
=
count
+
FIRST_DCODE
;
m_Aperture_List
[
count
]
->
Clear_D_CODE_Data
();
}
}
gerbview/class_gerber_draw_item.cpp
0 → 100644
View file @
b992af3e
/*************************************
* file class_gerber_draw_item.cpp
*************************************/
/*
* This program source code file is part of KICAD, a free EDA CAD application.
*
* Copyright (C) 1992-2010 <Jean-Pierre Charras>
* Copyright (C) 1992-2010 Kicad Developers, see change_log.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, you may find one here:
* http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* or you may search the http://www.gnu.org website for the version 2 license,
* or you may write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "fctsys.h"
#include "polygons_defs.h"
#include "gr_basic.h"
#include "common.h"
#include "trigo.h"
#include "class_drawpanel.h"
#include "drawtxt.h"
#include "gerbview.h"
#include "class_board_design_settings.h"
#include "colors_selection.h"
#include "class_gerber_draw_item.h"
/**********************************************************/
GERBER_DRAW_ITEM
::
GERBER_DRAW_ITEM
(
BOARD_ITEM
*
aParent
)
:
BOARD_ITEM
(
aParent
,
TYPE_GERBER_DRAW_ITEM
)
/**********************************************************/
{
m_Layer
=
0
;
m_Shape
=
GBR_SEGMENT
;
m_Flashed
=
false
;
m_DCode
=
0
;
}
// Copy constructor
GERBER_DRAW_ITEM
::
GERBER_DRAW_ITEM
(
const
GERBER_DRAW_ITEM
&
aSource
)
:
BOARD_ITEM
(
aSource
)
{
m_Shape
=
aSource
.
m_Shape
;
m_Flags
=
aSource
.
m_Flags
;
m_TimeStamp
=
aSource
.
m_TimeStamp
;
SetStatus
(
aSource
.
ReturnStatus
()
);
m_Start
=
aSource
.
m_Start
;
m_End
=
aSource
.
m_End
;
m_Size
=
aSource
.
m_Size
;
m_Layer
=
aSource
.
m_Layer
;
m_Shape
=
aSource
.
m_Shape
;
m_Flashed
=
aSource
.
m_Flashed
;
m_DCode
=
aSource
.
m_DCode
;
m_PolyCorners
=
aSource
.
m_PolyCorners
;
}
GERBER_DRAW_ITEM
::~
GERBER_DRAW_ITEM
()
{
}
GERBER_DRAW_ITEM
*
GERBER_DRAW_ITEM
::
Copy
()
const
{
return
new
GERBER_DRAW_ITEM
(
*
this
);
}
wxString
GERBER_DRAW_ITEM
::
ShowGBRShape
()
{
switch
(
m_Shape
)
{
case
GBR_SEGMENT
:
return
_
(
"Line"
);
case
GBR_ARC
:
return
_
(
"Arc"
);
case
GBR_CIRCLE
:
return
_
(
"Circle"
);
case
GBR_SPOT_OVAL
:
return
wxT
(
"spot_oval"
);
case
GBR_SPOT_CIRCLE
:
return
wxT
(
"spot_circle"
);
case
GBR_SPOT_RECT
:
return
wxT
(
"spot_rect"
);
case
GBR_POLYGON
:
return
wxT
(
"polygon"
);
case
GBR_MACRO
:
return
wxT
(
"apt_macro"
);
// TODO: add aperture macro name
default
:
return
wxT
(
"??"
);
}
}
/**
* Function GetDcodeDescr
* returns the GetDcodeDescr of this object, or NULL.
* @return D_CODE* - a pointer to the DCode description (for flashed items).
*/
D_CODE
*
GERBER_DRAW_ITEM
::
GetDcodeDescr
()
{
if
(
(
m_DCode
<
FIRST_DCODE
)
||
(
m_DCode
>
LAST_DCODE
)
)
return
NULL
;
GERBER
*
gerber
=
g_GERBER_List
[
m_Layer
];
if
(
gerber
==
NULL
)
return
NULL
;
D_CODE
*
d_code
=
gerber
->
GetDCODE
(
m_DCode
,
false
);
return
d_code
;
}
EDA_Rect
GERBER_DRAW_ITEM
::
GetBoundingBox
()
{
// return a rectangle which is (pos,dim) in nature. therefore the +1
EDA_Rect
bbox
(
m_Start
,
wxSize
(
1
,
1
)
);
bbox
.
Inflate
(
m_Size
.
x
/
2
,
m_Size
.
y
/
2
);
return
bbox
;
}
/**
* Function Move
* move this object.
* @param const wxPoint& aMoveVector - the move vector for this object.
*/
void
GERBER_DRAW_ITEM
::
Move
(
const
wxPoint
&
aMoveVector
)
{
m_Start
+=
aMoveVector
;
m_End
+=
aMoveVector
;
m_ArcCentre
+=
aMoveVector
;
for
(
unsigned
ii
=
0
;
ii
<
m_PolyCorners
.
size
();
ii
++
)
m_PolyCorners
[
ii
]
+=
aMoveVector
;
}
/** function Save.
* currently: no nothing, but must be defined to meet requirements
* of the basic class
*/
bool
GERBER_DRAW_ITEM
::
Save
(
FILE
*
aFile
)
const
{
return
true
;
}
/*********************************************************************/
void
GERBER_DRAW_ITEM
::
Draw
(
WinEDA_DrawPanel
*
panel
,
wxDC
*
DC
,
int
draw_mode
,
const
wxPoint
&
aOffset
)
/*********************************************************************/
{
static
D_CODE
dummyD_CODE
(
0
);
// used when a D_CODE is not found. default D_CODE to draw a flashed item
int
color
;
bool
isFilled
;
int
radius
;
int
halfPenWidth
;
static
bool
show_err
;
BOARD
*
brd
=
GetBoard
();
D_CODE
*
d_codeDescr
=
GetDcodeDescr
();
if
(
d_codeDescr
==
NULL
)
d_codeDescr
=
&
dummyD_CODE
;
if
(
m_Flags
&
DRAW_ERASED
)
// draw in background color ("negative" color)
{
color
=
g_DrawBgColor
;
}
else
{
if
(
brd
->
IsLayerVisible
(
GetLayer
()
)
==
false
)
return
;
color
=
brd
->
GetLayerColor
(
GetLayer
()
);
if
(
draw_mode
&
GR_SURBRILL
)
{
if
(
draw_mode
&
GR_AND
)
color
&=
~
HIGHT_LIGHT_FLAG
;
else
color
|=
HIGHT_LIGHT_FLAG
;
}
if
(
color
&
HIGHT_LIGHT_FLAG
)
color
=
ColorRefs
[
color
&
MASKCOLOR
].
m_LightColor
;
}
GRSetDrawMode
(
DC
,
draw_mode
);
isFilled
=
DisplayOpt
.
DisplayPcbTrackFill
?
true
:
false
;
switch
(
m_Shape
)
{
case
GBR_POLYGON
:
isFilled
=
(
g_DisplayPolygonsModeSketch
==
false
);
if
(
m_Flags
&
DRAW_ERASED
)
isFilled
=
true
;
DrawGbrPoly
(
&
panel
->
m_ClipBox
,
DC
,
color
,
aOffset
,
isFilled
);
break
;
case
GBR_CIRCLE
:
radius
=
(
int
)
hypot
(
(
double
)
(
m_End
.
x
-
m_Start
.
x
),
(
double
)
(
m_End
.
y
-
m_Start
.
y
)
);
halfPenWidth
=
m_Size
.
x
>>
1
;
if
(
isFilled
==
SKETCH
)
{
// draw the border of the pen's path using two circles, each as narrow as possible
#ifdef USE_WX_ZOOM
if
(
DC
->
LogicalToDeviceXRel
(
halfPenWidth
)
<
L_MIN_DESSIN
)
#else
if
(
panel
->
GetScreen
()
->
Scale
(
halfPenWidth
)
<
L_MIN_DESSIN
)
#endif
{
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
m_Start
.
x
,
m_Start
.
y
,
radius
,
0
,
color
);
}
else
{
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
m_Start
.
x
,
m_Start
.
y
,
radius
-
halfPenWidth
,
0
,
color
);
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
m_Start
.
x
,
m_Start
.
y
,
radius
+
halfPenWidth
,
0
,
color
);
}
}
else
{
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
m_Start
.
x
,
m_Start
.
y
,
radius
,
m_Size
.
x
,
color
);
}
break
;
case
GBR_ARC
:
if
(
!
isFilled
)
{
GRArc1
(
&
panel
->
m_ClipBox
,
DC
,
m_Start
.
x
,
m_Start
.
y
,
m_End
.
x
,
m_End
.
y
,
m_ArcCentre
.
x
,
m_ArcCentre
.
y
,
0
,
color
);
}
else
{
GRArc1
(
&
panel
->
m_ClipBox
,
DC
,
m_Start
.
x
,
m_Start
.
y
,
m_End
.
x
,
m_End
.
y
,
m_ArcCentre
.
x
,
m_ArcCentre
.
y
,
m_Size
.
x
,
color
);
}
break
;
case
GBR_SPOT_CIRCLE
:
case
GBR_SPOT_RECT
:
case
GBR_SPOT_OVAL
:
isFilled
=
DisplayOpt
.
DisplayPadFill
?
true
:
false
;
d_codeDescr
->
DrawFlashedShape
(
&
panel
->
m_ClipBox
,
DC
,
color
,
m_Start
,
isFilled
);
break
;
case
GBR_SEGMENT
:
if
(
!
isFilled
)
GRCSegm
(
&
panel
->
m_ClipBox
,
DC
,
m_Start
.
x
,
m_Start
.
y
,
m_End
.
x
,
m_End
.
y
,
m_Size
.
x
,
color
);
else
GRFillCSegm
(
&
panel
->
m_ClipBox
,
DC
,
m_Start
.
x
,
m_Start
.
y
,
m_End
.
x
,
m_End
.
y
,
m_Size
.
x
,
color
);
break
;
default
:
if
(
!
show_err
)
{
wxMessageBox
(
wxT
(
"Trace_Segment() type error"
)
);
show_err
=
TRUE
;
}
break
;
}
}
/** function DrawGbrPoly
* a helper function used id ::Draw to draw the polygon stored ion m_PolyCorners
* Draw filled polygons
*/
void
GERBER_DRAW_ITEM
::
DrawGbrPoly
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
int
aColor
,
const
wxPoint
&
aOffset
,
bool
aFilledShape
)
{
std
::
vector
<
wxPoint
>
points
;
points
=
m_PolyCorners
;
if
(
aOffset
!=
wxPoint
(
0
,
0
)
)
{
for
(
unsigned
ii
=
0
;
ii
<
points
.
size
();
ii
++
)
{
points
[
ii
]
+=
aOffset
;
}
}
GRClosedPoly
(
aClipBox
,
aDC
,
points
.
size
(),
&
points
[
0
],
aFilledShape
,
aColor
,
aColor
);
}
/** Function DisplayInfoBase
* has knowledge about the frame and how and where to put status information
* about this object into the frame's message panel.
* Display info about the track segment only, and does not calculate the full track length
* @param frame A WinEDA_DrawFrame in which to print status information.
*/
void
GERBER_DRAW_ITEM
::
DisplayInfo
(
WinEDA_DrawFrame
*
frame
)
{
wxString
msg
;
BOARD
*
board
=
(
(
WinEDA_BasePcbFrame
*
)
frame
)
->
GetBoard
();
frame
->
ClearMsgPanel
();
msg
=
ShowGBRShape
();
frame
->
AppendMsgPanel
(
_
(
"Type"
),
msg
,
DARKCYAN
);
/* Display layer */
msg
=
board
->
GetLayerName
(
m_Layer
);
frame
->
AppendMsgPanel
(
_
(
"Layer"
),
msg
,
BROWN
);
}
/**
* Function HitTest
* tests if the given wxPoint is within the bounds of this object.
* @param ref_pos A wxPoint to test
* @return bool - true if a hit, else false
*/
bool
GERBER_DRAW_ITEM
::
HitTest
(
const
wxPoint
&
ref_pos
)
{
// TODO: a better analyse od the shape (perhaps create a D_CODE::HitTest for flashed items)
int
radius
=
MIN
(
m_Size
.
x
,
m_Size
.
y
)
>>
1
;
// delta is a vector from m_Start to m_End (an origin of m_Start)
wxPoint
delta
=
m_End
-
m_Start
;
// dist is a vector from m_Start to ref_pos (an origin of m_Start)
wxPoint
dist
=
ref_pos
-
m_Start
;
if
(
m_Flashed
)
{
return
(
double
)
dist
.
x
*
dist
.
x
+
(
double
)
dist
.
y
*
dist
.
y
<=
(
double
)
radius
*
radius
;
}
else
{
if
(
DistanceTest
(
radius
,
delta
.
x
,
delta
.
y
,
dist
.
x
,
dist
.
y
)
)
return
true
;
}
return
false
;
}
/**
* Function HitTest (overlayed)
* tests if the given EDA_Rect intersect this object.
* For now, an ending point must be inside this rect.
* @param refArea : the given EDA_Rect
* @return bool - true if a hit, else false
*/
bool
GERBER_DRAW_ITEM
::
HitTest
(
EDA_Rect
&
refArea
)
{
if
(
refArea
.
Inside
(
m_Start
)
)
return
true
;
if
(
refArea
.
Inside
(
m_End
)
)
return
true
;
return
false
;
}
#if defined(DEBUG)
/**
* Function Show
* is used to output the object tree, currently for debugging only.
* @param nestLevel An aid to prettier tree indenting, and is the level
* of nesting of this object within the overall tree.
* @param os The ostream& to output to.
*/
void
GERBER_DRAW_ITEM
::
Show
(
int
nestLevel
,
std
::
ostream
&
os
)
{
NestedSpace
(
nestLevel
,
os
)
<<
'<'
<<
GetClass
().
Lower
().
mb_str
()
<<
" shape=
\"
"
<<
m_Shape
<<
'"'
<<
" addr=
\"
"
<<
std
::
hex
<<
this
<<
std
::
dec
<<
'"'
<<
" layer=
\"
"
<<
m_Layer
<<
'"'
<<
" size=
\"
"
<<
m_Size
<<
'"'
<<
" flags=
\"
"
<<
m_Flags
<<
'"'
<<
" status=
\"
"
<<
GetState
(
-
1
)
<<
'"'
<<
"<start"
<<
m_Start
<<
"/>"
<<
"<end"
<<
m_End
<<
"/>"
;
os
<<
"</"
<<
GetClass
().
Lower
().
mb_str
()
<<
">
\n
"
;
}
#endif
gerbview/class_gerber_draw_item.h
0 → 100644
View file @
b992af3e
/*******************************************************************/
/* class_gerber_draw_item.h: definitions relatives to tracks, vias and zones */
/*******************************************************************/
#ifndef CLASS_GERBER_DRAW_ITEM_H
#define CLASS_GERBER_DRAW_ITEM_H
/*
* This program source code file is part of KICAD, a free EDA CAD application.
*
* Copyright (C) 1992-2010 <Jean-Pierre Charras>
* Copyright (C) 1992-2010 Kicad Developers, see change_log.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, you may find one here:
* http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* or you may search the http://www.gnu.org website for the version 2 license,
* or you may write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "base_struct.h"
/* Shapes id for basic shapes ( .m_Shape member ) */
enum
Gbr_Basic_Shapes
{
GBR_SEGMENT
=
0
,
// usual segment : line with rounded ends
GBR_ARC
,
// Arcs (with rounded ends)
GBR_CIRCLE
,
// ring
GBR_POLYGON
,
// polygonal shape
GBR_SPOT_CIRCLE
,
// flashed shape: round shape (can have hole)
GBR_SPOT_RECT
,
// flashed shape: rectangular shape can have hole)
GBR_SPOT_OVAL
,
// flashed shape: oval shape
GBR_MACRO
,
// complex shape described by a macro
GBR_LAST
// last value for this list
};
/***/
class
GERBER_DRAW_ITEM
:
public
BOARD_ITEM
{
// make SetNext() and SetBack() private so that they may not be called from anywhere.
// list management is done on GERBER_DRAW_ITEMs using DLIST<GERBER_DRAW_ITEM> only.
private
:
void
SetNext
(
EDA_BaseStruct
*
aNext
)
{
Pnext
=
aNext
;
}
void
SetBack
(
EDA_BaseStruct
*
aBack
)
{
Pback
=
aBack
;
}
public
:
int
m_Layer
;
int
m_Shape
;
// Shape and type of this gerber item
wxPoint
m_Start
;
// Line or arc start point or position of the shape
// for flashed items
wxPoint
m_End
;
// Line or arc end point
wxPoint
m_ArcCentre
;
// for arcs only: Centre of arc
std
::
vector
<
wxPoint
>
m_PolyCorners
;
// list of corners for polygons (G36 to G37 coordinates)
// or for complex shapes which are converted to polygon
wxSize
m_Size
;
// Flashed shapes size of the shape
// Lines : m_Size.x = m_Size.y = line width
bool
m_Flashed
;
// True for flashed items
int
m_DCode
;
// DCode used to draw this item.
// 0 for items that do not use DCodes (polygons)
// or when unknown and normal values are 10 to 999
// values 0 to 9 can be used for special purposes
public
:
GERBER_DRAW_ITEM
(
BOARD_ITEM
*
aParent
);
GERBER_DRAW_ITEM
(
const
GERBER_DRAW_ITEM
&
aSource
);
~
GERBER_DRAW_ITEM
();
/**
* Function Copy
* will copy this object
* the corresponding type.
* @return - GERBER_DRAW_ITEM*
*/
GERBER_DRAW_ITEM
*
Copy
()
const
;
GERBER_DRAW_ITEM
*
Next
()
const
{
return
(
GERBER_DRAW_ITEM
*
)
Pnext
;
}
GERBER_DRAW_ITEM
*
Back
()
const
{
return
(
GERBER_DRAW_ITEM
*
)
Pback
;
}
int
ReturnMaskLayer
()
{
return
1
<<
m_Layer
;
}
/**
* Function Move
* move this object.
* @param const wxPoint& aMoveVector - the move vector for this object.
*/
void
Move
(
const
wxPoint
&
aMoveVector
);
/**
* Function GetPosition
* returns the position of this object.
* @return const wxPoint& - The position of this object.
*/
wxPoint
&
GetPosition
()
{
return
m_Start
;
// it had to be start or end.
}
/**
* Function GetDcodeDescr
* returns the GetDcodeDescr of this object, or NULL.
* @return D_CODE* - a pointer to the DCode description (for flashed items).
*/
D_CODE
*
GetDcodeDescr
();
EDA_Rect
GetBoundingBox
();
/* Display on screen: */
void
Draw
(
WinEDA_DrawPanel
*
aPanel
,
wxDC
*
aDC
,
int
aDrawMode
,
const
wxPoint
&
aOffset
=
ZeroOffset
);
/** function DrawGbrPoly
* a helper function used id ::Draw to draw the polygon stored ion m_PolyCorners
*/
void
DrawGbrPoly
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
int
aColor
,
const
wxPoint
&
aOffset
,
bool
aFilledShape
);
/* divers */
int
Shape
()
const
{
return
m_Shape
;
}
/**
* Function DisplayInfo
* has knowledge about the frame and how and where to put status information
* about this object into the frame's message panel.
* Is virtual from EDA_BaseStruct.
* Display info about the track segment and the full track length
* @param frame A WinEDA_DrawFrame in which to print status information.
*/
void
DisplayInfo
(
WinEDA_DrawFrame
*
frame
);
wxString
ShowGBRShape
();
/**
* Function HitTest
* tests if the given wxPoint is within the bounds of this object.
* @param refPos A wxPoint to test
* @return bool - true if a hit, else false
*/
bool
HitTest
(
const
wxPoint
&
refPos
);
/**
* Function HitTest (overlayed)
* tests if the given wxRect intersect this object.
* For now, an ending point must be inside this rect.
* @param refPos A wxPoint to test
* @return bool - true if a hit, else false
*/
bool
HitTest
(
EDA_Rect
&
refArea
);
/**
* Function GetClass
* returns the class name.
* @return wxString
*/
wxString
GetClass
()
const
{
return
wxT
(
"GERBER_DRAW_ITEM"
);
}
bool
Save
(
FILE
*
aFile
)
const
;
};
#endif
/* CLASS_GERBER_DRAW_ITEM_H */
gerbview/dcode.cpp
View file @
b992af3e
/***************************/
/****
Read GERBER files
****/
/****
class D_CODE
****/
/***************************/
#include "fctsys.h"
...
...
@@ -7,53 +7,16 @@
#include "class_drawpanel.h"
#include "confirm.h"
#include "macros.h"
#include "trigo.h"
#include "gerbview.h"
#include "pcbplot.h"
#include "protos.h"
#include "class_gerber_draw_item.h"
#define DEFAULT_SIZE 100
/* Format Gerber: NOTES:
* Features history:
* Gn =
* G01 linear interpolation (right trace)
* G02, G20, G21 Circular interpolation, meaning trig < 0
* G03, G30, G31 Circular interpolation, meaning trig > 0
* G04 review
* G06 parabolic interpolation
* G07 Cubic Interpolation
* G10 linear interpolation (scale x10)
* G11 linear interpolation (0.1x range)
* G12 linear interpolation (0.01x scale)
* G52 plot symbol reference code by Dnn
* G53 plot symbol reference by Dnn; symbol rotates from -90 degrees
* G54 Selection Tool
* G55 Fashion photo exhibition
* G56 plot symbol reference code for DNN
* G57 displays the symbol link to the console
* G58 plot displays the symbol and link to the console
* G60 linear interpolation (scale x100)
* G70 Units = Inches
* G71 Units = Millimeters
* G74 circular interpolation removes 360 degree, has returned G01
* G75 circular interpolation Active 360 degree
* G90 mode absolute coordinates
* G91 Fashion Related Contacts
*
* Coordinates X, Y
* X and Y are followed by + or - and m + n digits (not separated)
* m = integer part
* n = part after the comma
* conventional formats: m = 2, n = 3 (size 2.3)
* m = 3, n = 4 (size 3.4)
* eg
* G__ X00345Y-06123 * D__
*
* Tools and D_CODES
* tool number (identification of shapes)
* 1 to 99 (Classical)
* 1 to 999
*
* D_CODES:
...
...
@@ -62,145 +25,14 @@
* D02 = light extinction (lift pen) when di placement
* D03 Flash
* D09 = VAPE Flash
* D10 ... = Indentification Tool (Opening)
* D10 ... = Indentification Tool (Shape id)
*
* For tools:
* DCode min = D10
* DCode max = 999
*/
GERBER
::
GERBER
(
int
aLayer
)
{
m_Layer
=
aLayer
;
// Layer Number
m_Selected_Tool
=
FIRST_DCODE
;
ResetDefaultValues
();
for
(
unsigned
ii
=
0
;
ii
<
DIM
(
m_Aperture_List
);
ii
++
)
m_Aperture_List
[
ii
]
=
0
;
m_Pcb
=
0
;
}
GERBER
::~
GERBER
()
{
for
(
unsigned
ii
=
0
;
ii
<
DIM
(
m_Aperture_List
);
ii
++
)
{
delete
m_Aperture_List
[
ii
];
// m_Aperture_List[ii] = NULL;
}
delete
m_Pcb
;
}
D_CODE
*
GERBER
::
GetDCODE
(
int
aDCODE
,
bool
create
)
{
unsigned
ndx
=
aDCODE
-
FIRST_DCODE
;
if
(
ndx
<
(
unsigned
)
DIM
(
m_Aperture_List
)
)
{
// lazily create the D_CODE if it does not exist.
if
(
create
)
{
if
(
m_Aperture_List
[
ndx
]
==
NULL
)
m_Aperture_List
[
ndx
]
=
new
D_CODE
(
ndx
+
FIRST_DCODE
);
}
return
m_Aperture_List
[
ndx
];
}
return
NULL
;
}
APERTURE_MACRO
*
GERBER
::
FindApertureMacro
(
const
APERTURE_MACRO
&
aLookup
)
{
APERTURE_MACRO_SET
::
iterator
iter
=
m_aperture_macros
.
find
(
aLookup
);
if
(
iter
!=
m_aperture_macros
.
end
()
)
{
APERTURE_MACRO
*
pam
=
(
APERTURE_MACRO
*
)
&
(
*
iter
);
return
pam
;
}
return
NULL
;
// not found
}
void
GERBER
::
ResetDefaultValues
()
{
m_FileName
.
Empty
();
m_Name
=
wxT
(
"no name"
);
// Layer name
m_LayerNegative
=
FALSE
;
// TRUE = Negative Layer
m_ImageNegative
=
FALSE
;
// TRUE = Negative image
m_GerbMetric
=
FALSE
;
// FALSE = Inches, TRUE = metric
m_Relative
=
FALSE
;
// FALSE = absolute Coord, RUE =
// relative Coord
m_NoTrailingZeros
=
FALSE
;
// True: trailing zeros deleted
m_MirorA
=
FALSE
;
// True: miror / axe A (X)
m_MirorB
=
FALSE
;
// True: miror / axe B (Y)
m_Has_DCode
=
FALSE
;
// TRUE = DCodes in file (FALSE = no
// DCode->
// separate DCode file
m_Offset
.
x
=
m_Offset
.
y
=
0
;
// Coord Offset
m_FmtScale
.
x
=
m_FmtScale
.
y
=
g_Default_GERBER_Format
%
10
;
m_FmtLen
.
x
=
m_FmtLen
.
y
=
m_FmtScale
.
x
+
(
g_Default_GERBER_Format
/
10
);
m_LayerScale
.
x
=
m_LayerScale
.
y
=
1.0
;
// scale (X and Y) this
// layer
m_Rotation
=
0
;
m_Iterpolation
=
GERB_INTERPOL_LINEAR_1X
;
// Linear, 90 arc, Circ.
m_360Arc_enbl
=
FALSE
;
// 360 deg circular
// interpolation disable
m_Current_Tool
=
0
;
// Current Tool (Dcode)
// number selected
m_CommandState
=
0
;
// gives tate of the
// stacking order analysis
m_CurrentPos
.
x
=
m_CurrentPos
.
y
=
0
;
// current specified coord
// for plot
m_PreviousPos
.
x
=
m_PreviousPos
.
y
=
0
;
// old current specified
// coord for plot
m_IJPos
.
x
=
m_IJPos
.
y
=
0
;
// current centre coord for
// plot arcs & circles
m_Current_File
=
NULL
;
// File to read
m_FilesPtr
=
0
;
m_Transform
[
0
][
0
]
=
m_Transform
[
1
][
1
]
=
1
;
m_Transform
[
0
][
1
]
=
m_Transform
[
1
][
0
]
=
0
;
// Rotation/mirror = Normal
m_PolygonFillMode
=
FALSE
;
m_PolygonFillModeState
=
0
;
}
int
GERBER
::
ReturnUsedDcodeNumber
()
{
int
count
=
0
;
for
(
unsigned
ii
=
0
;
ii
<
DIM
(
m_Aperture_List
);
ii
++
)
{
if
(
m_Aperture_List
[
ii
]
)
if
(
m_Aperture_List
[
ii
]
->
m_InUse
||
m_Aperture_List
[
ii
]
->
m_Defined
)
++
count
;
}
return
count
;
}
void
GERBER
::
InitToolTable
()
{
for
(
int
count
=
0
;
count
<
MAX_TOOLS
;
count
++
)
{
if
(
m_Aperture_List
[
count
]
==
NULL
)
continue
;
m_Aperture_List
[
count
]
->
m_Num_Dcode
=
count
+
FIRST_DCODE
;
m_Aperture_List
[
count
]
->
Clear_D_CODE_Data
();
}
}
/***************/
/* Class DCODE */
/***************/
...
...
@@ -228,6 +60,7 @@ void D_CODE::Clear_D_CODE_Data()
m_InUse
=
FALSE
;
m_Defined
=
FALSE
;
m_Macro
=
0
;
m_Rotation
=
0.0
;
}
...
...
@@ -370,7 +203,7 @@ int WinEDA_GerberFrame::Read_D_Code_File( const wxString& D_Code_FullFileName )
if
(
current_Dcode
<
FIRST_DCODE
)
continue
;
if
(
current_Dcode
>=
MAX_TOOLS
)
if
(
current_Dcode
>=
TOOLS_MAX_COUNT
)
continue
;
dcode
=
gerber
->
GetDCODE
(
current_Dcode
);
...
...
@@ -393,134 +226,358 @@ void WinEDA_GerberFrame::CopyDCodesSizeToItems()
{
static
D_CODE
dummy
(
999
);
//Used if D_CODE not found in list
for
(
TRACK
*
track
=
GetBoard
()
->
m_Track
;
track
;
track
=
track
->
Next
()
)
{
GERBER
*
gerber
=
g_GERBER_List
[
track
->
GetLayer
()];
wxASSERT
(
gerber
);
BOARD_ITEM
*
item
=
GetBoard
()
->
m_Drawings
;
D_CODE
*
dcode
=
gerber
->
GetDCODE
(
track
->
GetNet
(),
false
);
for
(
;
item
;
item
=
item
->
Next
()
)
{
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
D_CODE
*
dcode
=
gerb_item
->
GetDcodeDescr
();
wxASSERT
(
dcode
);
if
(
dcode
==
NULL
)
dcode
=
&
dummy
;
dcode
->
m_InUse
=
TRUE
;
gerb_item
->
m_Size
=
dcode
->
m_Size
;
if
(
// Line Item
(
track
->
m_Shape
==
S_SEGMENT
)
/* rectilinear segment */
||
(
track
->
m_Shape
==
S_RECT
)
/* rect segment form (i.e.
* non-rounded ends) */
||
(
track
->
m_Shape
==
S_ARC
)
/* segment arc (rounded tips) */
||
(
track
->
m_Shape
==
S_CIRCLE
)
/* segment in a circle (ring) */
||
(
track
->
m_Shape
==
S_ARC_RECT
)
/* segment arc (stretches)
* (GERBER)*/
(
gerb_item
->
m_Shape
==
GBR_SEGMENT
)
/* rectilinear segment */
||
(
gerb_item
->
m_Shape
==
GBR_ARC
)
/* segment arc (rounded tips) */
||
(
gerb_item
->
m_Shape
==
GBR_CIRCLE
)
/* segment in a circle (ring) */
)
{
track
->
m_Width
=
dcode
->
m_Size
.
x
;
}
else
// Spots ( Flashed Items )
{
int
width
,
len
;
wxSize
size
=
dcode
->
m_Size
;
width
=
MIN
(
size
.
x
,
size
.
y
);
len
=
MAX
(
size
.
x
,
size
.
y
)
-
width
;
track
->
m_Width
=
width
;
track
->
m_Start
.
x
=
(
track
->
m_Start
.
x
+
track
->
m_End
.
x
)
/
2
;
track
->
m_Start
.
y
=
(
track
->
m_Start
.
y
+
track
->
m_End
.
y
)
/
2
;
track
->
m_End
=
track
->
m_Start
;
// m_Start = m_End = Spot center
switch
(
dcode
->
m_Shape
)
{
case
APT_LINE
:
// might not appears here, but some broken
// gerber files use it
case
APT_CIRCLE
:
/* spot round (for GERBER) */
track
->
m_Shape
=
S
_SPOT_CIRCLE
;
gerb_item
->
m_Shape
=
GBR
_SPOT_CIRCLE
;
break
;
case
APT_OVAL
:
/* spot oval (for GERBER)*/
track
->
m_Shape
=
S_SPOT_OVALE
;
gerb_item
->
m_Shape
=
GBR_SPOT_OVAL
;
break
;
default
:
/* spot rect (for GERBER)*/
track
->
m_Shape
=
S
_SPOT_RECT
;
gerb_item
->
m_Shape
=
GBR
_SPOT_RECT
;
break
;
}
}
}
}
len
>>=
1
;
if
(
size
.
x
>
size
.
y
)
/** function DrawFlashedShape
* Draw the dcode shape for flashed items.
* When an item is flashed, the DCode shape is the shape of the item
*/
void
D_CODE
::
DrawFlashedShape
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
int
aColor
,
wxPoint
aShapePos
,
bool
aFilledShape
)
{
int
radius
;
switch
(
m_Shape
)
{
case
APT_CIRCLE
:
radius
=
m_Size
.
x
>>
1
;
if
(
!
aFilledShape
)
GRCircle
(
aClipBox
,
aDC
,
aShapePos
.
x
,
aShapePos
.
y
,
radius
,
aColor
);
else
if
(
m_DrillShape
==
0
)
GRFilledCircle
(
aClipBox
,
aDC
,
aShapePos
,
radius
,
aColor
);
else
if
(
m_DrillShape
==
1
)
// round hole
{
int
width
=
(
m_Size
.
x
-
m_Drill
.
x
)
/
2
;
GRCircle
(
aClipBox
,
aDC
,
aShapePos
,
radius
-
(
width
/
2
),
width
,
aColor
);
}
else
// rectangular hole
{
if
(
m_PolyCorners
.
size
()
==
0
)
ConvertShapeToPolygon
();
DrawFlashedPolygon
(
aClipBox
,
aDC
,
aColor
,
aFilledShape
,
aShapePos
);
}
break
;
case
APT_LINE
:
// not used for flashed items
break
;
case
APT_RECT
:
{
wxPoint
start
;
start
.
x
=
aShapePos
.
x
-
m_Size
.
x
/
2
;
start
.
y
=
aShapePos
.
y
-
m_Size
.
y
/
2
;
wxPoint
end
=
start
+
m_Size
;
if
(
!
aFilledShape
)
{
track
->
m_Start
.
x
-=
len
;
track
->
m_End
.
x
+=
len
;
GRRect
(
aClipBox
,
aDC
,
start
.
x
,
start
.
y
,
end
.
x
,
end
.
y
,
0
,
aColor
);
}
else
if
(
m_DrillShape
==
0
)
{
GRFilledRect
(
aClipBox
,
aDC
,
start
.
x
,
start
.
y
,
end
.
x
,
end
.
y
,
0
,
aColor
,
aColor
);
}
else
{
track
->
m_Start
.
y
-=
len
;
track
->
m_End
.
y
+=
len
;
if
(
m_PolyCorners
.
size
()
==
0
)
ConvertShapeToPolygon
();
DrawFlashedPolygon
(
aClipBox
,
aDC
,
aColor
,
aFilledShape
,
aShapePos
);
}
}
break
;
case
APT_OVAL
:
{
wxPoint
start
=
aShapePos
;
wxPoint
end
=
aShapePos
;
if
(
m_Size
.
x
>
m_Size
.
y
)
// horizontal oval
{
int
delta
=
(
m_Size
.
x
-
m_Size
.
y
)
/
2
;
start
.
x
-=
delta
;
end
.
x
+=
delta
;
radius
=
m_Size
.
y
;
}
else
// horizontal oval
{
int
delta
=
(
m_Size
.
y
-
m_Size
.
x
)
/
2
;
start
.
y
-=
delta
;
end
.
y
+=
delta
;
radius
=
m_Size
.
x
;
}
if
(
!
aFilledShape
)
{
GRCSegm
(
aClipBox
,
aDC
,
start
.
x
,
start
.
y
,
end
.
x
,
end
.
y
,
radius
,
aColor
);
}
else
if
(
m_DrillShape
==
0
)
{
GRFillCSegm
(
aClipBox
,
aDC
,
start
.
x
,
start
.
y
,
end
.
x
,
end
.
y
,
radius
,
aColor
);
}
else
{
if
(
m_PolyCorners
.
size
()
==
0
)
ConvertShapeToPolygon
();
DrawFlashedPolygon
(
aClipBox
,
aDC
,
aColor
,
aFilledShape
,
aShapePos
);
}
}
break
;
case
APT_POLYGON
:
if
(
m_PolyCorners
.
size
()
==
0
)
ConvertShapeToPolygon
();
DrawFlashedPolygon
(
aClipBox
,
aDC
,
aColor
,
aFilledShape
,
aShapePos
);
break
;
case
APT_MACRO
:
// TODO
break
;
}
}
void
WinEDA_GerberFrame
::
Liste_D_Codes
(
)
/** function DrawFlashedPolygon
* a helper function used id ::Draw to draw the polygon stored ion m_PolyCorners
* Draw some Apertures shapes when they are defined as filled polygons.
* APT_POLYGON is always a polygon, but some complex shapes are also converted to
* polygons (shapes with holes)
*/
void
D_CODE
::
DrawFlashedPolygon
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
int
aColor
,
bool
aFilled
,
const
wxPoint
&
aPosition
)
{
int
ii
,
jj
;
D_CODE
*
pt_D_code
;
wxString
Line
;
WinEDA_TextFrame
*
List
;
int
scale
=
10000
;
int
curr_layer
=
GetScreen
()
->
m_Active_Layer
;
List
=
new
WinEDA_TextFrame
(
this
,
_
(
"List D codes"
)
);
if
(
m_PolyCorners
.
size
()
==
0
)
return
;
for
(
int
layer
=
0
;
layer
<
32
;
layer
++
)
std
::
vector
<
wxPoint
>
points
;
points
=
m_PolyCorners
;
for
(
unsigned
ii
=
0
;
ii
<
points
.
size
();
ii
++
)
{
GERBER
*
gerber
=
g_GERBER_List
[
layer
];
if
(
gerber
==
NULL
)
continue
;
points
[
ii
]
+=
aPosition
;
}
if
(
gerber
->
ReturnUsedDcodeNumber
()
==
0
)
continue
;
GRClosedPoly
(
aClipBox
,
aDC
,
points
.
size
(),
&
points
[
0
],
aFilled
,
aColor
,
aColor
);
}
if
(
layer
==
curr_layer
)
Line
.
Printf
(
wxT
(
"*** Active layer (%2.2d) ***"
),
layer
+
1
);
else
Line
.
Printf
(
wxT
(
"*** layer %2.2d ***"
),
layer
+
1
);
List
->
Append
(
Line
);
for
(
ii
=
0
,
jj
=
1
;
ii
<
MAX_TOOLS
;
ii
++
)
/** function ConvertShapeToPolygon
* convert a shape to an equivalent polygon.
* Arcs and circles are approximated by segments
* Useful when a shape is not a graphic primitive (shape with hole,
* Rotated shape ... ) and cannot be easily drawn.
*/
void
D_CODE
::
ConvertShapeToPolygon
()
{
#define SEGS_CNT 32 // number of segments to approximate a circle
wxPoint
initialpos
;
wxPoint
currpos
;;
m_PolyCorners
.
clear
();
switch
(
m_Shape
)
{
pt_D_code
=
gerber
->
GetDCODE
(
ii
+
FIRST_DCODE
,
false
);
if
(
pt_D_code
==
NULL
)
continue
;
case
APT_CIRCLE
:
// creates only a circle with rectangular hole
currpos
.
x
=
m_Size
.
x
>>
1
;
initialpos
=
currpos
;
for
(
unsigned
ii
=
0
;
ii
<=
SEGS_CNT
;
ii
++
)
{
currpos
=
initialpos
;
RotatePoint
(
&
currpos
,
ii
*
3600
/
SEGS_CNT
);
m_PolyCorners
.
push_back
(
currpos
);
}
if
(
m_DrillShape
==
1
)
{
for
(
unsigned
ii
=
0
;
ii
<=
SEGS_CNT
;
ii
++
)
{
currpos
.
x
=
m_Drill
.
x
/
2
;
currpos
.
y
=
0
;
RotatePoint
(
&
currpos
,
ii
*
3600
/
SEGS_CNT
);
m_PolyCorners
.
push_back
(
currpos
);
}
m_PolyCorners
.
push_back
(
initialpos
);
// link to outline
}
if
(
m_DrillShape
==
2
)
// Create rectangular hole
{
currpos
.
x
=
m_Drill
.
x
/
2
;
currpos
.
y
=
m_Drill
.
y
/
2
;
m_PolyCorners
.
push_back
(
currpos
);
// link to hole and begin hole
currpos
.
x
-=
m_Drill
.
x
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
y
-=
m_Drill
.
y
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
x
+=
m_Drill
.
x
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
y
+=
m_Drill
.
y
;
m_PolyCorners
.
push_back
(
currpos
);
// close hole
m_PolyCorners
.
push_back
(
initialpos
);
// link to outline
}
break
;
if
(
!
pt_D_code
->
m_InUse
&&
!
pt_D_code
->
m_Defined
)
continue
;
case
APT_LINE
:
// Not used for flashed shapes
break
;
Line
.
Printf
(
wxT
(
"tool %2.2d: D%2.2d V %2.4f H %2.4f %s"
),
jj
,
pt_D_code
->
m_Num_Dcode
,
(
float
)
pt_D_code
->
m_Size
.
y
/
scale
,
(
float
)
pt_D_code
->
m_Size
.
x
/
scale
,
D_CODE
::
ShowApertureType
(
pt_D_code
->
m_Shape
)
);
case
APT_RECT
:
currpos
.
x
=
m_Size
.
x
/
2
;
currpos
.
y
=
m_Size
.
y
/
2
;
initialpos
=
currpos
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
x
-=
m_Size
.
x
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
y
-=
m_Size
.
y
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
x
+=
m_Size
.
x
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
y
+=
m_Size
.
y
;
m_PolyCorners
.
push_back
(
currpos
);
// close polygon
if
(
m_DrillShape
==
1
)
// build a round hole
{
for
(
int
ii
=
0
;
ii
<=
SEGS_CNT
;
ii
++
)
{
currpos
.
x
=
0
;
currpos
.
y
=
m_Drill
.
x
/
2
;
// m_Drill.x / 2 is the radius of the hole
RotatePoint
(
&
currpos
,
ii
*
3600
/
SEGS_CNT
);
m_PolyCorners
.
push_back
(
currpos
);
}
m_PolyCorners
.
push_back
(
initialpos
);
// link to outline
}
if
(
m_DrillShape
==
2
)
// Create rectangular hole
{
currpos
.
x
=
m_Drill
.
x
/
2
;
currpos
.
y
=
m_Drill
.
y
/
2
;
m_PolyCorners
.
push_back
(
currpos
);
// link to hole and begin hole
currpos
.
x
-=
m_Drill
.
x
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
y
-=
m_Drill
.
y
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
x
+=
m_Drill
.
x
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
y
+=
m_Drill
.
y
;
m_PolyCorners
.
push_back
(
currpos
);
// close hole
m_PolyCorners
.
push_back
(
initialpos
);
// link to outline
}
break
;
if
(
!
pt_D_code
->
m_Defined
)
Line
+=
wxT
(
" ?"
);
case
APT_OVAL
:
{
int
delta
,
radius
;
// we create an horizontal oval shape. then rotate if needed
if
(
m_Size
.
x
>
m_Size
.
y
)
// horizontal oval
{
delta
=
(
m_Size
.
x
-
m_Size
.
y
)
/
2
;
radius
=
m_Size
.
y
/
2
;
}
else
// vertical oval
{
delta
=
(
m_Size
.
y
-
m_Size
.
x
)
/
2
;
radius
=
m_Size
.
x
/
2
;
}
currpos
.
y
=
radius
;
initialpos
=
currpos
;
m_PolyCorners
.
push_back
(
currpos
);
if
(
!
pt_D_code
->
m_InUse
)
Line
+=
wxT
(
" *"
);
// build the right arc of the shape
unsigned
ii
=
0
;
for
(
;
ii
<=
SEGS_CNT
/
2
;
ii
++
)
{
currpos
=
initialpos
;
RotatePoint
(
&
currpos
,
ii
*
3600
/
SEGS_CNT
);
currpos
.
x
+=
delta
;
m_PolyCorners
.
push_back
(
currpos
);
}
List
->
Append
(
Line
);
jj
++
;
// build the left arc of the shape
for
(
ii
=
SEGS_CNT
/
2
;
ii
<=
SEGS_CNT
;
ii
++
)
{
currpos
=
initialpos
;
RotatePoint
(
&
currpos
,
ii
*
3600
/
SEGS_CNT
);
currpos
.
x
-=
delta
;
m_PolyCorners
.
push_back
(
currpos
);
}
m_PolyCorners
.
push_back
(
initialpos
);
// close outline
if
(
m_Size
.
y
>
m_Size
.
x
)
// vertical oval, rotate polygon.
{
for
(
unsigned
jj
=
0
;
jj
<
m_PolyCorners
.
size
();
jj
++
)
RotatePoint
(
&
m_PolyCorners
[
jj
],
900
);
}
if
(
m_DrillShape
==
1
)
// build a round hole
{
for
(
ii
=
0
;
ii
<=
SEGS_CNT
;
ii
++
)
{
currpos
.
x
=
0
;
currpos
.
y
=
m_Drill
.
x
/
2
;
// m_Drill.x / 2 is the radius of the hole
RotatePoint
(
&
currpos
,
ii
*
3600
/
SEGS_CNT
);
m_PolyCorners
.
push_back
(
currpos
);
}
m_PolyCorners
.
push_back
(
initialpos
);
// link to outline
}
if
(
m_DrillShape
==
2
)
// Create rectangular hole
{
currpos
.
x
=
m_Drill
.
x
/
2
;
currpos
.
y
=
m_Drill
.
y
/
2
;
m_PolyCorners
.
push_back
(
currpos
);
// link to hole and begin hole
currpos
.
x
-=
m_Drill
.
x
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
y
-=
m_Drill
.
y
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
x
+=
m_Drill
.
x
;
m_PolyCorners
.
push_back
(
currpos
);
currpos
.
y
+=
m_Drill
.
y
;
m_PolyCorners
.
push_back
(
currpos
);
// close hole
m_PolyCorners
.
push_back
(
initialpos
);
// link to outline
}
}
break
;
ii
=
List
->
ShowModal
();
List
->
Destroy
();
if
(
ii
<
0
)
return
;
case
APT_POLYGON
:
// TODO
break
;
case
APT_MACRO
:
// TODO
break
;
}
}
gerbview/dcode.h
0 → 100644
View file @
b992af3e
/**************/
/* dcode.h */
/**************/
#ifndef _DCODE_H_
#define _DCODE_H_
#include <vector>
#include <set>
#include "base_struct.h"
/**
* Enum APERTURE_T
* is the set of all gerber aperture types allowed, according to page 16 of
* http://gerbv.sourceforge.net/docs/rs274xrevd_e.pdf
*/
enum
APERTURE_T
{
APT_CIRCLE
=
'C'
,
APT_LINE
=
'L'
,
APT_RECT
=
'R'
,
APT_OVAL
=
'0'
,
APT_POLYGON
=
'P'
,
APT_MACRO
=
'M'
};
#define FIRST_DCODE 10
#define LAST_DCODE 999 // dcodes values are from 10 to 999
#define TOOLS_MAX_COUNT (LAST_DCODE+1)
class
D_CODE
;
/**
* Class DCODE_PARAM
* holds a parameter for a DCODE or an "aperture macro" as defined within
* standard RS274X. The \a value field can be a constant, i.e. "immediate"
* parameter or it may not be used if this param is going to defer to the
* referencing aperture macro. In that case, the \a index field is an index
* into the aperture macro's parameters.
*/
class
DCODE_PARAM
{
public
:
DCODE_PARAM
()
:
index
(
-
1
),
value
(
0
.
0
)
{}
double
GetValue
(
const
D_CODE
*
aDcode
)
const
;
void
SetValue
(
double
aValue
)
{
value
=
aValue
;
index
=
-
1
;
}
/**
* Function IsImmediate
* tests if this DCODE_PARAM holds an immediate parameter or is a pointer
* into a parameter held by an owning D_CODE.
*/
bool
IsImmediate
()
const
{
return
index
==
-
1
;
}
unsigned
GetIndex
()
const
{
return
(
unsigned
)
index
;
}
void
SetIndex
(
int
aIndex
)
{
index
=
aIndex
;
}
private
:
int
index
;
///< if -1, then \a value field is an immediate value,
// else this is an index into parent's
// D_CODE.m_am_params.
double
value
;
///< if IsImmediate()==true then use the value, else
// not used.
};
/**
* Enum AM_PRIMITIVE_ID
* is the set of all "aperture macro primitives" (primitive numbers). See
* Table 3 in http://gerbv.sourceforge.net/docs/rs274xrevd_e.pdf
*/
enum
AM_PRIMITIVE_ID
{
AMP_CIRCLE
=
1
,
AMP_LINE2
=
2
,
AMP_LINE20
=
20
,
AMP_LINE_CENTER
=
21
,
AMP_LINE_LOWER_LEFT
=
22
,
AMP_EOF
=
3
,
AMP_OUTLINE
=
4
,
AMP_POLYGON
=
5
,
AMP_MOIRE
=
6
,
AMP_THERMAL
=
7
,
};
typedef
std
::
vector
<
DCODE_PARAM
>
DCODE_PARAMS
;
/**
* Struct AM_PRIMITIVE
* holds an aperture macro primitive as given in Table 3 of
* http://gerbv.sourceforge.net/docs/rs274xrevd_e.pdf
*/
struct
AM_PRIMITIVE
{
AM_PRIMITIVE_ID
primitive_id
;
///< The primitive type
DCODE_PARAMS
params
;
///< A sequence of parameters used by
// the primitive
/**
* Function GetExposure
* returns the first parameter in integer form. Some but not all primitives
* use the first parameter as an exposure control.
*/
int
GetExposure
()
const
{
// No D_CODE* for GetValue()
wxASSERT
(
params
.
size
()
&&
params
[
0
].
IsImmediate
()
);
return
(
int
)
params
[
0
].
GetValue
(
NULL
);
}
};
typedef
std
::
vector
<
AM_PRIMITIVE
>
AM_PRIMITIVES
;
/**
* Struct APERTURE_MACRO
* helps support the "aperture macro" defined within standard RS274X.
*/
struct
APERTURE_MACRO
{
wxString
name
;
///< The name of the aperture macro
AM_PRIMITIVES
primitives
;
///< A sequence of AM_PRIMITIVEs
};
/**
* Struct APERTURE_MACRO_less_than
* is used by std:set<APERTURE_MACRO> instantiation which uses
* APERTURE_MACRO.name as its key.
*/
struct
APERTURE_MACRO_less_than
{
// a "less than" test on two APERTURE_MACROs (.name wxStrings)
bool
operator
()(
const
APERTURE_MACRO
&
am1
,
const
APERTURE_MACRO
&
am2
)
const
{
return
am1
.
name
.
Cmp
(
am2
.
name
)
<
0
;
// case specific wxString compare
}
};
/**
* Type APERTURE_MACRO_SET
* is a sorted collection of APERTURE_MACROS whose key is the name field in
* the APERTURE_MACRO.
*/
typedef
std
::
set
<
APERTURE_MACRO
,
APERTURE_MACRO_less_than
>
APERTURE_MACRO_SET
;
typedef
std
::
pair
<
APERTURE_MACRO_SET
::
iterator
,
bool
>
APERTURE_MACRO_SET_PAIR
;
/**
* Class D_CODE
* holds a gerber DCODE definition.
*/
class
D_CODE
{
friend
class
DCODE_PARAM
;
APERTURE_MACRO
*
m_Macro
;
///< no ownership, points to
// GERBER.m_aperture_macros element
/**
* parameters used only when this D_CODE holds a reference to an aperture
* macro, and these parameters would customize the macro.
*/
DCODE_PARAMS
m_am_params
;
std
::
vector
<
wxPoint
>
m_PolyCorners
;
/* Polygon used to draw AMP_POLYGON shape and some other
* complex shapes which are converted to polygon
* (shapes with hole, rotated rectangles ...
*/
public
:
wxSize
m_Size
;
/* Horizontal and vertical dimensions. */
APERTURE_T
m_Shape
;
/* shape ( Line, rectangle, circle , oval .. ) */
int
m_Num_Dcode
;
/* D code ( >= 10 ) */
wxSize
m_Drill
;
/* dimension of the hole (if any) */
int
m_DrillShape
;
/* shape of the hole (round = 1, rect = 2) */
double
m_Rotation
;
/* shape rotation in degrees */
bool
m_InUse
;
/* FALSE if not used */
bool
m_Defined
;
/* FALSE if not defined */
wxString
m_SpecialDescr
;
public
:
D_CODE
(
int
num_dcode
);
~
D_CODE
();
void
Clear_D_CODE_Data
();
void
AppendParam
(
double
aValue
)
{
DCODE_PARAM
param
;
param
.
SetValue
(
aValue
);
m_am_params
.
push_back
(
param
);
}
void
SetMacro
(
APERTURE_MACRO
*
aMacro
)
{
m_Macro
=
aMacro
;
}
APERTURE_MACRO
*
GetMacro
()
{
return
m_Macro
;
}
/**
* Function ShowApertureType
* returns a character string telling what type of aperture type \a aType is.
* @param aType The aperture type to show.
*/
static
const
wxChar
*
ShowApertureType
(
APERTURE_T
aType
);
/** function DrawFlashedShape
* Draw the dcode shape for flashed items.
* When an item is flashed, the DCode shape is the shape of the item
*/
void
DrawFlashedShape
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
int
aColor
,
wxPoint
aShapePos
,
bool
aFilledShape
);
/** function DrawFlashedPolygon
* a helper function used id ::Draw to draw the polygon stored ion m_PolyCorners
* Draw some Apertures shapes when they are defined as filled polygons.
* APT_POLYGON is always a polygon, but some complex shapes are also converted to
* polygons (shapes with holes, some rotated shapes)
*/
void
DrawFlashedPolygon
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
int
aColor
,
bool
aFilled
,
const
wxPoint
&
aPosition
);
/** function ConvertShapeToPolygon
* convert a shape to an equivalent polygon.
* Arcs and circles are approximated by segments
* Useful when a shape is not a graphic primitive (shape with hole,
* rotated shape ... ) and cannot be easily drawn.
*/
void
ConvertShapeToPolygon
(
);
};
inline
double
DCODE_PARAM
::
GetValue
(
const
D_CODE
*
aDcode
)
const
{
if
(
IsImmediate
()
)
return
value
;
else
{
// the first one was numbered 1, not zero, as in $1, see page 19 of spec.
unsigned
ndx
=
GetIndex
()
-
1
;
wxASSERT
(
aDcode
);
// get the parameter from the aDcode
if
(
ndx
<
aDcode
->
m_am_params
.
size
()
)
return
aDcode
->
m_am_params
[
ndx
].
GetValue
(
NULL
);
else
{
wxASSERT
(
GetIndex
()
-
1
<
aDcode
->
m_am_params
.
size
()
);
return
0
.
0
;
}
}
}
#endif // ifndef _DCODE_H_
gerbview/deltrack.cpp
View file @
b992af3e
/*********************************************/
/* Edit Track: Erase Routines */
/* Drop the segment, track, and net area */
/* Edit Track: Erase functions */
/*********************************************/
#include "fctsys.h"
#include "common.h"
#include "class_drawpanel.h"
//
#include "class_drawpanel.h"
#include "gerbview.h"
#include "
protos
.h"
#include "
class_gerber_draw_item
.h"
void
WinEDA_GerberFrame
::
Delete_DCode_Items
(
wxDC
*
DC
,
...
...
@@ -18,73 +17,22 @@ void WinEDA_GerberFrame::Delete_DCode_Items( wxDC* DC,
if
(
dcode_value
<
FIRST_DCODE
)
// No tool selected
return
;
TRACK
*
next
;
for
(
TRACK
*
track
=
GetBoard
()
->
m_Track
;
track
;
track
=
next
)
BOARD_ITEM
*
item
=
GetBoard
()
->
m_Drawings
;
BOARD_ITEM
*
next
;
for
(
;
item
;
item
=
next
)
{
next
=
track
->
Next
();
next
=
item
->
Next
();
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
if
(
dcode_value
!=
track
->
GetNet
()
)
if
(
dcode_value
!=
gerb_item
->
m_DCode
)
continue
;
if
(
layer_number
>=
0
&&
layer_number
!=
track
->
GetLayer
()
)
if
(
layer_number
>=
0
&&
layer_number
!=
gerb_item
->
m_Layer
)
continue
;
Delete_Segment
(
DC
,
track
);
// TODO: Delete_Item( DC, item
);
}
GetScreen
()
->
SetCurItem
(
NULL
);
}
/* Removes 1 segment of track.
*
* If There is evidence of new track: erase segment
* Otherwise: Delete segment under the cursor.
*/
TRACK
*
WinEDA_GerberFrame
::
Delete_Segment
(
wxDC
*
DC
,
TRACK
*
Track
)
{
if
(
Track
==
NULL
)
return
NULL
;
if
(
Track
->
m_Flags
&
IS_NEW
)
// Trace in progress, delete the last
// segment
{
if
(
g_CurrentTrackList
.
GetCount
()
>
0
)
{
// Change track.
delete
g_CurrentTrackList
.
PopBack
();
if
(
g_CurrentTrackList
.
GetCount
()
&&
g_CurrentTrackSegment
->
Type
()
==
TYPE_VIA
)
{
delete
g_CurrentTrackList
.
PopBack
();
}
UpdateStatusBar
();
if
(
g_CurrentTrackList
.
GetCount
()
==
0
)
{
DrawPanel
->
ManageCurseur
=
NULL
;
DrawPanel
->
ForceCloseManageCurseur
=
NULL
;
return
NULL
;
}
else
{
if
(
DrawPanel
->
ManageCurseur
)
DrawPanel
->
ManageCurseur
(
DrawPanel
,
DC
,
FALSE
);
return
g_CurrentTrackSegment
;
}
}
return
NULL
;
}
Trace_Segment
(
GetBoard
(),
DrawPanel
,
DC
,
Track
,
GR_XOR
);
DLIST
<
TRACK
>*
container
=
(
DLIST
<
TRACK
>*
)
Track
->
GetList
();
wxASSERT
(
container
);
container
->
Remove
(
Track
);
GetScreen
()
->
SetModify
();
return
NULL
;
}
gerbview/dummy_functions.cpp
View file @
b992af3e
...
...
@@ -10,7 +10,6 @@
#include "common.h"
#include "pcbnew.h"
TRACK
*
Marque_Une_Piste
(
BOARD
*
aPcb
,
TRACK
*
aStartSegm
,
int
*
aSegmCount
,
...
...
@@ -19,3 +18,4 @@ TRACK* Marque_Une_Piste( BOARD* aPcb,
{
return
NULL
;
}
gerbview/edit.cpp
View file @
b992af3e
...
...
@@ -53,12 +53,11 @@ void WinEDA_GerberFrame::OnLeftClick( wxDC* DC, const wxPoint& MousePos )
DrawStruct
=
GerberGeneralLocateAndDisplay
();
if
(
DrawStruct
==
NULL
)
break
;
if
(
DrawStruct
->
Type
()
==
TYPE_TRACK
)
{
Delete_Segment
(
DC
,
(
TRACK
*
)
DrawStruct
);
/* TODO:
Delete_Item( DC, (GERBER_DRAW_ITEM*) DrawStruct );
GetScreen()->SetCurItem( NULL );
GetScreen()->SetModify();
}
*/
break
;
default
:
...
...
@@ -85,13 +84,9 @@ void WinEDA_GerberFrame::Process_Special_Functions( wxCommandEvent& event )
{
case
wxID_CUT
:
case
wxID_COPY
:
case
ID_POPUP_MIRROR_X_BLOCK
:
case
ID_POPUP_DELETE_BLOCK
:
case
ID_POPUP_PLACE_BLOCK
:
case
ID_POPUP_ZOOM_BLOCK
:
case
ID_POPUP_FLIP_BLOCK
:
case
ID_POPUP_ROTATE_BLOCK
:
case
ID_POPUP_COPY_BLOCK
:
break
;
case
ID_POPUP_CANCEL_CURRENT_COMMAND
:
...
...
@@ -196,13 +191,6 @@ void WinEDA_GerberFrame::Process_Special_Functions( wxCommandEvent& event )
HandleBlockPlace
(
&
dc
);
break
;
case
ID_POPUP_COPY_BLOCK
:
GetScreen
()
->
m_BlockLocate
.
m_Command
=
BLOCK_COPY
;
GetScreen
()
->
m_BlockLocate
.
SetMessageBlock
(
this
);
DrawPanel
->
m_AutoPAN_Request
=
FALSE
;
HandleBlockEnd
(
&
dc
);
break
;
case
ID_POPUP_ZOOM_BLOCK
:
GetScreen
()
->
m_BlockLocate
.
m_Command
=
BLOCK_ZOOM
;
GetScreen
()
->
m_BlockLocate
.
SetMessageBlock
(
this
);
...
...
@@ -216,12 +204,6 @@ void WinEDA_GerberFrame::Process_Special_Functions( wxCommandEvent& event )
HandleBlockEnd
(
&
dc
);
break
;
case
ID_POPUP_MIRROR_X_BLOCK
:
GetScreen
()
->
m_BlockLocate
.
m_Command
=
BLOCK_MIRROR_X
;
GetScreen
()
->
m_BlockLocate
.
SetMessageBlock
(
this
);
HandleBlockEnd
(
&
dc
);
break
;
case
ID_GERBVIEW_POPUP_DELETE_DCODE_ITEMS
:
if
(
gerber_layer
)
Delete_DCode_Items
(
&
dc
,
gerber_layer
->
m_Selected_Tool
,
...
...
gerbview/export_to_pcbnew.cpp
View file @
b992af3e
...
...
@@ -13,6 +13,7 @@
#include "gerbview.h"
#include "class_board_design_settings.h"
#include "class_gerber_draw_item.h"
#include "protos.h"
static
int
SavePcbFormatAscii
(
WinEDA_GerberFrame
*
frame
,
...
...
@@ -128,7 +129,6 @@ static int SavePcbFormatAscii( WinEDA_GerberFrame* frame, FILE* aFile,
int
*
LayerLookUpTable
)
{
char
line
[
256
];
TRACK
*
track
;
BOARD
*
gerberPcb
=
frame
->
GetBoard
();
BOARD
*
pcb
;
...
...
@@ -136,10 +136,11 @@ static int SavePcbFormatAscii( WinEDA_GerberFrame* frame, FILE* aFile,
// create an image of gerber data
pcb
=
new
BOARD
(
NULL
,
frame
);
for
(
track
=
gerberPcb
->
m_Track
;
track
;
track
=
track
->
Next
()
)
BOARD_ITEM
*
item
=
gerberPcb
->
m_Drawings
;
for
(
;
item
;
item
=
item
->
Next
()
)
{
int
layer
=
track
->
GetLayer
();
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
int
layer
=
gerb_item
->
m_Layer
;
int
pcb_layer_number
=
LayerLookUpTable
[
layer
];
if
(
pcb_layer_number
<
0
||
pcb_layer_number
>
LAST_NO_COPPER_LAYER
)
continue
;
...
...
@@ -149,17 +150,17 @@ static int SavePcbFormatAscii( WinEDA_GerberFrame* frame, FILE* aFile,
DRAWSEGMENT
*
drawitem
=
new
DRAWSEGMENT
(
pcb
,
TYPE_DRAWSEGMENT
);
drawitem
->
SetLayer
(
pcb_layer_number
);
drawitem
->
m_Start
=
track
->
m_Start
;
drawitem
->
m_End
=
track
->
m_End
;
drawitem
->
m_Width
=
track
->
m_Width
;
drawitem
->
m_Start
=
gerb_item
->
m_Start
;
drawitem
->
m_End
=
gerb_item
->
m_End
;
drawitem
->
m_Width
=
gerb_item
->
m_Size
.
x
;
if
(
track
->
m_Shape
==
S
_ARC
)
if
(
gerb_item
->
m_Shape
==
GBR
_ARC
)
{
double
cx
=
track
->
m_Param
;
double
cy
=
track
->
GetSubNet
()
;
double
a
=
atan2
(
track
->
m_Start
.
y
-
cy
,
track
->
m_Start
.
x
-
cx
);
double
b
=
atan2
(
track
->
m_End
.
y
-
cy
,
track
->
m_End
.
x
-
cx
);
double
cx
=
gerb_item
->
m_ArcCentre
.
x
;
double
cy
=
gerb_item
->
m_ArcCentre
.
y
;
double
a
=
atan2
(
gerb_item
->
m_Start
.
y
-
cy
,
gerb_item
->
m_Start
.
x
-
cx
);
double
b
=
atan2
(
gerb_item
->
m_End
.
y
-
cy
,
gerb_item
->
m_End
.
x
-
cx
);
drawitem
->
m_Shape
=
S_ARC
;
drawitem
->
m_Angle
=
(
int
)
fmod
(
...
...
@@ -175,34 +176,28 @@ static int SavePcbFormatAscii( WinEDA_GerberFrame* frame, FILE* aFile,
TRACK
*
newtrack
;
// replace spots with vias when possible
if
(
track
->
m_Shape
==
S
_SPOT_CIRCLE
||
track
->
m_Shape
==
S
_SPOT_RECT
||
track
->
m_Shape
==
S_SPOT_OVALE
)
if
(
gerb_item
->
m_Shape
==
GBR
_SPOT_CIRCLE
||
gerb_item
->
m_Shape
==
GBR
_SPOT_RECT
||
gerb_item
->
m_Shape
==
GBR_SPOT_OVAL
)
{
newtrack
=
new
SEGVIA
(
(
const
SEGVIA
&
)
*
track
);
newtrack
=
new
SEGVIA
(
pcb
);
// A spot is found, and can be a via: change it to via, and
// delete other
// spots at same location
newtrack
->
m_Shape
=
VIA_THROUGH
;
newtrack
->
SetLayer
(
0x0F
);
// Layers are 0 to 15 (Cu/Cmp)
newtrack
->
SetDrillDefault
();
// Compute the via position from track position ( Via position
// is the
// position of the middle of the track segment )
newtrack
->
m_Start
.
x
=
(
newtrack
->
m_Start
.
x
+
newtrack
->
m_End
.
x
)
/
2
;
newtrack
->
m_Start
.
y
=
(
newtrack
->
m_Start
.
y
+
newtrack
->
m_End
.
y
)
/
2
;
newtrack
->
m_End
=
newtrack
->
m_Start
;
newtrack
->
m_Start
=
newtrack
->
m_End
=
gerb_item
->
m_Start
;
newtrack
->
m_Width
=
(
gerb_item
->
m_Size
.
x
+
gerb_item
->
m_Size
.
y
)
/
2
;
}
else
// a true TRACK
{
newtrack
=
track
->
Copy
(
);
newtrack
=
new
TRACK
(
pcb
);
newtrack
->
SetLayer
(
pcb_layer_number
);
newtrack
->
m_Start
=
gerb_item
->
m_Start
;
newtrack
->
m_End
=
gerb_item
->
m_End
;
newtrack
->
m_Width
=
gerb_item
->
m_Size
.
x
;
}
pcb
->
Add
(
newtrack
);
...
...
@@ -210,7 +205,7 @@ static int SavePcbFormatAscii( WinEDA_GerberFrame* frame, FILE* aFile,
}
// delete redundant vias
for
(
track
=
pcb
->
m_Track
;
track
;
track
=
track
->
Next
()
)
for
(
TRACK
*
track
=
pcb
->
m_Track
;
track
;
track
=
track
->
Next
()
)
{
if
(
track
->
m_Shape
!=
VIA_THROUGH
)
continue
;
...
...
gerbview/gerber_test_files/aperture-circle-flash-with_hole.gbr
0 → 100644
View file @
b992af3e
G04 Test flashing of circular apertures*
G04 Four groups of circular apertures are arranged in a square*
G04 Handcoded by Julian Lamb *
%MOIN*%
%FSLAX23Y23*%
%ADD10C,0.050*%
%ADD11C,0.050X0.025*%
%ADD12C,0.050X0.025X0.030*%
G04 No hole, centered at 0,0 *
G54D10*
X0Y0D03*
G04 Round hole, centered at 0.1,0 *
G54D11*
X00100Y0D03*
G04 Square hole, centered at 0,0.1 *
G54D12*
X0Y00100D03*
G04 Two, with round holes, slightly overlapping, centered at 0.1,0.1 *
G54D11*
X00100Y00090D03*
X00100Y00110D03*
M02*
gerbview/gerber_test_files/aperture-obround-flash-with_hole.gbr
0 → 100644
View file @
b992af3e
G04 Test flashing of obround apertures*
G04 Four groups of obround apertures are arranged in a square*
G04 Handcoded by Julian Lamb *
%MOIN*%
%FSLAX23Y23*%
%ADD10O,0.050X0.080*%
%ADD11O,0.080X0.050X0.025*%
%ADD12O,0.050X0.025X0.025X0.0150*%
G04 No hole, centered at 0,0 *
G54D10*
X0Y0D03*
G04 Round hole, centered at 0.1,0 *
G54D11*
X00100Y0D03*
G04 Square hole, centered at 0,0.1 *
G54D12*
X0Y00100D03*
G04 Two, with round holes, slightly overlapping, centered at 0.1,0.1 *
G54D11*
X00100Y00090D03*
X00100Y00110D03*
M02*
gerbview/gerber_test_files/test-aperture-polygon-flash.gbr
0 → 100644
View file @
b992af3e
G04 Test flashing of polygon apertures*
G04 Four groups of polygon apertures are arranged in a square*
G04 Handcoded by Julian Lamb *
%MOIN*%
%FSLAX23Y23*%
%ADD10P,0.050X3*%
%ADD11P,0.050X6X-45X0.035*%
%ADD12P,0.040X10X25X0.025X0.025X0.0150*%
G04 Triangle, centered at 0,0 *
G54D10*
X0Y0D03*
G04 Hexagon with round hole rotate 45 degreed ccwise, centered at 0.1,0 *
G54D11*
X00100Y0D03*
G04 10-sided with square hole rotated 25 degrees, centered at 0,0.1 *
G54D12*
X0Y00100D03*
G04 Two, with round holes, slightly overlapping, centered at 0.1,0.1 *
G54D11*
X00100Y00090D03*
X00100Y00110D03*
M02*
gerbview/gerber_test_files/test-aperture-rectangle-flash-with_hole.gbr
0 → 100644
View file @
b992af3e
G04 Test flashing of rectangular apertures*
G04 Four groups of rectangular apertures are arranged in a square*
G04 Handcoded by Julian Lamb *
%MOIN*%
%FSLAX23Y23*%
%ADD10R,0.050X0.080*%
%ADD11R,0.080X0.050X0.025*%
%ADD12R,0.050X0.025X0.025X0.0150*%
G04 No hole, centered at 0,0 *
G54D10*
X0Y0D03*
G04 Round hole, centered at 0.1,0 *
G54D11*
X00100Y0D03*
G04 Square hole, centered at 0,0.1 *
G54D12*
X0Y00100D03*
G04 Two, with round holes, slightly overlapping, centered at 0.1,0.1 *
G54D11*
X00100Y00090D03*
X00100Y00110D03*
M02*
gerbview/gerberframe.cpp
View file @
b992af3e
...
...
@@ -13,6 +13,7 @@
#include "class_drawpanel.h"
#include "gerbview.h"
#include "class_gerber_draw_item.h"
#include "pcbplot.h"
#include "bitmaps.h"
#include "protos.h"
...
...
@@ -113,6 +114,10 @@ BEGIN_EVENT_TABLE( WinEDA_GerberFrame, WinEDA_BasePcbFrame )
// Option toolbar
EVT_TOOL_RANGE
(
ID_TB_OPTIONS_START
,
ID_TB_OPTIONS_END
,
WinEDA_GerberFrame
::
OnSelectOptionToolbar
)
EVT_TOOL
(
ID_TB_OPTIONS_SHOW_FLASHED_ITEMS_SKETCH
,
WinEDA_GerberFrame
::
OnSelectOptionToolbar
)
EVT_TOOL
(
ID_TB_OPTIONS_SHOW_LINES_SKETCH
,
WinEDA_GerberFrame
::
OnSelectOptionToolbar
)
EVT_TOOL
(
ID_TB_OPTIONS_SHOW_LAYERS_MANAGER_VERTICAL_TOOLBAR
,
WinEDA_GerberFrame
::
OnSelectOptionToolbar
)
EVT_TOOL
(
ID_TB_OPTIONS_SHOW_DCODES
,
...
...
@@ -236,117 +241,22 @@ void WinEDA_GerberFrame::OnCloseWindow( wxCloseEvent& Event )
}
/** Function SetToolbars()
* Set the tools state for the toolbars, according to display options
*/
void
WinEDA_GerberFrame
::
SetToolbars
()
int
WinEDA_GerberFrame
::
BestZoom
()
{
PCB_SCREEN
*
screen
=
(
PCB_SCREEN
*
)
GetScreen
();
int
layer
=
screen
->
m_Active_Layer
;
GERBER
*
gerber
=
g_GERBER_List
[
layer
];
if
(
m_HToolBar
==
NULL
)
return
;
if
(
GetScreen
()
->
m_BlockLocate
.
m_Command
==
BLOCK_MOVE
)
{
m_HToolBar
->
EnableTool
(
wxID_CUT
,
true
);
m_HToolBar
->
EnableTool
(
wxID_COPY
,
true
);
}
else
{
m_HToolBar
->
EnableTool
(
wxID_CUT
,
false
);
m_HToolBar
->
EnableTool
(
wxID_COPY
,
false
);
}
if
(
m_SelLayerBox
&&
(
m_SelLayerBox
->
GetSelection
()
!=
screen
->
m_Active_Layer
)
)
{
m_SelLayerBox
->
SetSelection
(
screen
->
m_Active_Layer
);
}
if
(
m_SelLayerTool
)
{
if
(
gerber
)
{
int
sel_index
;
m_SelLayerTool
->
Enable
(
true
);
if
(
gerber
->
m_Selected_Tool
<
FIRST_DCODE
)
// No tool selected
sel_index
=
0
;
else
sel_index
=
gerber
->
m_Selected_Tool
-
FIRST_DCODE
+
1
;
if
(
sel_index
!=
m_SelLayerTool
->
GetSelection
()
)
{
m_SelLayerTool
->
SetSelection
(
sel_index
);
}
}
else
{
m_SelLayerTool
->
SetSelection
(
0
);
m_SelLayerTool
->
Enable
(
false
);
}
}
double
x
,
y
;
EDA_Rect
bbox
;
if
(
m_OptionsToolBar
)
BOARD_ITEM
*
item
=
GetBoard
()
->
m_Drawings
;
for
(
;
item
;
item
=
item
->
Next
()
)
{
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SELECT_UNIT_MM
,
g_UserUnit
==
MILLIMETRES
?
true
:
false
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SELECT_UNIT_INCH
,
g_UserUnit
==
INCHES
?
true
:
false
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_POLAR_COORD
,
DisplayOpt
.
DisplayPolarCood
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_GRID
,
IsGridVisible
()
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SELECT_CURSOR
,
m_CursorShape
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_PADS_SKETCH
,
!
m_DisplayPadFill
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_TRACKS_SKETCH
,
!
m_DisplayPcbTrackFill
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_POLYGONS_SKETCH
,
g_DisplayPolygonsModeSketch
==
0
?
0
:
1
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_DCODES
,
IsElementVisible
(
DCODES_VISIBLE
)
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_LAYERS_MANAGER_VERTICAL_TOOLBAR
,
m_show_layer_manager_tools
);
if
(
m_show_layer_manager_tools
)
GetMenuBar
()
->
SetLabel
(
ID_MENU_GERBVIEW_SHOW_HIDE_LAYERS_MANAGER_DIALOG
,
_
(
"Hide &Layers Manager"
)
);
else
GetMenuBar
()
->
SetLabel
(
ID_MENU_GERBVIEW_SHOW_HIDE_LAYERS_MANAGER_DIALOG
,
_
(
"Show &Layers Manager"
)
);
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
bbox
.
Merge
(
gerb_item
->
GetBoundingBox
()
);
}
DisplayUnitsMsg
();
if
(
m_auimgr
.
GetManagedWindow
()
)
m_auimgr
.
Update
();
}
int
WinEDA_GerberFrame
::
BestZoom
()
{
double
x
,
y
;
wxSize
size
;
GetBoard
()
->
ComputeBoundaryBox
();
size
=
DrawPanel
->
GetClientSize
();
x
=
(
(
double
)
GetBoard
()
->
m_BoundaryBox
.
GetWidth
()
+
GetScreen
()
->
GetGridSize
().
x
)
/
(
double
)
size
.
x
;
y
=
(
(
double
)
GetBoard
()
->
m_BoundaryBox
.
GetHeight
()
+
GetScreen
()
->
GetGridSize
().
y
)
/
(
double
)
size
.
y
;
GetScreen
()
->
m_Curseur
=
GetBoard
()
->
m_BoundaryBox
.
Centre
();
wxSize
size
=
DrawPanel
->
GetClientSize
();
x
=
(
bbox
.
GetWidth
()
+
GetScreen
()
->
GetGridSize
().
x
)
/
(
double
)
size
.
x
;
y
=
(
bbox
.
GetHeight
()
+
GetScreen
()
->
GetGridSize
().
y
)
/
(
double
)
size
.
y
;
GetScreen
()
->
m_Curseur
=
bbox
.
Centre
();
return
wxRound
(
MAX
(
x
,
y
)
*
(
double
)
GetScreen
()
->
m_ZoomScalar
);
}
...
...
@@ -506,3 +416,65 @@ void WinEDA_GerberFrame::SetLanguage( wxCommandEvent& event )
ReFillLayerWidget
();
}
void
WinEDA_GerberFrame
::
Liste_D_Codes
(
)
{
int
ii
,
jj
;
D_CODE
*
pt_D_code
;
wxString
Line
;
WinEDA_TextFrame
*
List
;
int
scale
=
10000
;
int
curr_layer
=
GetScreen
()
->
m_Active_Layer
;
List
=
new
WinEDA_TextFrame
(
this
,
_
(
"List D codes"
)
);
for
(
int
layer
=
0
;
layer
<
32
;
layer
++
)
{
GERBER
*
gerber
=
g_GERBER_List
[
layer
];
if
(
gerber
==
NULL
)
continue
;
if
(
gerber
->
ReturnUsedDcodeNumber
()
==
0
)
continue
;
if
(
layer
==
curr_layer
)
Line
.
Printf
(
wxT
(
"*** Active layer (%2.2d) ***"
),
layer
+
1
);
else
Line
.
Printf
(
wxT
(
"*** layer %2.2d ***"
),
layer
+
1
);
List
->
Append
(
Line
);
for
(
ii
=
0
,
jj
=
1
;
ii
<
TOOLS_MAX_COUNT
;
ii
++
)
{
pt_D_code
=
gerber
->
GetDCODE
(
ii
+
FIRST_DCODE
,
false
);
if
(
pt_D_code
==
NULL
)
continue
;
if
(
!
pt_D_code
->
m_InUse
&&
!
pt_D_code
->
m_Defined
)
continue
;
Line
.
Printf
(
wxT
(
"tool %2.2d: D%2.2d V %2.4f H %2.4f %s"
),
jj
,
pt_D_code
->
m_Num_Dcode
,
(
float
)
pt_D_code
->
m_Size
.
y
/
scale
,
(
float
)
pt_D_code
->
m_Size
.
x
/
scale
,
D_CODE
::
ShowApertureType
(
pt_D_code
->
m_Shape
)
);
if
(
!
pt_D_code
->
m_Defined
)
Line
+=
wxT
(
" ?"
);
if
(
!
pt_D_code
->
m_InUse
)
Line
+=
wxT
(
" *"
);
List
->
Append
(
Line
);
jj
++
;
}
}
ii
=
List
->
ShowModal
();
List
->
Destroy
();
if
(
ii
<
0
)
return
;
}
gerbview/gerbview.h
View file @
b992af3e
...
...
@@ -8,6 +8,7 @@
#include <vector>
#include <set>
#include "dcode.h"
class
WinEDA_GerberFrame
;
class
BOARD
;
...
...
@@ -54,22 +55,6 @@ extern Ki_PageDescr* g_GerberPageSizeList[];
extern
const
wxString
GerbviewShowPageSizeOption
;
extern
const
wxString
GerbviewShowDCodes
;
/**
* Enum APERTURE_T
* is the set of all gerber aperture types allowed, according to page 16 of
* http://gerbv.sourceforge.net/docs/rs274xrevd_e.pdf
*/
enum
APERTURE_T
{
APT_CIRCLE
=
'C'
,
APT_LINE
=
'L'
,
APT_RECT
=
'R'
,
APT_OVAL
=
'0'
,
APT_POLYGON
=
'P'
,
APT_MACRO
=
'M'
};
// Interpolation type
enum
Gerb_Interpolation
{
...
...
@@ -106,9 +91,6 @@ enum Gerb_GCommand
};
#define MAX_TOOLS 2048
#define FIRST_DCODE 10
enum
Gerb_Analyse_Cmd
{
CMD_IDLE
=
0
,
...
...
@@ -119,223 +101,13 @@ enum Gerb_Analyse_Cmd
class
D_CODE
;
/**
* Class DCODE_PARAM
* holds a parameter for a DCODE or an "aperture macro" as defined within
* standard RS274X. The \a value field can be a constant, i.e. "immediate"
* parameter or it may not be used if this param is going to defer to the
* referencing aperture macro. In that case, the \a index field is an index
* into the aperture macro's parameters.
*/
class
DCODE_PARAM
{
public
:
DCODE_PARAM
()
:
index
(
-
1
),
value
(
0
.
0
)
{}
double
GetValue
(
const
D_CODE
*
aDcode
)
const
;
void
SetValue
(
double
aValue
)
{
value
=
aValue
;
index
=
-
1
;
}
/**
* Function IsImmediate
* tests if this DCODE_PARAM holds an immediate parameter or is a pointer
* into a parameter held by an owning D_CODE.
*/
bool
IsImmediate
()
const
{
return
index
==
-
1
;
}
unsigned
GetIndex
()
const
{
return
(
unsigned
)
index
;
}
void
SetIndex
(
int
aIndex
)
{
index
=
aIndex
;
}
private
:
int
index
;
///< if -1, then \a value field is an immediate value,
// else this is an index into parent's
// D_CODE.m_am_params.
double
value
;
///< if IsImmediate()==true then use the value, else
// not used.
};
/**
* Enum AM_PRIMITIVE_ID
* is the set of all "aperture macro primitives" (primitive numbers). See
* Table 3 in http://gerbv.sourceforge.net/docs/rs274xrevd_e.pdf
*/
enum
AM_PRIMITIVE_ID
{
AMP_CIRCLE
=
1
,
AMP_LINE2
=
2
,
AMP_LINE20
=
20
,
AMP_LINE_CENTER
=
21
,
AMP_LINE_LOWER_LEFT
=
22
,
AMP_EOF
=
3
,
AMP_OUTLINE
=
4
,
AMP_POLYGON
=
5
,
AMP_MOIRE
=
6
,
AMP_THERMAL
=
7
,
};
typedef
std
::
vector
<
DCODE_PARAM
>
DCODE_PARAMS
;
/**
* Struct AM_PRIMITIVE
* holds an aperture macro primitive as given in Table 3 of
* http://gerbv.sourceforge.net/docs/rs274xrevd_e.pdf
*/
struct
AM_PRIMITIVE
{
AM_PRIMITIVE_ID
primitive_id
;
///< The primitive type
DCODE_PARAMS
params
;
///< A sequence of parameters used by
// the primitive
/**
* Function GetExposure
* returns the first parameter in integer form. Some but not all primitives
* use the first parameter as an exposure control.
*/
int
GetExposure
()
const
{
// No D_CODE* for GetValue()
wxASSERT
(
params
.
size
()
&&
params
[
0
].
IsImmediate
()
);
return
(
int
)
params
[
0
].
GetValue
(
NULL
);
}
};
typedef
std
::
vector
<
AM_PRIMITIVE
>
AM_PRIMITIVES
;
/**
* Struct APERTURE_MACRO
* helps support the "aperture macro" defined within standard RS274X.
*/
struct
APERTURE_MACRO
{
wxString
name
;
///< The name of the aperture macro
AM_PRIMITIVES
primitives
;
///< A sequence of AM_PRIMITIVEs
};
/**
* Struct APERTURE_MACRO_less_than
* is used by std:set<APERTURE_MACRO> instantiation which uses
* APERTURE_MACRO.name as its key.
*/
struct
APERTURE_MACRO_less_than
{
// a "less than" test on two APERTURE_MACROs (.name wxStrings)
bool
operator
()(
const
APERTURE_MACRO
&
am1
,
const
APERTURE_MACRO
&
am2
)
const
{
return
am1
.
name
.
Cmp
(
am2
.
name
)
<
0
;
// case specific wxString compare
}
};
/**
* Type APERTURE_MACRO_SET
* is a sorted collection of APERTURE_MACROS whose key is the name field in
* the APERTURE_MACRO.
*/
typedef
std
::
set
<
APERTURE_MACRO
,
APERTURE_MACRO_less_than
>
APERTURE_MACRO_SET
;
typedef
std
::
pair
<
APERTURE_MACRO_SET
::
iterator
,
bool
>
APERTURE_MACRO_SET_PAIR
;
/**
* Class D_CODE
* holds a gerber DCODE definition.
*/
class
D_CODE
{
friend
class
DCODE_PARAM
;
APERTURE_MACRO
*
m_Macro
;
///< no ownership, points to
// GERBER.m_aperture_macros element
/**
* parameters used only when this D_CODE holds a reference to an aperture
* macro, and these parameters would customize the macro.
*/
DCODE_PARAMS
m_am_params
;
public
:
wxSize
m_Size
;
/* Horizontal and vertical dimensions. */
APERTURE_T
m_Shape
;
/* shape ( Line, rectangle, circle , oval .. ) */
int
m_Num_Dcode
;
/* D code ( >= 10 ) */
wxSize
m_Drill
;
/* dimension of the hole (if any) */
int
m_DrillShape
;
/* shape of the hole (round = 1, rect = 2) */
bool
m_InUse
;
/* FALSE if not used */
bool
m_Defined
;
/* FALSE if not defined */
wxString
m_SpecialDescr
;
public
:
D_CODE
(
int
num_dcode
);
~
D_CODE
();
void
Clear_D_CODE_Data
();
void
AppendParam
(
double
aValue
)
{
DCODE_PARAM
param
;
param
.
SetValue
(
aValue
);
m_am_params
.
push_back
(
param
);
}
void
SetMacro
(
APERTURE_MACRO
*
aMacro
)
{
m_Macro
=
aMacro
;
}
APERTURE_MACRO
*
GetMacro
()
{
return
m_Macro
;
}
/**
* Function ShowApertureType
* returns a character string telling what type of aperture type \a aType is.
* @param aType The aperture type to show.
*/
static
const
wxChar
*
ShowApertureType
(
APERTURE_T
aType
);
};
inline
double
DCODE_PARAM
::
GetValue
(
const
D_CODE
*
aDcode
)
const
{
if
(
IsImmediate
()
)
return
value
;
else
{
// the first one was numbered 1, not zero, as in $1, see page 19 of spec.
unsigned
ndx
=
GetIndex
()
-
1
;
wxASSERT
(
aDcode
);
// get the parameter from the aDcode
if
(
ndx
<
aDcode
->
m_am_params
.
size
()
)
return
aDcode
->
m_am_params
[
ndx
].
GetValue
(
NULL
);
else
{
wxASSERT
(
GetIndex
()
-
1
<
aDcode
->
m_am_params
.
size
()
);
return
0
.
0
;
}
}
}
/**
* Class GERBER
* holds the data for one gerber file or layer
*/
class
GERBER
{
D_CODE
*
m_Aperture_List
[
MAX_TOOLS
];
///< Dcode (Aperture) List for this layer
D_CODE
*
m_Aperture_List
[
TOOLS_MAX_COUNT
];
///< Dcode (Aperture) List for this layer
bool
m_Exposure
;
///< whether an aperture macro tool is flashed on or off
BOARD
*
m_Pcb
;
...
...
gerbview/gerbview_config.h
View file @
b992af3e
...
...
@@ -35,7 +35,7 @@ static PARAM_CFG_WXSTRING DrillExtBufCfg
static
PARAM_CFG_INT
UnitCfg
// Units; 0 inches, 1 mm
(
wxT
(
"Unit
e
"
),
wxT
(
"Unit
s
"
),
(
int
*
)
&
g_UserUnit
,
MILLIMETRES
);
...
...
gerbview/gerbview_id.h
View file @
b992af3e
...
...
@@ -24,6 +24,8 @@ enum gerbview_ids
ID_GERBVIEW_DISPLAY_OPTIONS_SETUP
,
ID_TB_OPTIONS_SHOW_LAYERS_MANAGER_VERTICAL_TOOLBAR
,
ID_TB_OPTIONS_SHOW_DCODES
,
ID_TB_OPTIONS_SHOW_FLASHED_ITEMS_SKETCH
,
ID_TB_OPTIONS_SHOW_LINES_SKETCH
,
ID_GERBER_END_LIST
};
...
...
gerbview/hotkeys.cpp
View file @
b992af3e
...
...
@@ -39,7 +39,7 @@ static Ki_HotkeyInfo HkHelp( wxT( "Help: this message" ), HK_HELP, '?' );
static
Ki_HotkeyInfo
HkSwitchUnits
(
wxT
(
"Switch Units"
),
HK_SWITCH_UNITS
,
'U'
);
static
Ki_HotkeyInfo
HkTrackDisplayMode
(
wxT
(
"Track Display Mode"
),
HK_SWITCH_
TRACK
_DISPLAY_MODE
,
'F'
);
HK_SWITCH_
GBR_ITEMS
_DISPLAY_MODE
,
'F'
);
static
Ki_HotkeyInfo
HkSwitch2NextCopperLayer
(
wxT
(
"Switch to Next Layer"
),
...
...
@@ -134,7 +134,7 @@ void WinEDA_GerberFrame::OnHotKey( wxDC* DC, int hotkey,
g_UserUnit
=
(
g_UserUnit
==
INCHES
)
?
MILLIMETRES
:
INCHES
;
break
;
case
HK_SWITCH_
TRACK
_DISPLAY_MODE
:
case
HK_SWITCH_
GBR_ITEMS
_DISPLAY_MODE
:
DisplayOpt
.
DisplayPcbTrackFill
^=
1
;
DisplayOpt
.
DisplayPcbTrackFill
&=
1
;
DrawPanel
->
Refresh
();
break
;
...
...
gerbview/hotkeys.h
View file @
b992af3e
...
...
@@ -11,7 +11,7 @@
// for shared hotkeys id
enum
hotkey_id_commnand
{
HK_SWITCH_UNITS
=
HK_COMMON_END
,
HK_SWITCH_
TRACK
_DISPLAY_MODE
,
HK_SWITCH_
GBR_ITEMS
_DISPLAY_MODE
,
HK_SWITCH_LAYER_TO_NEXT
,
HK_SWITCH_LAYER_TO_PREVIOUS
};
...
...
gerbview/initpcb.cpp
View file @
b992af3e
...
...
@@ -9,7 +9,8 @@
#include "confirm.h"
#include "gerbview.h"
#include "protos.h"
#include "class_gerber_draw_item.h"
//#include "protos.h"
bool
WinEDA_GerberFrame
::
Clear_Pcb
(
bool
query
)
...
...
@@ -24,13 +25,8 @@ bool WinEDA_GerberFrame::Clear_Pcb( bool query )
if
(
!
IsOK
(
this
,
_
(
"Current data will be lost?"
)
)
)
return
FALSE
;
}
GetBoard
()
->
m_Drawings
.
DeleteAll
();
GetBoard
()
->
m_Track
.
DeleteAll
();
GetBoard
()
->
m_Zone
.
DeleteAll
();
for
(
layer
=
0
;
layer
<
32
;
layer
++
)
{
if
(
g_GERBER_List
[
layer
]
)
...
...
@@ -60,26 +56,15 @@ void WinEDA_GerberFrame::Erase_Current_Layer( bool query )
if
(
query
&&
!
IsOK
(
this
,
msg
)
)
return
;
/* Delete tracks (spots and lines) */
TRACK
*
PtNext
;
for
(
TRACK
*
pt_segm
=
GetBoard
()
->
m_Track
;
pt_segm
!=
NULL
;
pt_segm
=
(
TRACK
*
)
PtNext
)
{
PtNext
=
pt_segm
->
Next
();
if
(
pt_segm
->
GetLayer
()
!=
layer
)
continue
;
pt_segm
->
DeleteStructure
();
}
/* Delete polygons */
SEGZONE
*
Nextzone
;
for
(
SEGZONE
*
zone
=
GetBoard
()
->
m_Zone
;
zone
!=
NULL
;
zone
=
Nextzone
)
BOARD_ITEM
*
item
=
GetBoard
()
->
m_Drawings
;
BOARD_ITEM
*
next
;
for
(
;
item
;
item
=
next
)
{
Nextzone
=
zone
->
Next
();
if
(
zone
->
GetLayer
()
!=
layer
)
next
=
item
->
Next
();
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
if
(
gerb_item
->
m_Layer
!=
layer
)
continue
;
zone
->
DeleteStructure
();
gerb_item
->
DeleteStructure
();
}
ScreenPcb
->
SetModify
();
...
...
gerbview/lay2plot.cpp
deleted
100644 → 0
View file @
3ae0df15
/****************/
/* lay2plot.cpp */
/****************/
#include "fctsys.h"
#include "common.h"
#include "class_drawpanel.h"
#include "gerbview.h"
#include "protos.h"
/* Routine to plot the pcb, by selected layers. */
void
Print_PcbItems
(
BOARD
*
Pcb
,
wxDC
*
DC
,
int
drawmode
,
int
printmasklayer
)
{
DISPLAY_OPTIONS
save_opt
;
TRACK
*
pt_piste
;
save_opt
=
DisplayOpt
;
DisplayOpt
.
DisplayPadFill
=
FILLED
;
DisplayOpt
.
DisplayViaFill
=
FILLED
;
DisplayOpt
.
DisplayPadNum
=
0
;
DisplayOpt
.
DisplayPadIsol
=
0
;
DisplayOpt
.
DisplayPcbTrackFill
=
FILLED
;
DisplayOpt
.
ShowTrackClearanceMode
=
DO_NOT_SHOW_CLEARANCE
;
DisplayOpt
.
DisplayDrawItems
=
FILLED
;
DisplayOpt
.
DisplayZonesMode
=
0
;
pt_piste
=
Pcb
->
m_Track
;
for
(
;
pt_piste
!=
NULL
;
pt_piste
=
pt_piste
->
Next
()
)
{
// if( (printmasklayer & ReturnMaskLayer(pt_piste) ) == 0 ) continue;
Trace_Segment
(
Pcb
,
NULL
,
DC
,
pt_piste
,
drawmode
);
}
DisplayOpt
=
save_opt
;
}
gerbview/locate.cpp
View file @
b992af3e
...
...
@@ -12,454 +12,12 @@
#include "protos.h"
int
ux0
,
uy0
,
dx
,
dy
,
spot_cX
,
spot_cY
;
static
TRACK
*
Locate_Zone
(
TRACK
*
start_adresse
,
int
layer
,
int
typeloc
);
static
TRACK
*
Locate_Zone
(
TRACK
*
start_adresse
,
wxPoint
ref
,
int
layer
);
static
TRACK
*
Locate_Pistes
(
TRACK
*
start_adresse
,
int
Layer
,
int
typeloc
);
static
TRACK
*
Locate_Pistes
(
TRACK
*
start_adresse
,
wxPoint
ref
,
int
Layer
);
static
DRAWSEGMENT
*
Locate_Segment_Pcb
(
BOARD
*
Pcb
,
int
typeloc
);
static
TEXTE_PCB
*
Locate_Texte_Pcb
(
TEXTE_PCB
*
pt_txt_pcb
,
int
typeloc
);
static
int
distance
(
int
seuil
);
/* Macro for calculating the coordinates of the cursor position.
*/
#define SET_REF_POS( ref ) if( typeloc == CURSEUR_ON_GRILLE ) \
{ ref = ActiveScreen->m_Curseur; } \
else { ref = ActiveScreen->m_MousePosition; }
/* Display the character of the localized STRUCTURE and return a pointer
* to it.
*/
BOARD_ITEM
*
WinEDA_GerberFrame
::
Locate
(
int
typeloc
)
{
TEXTE_PCB
*
pt_texte_pcb
;
TRACK
*
Track
,
*
TrackLocate
;
DRAWSEGMENT
*
DrawSegm
;
int
layer
;
/* Locate tracks and vias, with priority to vias */
layer
=
GetScreen
()
->
m_Active_Layer
;
Track
=
Locate_Pistes
(
GetBoard
()
->
m_Track
,
-
1
,
typeloc
);
if
(
Track
!=
NULL
)
{
TrackLocate
=
Track
;
while
(
(
TrackLocate
=
Locate_Pistes
(
TrackLocate
,
layer
,
typeloc
)
)
!=
NULL
)
{
Track
=
TrackLocate
;
if
(
TrackLocate
->
Type
()
==
TYPE_VIA
)
break
;
TrackLocate
=
TrackLocate
->
Next
();
}
Track
->
DisplayInfo
(
this
);
return
Track
;
}
pt_texte_pcb
=
Locate_Texte_Pcb
(
(
TEXTE_PCB
*
)
GetBoard
()
->
m_Drawings
.
GetFirst
(),
typeloc
);
if
(
pt_texte_pcb
)
{
pt_texte_pcb
->
DisplayInfo
(
this
);
return
pt_texte_pcb
;
}
if
(
(
DrawSegm
=
Locate_Segment_Pcb
(
GetBoard
(),
typeloc
)
)
!=
NULL
)
{
return
DrawSegm
;
}
if
(
(
TrackLocate
=
Locate_Zone
(
GetBoard
()
->
m_Zone
,
GetScreen
()
->
m_Active_Layer
,
typeloc
)
)
!=
NULL
)
{
TrackLocate
->
DisplayInfo
(
this
);
return
TrackLocate
;
}
MsgPanel
->
EraseMsgBox
();
return
NULL
;
}
/* Locate of segments of pcb edge or draw as active layer.
* Returns:
* Pointer to START segment if found
* NULL if nothing found
*/
DRAWSEGMENT
*
Locate_Segment_Pcb
(
BOARD
*
Pcb
,
int
typeloc
)
{
BOARD_ITEM
*
PtStruct
;
DRAWSEGMENT
*
pts
;
wxPoint
ref
;
PCB_SCREEN
*
screen
=
(
PCB_SCREEN
*
)
ActiveScreen
;
SET_REF_POS
(
ref
);
PtStruct
=
Pcb
->
m_Drawings
;
for
(
;
PtStruct
!=
NULL
;
PtStruct
=
PtStruct
->
Next
()
)
{
if
(
PtStruct
->
Type
()
!=
TYPE_DRAWSEGMENT
)
continue
;
pts
=
(
DRAWSEGMENT
*
)
PtStruct
;
ux0
=
pts
->
m_Start
.
x
;
uy0
=
pts
->
m_Start
.
y
;
dx
=
pts
->
m_End
.
x
-
ux0
;
dy
=
pts
->
m_End
.
y
-
uy0
;
spot_cX
=
ref
.
x
-
ux0
;
spot_cY
=
ref
.
y
-
uy0
;
if
(
pts
->
GetLayer
()
!=
screen
->
m_Active_Layer
)
continue
;
if
(
(
pts
->
m_Shape
==
S_CIRCLE
)
||
(
pts
->
m_Shape
==
S_ARC
)
)
{
int
rayon
,
dist
,
StAngle
,
EndAngle
,
MouseAngle
;
rayon
=
(
int
)
hypot
(
(
double
)
(
dx
),
(
double
)
(
dy
)
);
dist
=
(
int
)
hypot
(
(
double
)
(
spot_cX
),
(
double
)
(
spot_cY
)
);
if
(
abs
(
rayon
-
dist
)
<=
(
pts
->
m_Width
/
2
)
)
{
if
(
pts
->
m_Shape
==
S_CIRCLE
)
return
pts
;
MouseAngle
=
(
int
)
ArcTangente
(
spot_cY
,
spot_cX
);
StAngle
=
(
int
)
ArcTangente
(
dy
,
dx
);
EndAngle
=
StAngle
+
pts
->
m_Angle
;
if
(
EndAngle
>
3600
)
{
StAngle
-=
3600
;
EndAngle
-=
3600
;
}
if
(
(
MouseAngle
>=
StAngle
)
&&
(
MouseAngle
<=
EndAngle
)
)
return
pts
;
}
}
else
{
if
(
distance
(
pts
->
m_Width
/
2
)
)
return
pts
;
}
}
return
NULL
;
}
/*
* 1 - Locate segment of track at current cursor position.
* 2 - Locate segment of track point by point.
* Ref_pX, ref_pY.r
*
* The search begins to address start_adresse
*/
TRACK
*
Locate_Pistes
(
TRACK
*
start_adresse
,
int
Layer
,
int
typeloc
)
{
wxPoint
ref
;
SET_REF_POS
(
ref
);
return
Locate_Pistes
(
start_adresse
,
ref
,
Layer
);
}
TRACK
*
Locate_Pistes
(
TRACK
*
start_adresse
,
wxPoint
ref
,
int
Layer
)
{
TRACK
*
Track
;
int
l_piste
;
/* half-width of the track */
for
(
Track
=
start_adresse
;
Track
!=
NULL
;
Track
=
Track
->
Next
()
)
{
if
(
Track
->
GetState
(
BUSY
|
DELETED
)
)
continue
;
/* Calculate coordinates of the test segment. */
l_piste
=
Track
->
m_Width
>>
1
;
ux0
=
Track
->
m_Start
.
x
;
uy0
=
Track
->
m_Start
.
y
;
dx
=
Track
->
m_End
.
x
;
dy
=
Track
->
m_End
.
y
;
dx
-=
ux0
;
dy
-=
uy0
;
spot_cX
=
ref
.
x
-
ux0
;
spot_cY
=
ref
.
y
-
uy0
;
if
(
Track
->
Type
()
==
TYPE_VIA
)
{
if
(
(
abs
(
spot_cX
)
<=
l_piste
)
&&
(
abs
(
spot_cY
)
<=
l_piste
)
)
{
return
Track
;
}
continue
;
}
if
(
Layer
>=
0
)
if
(
Track
->
GetLayer
()
!=
Layer
)
continue
;
if
(
distance
(
l_piste
)
)
return
Track
;
}
return
NULL
;
}
/*
* Locate zone area at the cursor position.
*
* The search begins to address start_adresse
*/
TRACK
*
Locate_Zone
(
TRACK
*
start_adresse
,
int
layer
,
int
typeloc
)
{
wxPoint
ref
;
SET_REF_POS
(
ref
);
return
Locate_Zone
(
start_adresse
,
ref
,
layer
);
}
/*
* Locate zone area at point.
*
* The search begins to address start_adresse
*/
TRACK
*
Locate_Zone
(
TRACK
*
start_adresse
,
wxPoint
ref
,
int
layer
)
{
TRACK
*
Zone
;
int
l_segm
;
for
(
Zone
=
start_adresse
;
Zone
!=
NULL
;
Zone
=
Zone
->
Next
()
)
{
l_segm
=
Zone
->
m_Width
>>
1
;
ux0
=
Zone
->
m_Start
.
x
;
uy0
=
Zone
->
m_Start
.
y
;
dx
=
Zone
->
m_End
.
x
;
dy
=
Zone
->
m_End
.
y
;
dx
-=
ux0
;
dy
-=
uy0
;
spot_cX
=
ref
.
x
-
ux0
;
spot_cY
=
ref
.
y
-
uy0
;
if
(
(
layer
!=
-
1
)
&&
(
Zone
->
GetLayer
()
!=
layer
)
)
continue
;
if
(
distance
(
l_segm
)
)
return
Zone
;
}
return
NULL
;
}
/* Location of text on the PCB:
* INPUT: char pointer to the beginning of the search area
* Return: pointer to the text description located.
*/
TEXTE_PCB
*
Locate_Texte_Pcb
(
TEXTE_PCB
*
pt_txt_pcb
,
int
typeloc
)
{
int
angle
;
EDA_BaseStruct
*
PtStruct
;
wxPoint
ref
;
SET_REF_POS
(
ref
);
PtStruct
=
(
EDA_BaseStruct
*
)
pt_txt_pcb
;
for
(
;
PtStruct
!=
NULL
;
PtStruct
=
PtStruct
->
Next
()
)
{
if
(
PtStruct
->
Type
()
!=
TYPE_TEXTE
)
continue
;
pt_txt_pcb
=
(
TEXTE_PCB
*
)
PtStruct
;
angle
=
pt_txt_pcb
->
m_Orient
;
ux0
=
pt_txt_pcb
->
m_Pos
.
x
;
uy0
=
pt_txt_pcb
->
m_Pos
.
y
;
dx
=
(
pt_txt_pcb
->
m_Size
.
x
*
pt_txt_pcb
->
GetLength
()
)
/
2
;
dy
=
pt_txt_pcb
->
m_Size
.
y
/
2
;
dx
*=
13
;
dx
/=
9
;
/* Character for factor 13/9. */
/* Cursor in the rectangle around the center. */
spot_cX
=
ref
.
x
-
ux0
;
spot_cY
=
ref
.
y
-
uy0
;
RotatePoint
(
&
spot_cX
,
&
spot_cY
,
-
angle
);
if
(
(
abs
(
spot_cX
)
<=
abs
(
dx
)
)
&&
(
abs
(
spot_cY
)
<=
abs
(
dy
)
)
)
return
pt_txt_pcb
;
}
return
NULL
;
}
/*
* Calculate the distance from the cursor to a line segment:
* (Track, edge, contour module ..
* Returns:
* 0 if distance > threshold
* 1 if distance <= threshold
* Variables used (must be initialized before use, and
* are brought to the mark center on the origin of the segment)
* dx, dy = coord of extremity segment.
* spot_cX, spot_cY = coord of mouse cursor
* Search 4 cases:
* Horizontal segment
* Vertical segment
* Segment 45
* Any segment
*/
int
distance
(
int
seuil
)
{
int
cXrot
,
cYrot
,
segX
,
segY
;
int
pointX
,
pointY
;
segX
=
dx
;
segY
=
dy
;
pointX
=
spot_cX
;
pointY
=
spot_cY
;
/* Reroute coordinate for the segment in 1st quadrant (coord> = 0). */
if
(
segX
<
0
)
/* Set > 0 if symmetrical about the axis Y. */
{
segX
=
-
segX
;
pointX
=
-
pointX
;
}
if
(
segY
<
0
)
/* Set > 0 if symmetrical about the axis X. */
{
segY
=
-
segY
;
pointY
=
-
pointY
;
}
if
(
segY
==
0
)
/* Horizontal track. */
{
if
(
abs
(
pointY
)
<=
seuil
)
{
if
(
(
pointX
>=
0
)
&&
(
pointX
<=
segX
)
)
return
1
;
if
(
(
pointX
<
0
)
&&
(
pointX
>=
-
seuil
)
)
{
if
(
(
(
pointX
*
pointX
)
+
(
pointY
*
pointY
)
)
<=
(
seuil
*
seuil
)
)
return
1
;
}
if
(
(
pointX
>
segX
)
&&
(
pointX
<=
(
segX
+
seuil
)
)
)
{
if
(
(
(
(
pointX
-
segX
)
*
(
pointX
-
segX
)
)
+
(
pointY
*
pointY
)
)
<=
(
seuil
*
seuil
)
)
return
1
;
}
}
}
else
if
(
segX
==
0
)
/* Vertical track. */
{
if
(
abs
(
pointX
)
<=
seuil
)
{
if
(
(
pointY
>=
0
)
&&
(
pointY
<=
segY
)
)
return
1
;
if
(
(
pointY
<
0
)
&&
(
pointY
>=
-
seuil
)
)
{
if
(
(
(
pointY
*
pointY
)
+
(
pointX
*
pointX
)
)
<=
(
seuil
*
seuil
)
)
return
1
;
}
if
(
(
pointY
>
segY
)
&&
(
pointY
<=
(
segY
+
seuil
)
)
)
{
if
(
(
(
(
pointY
-
segY
)
*
(
pointY
-
segY
)
)
+
(
pointX
*
pointX
)
)
<=
(
seuil
*
seuil
)
)
return
1
;
}
}
}
else
if
(
segX
==
segY
)
/* 45 degree track. */
{
/* You spin axes of 45 degrees. mouse was then
* coord: x1 = x * y * cos45 + sin45
* y1 = y * cos45 - sin45 x *
* And the segment of track is horizontal.
* coord recalculation of the mouse (sin45 = cos45 = .707 = 7 / 10
* Note: sin or cos45 = .707, and when recalculating coord
* dX45 and dy45, lect coeff .707 is neglected, dx and dy are both
* actually .707
* too big. (security hole too small)
* spot_cX *, Y * must be by .707 * .707 = 0.5
*/
cXrot
=
(
pointX
+
pointY
)
>>
1
;
cYrot
=
(
pointY
-
pointX
)
>>
1
;
/* Recalculate coordinates of extremity segment, which will be vertical
* following the orientation of axes on the screen: DX45 = pointx
* (or pointy) and 1.414 is actually greater, and dy45 = 0
*
* Threshold should be .707 to reflect the difference in coeff dx, dy
*/
seuil
*=
7
;
seuil
/=
10
;
if
(
abs
(
cYrot
)
<=
seuil
)
{
if
(
(
cXrot
>=
0
)
&&
(
cXrot
<=
segX
)
)
return
1
;
if
(
(
cXrot
<
0
)
&&
(
cXrot
>=
-
seuil
)
)
{
if
(
(
(
cXrot
*
cXrot
)
+
(
cYrot
*
cYrot
)
)
<=
(
seuil
*
seuil
)
)
return
1
;
}
if
(
(
cXrot
>
segX
)
&&
(
cXrot
<=
(
segX
+
seuil
)
)
)
{
if
(
(
(
(
cXrot
-
segX
)
*
(
cXrot
-
segX
)
)
+
(
cYrot
*
cYrot
)
)
<=
(
seuil
*
seuil
)
)
return
1
;
}
}
}
else
/* Any orientation. */
{
/* There is a change of axis (rotation), so that the segment
* track is horizontal in the new reference, */
int
angle
;
angle
=
(
int
)
(
atan2
(
(
double
)
segY
,
(
double
)
segX
)
*
1800
/
M_PI
);
cXrot
=
pointX
;
cYrot
=
pointY
;
RotatePoint
(
&
cXrot
,
&
cYrot
,
angle
);
/* Rotate test point. */
RotatePoint
(
&
segX
,
&
segY
,
angle
);
/* Rotate segment. */
/* The track is horizontal, following the changes to coordinate
* axis and, therefore segX = length of segment
*/
if
(
abs
(
cYrot
)
<=
seuil
)
{
if
(
(
cXrot
>=
0
)
&&
(
cXrot
<=
segX
)
)
return
1
;
if
(
(
cXrot
<
0
)
&&
(
cXrot
>=
-
seuil
)
)
{
if
(
(
(
cXrot
*
cXrot
)
+
(
cYrot
*
cYrot
)
)
<=
(
seuil
*
seuil
)
)
return
1
;
}
if
(
(
cXrot
>
segX
)
&&
(
cXrot
<=
(
segX
+
seuil
)
)
)
{
if
(
(
(
(
cXrot
-
segX
)
*
(
cXrot
-
segX
)
)
+
(
cYrot
*
cYrot
)
)
<=
(
seuil
*
seuil
)
)
return
1
;
}
}
}
return
0
;
}
gerbview/onrightclick.cpp
View file @
b992af3e
...
...
@@ -47,17 +47,11 @@ bool WinEDA_GerberFrame::OnRightClick( const wxPoint& MousePos,
{
if
(
BlockActive
)
{
PopMenu
->
Append
(
ID_POPUP_CANCEL_CURRENT_COMMAND
,
_
(
"Cancel Block"
)
);
PopMenu
->
Append
(
ID_POPUP_ZOOM_BLOCK
,
_
(
"Zoom Block (drag middle mouse)"
)
);
PopMenu
->
Append
(
ID_POPUP_CANCEL_CURRENT_COMMAND
,
_
(
"Cancel Block"
)
);
PopMenu
->
AppendSeparator
();
PopMenu
->
Append
(
ID_POPUP_PLACE_BLOCK
,
_
(
"Place Block"
)
);
PopMenu
->
Append
(
ID_POPUP_COPY_BLOCK
,
_
(
"Copy Block (shift mouse)"
)
);
PopMenu
->
Append
(
ID_POPUP_DELETE_BLOCK
,
_
(
"Delete Block (ctrl + drag mouse)"
)
);
PopMenu
->
Append
(
ID_POPUP_MIRROR_X_BLOCK
,
_
(
"Mirror Block"
)
);
}
else
PopMenu
->
Append
(
ID_POPUP_CANCEL_CURRENT_COMMAND
,
...
...
@@ -77,19 +71,6 @@ bool WinEDA_GerberFrame::OnRightClick( const wxPoint& MousePos,
GetScreen
()
->
SetCurItem
(
DrawStruct
);
switch
(
DrawStruct
->
Type
()
)
{
case
TYPE_TRACK
:
break
;
default
:
msg
.
Printf
(
wxT
(
"WinEDA_GerberFrame::OnRightClick Error: illegal or unknown DrawType %d"
),
DrawStruct
->
Type
()
);
DisplayError
(
this
,
msg
);
break
;
}
PopMenu
->
AppendSeparator
();
return
true
;
}
gerbview/options.cpp
View file @
b992af3e
...
...
@@ -66,7 +66,7 @@ void WinEDA_GerberFrame::OnSelectOptionToolbar( wxCommandEvent& event )
DrawPanel
->
Refresh
(
TRUE
);
break
;
case
ID_TB_OPTIONS_SHOW_
PAD
S_SKETCH
:
case
ID_TB_OPTIONS_SHOW_
FLASHED_ITEM
S_SKETCH
:
if
(
state
)
{
DisplayOpt
.
DisplayPadFill
=
m_DisplayPadFill
=
false
;
...
...
@@ -78,19 +78,7 @@ void WinEDA_GerberFrame::OnSelectOptionToolbar( wxCommandEvent& event )
DrawPanel
->
Refresh
(
TRUE
);
break
;
case
ID_TB_OPTIONS_SHOW_VIAS_SKETCH
:
if
(
state
)
{
DisplayOpt
.
DisplayViaFill
=
m_DisplayViaFill
=
false
;
}
else
{
DisplayOpt
.
DisplayViaFill
=
m_DisplayViaFill
=
true
;
}
DrawPanel
->
Refresh
(
TRUE
);
break
;
case
ID_TB_OPTIONS_SHOW_TRACKS_SKETCH
:
case
ID_TB_OPTIONS_SHOW_LINES_SKETCH
:
if
(
state
)
{
m_DisplayPcbTrackFill
=
FALSE
;
...
...
gerbview/protos.h
View file @
b992af3e
/* declarations prototype */
int
*
InstallDialogLayerPairChoice
(
WinEDA_GerberFrame
*
parent
);
bool
Read_Config
();
void
Print_PcbItems
(
BOARD
*
Pcb
,
wxDC
*
DC
,
int
drawmode
,
int
printmasklayer
);
void
DisplayColorSetupFrame
(
WinEDA_GerberFrame
*
parent
,
const
wxPoint
&
framepos
);
void
Trace_Segment
(
BOARD
*
aBrd
,
WinEDA_DrawPanel
*
panel
,
wxDC
*
DC
,
TRACK
*
pt_piste
,
int
draw_mode
);
gerbview/readgerb.cpp
View file @
b992af3e
...
...
@@ -49,7 +49,6 @@
*
* Tools and D_CODES
* Tool number (identification of shapes)
* 1 to 99 (Classical)
* 1 to 999
* D_CODES:
*
...
...
@@ -60,8 +59,7 @@
* D09 = VAPE Flash
* D51 = G54 preceded by -> Select VAPE
*
* D10 ... D255 = Identification Tool (Opening)
* Not in order (see table in PCBPLOT.H)
* D10 ... D999 = Identification Tool (shapes id)
*/
...
...
@@ -83,14 +81,6 @@
* -1 = File not found
* -2 = Error reading file
* Rank D_code max lu (nbr of dCode)
*
* Internal Representation:
*
* Lines are represented as standard TRACKS
* The flash is represented as DRAWSEGMENTS
* - Round or oval: DRAWSEGMENTS
* - Rectangles DRAWSEGMENTS
* Reference to the D-CODE is set in the member Getnet()
*/
...
...
gerbview/rs274d.cpp
View file @
b992af3e
...
...
@@ -4,6 +4,7 @@
#include "fctsys.h"
#include "polygons_defs.h"
#include "common.h"
#include "confirm.h"
#include "macros.h"
...
...
@@ -11,6 +12,7 @@
#include "pcbplot.h"
#include "trigo.h"
#include "protos.h"
#include "class_gerber_draw_item.h"
#include <math.h>
...
...
@@ -79,18 +81,18 @@ static wxPoint LastPosition;
/* Local Functions (are lower case since they are private to this source file)
**/
**/
/**
* Function fillCircular
TRACK
* initializes a given
TRACK
so that it can draw a circle which is not filled
* Function fillCircular
GBRITEM
* initializes a given
GBRITEM
so that it can draw a circle which is not filled
* and
* has a given pen width (\a aPenWidth ).
*
* @param a
Track The TRACK
to fill in.
* @param a
GbrItem The GBRITEM
to fill in.
* @param Dcode_index The DCODE value, like D14
* @param aLayer The layer index to set into the
TRACK
* @param aLayer The layer index to set into the
GBRITEM
* @param aPos The center point of the flash
* @param aDiameter The diameter of the round flash
* @param aPenWidth The width of the pen used to draw the circle's
...
...
@@ -99,7 +101,7 @@ static wxPoint LastPosition;
* color other than the background color, else use the background color
* when drawing so that an erasure happens.
*/
static
void
fillCircular
TRACK
(
TRACK
*
aTrack
,
static
void
fillCircular
GBRITEM
(
GERBER_DRAW_ITEM
*
aGbrItem
,
int
Dcode_index
,
int
aLayer
,
const
wxPoint
&
aPos
,
...
...
@@ -107,79 +109,80 @@ static void fillCircularTRACK( TRACK* aTrack,
int
aPenWidth
,
bool
isDark
)
{
a
Track
->
m_Shape
=
S
_CIRCLE
;
a
Track
->
m_Width
=
aPenWidth
;
a
GbrItem
->
m_Shape
=
GBR
_CIRCLE
;
a
GbrItem
->
m_Size
.
x
=
aGbrItem
->
m_Size
.
y
=
aPenWidth
;
a
Track
->
SetLayer
(
aLayer
);
a
Track
->
SetNet
(
Dcode_index
)
;
a
GbrItem
->
SetLayer
(
aLayer
);
a
GbrItem
->
m_DCode
=
Dcode_index
;
// When drawing a
TRACK with shape S
_CIRCLE, the hypotenuse (i.e. distance)
// When drawing a
GBRITEM with shape GBR
_CIRCLE, the hypotenuse (i.e. distance)
// between the Start and End points gives the radius of the circle.
a
Track
->
m_Start
=
aTrack
->
m_End
=
aPos
;
a
Track
->
m_End
.
x
+=
max
(
0
,
(
aDiameter
+
1
)
/
2
);
a
GbrItem
->
m_Start
=
aGbrItem
->
m_End
=
aPos
;
a
GbrItem
->
m_End
.
x
+=
max
(
0
,
(
aDiameter
+
1
)
/
2
);
NEGATE
(
a
Track
->
m_Start
.
y
);
NEGATE
(
a
Track
->
m_End
.
y
);
NEGATE
(
a
GbrItem
->
m_Start
.
y
);
NEGATE
(
a
GbrItem
->
m_End
.
y
);
if
(
!
isDark
)
{
a
Track
->
m_Flags
|=
DRAW_ERASED
;
a
GbrItem
->
m_Flags
|=
DRAW_ERASED
;
}
}
/**
* Function fillRoundFlash
TRACK
* initializes a given
TRACK
so that it can draw a circle which is filled and
* Function fillRoundFlash
GBRITEM
* initializes a given
GBRITEM
so that it can draw a circle which is filled and
* has no pen border.
*
* @param a
Track The TRACK
to fill in.
* @param a
GbrItem The GBRITEM
to fill in.
* @param Dcode_index The DCODE value, like D14
* @param aLayer The layer index to set into the
TRACK
* @param aLayer The layer index to set into the
GBRITEM
* @param aPos The center point of the flash
* @param aDiameter The diameter of the round flash
* @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.
*/
static
void
fillRoundFlash
TRACK
(
TRACK
*
aTrack
,
static
void
fillRoundFlash
GBRITEM
(
GERBER_DRAW_ITEM
*
aGbrItem
,
int
Dcode_index
,
int
aLayer
,
const
wxPoint
&
aPos
,
int
aDiameter
,
bool
isDark
)
{
aTrack
->
SetLayer
(
aLayer
);
aTrack
->
m_Width
=
aDiameter
;
aTrack
->
m_Start
=
aTrack
->
m_End
=
aPos
;
NEGATE
(
aTrack
->
m_Start
.
y
);
NEGATE
(
aTrack
->
m_End
.
y
);
aTrack
->
SetNet
(
Dcode_index
);
aTrack
->
m_Shape
=
S_SPOT_CIRCLE
;
aGbrItem
->
SetLayer
(
aLayer
);
aGbrItem
->
m_Size
.
x
=
aGbrItem
->
m_Size
.
y
=
aDiameter
;
aGbrItem
->
m_Start
=
aPos
;
NEGATE
(
aGbrItem
->
m_Start
.
y
);
aGbrItem
->
m_End
=
aGbrItem
->
m_Start
;
aGbrItem
->
m_DCode
=
Dcode_index
;
aGbrItem
->
m_Shape
=
GBR_SPOT_CIRCLE
;
aGbrItem
->
m_Flashed
=
true
;
if
(
!
isDark
)
{
a
Track
->
m_Flags
|=
DRAW_ERASED
;
a
GbrItem
->
m_Flags
|=
DRAW_ERASED
;
}
}
/**
* Function fillOvalOrRectFlash
TRACK
* initializes a given
TRACK
so that it can draw an oval or rectangular
* Function fillOvalOrRectFlash
GBRITEM
* initializes a given
GBRITEM
so that it can draw an oval or rectangular
* filled rectangle.
*
* @param a
Track The TRACK
to fill in.
* @param a
GbrItem The GERBER_DRAW_ITEM
to fill in.
* @param Dcode_index The DCODE value, like D14
* @param aLayer The layer index to set into the
TRACK
* @param aLayer The layer index to set into the
GBRITEM
* @param aPos The center point of the rectangle
* @param aSize The size of the flash
* @param aShape What type of flash,
S_SPOT_OVALE or S
_SPOT_RECT
* @param aShape What type of flash,
GBR_SPOT_OVALE or GBR
_SPOT_RECT
* @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.
*/
static
void
fillOvalOrRectFlash
TRACK
(
TRACK
*
aTrack
,
static
void
fillOvalOrRectFlash
GBRITEM
(
GERBER_DRAW_ITEM
*
aGbrItem
,
int
Dcode_index
,
int
aLayer
,
const
wxPoint
&
aPos
,
...
...
@@ -187,54 +190,39 @@ static void fillOvalOrRectFlashTRACK( TRACK* aTrack,
int
aShape
,
bool
isDark
)
{
int
width
=
MIN
(
aSize
.
x
,
aSize
.
y
);
int
len
=
MAX
(
aSize
.
x
,
aSize
.
y
)
-
width
;
aGbrItem
->
SetLayer
(
aLayer
);
aGbrItem
->
m_Flashed
=
true
;
a
Track
->
SetLayer
(
aLayer
)
;
a
GbrItem
->
m_Size
=
aSize
;
aTrack
->
m_Width
=
width
;
aGbrItem
->
m_Start
=
aPos
;
NEGATE
(
aGbrItem
->
m_Start
.
y
);
aGbrItem
->
m_End
=
aGbrItem
->
m_Start
;
aTrack
->
m_Start
=
aTrack
->
m_End
=
aPos
;
NEGATE
(
aTrack
->
m_Start
.
y
);
NEGATE
(
aTrack
->
m_End
.
y
);
aTrack
->
SetNet
(
Dcode_index
);
aTrack
->
m_Shape
=
aShape
;
len
>>=
1
;
if
(
aSize
.
x
>
aSize
.
y
)
// oval or rectangle is horizontal
{
aTrack
->
m_Start
.
x
-=
len
;
aTrack
->
m_End
.
x
+=
len
;
}
else
// oval or rectangle is vertical
{
aTrack
->
m_Start
.
y
-=
len
;
aTrack
->
m_End
.
y
+=
len
;
}
aGbrItem
->
m_DCode
=
Dcode_index
;
aGbrItem
->
m_Shape
=
aShape
;
if
(
!
isDark
)
{
a
Track
->
m_Flags
|=
DRAW_ERASED
;
a
GbrItem
->
m_Flags
|=
DRAW_ERASED
;
}
}
/**
* Function fillLine
TRACK
* initializes a given
TRACK
so that it can draw a linear D code.
* Function fillLine
GBRITEM
* initializes a given
GBRITEM
so that it can draw a linear D code.
*
* @param a
Track The TRACK
to fill in.
* @param a
GbrItem The GERBER_DRAW_ITEM
to fill in.
* @param Dcode_index The DCODE value, like D14
* @param aLayer The layer index to set into the
TRACK
* @param aLayer The layer index to set into the
GBRITEM
* @param aPos The center point of the flash
* @param aDiameter The diameter of the round flash
* @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.
*/
static
void
fillLine
TRACK
(
TRACK
*
aTrack
,
static
void
fillLine
GBRITEM
(
GERBER_DRAW_ITEM
*
aGbrItem
,
int
Dcode_index
,
int
aLayer
,
const
wxPoint
&
aStart
,
...
...
@@ -242,28 +230,29 @@ static void fillLineTRACK( TRACK* aTrack,
int
aWidth
,
bool
isDark
)
{
aTrack
->
SetLayer
(
aLayer
);
aGbrItem
->
SetLayer
(
aLayer
);
aGbrItem
->
m_Flashed
=
false
;
a
Track
->
m_Width
=
aWidth
;
a
GbrItem
->
m_Size
.
x
=
aGbrItem
->
m_Size
.
y
=
aWidth
;
a
Track
->
m_Start
=
aStart
;
NEGATE
(
a
Track
->
m_Start
.
y
);
a
GbrItem
->
m_Start
=
aStart
;
NEGATE
(
a
GbrItem
->
m_Start
.
y
);
a
Track
->
m_End
=
aEnd
;
NEGATE
(
a
Track
->
m_End
.
y
);
a
GbrItem
->
m_End
=
aEnd
;
NEGATE
(
a
GbrItem
->
m_End
.
y
);
a
Track
->
SetNet
(
Dcode_index
)
;
a
GbrItem
->
m_DCode
=
Dcode_index
;
if
(
!
isDark
)
{
a
Track
->
m_Flags
|=
DRAW_ERASED
;
a
GbrItem
->
m_Flags
|=
DRAW_ERASED
;
}
}
/**
* Function fillArc
TRACK
* initializes a given
TRACK
so that it can draw an arc G code.
* Function fillArc
GBRITEM
* initializes a given
GBRITEM
so that it can draw an arc G code.
* <p>
* if multiquadrant == true : arc can be 0 to 360 degrees
* and \a rel_center is the center coordinate relative to start point.
...
...
@@ -276,9 +265,9 @@ static void fillLineTRACK( TRACK* aTrack,
* <li> absolute angle 180 to 270 (quadrant 3) or
* <li> absolute angle 270 to 0 (quadrant 4)
* </ul><p>
* @param
aTrack is the TRACK
to fill in.
* @param
GERBER_DRAW_ITEM is the GBRITEM
to fill in.
* @param Dcode_index is the DCODE value, like D14
* @param aLayer is the layer index to set into the
TRACK
* @param aLayer is the layer index to set into the
GBRITEM
* @param aStart is the starting point
* @param aEnd is the ending point
* @param rel_center is the center coordinate relative to start point,
...
...
@@ -291,16 +280,17 @@ static void fillLineTRACK( TRACK* aTrack,
* color other than the background color, else use the background color
* when drawing so that an erasure happens.
*/
static
void
fillArc
TRACK
(
TRACK
*
aTrack
,
int
Dcode_index
,
int
aLayer
,
static
void
fillArc
GBRITEM
(
GERBER_DRAW_ITEM
*
aGbrItem
,
int
Dcode_index
,
int
aLayer
,
const
wxPoint
&
aStart
,
const
wxPoint
&
aEnd
,
const
wxPoint
&
rel_center
,
int
aWidth
,
bool
clockwise
,
bool
multiquadrant
,
bool
isDark
)
{
wxPoint
center
,
delta
;
aTrack
->
m_Shape
=
S_ARC
;
aTrack
->
SetLayer
(
aLayer
);
aTrack
->
m_Width
=
aWidth
;
aGbrItem
->
m_Shape
=
GBR_ARC
;
aGbrItem
->
SetLayer
(
aLayer
);
aGbrItem
->
m_Size
.
x
=
aGbrItem
->
m_Size
.
y
=
aWidth
;
aGbrItem
->
m_Flashed
=
false
;
if
(
multiquadrant
)
{
...
...
@@ -309,20 +299,19 @@ static void fillArcTRACK( TRACK* aTrack, int Dcode_index, int aLayer,
if
(
clockwise
)
{
a
Track
->
m_Start
=
aStart
;
a
Track
->
m_End
=
aEnd
;
a
GbrItem
->
m_Start
=
aStart
;
a
GbrItem
->
m_End
=
aEnd
;
}
else
{
a
Track
->
m_Start
=
aEnd
;
a
Track
->
m_End
=
aStart
;
a
GbrItem
->
m_Start
=
aEnd
;
a
GbrItem
->
m_End
=
aStart
;
}
}
else
{
center
=
rel_center
;
delta
.
x
=
aEnd
.
x
-
aStart
.
x
;
delta
.
y
=
aEnd
.
y
-
aStart
.
y
;
delta
=
aEnd
-
aStart
;
if
(
(
delta
.
x
>=
0
)
&&
(
delta
.
y
>=
0
)
)
{
...
...
@@ -350,28 +339,26 @@ static void fillArcTRACK( TRACK* aTrack, int Dcode_index, int aLayer,
if
(
clockwise
)
{
a
Track
->
m_Start
=
aStart
;
a
Track
->
m_End
=
aEnd
;
a
GbrItem
->
m_Start
=
aStart
;
a
GbrItem
->
m_End
=
aEnd
;
}
else
{
a
Track
->
m_Start
=
aEnd
;
a
Track
->
m_End
=
aStart
;
a
GbrItem
->
m_Start
=
aEnd
;
a
GbrItem
->
m_End
=
aStart
;
}
}
aTrack
->
SetNet
(
Dcode_index
);
aTrack
->
m_Param
=
center
.
x
;
aTrack
->
SetSubNet
(
center
.
y
);
NEGATE
(
aTrack
->
m_Start
.
y
);
NEGATE
(
aTrack
->
m_End
.
y
);
aGbrItem
->
m_DCode
=
Dcode_index
;
aGbrItem
->
m_ArcCentre
=
center
;
aTrack
->
SetSubNet
(
-
aTrack
->
GetSubNet
()
);
NEGATE
(
aGbrItem
->
m_Start
.
y
);
NEGATE
(
aGbrItem
->
m_End
.
y
);
NEGATE
(
aGbrItem
->
m_ArcCentre
.
y
);
if
(
!
isDark
)
{
a
Track
->
m_Flags
|=
DRAW_ERASED
;
a
GbrItem
->
m_Flags
|=
DRAW_ERASED
;
}
}
...
...
@@ -392,7 +379,7 @@ static void fillArcTRACK( TRACK* aTrack, int Dcode_index, int aLayer,
* <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 aLayer is the layer index to set into the
GBRITEM
* @param aStart is the starting point
* @param aEnd is the ending point
* @param rel_center is the center coordinate relative to start point,
...
...
@@ -404,44 +391,38 @@ static void fillArcTRACK( TRACK* aTrack, int Dcode_index, int aLayer,
* @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
,
static
void
fillArcPOLY
(
BOARD
*
aPcb
,
GERBER_DRAW_ITEM
*
aGrbrItem
,
const
wxPoint
&
aStart
,
const
wxPoint
&
aEnd
,
const
wxPoint
&
rel_center
,
bool
clockwise
,
bool
multiquadrant
,
bool
isDark
)
{
/* in order to calculate arc parameters, we use fillArc
TRACK
* so we muse create a dummy track and use its geometric parmeters
/* in order to calculate arc parameters, we use fillArc
GBRITEM
* so we muse create a dummy track and use its geometric par
a
meters
*/
static
TRACK
dummyTrack
(
NULL
);
SEGZONE
*
firstSegment
=
NULL
;
static
GERBER_DRAW_ITEM
dummyGbrItem
(
NULL
);
fillArcTRACK
(
&
dummyTrack
,
0
,
aLayer
,
aStart
,
aEnd
,
rel_center
,
0
,
fillArcGBRITEM
(
&
dummyGbrItem
,
0
,
0
,
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
;
const
int
increment_angle
=
360
/
36
;
wxPoint
center
;
center
.
x
=
dummyTrack
.
m_Param
;
center
.
y
=
dummyTrack
.
GetSubNet
();
center
=
dummyGbrItem
.
m_ArcCentre
;
// Calculate relative coordinates;
wxPoint
start
=
dummy
Track
.
m_Start
-
center
;
wxPoint
end
=
dummyTrack
.
m_End
-
center
;
wxPoint
start
=
dummy
GbrItem
.
m_Start
-
center
;
wxPoint
end
=
dummyGbrItem
.
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
);
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
);
double
end_angle
=
atan2
(
(
double
)
end
.
y
,
(
double
)
end
.
x
);
end_angle
=
180
*
end_angle
/
M_PI
;
double
angle
=
start_angle
-
end_angle
;
...
...
@@ -449,19 +430,21 @@ static SEGZONE * fillArcPOLY( BOARD * aPcb, int aLayer,
// start.x, start.y, start_angle, end.x, end.y, end_angle, angle ) );
if
(
!
clockwise
)
{
EXCHG
(
start
,
end
);
D
(
printf
(
" >>>> reverse arc
\n
"
)
);
EXCHG
(
start
,
end
);
D
(
printf
(
" >>>> reverse arc
\n
"
)
);
}
// Normalize angle
while
(
angle
>
360.0
)
while
(
angle
>
360.0
)
angle
-=
360.0
;
while
(
angle
<
0.0
)
while
(
angle
<
0.0
)
angle
+=
360.0
;
int
count
=
(
int
)
(
angle
/
increment_angle
);
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
...
...
@@ -473,43 +456,29 @@ static SEGZONE * fillArcPOLY( BOARD * aPcb, int aLayer,
if
(
ii
<
count
)
{
if
(
clockwise
)
RotatePoint
(
&
end_arc
,
rot
);
RotatePoint
(
&
end_arc
,
rot
);
else
RotatePoint
(
&
end_arc
,
-
rot
);
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
;
if
(
aGrbrItem
->
m_PolyCorners
.
size
()
==
0
)
aGrbrItem
->
m_PolyCorners
.
push_back
(
start_arc
+
center
);
aGrbrItem
->
m_PolyCorners
.
push_back
(
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
;
aGrbrItem
->
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
*/
...
...
@@ -574,48 +543,14 @@ wxPoint GERBER::ReadXYCoord( char*& Text )
}
current_coord
=
atoi
(
line
);
double
real_scale
=
1.0
;
switch
(
fmt_scale
)
{
case
0
:
real_scale
=
10000.0
;
break
;
case
1
:
real_scale
=
1000.0
;
break
;
case
2
:
real_scale
=
100.0
;
break
;
case
3
:
real_scale
=
10.0
;
break
;
case
4
:
break
;
case
5
:
real_scale
=
0.1
;
break
;
case
6
:
real_scale
=
0.01
;
break
;
case
7
:
real_scale
=
0.001
;
break
;
case
8
:
real_scale
=
0.0001
;
break
;
case
9
:
real_scale
=
0.00001
;
break
;
}
if
(
fmt_scale
<
0
||
fmt_scale
>
9
)
fmt_scale
=
4
;
double
scale_list
[
10
]
=
{
10000.0
,
1000.0
,
100.0
,
10.0
,
1
,
0.1
,
0.01
,
0.001
,
0.0001
,
0.00001
};
real_scale
=
scale_list
[
fmt_scale
];
if
(
m_GerbMetric
)
real_scale
=
real_scale
/
25.4
;
...
...
@@ -855,8 +790,8 @@ bool GERBER::Execute_G_Command( char*& text, int G_commande )
int
D_commande
=
ReturnDCodeNumber
(
text
);
if
(
D_commande
<
FIRST_DCODE
)
return
false
;
if
(
D_commande
>
(
MAX_TOOLS
-
1
)
)
D_commande
=
MAX_TOOLS
-
1
;
if
(
D_commande
>
(
TOOLS_MAX_COUNT
-
1
)
)
D_commande
=
TOOLS_MAX_COUNT
-
1
;
m_Current_Tool
=
D_commande
;
D_CODE
*
pt_Dcode
=
GetDCODE
(
D_commande
,
false
);
if
(
pt_Dcode
)
...
...
@@ -988,7 +923,7 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
wxSize
size
(
15
,
15
);
APERTURE_T
aperture
=
APT_CIRCLE
;
TRACK
*
track
;
GERBER_DRAW_ITEM
*
gbritem
;
BOARD
*
pcb
=
frame
->
GetBoard
();
int
activeLayer
=
frame
->
GetScreen
()
->
m_Active_Layer
;
...
...
@@ -1001,8 +936,8 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
if
(
D_commande
>=
FIRST_DCODE
)
// This is a "Set tool" command
{
if
(
D_commande
>
(
MAX_TOOLS
-
1
)
)
D_commande
=
MAX_TOOLS
-
1
;
if
(
D_commande
>
(
TOOLS_MAX_COUNT
-
1
)
)
D_commande
=
TOOLS_MAX_COUNT
-
1
;
// remember which tool is selected, nothing is done with it in this
// call
...
...
@@ -1021,44 +956,48 @@ 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
if
(
!
m_Exposure
)
{
m_Exposure
=
true
;
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
gbritem
->
m_Shape
=
GBR_POLYGON
;
gbritem
->
SetLayer
(
activeLayer
);
gbritem
->
m_Flashed
=
false
;
}
switch
(
m_Iterpolation
)
{
case
GERB_INTERPOL_ARC_NEG
:
case
GERB_INTERPOL_ARC_POS
:
gbritem
=
(
GERBER_DRAW_ITEM
*
)(
pcb
->
m_Drawings
.
GetLast
()
);
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
,
fillArcPOLY
(
pcb
,
gbritem
,
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
);
gbritem
=
(
GERBER_DRAW_ITEM
*
)(
pcb
->
m_Drawings
.
GetLast
()
);
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
;
gbritem
->
m_Start
=
m_PreviousPos
;
// m_Start is used as temporary storage
NEGATE
(
gbritem
->
m_Start
.
y
);
if
(
gbritem
->
m_PolyCorners
.
size
()
==
0
)
gbritem
->
m_PolyCorners
.
push_back
(
gbritem
->
m_Start
);
edge_poly
->
m_Start
=
m_PreviousPos
;
NEGATE
(
edge_poly
->
m_Start
.
y
);
edge_poly
->
m_End
=
m_CurrentPos
;
NEGATE
(
edge_poly
->
m_End
.
y
);
edge_poly
->
SetNet
(
m_PolygonFillModeState
);
gbritem
->
m_End
=
m_CurrentPos
;
// m_End is used as temporary storage
NEGATE
(
gbritem
->
m_End
.
y
);
gbritem
->
m_PolyCorners
.
push_back
(
gbritem
->
m_End
);
// the first track of each polygon has a netcode of zero,
// otherwise one. Set the erasure flag in that special track,
...
...
@@ -1066,7 +1005,7 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
if
(
!
m_PolygonFillModeState
)
{
if
(
m_LayerNegative
^
m_ImageNegative
)
edge_poly
->
m_Flags
|=
DRAW_ERASED
;
gbritem
->
m_Flags
|=
DRAW_ERASED
;
D
(
printf
(
"
\n
m_Flags=0x%08X
\n
"
,
edge_poly
->
m_Flags
);
)
}
break
;
...
...
@@ -1104,10 +1043,10 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
switch
(
m_Iterpolation
)
{
case
GERB_INTERPOL_LINEAR_1X
:
track
=
new
TRACK
(
pcb
);
pcb
->
m_
Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillLine
TRACK
(
track
,
dcode
,
activeLayer
,
m_PreviousPos
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_
Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillLine
GBRITEM
(
gbritem
,
dcode
,
activeLayer
,
m_PreviousPos
,
m_CurrentPos
,
size
.
x
,
!
(
m_LayerNegative
^
m_ImageNegative
)
);
break
;
...
...
@@ -1120,10 +1059,10 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
case
GERB_INTERPOL_ARC_NEG
:
case
GERB_INTERPOL_ARC_POS
:
track
=
new
TRACK
(
pcb
);
pcb
->
m_
Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillArc
TRACK
(
track
,
dcode
,
activeLayer
,
m_PreviousPos
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_
Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillArc
GBRITEM
(
gbritem
,
dcode
,
activeLayer
,
m_PreviousPos
,
m_CurrentPos
,
m_IJPos
,
size
.
x
,
(
m_Iterpolation
==
GERB_INTERPOL_ARC_NEG
)
?
false
:
true
,
m_360Arc_enbl
,
...
...
@@ -1156,26 +1095,24 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
switch
(
aperture
)
{
case
APT_LINE
:
// APT_LINE is not in the spec, don't know why it's
// here
case
APT_CIRCLE
:
track
=
new
TRACK
(
pcb
);
pcb
->
m_
Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillRoundFlash
TRACK
(
track
,
dcode
,
activeLayer
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_
Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillRoundFlash
GBRITEM
(
gbritem
,
dcode
,
activeLayer
,
m_CurrentPos
,
size
.
x
,
!
(
m_LayerNegative
^
m_ImageNegative
)
);
break
;
case
APT_OVAL
:
case
APT_RECT
:
track
=
new
TRACK
(
pcb
);
pcb
->
m_
Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillOvalOrRectFlash
TRACK
(
track
,
dcode
,
activeLayer
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_
Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillOvalOrRectFlash
GBRITEM
(
gbritem
,
dcode
,
activeLayer
,
m_CurrentPos
,
size
,
(
aperture
==
APT_RECT
)
?
S_SPOT_RECT
:
S_SPOT_OVALE
,
GBR_SPOT_RECT
:
GBR_SPOT_OVAL
,
!
(
m_LayerNegative
^
m_ImageNegative
)
);
break
;
...
...
@@ -1184,7 +1121,7 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
APERTURE_MACRO
*
macro
=
tool
->
GetMacro
();
wxASSERT
(
macro
);
// split the macro primitives up into multiple normal TRACK
// split the macro primitives up into multiple normal GBRITEM
// elements
for
(
AM_PRIMITIVES
::
iterator
p
=
macro
->
primitives
.
begin
();
p
!=
macro
->
primitives
.
end
();
...
...
@@ -1205,10 +1142,10 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
int
diameter
=
scale
(
p
->
params
[
1
].
GetValue
(
tool
),
m_GerbMetric
);
track
=
new
TRACK
(
pcb
);
pcb
->
m_Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillRoundFlashTRACK
(
track
,
dcode
,
activeLayer
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillRoundFlashGBRITEM
(
gbritem
,
dcode
,
activeLayer
,
curPos
,
diameter
,
exposure
);
}
break
;
...
...
@@ -1241,11 +1178,11 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
wxPoint
midPoint
(
(
start
.
x
+
end
.
x
)
/
2
,
(
start
.
y
+
end
.
y
)
/
2
);
curPos
+=
midPoint
;
track
=
new
TRACK
(
pcb
);
pcb
->
m_Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillOvalOrRectFlashTRACK
(
track
,
dcode
,
activeLayer
,
curPos
,
size
,
S
_SPOT_RECT
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillOvalOrRectFlashGBRITEM
(
gbritem
,
dcode
,
activeLayer
,
curPos
,
size
,
GBR
_SPOT_RECT
,
exposure
);
}
break
;
...
...
@@ -1262,11 +1199,11 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
curPos
+=
mapPt
(
p
->
params
[
3
].
GetValue
(
tool
),
p
->
params
[
4
].
GetValue
(
tool
),
m_GerbMetric
);
track
=
new
TRACK
(
pcb
);
pcb
->
m_Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillOvalOrRectFlashTRACK
(
track
,
dcode
,
activeLayer
,
curPos
,
size
,
S
_SPOT_RECT
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillOvalOrRectFlashGBRITEM
(
gbritem
,
dcode
,
activeLayer
,
curPos
,
size
,
GBR
_SPOT_RECT
,
exposure
);
}
break
;
...
...
@@ -1288,11 +1225,11 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
// need the middle, so adjust from the lower left
curPos
.
y
+=
size
.
y
/
2
;
curPos
.
x
+=
size
.
x
/
2
;
track
=
new
TRACK
(
pcb
);
pcb
->
m_Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillOvalOrRectFlashTRACK
(
track
,
dcode
,
activeLayer
,
curPos
,
size
,
S
_SPOT_RECT
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillOvalOrRectFlashGBRITEM
(
gbritem
,
dcode
,
activeLayer
,
curPos
,
size
,
GBR
_SPOT_RECT
,
exposure
);
}
break
;
...
...
@@ -1308,17 +1245,17 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
p
->
params
[
1
].
GetValue
(
tool
),
m_GerbMetric
);
track
=
new
TRACK
(
pcb
);
pcb
->
m_Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillRoundFlashTRACK
(
track
,
dcode
,
activeLayer
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillRoundFlashGBRITEM
(
gbritem
,
dcode
,
activeLayer
,
curPos
,
outerDiam
,
!
(
m_LayerNegative
^
m_ImageNegative
)
);
track
=
new
TRACK
(
pcb
);
pcb
->
m_Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillRoundFlashTRACK
(
track
,
dcode
,
activeLayer
,
curPos
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillRoundFlashGBRITEM
(
gbritem
,
dcode
,
activeLayer
,
curPos
,
innerDiam
,
(
m_LayerNegative
^
m_ImageNegative
)
);
...
...
@@ -1351,39 +1288,37 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
// ignore rotation, not supported
// adjust outerDiam by this on each nested circle
int
diamAdjust
=
2
*
(
gap
+
penThickness
);
for
(
int
i
=
0
;
i
<
numCircles
;
++
i
,
outerDiam
-=
diamAdjust
)
{
track
=
new
TRACK
(
pcb
);
pcb
->
m_Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillCircularTRACK
(
track
,
dcode
,
activeLayer
,
for
(
int
i
=
0
;
i
<
numCircles
;
++
i
,
outerDiam
-=
diamAdjust
)
{
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillCircularGBRITEM
(
gbritem
,
dcode
,
activeLayer
,
curPos
,
outerDiam
,
penThickness
,
!
(
m_LayerNegative
^
m_ImageNegative
)
);
}
track
=
new
TRACK
(
pcb
);
pcb
->
m_Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
fillOvalOrRectFlashTRACK
(
track
,
dcode
,
activeLayer
,
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
fillOvalOrRectFlashGBRITEM
(
gbritem
,
dcode
,
activeLayer
,
curPos
,
wxSize
(
crossHairThickness
,
crossHairLength
),
S
_SPOT_RECT
,
GBR
_SPOT_RECT
,
!
(
m_LayerNegative
^
m_ImageNegative
)
);
track
=
new
TRACK
(
pcb
);
pcb
->
m_Track
.
Append
(
track
);
D
(
printf
(
"R:%p
\n
"
,
track
);
)
gbritem
=
new
GERBER_DRAW_ITEM
(
pcb
);
pcb
->
m_Drawings
.
Append
(
gbritem
);
D
(
printf
(
"R:%p
\n
"
,
gbritem
);
)
// swap x and y in wxSize() for this one
fillOvalOrRectFlashTRACK
(
track
,
dcode
,
activeLayer
,
fillOvalOrRectFlashGBRITEM
(
gbritem
,
dcode
,
activeLayer
,
curPos
,
wxSize
(
crossHairLength
,
crossHairThickness
),
S
_SPOT_RECT
,
GBR
_SPOT_RECT
,
!
(
m_LayerNegative
^
m_ImageNegative
)
);
}
break
;
...
...
@@ -1398,14 +1333,15 @@ bool GERBER::Execute_DCODE_Command( WinEDA_GerberFrame* frame,
printf
(
" # points: %d
\n
"
,
numPoints
);
// numPoints does not include the starting point, so add 1.
for
(
int
i
=
0
;
i
<
numPoints
+
1
;
++
i
)
for
(
int
i
=
0
;
i
<
numPoints
+
1
;
++
i
)
{
printf
(
" [%d]: X=%g Y=%g
\n
"
,
i
,
p
->
params
[
i
*
2
+
2
+
0
].
GetValue
(
tool
),
p
->
params
[
i
*
2
+
2
+
1
].
GetValue
(
tool
)
p
->
params
[
i
*
2
+
2
+
0
].
GetValue
(
tool
),
p
->
params
[
i
*
2
+
2
+
1
].
GetValue
(
tool
)
);
}
printf
(
" rotation: %g
\n
"
,
p
->
params
[
numPoints
*
2
+
4
].
GetValue
(
tool
)
);
printf
(
" rotation: %g
\n
"
,
p
->
params
[
numPoints
*
2
+
4
].
GetValue
(
tool
)
);
}
#endif
break
;
...
...
gerbview/rs274x.cpp
View file @
b992af3e
...
...
@@ -448,7 +448,7 @@ bool GERBER::ExecuteRS274XCommand( int command,
while
(
*
text
==
' '
)
text
++
;
if
(
*
text
==
'
Y
'
)
if
(
*
text
==
'
X
'
)
{
text
++
;
dcode
->
m_Drill
.
y
=
...
...
gerbview/toolbars_gerber.cpp
View file @
b992af3e
...
...
@@ -107,10 +107,10 @@ void WinEDA_GerberFrame::ReCreateHToolbar( void )
m_HToolBar
->
AddSeparator
();
choices
.
Clear
();
choices
.
Alloc
(
MAX_TOOLS
+
1
);
choices
.
Alloc
(
TOOLS_MAX_COUNT
+
1
);
choices
.
Add
(
_
(
"No tool"
)
);
for
(
ii
=
0
;
ii
<
MAX_TOOLS
;
ii
++
)
for
(
ii
=
0
;
ii
<
TOOLS_MAX_COUNT
;
ii
++
)
{
wxString
msg
;
msg
=
_
(
"Tool "
);
msg
<<
ii
+
FIRST_DCODE
;
...
...
@@ -187,11 +187,11 @@ void WinEDA_GerberFrame::ReCreateOptToolbar( void )
_
(
"Change cursor shape"
),
wxITEM_CHECK
);
m_OptionsToolBar
->
AddSeparator
();
m_OptionsToolBar
->
AddTool
(
ID_TB_OPTIONS_SHOW_
PAD
S_SKETCH
,
wxEmptyString
,
m_OptionsToolBar
->
AddTool
(
ID_TB_OPTIONS_SHOW_
FLASHED_ITEM
S_SKETCH
,
wxEmptyString
,
wxBitmap
(
pad_sketch_xpm
),
_
(
"Show spots in sketch mode"
),
wxITEM_CHECK
);
m_OptionsToolBar
->
AddTool
(
ID_TB_OPTIONS_SHOW_
TRACK
S_SKETCH
,
wxEmptyString
,
m_OptionsToolBar
->
AddTool
(
ID_TB_OPTIONS_SHOW_
LINE
S_SKETCH
,
wxEmptyString
,
wxBitmap
(
showtrack_xpm
),
_
(
"Show lines in sketch mode"
),
wxITEM_CHECK
);
...
...
@@ -215,3 +215,103 @@ void WinEDA_GerberFrame::ReCreateOptToolbar( void )
m_OptionsToolBar
->
Realize
();
}
/** Function SetToolbars()
* Set the tools state for the toolbars, according to display options
*/
void
WinEDA_GerberFrame
::
SetToolbars
()
{
PCB_SCREEN
*
screen
=
(
PCB_SCREEN
*
)
GetScreen
();
int
layer
=
screen
->
m_Active_Layer
;
GERBER
*
gerber
=
g_GERBER_List
[
layer
];
if
(
m_HToolBar
==
NULL
)
return
;
if
(
GetScreen
()
->
m_BlockLocate
.
m_Command
==
BLOCK_MOVE
)
{
m_HToolBar
->
EnableTool
(
wxID_CUT
,
true
);
m_HToolBar
->
EnableTool
(
wxID_COPY
,
true
);
}
else
{
m_HToolBar
->
EnableTool
(
wxID_CUT
,
false
);
m_HToolBar
->
EnableTool
(
wxID_COPY
,
false
);
}
if
(
m_SelLayerBox
&&
(
m_SelLayerBox
->
GetSelection
()
!=
screen
->
m_Active_Layer
)
)
{
m_SelLayerBox
->
SetSelection
(
screen
->
m_Active_Layer
);
}
if
(
m_SelLayerTool
)
{
if
(
gerber
)
{
int
sel_index
;
m_SelLayerTool
->
Enable
(
true
);
if
(
gerber
->
m_Selected_Tool
<
FIRST_DCODE
)
// No tool selected
sel_index
=
0
;
else
sel_index
=
gerber
->
m_Selected_Tool
-
FIRST_DCODE
+
1
;
if
(
sel_index
!=
m_SelLayerTool
->
GetSelection
()
)
{
m_SelLayerTool
->
SetSelection
(
sel_index
);
}
}
else
{
m_SelLayerTool
->
SetSelection
(
0
);
m_SelLayerTool
->
Enable
(
false
);
}
}
if
(
m_OptionsToolBar
)
{
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SELECT_UNIT_MM
,
g_UserUnit
==
MILLIMETRES
?
true
:
false
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SELECT_UNIT_INCH
,
g_UserUnit
==
INCHES
?
true
:
false
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_POLAR_COORD
,
DisplayOpt
.
DisplayPolarCood
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_GRID
,
IsGridVisible
()
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SELECT_CURSOR
,
m_CursorShape
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_FLASHED_ITEMS_SKETCH
,
!
m_DisplayPadFill
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_LINES_SKETCH
,
!
m_DisplayPcbTrackFill
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_POLYGONS_SKETCH
,
g_DisplayPolygonsModeSketch
==
0
?
0
:
1
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_DCODES
,
IsElementVisible
(
DCODES_VISIBLE
)
);
m_OptionsToolBar
->
ToggleTool
(
ID_TB_OPTIONS_SHOW_LAYERS_MANAGER_VERTICAL_TOOLBAR
,
m_show_layer_manager_tools
);
if
(
m_show_layer_manager_tools
)
GetMenuBar
()
->
SetLabel
(
ID_MENU_GERBVIEW_SHOW_HIDE_LAYERS_MANAGER_DIALOG
,
_
(
"Hide &Layers Manager"
)
);
else
GetMenuBar
()
->
SetLabel
(
ID_MENU_GERBVIEW_SHOW_HIDE_LAYERS_MANAGER_DIALOG
,
_
(
"Show &Layers Manager"
)
);
}
DisplayUnitsMsg
();
if
(
m_auimgr
.
GetManagedWindow
()
)
m_auimgr
.
Update
();
}
gerbview/tracepcb.cpp
View file @
b992af3e
...
...
@@ -7,6 +7,7 @@
*/
#include "fctsys.h"
#include "polygons_defs.h"
#include "gr_basic.h"
#include "common.h"
#include "class_drawpanel.h"
...
...
@@ -17,12 +18,13 @@
#include "protos.h"
#include "class_board_design_settings.h"
#include "colors_selection.h"
#include "class_gerber_draw_item.h"
/***************/
/* tracepcb.cpp */
/***************/
static
void
Affiche_DCodes_Pistes
(
WinEDA_DrawPanel
*
panel
,
wxDC
*
DC
,
static
void
Show_Items_DCode_Value
(
WinEDA_DrawPanel
*
panel
,
wxDC
*
DC
,
BOARD
*
Pcb
,
int
drawmode
);
/** virtual Function PrintPage
...
...
@@ -95,8 +97,7 @@ void WinEDA_GerberFrame::RedrawActiveWindow( wxDC* DC, bool EraseBg )
}
/********************************************************************/
void
BOARD
::
Draw
(
WinEDA_DrawPanel
*
aPanel
,
wxDC
*
DC
,
int
aDrawMode
,
const
wxPoint
&
offset
)
void
BOARD
::
Draw
(
WinEDA_DrawPanel
*
aPanel
,
wxDC
*
aDC
,
int
aDrawMode
,
const
wxPoint
&
aOffset
)
/********************************************************************/
/* Redraw the BOARD items but not cursors, axis or grid */
// @todo: replace WinEDA_GerberFrame::Trace_Gerber() by this function
...
...
@@ -116,315 +117,71 @@ void WinEDA_GerberFrame::Trace_Gerber( wxDC* aDC, int aDraw_mode, int aPrintMask
if
(
!
GetBoard
()
)
return
;
bool
erase
=
false
;
int
color
;
bool
filled
;
int
layer
=
GetScreen
()
->
m_Active_Layer
;
// Draw filled polygons
std
::
vector
<
wxPoint
>
points
;
// minimize reallocations of the vector's internal array by starting with a good sized one.
points
.
reserve
(
10000
);
TRACK
*
next_track
;
for
(
TRACK
*
track
=
GetBoard
()
->
m_Zone
;
track
;
track
=
next_track
)
{
next_track
=
track
->
Next
();
if
(
!
(
track
->
ReturnMaskLayer
()
&
aPrintMasklayer
)
)
continue
;
if
(
(
points
.
size
()
==
0
)
&&
(
track
->
GetNet
()
==
0
)
)
// first point of a new polygon
{
erase
=
(
track
->
m_Flags
&
DRAW_ERASED
);
points
.
push_back
(
track
->
m_Start
);
}
points
.
push_back
(
track
->
m_End
);
if
(
(
next_track
==
NULL
)
||
(
next_track
->
GetNet
()
==
0
)
)
// EndPoint of the current polygon
{
color
=
g_ColorsSettings
.
GetLayerColor
(
track
->
GetLayer
()
);
filled
=
(
g_DisplayPolygonsModeSketch
==
0
);
if
(
erase
)
{
color
=
g_DrawBgColor
;
filled
=
true
;
}
GRClosedPoly
(
&
DrawPanel
->
m_ClipBox
,
aDC
,
points
.
size
(),
&
points
[
0
],
filled
,
color
,
color
);
points
.
clear
();
}
}
// Draw tracks and flashes down here.
// This will probably not be a final solution to drawing order issues
GERBER
*
gerber
=
g_GERBER_List
[
layer
];
int
dcode_hightlight
=
0
;
if
(
gerber
)
dcode_hightlight
=
gerber
->
m_Selected_Tool
;
for
(
TRACK
*
track
=
GetBoard
()
->
m_Track
;
track
;
track
=
track
->
Next
()
)
BOARD_ITEM
*
item
=
GetBoard
()
->
m_Drawings
;
for
(
;
item
;
item
=
item
->
Next
()
)
{
if
(
!
(
track
->
ReturnMaskLayer
()
&
aPrintMasklayer
)
)
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
if
(
!
(
gerb_item
->
ReturnMaskLayer
()
&
aPrintMasklayer
)
)
continue
;
if
(
dcode_hightlight
==
track
->
GetNet
()
&&
track
->
GetLayer
()
==
layer
)
Trace_Segment
(
GetBoard
(),
DrawPanel
,
aDC
,
track
,
aDraw_mode
|
GR_SURBRILL
);
if
(
dcode_hightlight
==
gerb_item
->
m_DCode
&&
item
->
GetLayer
()
==
layer
)
gerb_item
->
Draw
(
DrawPanel
,
aDC
,
aDraw_mode
|
GR_SURBRILL
);
else
Trace_Segment
(
GetBoard
(),
DrawPanel
,
aDC
,
track
,
aDraw_mode
);
gerb_item
->
Draw
(
DrawPanel
,
aDC
,
aDraw_mode
);
}
if
(
IsElementVisible
(
DCODES_VISIBLE
)
)
Affiche_DCodes_Pistes
(
DrawPanel
,
aDC
,
GetBoard
(),
GR_COPY
);
Show_Items_DCode_Value
(
DrawPanel
,
aDC
,
GetBoard
(),
GR_COPY
);
GetScreen
()
->
ClrRefreshReq
();
}
#if 1
/***********************************************************************************/
void
Trace_Segment
(
BOARD
*
aBrd
,
WinEDA_DrawPanel
*
panel
,
wxDC
*
DC
,
TRACK
*
track
,
int
draw_mode
)
/***********************************************************************************/
/* Trace 1 segment of track (segment, spot...).
* Parameters :
* Track = a pointer on of the description of the track
* draw_mode = mode ( GR_XOR, GR_OR..)
*/
{
int
l_piste
;
int
color
;
int
fillopt
;
int
radius
;
int
halfPenWidth
;
static
bool
show_err
;
if
(
track
->
m_Flags
&
DRAW_ERASED
)
// draw in background color, used by classs TRACK in gerbview
{
color
=
g_DrawBgColor
;
}
else
{
if
(
aBrd
->
IsLayerVisible
(
track
->
GetLayer
()
)
==
false
)
return
;
color
=
aBrd
->
GetLayerColor
(
track
->
GetLayer
()
);
if
(
draw_mode
&
GR_SURBRILL
)
{
if
(
draw_mode
&
GR_AND
)
color
&=
~
HIGHT_LIGHT_FLAG
;
else
color
|=
HIGHT_LIGHT_FLAG
;
}
if
(
color
&
HIGHT_LIGHT_FLAG
)
color
=
ColorRefs
[
color
&
MASKCOLOR
].
m_LightColor
;
}
GRSetDrawMode
(
DC
,
draw_mode
);
fillopt
=
DisplayOpt
.
DisplayPcbTrackFill
?
FILLED
:
SKETCH
;
switch
(
track
->
m_Shape
)
{
case
S_CIRCLE
:
radius
=
(
int
)
hypot
(
(
double
)
(
track
->
m_End
.
x
-
track
->
m_Start
.
x
),
(
double
)
(
track
->
m_End
.
y
-
track
->
m_Start
.
y
)
);
halfPenWidth
=
track
->
m_Width
>>
1
;
#ifdef USE_WX_ZOOM
if
(
DC
->
LogicalToDeviceXRel
(
halfPenWidth
)
<
L_MIN_DESSIN
)
#else
if
(
panel
->
GetScreen
()
->
Scale
(
halfPenWidth
)
<
L_MIN_DESSIN
)
#endif
{
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
radius
,
0
,
color
);
}
if
(
fillopt
==
SKETCH
)
{
// draw the border of the pen's path using two circles, each as narrow as possible
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
radius
-
halfPenWidth
,
0
,
color
);
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
radius
+
halfPenWidth
,
0
,
color
);
}
else
{
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
radius
,
track
->
m_Width
,
color
);
}
break
;
case
S_ARC
:
if
(
fillopt
==
SKETCH
)
{
GRArc1
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
track
->
m_End
.
x
,
track
->
m_End
.
y
,
track
->
m_Param
,
track
->
GetSubNet
(),
0
,
color
);
}
else
{
GRArc1
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
track
->
m_End
.
x
,
track
->
m_End
.
y
,
track
->
m_Param
,
track
->
GetSubNet
(),
track
->
m_Width
,
color
);
}
break
;
case
S_SPOT_CIRCLE
:
radius
=
track
->
m_Width
>>
1
;
fillopt
=
DisplayOpt
.
DisplayPadFill
?
FILLED
:
SKETCH
;
#ifdef USE_WX_ZOOM
if
(
DC
->
LogicalToDeviceXRel
(
radius
)
<
L_MIN_DESSIN
)
#else
if
(
panel
->
GetScreen
()
->
Scale
(
radius
)
<
L_MIN_DESSIN
)
#endif
{
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
radius
,
0
,
color
);
}
else
if
(
fillopt
==
SKETCH
)
{
GRCircle
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
radius
,
0
,
color
);
}
else
{
GRFilledCircle
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
radius
,
0
,
color
,
color
);
}
break
;
case
S_SPOT_RECT
:
case
S_RECT
:
l_piste
=
track
->
m_Width
>>
1
;
fillopt
=
DisplayOpt
.
DisplayPadFill
?
FILLED
:
SKETCH
;
#ifdef USE_WX_ZOOM
if
(
DC
->
LogicalToDeviceXRel
(
l_piste
)
<
L_MIN_DESSIN
)
#else
if
(
panel
->
GetScreen
()
->
Scale
(
l_piste
)
<
L_MIN_DESSIN
)
#endif
{
GRLine
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
track
->
m_End
.
x
,
track
->
m_End
.
y
,
0
,
color
);
}
else
if
(
fillopt
==
SKETCH
)
{
GRRect
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
-
l_piste
,
track
->
m_Start
.
y
-
l_piste
,
track
->
m_End
.
x
+
l_piste
,
track
->
m_End
.
y
+
l_piste
,
0
,
color
);
}
else
{
GRFilledRect
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
-
l_piste
,
track
->
m_Start
.
y
-
l_piste
,
track
->
m_End
.
x
+
l_piste
,
track
->
m_End
.
y
+
l_piste
,
0
,
color
,
color
);
}
break
;
case
S_SPOT_OVALE
:
fillopt
=
DisplayOpt
.
DisplayPadFill
?
FILLED
:
SKETCH
;
case
S_SEGMENT
:
l_piste
=
track
->
m_Width
>>
1
;
#ifdef USE_WX_ZOOM
if
(
DC
->
LogicalToDeviceXRel
(
l_piste
)
<
L_MIN_DESSIN
)
#else
if
(
panel
->
GetScreen
()
->
Scale
(
l_piste
)
<
L_MIN_DESSIN
)
#endif
{
GRLine
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
track
->
m_End
.
x
,
track
->
m_End
.
y
,
0
,
color
);
break
;
}
if
(
fillopt
==
SKETCH
)
{
GRCSegm
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
track
->
m_End
.
x
,
track
->
m_End
.
y
,
track
->
m_Width
,
color
);
}
else
{
GRFillCSegm
(
&
panel
->
m_ClipBox
,
DC
,
track
->
m_Start
.
x
,
track
->
m_Start
.
y
,
track
->
m_End
.
x
,
track
->
m_End
.
y
,
track
->
m_Width
,
color
);
}
break
;
default
:
if
(
!
show_err
)
{
wxMessageBox
(
wxT
(
"Trace_Segment() type error"
)
);
show_err
=
TRUE
;
}
break
;
}
}
#endif
/*****************************************************************************************/
void
Affiche_DCodes_Pistes
(
WinEDA_DrawPanel
*
panel
,
wxDC
*
DC
,
BOARD
*
Pcb
,
int
drawm
ode
)
void
Show_Items_DCode_Value
(
WinEDA_DrawPanel
*
aPanel
,
wxDC
*
aDC
,
BOARD
*
aPcb
,
int
aDrawM
ode
)
/*****************************************************************************************/
{
TRACK
*
track
;
wxPoint
pos
;
int
width
,
orient
;
wxString
Line
;
GRSetDrawMode
(
DC
,
drawm
ode
);
track
=
Pcb
->
m_Track
;
for
(
;
track
!=
NULL
;
track
=
track
->
Next
()
)
GRSetDrawMode
(
aDC
,
aDrawM
ode
);
BOARD_ITEM
*
item
=
aPcb
->
m_Drawings
;
for
(
;
item
!=
NULL
;
item
=
item
->
Next
()
)
{
if
(
Pcb
->
IsLayerVisible
(
track
->
GetLayer
()
)
==
false
)
GERBER_DRAW_ITEM
*
gerb_item
=
(
GERBER_DRAW_ITEM
*
)
item
;
if
(
aPcb
->
IsLayerVisible
(
gerb_item
->
GetLayer
()
)
==
false
)
continue
;
if
(
gerb_item
->
m_DCode
<=
0
)
continue
;
if
(
(
track
->
m_Shape
==
S_ARC
)
||
(
track
->
m_Shape
==
S_CIRCLE
)
||
(
track
->
m_Shape
==
S_ARC_RECT
)
)
{
pos
.
x
=
track
->
m_Start
.
x
;
pos
.
y
=
track
->
m_Start
.
y
;
}
if
(
gerb_item
->
m_Flashed
)
pos
=
gerb_item
->
m_Start
;
else
{
pos
.
x
=
(
track
->
m_Start
.
x
+
track
->
m_End
.
x
)
/
2
;
pos
.
y
=
(
track
->
m_Start
.
y
+
track
->
m_End
.
y
)
/
2
;
pos
.
x
=
(
gerb_item
->
m_Start
.
x
+
gerb_item
->
m_End
.
x
)
/
2
;
pos
.
y
=
(
gerb_item
->
m_Start
.
y
+
gerb_item
->
m_End
.
y
)
/
2
;
}
Line
.
Printf
(
wxT
(
"D%d"
),
track
->
GetNet
()
);
Line
.
Printf
(
wxT
(
"D%d"
),
gerb_item
->
m_DCode
);
width
=
track
->
m_Width
;
width
=
MIN
(
gerb_item
->
m_Size
.
x
,
gerb_item
->
m_Size
.
y
)
;
orient
=
TEXT_ORIENT_HORIZ
;
if
(
track
->
m_Shape
>=
S_SPOT_CIRCLE
)
// forme flash
if
(
gerb_item
->
m_Flashed
)
{
width
/=
3
;
}
else
// lines
{
int
dx
,
dy
;
dx
=
track
->
m_Start
.
x
-
track
->
m_End
.
x
;
dy
=
track
->
m_Start
.
y
-
track
->
m_End
.
y
;
dx
=
gerb_item
->
m_Start
.
x
-
gerb_item
->
m_End
.
x
;
dy
=
gerb_item
->
m_Start
.
y
-
gerb_item
->
m_End
.
y
;
if
(
abs
(
dx
)
<
abs
(
dy
)
)
orient
=
TEXT_ORIENT_VERT
;
width
/=
2
;
...
...
@@ -432,7 +189,7 @@ void Affiche_DCodes_Pistes( WinEDA_DrawPanel* panel, wxDC* DC, BOARD* Pcb, int d
int
color
=
g_ColorsSettings
.
GetItemColor
(
DCODES_VISIBLE
);
DrawGraphicText
(
panel
,
DC
,
DrawGraphicText
(
aPanel
,
a
DC
,
pos
,
(
EDA_Colors
)
color
,
Line
,
orient
,
wxSize
(
width
,
width
),
GR_TEXT_HJUSTIFY_CENTER
,
GR_TEXT_VJUSTIFY_CENTER
,
...
...
gerbview/wxGerberFrame.h
View file @
b992af3e
...
...
@@ -223,8 +223,6 @@ public:
* @param DC A device context to draw on.
*/
void
Block_Delete
(
wxDC
*
DC
);
void
Block_Rotate
(
wxDC
*
DC
);
void
Block_Invert
(
wxDC
*
DC
);
/**
* Function Block_Move
...
...
@@ -237,14 +235,6 @@ public:
*/
void
Block_Move
(
wxDC
*
DC
);
/**
* Function Block_Mirror_X
* mirrors all tracks and segments within the currently selected block
* in the X axis.
*
* @param DC A device context to draw on.
*/
void
Block_Mirror_X
(
wxDC
*
DC
);
/**
* Function Block_Duplicate
* copies-and-moves all tracks and segments within the selected block.
...
...
@@ -339,7 +329,6 @@ public:
bool
Clear_Pcb
(
bool
query
);
void
Erase_Current_Layer
(
bool
query
);
void
Delete_DCode_Items
(
wxDC
*
DC
,
int
dcode_value
,
int
layer_number
);
TRACK
*
Delete_Segment
(
wxDC
*
DC
,
TRACK
*
Track
);
// Conversion function
void
ExportDataInPcbnewFormat
(
wxCommandEvent
&
event
);
...
...
include/base_struct.h
View file @
b992af3e
...
...
@@ -87,6 +87,11 @@ enum KICAD_T {
*/
COMPONENT_FIELD_DRAW_TYPE
,
/*
* For Gerbview: items type:
*/
TYPE_GERBER_DRAW_ITEM
,
// End value
MAX_STRUCT_TYPE_ID
};
...
...
include/class_board_item.h
View file @
b992af3e
...
...
@@ -9,18 +9,15 @@
#include <boost/ptr_container/ptr_vector.hpp>
/* Shapes for segments (graphic segments and tracks) ( .
s
hape member ) */
/* Shapes for segments (graphic segments and tracks) ( .
m_S
hape member ) */
enum
Track_Shapes
{
S_SEGMENT
=
0
,
/* usual segment : line with rounded ends */
S_RECT
,
/* segment with non rounded ends */
S_ARC
,
/* Arcs (with rounded ends)*/
S_CIRCLE
,
/* ring*/
S_ARC_RECT
,
/* Arcs (with non rounded ends) (GERBER)*/
S_SPOT_OVALE
,
/* Oblong spot (for GERBER)*/
S_SPOT_CIRCLE
,
/* rounded spot (for GERBER)*/
S_SPOT_RECT
,
/* Rectangular spott (for GERBER)*/
S_POLYGON
,
/* polygonal shape */
S_CURVE
/* Bezier Curve*/
S_POLYGON
,
/* polygonal shape (not yet used for tracks, but could be in microwave apps) */
S_CURVE
,
/* Bezier Curve*/
S_LAST
/* last value for this list */
};
...
...
include/gr_basic.h
View file @
b992af3e
...
...
@@ -171,12 +171,10 @@ void GRCircle( EDA_Rect* ClipBox, wxDC* aDC, int x, int y, int aRadius,
void
GRCircle
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
r
,
int
width
,
int
Color
);
void
GRFilledCircle
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
r
,
int
width
,
int
Color
,
int
BgColor
);
void
GRSCircle
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
r
,
int
width
,
int
Color
);
void
GRSFilledCircle
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
r
,
int
width
,
int
Color
,
int
BgColor
);
void
GRFilledCircle
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
r
,
int
width
,
int
Color
,
int
BgColor
);
void
GRFilledCircle
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
wxPoint
aPos
,
int
aRadius
,
int
aColor
);
void
GRCircle
(
EDA_Rect
*
aClipBox
,
wxDC
*
aDC
,
wxPoint
aPos
,
int
aRadius
,
int
aWidth
,
int
aColor
);
void
GRArc
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
StAngle
,
int
EndAngle
,
int
r
,
int
Color
);
void
GRArc
(
EDA_Rect
*
ClipBox
,
wxDC
*
DC
,
int
x
,
int
y
,
int
StAngle
,
...
...
pcbnew/class_board_item.cpp
View file @
b992af3e
...
...
@@ -25,12 +25,6 @@ wxString BOARD_ITEM::ShowShape( Track_Shapes aShape )
case
S_ARC
:
return
_
(
"Arc"
);
case
S_CIRCLE
:
return
_
(
"Circle"
);
case
S_CURVE
:
return
_
(
"Bezier Curve"
);
// used in Gerbview:
case
S_ARC_RECT
:
return
wxT
(
"arc_rect"
);
case
S_SPOT_OVALE
:
return
wxT
(
"spot_oval"
);
case
S_SPOT_CIRCLE
:
return
wxT
(
"spot_circle"
);
case
S_SPOT_RECT
:
return
wxT
(
"spot_rect"
);
case
S_POLYGON
:
return
wxT
(
"polygon"
);
default
:
return
wxT
(
"??"
);
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment