4 * PCB, interactive printed circuit board design
5 * Copyright (C) 1994,1995,1996, 2003, 2004 Thomas Nau
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 * Contact addresses for paper mail and Email:
22 * Thomas Nau, Schlehenweg 15, 88471 Baustetten, Germany
23 * Thomas.Nau@rz.uni-ulm.de
40 #include "crosshair.h"
52 #ifdef HAVE_LIBDMALLOC
60 #define MAXINT (((unsigned int)(~0))>>1)
63 #define SMALL_SMALL_TEXT_SIZE 0
64 #define SMALL_TEXT_SIZE 1
65 #define NORMAL_TEXT_SIZE 2
66 #define LARGE_TEXT_SIZE 3
67 #define N_TEXT_SIZES 4
70 /* ---------------------------------------------------------------------------
71 * some local identifiers
73 static BoxType Block
= {MAXINT
, MAXINT
, -MAXINT
, -MAXINT
};
75 static int doing_pinout
= 0;
76 static bool doing_assy
= false;
78 /* ---------------------------------------------------------------------------
79 * some local prototypes
81 static void DrawEverything (const BoxType
*);
82 static void DrawPPV (int group
, const BoxType
*);
83 static void AddPart (void *);
84 static void DrawEMark (ElementType
*, Coord
, Coord
, bool);
85 static void DrawRats (const BoxType
*);
88 set_object_color (AnyObjectType
*obj
,
89 char *warn_color
, char *selected_color
,
90 char *found_color
, char *normal_color
)
94 if (warn_color
!= NULL
&& TEST_FLAG (WARNFLAG
, obj
)) color
= warn_color
;
95 else if (selected_color
!= NULL
&& TEST_FLAG (SELECTEDFLAG
, obj
)) color
= selected_color
;
96 else if (found_color
!= NULL
&& TEST_FLAG (FOUNDFLAG
, obj
)) color
= found_color
;
97 else color
= normal_color
;
99 gui
->graphics
->set_color (Output
.fgGC
, color
);
103 set_layer_object_color (LayerType
*layer
, AnyObjectType
*obj
)
105 set_object_color (obj
, NULL
, layer
->SelectedColor
, PCB
->ConnectedColor
, layer
->Color
);
108 /*---------------------------------------------------------------------------
109 * Adds the update rect to the update region
114 BoxType
*box
= (BoxType
*) b
;
116 Block
.X1
= MIN (Block
.X1
, box
->X1
);
117 Block
.X2
= MAX (Block
.X2
, box
->X2
);
118 Block
.Y1
= MIN (Block
.Y1
, box
->Y1
);
119 Block
.Y2
= MAX (Block
.Y2
, box
->Y2
);
123 * initiate the actual redrawing of the updated area
128 if (Block
.X1
<= Block
.X2
&& Block
.Y1
<= Block
.Y2
)
129 gui
->invalidate_lr (Block
.X1
, Block
.X2
, Block
.Y1
, Block
.Y2
);
131 /* shrink the update block */
132 Block
.X1
= Block
.Y1
= MAXINT
;
133 Block
.X2
= Block
.Y2
= -MAXINT
;
136 /* ----------------------------------------------------------------------
137 * redraws all the data by the event handlers
142 gui
->invalidate_all ();
146 _draw_pv_name (PinType
*pv
)
152 if (!pv
->Name
|| !pv
->Name
[0])
153 text
.TextString
= EMPTY (pv
->Number
);
155 text
.TextString
= EMPTY (TEST_FLAG (SHOWNUMBERFLAG
, PCB
) ? pv
->Number
: pv
->Name
);
157 vert
= TEST_FLAG (EDGE2FLAG
, pv
);
161 box
.X1
= pv
->X
- pv
->Thickness
/ 2 + Settings
.PinoutTextOffsetY
;
162 box
.Y1
= pv
->Y
- pv
->DrillingHole
/ 2 - Settings
.PinoutTextOffsetX
;
166 box
.X1
= pv
->X
+ pv
->DrillingHole
/ 2 + Settings
.PinoutTextOffsetX
;
167 box
.Y1
= pv
->Y
- pv
->Thickness
/ 2 + Settings
.PinoutTextOffsetY
;
170 gui
->graphics
->set_color (Output
.fgGC
, PCB
->PinNameColor
);
172 text
.Flags
= NoFlags ();
173 /* Set font height to approx 56% of pin thickness */
174 text
.Scale
= 56 * pv
->Thickness
/ FONT_CAPHEIGHT
;
177 text
.Direction
= vert
? 1 : 0;
181 DrawTextLowLevel (Output
.fgGC
, &text
, 0);
187 _draw_pv (PinType
*pv
, bool draw_hole
)
189 if (TEST_FLAG (THINDRAWFLAG
, PCB
))
190 gui
->graphics
->thindraw_pcb_pv (Output
.fgGC
, Output
.fgGC
, pv
, draw_hole
, false);
192 gui
->graphics
->fill_pcb_pv (Output
.fgGC
, Output
.bgGC
, pv
, draw_hole
, false);
194 if (!TEST_FLAG (HOLEFLAG
, pv
) && TEST_FLAG (DISPLAYNAMEFLAG
, pv
))
199 draw_pin (PinType
*pin
, bool draw_hole
)
202 gui
->graphics
->set_color (Output
.fgGC
, PCB
->PinColor
);
204 set_object_color ((AnyObjectType
*)pin
,
205 PCB
->WarnColor
, PCB
->PinSelectedColor
,
206 PCB
->ConnectedColor
, PCB
->PinColor
);
208 _draw_pv (pin
, draw_hole
);
212 pin_callback (const BoxType
* b
, void *cl
)
214 draw_pin ((PinType
*)b
, false);
219 draw_via (PinType
*via
, bool draw_hole
)
222 gui
->graphics
->set_color (Output
.fgGC
, PCB
->ViaColor
);
224 set_object_color ((AnyObjectType
*)via
,
225 PCB
->WarnColor
, PCB
->ViaSelectedColor
,
226 PCB
->ConnectedColor
, PCB
->ViaColor
);
228 _draw_pv (via
, draw_hole
);
232 via_callback (const BoxType
* b
, void *cl
)
234 draw_via ((PinType
*)b
, false);
239 draw_pad_name (PadType
*pad
)
245 if (!pad
->Name
|| !pad
->Name
[0])
246 text
.TextString
= EMPTY (pad
->Number
);
248 text
.TextString
= EMPTY (TEST_FLAG (SHOWNUMBERFLAG
, PCB
) ? pad
->Number
: pad
->Name
);
250 /* should text be vertical ? */
251 vert
= (pad
->Point1
.X
== pad
->Point2
.X
);
255 box
.X1
= pad
->Point1
.X
- pad
->Thickness
/ 2;
256 box
.Y1
= MAX (pad
->Point1
.Y
, pad
->Point2
.Y
) + pad
->Thickness
/ 2;
257 box
.X1
+= Settings
.PinoutTextOffsetY
;
258 box
.Y1
-= Settings
.PinoutTextOffsetX
;
262 box
.X1
= MIN (pad
->Point1
.X
, pad
->Point2
.X
) - pad
->Thickness
/ 2;
263 box
.Y1
= pad
->Point1
.Y
- pad
->Thickness
/ 2;
264 box
.X1
+= Settings
.PinoutTextOffsetX
;
265 box
.Y1
+= Settings
.PinoutTextOffsetY
;
268 gui
->graphics
->set_color (Output
.fgGC
, PCB
->PinNameColor
);
270 text
.Flags
= NoFlags ();
271 /* Set font height to approx 90% of pin thickness */
272 text
.Scale
= 90 * pad
->Thickness
/ FONT_CAPHEIGHT
;
275 text
.Direction
= vert
? 1 : 0;
277 DrawTextLowLevel (Output
.fgGC
, &text
, 0);
281 _draw_pad (hidGC gc
, PadType
*pad
, bool clear
, bool mask
)
283 if (clear
&& !mask
&& pad
->Clearance
<= 0)
286 if (TEST_FLAG (THINDRAWFLAG
, PCB
) ||
287 (clear
&& TEST_FLAG (THINDRAWPOLYFLAG
, PCB
)))
288 gui
->graphics
->thindraw_pcb_pad (gc
, pad
, clear
, mask
);
290 gui
->graphics
->fill_pcb_pad (gc
, pad
, clear
, mask
);
294 draw_pad (PadType
*pad
)
297 gui
->graphics
->set_color (Output
.fgGC
, PCB
->PinColor
);
299 set_object_color ((AnyObjectType
*)pad
, PCB
->WarnColor
,
300 PCB
->PinSelectedColor
, PCB
->ConnectedColor
,
301 FRONT (pad
) ? PCB
->PinColor
: PCB
->InvisibleObjectsColor
);
303 _draw_pad (Output
.fgGC
, pad
, false, false);
305 if (doing_pinout
|| TEST_FLAG (DISPLAYNAMEFLAG
, pad
))
310 pad_callback (const BoxType
* b
, void *cl
)
312 PadType
*pad
= (PadType
*) b
;
315 if (ON_SIDE (pad
, *side
))
321 draw_element_name (ElementType
*element
)
323 if ((TEST_FLAG (HIDENAMESFLAG
, PCB
) && gui
->gui
) ||
324 TEST_FLAG (HIDENAMEFLAG
, element
))
326 if (doing_pinout
|| doing_assy
)
327 gui
->graphics
->set_color (Output
.fgGC
, PCB
->ElementColor
);
328 else if (TEST_FLAG (SELECTEDFLAG
, &ELEMENT_TEXT (PCB
, element
)))
329 gui
->graphics
->set_color (Output
.fgGC
, PCB
->ElementSelectedColor
);
330 else if (FRONT (element
))
331 gui
->graphics
->set_color (Output
.fgGC
, PCB
->ElementColor
);
333 gui
->graphics
->set_color (Output
.fgGC
, PCB
->InvisibleObjectsColor
);
334 DrawTextLowLevel (Output
.fgGC
, &ELEMENT_TEXT (PCB
, element
), PCB
->minSlk
);
338 name_callback (const BoxType
* b
, void *cl
)
340 TextType
*text
= (TextType
*) b
;
341 ElementType
*element
= (ElementType
*) text
->Element
;
344 if (TEST_FLAG (HIDENAMEFLAG
, element
))
347 if (ON_SIDE (element
, *side
))
348 draw_element_name (element
);
353 draw_element_pins_and_pads (ElementType
*element
)
357 if (doing_pinout
|| doing_assy
|| FRONT (pad
) || PCB
->InvisibleObjectsOn
)
363 draw_pin (pin
, true);
369 EMark_callback (const BoxType
* b
, void *cl
)
371 ElementType
*element
= (ElementType
*) b
;
373 DrawEMark (element
, element
->MarkX
, element
->MarkY
, !FRONT (element
));
378 hole_callback (const BoxType
* b
, void *cl
)
380 PinType
*pv
= (PinType
*) b
;
381 int plated
= cl
? *(int *) cl
: -1;
383 if ((plated
== 0 && !TEST_FLAG (HOLEFLAG
, pv
)) ||
384 (plated
== 1 && TEST_FLAG (HOLEFLAG
, pv
)))
387 if (TEST_FLAG (THINDRAWFLAG
, PCB
))
389 if (!TEST_FLAG (HOLEFLAG
, pv
))
391 gui
->graphics
->set_line_cap (Output
.fgGC
, Round_Cap
);
392 gui
->graphics
->set_line_width (Output
.fgGC
, 0);
393 gui
->graphics
->draw_arc (Output
.fgGC
,
394 pv
->X
, pv
->Y
, pv
->DrillingHole
/ 2,
395 pv
->DrillingHole
/ 2, 0, 360);
399 gui
->graphics
->fill_circle (Output
.bgGC
, pv
->X
, pv
->Y
, pv
->DrillingHole
/ 2);
401 if (TEST_FLAG (HOLEFLAG
, pv
))
403 set_object_color ((AnyObjectType
*) pv
,
404 PCB
->WarnColor
, PCB
->ViaSelectedColor
,
405 NULL
, Settings
.BlackColor
);
407 gui
->graphics
->set_line_cap (Output
.fgGC
, Round_Cap
);
408 gui
->graphics
->set_line_width (Output
.fgGC
, 0);
409 gui
->graphics
->draw_arc (Output
.fgGC
,
410 pv
->X
, pv
->Y
, pv
->DrillingHole
/ 2,
411 pv
->DrillingHole
/ 2, 0, 360);
417 DrawHoles (bool draw_plated
, bool draw_unplated
, const BoxType
*drawn_area
)
421 if ( draw_plated
&& !draw_unplated
) plated
= 1;
422 if (!draw_plated
&& draw_unplated
) plated
= 0;
424 r_search (PCB
->Data
->pin_tree
, drawn_area
, NULL
, hole_callback
, &plated
);
425 r_search (PCB
->Data
->via_tree
, drawn_area
, NULL
, hole_callback
, &plated
);
429 draw_line (LayerType
*layer
, LineType
*line
)
431 set_layer_object_color (layer
, (AnyObjectType
*) line
);
432 gui
->graphics
->draw_pcb_line (Output
.fgGC
, line
);
436 line_callback (const BoxType
* b
, void *cl
)
438 draw_line ((LayerType
*) cl
, (LineType
*) b
);
443 rat_callback (const BoxType
* b
, void *cl
)
445 RatType
*rat
= (RatType
*)b
;
447 set_object_color ((AnyObjectType
*) rat
, NULL
, PCB
->RatSelectedColor
,
448 PCB
->ConnectedColor
, PCB
->RatColor
);
450 if (Settings
.RatThickness
< 100)
451 rat
->Thickness
= pixel_slop
* Settings
.RatThickness
;
452 /* rats.c set VIAFLAG if this rat goes to a containing poly: draw a donut */
453 if (TEST_FLAG(VIAFLAG
, rat
))
455 int w
= rat
->Thickness
;
457 if (TEST_FLAG (THINDRAWFLAG
, PCB
))
458 gui
->graphics
->set_line_width (Output
.fgGC
, 0);
460 gui
->graphics
->set_line_width (Output
.fgGC
, w
);
461 gui
->graphics
->draw_arc (Output
.fgGC
, rat
->Point1
.X
, rat
->Point1
.Y
,
462 w
* 2, w
* 2, 0, 360);
465 gui
->graphics
->draw_pcb_line (Output
.fgGC
, (LineType
*) rat
);
470 draw_arc (LayerType
*layer
, ArcType
*arc
)
472 set_layer_object_color (layer
, (AnyObjectType
*) arc
);
473 gui
->graphics
->draw_pcb_arc (Output
.fgGC
, arc
);
477 arc_callback (const BoxType
* b
, void *cl
)
479 draw_arc ((LayerType
*) cl
, (ArcType
*) b
);
484 draw_element_package (ElementType
*element
)
486 /* set color and draw lines, arcs, text and pins */
487 if (doing_pinout
|| doing_assy
)
488 gui
->graphics
->set_color (Output
.fgGC
, PCB
->ElementColor
);
489 else if (TEST_FLAG (SELECTEDFLAG
, element
))
490 gui
->graphics
->set_color (Output
.fgGC
, PCB
->ElementSelectedColor
);
491 else if (FRONT (element
))
492 gui
->graphics
->set_color (Output
.fgGC
, PCB
->ElementColor
);
494 gui
->graphics
->set_color (Output
.fgGC
, PCB
->InvisibleObjectsColor
);
496 /* draw lines, arcs, text and pins */
497 ELEMENTLINE_LOOP (element
);
499 gui
->graphics
->draw_pcb_line (Output
.fgGC
, line
);
504 gui
->graphics
->draw_pcb_arc (Output
.fgGC
, arc
);
510 element_callback (const BoxType
* b
, void *cl
)
512 ElementType
*element
= (ElementType
*) b
;
515 if (ON_SIDE (element
, *side
))
516 draw_element_package (element
);
520 /* ---------------------------------------------------------------------------
521 * prints assembly drawing.
525 PrintAssembly (int side
, const BoxType
* drawn_area
)
527 int side_group
= GetLayerGroupNumberByNumber (max_copper_layer
+ side
);
530 gui
->graphics
->set_draw_faded (Output
.fgGC
, 1);
531 DrawLayerGroup (side_group
, drawn_area
);
532 gui
->graphics
->set_draw_faded (Output
.fgGC
, 0);
535 DrawSilk (side
, drawn_area
);
539 /* ---------------------------------------------------------------------------
540 * initializes some identifiers for a new zoom factor and redraws whole screen
543 DrawEverything (const BoxType
*drawn_area
)
545 int i
, ngroups
, side
;
546 int component
, solder
;
547 /* This is the list of layer groups we will draw. */
548 int do_group
[MAX_LAYER
];
549 /* This is the reverse of the order in which we draw them. */
550 int drawn_groups
[MAX_LAYER
];
551 int plated
, unplated
;
554 PCB
->Data
->SILKLAYER
.Color
= PCB
->ElementColor
;
555 PCB
->Data
->BACKSILKLAYER
.Color
= PCB
->InvisibleObjectsColor
;
557 memset (do_group
, 0, sizeof (do_group
));
558 for (ngroups
= 0, i
= 0; i
< max_copper_layer
; i
++)
560 LayerType
*l
= LAYER_ON_STACK (i
);
561 int group
= GetLayerGroupNumberByNumber (LayerStack
[i
]);
562 if (l
->On
&& !do_group
[group
])
565 drawn_groups
[ngroups
++] = group
;
569 component
= GetLayerGroupNumberByNumber (component_silk_layer
);
570 solder
= GetLayerGroupNumberByNumber (solder_silk_layer
);
573 * first draw all 'invisible' stuff
575 if (!TEST_FLAG (CHECKPLANESFLAG
, PCB
)
576 && gui
->set_layer ("invisible", SL (INVISIBLE
, 0), 0))
578 side
= SWAP_IDENT
? COMPONENT_LAYER
: SOLDER_LAYER
;
581 r_search (PCB
->Data
->element_tree
, drawn_area
, NULL
, element_callback
, &side
);
582 r_search (PCB
->Data
->name_tree
[NAME_INDEX (PCB
)], drawn_area
, NULL
, name_callback
, &side
);
583 DrawLayer (&(PCB
->Data
->Layer
[max_copper_layer
+ side
]), drawn_area
);
585 r_search (PCB
->Data
->pad_tree
, drawn_area
, NULL
, pad_callback
, &side
);
589 /* draw all layers in layerstack order */
590 for (i
= ngroups
- 1; i
>= 0; i
--)
592 int group
= drawn_groups
[i
];
594 if (gui
->set_layer (0, group
, 0))
596 DrawLayerGroup (group
, drawn_area
);
601 if (TEST_FLAG (CHECKPLANESFLAG
, PCB
) && gui
->gui
)
604 /* Draw pins, pads, vias below silk */
606 DrawPPV (SWAP_IDENT
? solder
: component
, drawn_area
);
609 CountHoles (&plated
, &unplated
, drawn_area
);
611 if (plated
&& gui
->set_layer ("plated-drill", SL (PDRILL
, 0), 0))
613 DrawHoles (true, false, drawn_area
);
617 if (unplated
&& gui
->set_layer ("unplated-drill", SL (UDRILL
, 0), 0))
619 DrawHoles (false, true, drawn_area
);
624 /* Draw the solder mask if turned on */
625 if (gui
->set_layer ("componentmask", SL (MASK
, TOP
), 0))
627 DrawMask (COMPONENT_LAYER
, drawn_area
);
631 if (gui
->set_layer ("soldermask", SL (MASK
, BOTTOM
), 0))
633 DrawMask (SOLDER_LAYER
, drawn_area
);
637 if (gui
->set_layer ("topsilk", SL (SILK
, TOP
), 0))
639 DrawSilk (COMPONENT_LAYER
, drawn_area
);
643 if (gui
->set_layer ("bottomsilk", SL (SILK
, BOTTOM
), 0))
645 DrawSilk (SOLDER_LAYER
, drawn_area
);
651 /* Draw element Marks */
653 r_search (PCB
->Data
->element_tree
, drawn_area
, NULL
, EMark_callback
,
655 /* Draw rat lines on top */
656 if (gui
->set_layer ("rats", SL (RATS
, 0), 0))
658 DrawRats(drawn_area
);
663 paste_empty
= IsPasteEmpty (COMPONENT_LAYER
);
664 if (gui
->set_layer ("toppaste", SL (PASTE
, TOP
), paste_empty
))
666 DrawPaste (COMPONENT_LAYER
, drawn_area
);
670 paste_empty
= IsPasteEmpty (SOLDER_LAYER
);
671 if (gui
->set_layer ("bottompaste", SL (PASTE
, BOTTOM
), paste_empty
))
673 DrawPaste (SOLDER_LAYER
, drawn_area
);
677 if (gui
->set_layer ("topassembly", SL (ASSY
, TOP
), 0))
679 PrintAssembly (COMPONENT_LAYER
, drawn_area
);
683 if (gui
->set_layer ("bottomassembly", SL (ASSY
, BOTTOM
), 0))
685 PrintAssembly (SOLDER_LAYER
, drawn_area
);
689 if (gui
->set_layer ("fab", SL (FAB
, 0), 0))
691 PrintFab (Output
.fgGC
);
697 DrawEMark (ElementType
*e
, Coord X
, Coord Y
, bool invisible
)
699 Coord mark_size
= EMARK_SIZE
;
700 if (!PCB
->InvisibleObjectsOn
&& invisible
)
705 PinType
*pin0
= e
->Pin
->data
;
706 if (TEST_FLAG (HOLEFLAG
, pin0
))
707 mark_size
= MIN (mark_size
, pin0
->DrillingHole
/ 2);
709 mark_size
= MIN (mark_size
, pin0
->Thickness
/ 2);
714 PadType
*pad0
= e
->Pad
->data
;
715 mark_size
= MIN (mark_size
, pad0
->Thickness
/ 2);
718 gui
->graphics
->set_color (Output
.fgGC
,
719 invisible
? PCB
->InvisibleMarkColor
: PCB
->ElementColor
);
720 gui
->graphics
->set_line_cap (Output
.fgGC
, Trace_Cap
);
721 gui
->graphics
->set_line_width (Output
.fgGC
, 0);
722 gui
->graphics
->draw_line (Output
.fgGC
, X
- mark_size
, Y
, X
, Y
- mark_size
);
723 gui
->graphics
->draw_line (Output
.fgGC
, X
+ mark_size
, Y
, X
, Y
- mark_size
);
724 gui
->graphics
->draw_line (Output
.fgGC
, X
- mark_size
, Y
, X
, Y
+ mark_size
);
725 gui
->graphics
->draw_line (Output
.fgGC
, X
+ mark_size
, Y
, X
, Y
+ mark_size
);
728 * If an element is locked, place a "L" on top of the "diamond".
729 * This provides a nice visual indication that it is locked that
730 * works even for color blind users.
732 if (TEST_FLAG (LOCKFLAG
, e
) )
734 gui
->graphics
->draw_line (Output
.fgGC
, X
, Y
, X
+ 2 * mark_size
, Y
);
735 gui
->graphics
->draw_line (Output
.fgGC
, X
, Y
, X
, Y
- 4* mark_size
);
739 /* ---------------------------------------------------------------------------
740 * Draws pins pads and vias - Always draws for non-gui HIDs,
741 * otherwise drawing depends on PCB->PinOn and PCB->ViaOn
744 DrawPPV (int group
, const BoxType
*drawn_area
)
746 int component_group
= GetLayerGroupNumberByNumber (component_silk_layer
);
747 int solder_group
= GetLayerGroupNumberByNumber (solder_silk_layer
);
750 if (PCB
->PinOn
|| !gui
->gui
)
752 /* draw element pins */
753 r_search (PCB
->Data
->pin_tree
, drawn_area
, NULL
, pin_callback
, NULL
);
755 /* draw element pads */
756 if (group
== component_group
)
758 side
= COMPONENT_LAYER
;
759 r_search (PCB
->Data
->pad_tree
, drawn_area
, NULL
, pad_callback
, &side
);
762 if (group
== solder_group
)
765 r_search (PCB
->Data
->pad_tree
, drawn_area
, NULL
, pad_callback
, &side
);
770 if (PCB
->ViaOn
|| !gui
->gui
)
772 r_search (PCB
->Data
->via_tree
, drawn_area
, NULL
, via_callback
, NULL
);
773 r_search (PCB
->Data
->via_tree
, drawn_area
, NULL
, hole_callback
, NULL
);
775 if (PCB
->PinOn
|| doing_assy
)
776 r_search (PCB
->Data
->pin_tree
, drawn_area
, NULL
, hole_callback
, NULL
);
780 clearPin_callback (const BoxType
* b
, void *cl
)
782 PinType
*pin
= (PinType
*) b
;
783 if (TEST_FLAG (THINDRAWFLAG
, PCB
) || TEST_FLAG (THINDRAWPOLYFLAG
, PCB
))
784 gui
->graphics
->thindraw_pcb_pv (Output
.pmGC
, Output
.pmGC
, pin
, false, true);
786 gui
->graphics
->fill_pcb_pv (Output
.pmGC
, Output
.pmGC
, pin
, false, true);
791 const BoxType
*drawn_area
;
796 poly_callback (const BoxType
* b
, void *cl
)
798 struct poly_info
*i
= cl
;
799 PolygonType
*polygon
= (PolygonType
*)b
;
801 if (!polygon
->Clipped
)
804 set_layer_object_color (i
->layer
, (AnyObjectType
*) polygon
);
806 if (gui
->graphics
->thindraw_pcb_polygon
!= NULL
&&
807 (TEST_FLAG (THINDRAWFLAG
, PCB
) ||
808 TEST_FLAG (THINDRAWPOLYFLAG
, PCB
)))
809 gui
->graphics
->thindraw_pcb_polygon (Output
.fgGC
, polygon
, i
->drawn_area
);
811 gui
->graphics
->fill_pcb_polygon (Output
.fgGC
, polygon
, i
->drawn_area
);
813 /* If checking planes, thin-draw any pieces which have been clipped away */
814 if (gui
->graphics
->thindraw_pcb_polygon
!= NULL
&&
815 TEST_FLAG (CHECKPLANESFLAG
, PCB
) &&
816 !TEST_FLAG (FULLPOLYFLAG
, polygon
))
818 PolygonType poly
= *polygon
;
820 for (poly
.Clipped
= polygon
->Clipped
->f
;
821 poly
.Clipped
!= polygon
->Clipped
;
822 poly
.Clipped
= poly
.Clipped
->f
)
823 gui
->graphics
->thindraw_pcb_polygon (Output
.fgGC
, &poly
, i
->drawn_area
);
830 clearPad_callback (const BoxType
* b
, void *cl
)
832 PadType
*pad
= (PadType
*) b
;
834 if (ON_SIDE (pad
, *side
) && pad
->Mask
)
835 _draw_pad (Output
.pmGC
, pad
, true, true);
839 /* ---------------------------------------------------------------------------
844 DrawSilk (int side
, const BoxType
* drawn_area
)
847 /* This code is used when you want to mask silk to avoid exposed
848 pins and pads. We decided it was a bad idea to do this
849 unconditionally, but the code remains. */
853 if (gui
->poly_before
)
855 gui
->graphics
->use_mask (HID_MASK_BEFORE
);
857 DrawLayer (LAYER_PTR (max_copper_layer
+ side
), drawn_area
);
859 r_search (PCB
->Data
->element_tree
, drawn_area
, NULL
, element_callback
, &side
);
860 r_search (PCB
->Data
->name_tree
[NAME_INDEX (PCB
)], drawn_area
, NULL
, name_callback
, &side
);
864 gui
->graphics
->use_mask (HID_MASK_CLEAR
);
865 r_search (PCB
->Data
->pin_tree
, drawn_area
, NULL
, clearPin_callback
, NULL
);
866 r_search (PCB
->Data
->via_tree
, drawn_area
, NULL
, clearPin_callback
, NULL
);
867 r_search (PCB
->Data
->pad_tree
, drawn_area
, NULL
, clearPad_callback
, &side
);
871 gui
->graphics
->use_mask (HID_MASK_AFTER
);
872 DrawLayer (LAYER_PTR (max_copper_layer
+ layer
), drawn_area
);
874 r_search (PCB
->Data
->element_tree
, drawn_area
, NULL
, element_callback
, &side
);
875 r_search (PCB
->Data
->name_tree
[NAME_INDEX (PCB
)], drawn_area
, NULL
, name_callback
, &side
);
877 gui
->graphics
->use_mask (HID_MASK_OFF
);
883 DrawMaskBoardArea (int mask_type
, const BoxType
*drawn_area
)
885 /* Skip the mask drawing if the GUI doesn't want this type */
886 if ((mask_type
== HID_MASK_BEFORE
&& !gui
->poly_before
) ||
887 (mask_type
== HID_MASK_AFTER
&& !gui
->poly_after
))
890 gui
->graphics
->use_mask (mask_type
);
891 gui
->graphics
->set_color (Output
.fgGC
, PCB
->MaskColor
);
892 if (drawn_area
== NULL
)
893 gui
->graphics
->fill_rect (Output
.fgGC
, 0, 0, PCB
->MaxWidth
, PCB
->MaxHeight
);
895 gui
->graphics
->fill_rect (Output
.fgGC
, drawn_area
->X1
, drawn_area
->Y1
,
896 drawn_area
->X2
, drawn_area
->Y2
);
899 /* ---------------------------------------------------------------------------
900 * draws solder mask layer - this will cover nearly everything
903 DrawMask (int side
, const BoxType
*screen
)
905 int thin
= TEST_FLAG(THINDRAWFLAG
, PCB
) || TEST_FLAG(THINDRAWPOLYFLAG
, PCB
);
908 gui
->graphics
->set_color (Output
.pmGC
, PCB
->MaskColor
);
911 DrawMaskBoardArea (HID_MASK_BEFORE
, screen
);
912 gui
->graphics
->use_mask (HID_MASK_CLEAR
);
915 r_search (PCB
->Data
->pin_tree
, screen
, NULL
, clearPin_callback
, NULL
);
916 r_search (PCB
->Data
->via_tree
, screen
, NULL
, clearPin_callback
, NULL
);
917 r_search (PCB
->Data
->pad_tree
, screen
, NULL
, clearPad_callback
, &side
);
920 gui
->graphics
->set_color (Output
.pmGC
, "erase");
923 DrawMaskBoardArea (HID_MASK_AFTER
, screen
);
924 gui
->graphics
->use_mask (HID_MASK_OFF
);
928 /* ---------------------------------------------------------------------------
929 * draws solder paste layer for a given side of the board
932 DrawPaste (int side
, const BoxType
*drawn_area
)
934 gui
->graphics
->set_color (Output
.fgGC
, PCB
->ElementColor
);
935 ALLPAD_LOOP (PCB
->Data
);
937 if (ON_SIDE (pad
, side
) && !TEST_FLAG (NOPASTEFLAG
, pad
) && pad
->Mask
> 0)
939 if (pad
->Mask
< pad
->Thickness
)
940 _draw_pad (Output
.fgGC
, pad
, true, true);
942 _draw_pad (Output
.fgGC
, pad
, false, false);
949 DrawRats (const BoxType
*drawn_area
)
952 * XXX lesstif allows positive AND negative drawing in HID_MASK_CLEAR.
953 * XXX gtk only allows negative drawing.
954 * XXX using the mask here is to get rat transparency
956 int can_mask
= strcmp(gui
->name
, "lesstif") == 0;
959 gui
->graphics
->use_mask (HID_MASK_CLEAR
);
960 r_search (PCB
->Data
->rat_tree
, drawn_area
, NULL
, rat_callback
, NULL
);
962 gui
->graphics
->use_mask (HID_MASK_OFF
);
966 text_callback (const BoxType
* b
, void *cl
)
968 LayerType
*layer
= cl
;
969 TextType
*text
= (TextType
*)b
;
972 if (TEST_FLAG (SELECTEDFLAG
, text
))
973 gui
->graphics
->set_color (Output
.fgGC
, layer
->SelectedColor
);
975 gui
->graphics
->set_color (Output
.fgGC
, layer
->Color
);
976 if (layer
== &PCB
->Data
->SILKLAYER
||
977 layer
== &PCB
->Data
->BACKSILKLAYER
)
978 min_silk_line
= PCB
->minSlk
;
980 min_silk_line
= PCB
->minWid
;
981 DrawTextLowLevel (Output
.fgGC
, text
, min_silk_line
);
986 DrawLayer (LayerType
*Layer
, const BoxType
*screen
)
988 struct poly_info info
= {screen
, Layer
};
990 /* print the non-clearing polys */
991 r_search (Layer
->polygon_tree
, screen
, NULL
, poly_callback
, &info
);
993 if (TEST_FLAG (CHECKPLANESFLAG
, PCB
))
996 /* draw all visible lines this layer */
997 r_search (Layer
->line_tree
, screen
, NULL
, line_callback
, Layer
);
999 /* draw the layer arcs on screen */
1000 r_search (Layer
->arc_tree
, screen
, NULL
, arc_callback
, Layer
);
1002 /* draw the layer text on screen */
1003 r_search (Layer
->text_tree
, screen
, NULL
, text_callback
, Layer
);
1005 /* We should check for gui->gui here, but it's kinda cool seeing the
1006 auto-outline magically disappear when you first add something to
1007 the "outline" layer. */
1008 if (IsLayerEmpty (Layer
)
1009 && (strcmp (Layer
->Name
, "outline") == 0
1010 || strcmp (Layer
->Name
, "route") == 0))
1012 gui
->graphics
->set_color (Output
.fgGC
, Layer
->Color
);
1013 gui
->graphics
->set_line_width (Output
.fgGC
, PCB
->minWid
);
1014 gui
->graphics
->draw_rect (Output
.fgGC
,
1016 PCB
->MaxWidth
, PCB
->MaxHeight
);
1020 /* ---------------------------------------------------------------------------
1021 * draws one layer group. If the exporter is not a GUI,
1022 * also draws the pins / pads / vias in this layer group.
1025 DrawLayerGroup (int group
, const BoxType
*drawn_area
)
1030 int n_entries
= PCB
->LayerGroups
.Number
[group
];
1031 Cardinal
*layers
= PCB
->LayerGroups
.Entries
[group
];
1033 for (i
= n_entries
- 1; i
>= 0; i
--)
1035 layernum
= layers
[i
];
1036 Layer
= PCB
->Data
->Layer
+ layers
[i
];
1037 if (strcmp (Layer
->Name
, "outline") == 0 ||
1038 strcmp (Layer
->Name
, "route") == 0)
1040 if (layernum
< max_copper_layer
&& Layer
->On
)
1041 DrawLayer (Layer
, drawn_area
);
1046 if (rv
&& !gui
->gui
)
1047 DrawPPV (group
, drawn_area
);
1051 GatherPVName (PinType
*Ptr
)
1054 bool vert
= TEST_FLAG (EDGE2FLAG
, Ptr
);
1058 box
.X1
= Ptr
->X
- Ptr
->Thickness
/ 2 + Settings
.PinoutTextOffsetY
;
1059 box
.Y1
= Ptr
->Y
- Ptr
->DrillingHole
/ 2 - Settings
.PinoutTextOffsetX
;
1063 box
.X1
= Ptr
->X
+ Ptr
->DrillingHole
/ 2 + Settings
.PinoutTextOffsetX
;
1064 box
.Y1
= Ptr
->Y
- Ptr
->Thickness
/ 2 + Settings
.PinoutTextOffsetY
;
1081 GatherPadName (PadType
*Pad
)
1086 /* should text be vertical ? */
1087 vert
= (Pad
->Point1
.X
== Pad
->Point2
.X
);
1091 box
.X1
= Pad
->Point1
.X
- Pad
->Thickness
/ 2;
1092 box
.Y1
= MAX (Pad
->Point1
.Y
, Pad
->Point2
.Y
) + Pad
->Thickness
/ 2;
1093 box
.X1
+= Settings
.PinoutTextOffsetY
;
1094 box
.Y1
-= Settings
.PinoutTextOffsetX
;
1100 box
.X1
= MIN (Pad
->Point1
.X
, Pad
->Point2
.X
) - Pad
->Thickness
/ 2;
1101 box
.Y1
= Pad
->Point1
.Y
- Pad
->Thickness
/ 2;
1102 box
.X1
+= Settings
.PinoutTextOffsetX
;
1103 box
.Y1
+= Settings
.PinoutTextOffsetY
;
1112 /* ---------------------------------------------------------------------------
1113 * lowlevel drawing routine for text objects
1116 DrawTextLowLevel (hidGC gc
, TextType
*Text
, Coord min_line_width
)
1119 unsigned char *string
= (unsigned char *) Text
->TextString
;
1121 FontType
*font
= &PCB
->Font
;
1123 while (string
&& *string
)
1125 /* draw lines if symbol is valid and data is present */
1126 if (*string
<= MAX_FONTPOSITION
&& font
->Symbol
[*string
].Valid
)
1128 LineType
*line
= font
->Symbol
[*string
].Line
;
1131 for (n
= font
->Symbol
[*string
].LineN
; n
; n
--, line
++)
1133 /* create one line, scale, move, rotate and swap it */
1135 newline
.Point1
.X
= SCALE_TEXT (newline
.Point1
.X
+ x
, Text
->Scale
);
1136 newline
.Point1
.Y
= SCALE_TEXT (newline
.Point1
.Y
, Text
->Scale
);
1137 newline
.Point2
.X
= SCALE_TEXT (newline
.Point2
.X
+ x
, Text
->Scale
);
1138 newline
.Point2
.Y
= SCALE_TEXT (newline
.Point2
.Y
, Text
->Scale
);
1139 newline
.Thickness
= SCALE_TEXT (newline
.Thickness
, Text
->Scale
/ 2);
1140 if (newline
.Thickness
< min_line_width
)
1141 newline
.Thickness
= min_line_width
;
1143 RotateLineLowLevel (&newline
, 0, 0, Text
->Direction
);
1145 /* the labels of SMD objects on the bottom
1146 * side haven't been swapped yet, only their offset
1148 if (TEST_FLAG (ONSOLDERFLAG
, Text
))
1150 newline
.Point1
.X
= SWAP_SIGN_X (newline
.Point1
.X
);
1151 newline
.Point1
.Y
= SWAP_SIGN_Y (newline
.Point1
.Y
);
1152 newline
.Point2
.X
= SWAP_SIGN_X (newline
.Point2
.X
);
1153 newline
.Point2
.Y
= SWAP_SIGN_Y (newline
.Point2
.Y
);
1155 /* add offset and draw line */
1156 newline
.Point1
.X
+= Text
->X
;
1157 newline
.Point1
.Y
+= Text
->Y
;
1158 newline
.Point2
.X
+= Text
->X
;
1159 newline
.Point2
.Y
+= Text
->Y
;
1160 gui
->graphics
->draw_pcb_line (gc
, &newline
);
1163 /* move on to next cursor position */
1164 x
+= (font
->Symbol
[*string
].Width
+ font
->Symbol
[*string
].Delta
);
1168 /* the default symbol is a filled box */
1169 BoxType defaultsymbol
= PCB
->Font
.DefaultSymbol
;
1170 Coord size
= (defaultsymbol
.X2
- defaultsymbol
.X1
) * 6 / 5;
1172 defaultsymbol
.X1
= SCALE_TEXT (defaultsymbol
.X1
+ x
, Text
->Scale
);
1173 defaultsymbol
.Y1
= SCALE_TEXT (defaultsymbol
.Y1
, Text
->Scale
);
1174 defaultsymbol
.X2
= SCALE_TEXT (defaultsymbol
.X2
+ x
, Text
->Scale
);
1175 defaultsymbol
.Y2
= SCALE_TEXT (defaultsymbol
.Y2
, Text
->Scale
);
1177 RotateBoxLowLevel (&defaultsymbol
, 0, 0, Text
->Direction
);
1179 /* add offset and draw box */
1180 defaultsymbol
.X1
+= Text
->X
;
1181 defaultsymbol
.Y1
+= Text
->Y
;
1182 defaultsymbol
.X2
+= Text
->X
;
1183 defaultsymbol
.Y2
+= Text
->Y
;
1184 gui
->graphics
->fill_rect (gc
,
1185 defaultsymbol
.X1
, defaultsymbol
.Y1
,
1186 defaultsymbol
.X2
, defaultsymbol
.Y2
);
1188 /* move on to next cursor position */
1195 /* ---------------------------------------------------------------------------
1199 DrawVia (PinType
*Via
)
1202 if (!TEST_FLAG (HOLEFLAG
, Via
) && TEST_FLAG (DISPLAYNAMEFLAG
, Via
))
1206 /* ---------------------------------------------------------------------------
1207 * draws the name of a via
1210 DrawViaName (PinType
*Via
)
1215 /* ---------------------------------------------------------------------------
1219 DrawPin (PinType
*Pin
)
1222 if ((!TEST_FLAG (HOLEFLAG
, Pin
) && TEST_FLAG (DISPLAYNAMEFLAG
, Pin
))
1227 /* ---------------------------------------------------------------------------
1228 * draws the name of a pin
1231 DrawPinName (PinType
*Pin
)
1236 /* ---------------------------------------------------------------------------
1240 DrawPad (PadType
*Pad
)
1243 if (doing_pinout
|| TEST_FLAG (DISPLAYNAMEFLAG
, Pad
))
1247 /* ---------------------------------------------------------------------------
1248 * draws the name of a pad
1251 DrawPadName (PadType
*Pad
)
1253 GatherPadName (Pad
);
1256 /* ---------------------------------------------------------------------------
1257 * draws a line on a layer
1260 DrawLine (LayerType
*Layer
, LineType
*Line
)
1265 /* ---------------------------------------------------------------------------
1269 DrawRat (RatType
*Rat
)
1271 if (Settings
.RatThickness
< 100)
1272 Rat
->Thickness
= pixel_slop
* Settings
.RatThickness
;
1273 /* rats.c set VIAFLAG if this rat goes to a containing poly: draw a donut */
1274 if (TEST_FLAG(VIAFLAG
, Rat
))
1276 Coord w
= Rat
->Thickness
;
1280 b
.X1
= Rat
->Point1
.X
- w
* 2 - w
/ 2;
1281 b
.X2
= Rat
->Point1
.X
+ w
* 2 + w
/ 2;
1282 b
.Y1
= Rat
->Point1
.Y
- w
* 2 - w
/ 2;
1283 b
.Y2
= Rat
->Point1
.Y
+ w
* 2 + w
/ 2;
1287 DrawLine (NULL
, (LineType
*)Rat
);
1290 /* ---------------------------------------------------------------------------
1291 * draws an arc on a layer
1294 DrawArc (LayerType
*Layer
, ArcType
*Arc
)
1299 /* ---------------------------------------------------------------------------
1300 * draws a text on a layer
1303 DrawText (LayerType
*Layer
, TextType
*Text
)
1309 /* ---------------------------------------------------------------------------
1310 * draws a polygon on a layer
1313 DrawPolygon (LayerType
*Layer
, PolygonType
*Polygon
)
1318 /* ---------------------------------------------------------------------------
1322 DrawElement (ElementType
*Element
)
1324 DrawElementPackage (Element
);
1325 DrawElementName (Element
);
1326 DrawElementPinsAndPads (Element
);
1329 /* ---------------------------------------------------------------------------
1330 * draws the name of an element
1333 DrawElementName (ElementType
*Element
)
1335 if (TEST_FLAG (HIDENAMEFLAG
, Element
))
1337 DrawText (NULL
, &ELEMENT_TEXT (PCB
, Element
));
1340 /* ---------------------------------------------------------------------------
1341 * draws the package of an element
1344 DrawElementPackage (ElementType
*Element
)
1346 ELEMENTLINE_LOOP (Element
);
1348 DrawLine (NULL
, line
);
1353 DrawArc (NULL
, arc
);
1358 /* ---------------------------------------------------------------------------
1359 * draw pins of an element
1362 DrawElementPinsAndPads (ElementType
*Element
)
1366 if (doing_pinout
|| doing_assy
|| FRONT (pad
) || PCB
->InvisibleObjectsOn
)
1377 /* ---------------------------------------------------------------------------
1381 EraseVia (PinType
*Via
)
1384 if (TEST_FLAG (DISPLAYNAMEFLAG
, Via
))
1388 /* ---------------------------------------------------------------------------
1392 EraseRat (RatType
*Rat
)
1394 if (TEST_FLAG(VIAFLAG
, Rat
))
1396 Coord w
= Rat
->Thickness
;
1400 b
.X1
= Rat
->Point1
.X
- w
* 2 - w
/ 2;
1401 b
.X2
= Rat
->Point1
.X
+ w
* 2 + w
/ 2;
1402 b
.Y1
= Rat
->Point1
.Y
- w
* 2 - w
/ 2;
1403 b
.Y2
= Rat
->Point1
.Y
+ w
* 2 + w
/ 2;
1407 EraseLine ((LineType
*)Rat
);
1411 /* ---------------------------------------------------------------------------
1415 EraseViaName (PinType
*Via
)
1420 /* ---------------------------------------------------------------------------
1421 * erase a pad object
1424 ErasePad (PadType
*Pad
)
1427 if (TEST_FLAG (DISPLAYNAMEFLAG
, Pad
))
1431 /* ---------------------------------------------------------------------------
1435 ErasePadName (PadType
*Pad
)
1437 GatherPadName (Pad
);
1440 /* ---------------------------------------------------------------------------
1441 * erase a pin object
1444 ErasePin (PinType
*Pin
)
1447 if (TEST_FLAG (DISPLAYNAMEFLAG
, Pin
))
1451 /* ---------------------------------------------------------------------------
1455 ErasePinName (PinType
*Pin
)
1460 /* ---------------------------------------------------------------------------
1461 * erases a line on a layer
1464 EraseLine (LineType
*Line
)
1469 /* ---------------------------------------------------------------------------
1470 * erases an arc on a layer
1473 EraseArc (ArcType
*Arc
)
1475 if (!Arc
->Thickness
)
1480 /* ---------------------------------------------------------------------------
1481 * erases a text on a layer
1484 EraseText (LayerType
*Layer
, TextType
*Text
)
1489 /* ---------------------------------------------------------------------------
1490 * erases a polygon on a layer
1493 ErasePolygon (PolygonType
*Polygon
)
1498 /* ---------------------------------------------------------------------------
1502 EraseElement (ElementType
*Element
)
1504 ELEMENTLINE_LOOP (Element
);
1514 EraseElementName (Element
);
1515 EraseElementPinsAndPads (Element
);
1518 /* ---------------------------------------------------------------------------
1519 * erases all pins and pads of an element
1522 EraseElementPinsAndPads (ElementType
*Element
)
1536 /* ---------------------------------------------------------------------------
1537 * erases the name of an element
1540 EraseElementName (ElementType
*Element
)
1542 if (TEST_FLAG (HIDENAMEFLAG
, Element
))
1544 DrawText (NULL
, &ELEMENT_TEXT (PCB
, Element
));
1549 EraseObject (int type
, void *lptr
, void *ptr
)
1555 ErasePin ((PinType
*) ptr
);
1558 case ELEMENTNAME_TYPE
:
1559 EraseText ((LayerType
*)lptr
, (TextType
*) ptr
);
1562 ErasePolygon ((PolygonType
*) ptr
);
1565 EraseElement ((ElementType
*) ptr
);
1568 case ELEMENTLINE_TYPE
:
1570 EraseLine ((LineType
*) ptr
);
1573 ErasePad ((PadType
*) ptr
);
1576 case ELEMENTARC_TYPE
:
1577 EraseArc ((ArcType
*) ptr
);
1580 Message ("hace: Internal ERROR, trying to erase an unknown type\n");
1587 DrawObject (int type
, void *ptr1
, void *ptr2
)
1593 DrawVia ((PinType
*) ptr2
);
1596 if (((LayerType
*) ptr1
)->On
)
1597 DrawLine ((LayerType
*) ptr1
, (LineType
*) ptr2
);
1600 if (((LayerType
*) ptr1
)->On
)
1601 DrawArc ((LayerType
*) ptr1
, (ArcType
*) ptr2
);
1604 if (((LayerType
*) ptr1
)->On
)
1605 DrawText ((LayerType
*) ptr1
, (TextType
*) ptr2
);
1608 if (((LayerType
*) ptr1
)->On
)
1609 DrawPolygon ((LayerType
*) ptr1
, (PolygonType
*) ptr2
);
1612 if (PCB
->ElementOn
&&
1613 (FRONT ((ElementType
*) ptr2
) || PCB
->InvisibleObjectsOn
))
1614 DrawElement ((ElementType
*) ptr2
);
1618 DrawRat ((RatType
*) ptr2
);
1622 DrawPin ((PinType
*) ptr2
);
1626 DrawPad ((PadType
*) ptr2
);
1628 case ELEMENTNAME_TYPE
:
1629 if (PCB
->ElementOn
&&
1630 (FRONT ((ElementType
*) ptr2
) || PCB
->InvisibleObjectsOn
))
1631 DrawElementName ((ElementType
*) ptr1
);
1637 draw_element (ElementType
*element
)
1639 draw_element_package (element
);
1640 draw_element_name (element
);
1641 draw_element_pins_and_pads (element
);
1644 /* ---------------------------------------------------------------------------
1645 * HID drawing callback.
1649 hid_expose_callback (HID
* hid
, BoxType
* region
, void *item
)
1654 Output
.fgGC
= gui
->graphics
->make_gc ();
1655 Output
.bgGC
= gui
->graphics
->make_gc ();
1656 Output
.pmGC
= gui
->graphics
->make_gc ();
1658 hid
->graphics
->set_color (Output
.pmGC
, "erase");
1659 hid
->graphics
->set_color (Output
.bgGC
, "drill");
1663 doing_pinout
= true;
1664 draw_element ((ElementType
*)item
);
1665 doing_pinout
= false;
1668 DrawEverything (region
);
1670 gui
->graphics
->destroy_gc (Output
.fgGC
);
1671 gui
->graphics
->destroy_gc (Output
.bgGC
);
1672 gui
->graphics
->destroy_gc (Output
.pmGC
);