You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1705 lines
47 KiB

17 years ago
17 years ago
  1. /*****************/
  2. /* class_pin.cpp */
  3. /*****************/
  4. #include "fctsys.h"
  5. #include "appl_wxstruct.h"
  6. #include "gr_basic.h"
  7. #include "trigo.h"
  8. #include "common.h"
  9. #include "class_drawpanel.h"
  10. #include "drawtxt.h"
  11. #include "plot_common.h"
  12. #include "program.h"
  13. #include "general.h"
  14. #include "protos.h"
  15. #include "libeditfrm.h"
  16. #include "class_libentry.h"
  17. /**
  18. * Note: The following name lists are sentence capitalized per the GNOME UI
  19. * standards for list controls. Please do not change the capitalization
  20. * of these strings unless the GNOME UI standards are changed.
  21. */
  22. static const wxString pin_orientation_names[] =
  23. {
  24. _( "Right" ),
  25. _( "Left" ),
  26. _( "Up" ),
  27. _( "Down" )
  28. };
  29. static const int pin_orientation_codes[] =
  30. {
  31. PIN_RIGHT,
  32. PIN_LEFT,
  33. PIN_UP,
  34. PIN_DOWN
  35. };
  36. #define PIN_ORIENTATION_CNT ( sizeof( pin_orientation_names ) / \
  37. sizeof( wxString* ) )
  38. static const wxString pin_style_names[] =
  39. {
  40. _( "Line" ),
  41. _( "Inverted" ),
  42. _( "Clock" ),
  43. _( "Inverted clock" ),
  44. _( "Input low" ),
  45. _( "Clock low" ),
  46. _( "Output low" )
  47. };
  48. #define PIN_STYLE_CNT ( sizeof( pin_style_names ) / sizeof( wxString* ) )
  49. static const int pin_style_codes[] =
  50. {
  51. NONE,
  52. INVERT,
  53. CLOCK,
  54. CLOCK | INVERT,
  55. LOWLEVEL_IN,
  56. LOWLEVEL_IN | CLOCK,
  57. LOWLEVEL_OUT
  58. };
  59. static const wxString pin_electrical_type_names[] =
  60. {
  61. _( "Input" ),
  62. _( "Output" ),
  63. _( "Bidirectional" ),
  64. _( "Tri-state" ),
  65. _( "Passive" ),
  66. _( "Unspecified" ),
  67. _( "Power input" ),
  68. _( "Power output" ),
  69. _( "Open collector" ),
  70. _( "Open emitter" ),
  71. _( "Not connected" )
  72. };
  73. #define PIN_ELECTRICAL_TYPE_CNT ( sizeof( pin_electrical_type_names ) / \
  74. sizeof( wxString* ) )
  75. const wxChar* MsgPinElectricType[] =
  76. {
  77. wxT( "input" ),
  78. wxT( "output" ),
  79. wxT( "BiDi" ),
  80. wxT( "3state" ),
  81. wxT( "passive" ),
  82. wxT( "unspc" ),
  83. wxT( "power_in" ),
  84. wxT( "power_out" ),
  85. wxT( "openCol" ),
  86. wxT( "openEm" ),
  87. wxT( "?????" )
  88. };
  89. extern void PlotPinSymbol( PLOTTER* plotter, const wxPoint& pos,
  90. int len, int orient, int Shape );
  91. LIB_PIN::LIB_PIN(LIB_COMPONENT * aParent) :
  92. LIB_DRAW_ITEM( COMPONENT_PIN_DRAW_TYPE, aParent )
  93. {
  94. m_PinLen = 300; /* default Pin len */
  95. m_Orient = PIN_RIGHT; /* Pin oprient: Up, Down, Left, Right */
  96. m_PinShape = NONE; /* Pin shape, bitwise. */
  97. m_PinType = PIN_UNSPECIFIED; /* electrical type of pin */
  98. m_Attributs = 0; /* bit 0 != 0: pin invisible */
  99. m_PinNum = 0; /* pin number ( i.e. 4 codes ASCII ) */
  100. m_PinNumSize = 50;
  101. m_PinNameSize = 50; /* Default size for pin name and num */
  102. m_Width = 0;
  103. m_typeName = _( "Pin" );
  104. m_PinNumShapeOpt = 0;
  105. m_PinNameShapeOpt = 0;
  106. m_PinNumPositionOpt = 0;
  107. m_PinNamePositionOpt = 0;
  108. }
  109. LIB_PIN::LIB_PIN( const LIB_PIN& pin ) : LIB_DRAW_ITEM( pin )
  110. {
  111. m_Pos = pin.m_Pos;
  112. m_PinLen = pin.m_PinLen;
  113. m_Orient = pin.m_Orient;
  114. m_PinShape = pin.m_PinShape;
  115. m_PinType = pin.m_PinType;
  116. m_Attributs = pin.m_Attributs;
  117. m_PinNum = pin.m_PinNum;
  118. m_PinNumSize = pin.m_PinNumSize;
  119. m_PinNameSize = pin.m_PinNameSize;
  120. m_PinNumShapeOpt = pin.m_PinNumShapeOpt;
  121. m_PinNameShapeOpt = pin.m_PinNameShapeOpt;
  122. m_PinNumPositionOpt = pin.m_PinNumPositionOpt;
  123. m_PinNamePositionOpt = pin.m_PinNamePositionOpt;
  124. m_Width = pin.m_Width;
  125. m_PinName = pin.m_PinName;
  126. }
  127. void LIB_PIN::SetName( const wxString& name )
  128. {
  129. wxString tmp = ( name.IsEmpty() ) ? wxT( "~" ) : name;
  130. tmp.Replace( wxT( " " ), wxT( "_" ) );
  131. if( m_PinName != tmp )
  132. {
  133. m_PinName = tmp;
  134. m_Flags |= IS_CHANGED;
  135. }
  136. if( GetParent() == NULL )
  137. return;
  138. LIB_PIN_LIST pinList;
  139. GetParent()->GetPins( pinList );
  140. for( size_t i = 0; i < pinList.size(); i++ )
  141. {
  142. if( ( pinList[i]->m_Flags & IS_LINKED ) == 0
  143. || pinList[i]->m_PinName == m_PinName )
  144. continue;
  145. pinList[i]->m_PinName = m_PinName;
  146. pinList[i]->m_Flags |= IS_CHANGED;
  147. }
  148. }
  149. void LIB_PIN::SetNameTextSize( int size )
  150. {
  151. if( size != m_PinNameSize )
  152. {
  153. m_PinNameSize = size;
  154. m_Flags |= IS_CHANGED;
  155. }
  156. if( GetParent() == NULL )
  157. return;
  158. LIB_PIN_LIST pinList;
  159. GetParent()->GetPins( pinList );
  160. for( size_t i = 0; i < pinList.size(); i++ )
  161. {
  162. if( ( pinList[i]->m_Flags & IS_LINKED ) == 0
  163. || pinList[i]->m_PinNameSize == size )
  164. continue;
  165. pinList[i]->m_PinNameSize = size;
  166. pinList[i]->m_Flags |= IS_CHANGED;
  167. }
  168. }
  169. void LIB_PIN::SetNumber( const wxString& number )
  170. {
  171. wxString tmp = ( number.IsEmpty() ) ? wxT( "~" ) : number;
  172. tmp.Replace( wxT( " " ), wxT( "_" ) );
  173. long oldNumber = m_PinNum;
  174. SetPinNumFromString( tmp );
  175. if( m_PinNum != oldNumber )
  176. {
  177. m_Flags |= IS_CHANGED;
  178. }
  179. if( GetParent() == NULL )
  180. return;
  181. LIB_PIN_LIST pinList;
  182. GetParent()->GetPins( pinList );
  183. for( size_t i = 0; i < pinList.size(); i++ )
  184. {
  185. if( ( pinList[i]->m_Flags & IS_LINKED ) == 0
  186. || pinList[i]->m_PinNum == m_PinNum )
  187. continue;
  188. pinList[i]->m_PinNum = m_PinNum;
  189. pinList[i]->m_Flags |= IS_CHANGED;
  190. }
  191. }
  192. void LIB_PIN::SetNumberTextSize( int size )
  193. {
  194. if( size != m_PinNumSize )
  195. {
  196. m_PinNumSize = size;
  197. m_Flags |= IS_CHANGED;
  198. }
  199. if( GetParent() == NULL )
  200. return;
  201. LIB_PIN_LIST pinList;
  202. GetParent()->GetPins( pinList );
  203. for( size_t i = 0; i < pinList.size(); i++ )
  204. {
  205. if( ( pinList[i]->m_Flags & IS_LINKED ) == 0
  206. || pinList[i]->m_PinNumSize == size )
  207. continue;
  208. pinList[i]->m_PinNumSize = size;
  209. pinList[i]->m_Flags |= IS_CHANGED;
  210. }
  211. }
  212. void LIB_PIN::SetOrientation( int orientation )
  213. {
  214. if( m_Orient != orientation )
  215. {
  216. m_Orient = orientation;
  217. m_Flags |= IS_CHANGED;
  218. }
  219. if( GetParent() == NULL )
  220. return;
  221. LIB_PIN_LIST pinList;
  222. GetParent()->GetPins( pinList );
  223. for( size_t i = 0; i < pinList.size(); i++ )
  224. {
  225. if( ( pinList[i]->m_Flags & IS_LINKED ) == 0
  226. || pinList[i]->m_Orient == orientation )
  227. continue;
  228. pinList[i]->m_Orient = orientation;
  229. pinList[i]->m_Flags |= IS_CHANGED;
  230. }
  231. }
  232. void LIB_PIN::SetDrawStyle( int style )
  233. {
  234. if( m_PinShape != style )
  235. {
  236. m_PinShape = style;
  237. m_Flags |= IS_CHANGED;
  238. }
  239. if( GetParent() == NULL )
  240. return;
  241. LIB_PIN_LIST pinList;
  242. GetParent()->GetPins( pinList );
  243. for( size_t i = 0; i < pinList.size(); i++ )
  244. {
  245. if( ( pinList[i]->m_Flags & IS_LINKED ) == 0
  246. || pinList[i]->m_PinShape == style )
  247. continue;
  248. pinList[i]->m_PinShape = style;
  249. pinList[i]->m_Flags |= IS_CHANGED;
  250. }
  251. }
  252. void LIB_PIN::SetElectricalType( int type )
  253. {
  254. if( m_PinType != type )
  255. {
  256. m_PinType = type;
  257. m_Flags |= IS_CHANGED;
  258. }
  259. if( GetParent() == NULL )
  260. return;
  261. LIB_PIN_LIST pinList;
  262. GetParent()->GetPins( pinList );
  263. for( size_t i = 0; i < pinList.size(); i++ )
  264. {
  265. if( ( pinList[i]->m_Flags & IS_LINKED ) == 0
  266. || pinList[i]->m_PinType == type )
  267. continue;
  268. pinList[i]->m_PinType = type;
  269. pinList[i]->m_Flags |= IS_CHANGED;
  270. }
  271. }
  272. void LIB_PIN::SetLength( int length )
  273. {
  274. if( m_PinLen != length )
  275. {
  276. m_PinLen = length;
  277. m_Flags |= IS_CHANGED;
  278. }
  279. if( GetParent() == NULL )
  280. return;
  281. LIB_PIN_LIST pinList;
  282. GetParent()->GetPins( pinList );
  283. for( size_t i = 0; i < pinList.size(); i++ )
  284. {
  285. if( ( pinList[i]->m_Flags & IS_LINKED ) == 0
  286. || pinList[i]->m_Convert != m_Convert
  287. || pinList[i]->m_PinLen == length )
  288. continue;
  289. pinList[i]->m_PinLen = length;
  290. pinList[i]->m_Flags |= IS_CHANGED;
  291. }
  292. }
  293. void LIB_PIN::SetPartNumber( int part )
  294. {
  295. if( m_Unit == part )
  296. return;
  297. m_Unit = part;
  298. m_Flags |= IS_CHANGED;
  299. if( m_Unit == 0 )
  300. {
  301. LIB_PIN* pin;
  302. LIB_PIN* tmp = GetParent()->GetNextPin();
  303. while( tmp != NULL )
  304. {
  305. pin = tmp;
  306. tmp = GetParent()->GetNextPin( pin );
  307. if( pin->m_Flags == 0 || pin == this
  308. || ( m_Convert && ( m_Convert != pin->m_Convert ) )
  309. || ( m_Pos != pin->m_Pos )
  310. || ( pin->m_Orient != m_Orient ) )
  311. continue;
  312. GetParent()->RemoveDrawItem( (LIB_DRAW_ITEM*) pin );
  313. }
  314. }
  315. }
  316. void LIB_PIN::SetConversion( int style )
  317. {
  318. if( m_Convert == style )
  319. return;
  320. m_Convert = style;
  321. m_Flags |= IS_CHANGED;
  322. if( style == 0 )
  323. {
  324. LIB_PIN* pin;
  325. LIB_PIN* tmp = GetParent()->GetNextPin();
  326. while( tmp != NULL )
  327. {
  328. pin = tmp;
  329. tmp = GetParent()->GetNextPin( pin );
  330. if( ( pin->m_Flags & IS_LINKED ) == 0
  331. || ( pin == this )
  332. || ( m_Unit && ( m_Unit != pin->m_Unit ) )
  333. || ( m_Pos != pin->m_Pos )
  334. || ( pin->m_Orient != m_Orient ) )
  335. continue;
  336. GetParent()->RemoveDrawItem( (LIB_DRAW_ITEM*) pin );
  337. }
  338. }
  339. }
  340. void LIB_PIN::SetVisible( bool visible )
  341. {
  342. if( visible == IsVisible() )
  343. return;
  344. if( visible )
  345. m_Attributs &= ~PINNOTDRAW;
  346. else
  347. m_Attributs |= PINNOTDRAW;
  348. m_Flags |= IS_CHANGED;
  349. if( GetParent() == NULL )
  350. return;
  351. LIB_PIN_LIST pinList;
  352. GetParent()->GetPins( pinList );
  353. for( size_t i = 0; i < pinList.size(); i++ )
  354. {
  355. if( ( pinList[i]->m_Flags & IS_LINKED ) == 0
  356. || pinList[i]->IsVisible() == visible )
  357. continue;
  358. if( visible )
  359. pinList[i]->m_Attributs &= ~PINNOTDRAW;
  360. else
  361. pinList[i]->m_Attributs |= PINNOTDRAW;
  362. pinList[i]->m_Flags |= IS_CHANGED;
  363. }
  364. }
  365. void LIB_PIN::EnableEditMode( bool enable, bool editPinByPin )
  366. {
  367. LIB_PIN_LIST pinList;
  368. if( GetParent() == NULL )
  369. return;
  370. GetParent()->GetPins( pinList );
  371. for( size_t i = 0; i < pinList.size(); i++ )
  372. {
  373. if( pinList[i] == this )
  374. continue;
  375. if( ( pinList[i]->m_Pos == m_Pos )
  376. && ( pinList[i]->m_Orient == m_Orient )
  377. && ( !( m_Flags & IS_NEW ) )
  378. && !editPinByPin == false
  379. && enable )
  380. pinList[i]->m_Flags |= IS_LINKED | IN_EDIT;
  381. else
  382. pinList[i]->m_Flags &= ~( IS_LINKED | IN_EDIT );
  383. }
  384. }
  385. /**
  386. * Function HitTest
  387. * tests if the given wxPoint is within the bounds of this object.
  388. * @param aRefPos A wxPoint to test
  389. * @return bool - true if a hit, else false
  390. */
  391. bool LIB_PIN::HitTest( const wxPoint& aRefPos )
  392. {
  393. int mindist = m_Width ? m_Width / 2 : g_DrawDefaultLineThickness / 2;
  394. // Have a minimal tolerance for hit test
  395. if( mindist < 3 )
  396. mindist = 3; // = 3 mils
  397. return HitTest( aRefPos, mindist, DefaultTransformMatrix );
  398. }
  399. /** Function HitTest
  400. * @return true if the point aPosRef is near a pin
  401. * @param aRefPos = a wxPoint to test
  402. * @param aThreshold = max distance to a segment
  403. * @param aTransMat = the transform matrix
  404. */
  405. bool LIB_PIN::HitTest( wxPoint aRefPos, int aThreshold,
  406. const int aTransMat[2][2] )
  407. {
  408. wxPoint pinPos = TransformCoordinate( aTransMat, m_Pos );
  409. wxPoint pinEnd = TransformCoordinate( aTransMat, ReturnPinEndPoint() );
  410. return TestSegmentHit( aRefPos, pinPos, pinEnd, aThreshold );
  411. }
  412. bool LIB_PIN::Save( FILE* ExportFile )
  413. {
  414. wxString StringPinNum;
  415. int Etype;
  416. switch( m_PinType )
  417. {
  418. default:
  419. case PIN_INPUT:
  420. Etype = 'I';
  421. break;
  422. case PIN_OUTPUT:
  423. Etype = 'O';
  424. break;
  425. case PIN_BIDI:
  426. Etype = 'B';
  427. break;
  428. case PIN_TRISTATE:
  429. Etype = 'T';
  430. break;
  431. case PIN_PASSIVE:
  432. Etype = 'P';
  433. break;
  434. case PIN_UNSPECIFIED:
  435. Etype = 'U';
  436. break;
  437. case PIN_POWER_IN:
  438. Etype = 'W';
  439. break;
  440. case PIN_POWER_OUT:
  441. Etype = 'w';
  442. break;
  443. case PIN_OPENCOLLECTOR:
  444. Etype = 'C';
  445. break;
  446. case PIN_OPENEMITTER:
  447. Etype = 'E';
  448. break;
  449. }
  450. ReturnPinStringNum( StringPinNum );
  451. if( StringPinNum.IsEmpty() )
  452. StringPinNum = wxT( "~" );
  453. if( !m_PinName.IsEmpty() )
  454. {
  455. if( fprintf( ExportFile, "X %s", CONV_TO_UTF8( m_PinName ) ) < 0 )
  456. return false;
  457. }
  458. else
  459. {
  460. if( fprintf( ExportFile, "X ~" ) < 0 )
  461. return false;
  462. }
  463. if( fprintf( ExportFile, " %s %d %d %d %c %d %d %d %d %c",
  464. CONV_TO_UTF8( StringPinNum ), m_Pos.x, m_Pos.y,
  465. (int) m_PinLen, (int) m_Orient, m_PinNumSize, m_PinNameSize,
  466. m_Unit, m_Convert, Etype ) < 0 )
  467. return false;
  468. if( ( m_PinShape ) || ( m_Attributs & PINNOTDRAW ) )
  469. {
  470. if( fprintf( ExportFile, " " ) < 0 )
  471. return false;
  472. }
  473. if( m_Attributs & PINNOTDRAW
  474. && fprintf( ExportFile, "N" ) < 0 )
  475. return false;
  476. if( m_PinShape & INVERT
  477. && fprintf( ExportFile, "I" ) < 0 )
  478. return false;
  479. if( m_PinShape & CLOCK
  480. && fprintf( ExportFile, "C" ) < 0 )
  481. return false;
  482. if( m_PinShape & LOWLEVEL_IN
  483. && fprintf( ExportFile, "L" ) < 0 )
  484. return false;
  485. if( m_PinShape & LOWLEVEL_OUT
  486. && fprintf( ExportFile, "V" ) < 0 )
  487. return false;
  488. if( fprintf( ExportFile, "\n" ) < 0 )
  489. return false;
  490. m_Flags &= ~IS_CHANGED;
  491. return true;
  492. }
  493. bool LIB_PIN::Load( char* line, wxString& errorMsg )
  494. {
  495. int i, j;
  496. char pinAttrs[64];
  497. char pinName[256];
  498. char pinNum[64];
  499. char pinOrient[64];
  500. char pinType[64];
  501. *pinAttrs = 0;
  502. i = sscanf( line + 2, "%s %s %d %d %d %s %d %d %d %d %s %s", pinName,
  503. pinNum, &m_Pos.x, &m_Pos.y, &m_PinLen, pinOrient, &m_PinNumSize,
  504. &m_PinNameSize, &m_Unit, &m_Convert, pinType, pinAttrs );
  505. if( i < 11 )
  506. {
  507. errorMsg.Printf( wxT( "pin only had %d parameters of the required 11 or 12" ), i );
  508. return false;
  509. }
  510. m_Orient = pinOrient[0] & 255;
  511. strncpy( (char*) &m_PinNum, pinNum, 4 );
  512. m_PinName = CONV_FROM_UTF8( pinName );
  513. switch( *pinType & 255 )
  514. {
  515. case 'I':
  516. m_PinType = PIN_INPUT;
  517. break;
  518. case 'O':
  519. m_PinType = PIN_OUTPUT;
  520. break;
  521. case 'B':
  522. m_PinType = PIN_BIDI;
  523. break;
  524. case 'T':
  525. m_PinType = PIN_TRISTATE;
  526. break;
  527. case 'P':
  528. m_PinType = PIN_PASSIVE;
  529. break;
  530. case 'U':
  531. m_PinType = PIN_UNSPECIFIED;
  532. break;
  533. case 'W':
  534. m_PinType = PIN_POWER_IN;
  535. break;
  536. case 'w':
  537. m_PinType = PIN_POWER_OUT;
  538. break;
  539. case 'C':
  540. m_PinType = PIN_OPENCOLLECTOR;
  541. break;
  542. case 'E':
  543. m_PinType = PIN_OPENEMITTER;
  544. break;
  545. default:
  546. errorMsg.Printf( wxT( "unknown pin type [%c]" ), *pinType & 255 );
  547. return false;
  548. }
  549. if( i == 12 ) /* Special Symbol defined */
  550. {
  551. for( j = strlen( pinAttrs ); j > 0; )
  552. {
  553. switch( pinAttrs[--j] )
  554. {
  555. case '~':
  556. break;
  557. case 'N':
  558. m_Attributs |= PINNOTDRAW;
  559. break;
  560. case 'I':
  561. m_PinShape |= INVERT;
  562. break;
  563. case 'C':
  564. m_PinShape |= CLOCK;
  565. break;
  566. case 'L':
  567. m_PinShape |= LOWLEVEL_IN;
  568. break;
  569. case 'V':
  570. m_PinShape |= LOWLEVEL_OUT;
  571. break;
  572. default:
  573. errorMsg.Printf( wxT( "unknown pin attribute [%c]" ),
  574. pinAttrs[j] );
  575. return false;
  576. }
  577. }
  578. }
  579. return true;
  580. }
  581. /** Function GetPenSize
  582. * @return the size of the "pen" that be used to draw or plot this item
  583. */
  584. int LIB_PIN::GetPenSize()
  585. {
  586. return ( m_Width == 0 ) ? g_DrawDefaultLineThickness : m_Width;
  587. }
  588. void LIB_PIN::Draw( WinEDA_DrawPanel* aPanel,
  589. wxDC* aDC,
  590. const wxPoint& aOffset,
  591. int aColor,
  592. int aDrawMode,
  593. void* aData,
  594. const int aTransformMatrix[2][2] )
  595. {
  596. // Invisible pins are only drawn on request. In libedit they are drawn
  597. // in g_InvisibleItemColor because we must see them.
  598. WinEDA_SchematicFrame* frame =
  599. (WinEDA_SchematicFrame*) wxGetApp().GetTopWindow();
  600. if( ( m_Attributs & PINNOTDRAW ) )
  601. {
  602. if( frame->m_LibeditFrame && frame->m_LibeditFrame->IsActive() )
  603. aColor = g_InvisibleItemColor;
  604. else if( !frame->m_ShowAllPins )
  605. return;
  606. }
  607. LIB_COMPONENT* Entry = GetParent();
  608. bool DrawPinText = true;
  609. if( ( aData != NULL ) && ( (bool*) aData == false ) )
  610. DrawPinText = false;
  611. /* Calculate pin orient taking in account the component orientation. */
  612. int orient = ReturnPinDrawOrient( aTransformMatrix );
  613. /* Calculate the pin position */
  614. wxPoint pos1 = TransformCoordinate( aTransformMatrix, m_Pos ) + aOffset;
  615. /* Drawing from the pin and the special symbol combination */
  616. DrawPinSymbol( aPanel, aDC, pos1, orient, aDrawMode, aColor );
  617. if( DrawPinText )
  618. {
  619. DrawPinTexts( aPanel, aDC, pos1, orient, Entry->m_TextInside,
  620. Entry->m_DrawPinNum, Entry->m_DrawPinName,
  621. aColor, aDrawMode );
  622. }
  623. /* Set to one (1) to draw bounding box around pin to validate bounding
  624. * box calculation. */
  625. #if 0
  626. EDA_Rect bBox = GetBoundingBox();
  627. bBox.Inflate( 5, 5 );
  628. GRRect( &aPanel->m_ClipBox, aDC, bBox.GetOrigin().x, bBox.GetOrigin().y,
  629. bBox.GetEnd().x, bBox.GetEnd().y, 0, LIGHTMAGENTA );
  630. #endif
  631. }
  632. /** Function DrawPinSymbol
  633. * Draw the pin symbol (without texts)
  634. * if Color != 0 draw with Color, else with the normal pin color
  635. */
  636. void LIB_PIN::DrawPinSymbol( WinEDA_DrawPanel* aPanel,
  637. wxDC* aDC,
  638. const wxPoint& aPinPos,
  639. int aOrient,
  640. int aDrawMode,
  641. int aColor )
  642. {
  643. int MapX1, MapY1, x1, y1;
  644. int color;
  645. int width = GetPenSize( );
  646. int posX = aPinPos.x, posY = aPinPos.y, len = m_PinLen;
  647. BASE_SCREEN* screen = aPanel->GetScreen();
  648. color = ReturnLayerColor( LAYER_PIN );
  649. if( aColor < 0 ) // Used normal color or selected color
  650. {
  651. if( (m_Selected & IS_SELECTED) )
  652. color = g_ItemSelectetColor;
  653. }
  654. else
  655. color = aColor;
  656. GRSetDrawMode( aDC, aDrawMode );
  657. MapX1 = MapY1 = 0; x1 = posX; y1 = posY;
  658. switch( aOrient )
  659. {
  660. case PIN_UP:
  661. y1 = posY - len; MapY1 = 1;
  662. break;
  663. case PIN_DOWN:
  664. y1 = posY + len; MapY1 = -1;
  665. break;
  666. case PIN_LEFT:
  667. x1 = posX - len, MapX1 = 1;
  668. break;
  669. case PIN_RIGHT:
  670. x1 = posX + len; MapX1 = -1;
  671. break;
  672. }
  673. if( m_PinShape & INVERT )
  674. {
  675. GRCircle( &aPanel->m_ClipBox, aDC, MapX1 * INVERT_PIN_RADIUS + x1,
  676. MapY1 * INVERT_PIN_RADIUS + y1,
  677. INVERT_PIN_RADIUS, width, color );
  678. GRMoveTo( MapX1 * INVERT_PIN_RADIUS * 2 + x1,
  679. MapY1 * INVERT_PIN_RADIUS * 2 + y1 );
  680. GRLineTo( &aPanel->m_ClipBox, aDC, posX, posY, width, color );
  681. }
  682. else
  683. {
  684. GRMoveTo( x1, y1 );
  685. GRLineTo( &aPanel->m_ClipBox, aDC, posX, posY, width, color );
  686. }
  687. if( m_PinShape & CLOCK )
  688. {
  689. if( MapY1 == 0 ) /* MapX1 = +- 1 */
  690. {
  691. GRMoveTo( x1, y1 + CLOCK_PIN_DIM );
  692. GRLineTo( &aPanel->m_ClipBox,
  693. aDC,
  694. x1 - MapX1 * CLOCK_PIN_DIM,
  695. y1,
  696. width,
  697. color );
  698. GRLineTo( &aPanel->m_ClipBox,
  699. aDC,
  700. x1,
  701. y1 - CLOCK_PIN_DIM,
  702. width,
  703. color );
  704. }
  705. else /* MapX1 = 0 */
  706. {
  707. GRMoveTo( x1 + CLOCK_PIN_DIM, y1 );
  708. GRLineTo( &aPanel->m_ClipBox,
  709. aDC,
  710. x1,
  711. y1 - MapY1 * CLOCK_PIN_DIM,
  712. width,
  713. color );
  714. GRLineTo( &aPanel->m_ClipBox,
  715. aDC,
  716. x1 - CLOCK_PIN_DIM,
  717. y1,
  718. width,
  719. color );
  720. }
  721. }
  722. if( m_PinShape & LOWLEVEL_IN ) /* IEEE symbol "Active Low Input" */
  723. {
  724. if( MapY1 == 0 ) /* MapX1 = +- 1 */
  725. {
  726. GRMoveTo( x1 + MapX1 * IEEE_SYMBOL_PIN_DIM * 2, y1 );
  727. GRLineTo( &aPanel->m_ClipBox,
  728. aDC,
  729. x1 + MapX1 * IEEE_SYMBOL_PIN_DIM * 2,
  730. y1 - IEEE_SYMBOL_PIN_DIM,
  731. width,
  732. color );
  733. GRLineTo( &aPanel->m_ClipBox, aDC, x1, y1, width, color );
  734. }
  735. else /* MapX1 = 0 */
  736. {
  737. GRMoveTo( x1, y1 + MapY1 * IEEE_SYMBOL_PIN_DIM * 2 );
  738. GRLineTo( &aPanel->m_ClipBox, aDC, x1 - IEEE_SYMBOL_PIN_DIM,
  739. y1 + MapY1 * IEEE_SYMBOL_PIN_DIM * 2, width, color );
  740. GRLineTo( &aPanel->m_ClipBox, aDC, x1, y1, width, color );
  741. }
  742. }
  743. if( m_PinShape & LOWLEVEL_OUT ) /* IEEE symbol "Active Low Output" */
  744. {
  745. if( MapY1 == 0 ) /* MapX1 = +- 1 */
  746. {
  747. GRMoveTo( x1, y1 - IEEE_SYMBOL_PIN_DIM );
  748. GRLineTo( &aPanel->m_ClipBox,
  749. aDC,
  750. x1 + MapX1 * IEEE_SYMBOL_PIN_DIM * 2,
  751. y1,
  752. width,
  753. color );
  754. }
  755. else /* MapX1 = 0 */
  756. {
  757. GRMoveTo( x1 - IEEE_SYMBOL_PIN_DIM, y1 );
  758. GRLineTo( &aPanel->m_ClipBox,
  759. aDC,
  760. x1,
  761. y1 + MapY1 * IEEE_SYMBOL_PIN_DIM * 2,
  762. width,
  763. color );
  764. }
  765. }
  766. /* Draw the pin end target (active end of the pin)
  767. * Draw but do not print the pin end target 1 pixel width
  768. */
  769. if( !screen->m_IsPrinting )
  770. GRCircle( &aPanel->m_ClipBox,
  771. aDC,
  772. posX,
  773. posY,
  774. TARGET_PIN_DIAM,
  775. 0,
  776. color );
  777. }
  778. /*****************************************************************************
  779. * Put out pin number and pin text info, given the pin line coordinates.
  780. * The line must be vertical or horizontal.
  781. * If PinText == NULL nothing is printed. If PinNum = 0 no number is printed.
  782. * Current Zoom factor is taken into account.
  783. * If TextInside then the text is been put inside,otherwise all is drawn outside.
  784. * Pin Name: substring beteween '~' is negated
  785. * DrawMode = GR_OR, XOR ...
  786. *****************************************************************************/
  787. void LIB_PIN::DrawPinTexts( WinEDA_DrawPanel* panel,
  788. wxDC* DC,
  789. wxPoint& pin_pos,
  790. int orient,
  791. int TextInside,
  792. bool DrawPinNum,
  793. bool DrawPinName,
  794. int Color,
  795. int DrawMode )
  796. {
  797. int x, y, x1, y1;
  798. wxString StringPinNum;
  799. EDA_Colors NameColor, NumColor;
  800. wxSize PinNameSize( m_PinNameSize, m_PinNameSize );
  801. wxSize PinNumSize( m_PinNumSize, m_PinNumSize );
  802. int nameLineWidth = GetPenSize( );
  803. nameLineWidth = Clamp_Text_PenSize( nameLineWidth, m_PinNameSize, false );
  804. int numLineWidth = GetPenSize( );
  805. numLineWidth = Clamp_Text_PenSize( numLineWidth, m_PinNumSize, false );
  806. GRSetDrawMode( DC, DrawMode );
  807. /* Get the num and name colors */
  808. if( (Color < 0) && (m_Selected & IS_SELECTED) )
  809. Color = g_ItemSelectetColor;
  810. NameColor = (EDA_Colors) ( Color == -1 ? ReturnLayerColor( LAYER_PINNAM ) : Color );
  811. NumColor = (EDA_Colors) ( Color == -1 ? ReturnLayerColor( LAYER_PINNUM ) : Color );
  812. /* Create the pin num string */
  813. ReturnPinStringNum( StringPinNum );
  814. x1 = pin_pos.x; y1 = pin_pos.y;
  815. switch( orient )
  816. {
  817. case PIN_UP:
  818. y1 -= m_PinLen; break;
  819. case PIN_DOWN:
  820. y1 += m_PinLen; break;
  821. case PIN_LEFT:
  822. x1 -= m_PinLen; break;
  823. case PIN_RIGHT:
  824. x1 += m_PinLen; break;
  825. }
  826. if( m_PinName.IsEmpty() )
  827. DrawPinName = FALSE;
  828. if( TextInside ) /* Draw the text inside, but the pin numbers outside. */
  829. {
  830. if( (orient == PIN_LEFT) || (orient == PIN_RIGHT) )
  831. {
  832. // It is an horizontal line
  833. if( DrawPinName )
  834. {
  835. if( orient == PIN_RIGHT )
  836. {
  837. x = x1 + TextInside;
  838. DrawGraphicText( panel, DC, wxPoint( x, y1 ), NameColor,
  839. m_PinName,
  840. TEXT_ORIENT_HORIZ,
  841. PinNameSize,
  842. GR_TEXT_HJUSTIFY_LEFT,
  843. GR_TEXT_VJUSTIFY_CENTER, nameLineWidth,
  844. false, false );
  845. }
  846. else // Orient == PIN_LEFT
  847. {
  848. x = x1 - TextInside;
  849. DrawGraphicText( panel, DC, wxPoint( x, y1 ), NameColor,
  850. m_PinName,
  851. TEXT_ORIENT_HORIZ,
  852. PinNameSize,
  853. GR_TEXT_HJUSTIFY_RIGHT,
  854. GR_TEXT_VJUSTIFY_CENTER, nameLineWidth,
  855. false, false );
  856. }
  857. }
  858. if( DrawPinNum )
  859. {
  860. DrawGraphicText( panel, DC,
  861. wxPoint( (x1 + pin_pos.x) / 2,
  862. y1 - TXTMARGE ), NumColor,
  863. StringPinNum,
  864. TEXT_ORIENT_HORIZ, PinNumSize,
  865. GR_TEXT_HJUSTIFY_CENTER,
  866. GR_TEXT_VJUSTIFY_BOTTOM, numLineWidth,
  867. false, false );
  868. }
  869. }
  870. else /* Its a vertical line. */
  871. {
  872. // Text is drawn from bottom to top (i.e. to negative value for Y axis)
  873. if( orient == PIN_DOWN )
  874. {
  875. y = y1 + TextInside;
  876. if( DrawPinName )
  877. DrawGraphicText( panel, DC, wxPoint( x1, y ), NameColor,
  878. m_PinName,
  879. TEXT_ORIENT_VERT, PinNameSize,
  880. GR_TEXT_HJUSTIFY_RIGHT,
  881. GR_TEXT_VJUSTIFY_CENTER, nameLineWidth,
  882. false, false );
  883. if( DrawPinNum )
  884. DrawGraphicText( panel, DC,
  885. wxPoint( x1 - TXTMARGE,
  886. (y1 + pin_pos.y) / 2 ), NumColor,
  887. StringPinNum,
  888. TEXT_ORIENT_VERT, PinNumSize,
  889. GR_TEXT_HJUSTIFY_CENTER,
  890. GR_TEXT_VJUSTIFY_BOTTOM, numLineWidth,
  891. false, false );
  892. }
  893. else /* PIN_UP */
  894. {
  895. y = y1 - TextInside;
  896. if( DrawPinName )
  897. DrawGraphicText( panel, DC, wxPoint( x1, y ), NameColor,
  898. m_PinName,
  899. TEXT_ORIENT_VERT, PinNameSize,
  900. GR_TEXT_HJUSTIFY_LEFT,
  901. GR_TEXT_VJUSTIFY_CENTER, nameLineWidth,
  902. false, false );
  903. if( DrawPinNum )
  904. DrawGraphicText( panel, DC,
  905. wxPoint( x1 - TXTMARGE,
  906. (y1 + pin_pos.y) / 2 ), NumColor,
  907. StringPinNum,
  908. TEXT_ORIENT_VERT, PinNumSize,
  909. GR_TEXT_HJUSTIFY_CENTER,
  910. GR_TEXT_VJUSTIFY_BOTTOM, numLineWidth,
  911. false, false );
  912. }
  913. }
  914. }
  915. else /**** Draw num & text pin outside ****/
  916. {
  917. if( (orient == PIN_LEFT) || (orient == PIN_RIGHT) )
  918. {
  919. /* Its an horizontal line. */
  920. if( DrawPinName )
  921. {
  922. x = (x1 + pin_pos.x) / 2;
  923. DrawGraphicText( panel, DC, wxPoint( x, y1 - TXTMARGE ),
  924. NameColor, m_PinName,
  925. TEXT_ORIENT_HORIZ, PinNameSize,
  926. GR_TEXT_HJUSTIFY_CENTER,
  927. GR_TEXT_VJUSTIFY_BOTTOM, nameLineWidth,
  928. false, false );
  929. }
  930. if( DrawPinNum )
  931. {
  932. x = (x1 + pin_pos.x) / 2;
  933. DrawGraphicText( panel, DC, wxPoint( x, y1 + TXTMARGE ),
  934. NumColor, StringPinNum,
  935. TEXT_ORIENT_HORIZ, PinNumSize,
  936. GR_TEXT_HJUSTIFY_CENTER,
  937. GR_TEXT_VJUSTIFY_TOP, numLineWidth,
  938. false, false );
  939. }
  940. }
  941. else /* Its a vertical line. */
  942. {
  943. if( DrawPinName )
  944. {
  945. y = (y1 + pin_pos.y) / 2;
  946. DrawGraphicText( panel, DC, wxPoint( x1 - TXTMARGE, y ),
  947. NameColor, m_PinName,
  948. TEXT_ORIENT_VERT, PinNameSize,
  949. GR_TEXT_HJUSTIFY_CENTER,
  950. GR_TEXT_VJUSTIFY_BOTTOM, nameLineWidth,
  951. false, false );
  952. }
  953. if( DrawPinNum )
  954. {
  955. DrawGraphicText( panel, DC,
  956. wxPoint( x1 + TXTMARGE, (y1 + pin_pos.y) / 2 ),
  957. NumColor, StringPinNum,
  958. TEXT_ORIENT_VERT, PinNumSize,
  959. GR_TEXT_HJUSTIFY_CENTER,
  960. GR_TEXT_VJUSTIFY_TOP, numLineWidth,
  961. false, false );
  962. }
  963. }
  964. }
  965. }
  966. /*****************************************************************************
  967. * Plot pin number and pin text info, given the pin line coordinates. *
  968. * Same as DrawPinTexts((), but output is the plotter
  969. * The line must be vertical or horizontal. *
  970. * If PinNext == NULL nothing is printed. *
  971. * Current Zoom factor is taken into account. *
  972. * If TextInside then the text is been put inside (moving from x1, y1 in *
  973. * the opposite direction to x2,y2), otherwise all is drawn outside. *
  974. *****************************************************************************/
  975. void LIB_PIN::PlotPinTexts( PLOTTER *plotter,
  976. wxPoint& pin_pos,
  977. int orient,
  978. int TextInside,
  979. bool DrawPinNum,
  980. bool DrawPinName,
  981. int aWidth )
  982. {
  983. int x, y, x1, y1;
  984. wxString StringPinNum;
  985. EDA_Colors NameColor, NumColor;
  986. wxSize PinNameSize = wxSize( m_PinNameSize, m_PinNameSize );
  987. wxSize PinNumSize = wxSize( m_PinNumSize, m_PinNumSize );
  988. /* Get the num and name colors */
  989. NameColor = ReturnLayerColor( LAYER_PINNAM );
  990. NumColor = ReturnLayerColor( LAYER_PINNUM );
  991. /* Create the pin num string */
  992. ReturnPinStringNum( StringPinNum );
  993. x1 = pin_pos.x; y1 = pin_pos.y;
  994. switch( orient )
  995. {
  996. case PIN_UP:
  997. y1 -= m_PinLen; break;
  998. case PIN_DOWN:
  999. y1 += m_PinLen; break;
  1000. case PIN_LEFT:
  1001. x1 -= m_PinLen; break;
  1002. case PIN_RIGHT:
  1003. x1 += m_PinLen; break;
  1004. }
  1005. if( m_PinName.IsEmpty() )
  1006. DrawPinName = FALSE;
  1007. /* Draw the text inside, but the pin numbers outside. */
  1008. if( TextInside )
  1009. {
  1010. if( (orient == PIN_LEFT) || (orient == PIN_RIGHT) ) /* Its an horizontal line. */
  1011. {
  1012. if( DrawPinName )
  1013. {
  1014. if( orient == PIN_RIGHT )
  1015. {
  1016. x = x1 + TextInside;
  1017. plotter->text( wxPoint( x, y1 ), NameColor,
  1018. m_PinName,
  1019. TEXT_ORIENT_HORIZ,
  1020. PinNameSize,
  1021. GR_TEXT_HJUSTIFY_LEFT,
  1022. GR_TEXT_VJUSTIFY_CENTER,
  1023. aWidth, false, false );
  1024. }
  1025. else // orient == PIN_LEFT
  1026. {
  1027. x = x1 - TextInside;
  1028. if( DrawPinName )
  1029. plotter->text( wxPoint( x, y1 ),
  1030. NameColor, m_PinName, TEXT_ORIENT_HORIZ,
  1031. PinNameSize,
  1032. GR_TEXT_HJUSTIFY_RIGHT,
  1033. GR_TEXT_VJUSTIFY_CENTER,
  1034. aWidth, false, false );
  1035. }
  1036. }
  1037. if( DrawPinNum )
  1038. {
  1039. plotter->text( wxPoint( (x1 + pin_pos.x) / 2,
  1040. y1 - TXTMARGE ),
  1041. NumColor, StringPinNum,
  1042. TEXT_ORIENT_HORIZ, PinNumSize,
  1043. GR_TEXT_HJUSTIFY_CENTER,
  1044. GR_TEXT_VJUSTIFY_BOTTOM,
  1045. aWidth, false, false );
  1046. }
  1047. }
  1048. else /* Its a vertical line. */
  1049. {
  1050. if( orient == PIN_DOWN )
  1051. {
  1052. y = y1 + TextInside;
  1053. if( DrawPinName )
  1054. plotter->text( wxPoint( x1, y ), NameColor,
  1055. m_PinName,
  1056. TEXT_ORIENT_VERT, PinNameSize,
  1057. GR_TEXT_HJUSTIFY_RIGHT,
  1058. GR_TEXT_VJUSTIFY_CENTER,
  1059. aWidth, false, false );
  1060. if( DrawPinNum )
  1061. {
  1062. plotter->text( wxPoint( x1 - TXTMARGE,
  1063. (y1 + pin_pos.y) / 2 ),
  1064. NumColor, StringPinNum,
  1065. TEXT_ORIENT_VERT, PinNumSize,
  1066. GR_TEXT_HJUSTIFY_CENTER,
  1067. GR_TEXT_VJUSTIFY_BOTTOM,
  1068. aWidth, false, false );
  1069. }
  1070. }
  1071. else /* PIN_UP */
  1072. {
  1073. y = y1 - TextInside;
  1074. if( DrawPinName )
  1075. plotter->text( wxPoint( x1, y ), NameColor,
  1076. m_PinName,
  1077. TEXT_ORIENT_VERT, PinNameSize,
  1078. GR_TEXT_HJUSTIFY_LEFT,
  1079. GR_TEXT_VJUSTIFY_CENTER,
  1080. aWidth, false, false );
  1081. if( DrawPinNum )
  1082. {
  1083. plotter->text( wxPoint( x1 - TXTMARGE,
  1084. (y1 + pin_pos.y) / 2 ),
  1085. NumColor, StringPinNum,
  1086. TEXT_ORIENT_VERT, PinNumSize,
  1087. GR_TEXT_HJUSTIFY_CENTER,
  1088. GR_TEXT_VJUSTIFY_BOTTOM,
  1089. aWidth, false, false );
  1090. }
  1091. }
  1092. }
  1093. }
  1094. else /* Draw num & text pin outside */
  1095. {
  1096. if( (orient == PIN_LEFT) || (orient == PIN_RIGHT) )
  1097. {
  1098. /* Its an horizontal line. */
  1099. if( DrawPinName )
  1100. {
  1101. x = (x1 + pin_pos.x) / 2;
  1102. plotter->text( wxPoint( x, y1 - TXTMARGE ),
  1103. NameColor, m_PinName,
  1104. TEXT_ORIENT_HORIZ, PinNameSize,
  1105. GR_TEXT_HJUSTIFY_CENTER,
  1106. GR_TEXT_VJUSTIFY_BOTTOM,
  1107. aWidth, false, false );
  1108. }
  1109. if( DrawPinNum )
  1110. {
  1111. x = (x1 + pin_pos.x) / 2;
  1112. plotter->text( wxPoint( x, y1 + TXTMARGE ),
  1113. NumColor, StringPinNum,
  1114. TEXT_ORIENT_HORIZ, PinNumSize,
  1115. GR_TEXT_HJUSTIFY_CENTER,
  1116. GR_TEXT_VJUSTIFY_TOP,
  1117. aWidth, false, false );
  1118. }
  1119. }
  1120. else /* Its a vertical line. */
  1121. {
  1122. if( DrawPinName )
  1123. {
  1124. y = (y1 + pin_pos.y) / 2;
  1125. plotter->text( wxPoint( x1 - TXTMARGE, y ),
  1126. NameColor, m_PinName,
  1127. TEXT_ORIENT_VERT, PinNameSize,
  1128. GR_TEXT_HJUSTIFY_CENTER,
  1129. GR_TEXT_VJUSTIFY_BOTTOM,
  1130. aWidth, false, false );
  1131. }
  1132. if( DrawPinNum )
  1133. {
  1134. plotter->text( wxPoint( x1 + TXTMARGE, (y1 + pin_pos.y) / 2 ),
  1135. NumColor, StringPinNum,
  1136. TEXT_ORIENT_VERT, PinNumSize,
  1137. GR_TEXT_HJUSTIFY_CENTER,
  1138. GR_TEXT_VJUSTIFY_TOP,
  1139. aWidth, false, false );
  1140. }
  1141. }
  1142. }
  1143. }
  1144. /* return the pin end position, for a component in normal orient */
  1145. wxPoint LIB_PIN::ReturnPinEndPoint()
  1146. {
  1147. wxPoint pos = m_Pos;
  1148. switch( m_Orient )
  1149. {
  1150. case PIN_UP:
  1151. pos.y += m_PinLen; break;
  1152. case PIN_DOWN:
  1153. pos.y -= m_PinLen; break;
  1154. case PIN_LEFT:
  1155. pos.x -= m_PinLen; break;
  1156. case PIN_RIGHT:
  1157. pos.x += m_PinLen; break;
  1158. }
  1159. return pos;
  1160. }
  1161. /** Function ReturnPinDrawOrient
  1162. * Return the pin real orientation (PIN_UP, PIN_DOWN, PIN_RIGHT, PIN_LEFT),
  1163. * according to its orientation and the matrix transform (rot, mirror) TransMat
  1164. * @param TransMat = transform matrix
  1165. */
  1166. int LIB_PIN::ReturnPinDrawOrient( const int TransMat[2][2] )
  1167. {
  1168. int orient;
  1169. wxPoint end; // position of a end pin starting at 0,0 according to its orientation, lenght = 1
  1170. switch( m_Orient )
  1171. {
  1172. case PIN_UP:
  1173. end.y = 1; break;
  1174. case PIN_DOWN:
  1175. end.y = -1; break;
  1176. case PIN_LEFT:
  1177. end.x = -1; break;
  1178. case PIN_RIGHT:
  1179. end.x = 1; break;
  1180. }
  1181. // = pos of end point, according to the component orientation
  1182. end = TransformCoordinate( TransMat, end );
  1183. orient = PIN_UP;
  1184. if( end.x == 0 )
  1185. {
  1186. if( end.y > 0 )
  1187. orient = PIN_DOWN;
  1188. }
  1189. else
  1190. {
  1191. orient = PIN_RIGHT;
  1192. if( end.x < 0 )
  1193. orient = PIN_LEFT;
  1194. }
  1195. return orient;
  1196. }
  1197. /** Function ReturnPinStringNum
  1198. * fill a buffer with pin num as a wxString
  1199. * Pin num is coded as a long or 4 ascii chars
  1200. * Used to print/draw the pin num
  1201. * @param aStringBuffer = the wxString to store the pin num as an unicode string
  1202. */
  1203. void LIB_PIN::ReturnPinStringNum( wxString& aStringBuffer ) const
  1204. {
  1205. aStringBuffer = ReturnPinStringNum( m_PinNum );
  1206. }
  1207. /** Function ReturnPinStringNum (static function)
  1208. * Pin num is coded as a long or 4 ascii chars
  1209. * @param aPinNum = a long containing a pin num
  1210. * @return aStringBuffer = the wxString to store the pin num as an unicode string
  1211. */
  1212. wxString LIB_PIN::ReturnPinStringNum( long aPinNum )
  1213. {
  1214. char ascii_buf[5];
  1215. memcpy( ascii_buf, &aPinNum, 4 );
  1216. ascii_buf[4] = 0;
  1217. wxString buffer = CONV_FROM_UTF8( ascii_buf );
  1218. return buffer;
  1219. }
  1220. wxString LIB_PIN::GetNumber( void )
  1221. {
  1222. return ReturnPinStringNum( m_PinNum );
  1223. }
  1224. /** Function LIB_PIN::SetPinNumFromString()
  1225. * fill the buffer with pin num as a wxString
  1226. * Pin num is coded as a long
  1227. * Used to print/draw the pin num
  1228. */
  1229. void LIB_PIN::SetPinNumFromString( wxString& buffer )
  1230. {
  1231. char ascii_buf[4];
  1232. unsigned ii, len = buffer.Len();
  1233. ascii_buf[0] = ascii_buf[1] = ascii_buf[2] = ascii_buf[3] = 0;
  1234. if( len > 4 )
  1235. len = 4;
  1236. for( ii = 0; ii < len; ii++ )
  1237. {
  1238. ascii_buf[ii] = buffer.GetChar( ii );
  1239. ascii_buf[ii] &= 0xFF;
  1240. }
  1241. strncpy( (char*) &m_PinNum, ascii_buf, 4 );
  1242. }
  1243. LIB_DRAW_ITEM* LIB_PIN::DoGenCopy()
  1244. {
  1245. LIB_PIN* newpin = new LIB_PIN( GetParent() );
  1246. newpin->m_Pos = m_Pos;
  1247. newpin->m_PinLen = m_PinLen;
  1248. newpin->m_Orient = m_Orient;
  1249. newpin->m_PinShape = m_PinShape;
  1250. newpin->m_PinType = m_PinType;
  1251. newpin->m_Attributs = m_Attributs;
  1252. newpin->m_PinNum = m_PinNum;
  1253. newpin->m_PinNumSize = m_PinNumSize;
  1254. newpin->m_PinNameSize = m_PinNameSize;
  1255. newpin->m_PinNumShapeOpt = m_PinNumShapeOpt;
  1256. newpin->m_PinNameShapeOpt = m_PinNameShapeOpt;
  1257. newpin->m_PinNumPositionOpt = m_PinNumPositionOpt;
  1258. newpin->m_PinNamePositionOpt = m_PinNamePositionOpt;
  1259. newpin->m_Unit = m_Unit;
  1260. newpin->m_Convert = m_Convert;
  1261. newpin->m_Flags = m_Flags;
  1262. newpin->m_Width = m_Width;
  1263. newpin->m_PinName = m_PinName;
  1264. return (LIB_DRAW_ITEM*) newpin;
  1265. }
  1266. int LIB_PIN::DoCompare( const LIB_DRAW_ITEM& other ) const
  1267. {
  1268. wxASSERT( other.Type() == COMPONENT_PIN_DRAW_TYPE );
  1269. const LIB_PIN* tmp = ( LIB_PIN* ) &other;
  1270. if( m_PinNum != tmp->m_PinNum )
  1271. return m_PinNum - tmp->m_PinNum;
  1272. int result = m_PinName.CmpNoCase( tmp->m_PinName );
  1273. if( result != 0 )
  1274. return result;
  1275. if( m_Pos.x != tmp->m_Pos.x )
  1276. return m_Pos.x - tmp->m_Pos.x;
  1277. if( m_Pos.y != tmp->m_Pos.y )
  1278. return m_Pos.y - tmp->m_Pos.y;
  1279. return 0;
  1280. }
  1281. void LIB_PIN::DoOffset( const wxPoint& offset )
  1282. {
  1283. m_Pos += offset;
  1284. }
  1285. bool LIB_PIN::DoTestInside( EDA_Rect& rect )
  1286. {
  1287. wxPoint end = ReturnPinEndPoint();
  1288. return rect.Inside( m_Pos.x, -m_Pos.y ) || rect.Inside( end.x, -end.y );
  1289. }
  1290. void LIB_PIN::DoMove( const wxPoint& newPosition )
  1291. {
  1292. m_Pos = newPosition;
  1293. }
  1294. void LIB_PIN::DoMirrorHorizontal( const wxPoint& center )
  1295. {
  1296. m_Pos.x -= center.x;
  1297. m_Pos.x *= -1;
  1298. m_Pos.x += center.x;
  1299. if( m_Orient == PIN_RIGHT )
  1300. m_Orient = PIN_LEFT;
  1301. else if( m_Orient == PIN_LEFT )
  1302. m_Orient = PIN_RIGHT;
  1303. }
  1304. void LIB_PIN::DoPlot( PLOTTER* plotter, const wxPoint& offset, bool fill,
  1305. const int transform[2][2] )
  1306. {
  1307. if( m_Attributs & PINNOTDRAW )
  1308. return;
  1309. int orient = ReturnPinDrawOrient( transform );
  1310. wxPoint pos = TransformCoordinate( transform, m_Pos ) + offset;
  1311. plotter->set_current_line_width( GetPenSize() );
  1312. PlotPinSymbol( plotter, pos, m_PinLen, orient, m_PinShape );
  1313. PlotPinTexts( plotter, pos, orient, GetParent()->m_TextInside,
  1314. GetParent()->m_DrawPinNum, GetParent()->m_DrawPinName,
  1315. GetPenSize() );
  1316. }
  1317. /** Function LIB_PIN::DisplayInfo
  1318. * Displays info (pin num and name, orientation ...
  1319. * on the Info window
  1320. */
  1321. void LIB_PIN::DisplayInfo( WinEDA_DrawFrame* frame )
  1322. {
  1323. wxString Text;
  1324. LIB_DRAW_ITEM::DisplayInfo( frame );
  1325. frame->AppendMsgPanel( _( "Name" ), m_PinName, DARKCYAN );
  1326. if( m_PinNum == 0 )
  1327. Text = wxT( "?" );
  1328. else
  1329. ReturnPinStringNum( Text );
  1330. frame->AppendMsgPanel( _( "Number" ), Text, DARKCYAN );
  1331. frame->AppendMsgPanel( _( "Type" ),
  1332. pin_electrical_type_names[ m_PinType ], RED );
  1333. Text = pin_style_names[ GetStyleCodeIndex( m_PinShape ) ];
  1334. frame->AppendMsgPanel( _( "Style" ), Text, BLUE );
  1335. if( IsVisible() )
  1336. Text = _( "Yes" );
  1337. else
  1338. Text = _( "No" );
  1339. frame->AppendMsgPanel( _( "Visible" ), Text, DARKGREEN );
  1340. /* Display pin length */
  1341. Text = ReturnStringFromValue( g_UnitMetric, m_PinLen,
  1342. EESCHEMA_INTERNAL_UNIT, true );
  1343. frame->AppendMsgPanel( _( "Length" ), Text, MAGENTA );
  1344. Text = pin_orientation_names[ GetOrientationCodeIndex( m_Orient ) ];
  1345. frame->AppendMsgPanel( _( "Orientation" ), Text, DARKMAGENTA );
  1346. }
  1347. /** Function LIB_PIN::GetBoundingBox
  1348. * @return the boundary box for this, in schematic coordinates
  1349. */
  1350. EDA_Rect LIB_PIN::GetBoundingBox()
  1351. {
  1352. wxPoint pt = m_Pos;
  1353. pt.y *= -1; // Reverse the Y axis, according to the schematic orientation
  1354. return EDA_Rect( pt, wxSize( 1, 1 ) );
  1355. }
  1356. wxArrayString LIB_PIN::GetOrientationNames( void )
  1357. {
  1358. return wxArrayString( PIN_ORIENTATION_CNT, pin_orientation_names );
  1359. }
  1360. int LIB_PIN::GetOrientationCode( int index )
  1361. {
  1362. if( index >= 0 && index < (int) PIN_ORIENTATION_CNT )
  1363. return pin_orientation_codes[ index ];
  1364. return PIN_RIGHT;
  1365. }
  1366. int LIB_PIN::GetOrientationCodeIndex( int code )
  1367. {
  1368. size_t i;
  1369. for( i = 0; i < PIN_ORIENTATION_CNT; i++ )
  1370. {
  1371. if( pin_orientation_codes[i] == code )
  1372. return (int) i;
  1373. }
  1374. return wxNOT_FOUND;
  1375. }
  1376. wxArrayString LIB_PIN::GetStyleNames( void )
  1377. {
  1378. return wxArrayString( PIN_STYLE_CNT, pin_style_names );
  1379. }
  1380. int LIB_PIN::GetStyleCode( int index )
  1381. {
  1382. if( index >= 0 && index < (int) PIN_STYLE_CNT )
  1383. return pin_style_codes[ index ];
  1384. return NONE;
  1385. }
  1386. int LIB_PIN::GetStyleCodeIndex( int code )
  1387. {
  1388. size_t i;
  1389. for( i = 0; i < PIN_STYLE_CNT; i++ )
  1390. {
  1391. if( pin_style_codes[i] == code )
  1392. return (int) i;
  1393. }
  1394. return wxNOT_FOUND;
  1395. }
  1396. wxArrayString LIB_PIN::GetElectricalTypeNames( void )
  1397. {
  1398. return wxArrayString( PIN_ELECTRICAL_TYPE_CNT, pin_electrical_type_names );
  1399. }