6 * PCB, interactive printed circuit board design
7 * Copyright (C) 2006 DJ Delorie
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
19 * You should have received a copy of the GNU General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 * Contact addresses for paper mail and Email:
24 * DJ Delorie, 334 North Road, Deerfield NH 03037-1110, USA
49 #include "pcb-printf.h"
51 #ifdef HAVE_LIBDMALLOC
57 /* FIXME - we currently hardcode the grid and PCB size. What we
58 should do in the future is scan the font for its extents, and size
59 the grid appropriately. Also, when we convert back to a font, we
60 should search the grid for the gridlines and use them to figure out
61 where the symbols are. */
63 #define CELL_SIZE MIL_TO_COORD (100)
64 #define CELL_OFFSET MIL_TO_COORD (10)
66 #define XYtoSym(x,y) ((x1 + CELL_OFFSET) / CELL_SIZE - 1 \
67 + 16 * ((y1 + CELL_OFFSET) / CELL_SIZE - 1))
69 static const char fontedit_syntax
[] = "FontEdit()";
71 static const char fontedit_help
[] =
72 "Convert the current font to a PCB for editing.";
74 /* %start-doc actions FontEdit
79 FontEdit (int argc
, char **argv
, Coord Ux
, Coord Uy
)
83 LayerTypePtr lfont
, lorig
, lwidth
, lgrid
;
86 if (hid_actionl ("New", "Font", 0))
89 Settings
.grid_unit
= get_unit_struct("mil");
90 Settings
.Bloat
= PCB
->Bloat
= 1;
91 Settings
.Shrink
= PCB
->Shrink
= 1;
92 Settings
.minWid
= PCB
->minWid
= 1;
93 Settings
.minSlk
= PCB
->minSlk
= 1;
95 MoveLayerToGroup (max_copper_layer
+ COMPONENT_LAYER
, 0);
96 MoveLayerToGroup (max_copper_layer
+ SOLDER_LAYER
, 1);
98 while (PCB
->Data
->LayerN
> 4)
100 for (l
= 0; l
< 4; l
++)
102 MoveLayerToGroup (l
, l
);
104 PCB
->MaxWidth
= CELL_SIZE
* 18;
105 PCB
->MaxHeight
= CELL_SIZE
* ((MAX_FONTPOSITION
+ 15) / 16 + 2);
106 PCB
->Grid
= MIL_TO_COORD (5);
107 PCB
->Data
->Layer
[0].Name
= strdup ("Font");
108 PCB
->Data
->Layer
[1].Name
= strdup ("OrigFont");
109 PCB
->Data
->Layer
[2].Name
= strdup ("Width");
110 PCB
->Data
->Layer
[3].Name
= strdup ("Grid");
111 hid_action ("PCBChanged");
112 hid_action ("LayersChanged");
114 lfont
= PCB
->Data
->Layer
+ 0;
115 lorig
= PCB
->Data
->Layer
+ 1;
116 lwidth
= PCB
->Data
->Layer
+ 2;
117 lgrid
= PCB
->Data
->Layer
+ 3;
120 for (s
= 0; s
<= MAX_FONTPOSITION
; s
++)
122 Coord ox
= (s
% 16 + 1) * CELL_SIZE
;
123 Coord oy
= (s
/ 16 + 1) * CELL_SIZE
;
124 Coord w
, miny
, maxy
, maxx
= 0;
126 symbol
= &font
->Symbol
[s
];
128 miny
= MIL_TO_COORD (5);
129 maxy
= font
->MaxHeight
;
131 for (l
= 0; l
< symbol
->LineN
; l
++)
133 CreateDrawnLineOnLayer (lfont
,
134 symbol
->Line
[l
].Point1
.X
+ ox
,
135 symbol
->Line
[l
].Point1
.Y
+ oy
,
136 symbol
->Line
[l
].Point2
.X
+ ox
,
137 symbol
->Line
[l
].Point2
.Y
+ oy
,
138 symbol
->Line
[l
].Thickness
,
139 symbol
->Line
[l
].Thickness
, NoFlags ());
140 CreateDrawnLineOnLayer (lorig
, symbol
->Line
[l
].Point1
.X
+ ox
,
141 symbol
->Line
[l
].Point1
.Y
+ oy
,
142 symbol
->Line
[l
].Point2
.X
+ ox
,
143 symbol
->Line
[l
].Point2
.Y
+ oy
,
144 symbol
->Line
[l
].Thickness
,
145 symbol
->Line
[l
].Thickness
, NoFlags ());
146 if (maxx
< symbol
->Line
[l
].Point1
.X
)
147 maxx
= symbol
->Line
[l
].Point1
.X
;
148 if (maxx
< symbol
->Line
[l
].Point2
.X
)
149 maxx
= symbol
->Line
[l
].Point2
.X
;
151 w
= maxx
+ symbol
->Delta
+ ox
;
152 CreateDrawnLineOnLayer (lwidth
,
154 w
, maxy
+ oy
, MIL_TO_COORD (1), MIL_TO_COORD (1), NoFlags ());
157 for (l
= 0; l
< 16; l
++)
159 int x
= (l
+ 1) * CELL_SIZE
;
160 CreateDrawnLineOnLayer (lgrid
, x
, 0, x
, PCB
->MaxHeight
, MIL_TO_COORD (1),
161 MIL_TO_COORD (1), NoFlags ());
163 for (l
= 0; l
<= MAX_FONTPOSITION
/ 16 + 1; l
++)
165 int y
= (l
+ 1) * CELL_SIZE
;
166 CreateDrawnLineOnLayer (lgrid
, 0, y
, PCB
->MaxWidth
, y
, MIL_TO_COORD (1),
167 MIL_TO_COORD (1), NoFlags ());
172 static const char fontsave_syntax
[] = "FontSave()";
174 static const char fontsave_help
[] = "Convert the current PCB back to a font.";
176 /* %start-doc actions FontSave
181 FontSave (int argc
, char **argv
, Coord Ux
, Coord Uy
)
184 SymbolTypePtr symbol
;
187 LayerTypePtr lfont
, lwidth
;
190 lfont
= PCB
->Data
->Layer
+ 0;
191 lwidth
= PCB
->Data
->Layer
+ 2;
193 for (i
= 0; i
<= MAX_FONTPOSITION
; i
++)
195 font
->Symbol
[i
].LineN
= 0;
196 font
->Symbol
[i
].Valid
= 0;
197 font
->Symbol
[i
].Width
= 0;
200 for (ii
= lfont
->Line
; ii
!= NULL
; ii
= g_list_next (ii
))
202 LineType
*l
= ii
->data
;
203 int x1
= l
->Point1
.X
;
204 int y1
= l
->Point1
.Y
;
205 int x2
= l
->Point2
.X
;
206 int y2
= l
->Point2
.Y
;
209 s
= XYtoSym (x1
, y1
);
210 ox
= (s
% 16 + 1) * CELL_SIZE
;
211 oy
= (s
/ 16 + 1) * CELL_SIZE
;
212 symbol
= &PCB
->Font
.Symbol
[s
];
219 if (symbol
->Width
< x1
)
221 if (symbol
->Width
< x2
)
225 CreateNewLineInSymbol (symbol
, x1
, y1
, x2
, y2
, l
->Thickness
);
228 for (ii
= lwidth
->Line
; ii
!= NULL
; ii
= g_list_next (ii
))
230 LineType
*l
= ii
->data
;
231 Coord x1
= l
->Point1
.X
;
232 Coord y1
= l
->Point1
.Y
;
235 s
= XYtoSym (x1
, y1
);
236 ox
= (s
% 16 + 1) * CELL_SIZE
;
237 symbol
= &PCB
->Font
.Symbol
[s
];
241 symbol
->Delta
= x1
- symbol
->Width
;
249 HID_Action fontmode_action_list
[] = {
250 {"FontEdit", 0, FontEdit
,
251 fontedit_help
, fontedit_syntax
},
252 {"FontSave", 0, FontSave
,
253 fontsave_help
, fontsave_syntax
}
256 REGISTER_ACTIONS (fontmode_action_list
)