6 * PCB, interactive printed circuit board design
7 * Copyright (C) 1994,1995,1996,1997,1998,1999 Thomas Nau
9 * This module, report.c, was written and is Copyright (C) 1997 harry eaton
11 * This program is free software; you can redistribute it and/or modify
12 * it under the terms of the GNU General Public License as published by
13 * the Free Software Foundation; either version 2 of the License, or
14 * (at your option) any later version.
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU General Public License for more details.
21 * You should have received a copy of the GNU General Public License
22 * along with this program; if not, write to the Free Software
23 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
25 * Contact addresses for paper mail and Email:
26 * Thomas Nau, Schlehenweg 15, 88471 Baustetten, Germany
27 * Thomas.Nau@rz.uni-ulm.de
39 #include "crosshair.h"
52 #ifdef HAVE_LIBDMALLOC
59 #define UNIT1(value) (Settings.grid_units_mm ? ((value) / 100000.0 * 25.4) : ((value) / 100.0))
60 #define UNIT(value) UNIT1(value) , (Settings.grid_units_mm ? "mm" : "mils")
63 ReportDrills (int argc
, char **argv
, int x
, int y
)
65 DrillInfoTypePtr AllDrills
;
67 char *stringlist
, *thestring
;
70 AllDrills
= GetDrillInfo (PCB
->Data
);
71 RoundDrillInfo (AllDrills
, 100);
73 for (n
= 0; n
< AllDrills
->DrillN
; n
++)
75 total_drills
+= AllDrills
->Drill
[n
].PinCount
;
76 total_drills
+= AllDrills
->Drill
[n
].ViaCount
;
77 total_drills
+= AllDrills
->Drill
[n
].UnplatedCount
;
80 stringlist
= malloc (512L + AllDrills
->DrillN
* 64L);
82 /* Use tabs for formatting since can't count on a fixed font anymore.
83 | And even that probably isn't going to work in all cases.
86 "There are %d different drill sizes used in this layout, %d holes total\n\n"
87 "Drill Diam. (mils)\t# of Pins\t# of Vias\t# of Elements\t# Unplated\n",
88 AllDrills
->DrillN
, total_drills
);
89 thestring
= stringlist
;
90 while (*thestring
!= '\0')
92 for (n
= 0; n
< AllDrills
->DrillN
; n
++)
95 "\t%d\t\t\t%d\t\t%d\t\t%d\t\t%d\n",
96 (AllDrills
->Drill
[n
].DrillSize
+50) / 100,
97 AllDrills
->Drill
[n
].PinCount
, AllDrills
->Drill
[n
].ViaCount
,
98 AllDrills
->Drill
[n
].ElementN
,
99 AllDrills
->Drill
[n
].UnplatedCount
);
100 while (*thestring
!= '\0')
103 FreeDrillInfo (AllDrills
);
104 /* create dialog box */
105 gui
->report_dialog ("Drill Report", stringlist
);
107 SaveFree (stringlist
);
112 static const char reportdialog_syntax
[] = "ReportDialog()";
114 static const char reportdialog_help
[] =
115 "Report on the object under the crosshair";
117 /* %start-doc actions ReportDialog
119 This is a shortcut for @code{Report(Object)}.
124 ReportDialog (int argc
, char **argv
, int x
, int y
)
126 void *ptr1
, *ptr2
, *ptr3
;
130 type
= SearchScreen (x
, y
, REPORT_TYPES
, &ptr1
, &ptr2
, &ptr3
);
133 SearchScreen (x
, y
, REPORT_TYPES
| LOCKED_TYPE
, &ptr1
, &ptr2
, &ptr3
);
141 if (gui
->shift_is_pressed ())
143 __r_dump_tree (PCB
->Data
->via_tree
->root
, 0);
147 via
= (PinTypePtr
) ptr2
;
148 if (TEST_FLAG (HOLEFLAG
, via
))
149 sprintf (&report
[0], "VIA ID# %ld Flags:%s\n"
151 "It is a pure hole of diameter %0.2f %s\n"
153 "%s", via
->ID
, flags_to_string (via
->Flags
, VIA_TYPE
),
154 via
->X
, via
->Y
, UNIT (via
->DrillingHole
),
155 EMPTY (via
->Name
), TEST_FLAG (LOCKFLAG
,
156 via
) ? "It is LOCKED\n" :
159 sprintf (&report
[0], "VIA ID# %ld Flags:%s\n"
161 "Copper width = %0.2f %s Drill width = %0.2f %s\n"
162 "Clearance width in polygons = %0.2f %s\n"
163 "Annulus = %0.2f %s\n"
164 "Solder mask hole = %0.2f %s (gap = %0.2f %s)\n"
166 "%s", via
->ID
, flags_to_string (via
->Flags
, VIA_TYPE
),
167 via
->X
, via
->Y
, UNIT (via
->Thickness
),
168 UNIT (via
->DrillingHole
), UNIT (via
->Clearance
/ 2.),
169 UNIT ((via
->Thickness
- via
->DrillingHole
)/2),
170 UNIT (via
->Mask
), UNIT ((via
->Mask
- via
->Thickness
)/2),
171 EMPTY (via
->Name
), TEST_FLAG (LOCKFLAG
, via
) ?
172 "It is LOCKED\n" : "");
178 ElementTypePtr element
;
180 if (gui
->shift_is_pressed ())
182 __r_dump_tree (PCB
->Data
->pin_tree
->root
, 0);
186 Pin
= (PinTypePtr
) ptr2
;
187 element
= (ElementTypePtr
) ptr1
;
195 if (TEST_FLAG (HOLEFLAG
, Pin
))
196 sprintf (&report
[0], "PIN ID# %ld Flags:%s\n"
198 "It is a mounting hole, Drill width = %0.2f %s\n"
199 "It is owned by element %s\n"
200 "%s", Pin
->ID
, flags_to_string (Pin
->Flags
, PIN_TYPE
),
201 Pin
->X
, Pin
->Y
, UNIT (Pin
->DrillingHole
),
202 EMPTY (element
->Name
[1].TextString
),
203 TEST_FLAG (LOCKFLAG
, Pin
) ? "It is LOCKED\n" : "");
206 "PIN ID# %ld Flags:%s\n" "(X,Y) = (%d, %d)\n"
207 "Copper width = %0.2f %s Drill width = %0.2f %s\n"
208 "Clearance width to Polygon = %0.2f %s\n"
209 "Annulus = %0.2f %s\n"
210 "Solder mask hole = %0.2f %s (gap = %0.2f %s)\n"
212 "It is owned by element %s\n" "As pin number %s\n"
214 Pin
->ID
, flags_to_string (Pin
->Flags
, PIN_TYPE
),
215 Pin
->X
, Pin
->Y
, UNIT (Pin
->Thickness
),
216 UNIT (Pin
->DrillingHole
), UNIT (Pin
->Clearance
/ 2.),
217 UNIT ((Pin
->Thickness
- Pin
->DrillingHole
)/2),
218 UNIT (Pin
->Mask
), UNIT ((Pin
->Mask
- Pin
->Thickness
)/2),
220 EMPTY (element
->Name
[1].TextString
), EMPTY (Pin
->Number
),
221 TEST_FLAG (LOCKFLAG
, Pin
) ? "It is LOCKED\n" : "");
228 if (gui
->shift_is_pressed ())
230 LayerTypePtr layer
= (LayerTypePtr
) ptr1
;
231 __r_dump_tree (layer
->line_tree
->root
, 0);
235 line
= (LineTypePtr
) ptr2
;
236 sprintf (&report
[0], "LINE ID# %ld Flags:%s\n"
237 "FirstPoint(X,Y) = (%d, %d) ID = %ld\n"
238 "SecondPoint(X,Y) = (%d, %d) ID = %ld\n"
239 "Width = %0.2f %s.\nClearance width in polygons = %0.2f %s.\n"
240 "It is on layer %d\n"
243 line
->ID
, flags_to_string (line
->Flags
, LINE_TYPE
),
244 line
->Point1
.X
, line
->Point1
.Y
,
245 line
->Point1
.ID
, line
->Point2
.X
, line
->Point2
.Y
,
246 line
->Point2
.ID
, UNIT (line
->Thickness
),
247 UNIT (line
->Clearance
/ 2.), GetLayerNumber (PCB
->Data
,
248 (LayerTypePtr
) ptr1
),
249 UNKNOWN (line
->Number
), TEST_FLAG (LOCKFLAG
,
250 line
) ? "It is LOCKED\n" :
258 if (gui
->shift_is_pressed ())
260 __r_dump_tree (PCB
->Data
->rat_tree
->root
, 0);
264 line
= (RatTypePtr
) ptr2
;
265 sprintf (&report
[0], "RAT-LINE ID# %ld Flags:%s\n"
266 "FirstPoint(X,Y) = (%d, %d) ID = %ld "
267 "connects to layer group %d\n"
268 "SecondPoint(X,Y) = (%d, %d) ID = %ld "
269 "connects to layer group %d\n",
270 line
->ID
, flags_to_string (line
->Flags
, LINE_TYPE
),
271 line
->Point1
.X
, line
->Point1
.Y
,
272 line
->Point1
.ID
, line
->group1
,
273 line
->Point2
.X
, line
->Point2
.Y
,
274 line
->Point2
.ID
, line
->group2
);
282 if (gui
->shift_is_pressed ())
284 LayerTypePtr layer
= (LayerTypePtr
) ptr1
;
285 __r_dump_tree (layer
->arc_tree
->root
, 0);
289 Arc
= (ArcTypePtr
) ptr2
;
290 box
= GetArcEnds (Arc
);
292 sprintf (&report
[0], "ARC ID# %ld Flags:%s\n"
293 "CenterPoint(X,Y) = (%d, %d)\n"
294 "Radius = %0.2f %s, Thickness = %0.2f %s\n"
295 "Clearance width in polygons = %0.2f %s\n"
296 "StartAngle = %ld degrees, DeltaAngle = %ld degrees\n"
297 "Bounding Box is (%d,%d), (%d,%d)\n"
298 "That makes the end points at (%d,%d) and (%d,%d)\n"
299 "It is on layer %d\n"
300 "%s", Arc
->ID
, flags_to_string (Arc
->Flags
, ARC_TYPE
),
301 Arc
->X
, Arc
->Y
, UNIT (Arc
->Width
), UNIT (Arc
->Thickness
),
302 UNIT (Arc
->Clearance
/ 2.), Arc
->StartAngle
, Arc
->Delta
,
303 Arc
->BoundingBox
.X1
, Arc
->BoundingBox
.Y1
,
304 Arc
->BoundingBox
.X2
, Arc
->BoundingBox
.Y2
, box
->X1
,
305 box
->Y1
, box
->X2
, box
->Y2
, GetLayerNumber (PCB
->Data
,
308 TEST_FLAG (LOCKFLAG
, Arc
) ? "It is LOCKED\n" : "");
313 PolygonTypePtr Polygon
;
315 if (gui
->shift_is_pressed ())
317 LayerTypePtr layer
= (LayerTypePtr
) ptr1
;
318 __r_dump_tree (layer
->polygon_tree
->root
, 0);
322 Polygon
= (PolygonTypePtr
) ptr2
;
324 sprintf (&report
[0], "POLYGON ID# %ld Flags:%s\n"
325 "Its bounding box is (%d,%d) (%d,%d)\n"
326 "It has %d points and could store %d more\n"
327 "without using more memory.\n"
328 "It resides on layer %d\n"
330 flags_to_string (Polygon
->Flags
, POLYGON_TYPE
),
331 Polygon
->BoundingBox
.X1
, Polygon
->BoundingBox
.Y1
,
332 Polygon
->BoundingBox
.X2
, Polygon
->BoundingBox
.Y2
,
333 Polygon
->PointN
, Polygon
->PointMax
- Polygon
->PointN
,
334 GetLayerNumber (PCB
->Data
, (LayerTypePtr
) ptr1
),
335 TEST_FLAG (LOCKFLAG
, Polygon
) ? "It is LOCKED\n" : "");
340 int len
, dx
, dy
, mgap
;
342 ElementTypePtr element
;
344 if (gui
->shift_is_pressed ())
346 __r_dump_tree (PCB
->Data
->pad_tree
->root
, 0);
350 Pad
= (PadTypePtr
) ptr2
;
351 element
= (ElementTypePtr
) ptr1
;
361 dx
= Pad
->Point1
.X
- Pad
->Point2
.X
;
362 dy
= Pad
->Point1
.Y
- Pad
->Point2
.Y
;
363 len
= sqrt (dx
*dx
+dy
*dy
);
364 mgap
= (Pad
->Mask
- Pad
->Thickness
)/2;
365 sprintf (&report
[0], "PAD ID# %ld Flags:%s\n"
366 "FirstPoint(X,Y) = (%d, %d) ID = %ld\n"
367 "SecondPoint(X,Y) = (%d, %d) ID = %ld\n"
368 "Width = %0.2f %s. Length = %0.2f %s.\n"
369 "Clearance width in polygons = %0.2f %s.\n"
370 "Solder mask = %0.2f x %0.2f %s (gap = %0.2f %s).\n"
372 "It is owned by SMD element %s\n"
373 "As pin number %s and is on the %s\n"
374 "side of the board.\n"
376 flags_to_string (Pad
->Flags
, PAD_TYPE
),
377 Pad
->Point1
.X
, Pad
->Point1
.Y
, Pad
->Point1
.ID
,
378 Pad
->Point2
.X
, Pad
->Point2
.Y
, Pad
->Point2
.ID
,
379 UNIT (Pad
->Thickness
), UNIT (len
+ Pad
->Thickness
),
380 UNIT (Pad
->Clearance
/ 2.),
381 UNIT1 (Pad
->Mask
), UNIT (Pad
->Mask
+ len
), UNIT (mgap
),
383 EMPTY (element
->Name
[1].TextString
),
385 TEST_FLAG (ONSOLDERFLAG
,
386 Pad
) ? "solder (bottom)" : "component",
387 TEST_FLAG (LOCKFLAG
, Pad
) ? "It is LOCKED\n" : "");
392 ElementTypePtr element
;
394 if (gui
->shift_is_pressed ())
396 __r_dump_tree (PCB
->Data
->element_tree
->root
, 0);
400 element
= (ElementTypePtr
) ptr2
;
401 sprintf (&report
[0], "ELEMENT ID# %ld Flags:%s\n"
402 "BoundingBox (%d,%d) (%d,%d)\n"
403 "Descriptive Name \"%s\"\n"
404 "Name on board \"%s\"\n"
405 "Part number name \"%s\"\n"
406 "It is %0.2f %s tall and is located at (X,Y) = (%d,%d)\n"
408 "Mark located at point (X,Y) = (%d,%d)\n"
409 "It is on the %s side of the board.\n"
411 element
->ID
, flags_to_string (element
->Flags
, ELEMENT_TYPE
),
412 element
->BoundingBox
.X1
, element
->BoundingBox
.Y1
,
413 element
->BoundingBox
.X2
, element
->BoundingBox
.Y2
,
414 EMPTY (element
->Name
[0].TextString
),
415 EMPTY (element
->Name
[1].TextString
),
416 EMPTY (element
->Name
[2].TextString
),
417 UNIT (0.45 * element
->Name
[1].Scale
* 100.), element
->Name
[1].X
,
418 element
->Name
[1].Y
, TEST_FLAG (HIDENAMEFLAG
, element
) ?
419 "But it's hidden\n" : "", element
->MarkX
,
420 element
->MarkY
, TEST_FLAG (ONSOLDERFLAG
,
421 element
) ? "solder (bottom)" :
422 "component", TEST_FLAG (LOCKFLAG
, element
) ?
423 "It is LOCKED\n" : "");
428 if (gui
->shift_is_pressed ())
430 LayerTypePtr layer
= (LayerTypePtr
) ptr1
;
431 __r_dump_tree (layer
->text_tree
->root
, 0);
435 case ELEMENTNAME_TYPE
:
440 if (gui
->shift_is_pressed ())
442 __r_dump_tree (PCB
->Data
->name_tree
[NAME_INDEX (PCB
)]->root
, 0);
446 text
= (TextTypePtr
) ptr2
;
448 if (type
== TEXT_TYPE
)
449 sprintf (laynum
, "is on layer %d",
450 GetLayerNumber (PCB
->Data
, (LayerTypePtr
) ptr1
));
451 sprintf (&report
[0], "TEXT ID# %ld Flags:%s\n"
452 "Located at (X,Y) = (%d,%d)\n"
453 "Characters are %0.2f %s tall\n"
456 "The bounding box is (%d,%d) (%d, %d)\n"
458 "%s", text
->ID
, flags_to_string (text
->Flags
, TEXT_TYPE
),
459 text
->X
, text
->Y
, UNIT (0.45 * text
->Scale
* 100.),
460 text
->TextString
, text
->Direction
,
461 text
->BoundingBox
.X1
, text
->BoundingBox
.Y1
,
462 text
->BoundingBox
.X2
, text
->BoundingBox
.Y2
,
463 (type
== TEXT_TYPE
) ? laynum
: "is an element name.",
464 TEST_FLAG (LOCKFLAG
, text
) ? "It is LOCKED\n" : "");
468 case POLYGONPOINT_TYPE
:
470 PointTypePtr point
= (PointTypePtr
) ptr2
;
471 sprintf (&report
[0], "POINT ID# %ld. Points don't have flags.\n"
472 "Located at (X,Y) = (%d,%d)\n"
473 "It belongs to a %s on layer %d\n", point
->ID
,
475 (type
== LINEPOINT_TYPE
) ? "line" : "polygon",
476 GetLayerNumber (PCB
->Data
, (LayerTypePtr
) ptr1
));
484 sprintf (&report
[0], "Unknown\n");
488 if (report
[0] == '\0')
490 Message (_("Nothing found to report on\n"));
493 HideCrosshair (False
);
494 /* create dialog box */
495 gui
->report_dialog ("Report", &report
[0]);
497 RestoreCrosshair (False
);
502 ReportFoundPins (int argc
, char **argv
, int x
, int y
)
504 static DynamicStringType list
;
508 DSClearString (&list
);
509 DSAddString (&list
, "The following pins/pads are FOUND:\n");
510 ELEMENT_LOOP (PCB
->Data
);
514 if (TEST_FLAG (FOUNDFLAG
, pin
))
516 sprintf (temp
, "%s-%s,%c",
517 NAMEONPCB_NAME (element
),
519 ((col
++ % (COLUMNS
+ 1)) == COLUMNS
) ? '\n' : ' ');
520 DSAddString (&list
, temp
);
526 if (TEST_FLAG (FOUNDFLAG
, pad
))
528 sprintf (temp
, "%s-%s,%c",
529 NAMEONPCB_NAME (element
), pad
->Number
,
530 ((col
++ % (COLUMNS
+ 1)) == COLUMNS
) ? '\n' : ' ');
531 DSAddString (&list
, temp
);
538 HideCrosshair (False
);
539 gui
->report_dialog ("Report", list
.Data
);
540 RestoreCrosshair (False
);
545 XYtoNetLength (int x
, int y
, int *found
)
551 LookupConnection (x
, y
, True
, PCB
->Grid
, FOUNDFLAG
);
553 ALLLINE_LOOP (PCB
->Data
);
555 if (TEST_FLAG (FOUNDFLAG
, line
))
559 dx
= line
->Point1
.X
- line
->Point2
.X
;
560 dy
= line
->Point1
.Y
- line
->Point2
.Y
;
561 l
= sqrt ((double)dx
*dx
+ (double)dy
*dy
);
568 ALLARC_LOOP (PCB
->Data
);
570 if (TEST_FLAG (FOUNDFLAG
, arc
))
573 /* FIXME: we assume width==height here */
574 l
= M_PI
* 2*arc
->Width
* abs(arc
->Delta
)/360.0;
585 ReportAllNetLengths (int argc
, char **argv
, int x
, int y
)
587 enum { Upcb
, Umm
, Umil
, Uin
} units
;
592 units
= Settings
.grid_units_mm
? Umm
: Umil
;
596 printf("Units: %s\n", argv
[0]);
597 if (strcasecmp (argv
[0], "mm") == 0)
599 else if (strcasecmp (argv
[0], "mil") == 0)
601 else if (strcasecmp (argv
[0], "in") == 0)
607 for (ni
= 0; ni
< PCB
->NetlistLib
.MenuN
; ni
++)
609 char *netname
= PCB
->NetlistLib
.Menu
[ni
].Name
+ 2;
610 char *ename
= PCB
->NetlistLib
.Menu
[ni
].Entry
[0].ListEntry
;
613 ename
= strdup (ename
);
614 pname
= strchr (ename
, '-');
622 ELEMENT_LOOP (PCB
->Data
);
624 char *es
= element
->Name
[NAMEONPCB_INDEX
].TextString
;
625 if (es
&& strcmp (es
, ename
) == 0)
629 if (strcmp (pin
->Number
, pname
) == 0)
639 if (strcmp (pad
->Number
, pname
) == 0)
641 x
= (pad
->Point1
.X
+ pad
->Point2
.X
) / 2;
642 y
= (pad
->Point1
.Y
+ pad
->Point2
.Y
) / 2;
654 SaveUndoSerialNumber ();
655 ResetFoundPinsViasAndPads (True
);
656 RestoreUndoSerialNumber ();
657 ResetFoundLinesAndPolygons (True
);
658 RestoreUndoSerialNumber ();
659 length
= XYtoNetLength (x
, y
, &found
);
664 gui
->log("Net %s length %d\n", netname
, (int)length
);
667 length
*= COOR_TO_MM
;
668 gui
->log("Net %s length %.2f mm\n", netname
, length
);
672 gui
->log("Net %s length %d mil\n", netname
, (int)length
);
676 gui
->log("Net %s length %.3f in\n", netname
, length
);
683 ReportNetLength (int argc
, char **argv
, int x
, int y
)
689 SaveUndoSerialNumber ();
690 ResetFoundPinsViasAndPads (True
);
691 RestoreUndoSerialNumber ();
692 ResetFoundLinesAndPolygons (True
);
693 RestoreUndoSerialNumber ();
694 gui
->get_coords ("Click on a connection", &x
, &y
);
696 XYtoNetLength (x
, y
, &found
);
700 gui
->log ("No net under cursor.\n");
704 ELEMENT_LOOP (PCB
->Data
);
708 if (TEST_FLAG (FOUNDFLAG
, pin
))
711 char *ename
= element
->Name
[NAMEONPCB_INDEX
].TextString
;
712 char *pname
= pin
->Number
;
717 n
= Concat (ename
, "-", pname
, NULL
);
718 for (ni
= 0; ni
< PCB
->NetlistLib
.MenuN
; ni
++)
719 for (nei
= 0; nei
< PCB
->NetlistLib
.Menu
[ni
].EntryN
; nei
++)
721 if (strcmp (PCB
->NetlistLib
.Menu
[ni
].Entry
[nei
].ListEntry
, n
) == 0)
723 netname
= PCB
->NetlistLib
.Menu
[ni
].Name
+ 2;
724 goto got_net_name
; /* four for loops deep */
733 if (TEST_FLAG (FOUNDFLAG
, pad
))
736 char *ename
= element
->Name
[NAMEONPCB_INDEX
].TextString
;
737 char *pname
= pad
->Number
;
742 n
= Concat (ename
, "-", pname
, NULL
);
743 for (ni
= 0; ni
< PCB
->NetlistLib
.MenuN
; ni
++)
744 for (nei
= 0; nei
< PCB
->NetlistLib
.Menu
[ni
].EntryN
; nei
++)
746 if (strcmp (PCB
->NetlistLib
.Menu
[ni
].Entry
[nei
].ListEntry
, n
) == 0)
748 netname
= PCB
->NetlistLib
.Menu
[ni
].Name
+ 2;
749 goto got_net_name
; /* four for loops deep */
760 HideCrosshair (False
);
762 gui
->log ("Net %s length: %0.2f %s\n", netname
, UNIT (length
));
764 gui
->log ("Net length: %0.2f %s\n", UNIT (length
));
765 RestoreCrosshair (False
);
768 /* ---------------------------------------------------------------------------
769 * reports on an object
773 static const char report_syntax
[] = "Report(Object|DrillReport|FoundPins|NetLength|AllNetLengths)";
775 static const char report_help
[] = "Produce various report.";
777 /* %start-doc actions Report
782 The object under the crosshair will be reported, describing various
783 aspects of the object.
786 A report summarizing the number of drill sizes used, and how many of
787 each, will be produced.
790 A report listing all pins and pads which are marked as ``found'' will
794 The name and length of the net under the crosshair will be reported to
798 The name and length of the net under the crosshair will be reported to
799 the message log. An optional parameter specifies mm, mil, pcb, or in
807 Report (int argc
, char **argv
, int x
, int y
)
811 else if (strcasecmp (argv
[0], "Object") == 0)
813 gui
->get_coords ("Click on an object", &x
, &y
);
814 return ReportDialog (argc
- 1, argv
+ 1, x
, y
);
816 else if (strcasecmp (argv
[0], "DrillReport") == 0)
817 return ReportDrills (argc
- 1, argv
+ 1, x
, y
);
818 else if (strcasecmp (argv
[0], "FoundPins") == 0)
819 return ReportFoundPins (argc
- 1, argv
+ 1, x
, y
);
820 else if (strcasecmp (argv
[0], "NetLength") == 0)
821 return ReportNetLength (argc
- 1, argv
+ 1, x
, y
);
822 else if (strcasecmp (argv
[0], "AllNetLengths") == 0)
823 return ReportAllNetLengths (argc
- 1, argv
+ 1, x
, y
);
829 HID_Action report_action_list
[] = {
830 {"ReportObject", "Click on an object", ReportDialog
,
831 reportdialog_help
, reportdialog_syntax
}
833 {"Report", 0, Report
,
834 report_help
, report_syntax
}
837 REGISTER_ACTIONS (report_action_list
)