Undo changes from my last commit that caused a trace drag bug.
This commit is contained in:
parent
134a935376
commit
cb78c9452b
|
@ -8,19 +8,32 @@
|
||||||
static const char png[] = {
|
static const char png[] = {
|
||||||
0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a, 0x00, 0x00, 0x00, 0x0d, 0x49, 0x48, 0x44, 0x52,
|
0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a, 0x00, 0x00, 0x00, 0x0d, 0x49, 0x48, 0x44, 0x52,
|
||||||
0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00, 0x1a, 0x08, 0x06, 0x00, 0x00, 0x00, 0xa9, 0x4a, 0x4c,
|
0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00, 0x1a, 0x08, 0x06, 0x00, 0x00, 0x00, 0xa9, 0x4a, 0x4c,
|
||||||
0xce, 0x00, 0x00, 0x00, 0xb1, 0x49, 0x44, 0x41, 0x54, 0x48, 0xc7, 0x63, 0xf8, 0xff, 0xff, 0x3f,
|
0xce, 0x00, 0x00, 0x00, 0x09, 0x76, 0x70, 0x41, 0x67, 0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00,
|
||||||
0x03, 0x3d, 0x30, 0x82, 0xd1, 0xc0, 0xc0, 0x24, 0x50, 0x20, 0x20, 0x40, 0x4d, 0xcc, 0x90, 0xc6,
|
0x1a, 0x00, 0x07, 0xb2, 0x66, 0x2f, 0x00, 0x00, 0x01, 0x64, 0x49, 0x44, 0x41, 0x54, 0x48, 0xc7,
|
||||||
0xc0, 0x8a, 0x61, 0x91, 0x50, 0x01, 0xd7, 0x6e, 0xa1, 0x7c, 0xce, 0x2f, 0x42, 0x05, 0x9c, 0x9f,
|
0xd5, 0x96, 0xb1, 0x4e, 0x02, 0x41, 0x10, 0x86, 0xbf, 0xb9, 0xbb, 0xa5, 0x38, 0xa3, 0x31, 0x21,
|
||||||
0xa8, 0x86, 0x73, 0x38, 0x9f, 0x30, 0x84, 0x32, 0xb0, 0xc1, 0x2d, 0x12, 0x49, 0x62, 0xe0, 0x15,
|
0xda, 0x28, 0x34, 0x1a, 0xe9, 0xa4, 0x35, 0x3c, 0x03, 0xa1, 0xb1, 0xb2, 0xb0, 0xf7, 0x21, 0xe4,
|
||||||
0xcc, 0xe1, 0xfc, 0xa1, 0x74, 0x56, 0xe8, 0xbf, 0xd2, 0x39, 0xea, 0x61, 0x91, 0x3a, 0xee, 0x77,
|
0x11, 0x78, 0x05, 0x0b, 0x5e, 0x81, 0xc6, 0xc6, 0x52, 0x63, 0x30, 0x34, 0x24, 0x58, 0x99, 0xa0,
|
||||||
0x82, 0x99, 0x1c, 0xb6, 0x70, 0x8b, 0x40, 0xde, 0x14, 0xca, 0xe3, 0xfc, 0x46, 0x4d, 0x4b, 0x40,
|
0x84, 0x82, 0xc4, 0x12, 0x84, 0x53, 0xb8, 0x1d, 0x0b, 0x90, 0x28, 0x9c, 0xd1, 0x18, 0xee, 0x12,
|
||||||
0x58, 0xb4, 0x99, 0xe7, 0x9d, 0x40, 0x06, 0x87, 0xc3, 0xa8, 0x45, 0xa3, 0x16, 0x8d, 0x5a, 0x34,
|
0xff, 0x6e, 0x27, 0x9b, 0xf9, 0xb2, 0xff, 0xec, 0xce, 0x8e, 0x00, 0x04, 0x41, 0x50, 0x02, 0xca,
|
||||||
0x6a, 0xd1, 0xa8, 0x45, 0xa3, 0x16, 0x8d, 0x4c, 0x8b, 0x04, 0xd3, 0x04, 0xf9, 0x69, 0x62, 0x51,
|
0x02, 0x79, 0x44, 0x0c, 0x9f, 0x24, 0x00, 0x22, 0x7c, 0x89, 0x2d, 0xac, 0xbf, 0x51, 0x08, 0xb4,
|
||||||
0x13, 0xd0, 0xa2, 0x4c, 0x0e, 0x7b, 0xb8, 0x45, 0x40, 0xc0, 0x08, 0xb4, 0xe8, 0xbe, 0x58, 0x3b,
|
0x80, 0x8a, 0x31, 0xa6, 0x2a, 0xa3, 0xd1, 0xa8, 0x08, 0xd4, 0x54, 0x2d, 0xfd, 0xd7, 0xc1, 0xd2,
|
||||||
0xcf, 0x27, 0xb1, 0x2e, 0x9e, 0x0f, 0xd4, 0xc2, 0x42, 0xb9, 0x5c, 0x1f, 0x79, 0xb3, 0x79, 0x85,
|
0xee, 0x48, 0xd0, 0x2f, 0xe1, 0x7e, 0xca, 0xc7, 0xb8, 0x06, 0xe0, 0x4c, 0x86, 0xc3, 0xe1, 0x35,
|
||||||
0x51, 0x5b, 0x41, 0x59, 0x9c, 0xb2, 0x02, 0x99, 0x5c, 0x01, 0xd4, 0xc4, 0x82, 0x99, 0xdc, 0x7a,
|
0x50, 0x38, 0xb9, 0x38, 0xa6, 0xf1, 0x54, 0xc7, 0x71, 0x1c, 0x56, 0xa5, 0x75, 0x6f, 0x83, 0xfa,
|
||||||
0x18, 0xcd, 0x2d, 0x5a, 0x63, 0x00, 0xe2, 0xb1, 0x17, 0xfe, 0x13, 0xe0, 0x61, 0xbb, 0x00, 0x00,
|
0x79, 0x93, 0x94, 0x97, 0xea, 0x7a, 0x6a, 0xed, 0xe1, 0xcb, 0xdb, 0x0b, 0xb7, 0x0f, 0x37, 0xac,
|
||||||
0x00, 0x00, 0x49, 0x45, 0x4e, 0x44, 0xae, 0x42, 0x60, 0x82,
|
0x9d, 0xba, 0x20, 0xe1, 0xca, 0x40, 0xc1, 0x65, 0x40, 0xe3, 0xf1, 0x8e, 0xa3, 0xbd, 0xc2, 0xae,
|
||||||
|
0xa3, 0xaa, 0x66, 0x62, 0x43, 0x5c, 0xd7, 0x99, 0x79, 0xb2, 0x3a, 0x89, 0x11, 0x42, 0x1b, 0xa2,
|
||||||
|
0xaa, 0x38, 0xaa, 0x8a, 0xaa, 0x12, 0x97, 0x3e, 0xf2, 0x4f, 0x41, 0xd6, 0x26, 0x04, 0x4a, 0xea,
|
||||||
|
0x44, 0xc4, 0x06, 0x9a, 0xe6, 0x8e, 0xff, 0x44, 0x1a, 0x65, 0x9d, 0xc6, 0x68, 0x9d, 0xb5, 0x09,
|
||||||
|
0xd4, 0x68, 0x06, 0x8b, 0x1d, 0x34, 0xaf, 0x11, 0x89, 0xbe, 0xa3, 0x44, 0x40, 0xd6, 0xc6, 0x06,
|
||||||
|
0xd2, 0xa5, 0x1a, 0x41, 0xac, 0x35, 0x22, 0xf9, 0xce, 0x90, 0x64, 0xaf, 0xd3, 0xff, 0x7e, 0xeb,
|
||||||
|
0x48, 0x14, 0x34, 0x6b, 0x41, 0xe3, 0x18, 0x7d, 0x9b, 0xdb, 0xe7, 0xa9, 0x6a, 0xd3, 0x37, 0x7e,
|
||||||
|
0x21, 0xed, 0xa7, 0x19, 0x5c, 0xf5, 0x71, 0x3c, 0x89, 0x9a, 0x83, 0xfe, 0xa4, 0xf1, 0xf3, 0x84,
|
||||||
|
0xfd, 0xad, 0x03, 0x54, 0xb5, 0x2b, 0x9d, 0x76, 0xbb, 0x08, 0xd4, 0x7a, 0xfd, 0x1e, 0xf7, 0xbd,
|
||||||
|
0x56, 0xc4, 0xc7, 0x2f, 0x11, 0xa8, 0x08, 0xb8, 0x2c, 0x44, 0x45, 0xc8, 0x6c, 0x66, 0xc8, 0x6d,
|
||||||
|
0xe7, 0xa6, 0xe3, 0x16, 0x40, 0xa7, 0xdd, 0x2e, 0x01, 0x65, 0x20, 0x0f, 0x98, 0x9f, 0xa7, 0x8e,
|
||||||
|
0x08, 0xf8, 0x62, 0x4c, 0x24, 0x04, 0x5a, 0x02, 0x95, 0x9d, 0x6c, 0xb6, 0xfa, 0x0e, 0x74, 0x04,
|
||||||
|
0x22, 0x77, 0x71, 0x16, 0xc1, 0x16, 0x00, 0x00, 0x00, 0x00, 0x49, 0x45, 0x4e, 0x44, 0xae, 0x42,
|
||||||
|
0x60, 0x82,
|
||||||
};
|
};
|
||||||
|
|
||||||
const BITMAP_OPAQUE erc_green_xpm[1] = {{ png, sizeof( png ), "erc_green_xpm" }};
|
const BITMAP_OPAQUE erc_green_xpm[1] = {{ png, sizeof( png ), "erc_green_xpm" }};
|
||||||
|
|
|
@ -8,71 +8,65 @@
|
||||||
static const char png[] = {
|
static const char png[] = {
|
||||||
0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a, 0x00, 0x00, 0x00, 0x0d, 0x49, 0x48, 0x44, 0x52,
|
0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a, 0x00, 0x00, 0x00, 0x0d, 0x49, 0x48, 0x44, 0x52,
|
||||||
0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00, 0x1a, 0x08, 0x06, 0x00, 0x00, 0x00, 0xa9, 0x4a, 0x4c,
|
0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00, 0x1a, 0x08, 0x06, 0x00, 0x00, 0x00, 0xa9, 0x4a, 0x4c,
|
||||||
0xce, 0x00, 0x00, 0x03, 0xf2, 0x49, 0x44, 0x41, 0x54, 0x48, 0xc7, 0xbd, 0x56, 0xeb, 0x4f, 0x93,
|
0xce, 0x00, 0x00, 0x03, 0x8b, 0x49, 0x44, 0x41, 0x54, 0x48, 0xc7, 0xc5, 0x56, 0x5b, 0x4b, 0x54,
|
||||||
0x57, 0x18, 0xaf, 0x7f, 0x80, 0x0a, 0xda, 0xa8, 0x40, 0x91, 0x62, 0x54, 0xdc, 0x12, 0xd4, 0x38,
|
0x51, 0x14, 0xf6, 0x2f, 0x94, 0x52, 0x56, 0x8e, 0xa3, 0x20, 0x5e, 0xa2, 0xcc, 0x0a, 0x2b, 0x21,
|
||||||
0x4d, 0x50, 0xa4, 0xe5, 0xba, 0x98, 0x4d, 0x2e, 0x4b, 0x43, 0xcc, 0x3e, 0x4d, 0x31, 0x99, 0x90,
|
0x6b, 0x28, 0xb5, 0x54, 0xb0, 0x42, 0xc4, 0x27, 0x89, 0x8c, 0x54, 0x90, 0x4a, 0x9d, 0xb1, 0xf1,
|
||||||
0x19, 0x83, 0xa2, 0x14, 0x50, 0xb4, 0x08, 0x61, 0x4c, 0xcd, 0x0c, 0x24, 0x73, 0x06, 0xf0, 0x92,
|
0x92, 0xa4, 0x29, 0x68, 0x92, 0xd4, 0x43, 0x5a, 0x69, 0xea, 0xa0, 0xa8, 0x0f, 0x29, 0x3e, 0x28,
|
||||||
0x10, 0xc2, 0x30, 0x5e, 0x12, 0xf5, 0xcb, 0x64, 0x36, 0x81, 0x44, 0x64, 0x64, 0xb1, 0x26, 0x8c,
|
0x4a, 0xde, 0x22, 0x15, 0xd4, 0xbc, 0xa6, 0x28, 0x46, 0x48, 0x85, 0x05, 0x81, 0xa9, 0x8c, 0x33,
|
||||||
0xd4, 0x88, 0x06, 0xa7, 0x76, 0xf1, 0xce, 0x45, 0x90, 0x02, 0x7d, 0xcf, 0xcf, 0xe7, 0x3c, 0x7d,
|
0x79, 0x39, 0x7b, 0x9c, 0xaf, 0x75, 0xb6, 0xe3, 0x61, 0x46, 0x9d, 0x52, 0x18, 0xeb, 0xc0, 0xe2,
|
||||||
0xdb, 0xb4, 0xb4, 0x20, 0x1f, 0x8a, 0x6f, 0xf2, 0xe4, 0x3d, 0xef, 0x39, 0xcf, 0x79, 0x7e, 0xcf,
|
0x9c, 0xd9, 0xfb, 0xdb, 0xfb, 0x5b, 0xeb, 0x5b, 0x6b, 0xaf, 0x3d, 0x76, 0x00, 0xec, 0xfe, 0x85,
|
||||||
0xf9, 0x3d, 0x97, 0xf3, 0x6a, 0x00, 0x68, 0x3e, 0x87, 0x78, 0x07, 0x66, 0x73, 0xec, 0xba, 0xd2,
|
0x49, 0x1f, 0x6a, 0xb5, 0xeb, 0xb1, 0xd4, 0x54, 0xd9, 0x55, 0xdb, 0x9a, 0xd3, 0x79, 0x0b, 0xa2,
|
||||||
0xd2, 0xe8, 0x9c, 0xd0, 0x8a, 0xce, 0xe8, 0x07, 0x74, 0xf8, 0xb0, 0x2e, 0xaa, 0xbc, 0x3c, 0x66,
|
0xf4, 0x74, 0xa7, 0x43, 0x19, 0x19, 0x72, 0xbd, 0x46, 0xe3, 0xb9, 0x60, 0x4b, 0xcb, 0xce, 0x76,
|
||||||
0xe4, 0xe2, 0xc5, 0x35, 0xc3, 0xa1, 0x94, 0xca, 0x4a, 0xfd, 0x48, 0x49, 0xc9, 0xf2, 0x74, 0x2f,
|
0xd1, 0xa7, 0xa4, 0x38, 0x07, 0x48, 0x44, 0x6a, 0xb5, 0xec, 0x4a, 0x59, 0x99, 0xc7, 0xfc, 0xea,
|
||||||
0x90, 0xd9, 0x1c, 0x9d, 0x7d, 0xfe, 0x7c, 0xdc, 0x80, 0xa2, 0x24, 0x23, 0x94, 0x62, 0xb5, 0xae,
|
0xaa, 0x02, 0xb6, 0xb4, 0x8e, 0x0e, 0x1f, 0x10, 0xd1, 0x03, 0x89, 0x48, 0x0c, 0xb3, 0xbc, 0xdc,
|
||||||
0x07, 0x01, 0x1d, 0xf3, 0x02, 0xc9, 0x63, 0x5e, 0xb8, 0xf0, 0xc5, 0x5c, 0x01, 0x59, 0x02, 0x80,
|
0x6b, 0xb7, 0x88, 0x32, 0xff, 0x2f, 0x91, 0xd1, 0x58, 0x4a, 0xa0, 0xf7, 0x58, 0x5e, 0xbe, 0x05,
|
||||||
0x84, 0xf8, 0x03, 0x42, 0x74, 0x93, 0x52, 0x21, 0x26, 0x27, 0x8d, 0x70, 0xb9, 0xa6, 0x6e, 0x36,
|
0xc6, 0xce, 0x6f, 0x5a, 0x6c, 0x34, 0x16, 0xf3, 0x79, 0x83, 0xe1, 0x0d, 0x96, 0x96, 0xce, 0x6d,
|
||||||
0xf1, 0xba, 0x5b, 0xe7, 0x14, 0xeb, 0x04, 0x02, 0xa4, 0xd0, 0xfa, 0x1d, 0x92, 0xbf, 0xd1, 0xde,
|
0x41, 0x10, 0x42, 0x98, 0x3e, 0x5a, 0xdb, 0x80, 0x96, 0x96, 0x63, 0xd6, 0x89, 0x18, 0x2b, 0x84,
|
||||||
0x9e, 0x08, 0xb3, 0x39, 0x28, 0x50, 0x33, 0xe4, 0xf3, 0xe1, 0x43, 0x0b, 0xee, 0xdd, 0xdb, 0x88,
|
0xf8, 0x68, 0x34, 0x39, 0xe8, 0xed, 0x3d, 0x49, 0xbf, 0x37, 0x12, 0xcd, 0x60, 0xfd, 0x49, 0x4a,
|
||||||
0x27, 0x4f, 0x36, 0xfb, 0x81, 0x09, 0x71, 0x02, 0x9e, 0x67, 0x74, 0xd4, 0xce, 0x3a, 0xc3, 0xc3,
|
0xf2, 0xc5, 0xe2, 0xa2, 0x25, 0x99, 0xc1, 0xa0, 0xe6, 0x73, 0xcd, 0xcd, 0x15, 0x88, 0x8c, 0xdc,
|
||||||
0x49, 0x53, 0x80, 0x76, 0xf3, 0xfa, 0xc4, 0x44, 0x3f, 0x1a, 0x1a, 0xe2, 0xb0, 0x77, 0x6f, 0x54,
|
0x07, 0xa5, 0x52, 0x96, 0x6d, 0x85, 0xe8, 0x06, 0x07, 0xf6, 0xf4, 0xb4, 0xa0, 0xa4, 0xc4, 0x03,
|
||||||
0xb5, 0x46, 0xa3, 0x99, 0x37, 0x05, 0x68, 0xbf, 0x6a, 0xe4, 0x5f, 0xa4, 0xa4, 0x84, 0xa3, 0xb0,
|
0x2b, 0x2b, 0xe6, 0x51, 0x45, 0xf3, 0xb9, 0x91, 0x91, 0x6e, 0xfe, 0x7e, 0xfc, 0x38, 0x09, 0x1f,
|
||||||
0x50, 0x87, 0xb1, 0x31, 0x83, 0x0f, 0x50, 0x3b, 0xad, 0x0a, 0x0c, 0x0d, 0x3d, 0xa4, 0xb1, 0x40,
|
0x3f, 0x9e, 0xa6, 0xcd, 0xcd, 0x9d, 0xa9, 0xe2, 0x73, 0xf7, 0xef, 0x5f, 0x47, 0x72, 0xb2, 0x0c,
|
||||||
0x56, 0xd6, 0x2a, 0xdc, 0xbc, 0x19, 0x4f, 0x46, 0x8d, 0x3e, 0x3a, 0x75, 0x6c, 0xe3, 0xd6, 0xad,
|
0x2a, 0x95, 0xec, 0xa1, 0x15, 0x22, 0xd1, 0x66, 0xa1, 0xd7, 0x6b, 0x91, 0x90, 0xe0, 0x4c, 0xf2,
|
||||||
0x7a, 0x6c, 0xd8, 0x30, 0x1f, 0x3b, 0x77, 0x2e, 0xfb, 0x35, 0x00, 0x48, 0x51, 0x32, 0xe8, 0xd3,
|
0x98, 0x13, 0x3d, 0xe7, 0x9b, 0xc4, 0xc7, 0x87, 0xd0, 0xe6, 0x0c, 0x5d, 0x5d, 0x4d, 0xa8, 0xae,
|
||||||
0x49, 0xe2, 0x42, 0x76, 0x76, 0x14, 0x32, 0x32, 0x16, 0xe1, 0xfd, 0x7b, 0x8f, 0xc7, 0x69, 0x34,
|
0x3e, 0x0c, 0x41, 0x30, 0xc7, 0x8c, 0x93, 0x19, 0x10, 0x1c, 0x2c, 0xe7, 0x8e, 0xaa, 0xd5, 0xce,
|
||||||
0x3f, 0x42, 0x86, 0x1e, 0x91, 0x91, 0x93, 0x6c, 0xac, 0xa2, 0xe2, 0x47, 0x1c, 0x3d, 0xaa, 0x87,
|
0x59, 0x56, 0x8b, 0x81, 0xb1, 0x16, 0xbe, 0x61, 0x5c, 0x9c, 0x3f, 0x74, 0x3a, 0x73, 0x69, 0x06,
|
||||||
0xd3, 0xe9, 0x0b, 0xd4, 0xc1, 0x6b, 0x87, 0x0e, 0x99, 0x90, 0x96, 0x16, 0x8e, 0x03, 0x07, 0x74,
|
0xf1, 0xeb, 0xd7, 0x2c, 0x14, 0x8a, 0x3d, 0xf4, 0x1e, 0x24, 0xd9, 0xf4, 0xe4, 0xb1, 0xab, 0x99,
|
||||||
0x95, 0x41, 0x93, 0x41, 0xf2, 0x2f, 0x9f, 0xfa, 0xfa, 0x1d, 0xd8, 0xba, 0x75, 0x21, 0xee, 0xdf,
|
0x33, 0x97, 0x69, 0x95, 0x01, 0x93, 0x93, 0xfd, 0x08, 0x0d, 0xb5, 0x47, 0x53, 0x93, 0xf7, 0x9f,
|
||||||
0xdf, 0xa4, 0xc6, 0x62, 0x1f, 0xcf, 0x8f, 0x8f, 0xb7, 0xd2, 0x49, 0xd3, 0x79, 0xdc, 0xd9, 0x79,
|
0xab, 0x8e, 0xb1, 0x5c, 0x4e, 0x54, 0x50, 0xa0, 0xc4, 0xd8, 0x98, 0xaf, 0x29, 0x4f, 0xe2, 0x26,
|
||||||
0x15, 0x99, 0x99, 0x5a, 0x1f, 0x67, 0x52, 0x68, 0x76, 0x80, 0xde, 0xe3, 0x48, 0x4f, 0x5f, 0x8a,
|
0x02, 0x45, 0x51, 0x8b, 0xe8, 0xe8, 0x03, 0xb4, 0xf9, 0x4b, 0x8e, 0x49, 0x4e, 0x0e, 0xc3, 0xfc,
|
||||||
0x82, 0x82, 0x28, 0x14, 0x15, 0x45, 0x1f, 0x9f, 0x06, 0xe8, 0x77, 0x36, 0xd2, 0xd3, 0x53, 0x87,
|
0xfc, 0x59, 0x13, 0x91, 0x8a, 0x8f, 0x95, 0x95, 0xe5, 0x22, 0x3d, 0x5d, 0xfe, 0xe7, 0x62, 0x58,
|
||||||
0xa4, 0xa4, 0x85, 0x68, 0x6e, 0xfe, 0x92, 0xa9, 0xf1, 0xc4, 0xef, 0xc1, 0x83, 0x9f, 0x90, 0x9c,
|
0x23, 0x0a, 0xe7, 0x0b, 0x5a, 0x5b, 0x5f, 0xa3, 0xa6, 0x66, 0x5d, 0x9a, 0x34, 0x3e, 0x96, 0x93,
|
||||||
0xbc, 0x88, 0x4e, 0xf1, 0x8e, 0x68, 0x1d, 0xe0, 0xb1, 0xcd, 0xb6, 0x51, 0x75, 0xe6, 0x07, 0xd6,
|
0x13, 0x83, 0xc2, 0x42, 0x77, 0x22, 0xba, 0xc9, 0x7f, 0x57, 0x55, 0x3d, 0x25, 0xf2, 0xe3, 0xa6,
|
||||||
0x79, 0xfa, 0xf4, 0x0e, 0xef, 0xad, 0xad, 0x5d, 0x85, 0xe2, 0xe2, 0xe5, 0x15, 0xd3, 0xa4, 0xf7,
|
0x0a, 0xad, 0x30, 0x29, 0x11, 0x84, 0xfa, 0xfa, 0x23, 0x68, 0x6b, 0xfb, 0x0b, 0x91, 0x98, 0x5c,
|
||||||
0x6e, 0x35, 0x4e, 0x5d, 0xac, 0x5c, 0x5a, 0x1a, 0xc3, 0x71, 0x02, 0xfa, 0x98, 0xd6, 0xb3, 0x67,
|
0x41, 0xf8, 0x8c, 0x1f, 0x3f, 0xa6, 0x29, 0xa9, 0x72, 0x93, 0x34, 0xf5, 0x04, 0x35, 0x22, 0x2c,
|
||||||
0xe3, 0x61, 0x30, 0x84, 0x51, 0x9c, 0xfe, 0x64, 0xbd, 0x3d, 0x7b, 0xd2, 0xd0, 0xd8, 0x18, 0x47,
|
0xcc, 0x0d, 0x7d, 0x7d, 0x27, 0x69, 0x5e, 0x74, 0x68, 0x0e, 0x9f, 0x3e, 0x8d, 0xe1, 0xc9, 0x13,
|
||||||
0x27, 0x95, 0xce, 0x9c, 0xe6, 0xb9, 0x4b, 0x97, 0x8e, 0x23, 0x35, 0x35, 0x1c, 0xd7, 0xaf, 0xc7,
|
0x37, 0x3a, 0x0e, 0x22, 0xe6, 0x03, 0x61, 0xb5, 0x24, 0xad, 0x3d, 0xbe, 0x7e, 0xf5, 0x43, 0x7b,
|
||||||
0x07, 0x4f, 0x6f, 0xdf, 0xe3, 0x0b, 0x31, 0x8a, 0xdc, 0xdc, 0x65, 0x14, 0x2b, 0x2d, 0x65, 0xe1,
|
0xfb, 0x36, 0x0e, 0x2c, 0x63, 0x75, 0xdc, 0xbb, 0x98, 0x18, 0x1f, 0xca, 0xc7, 0x39, 0x2a, 0xeb,
|
||||||
0x77, 0x6c, 0xc0, 0xe5, 0xea, 0x42, 0x5e, 0x5e, 0x04, 0xcd, 0x2f, 0x21, 0xc3, 0xd5, 0x3c, 0xd7,
|
0xef, 0x98, 0x9e, 0x1e, 0x45, 0x48, 0x88, 0x3d, 0x16, 0x16, 0xfc, 0x4d, 0x98, 0x37, 0x34, 0xbe,
|
||||||
0xd4, 0x54, 0x83, 0xfc, 0xfc, 0x48, 0x76, 0x46, 0x08, 0x2b, 0xcf, 0xe5, 0xe5, 0x6d, 0x91, 0xd9,
|
0x8a, 0xd8, 0x58, 0x77, 0xca, 0x57, 0x00, 0x97, 0xb6, 0xa7, 0xa7, 0x01, 0x51, 0x51, 0xfb, 0x79,
|
||||||
0x46, 0xb1, 0x5c, 0x37, 0x13, 0x90, 0xa4, 0xef, 0x2f, 0xde, 0xd0, 0xd0, 0xf0, 0x2d, 0x7b, 0xff,
|
0xd9, 0x6f, 0xab, 0x33, 0x08, 0x42, 0x2a, 0x27, 0xca, 0xca, 0xba, 0x89, 0x6f, 0xdf, 0x22, 0xf8,
|
||||||
0xf2, 0x65, 0x15, 0x7f, 0x0f, 0x0e, 0x9e, 0x86, 0xd1, 0x18, 0x86, 0x9a, 0x9a, 0x15, 0x04, 0xe4,
|
0x77, 0x75, 0x75, 0x81, 0xb8, 0x50, 0x4a, 0xbe, 0x20, 0xe4, 0xf0, 0x71, 0x95, 0x2a, 0x1c, 0x73,
|
||||||
0x06, 0xef, 0xef, 0xff, 0x87, 0xe8, 0x0b, 0xc3, 0x8b, 0x17, 0x89, 0xf4, 0xf5, 0x86, 0xe6, 0x5f,
|
0x73, 0xf1, 0xfc, 0x3b, 0x3f, 0xff, 0xae, 0x14, 0xe1, 0xb6, 0x88, 0x18, 0x0b, 0x26, 0x6f, 0x0d,
|
||||||
0x31, 0x13, 0xd4, 0x82, 0xd0, 0xd6, 0xf6, 0x49, 0xa0, 0x5f, 0xd8, 0x48, 0x6f, 0xef, 0xcf, 0xbc,
|
0xa8, 0xad, 0x7d, 0x81, 0xd1, 0xd1, 0x6c, 0x53, 0x59, 0x5f, 0x42, 0x5d, 0xdd, 0x11, 0xa9, 0x9c,
|
||||||
0xc9, 0xe1, 0x70, 0xd3, 0x64, 0xb5, 0x6e, 0xe7, 0xef, 0xdb, 0xb7, 0xd7, 0x73, 0x4c, 0x64, 0x06,
|
0x19, 0xbb, 0xca, 0xe5, 0xd4, 0x68, 0x1e, 0x61, 0x6a, 0xea, 0x19, 0xc7, 0x44, 0x44, 0x1c, 0x45,
|
||||||
0x2a, 0xca, 0x24, 0x65, 0x67, 0x04, 0xee, 0xde, 0xcd, 0x62, 0x1d, 0xbb, 0xfd, 0x0a, 0x3b, 0xd7,
|
0x67, 0xe7, 0x5a, 0xce, 0xb6, 0xdd, 0xeb, 0x04, 0x61, 0x14, 0x13, 0x13, 0xfd, 0x64, 0x8d, 0xe4,
|
||||||
0xd3, 0xb3, 0x89, 0xf5, 0x66, 0x04, 0x52, 0x94, 0x5c, 0xb5, 0x70, 0xdb, 0xa8, 0x9e, 0x16, 0x13,
|
0xe1, 0x02, 0x2e, 0x5c, 0x70, 0xc0, 0x97, 0x2f, 0x7e, 0xd2, 0x01, 0x5d, 0xcb, 0xe5, 0x24, 0x06,
|
||||||
0x2d, 0x43, 0x34, 0xf7, 0x3f, 0xa7, 0xb2, 0x4c, 0xd9, 0xd7, 0xaf, 0x13, 0x55, 0x87, 0x5a, 0x58,
|
0x06, 0xde, 0xd2, 0xf8, 0x3b, 0xfc, 0xfc, 0x39, 0x85, 0xa0, 0xa0, 0xbd, 0x14, 0xdd, 0xd9, 0x9d,
|
||||||
0xef, 0xe0, 0x41, 0x13, 0x19, 0x2d, 0xe3, 0x71, 0x63, 0x63, 0x01, 0x72, 0x72, 0xb4, 0x14, 0x63,
|
0x35, 0x55, 0xc6, 0xca, 0xc9, 0x56, 0xa0, 0xd5, 0xce, 0xa0, 0xbf, 0xbf, 0x91, 0xb4, 0x77, 0xdc,
|
||||||
0xc3, 0xf4, 0x2d, 0xc8, 0xb7, 0xc2, 0x81, 0xff, 0xc8, 0x90, 0x03, 0x16, 0xcb, 0xd7, 0x6c, 0xc0,
|
0xd4, 0x72, 0x18, 0xab, 0x24, 0x29, 0x75, 0x94, 0x47, 0x2d, 0xb5, 0x9d, 0x62, 0x24, 0x26, 0x3a,
|
||||||
0xe9, 0xbc, 0x46, 0x05, 0xaa, 0x65, 0xee, 0x3d, 0x45, 0xec, 0x29, 0xf0, 0xcb, 0x97, 0x4f, 0x52,
|
0x49, 0xd2, 0xee, 0x20, 0xa2, 0x78, 0xa9, 0xaf, 0xe5, 0xe5, 0xdd, 0xe6, 0xda, 0x5b, 0xb6, 0x24,
|
||||||
0xaa, 0xb7, 0xd2, 0x48, 0x81, 0xc9, 0xb4, 0x92, 0xea, 0x2b, 0x96, 0x6b, 0x6b, 0x56, 0x40, 0x42,
|
0x11, 0x73, 0x47, 0xc2, 0x28, 0x95, 0x11, 0xa8, 0xac, 0xf4, 0x92, 0xa4, 0xdd, 0x41, 0x44, 0x17,
|
||||||
0x5c, 0x61, 0x23, 0xdd, 0xdd, 0xbf, 0xa9, 0x34, 0x16, 0x32, 0x25, 0x92, 0x7b, 0x99, 0x61, 0x6e,
|
0x29, 0x9a, 0x5e, 0x0c, 0x0f, 0x77, 0xe3, 0xda, 0x35, 0x4f, 0x74, 0x77, 0x9f, 0xd8, 0xd4, 0xd1,
|
||||||
0x3d, 0x59, 0x4f, 0x63, 0xe8, 0xeb, 0x6b, 0xc3, 0xf3, 0xe7, 0x8f, 0xa8, 0x1d, 0xf5, 0xb2, 0x8e,
|
0x19, 0x0b, 0x20, 0x4c, 0x1f, 0x86, 0x86, 0x3a, 0x11, 0x18, 0xe8, 0x88, 0xf1, 0xf1, 0x53, 0x52,
|
||||||
0xec, 0x16, 0x92, 0xda, 0x59, 0x02, 0x95, 0xa9, 0x3d, 0x6b, 0x80, 0x36, 0x4d, 0x50, 0x73, 0x8c,
|
0x23, 0xde, 0xd1, 0x7d, 0x24, 0x96, 0xf6, 0xab, 0x57, 0x9e, 0xdc, 0x74, 0x3a, 0xff, 0x2d, 0xef,
|
||||||
0xe3, 0xf8, 0x48, 0xee, 0x7d, 0x9b, 0xa9, 0x10, 0x9d, 0xa4, 0x33, 0xa8, 0xb6, 0x9d, 0x3a, 0x4e,
|
0x1d, 0xbd, 0x7e, 0x0d, 0xa3, 0xd1, 0x78, 0x99, 0xce, 0x93, 0x15, 0x22, 0xf1, 0x2a, 0x2f, 0x2d,
|
||||||
0x16, 0x87, 0x63, 0x0b, 0xf7, 0xc8, 0x59, 0x01, 0x29, 0xca, 0x37, 0xdc, 0x8a, 0xe4, 0x63, 0xb3,
|
0xb5, 0x7e, 0x95, 0x8b, 0x72, 0x6d, 0x94, 0x6c, 0x2b, 0x8c, 0x65, 0x73, 0x55, 0x88, 0x07, 0xd6,
|
||||||
0x75, 0x20, 0x21, 0x61, 0x01, 0xa7, 0xba, 0xe4, 0xde, 0xdf, 0xa1, 0x5a, 0x6f, 0xa3, 0xcd, 0xcf,
|
0x68, 0x71, 0x95, 0x2b, 0x95, 0x07, 0x1d, 0x32, 0x32, 0x5c, 0xb4, 0x45, 0x45, 0xee, 0xb3, 0xb6,
|
||||||
0xdf, 0x86, 0x5d, 0xbb, 0x22, 0x28, 0xb6, 0x86, 0x99, 0xaf, 0x89, 0xa9, 0x2d, 0x5f, 0x88, 0x1b,
|
0xb4, 0xcc, 0x4c, 0xb9, 0xfe, 0xde, 0x3d, 0x97, 0x33, 0x16, 0x7f, 0xb7, 0xa8, 0xd5, 0xb8, 0xa6,
|
||||||
0xf4, 0xb6, 0x51, 0x77, 0xd8, 0xcf, 0x94, 0x54, 0x55, 0xc5, 0xfa, 0xf5, 0x35, 0xb7, 0x7c, 0xcf,
|
0xa4, 0xb8, 0x28, 0x6c, 0x69, 0x69, 0x69, 0x4e, 0xde, 0x9b, 0xfe, 0xd7, 0xed, 0xb6, 0xfd, 0x06,
|
||||||
0x3a, 0x76, 0x7b, 0x07, 0x25, 0x8e, 0x16, 0x67, 0xce, 0xac, 0xf6, 0x52, 0x3b, 0x6b, 0x20, 0x29,
|
0xf5, 0x7b, 0x75, 0x19, 0x48, 0x1d, 0x69, 0x95, 0x00, 0x00, 0x00, 0x00, 0x49, 0x45, 0x4e, 0x44,
|
||||||
0x92, 0x82, 0xc7, 0x8f, 0x13, 0xd0, 0xd5, 0xf5, 0x15, 0x9e, 0x3d, 0xdb, 0x1c, 0xe4, 0x8e, 0xf2,
|
0xae, 0x42, 0x60, 0x82,
|
||||||
0xd7, 0x91, 0xf5, 0xe4, 0xd1, 0x09, 0x00, 0x92, 0x57, 0xf9, 0xb9, 0x73, 0xd3, 0x5f, 0xe5, 0x72,
|
|
||||||
0x63, 0xf0, 0x8b, 0x70, 0x66, 0x1d, 0xaa, 0x23, 0xe1, 0x77, 0x95, 0x17, 0x15, 0x45, 0x6a, 0xcb,
|
|
||||||
0xcb, 0xf5, 0x43, 0x74, 0xec, 0xb7, 0xa1, 0x14, 0x8b, 0x25, 0x66, 0xa4, 0xb8, 0x58, 0x9f, 0xe0,
|
|
||||||
0xf7, 0xbb, 0x75, 0xe4, 0x48, 0x4c, 0x6c, 0x49, 0x89, 0x3e, 0x39, 0x94, 0x52, 0x56, 0xa6, 0x5b,
|
|
||||||
0x1b, 0xf0, 0x5f, 0x37, 0xd7, 0xf2, 0x11, 0x7a, 0x44, 0x55, 0x8d, 0x15, 0xe4, 0xa5, 0xf6, 0x00,
|
|
||||||
0x00, 0x00, 0x00, 0x49, 0x45, 0x4e, 0x44, 0xae, 0x42, 0x60, 0x82,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const BITMAP_OPAQUE ercwarn_xpm[1] = {{ png, sizeof( png ), "ercwarn_xpm" }};
|
const BITMAP_OPAQUE ercwarn_xpm[1] = {{ png, sizeof( png ), "ercwarn_xpm" }};
|
||||||
|
|
|
@ -8,189 +8,188 @@
|
||||||
static const char png[] = {
|
static const char png[] = {
|
||||||
0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a, 0x00, 0x00, 0x00, 0x0d, 0x49, 0x48, 0x44, 0x52,
|
0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a, 0x00, 0x00, 0x00, 0x0d, 0x49, 0x48, 0x44, 0x52,
|
||||||
0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x30, 0x08, 0x06, 0x00, 0x00, 0x00, 0x57, 0x02, 0xf9,
|
0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x30, 0x08, 0x06, 0x00, 0x00, 0x00, 0x57, 0x02, 0xf9,
|
||||||
0x87, 0x00, 0x00, 0x0b, 0x49, 0x49, 0x44, 0x41, 0x54, 0x68, 0xde, 0xd5, 0x9a, 0x7f, 0x6c, 0x5b,
|
0x87, 0x00, 0x00, 0x0b, 0x40, 0x49, 0x44, 0x41, 0x54, 0x68, 0xde, 0xd5, 0x9a, 0x7d, 0x6c, 0x5b,
|
||||||
0xd7, 0x75, 0xc7, 0x3f, 0xf7, 0x3e, 0x52, 0xfc, 0x21, 0x8a, 0xa2, 0x18, 0x8a, 0x22, 0x25, 0xea,
|
0xd7, 0x79, 0xc6, 0x7f, 0xe7, 0x5c, 0x52, 0xa4, 0x68, 0x52, 0xa2, 0x68, 0x8a, 0x22, 0x25, 0x51,
|
||||||
0xb7, 0x25, 0x19, 0x96, 0x15, 0xa9, 0x49, 0x6c, 0x2f, 0xce, 0x8f, 0xc2, 0xc5, 0xb2, 0x16, 0x2b,
|
0x9f, 0x96, 0x64, 0x58, 0x96, 0xa5, 0x26, 0xb1, 0x3a, 0x77, 0x4e, 0x0a, 0x17, 0x4d, 0x5b, 0xac,
|
||||||
0xe6, 0xa1, 0x6d, 0xe0, 0xae, 0x41, 0xdb, 0x24, 0x6d, 0x91, 0xfe, 0x1a, 0x86, 0x0e, 0xe8, 0x32,
|
0x98, 0x87, 0xb5, 0x81, 0xbb, 0x06, 0x6d, 0x93, 0xb4, 0x45, 0xda, 0xb5, 0xd8, 0xd0, 0x01, 0x5d,
|
||||||
0xac, 0xeb, 0xb2, 0x75, 0x5b, 0xd0, 0xac, 0xdb, 0x82, 0xfe, 0xd5, 0xa4, 0x68, 0x80, 0x64, 0x6b,
|
0x86, 0x75, 0x5d, 0xb6, 0x6e, 0x0b, 0x8a, 0x74, 0x5b, 0xb0, 0xbf, 0x96, 0x14, 0x4d, 0xd1, 0xf4,
|
||||||
0xd3, 0x04, 0xeb, 0x32, 0x18, 0x29, 0x50, 0x14, 0x45, 0x7f, 0x7a, 0x88, 0xdb, 0x3a, 0xb0, 0xdd,
|
0x23, 0x4b, 0xb0, 0x2e, 0x83, 0x91, 0x01, 0x43, 0x31, 0xac, 0x5f, 0x2e, 0xdc, 0x6e, 0x31, 0x6c,
|
||||||
0x2a, 0xaa, 0x65, 0xcb, 0x92, 0x23, 0x5b, 0xb6, 0x65, 0xd9, 0xa2, 0x48, 0x51, 0xa2, 0x28, 0xf2,
|
0x35, 0x8e, 0x6a, 0x59, 0xb6, 0x98, 0xc8, 0x96, 0x23, 0x59, 0x91, 0x48, 0x51, 0xd4, 0x07, 0x3f,
|
||||||
0xbd, 0x77, 0xef, 0xfe, 0xe0, 0x0f, 0x8b, 0x14, 0x49, 0xc9, 0xb1, 0x3d, 0xa0, 0x17, 0x78, 0x7a,
|
0xee, 0xbd, 0xe7, 0xec, 0x0f, 0x7e, 0x84, 0xa2, 0x44, 0x8a, 0xaa, 0xed, 0x01, 0xbd, 0x80, 0x74,
|
||||||
0x57, 0xef, 0x91, 0xe7, 0xde, 0x73, 0xce, 0xf7, 0x7c, 0xcf, 0xb9, 0xf7, 0x52, 0x68, 0xad, 0xf9,
|
0x2f, 0x2f, 0xc9, 0xf7, 0x9c, 0xe7, 0xbc, 0xcf, 0xf3, 0x3e, 0xe7, 0x9c, 0x4b, 0xa1, 0xb5, 0xe6,
|
||||||
0x7d, 0x6e, 0x8e, 0xdb, 0x21, 0x54, 0x08, 0x21, 0x01, 0x03, 0x10, 0xb7, 0x41, 0xbc, 0xad, 0xb5,
|
0x37, 0xf9, 0x70, 0xdc, 0x89, 0xa0, 0x42, 0x08, 0x09, 0x18, 0x80, 0xb8, 0x03, 0xe1, 0x6d, 0xad,
|
||||||
0xb6, 0x6f, 0x9b, 0x02, 0x42, 0x88, 0x86, 0x23, 0x47, 0x8e, 0x7c, 0xba, 0xab, 0xb3, 0xe3, 0xf3,
|
0xb5, 0x7d, 0xc7, 0x00, 0x08, 0x21, 0x1a, 0xce, 0x9c, 0x39, 0xf3, 0x99, 0xae, 0x68, 0xc7, 0xe7,
|
||||||
0x86, 0xe1, 0xf0, 0xde, 0x52, 0xe1, 0x4a, 0xe9, 0x64, 0x6a, 0xe5, 0xc8, 0xc1, 0x83, 0x07, 0xff,
|
0x0d, 0xc3, 0xe1, 0xb9, 0xad, 0xc1, 0x95, 0xd2, 0xc9, 0xd4, 0xda, 0x99, 0x93, 0x27, 0x4f, 0xfe,
|
||||||
0xf2, 0xf5, 0xd7, 0x5f, 0x5f, 0xbc, 0x2d, 0x0a, 0xdc, 0x7b, 0xef, 0xbd, 0x7d, 0x03, 0xfd, 0x3d,
|
0xc9, 0xcb, 0x2f, 0xbf, 0xbc, 0x7c, 0x47, 0x00, 0x1c, 0x3b, 0x76, 0xac, 0x6f, 0xa0, 0xbf, 0xe7,
|
||||||
0xff, 0x06, 0xba, 0xe1, 0x96, 0xdb, 0xde, 0x90, 0xb4, 0x85, 0x83, 0x1f, 0x7d, 0xfc, 0xd1, 0x8f,
|
0x1f, 0x40, 0x37, 0xdc, 0xf6, 0xb1, 0x37, 0x24, 0x6d, 0xa1, 0xc0, 0xc7, 0x1e, 0x79, 0xe8, 0x13,
|
||||||
0x5f, 0x13, 0x42, 0xfc, 0x95, 0xd6, 0xda, 0x76, 0xdc, 0x62, 0xeb, 0x3b, 0xfe, 0xfd, 0x5f, 0xff,
|
0x4b, 0x42, 0x88, 0x3f, 0xd5, 0x5a, 0xdb, 0x8e, 0xdb, 0x3c, 0xfa, 0x8e, 0x7f, 0xfc, 0xfb, 0x27,
|
||||||
0xe5, 0x03, 0x5a, 0xeb, 0x06, 0xad, 0x15, 0x99, 0xb5, 0x34, 0xa9, 0x95, 0x6b, 0x68, 0xad, 0x6e,
|
0x7f, 0x5f, 0x6b, 0xdd, 0xa0, 0xb5, 0x22, 0xbd, 0xb9, 0x41, 0x6a, 0x6d, 0x09, 0xad, 0xd5, 0x2d,
|
||||||
0x5a, 0xb6, 0xab, 0xa1, 0x89, 0x96, 0x60, 0x2b, 0x4a, 0x29, 0x9a, 0x9a, 0x7c, 0x7f, 0x00, 0xf8,
|
0xc7, 0x76, 0x35, 0xf8, 0x68, 0x09, 0xb4, 0xa2, 0x94, 0xc2, 0xe7, 0xf3, 0xfe, 0x16, 0xe0, 0x05,
|
||||||
0x80, 0xe5, 0x6a, 0x0a, 0x88, 0xe7, 0x9f, 0x7f, 0xfe, 0xc3, 0x2e, 0x97, 0x6b, 0xaf, 0x94, 0x52,
|
0x56, 0x77, 0x02, 0x20, 0x9e, 0x79, 0xe6, 0x99, 0x8f, 0xb8, 0x5c, 0xae, 0x71, 0x29, 0xa5, 0x90,
|
||||||
0x48, 0x29, 0x91, 0x52, 0x16, 0x3c, 0xa8, 0x50, 0x4a, 0xa1, 0xb5, 0xc6, 0xb2, 0xac, 0x4d, 0xfd,
|
0x52, 0x22, 0xa5, 0x2c, 0x64, 0x50, 0xa1, 0x94, 0x42, 0x6b, 0x8d, 0x65, 0x59, 0xdb, 0xae, 0x9f,
|
||||||
0x67, 0x9e, 0x79, 0xc6, 0x30, 0x6d, 0x7b, 0x9f, 0x56, 0x36, 0x5a, 0x6b, 0xb2, 0xd9, 0x34, 0x67,
|
0x7c, 0xf2, 0x49, 0x23, 0x67, 0xa9, 0x77, 0x6a, 0x65, 0xa3, 0xb5, 0x26, 0x9b, 0xdd, 0x60, 0xfa,
|
||||||
0xde, 0xfe, 0x31, 0x0e, 0xe7, 0xcd, 0xdb, 0xa9, 0x23, 0x7c, 0x37, 0x4d, 0x4d, 0xcd, 0x18, 0x86,
|
0x8d, 0xff, 0xc6, 0xe1, 0xbc, 0xf5, 0x71, 0xea, 0x08, 0xdd, 0x8d, 0xcf, 0xd7, 0x8c, 0x61, 0x38,
|
||||||
0x03, 0x33, 0x97, 0x73, 0x00, 0xae, 0xaa, 0x10, 0x7a, 0xee, 0xb9, 0xe7, 0x3e, 0xd2, 0xdf, 0xdf,
|
0x30, 0x73, 0x39, 0x07, 0xe0, 0xda, 0x91, 0x42, 0x4f, 0x3f, 0xfd, 0xf4, 0x47, 0xfb, 0xfb, 0xfb,
|
||||||
0xff, 0xc2, 0xd8, 0xd8, 0x98, 0x47, 0x08, 0x51, 0xb4, 0x6c, 0xe9, 0xfd, 0x46, 0xd6, 0x2a, 0xf6,
|
0x9f, 0x1d, 0x1b, 0x1b, 0x6b, 0x14, 0x42, 0x14, 0x47, 0xb6, 0xf4, 0x7e, 0x79, 0xd5, 0x2a, 0x5e,
|
||||||
0x8b, 0xf7, 0x6c, 0x36, 0xcb, 0x6f, 0x4e, 0x9e, 0x28, 0x29, 0x26, 0x1d, 0x92, 0xe6, 0x16, 0x3f,
|
0x17, 0xcf, 0xb9, 0x5c, 0x8e, 0x5f, 0x4e, 0x5c, 0x28, 0x01, 0x93, 0x0e, 0x49, 0x73, 0x4b, 0x13,
|
||||||
0x2e, 0xb7, 0xeb, 0x86, 0x26, 0x3b, 0x7f, 0x39, 0xce, 0x5b, 0xe3, 0xe7, 0x88, 0x46, 0x83, 0x8c,
|
0x2e, 0xb7, 0x6b, 0x4f, 0x9d, 0x5d, 0x98, 0x8f, 0xf3, 0xda, 0xc5, 0xd7, 0x89, 0x44, 0x02, 0x8c,
|
||||||
0x8c, 0xf6, 0x03, 0x20, 0xa5, 0x2e, 0x19, 0xd1, 0x56, 0xa5, 0x18, 0x46, 0x6e, 0x82, 0x99, 0x61,
|
0x8c, 0xf6, 0x03, 0x20, 0xa5, 0x2e, 0x0d, 0xa2, 0xad, 0x4a, 0x1a, 0x46, 0x6e, 0xa3, 0x99, 0x61,
|
||||||
0xec, 0x19, 0x1a, 0x1a, 0xf2, 0xb8, 0xdd, 0x6e, 0x6c, 0xdb, 0xc6, 0xb6, 0x6d, 0x2c, 0xcb, 0xca,
|
0x1c, 0x1d, 0x1a, 0x1a, 0x6a, 0x74, 0xbb, 0xdd, 0xd8, 0xb6, 0x8d, 0x6d, 0xdb, 0x58, 0x96, 0x95,
|
||||||
0x87, 0xbf, 0x6d, 0x97, 0x79, 0xa1, 0x24, 0xa4, 0xe0, 0xa5, 0xbc, 0xa7, 0x44, 0xe9, 0x33, 0x0e,
|
0x97, 0xbf, 0x6d, 0x6f, 0xc9, 0x42, 0x29, 0x48, 0x21, 0x4b, 0x52, 0x4a, 0x74, 0x59, 0xa6, 0x1c,
|
||||||
0xc3, 0x01, 0x42, 0xde, 0xb0, 0xb5, 0xcf, 0xcd, 0x5c, 0xe6, 0xfe, 0x07, 0x46, 0x58, 0xb8, 0x92,
|
0x86, 0x03, 0x84, 0xdc, 0xf3, 0x68, 0xbf, 0x1e, 0x9b, 0xe7, 0xf8, 0xbd, 0x23, 0x2c, 0xde, 0x5c,
|
||||||
0x40, 0xa9, 0xfc, 0x38, 0xd2, 0x30, 0xd0, 0x05, 0xd9, 0x96, 0xad, 0x28, 0x32, 0x5c, 0x55, 0xdf,
|
0x41, 0xa9, 0x7c, 0x3b, 0xd2, 0x30, 0xd0, 0x08, 0x94, 0x52, 0x58, 0xb6, 0xa2, 0x58, 0xe1, 0x76,
|
||||||
0x6a, 0xad, 0x31, 0x4d, 0x93, 0x4c, 0x26, 0x83, 0x10, 0x02, 0xdb, 0xb6, 0xf1, 0x7a, 0xbd, 0xe4,
|
0xcc, 0xad, 0xd6, 0x1a, 0xd3, 0x34, 0x49, 0xa7, 0xd3, 0x08, 0x21, 0xb0, 0x6d, 0x1b, 0x8f, 0xc7,
|
||||||
0x72, 0xb9, 0x32, 0x6f, 0x54, 0xf6, 0xb3, 0xd9, 0x2c, 0xa6, 0x95, 0x43, 0xeb, 0x82, 0x07, 0x0c,
|
0x43, 0x2e, 0x97, 0xdb, 0x92, 0x8d, 0xca, 0xeb, 0x6c, 0x36, 0x8b, 0x99, 0xcb, 0xa1, 0x75, 0x21,
|
||||||
0x89, 0xe0, 0xc6, 0xf3, 0x8c, 0xaf, 0xc9, 0x8b, 0x34, 0x24, 0xcd, 0x81, 0x46, 0x8a, 0x43, 0x14,
|
0x03, 0x86, 0x44, 0xb0, 0x77, 0x9f, 0xf1, 0xfa, 0x3c, 0x48, 0x43, 0xd2, 0xec, 0xdf, 0x47, 0xb1,
|
||||||
0x65, 0x29, 0xad, 0x50, 0xb6, 0x25, 0x6a, 0x2a, 0xa0, 0xb5, 0xa6, 0x12, 0x3a, 0xb5, 0xee, 0xd5,
|
0x89, 0x62, 0x2c, 0xa5, 0x15, 0xca, 0xb6, 0x44, 0x55, 0x00, 0x5a, 0x6b, 0x2a, 0xa9, 0x53, 0xed,
|
||||||
0xfa, 0x45, 0x2f, 0x15, 0x21, 0x54, 0x8c, 0x9f, 0x1b, 0x0a, 0x58, 0x97, 0x93, 0x5f, 0xff, 0xf2,
|
0xbc, 0xd3, 0xb5, 0xd6, 0x7a, 0x0b, 0x85, 0x8a, 0xfa, 0xd9, 0x93, 0x60, 0x5d, 0x4e, 0xfe, 0xf7,
|
||||||
0x14, 0x52, 0x4a, 0xe2, 0x8b, 0x29, 0x5c, 0x6e, 0x27, 0xc1, 0x46, 0x81, 0xd6, 0x85, 0x38, 0xb4,
|
0x17, 0x97, 0x90, 0x52, 0x12, 0x5f, 0x4e, 0xe1, 0x72, 0x3b, 0x09, 0xec, 0x13, 0x68, 0x5d, 0xc8,
|
||||||
0x55, 0xfd, 0x44, 0x76, 0x33, 0x4a, 0x50, 0x18, 0x44, 0x6b, 0x8d, 0x21, 0x0a, 0x2e, 0x2f, 0x40,
|
0xae, 0xad, 0x6a, 0x1b, 0xd9, 0xad, 0x80, 0x28, 0xa7, 0x98, 0x21, 0x0a, 0x29, 0x2f, 0x50, 0xb0,
|
||||||
0x70, 0xbb, 0x6d, 0xc7, 0x40, 0x3b, 0x1d, 0x1d, 0x77, 0xe0, 0x72, 0x37, 0x20, 0x44, 0x41, 0xbe,
|
0xde, 0xe3, 0xc0, 0x40, 0x3b, 0x1d, 0x1d, 0xfb, 0x71, 0xb9, 0x1b, 0x10, 0xa2, 0x10, 0x5f, 0xbe,
|
||||||
0x14, 0x68, 0xad, 0x37, 0xc5, 0x80, 0x63, 0x73, 0xae, 0x50, 0x9b, 0x26, 0xb6, 0x5d, 0x25, 0x44,
|
0x3d, 0x38, 0xe5, 0x1a, 0x70, 0x6c, 0xf7, 0x0a, 0xb5, 0xad, 0x63, 0xf5, 0x82, 0x10, 0x85, 0x0e,
|
||||||
0x61, 0xc2, 0xba, 0xa0, 0x80, 0x43, 0x36, 0xd2, 0xd7, 0x75, 0x3f, 0x4a, 0x5b, 0x37, 0xcd, 0x42,
|
0xeb, 0x02, 0x00, 0x87, 0xe1, 0xa5, 0xaf, 0xeb, 0x38, 0x4a, 0x5b, 0xb7, 0x5c, 0x85, 0x7c, 0x8d,
|
||||||
0x4d, 0x9e, 0x88, 0xce, 0xac, 0x66, 0x85, 0xd6, 0x0a, 0xa5, 0x6c, 0xb1, 0x2d, 0x05, 0xb6, 0x82,
|
0x61, 0x9d, 0x5e, 0xcf, 0x0a, 0xad, 0x15, 0x4a, 0xd9, 0xa2, 0x2e, 0x00, 0xbb, 0xd1, 0x65, 0xa7,
|
||||||
0x4b, 0xb5, 0x67, 0x45, 0x2b, 0x69, 0xad, 0x59, 0x5d, 0x59, 0x01, 0x3c, 0xb7, 0xa4, 0x9e, 0x58,
|
0x7b, 0xb6, 0xb2, 0x4b, 0x19, 0x58, 0x4f, 0xa5, 0x80, 0xc6, 0xdb, 0x32, 0x9f, 0x58, 0xcf, 0x6d,
|
||||||
0xcd, 0xa5, 0x4b, 0x62, 0x54, 0xbd, 0x20, 0xae, 0xf4, 0xc0, 0xc6, 0x6b, 0x2b, 0x08, 0x69, 0xad,
|
0x94, 0xc2, 0xa8, 0x5a, 0x22, 0xae, 0xcc, 0x40, 0xf9, 0x5f, 0x3d, 0x14, 0xd2, 0x4a, 0x63, 0x2b,
|
||||||
0xf3, 0xcc, 0xa5, 0x14, 0x68, 0xcd, 0x7f, 0xff, 0xcf, 0x61, 0xc6, 0xdf, 0xfa, 0x1d, 0x81, 0x40,
|
0x05, 0x5a, 0xf3, 0x6f, 0xff, 0x7e, 0x9a, 0x8b, 0xaf, 0xfd, 0x0a, 0xbf, 0xdf, 0xcf, 0x6a, 0x32,
|
||||||
0x80, 0xe5, 0x64, 0x92, 0xbf, 0x7f, 0xea, 0x4b, 0x9c, 0x9f, 0x3d, 0xcf, 0x37, 0xbe, 0xf9, 0x02,
|
0xc9, 0x5f, 0x3d, 0xfe, 0x25, 0xae, 0xcd, 0x5e, 0xe3, 0x9f, 0xbf, 0xfe, 0x2c, 0x91, 0x48, 0x3b,
|
||||||
0xd1, 0x68, 0x3b, 0xf3, 0xf3, 0x97, 0xf9, 0xd4, 0x27, 0x1e, 0x65, 0x70, 0x60, 0x07, 0xff, 0xf4,
|
0x0b, 0x0b, 0xf3, 0x7c, 0xfa, 0x93, 0x0f, 0x31, 0x38, 0x70, 0x80, 0xbf, 0x7d, 0xe2, 0x6b, 0xb8,
|
||||||
0xf4, 0xd7, 0x70, 0xb9, 0xdd, 0x24, 0x12, 0x4b, 0x8c, 0x8d, 0x8e, 0xf0, 0x67, 0x87, 0x1e, 0xe6,
|
0xdc, 0x6e, 0x56, 0x56, 0x12, 0x8c, 0x8d, 0x8e, 0xf0, 0x07, 0xa7, 0x1e, 0xe0, 0xcc, 0xf7, 0x9e,
|
||||||
0xc8, 0x77, 0x5e, 0x26, 0x3d, 0x3b, 0x8b, 0x56, 0x0a, 0xd5, 0xd0, 0xc0, 0xfb, 0xff, 0xfa, 0xc9,
|
0x67, 0x63, 0x76, 0x16, 0xad, 0x14, 0xaa, 0xa1, 0x81, 0x0f, 0xfe, 0xd9, 0x63, 0xa5, 0x41, 0x2a,
|
||||||
0x7c, 0x9c, 0xe5, 0x21, 0x24, 0xaa, 0xd2, 0x68, 0xd1, 0x7a, 0xf5, 0xac, 0xbd, 0xf1, 0x5e, 0xd9,
|
0x02, 0x90, 0x3b, 0x01, 0x28, 0xd7, 0xc0, 0x6e, 0x14, 0xaa, 0xbc, 0xd6, 0x5a, 0x17, 0xaa, 0x90,
|
||||||
0xd7, 0x5a, 0x17, 0x58, 0x48, 0x31, 0x79, 0xfa, 0x0c, 0x4b, 0x89, 0x24, 0x2d, 0xc1, 0x3b, 0x58,
|
0x62, 0xea, 0xf2, 0x34, 0x89, 0x95, 0x24, 0x2d, 0x81, 0xfd, 0x2c, 0x27, 0x56, 0xc8, 0x65, 0xb3,
|
||||||
0x5c, 0x4a, 0x90, 0xcb, 0x66, 0x99, 0x3c, 0x73, 0x86, 0xb5, 0xcc, 0x3a, 0x7f, 0x72, 0xf0, 0x20,
|
0x4c, 0x4d, 0x4f, 0xb3, 0x99, 0xce, 0xf0, 0xbb, 0x27, 0x4f, 0xb2, 0x99, 0xce, 0x70, 0x69, 0xea,
|
||||||
0x6b, 0x99, 0x75, 0x4e, 0x4d, 0x9e, 0xc6, 0x34, 0x73, 0x5c, 0xbd, 0x76, 0x8d, 0x68, 0x7b, 0x3b,
|
0x32, 0xa6, 0x99, 0xe3, 0xad, 0xa5, 0x25, 0x22, 0xed, 0xed, 0x1c, 0x18, 0x18, 0x64, 0xea, 0xf2,
|
||||||
0x3b, 0x06, 0x06, 0x99, 0x3c, 0x3d, 0x85, 0xd6, 0x8a, 0xa5, 0xdf, 0x8e, 0x33, 0xb6, 0x6b, 0x37,
|
0x15, 0xb4, 0x56, 0x24, 0x5e, 0xbd, 0xc8, 0xd8, 0xa1, 0xc3, 0xdc, 0x73, 0xd7, 0xdd, 0xec, 0x9b,
|
||||||
0xf7, 0xdc, 0x75, 0x37, 0x8d, 0x97, 0xe7, 0x31, 0xcd, 0x3c, 0xc3, 0xd9, 0x96, 0x5d, 0x9f, 0x85,
|
0x5f, 0xc0, 0x34, 0xf3, 0x15, 0xce, 0xb6, 0xec, 0xda, 0x55, 0xa8, 0x32, 0x03, 0xb5, 0x40, 0xcc,
|
||||||
0x2a, 0x3d, 0x50, 0x4f, 0x89, 0xe9, 0xe9, 0x69, 0x5a, 0x5b, 0x5b, 0x09, 0x04, 0x02, 0xd7, 0x59,
|
0xcc, 0xcc, 0xd0, 0xda, 0xda, 0x8a, 0xdf, 0xef, 0x2f, 0x69, 0x20, 0x9f, 0x62, 0x4d, 0xb8, 0xad,
|
||||||
0xc8, 0x56, 0x80, 0x26, 0xd2, 0xd6, 0xc6, 0x5a, 0x66, 0x9d, 0xb9, 0xb9, 0x0b, 0x34, 0xfb, 0xfd,
|
0x8d, 0xcd, 0x74, 0x86, 0xb9, 0xb9, 0xeb, 0x34, 0x37, 0x35, 0x21, 0x04, 0xb4, 0x85, 0x42, 0x78,
|
||||||
0x08, 0x01, 0x6d, 0xe1, 0x30, 0x3e, 0x5f, 0x23, 0x3f, 0xfd, 0xe9, 0x4f, 0xf0, 0xf9, 0x1a, 0x89,
|
0xbd, 0xfb, 0xf8, 0xd1, 0x8f, 0x7e, 0x88, 0xd7, 0xbb, 0x8f, 0x70, 0x5b, 0x1b, 0x00, 0x7e, 0x7f,
|
||||||
0xb4, 0xb5, 0x01, 0x10, 0x08, 0x34, 0x13, 0x8f, 0x2f, 0x12, 0x8f, 0xc7, 0x69, 0x8f, 0x44, 0x50,
|
0x33, 0xf1, 0xf8, 0x32, 0xf1, 0x78, 0x9c, 0xf6, 0x70, 0x18, 0xa5, 0x14, 0xee, 0x48, 0x98, 0x6b,
|
||||||
0x4a, 0xe1, 0x8e, 0x46, 0x38, 0x3f, 0xf9, 0x3b, 0xb4, 0xd2, 0x58, 0xcd, 0xfe, 0xaa, 0x89, 0xec,
|
0x53, 0xbf, 0x42, 0x2b, 0x8d, 0xd5, 0xdc, 0xb4, 0xa3, 0x91, 0xdd, 0x16, 0x11, 0x97, 0x03, 0xd5,
|
||||||
0x96, 0x04, 0x71, 0x25, 0xcc, 0x74, 0x61, 0x80, 0xc7, 0x3e, 0xf6, 0x91, 0x12, 0x03, 0x09, 0x21,
|
0x5a, 0xa3, 0x0b, 0x0d, 0x3c, 0xfc, 0xf1, 0x8f, 0x96, 0x2a, 0x90, 0x10, 0x12, 0x43, 0x4a, 0x46,
|
||||||
0x31, 0xa4, 0x64, 0x74, 0x64, 0x98, 0x5d, 0x3b, 0x07, 0x4b, 0x63, 0x38, 0x9d, 0x4e, 0x00, 0xfe,
|
0x47, 0x86, 0x39, 0x74, 0x70, 0xb0, 0xd4, 0x86, 0xd3, 0xe9, 0x04, 0xe0, 0x2f, 0xff, 0xfc, 0x8b,
|
||||||
0xee, 0x6f, 0xbe, 0x58, 0x1a, 0xdb, 0x30, 0x0c, 0xb4, 0x52, 0xbc, 0xe7, 0xf3, 0x9f, 0xc5, 0xb6,
|
0xa5, 0xb6, 0x0d, 0xc3, 0x40, 0x2b, 0xc5, 0x7b, 0x3e, 0xff, 0x87, 0xd8, 0xb6, 0xfd, 0xb6, 0x59,
|
||||||
0xed, 0xeb, 0xc9, 0x52, 0x88, 0x3c, 0x9c, 0xf2, 0x79, 0xa0, 0xb6, 0x02, 0x95, 0x5e, 0xa8, 0x75,
|
0x0a, 0x91, 0xa7, 0x53, 0xde, 0x07, 0xaa, 0x03, 0xa8, 0xcc, 0x42, 0xb5, 0x73, 0x22, 0x91, 0x20,
|
||||||
0x4f, 0x24, 0x12, 0x24, 0x93, 0x49, 0x72, 0xb9, 0x1c, 0x3e, 0x9f, 0xaf, 0xe0, 0x41, 0x55, 0x9a,
|
0x99, 0x4c, 0x92, 0xcd, 0x66, 0xf1, 0x7a, 0xbd, 0x79, 0xb7, 0x2e, 0x88, 0x18, 0xe0, 0xf9, 0x17,
|
||||||
0xc8, 0xcb, 0xaf, 0x7c, 0x8f, 0xe3, 0x27, 0x7f, 0x43, 0x24, 0x12, 0x21, 0x91, 0x48, 0xf0, 0xf4,
|
0xbe, 0xcf, 0xf9, 0x89, 0x5f, 0x12, 0x0e, 0x87, 0x59, 0x59, 0x59, 0xe1, 0x89, 0xaf, 0x7c, 0x99,
|
||||||
0x57, 0xbe, 0xcc, 0xd9, 0xe9, 0x19, 0xbe, 0xf9, 0xc2, 0x7f, 0xb0, 0x7b, 0x64, 0x37, 0x13, 0x6f,
|
0xab, 0x33, 0x31, 0xbe, 0xfe, 0xec, 0xb7, 0x39, 0x3c, 0x72, 0x98, 0xc9, 0xd7, 0x26, 0x79, 0xe4,
|
||||||
0x4d, 0xf0, 0xf8, 0xc7, 0x1f, 0x61, 0x78, 0xd7, 0x4e, 0x9e, 0xfa, 0xc7, 0xaf, 0xd2, 0xd4, 0xd4,
|
0x13, 0x0f, 0x32, 0x7c, 0xe8, 0x20, 0x8f, 0xff, 0xcd, 0x57, 0xf1, 0xf9, 0x7c, 0xac, 0xaf, 0xaf,
|
||||||
0xc4, 0xea, 0xea, 0x2a, 0xfd, 0x7d, 0x3d, 0x3c, 0xf6, 0xb1, 0x47, 0x38, 0xfc, 0xda, 0x6b, 0xcc,
|
0xd3, 0xdf, 0xd7, 0xc3, 0xc3, 0x1f, 0x7f, 0x90, 0xd3, 0x2f, 0xbd, 0xc4, 0xdc, 0xb5, 0xd9, 0xbc,
|
||||||
0x9d, 0x9f, 0xcd, 0xe7, 0x06, 0xb7, 0x87, 0x4f, 0x7d, 0xe6, 0x33, 0x48, 0x29, 0x8b, 0x4a, 0xd5,
|
0x37, 0xb8, 0x1b, 0xf9, 0xf4, 0x67, 0x3f, 0x8b, 0x94, 0xb2, 0x08, 0xaa, 0xba, 0x06, 0xea, 0xf1,
|
||||||
0x8e, 0x81, 0xed, 0xe4, 0x04, 0x21, 0x04, 0xc9, 0x64, 0x92, 0x68, 0x34, 0x0a, 0xc0, 0xda, 0xda,
|
0x04, 0x21, 0x04, 0xab, 0xab, 0xab, 0x44, 0x22, 0x11, 0xa4, 0x94, 0x6c, 0x6e, 0x6e, 0xe6, 0x29,
|
||||||
0x5a, 0x89, 0x46, 0x8b, 0xd7, 0xdc, 0xc5, 0x4b, 0x74, 0xf7, 0xf4, 0xf2, 0xc0, 0x83, 0xef, 0x26,
|
0x64, 0xab, 0x92, 0x17, 0xcc, 0xdd, 0x78, 0x93, 0xee, 0x9e, 0x5e, 0xee, 0xbd, 0xef, 0xdd, 0x64,
|
||||||
0x9b, 0x33, 0xc9, 0xe5, 0x72, 0xbc, 0x3d, 0x7b, 0x01, 0x84, 0xe0, 0x9e, 0x7b, 0xf6, 0x80, 0x10,
|
0x73, 0x26, 0xb9, 0x5c, 0x8e, 0x37, 0x66, 0xaf, 0x83, 0x10, 0xdc, 0x73, 0xcf, 0x51, 0x10, 0x82,
|
||||||
0xbc, 0x3d, 0x7b, 0x1e, 0xd3, 0x34, 0x59, 0xcb, 0xac, 0xb3, 0x7b, 0xe4, 0x4e, 0xa2, 0xed, 0x1d,
|
0x37, 0x66, 0xaf, 0x61, 0x9a, 0x26, 0x9b, 0xe9, 0x0c, 0x87, 0x47, 0x8e, 0x10, 0x69, 0xef, 0xe0,
|
||||||
0x5c, 0xbc, 0x34, 0x8f, 0x52, 0x8a, 0x95, 0xe5, 0x24, 0x7d, 0x5d, 0x9d, 0x8c, 0xec, 0xda, 0x85,
|
0xc6, 0x9b, 0x0b, 0x28, 0xa5, 0x58, 0x5b, 0x4d, 0xd2, 0xd7, 0x15, 0x65, 0xe4, 0xd0, 0x21, 0x3c,
|
||||||
0xd7, 0x69, 0x60, 0x9a, 0x66, 0x1e, 0x42, 0xf6, 0x75, 0x1a, 0xdd, 0xa4, 0x80, 0x6d, 0xdb, 0x25,
|
0x4e, 0x03, 0xd3, 0x34, 0xf3, 0x14, 0xb2, 0xdf, 0x2e, 0xa3, 0xdb, 0x00, 0xd8, 0xb6, 0x5d, 0xca,
|
||||||
0x0f, 0x4c, 0x4c, 0x4c, 0x30, 0x39, 0x39, 0x49, 0x32, 0x99, 0xac, 0x1a, 0xb8, 0x00, 0x5e, 0xaf,
|
0xc0, 0xe4, 0xe4, 0x24, 0x53, 0x53, 0x53, 0x24, 0x93, 0xc9, 0xaa, 0xc2, 0xf5, 0x78, 0x3c, 0x38,
|
||||||
0x17, 0xa7, 0xd3, 0x59, 0x7a, 0xa6, 0xec, 0x42, 0x1e, 0x50, 0x8a, 0xee, 0xce, 0x18, 0x89, 0xa5,
|
0x9d, 0xce, 0xad, 0x02, 0x2e, 0x78, 0x41, 0x77, 0xb4, 0x93, 0x95, 0x44, 0x9c, 0x33, 0x3f, 0xfd,
|
||||||
0x38, 0x47, 0x7e, 0xf1, 0x73, 0x82, 0xc1, 0x00, 0x52, 0x08, 0x3a, 0x63, 0xed, 0xf8, 0x9b, 0x7c,
|
0x09, 0x81, 0x80, 0x1f, 0x29, 0x04, 0xd1, 0xce, 0x76, 0x9a, 0x7c, 0x5e, 0x7e, 0xfa, 0x93, 0x1f,
|
||||||
0xfc, 0xe2, 0xe7, 0x3f, 0xc3, 0xdf, 0xe4, 0xa3, 0xab, 0xb3, 0x03, 0x21, 0x04, 0xa1, 0x3b, 0x82,
|
0xd3, 0xe4, 0xf3, 0xd2, 0x15, 0xed, 0x40, 0x08, 0x41, 0x70, 0x7f, 0x80, 0xe9, 0xcb, 0x53, 0xac,
|
||||||
0x9c, 0x39, 0x3d, 0x49, 0x62, 0x29, 0x4e, 0x77, 0x67, 0x0c, 0xad, 0x14, 0xa1, 0xd6, 0x30, 0x6b,
|
0x24, 0xe2, 0x74, 0x47, 0x3b, 0xd1, 0x4a, 0x11, 0x6c, 0x0d, 0xb1, 0x99, 0x4e, 0xb3, 0xb4, 0xf4,
|
||||||
0x99, 0x0c, 0xd7, 0xae, 0x5d, 0xc5, 0xe5, 0xf5, 0xe6, 0x49, 0x42, 0x29, 0x94, 0xb5, 0x8d, 0x3c,
|
0x16, 0x2e, 0x8f, 0x27, 0xdf, 0x86, 0x52, 0x28, 0xab, 0x0e, 0x1f, 0x10, 0x42, 0x10, 0x0e, 0x87,
|
||||||
0x20, 0x84, 0x20, 0x12, 0x89, 0x30, 0x33, 0x33, 0xc3, 0xd0, 0xd0, 0xd0, 0xb6, 0x82, 0x3a, 0x4f,
|
0x89, 0xc5, 0x62, 0x0c, 0x0d, 0x0d, 0x55, 0x15, 0xf5, 0x36, 0xc1, 0x6b, 0x50, 0x85, 0xf9, 0xff,
|
||||||
0x71, 0x0a, 0x55, 0xa8, 0xff, 0x1f, 0xfe, 0xd0, 0xc1, 0x4d, 0x70, 0x1c, 0x1c, 0xe8, 0xe7, 0x4b,
|
0x03, 0x1f, 0x3e, 0xb9, 0x8d, 0x8e, 0x83, 0x03, 0xfd, 0x7c, 0xe9, 0xb1, 0x2f, 0x6c, 0xa3, 0xe8,
|
||||||
0x4f, 0x7e, 0x61, 0x13, 0x44, 0xbf, 0xf8, 0x85, 0xcf, 0x95, 0x3d, 0x53, 0x5a, 0xf1, 0x87, 0xef,
|
0x17, 0xbf, 0xf0, 0xb9, 0x2d, 0xf7, 0x94, 0x56, 0xbc, 0xf7, 0x03, 0xef, 0xaf, 0xf8, 0x7e, 0x3e,
|
||||||
0x7b, 0x6f, 0xc5, 0xf7, 0xc9, 0xd7, 0x42, 0x5a, 0xe9, 0x6d, 0xe5, 0x81, 0x70, 0x38, 0x4c, 0x38,
|
0xb6, 0xd2, 0x4a, 0xd7, 0xe5, 0x03, 0xa1, 0x50, 0x88, 0x50, 0x28, 0x54, 0xd3, 0xdc, 0x2a, 0xef,
|
||||||
0x1c, 0xae, 0x99, 0xdc, 0xaa, 0xe5, 0x84, 0x22, 0x7c, 0x00, 0x5e, 0xfc, 0xcf, 0xef, 0x72, 0x6e,
|
0xdb, 0x05, 0xfa, 0x00, 0x7c, 0xeb, 0x3b, 0xff, 0xc2, 0xeb, 0xb3, 0x73, 0x34, 0x35, 0x35, 0x11,
|
||||||
0x76, 0x0e, 0xbf, 0xdf, 0x4f, 0x7c, 0xf1, 0x1a, 0x4f, 0x7f, 0xe5, 0x6f, 0x39, 0x75, 0x7a, 0x8a,
|
0x5f, 0x5e, 0xe2, 0x89, 0xaf, 0xfc, 0x05, 0x97, 0x2e, 0x5f, 0xe1, 0xb9, 0xef, 0xbe, 0xc0, 0x5d,
|
||||||
0x97, 0xbe, 0xfd, 0x0a, 0x77, 0xdd, 0x75, 0x37, 0x27, 0x4e, 0x1c, 0xe7, 0x91, 0x0f, 0x7f, 0x88,
|
0x77, 0xdd, 0xcd, 0x85, 0x0b, 0xe7, 0x79, 0xf0, 0x23, 0x1f, 0xe6, 0x1d, 0xa3, 0x23, 0x7c, 0xf9,
|
||||||
0x77, 0x8d, 0x8e, 0xf0, 0xe5, 0x7f, 0xf8, 0x2a, 0x91, 0x68, 0x94, 0x54, 0x2a, 0x45, 0x38, 0xd4,
|
0xaf, 0xbf, 0x4a, 0x38, 0x12, 0x21, 0x95, 0x4a, 0x11, 0x0a, 0xb6, 0xf0, 0xe8, 0xa7, 0x1e, 0xe2,
|
||||||
0xc2, 0x13, 0x9f, 0x7c, 0x94, 0xd7, 0xfe, 0xeb, 0x7b, 0xc4, 0x17, 0xae, 0xd0, 0xe8, 0xf3, 0xb1,
|
0xa5, 0x7f, 0xfd, 0x3e, 0xf1, 0xc5, 0x9b, 0xec, 0xf3, 0x7a, 0xc9, 0x64, 0xb3, 0x3c, 0xf2, 0xe8,
|
||||||
0x9e, 0xcd, 0xf2, 0xf8, 0x13, 0x4f, 0x14, 0x63, 0x40, 0x6c, 0x3b, 0x0f, 0x54, 0xe3, 0xfa, 0x4d,
|
0xa3, 0x45, 0x0d, 0x88, 0xba, 0x7d, 0x60, 0xa7, 0x5a, 0x5f, 0x4b, 0xdc, 0xe5, 0x14, 0x5a, 0x59,
|
||||||
0xf5, 0x4f, 0x99, 0x32, 0x94, 0x20, 0x94, 0x48, 0x2c, 0x63, 0x18, 0x06, 0x23, 0x23, 0x23, 0x48,
|
0x59, 0xc5, 0x30, 0x0c, 0x46, 0x46, 0x46, 0x90, 0x86, 0x03, 0xcb, 0x34, 0x59, 0xbc, 0xb9, 0x88,
|
||||||
0xc3, 0x81, 0x65, 0x9a, 0x2c, 0x5c, 0x59, 0xc0, 0xe5, 0x72, 0x33, 0x38, 0x38, 0x88, 0xcb, 0xe5,
|
0xcb, 0xe5, 0x66, 0x70, 0x70, 0x10, 0x97, 0xcb, 0xcd, 0xe2, 0xe2, 0x22, 0x96, 0x69, 0x82, 0x10,
|
||||||
0x66, 0x61, 0x61, 0x01, 0xcb, 0x34, 0x41, 0x08, 0x82, 0xc1, 0x20, 0x7d, 0x7d, 0x7d, 0x24, 0x97,
|
0x04, 0x02, 0x01, 0xfa, 0xfa, 0xfa, 0x48, 0xae, 0xa6, 0xd0, 0x4a, 0x61, 0x9b, 0x39, 0x06, 0x07,
|
||||||
0x53, 0x68, 0xa5, 0xb0, 0xcd, 0x1c, 0x83, 0x03, 0x3b, 0x78, 0xe0, 0xc1, 0x77, 0x13, 0xf0, 0x79,
|
0x0e, 0x70, 0xef, 0x7d, 0xef, 0xc6, 0xef, 0xf5, 0x60, 0x99, 0x66, 0x9e, 0x42, 0x4a, 0x55, 0xd7,
|
||||||
0xb1, 0x4c, 0x33, 0x0f, 0x21, 0xa5, 0x6a, 0xc7, 0x40, 0x3e, 0x11, 0xe9, 0x9a, 0xc9, 0xac, 0xb2,
|
0x40, 0x9e, 0xc7, 0xba, 0xaa, 0x99, 0x55, 0x76, 0x3a, 0x93, 0xc9, 0x94, 0x95, 0xca, 0x82, 0x0f,
|
||||||
0xbf, 0xbe, 0xbe, 0x5e, 0x56, 0xac, 0xe5, 0xab, 0xd1, 0xfc, 0x35, 0xb0, 0xa3, 0x97, 0x66, 0xbf,
|
0x28, 0x1b, 0xa5, 0x6c, 0x06, 0x0e, 0xf4, 0xd2, 0xdc, 0xe4, 0x25, 0x36, 0x73, 0x85, 0xb6, 0x50,
|
||||||
0x8f, 0x99, 0xe9, 0x29, 0xda, 0xc2, 0x21, 0x84, 0x10, 0xf4, 0xf6, 0x76, 0x12, 0x0c, 0x34, 0x73,
|
0x10, 0x21, 0x04, 0xbd, 0xbd, 0x51, 0x02, 0xfe, 0x66, 0x26, 0x26, 0xce, 0x13, 0xf0, 0x37, 0xd3,
|
||||||
0xf2, 0xe4, 0x71, 0x82, 0x81, 0x66, 0xfa, 0x7b, 0xbb, 0x11, 0x02, 0xa2, 0x91, 0x30, 0x4b, 0xf1,
|
0xdf, 0xdb, 0x8d, 0x10, 0x10, 0x09, 0x87, 0x48, 0xc4, 0x97, 0x58, 0x98, 0xbf, 0xc1, 0x40, 0x7f,
|
||||||
0x6b, 0xcc, 0x5f, 0xbe, 0xc8, 0x40, 0x7f, 0x2f, 0x4a, 0xd9, 0x84, 0x23, 0x11, 0x92, 0xa9, 0x14,
|
0x2f, 0x4a, 0xd9, 0x84, 0xc2, 0x61, 0x92, 0xa9, 0x14, 0x17, 0xce, 0x9f, 0xa3, 0xc1, 0xe3, 0xcd,
|
||||||
0x27, 0x8e, 0xbf, 0x49, 0x83, 0xd7, 0x97, 0x87, 0x90, 0xb2, 0xd1, 0x4a, 0xd7, 0x4e, 0x64, 0x95,
|
0x53, 0x48, 0xd9, 0x68, 0xa5, 0xab, 0x1b, 0x59, 0xe5, 0xcc, 0xb1, 0x16, 0x88, 0x96, 0x96, 0x16,
|
||||||
0x95, 0x63, 0x3d, 0x25, 0x5a, 0x5a, 0x5a, 0x38, 0x7b, 0xf6, 0x2c, 0x1e, 0x8f, 0x07, 0xaf, 0xd7,
|
0xa6, 0xa7, 0xa7, 0xf1, 0x78, 0x3c, 0x78, 0x3c, 0x1e, 0x94, 0x52, 0x48, 0x29, 0x4b, 0x14, 0xfa,
|
||||||
0x5b, 0xe2, 0xec, 0x22, 0x84, 0xde, 0xf7, 0xd0, 0x81, 0x4d, 0x18, 0xee, 0x8a, 0xc5, 0xf8, 0x8b,
|
0xc0, 0xfd, 0x27, 0xb6, 0x71, 0xb8, 0xab, 0xb3, 0x93, 0x3f, 0xfe, 0xdc, 0xa7, 0xb6, 0xc5, 0xfc,
|
||||||
0xcf, 0x7d, 0x72, 0x93, 0xcc, 0x4f, 0x7f, 0xe2, 0xa3, 0xe5, 0x31, 0xa0, 0x14, 0xf7, 0x3d, 0x70,
|
0xcc, 0x27, 0x3f, 0xb6, 0x55, 0x03, 0x4a, 0xf1, 0xdb, 0xf7, 0x1e, 0xa7, 0x72, 0xdf, 0x2a, 0xcf,
|
||||||
0x3f, 0x95, 0xfb, 0x56, 0x79, 0x84, 0x28, 0xb6, 0x15, 0xc4, 0x5b, 0x29, 0x11, 0x0a, 0x85, 0x58,
|
0x10, 0x45, 0x5d, 0x22, 0xde, 0x0d, 0xc4, 0xfe, 0xfd, 0xfb, 0x09, 0x04, 0x02, 0x84, 0xc3, 0x61,
|
||||||
0x5c, 0x5c, 0x24, 0x12, 0x89, 0xe0, 0x72, 0xb9, 0xf2, 0x54, 0x4a, 0x1e, 0x42, 0x00, 0xdf, 0x7a,
|
0x5c, 0x2e, 0x17, 0x9b, 0x9b, 0x9b, 0x28, 0x3b, 0x4f, 0x1f, 0x80, 0x6f, 0x7c, 0xeb, 0x79, 0x96,
|
||||||
0xf1, 0x65, 0x16, 0x13, 0x49, 0xc2, 0xe1, 0x30, 0xd3, 0x67, 0xa7, 0xf9, 0xe7, 0xa7, 0x9e, 0xe4,
|
0x57, 0x92, 0x84, 0x42, 0x21, 0x66, 0xae, 0xce, 0xf0, 0x77, 0x8f, 0x3f, 0xc6, 0xd5, 0x2b, 0x57,
|
||||||
0xec, 0xd4, 0x59, 0x8e, 0x1d, 0x7d, 0xa3, 0x24, 0xe3, 0x5d, 0x7b, 0xf6, 0xb1, 0x6b, 0x78, 0x17,
|
0x79, 0xe5, 0xe7, 0x67, 0x4b, 0x31, 0xde, 0x71, 0xf4, 0x9d, 0x1c, 0x1a, 0x3e, 0xc4, 0xf3, 0xcf,
|
||||||
0x2f, 0xbf, 0xf4, 0x12, 0x3b, 0x06, 0x87, 0x58, 0xb8, 0x32, 0x8f, 0x16, 0x92, 0x0f, 0x3e, 0xfc,
|
0x3d, 0xc7, 0x81, 0xc1, 0x21, 0x16, 0x6f, 0x2e, 0xa0, 0x85, 0xe4, 0x43, 0x0f, 0x7c, 0x88, 0xeb,
|
||||||
0x41, 0x2e, 0xfc, 0xe0, 0xeb, 0x0c, 0xb8, 0x96, 0x70, 0x78, 0xfc, 0x5c, 0xb9, 0x72, 0x05, 0xef,
|
0xff, 0xf9, 0x4f, 0x0c, 0xb8, 0x12, 0x38, 0x1a, 0x9b, 0xb8, 0x79, 0xf3, 0x26, 0x9e, 0xdf, 0xfb,
|
||||||
0x9f, 0x7e, 0x0d, 0xc3, 0x90, 0x68, 0xad, 0x65, 0xdd, 0x20, 0x2e, 0x6a, 0x5d, 0x4f, 0x89, 0x12,
|
0x1a, 0x86, 0x21, 0xd1, 0x5a, 0xcb, 0x9a, 0x22, 0x2e, 0xa2, 0xae, 0x05, 0xa2, 0xdc, 0x79, 0x17,
|
||||||
0x6d, 0x2a, 0xc5, 0xc2, 0xc2, 0x02, 0xe9, 0x74, 0x9a, 0x6c, 0x36, 0xcb, 0x72, 0x2a, 0x55, 0x62,
|
0x17, 0x17, 0xd9, 0xd8, 0xd8, 0x20, 0x93, 0xc9, 0x90, 0x5a, 0x4b, 0x95, 0xaa, 0x50, 0x3a, 0x9b,
|
||||||
0xa1, 0x4c, 0x36, 0x4b, 0x5f, 0x5f, 0x3f, 0xa1, 0x50, 0x88, 0x8b, 0x17, 0x2f, 0x61, 0x5a, 0x26,
|
0xa5, 0xaf, 0xaf, 0x9f, 0x60, 0x30, 0xc8, 0x8d, 0x1b, 0x6f, 0x62, 0x5a, 0x26, 0xeb, 0x1b, 0xeb,
|
||||||
0xab, 0xe9, 0x55, 0xda, 0x42, 0x41, 0x9a, 0x5b, 0x82, 0x2c, 0x27, 0x96, 0x48, 0xa7, 0x57, 0xb1,
|
0xb4, 0x05, 0x03, 0x34, 0xb7, 0x04, 0x58, 0x5d, 0x49, 0xb0, 0xb1, 0xb1, 0x8e, 0x65, 0x5b, 0x04,
|
||||||
0x6c, 0x8b, 0x50, 0x4b, 0x33, 0x03, 0x83, 0x83, 0x0c, 0x0e, 0x0d, 0xf1, 0xc6, 0xff, 0x1e, 0x41,
|
0x5b, 0x9a, 0x19, 0x18, 0x1c, 0x64, 0x70, 0x68, 0x88, 0xb3, 0x3f, 0x3b, 0x83, 0xd2, 0x0a, 0x37,
|
||||||
0x69, 0x85, 0x1b, 0x93, 0x60, 0xf0, 0x0e, 0x0c, 0x6f, 0x00, 0x3b, 0x9d, 0x60, 0xd9, 0xb6, 0x10,
|
0x26, 0x81, 0xc0, 0x7e, 0x0c, 0x8f, 0x1f, 0x7b, 0x63, 0x85, 0x55, 0xdb, 0x42, 0x48, 0x07, 0x4a,
|
||||||
0xd2, 0x81, 0xd2, 0xaa, 0x36, 0x8d, 0x56, 0xba, 0xac, 0xd6, 0xc4, 0x6b, 0x15, 0x75, 0xc5, 0x3c,
|
0xab, 0xea, 0x65, 0xb4, 0x32, 0x65, 0xd5, 0x3a, 0x5e, 0x6d, 0x2a, 0x51, 0xf4, 0x11, 0xad, 0x35,
|
||||||
0xa2, 0xb5, 0x66, 0xf7, 0xae, 0x21, 0xce, 0x4c, 0xcd, 0xb0, 0xb4, 0x78, 0x95, 0xce, 0x8e, 0x08,
|
0x87, 0x0f, 0x0d, 0x31, 0x7d, 0x25, 0x46, 0x62, 0xf9, 0x2d, 0xa2, 0x1d, 0x61, 0xa4, 0x94, 0x74,
|
||||||
0x52, 0x4a, 0x3a, 0x3a, 0x63, 0x5c, 0x9d, 0x9f, 0x67, 0x69, 0x39, 0x05, 0xd2, 0x41, 0xac, 0x2b,
|
0x44, 0x3b, 0x79, 0x6b, 0x61, 0x81, 0xc4, 0x6a, 0x0a, 0xa4, 0x83, 0xce, 0xae, 0x4e, 0xa4, 0x14,
|
||||||
0x86, 0x94, 0x02, 0xc3, 0xdb, 0xc8, 0x9b, 0xc7, 0x7e, 0x05, 0x40, 0x34, 0xd6, 0x81, 0x52, 0x8a,
|
0x18, 0x9e, 0x7d, 0x9c, 0x7b, 0xe5, 0x7f, 0x00, 0x88, 0x74, 0x76, 0xa0, 0x94, 0x22, 0x15, 0x1c,
|
||||||
0x54, 0x68, 0x8c, 0xa3, 0x0b, 0x33, 0x40, 0x86, 0x9c, 0x63, 0x27, 0x7d, 0xb2, 0xb0, 0x40, 0x32,
|
0xe3, 0xe7, 0x8b, 0x31, 0x20, 0x4d, 0xce, 0x71, 0x90, 0x3e, 0x59, 0x58, 0x20, 0x99, 0xb6, 0xda,
|
||||||
0x6d, 0xb5, 0xa5, 0x07, 0xaa, 0x95, 0x13, 0xd5, 0xfe, 0x37, 0x0c, 0x83, 0xb6, 0xb6, 0x36, 0x82,
|
0x35, 0x03, 0x3b, 0x4d, 0x27, 0x76, 0x7a, 0x2d, 0xa5, 0xa4, 0xad, 0xad, 0x8d, 0x40, 0x20, 0x80,
|
||||||
0xc1, 0x20, 0xb6, 0x6d, 0xd3, 0xd9, 0xd5, 0x43, 0x3a, 0x9d, 0xc1, 0xeb, 0x71, 0xf3, 0xe0, 0xfe,
|
0x6d, 0xdb, 0x44, 0xbb, 0x7a, 0xd8, 0xd8, 0x4c, 0xe3, 0x71, 0xbb, 0xb9, 0xef, 0x5d, 0xe3, 0xdc,
|
||||||
0xbd, 0x3c, 0xb8, 0x7f, 0x2f, 0x08, 0x51, 0x5a, 0x13, 0x84, 0x43, 0xad, 0xbc, 0xf7, 0xfd, 0x7f,
|
0xf7, 0xae, 0x71, 0x10, 0xa2, 0xb4, 0x26, 0x08, 0x05, 0x5b, 0x79, 0xff, 0x07, 0x7f, 0x07, 0x2a,
|
||||||
0x0c, 0x15, 0xfb, 0x8e, 0x0f, 0xfd, 0xd1, 0x43, 0xc5, 0x05, 0x5d, 0xe9, 0x4f, 0xef, 0xdd, 0x07,
|
0xf6, 0x1d, 0xef, 0x7f, 0xdf, 0xfd, 0xf9, 0x01, 0x2c, 0xfb, 0xd7, 0x7b, 0xf7, 0x09, 0xe0, 0x04,
|
||||||
0x80, 0x03, 0xe8, 0xeb, 0x0f, 0x91, 0x42, 0xf2, 0xe6, 0xf1, 0x13, 0x13, 0xc0, 0x72, 0xdd, 0x20,
|
0xfa, 0xed, 0x9b, 0x48, 0x21, 0x39, 0x77, 0xfe, 0xc2, 0x24, 0xb0, 0x5a, 0x53, 0xc4, 0x42, 0x08,
|
||||||
0x16, 0x42, 0xb0, 0xba, 0xba, 0xca, 0xec, 0xec, 0x2c, 0xc3, 0xc3, 0xc3, 0x08, 0x21, 0xc8, 0xe5,
|
0xd6, 0xd7, 0xd7, 0x99, 0x9d, 0x9d, 0x65, 0x78, 0x78, 0x18, 0x21, 0x44, 0x69, 0x51, 0xef, 0x72,
|
||||||
0x72, 0x00, 0xb8, 0xdd, 0x6e, 0x84, 0x10, 0x58, 0x96, 0x45, 0x2e, 0x97, 0xc3, 0xe1, 0xc8, 0x8b,
|
0xb9, 0x10, 0x42, 0x60, 0x59, 0x16, 0xb9, 0x5c, 0x0e, 0x87, 0x23, 0x1f, 0xc6, 0xe1, 0x70, 0x30,
|
||||||
0x71, 0x38, 0x1c, 0x8c, 0x8c, 0x8c, 0xf0, 0xea, 0xab, 0xaf, 0xd0, 0x1a, 0xf4, 0xe3, 0x71, 0x7b,
|
0x32, 0x32, 0xc2, 0x8b, 0x2f, 0xbe, 0x40, 0x28, 0xe0, 0xa7, 0xb1, 0xd1, 0x8d, 0x61, 0x18, 0x88,
|
||||||
0x90, 0x86, 0xc4, 0x90, 0x06, 0x86, 0x61, 0x20, 0x0d, 0x03, 0x43, 0x4a, 0xa4, 0x61, 0x20, 0xa5,
|
0xc2, 0x8e, 0x85, 0x61, 0x18, 0x5b, 0xce, 0xc5, 0x6b, 0x10, 0x85, 0xca, 0xa5, 0x4a, 0x3b, 0x21,
|
||||||
0xcc, 0x3f, 0x93, 0xb2, 0x20, 0xab, 0xc8, 0x5e, 0x0a, 0x65, 0xdb, 0x24, 0x12, 0x09, 0xcb, 0x90,
|
0xc9, 0x64, 0xd2, 0x34, 0x84, 0x58, 0xb2, 0x95, 0xad, 0x2d, 0xcb, 0x46, 0xd9, 0x96, 0x36, 0x2d,
|
||||||
0xf2, 0xaa, 0xad, 0x6c, 0x6d, 0x59, 0x36, 0xca, 0xb6, 0xb4, 0x69, 0x99, 0xea, 0x8d, 0x5f, 0x1e,
|
0x53, 0x9d, 0xfd, 0xc5, 0x2b, 0x57, 0x7e, 0xf0, 0x5f, 0x3f, 0x7c, 0x01, 0x48, 0x55, 0xa5, 0x50,
|
||||||
0x9b, 0xfa, 0xe1, 0x8f, 0x7e, 0xf2, 0x0a, 0x90, 0xaa, 0x09, 0xa1, 0xa2, 0xf5, 0x4f, 0x9f, 0x3e,
|
0x71, 0xf4, 0x2f, 0x5f, 0xbe, 0x4c, 0x4b, 0x4b, 0x0b, 0xcb, 0xcb, 0xcb, 0x74, 0x76, 0x76, 0x92,
|
||||||
0x4d, 0x4b, 0x4b, 0x0b, 0x8b, 0x8b, 0x8b, 0xc4, 0x62, 0x31, 0xe2, 0xf1, 0x38, 0x96, 0x65, 0xd1,
|
0x48, 0x24, 0x30, 0x4d, 0x93, 0xee, 0xee, 0x6e, 0x16, 0x16, 0x16, 0x98, 0x9b, 0x9b, 0xa3, 0xad,
|
||||||
0xdd, 0xdd, 0xcd, 0xfc, 0xfc, 0x3c, 0x73, 0x73, 0x73, 0xb4, 0xb5, 0xb5, 0xe1, 0xf7, 0xfb, 0x4b,
|
0xad, 0x0d, 0x9f, 0xcf, 0x57, 0xa2, 0x51, 0x77, 0x77, 0x37, 0x0f, 0x3f, 0xfc, 0x08, 0xb1, 0x58,
|
||||||
0x30, 0xea, 0xee, 0xee, 0xe6, 0xb1, 0xc7, 0x1e, 0xe7, 0xdc, 0xb9, 0x73, 0x64, 0xb3, 0xd9, 0xda,
|
0x8c, 0x5c, 0x2e, 0x57, 0x97, 0x01, 0x6a, 0xad, 0x31, 0x2a, 0xa6, 0x33, 0xdf, 0x7c, 0xee, 0x7b,
|
||||||
0x6b, 0xe7, 0x8a, 0x31, 0x8d, 0x86, 0xeb, 0x75, 0x97, 0x65, 0x59, 0x7c, 0xeb, 0xc5, 0x6f, 0x5f,
|
0x6f, 0x9e, 0x3d, 0x7b, 0xf6, 0x8f, 0x2a, 0x09, 0x02, 0x5c, 0x07, 0xae, 0x6b, 0x9d, 0x5f, 0xa7,
|
||||||
0x3a, 0x7a, 0xf4, 0xe8, 0x9f, 0x57, 0x02, 0x04, 0xb8, 0x00, 0x5c, 0xd0, 0x3a, 0xbf, 0x4e, 0xad,
|
0xd6, 0x74, 0xe2, 0xa3, 0x47, 0x8f, 0x32, 0x3b, 0x3b, 0x4b, 0x30, 0x18, 0x2c, 0xdd, 0xcb, 0x64,
|
||||||
0x9b, 0x89, 0xf7, 0xec, 0xd9, 0xc3, 0xec, 0xec, 0x2c, 0xa1, 0x50, 0xa8, 0x8c, 0xf7, 0x4f, 0x9e,
|
0x32, 0x4c, 0x4c, 0x4c, 0xe0, 0x76, 0xbb, 0x19, 0x1d, 0x1d, 0xa5, 0xb1, 0xb1, 0xb1, 0x62, 0x47,
|
||||||
0x3c, 0x89, 0xc7, 0xe3, 0x61, 0x74, 0x74, 0x14, 0x8f, 0xc7, 0x53, 0xb1, 0xa3, 0xe0, 0xa2, 0xab,
|
0xc1, 0x45, 0x57, 0x57, 0x17, 0x1d, 0x1d, 0x1d, 0x35, 0x57, 0x71, 0xd5, 0x36, 0xc7, 0x00, 0x4c,
|
||||||
0xab, 0x8b, 0x58, 0x2c, 0x56, 0x77, 0xf9, 0x59, 0x6b, 0x73, 0x0c, 0xc0, 0x34, 0x4d, 0x0e, 0x1f,
|
0xd3, 0xe4, 0xf4, 0xe9, 0xd3, 0xeb, 0xc0, 0x0f, 0xaa, 0xec, 0x4e, 0xeb, 0xaa, 0x22, 0xb6, 0x2c,
|
||||||
0x3e, 0xbc, 0x72, 0xf4, 0xe8, 0xd1, 0x1f, 0xd6, 0xd8, 0x9d, 0xd6, 0x35, 0x83, 0xd8, 0xb2, 0xac,
|
0x6b, 0x4b, 0xb0, 0xde, 0xde, 0xde, 0x12, 0x28, 0xad, 0x35, 0xf1, 0x78, 0x9c, 0xe1, 0xe1, 0xe1,
|
||||||
0x32, 0x61, 0xbd, 0xbd, 0xbd, 0x25, 0xa5, 0x94, 0x52, 0xc4, 0xe3, 0x71, 0x86, 0x87, 0x87, 0x4b,
|
0xd2, 0x02, 0xa6, 0x9a, 0x46, 0x1c, 0x0e, 0x47, 0xd5, 0xb9, 0x53, 0x79, 0x05, 0xab, 0xcc, 0x7c,
|
||||||
0x0b, 0x98, 0x5a, 0x31, 0x62, 0x18, 0x46, 0xcd, 0xcc, 0xbd, 0x71, 0x09, 0x5a, 0xe9, 0xf9, 0xe2,
|
0x71, 0x52, 0x28, 0xa5, 0xd4, 0xc5, 0x51, 0xde, 0xd3, 0xf3, 0x81, 0x4a, 0x11, 0x17, 0xa7, 0xb0,
|
||||||
0xaa, 0x4e, 0x4a, 0xa9, 0x8b, 0x56, 0xbe, 0xa1, 0xf3, 0x81, 0xca, 0x20, 0x2e, 0x96, 0xb0, 0xc5,
|
0xc5, 0xc0, 0x9d, 0x9d, 0x9d, 0x5b, 0x3a, 0x5f, 0x8f, 0xd0, 0x6b, 0x01, 0x2d, 0x07, 0x52, 0x8d,
|
||||||
0x41, 0x63, 0xb1, 0x58, 0xd9, 0xe4, 0xb7, 0x13, 0xe8, 0x5b, 0x95, 0x1f, 0xd5, 0x68, 0xfb, 0x1d,
|
0x62, 0x7b, 0x02, 0x50, 0x59, 0x46, 0x63, 0xb1, 0x18, 0x99, 0x4c, 0x06, 0xc3, 0x30, 0x70, 0x38,
|
||||||
0x1f, 0x70, 0x54, 0xd2, 0xe8, 0xcc, 0xcc, 0x0c, 0xeb, 0xeb, 0xeb, 0x18, 0x86, 0x81, 0xc3, 0xe1,
|
0x1c, 0x34, 0x35, 0x35, 0xd5, 0xd5, 0xe9, 0x7a, 0x41, 0x94, 0x4f, 0x59, 0x7e, 0x9d, 0xa7, 0x45,
|
||||||
0xc0, 0xef, 0xf7, 0x6f, 0x6b, 0xd2, 0xdb, 0x55, 0x62, 0x63, 0xc9, 0xf2, 0x4e, 0x4e, 0x8b, 0xb6,
|
0xbb, 0x3a, 0xf1, 0xc1, 0x83, 0x07, 0xf3, 0xeb, 0x53, 0xb7, 0x9b, 0xb9, 0xb9, 0x39, 0x4c, 0xd3,
|
||||||
0xcc, 0xc4, 0x3b, 0x77, 0xee, 0xcc, 0xaf, 0x4f, 0xdd, 0x6e, 0x2e, 0x5c, 0xb8, 0xb0, 0xe5, 0x26,
|
0xdc, 0x6d, 0x8b, 0xbd, 0x6e, 0x10, 0xe5, 0x94, 0xd9, 0x4d, 0xe8, 0x7b, 0xa6, 0x50, 0xb5, 0x6a,
|
||||||
0xd5, 0x8d, 0x28, 0xb1, 0x11, 0x32, 0x5b, 0x05, 0xfa, 0x0d, 0x43, 0xa8, 0xfa, 0x01, 0x89, 0x62,
|
0x71, 0xed, 0xda, 0x35, 0x9c, 0x4e, 0x27, 0xcd, 0xcd, 0xcd, 0xa5, 0xea, 0xb3, 0xd3, 0x11, 0x8f,
|
||||||
0x76, 0x76, 0x16, 0xa7, 0xd3, 0x49, 0x20, 0x10, 0xc0, 0xe7, 0xf3, 0xd5, 0x1c, 0x70, 0x69, 0x69,
|
0xc7, 0x89, 0xc5, 0x62, 0x5b, 0x3a, 0xd5, 0xd3, 0xd3, 0x43, 0x7b, 0x7b, 0x3b, 0x6b, 0x6b, 0x6b,
|
||||||
0x89, 0xe9, 0xe9, 0xe9, 0xb2, 0xf7, 0x3d, 0x3d, 0x3d, 0xb4, 0xb7, 0xb7, 0xb3, 0xb2, 0xb2, 0xc2,
|
0x4c, 0x4e, 0x4e, 0x6e, 0x19, 0xf5, 0xf6, 0xf6, 0x76, 0xa2, 0xd1, 0xe8, 0xad, 0x67, 0xa0, 0xb8,
|
||||||
0xc4, 0xc4, 0x44, 0x99, 0xd5, 0xdb, 0xdb, 0xdb, 0xe9, 0xec, 0xec, 0xbc, 0x79, 0x0f, 0x14, 0x0b,
|
0x88, 0xae, 0x36, 0xba, 0xd1, 0x68, 0x94, 0x8d, 0x8d, 0x0d, 0x2e, 0x5d, 0xba, 0x44, 0x24, 0x12,
|
||||||
0xb2, 0x6a, 0x4d, 0x4a, 0x49, 0x67, 0x67, 0x27, 0xab, 0xab, 0xab, 0x9c, 0x3a, 0x75, 0x8a, 0x68,
|
0xe1, 0xc8, 0x91, 0x23, 0x3b, 0x7e, 0xd6, 0xef, 0xf7, 0x73, 0xe4, 0xc8, 0x91, 0x2d, 0x42, 0x6e,
|
||||||
0x34, 0xca, 0x9d, 0x77, 0xde, 0x59, 0xf5, 0xb3, 0xcd, 0xcd, 0xcd, 0x8c, 0x8e, 0x8e, 0x96, 0x59,
|
0x68, 0xc8, 0x3f, 0xb4, 0xf1, 0x7a, 0xbd, 0x8c, 0x8d, 0x8d, 0x6d, 0x11, 0x6f, 0xde, 0x0f, 0xb8,
|
||||||
0xb5, 0xa1, 0x21, 0x7f, 0x68, 0xe3, 0xf3, 0xf9, 0x18, 0x1b, 0x1b, 0x2b, 0x0b, 0x5e, 0xc3, 0x30,
|
0x3d, 0x14, 0xaa, 0xc5, 0x45, 0xc3, 0x30, 0x68, 0x6f, 0x6f, 0x67, 0x75, 0x75, 0x95, 0xf9, 0xf9,
|
||||||
0x6e, 0xcd, 0x21, 0x5f, 0x3d, 0x0f, 0x14, 0x93, 0x55, 0x47, 0x47, 0x07, 0xa9, 0x54, 0x8a, 0x4b,
|
0x79, 0x32, 0x99, 0x0c, 0xe3, 0xe3, 0xe3, 0xdb, 0x32, 0x91, 0x48, 0x24, 0x98, 0x9a, 0x9a, 0xda,
|
||||||
0x97, 0x2e, 0xb1, 0xbe, 0xbe, 0xce, 0xbe, 0x7d, 0xfb, 0xaa, 0x7a, 0x60, 0x72, 0x72, 0xb2, 0x0c,
|
0x02, 0x3e, 0x10, 0x08, 0x30, 0x3a, 0x3a, 0x4a, 0x32, 0x99, 0x64, 0x62, 0x62, 0x62, 0xcb, 0xe7,
|
||||||
0xeb, 0xa1, 0x50, 0x88, 0xd1, 0xd1, 0x51, 0x96, 0x97, 0x97, 0x39, 0x71, 0xe2, 0x44, 0xd9, 0xbb,
|
0xa3, 0xd1, 0x28, 0xbd, 0xbd, 0xbd, 0xb7, 0x46, 0x21, 0x21, 0x84, 0xeb, 0xd4, 0xa9, 0x53, 0xee,
|
||||||
0xae, 0xae, 0x2e, 0x7a, 0x7b, 0x7b, 0x6f, 0x0e, 0x42, 0x42, 0x08, 0xd7, 0xa1, 0x43, 0x87, 0xdc,
|
0xca, 0xa9, 0x44, 0xf1, 0x08, 0x87, 0xc3, 0x08, 0x21, 0x90, 0x52, 0x32, 0x3e, 0x3e, 0x8e, 0xd6,
|
||||||
0x95, 0xa5, 0x44, 0xb1, 0x45, 0xa3, 0x51, 0x84, 0x10, 0x48, 0x29, 0xd9, 0xbb, 0x77, 0x2f, 0x00,
|
0x9a, 0x8b, 0x17, 0x2f, 0x92, 0x4c, 0x26, 0x09, 0x04, 0x02, 0x5b, 0x78, 0xdd, 0xda, 0xda, 0x4a,
|
||||||
0xe3, 0xe3, 0xe3, 0x24, 0x12, 0x09, 0x82, 0xc1, 0x60, 0x19, 0xae, 0x5b, 0x5b, 0x5b, 0x09, 0x87,
|
0x28, 0x14, 0x2a, 0x75, 0xde, 0x34, 0x4d, 0xce, 0x9d, 0x3b, 0x57, 0xca, 0xce, 0x89, 0x13, 0x27,
|
||||||
0xc3, 0x25, 0x0f, 0x58, 0x96, 0xc5, 0xb1, 0x63, 0xc7, 0x4a, 0xde, 0x39, 0x70, 0xe0, 0xc0, 0xa6,
|
0xb6, 0x19, 0x67, 0xf9, 0xb5, 0x52, 0xca, 0x21, 0x84, 0xd8, 0xa7, 0xb5, 0xde, 0xa8, 0x05, 0x40,
|
||||||
0xc4, 0xb9, 0xb1, 0xaf, 0x94, 0x72, 0x08, 0x21, 0x1a, 0xb5, 0xd6, 0xe9, 0x7a, 0x0a, 0xc8, 0x8d,
|
0x96, 0x3f, 0x5d, 0x04, 0x7c, 0xd9, 0x6c, 0xd6, 0x55, 0x6b, 0xc7, 0xba, 0x52, 0x94, 0x2e, 0x97,
|
||||||
0xa7, 0x8b, 0x40, 0x53, 0x36, 0x9b, 0x75, 0xd5, 0xdb, 0xb1, 0xae, 0xb4, 0x50, 0x43, 0x43, 0x43,
|
0x6b, 0x47, 0x33, 0xaa, 0x56, 0x55, 0xca, 0x17, 0x4c, 0x3b, 0x3d, 0xed, 0x29, 0x7b, 0x6d, 0x00,
|
||||||
0xd5, 0x64, 0x54, 0x8b, 0xe7, 0x2b, 0xaf, 0x5a, 0xec, 0x57, 0x28, 0x99, 0x9b, 0x85, 0x10, 0xbe,
|
0xcd, 0x42, 0x08, 0x6f, 0xbd, 0x19, 0x70, 0x03, 0x8d, 0x96, 0x65, 0x39, 0xea, 0x29, 0x67, 0xa6,
|
||||||
0xed, 0x7a, 0xc0, 0x0d, 0x78, 0x2c, 0xcb, 0x72, 0x6e, 0x87, 0xce, 0x4c, 0xd3, 0x64, 0x6a, 0x6a,
|
0x69, 0x72, 0xf5, 0xea, 0x55, 0x92, 0xc9, 0x24, 0xe9, 0x74, 0x9a, 0xb5, 0xb5, 0x35, 0x7a, 0x7a,
|
||||||
0x8a, 0xe5, 0xe5, 0x65, 0x32, 0x99, 0x0c, 0x2b, 0x2b, 0x2b, 0xf4, 0xf4, 0xf4, 0xd4, 0xa4, 0x47,
|
0x7a, 0xaa, 0x96, 0x47, 0xa7, 0xd3, 0xc9, 0xb1, 0x63, 0xc7, 0x6a, 0x96, 0xcd, 0x8a, 0xf7, 0x24,
|
||||||
0xa7, 0xd3, 0xc9, 0xfe, 0xfd, 0xfb, 0xeb, 0xd2, 0x66, 0xc5, 0x3b, 0x03, 0xf0, 0x00, 0x39, 0x21,
|
0xd0, 0x08, 0xe4, 0x84, 0x10, 0x99, 0x6a, 0xa6, 0xe6, 0xa8, 0xc8, 0x86, 0xb4, 0x6d, 0x5b, 0x99,
|
||||||
0xc4, 0x7a, 0xad, 0xa4, 0xe6, 0xa8, 0xf0, 0x86, 0xb4, 0x6d, 0xdb, 0x36, 0x4d, 0x53, 0xbb, 0x5c,
|
0xa6, 0xa9, 0x5d, 0x2e, 0x97, 0x28, 0xba, 0xa9, 0x52, 0x2a, 0xbf, 0x5b, 0x56, 0xd1, 0x78, 0x4f,
|
||||||
0x2e, 0xe1, 0x70, 0x38, 0x4a, 0xab, 0x23, 0xc3, 0x30, 0xca, 0x06, 0x50, 0x4a, 0x95, 0x61, 0xd6,
|
0x4f, 0x4f, 0xe9, 0xb5, 0xd3, 0xe9, 0x2c, 0xed, 0xb2, 0xd5, 0xb3, 0xa2, 0xab, 0xf5, 0x9e, 0x6d,
|
||||||
0xe9, 0x74, 0x96, 0x76, 0xd9, 0xb6, 0xb3, 0xa2, 0xab, 0xf7, 0xce, 0xb6, 0x6d, 0x84, 0x10, 0x56,
|
0xdb, 0x08, 0x21, 0xac, 0x42, 0x9f, 0xc4, 0x4e, 0x4b, 0xdf, 0x9d, 0x00, 0x98, 0x80, 0x39, 0x3f,
|
||||||
0x61, 0x4e, 0xa2, 0xda, 0xd2, 0xb7, 0x9a, 0x02, 0x26, 0x60, 0x5e, 0xbe, 0x7c, 0xf9, 0xfb, 0xcf,
|
0x3f, 0xff, 0x1f, 0x4f, 0x3d, 0xf5, 0xd4, 0xa9, 0xe3, 0xc7, 0x8f, 0x6b, 0x51, 0x88, 0xba, 0x57,
|
||||||
0x3e, 0xfb, 0xec, 0xa1, 0xfb, 0xee, 0xbb, 0xef, 0x1d, 0x65, 0xc6, 0x77, 0x9a, 0x51, 0x37, 0xb6,
|
0x83, 0xf9, 0x75, 0x1c, 0xb5, 0xec, 0x7b, 0xfa, 0xd5, 0x57, 0x5f, 0x95, 0x8b, 0x8b, 0x8b, 0x2f,
|
||||||
0xf1, 0xf1, 0x71, 0xb1, 0xb0, 0xb0, 0xf0, 0x2a, 0x90, 0x2b, 0xce, 0xab, 0xe6, 0x58, 0x1b, 0xd2,
|
0x02, 0xb9, 0x62, 0xbf, 0xaa, 0x7e, 0xa7, 0xcc, 0xc6, 0x05, 0xe0, 0x03, 0x7c, 0x91, 0x48, 0x24,
|
||||||
0xb8, 0x00, 0x9a, 0x80, 0xa6, 0x68, 0x34, 0x1a, 0x0d, 0x85, 0x42, 0x83, 0x42, 0x08, 0xa7, 0xd6,
|
0x12, 0x0c, 0x06, 0x07, 0x85, 0x10, 0x4e, 0xad, 0xb5, 0x28, 0xa4, 0xf3, 0x8e, 0x1f, 0x52, 0x4a,
|
||||||
0x5a, 0x14, 0xf0, 0x78, 0xdb, 0x9b, 0x94, 0xd2, 0x12, 0x42, 0xe8, 0x74, 0x3a, 0x3d, 0x37, 0x3d,
|
0x0b, 0xd0, 0x9b, 0x9b, 0x9b, 0x73, 0x33, 0x33, 0x33, 0x6f, 0x00, 0xeb, 0x40, 0x4a, 0x6b, 0xbd,
|
||||||
0x3d, 0xfd, 0x36, 0xb0, 0x0a, 0xa4, 0xb4, 0xd6, 0x5b, 0x2b, 0xb0, 0xc1, 0x7a, 0x6e, 0xc0, 0x0b,
|
0x3b, 0x80, 0xb2, 0x51, 0x70, 0x03, 0x1e, 0xa0, 0xa1, 0xf0, 0x7b, 0x07, 0xa3, 0x56, 0x0a, 0x6f,
|
||||||
0x34, 0x14, 0x7e, 0xef, 0x60, 0xd4, 0x73, 0xe1, 0x2d, 0x6e, 0x56, 0xa1, 0x64, 0xce, 0x01, 0xeb,
|
0xf3, 0x61, 0x15, 0xa6, 0xcc, 0x39, 0x20, 0x03, 0x6c, 0xea, 0x5d, 0x9e, 0x92, 0x8b, 0x6a, 0xf4,
|
||||||
0xc0, 0x9a, 0xde, 0xe2, 0x94, 0x5c, 0xd4, 0x0a, 0xd8, 0x82, 0x47, 0x8c, 0x02, 0xcc, 0xc4, 0xff,
|
0x28, 0x64, 0xc4, 0x28, 0xd0, 0x4c, 0xfc, 0x3f, 0x02, 0xb0, 0xf5, 0x1e, 0x1e, 0xed, 0x8b, 0xdf,
|
||||||
0xa3, 0x02, 0xb6, 0xbe, 0x81, 0xa3, 0x7d, 0xf1, 0xfb, 0xfe, 0x73, 0x9b, 0xff, 0x03, 0xce, 0xd3,
|
0xf4, 0x9f, 0xdb, 0xfc, 0x1f, 0x45, 0xe2, 0x2c, 0x7d, 0x65, 0x42, 0xd5, 0x87, 0x00, 0x00, 0x00,
|
||||||
0x2b, 0x55, 0x21, 0x2a, 0xd7, 0xa4, 0x00, 0x00, 0x00, 0x00, 0x49, 0x45, 0x4e, 0x44, 0xae, 0x42,
|
0x00, 0x49, 0x45, 0x4e, 0x44, 0xae, 0x42, 0x60, 0x82,
|
||||||
0x60, 0x82,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const BITMAP_OPAQUE icon_pcbcalculator_xpm[1] = {{ png, sizeof( png ), "icon_pcbcalculator_xpm" }};
|
const BITMAP_OPAQUE icon_pcbcalculator_xpm[1] = {{ png, sizeof( png ), "icon_pcbcalculator_xpm" }};
|
||||||
|
|
|
@ -59,7 +59,7 @@ DISPLAY_FOOTPRINTS_FRAME::DISPLAY_FOOTPRINTS_FRAME( CVPCB_MAINFRAME* father,
|
||||||
icon.CopyFromBitmap( KiBitmap( icon_cvpcb_xpm ) );
|
icon.CopyFromBitmap( KiBitmap( icon_cvpcb_xpm ) );
|
||||||
SetIcon( icon );
|
SetIcon( icon );
|
||||||
|
|
||||||
SetBoard( new BOARD( NULL ) );
|
SetBoard( new BOARD( NULL, this ) );
|
||||||
SetScreen( new PCB_SCREEN() );
|
SetScreen( new PCB_SCREEN() );
|
||||||
|
|
||||||
LoadSettings();
|
LoadSettings();
|
||||||
|
@ -68,7 +68,6 @@ DISPLAY_FOOTPRINTS_FRAME::DISPLAY_FOOTPRINTS_FRAME( CVPCB_MAINFRAME* father,
|
||||||
if( (m_LastGridSizeId <= 0) ||
|
if( (m_LastGridSizeId <= 0) ||
|
||||||
(m_LastGridSizeId > (ID_POPUP_GRID_USER - ID_POPUP_GRID_LEVEL_1000)) )
|
(m_LastGridSizeId > (ID_POPUP_GRID_USER - ID_POPUP_GRID_LEVEL_1000)) )
|
||||||
m_LastGridSizeId = ID_POPUP_GRID_LEVEL_500 - ID_POPUP_GRID_LEVEL_1000;
|
m_LastGridSizeId = ID_POPUP_GRID_LEVEL_500 - ID_POPUP_GRID_LEVEL_1000;
|
||||||
|
|
||||||
GetScreen()->SetGrid( ID_POPUP_GRID_LEVEL_1000 + m_LastGridSizeId );
|
GetScreen()->SetGrid( ID_POPUP_GRID_LEVEL_1000 + m_LastGridSizeId );
|
||||||
|
|
||||||
// Initialize some display options
|
// Initialize some display options
|
||||||
|
|
|
@ -41,11 +41,10 @@
|
||||||
#include "class_GERBER.h"
|
#include "class_GERBER.h"
|
||||||
|
|
||||||
|
|
||||||
#define SHOW_BOUNDING_BOX 0 // Set to 1 to draw the bounding box for debugging purposes.
|
/**********************************************************/
|
||||||
|
|
||||||
|
|
||||||
GERBER_DRAW_ITEM::GERBER_DRAW_ITEM( BOARD_ITEM* aParent, GERBER_IMAGE* aGerberparams ) :
|
GERBER_DRAW_ITEM::GERBER_DRAW_ITEM( BOARD_ITEM* aParent, GERBER_IMAGE* aGerberparams ) :
|
||||||
BOARD_ITEM( aParent, TYPE_GERBER_DRAW_ITEM )
|
BOARD_ITEM( aParent, TYPE_GERBER_DRAW_ITEM )
|
||||||
|
/**********************************************************/
|
||||||
{
|
{
|
||||||
m_imageParams = aGerberparams;
|
m_imageParams = aGerberparams;
|
||||||
m_Layer = 0;
|
m_Layer = 0;
|
||||||
|
@ -340,8 +339,10 @@ bool GERBER_DRAW_ITEM::HasNegativeItems()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*********************************************************************/
|
||||||
void GERBER_DRAW_ITEM::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode,
|
void GERBER_DRAW_ITEM::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode,
|
||||||
const wxPoint& aOffset )
|
const wxPoint& aOffset )
|
||||||
|
/*********************************************************************/
|
||||||
{
|
{
|
||||||
static D_CODE dummyD_CODE( 0 ); // used when a D_CODE is not found. default D_CODE to draw a flashed item
|
static D_CODE dummyD_CODE( 0 ); // used when a D_CODE is not found. default D_CODE to draw a flashed item
|
||||||
int color, alt_color;
|
int color, alt_color;
|
||||||
|
@ -485,14 +486,6 @@ void GERBER_DRAW_ITEM::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode,
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
#if SHOW_BOUNDING_BOX
|
|
||||||
/* Draw the component boundary box */
|
|
||||||
{
|
|
||||||
EDA_RECT boundaryBox = GetBoundingBox();
|
|
||||||
GRRect( &aPanel->m_ClipBox, aDC, boundaryBox, 0, BROWN );
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -139,7 +139,6 @@ void BOARD::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode, const wxPoin
|
||||||
// this is due to negative objects (drawn using background color) that create artefacct
|
// this is due to negative objects (drawn using background color) that create artefacct
|
||||||
// on other images when drawn on screen
|
// on other images when drawn on screen
|
||||||
bool useBufferBitmap = false;
|
bool useBufferBitmap = false;
|
||||||
|
|
||||||
if( (aDrawMode == GR_COPY) || ( aDrawMode == GR_OR ) )
|
if( (aDrawMode == GR_COPY) || ( aDrawMode == GR_OR ) )
|
||||||
useBufferBitmap = true;
|
useBufferBitmap = true;
|
||||||
|
|
||||||
|
@ -174,11 +173,9 @@ void BOARD::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode, const wxPoin
|
||||||
bool doBlit = false; // this flag requests an image transfert to actual screen when true.
|
bool doBlit = false; // this flag requests an image transfert to actual screen when true.
|
||||||
|
|
||||||
bool end = false;
|
bool end = false;
|
||||||
|
|
||||||
for( int layer = 0; !end; layer++ )
|
for( int layer = 0; !end; layer++ )
|
||||||
{
|
{
|
||||||
int active_layer = ( (GERBVIEW_FRAME*) aPanel->GetParent() )->getActiveLayer();
|
int active_layer = ( (GERBVIEW_FRAME*) m_PcbFrame )->getActiveLayer();
|
||||||
|
|
||||||
if( layer == active_layer ) // active layer will be drawn after other layers
|
if( layer == active_layer ) // active layer will be drawn after other layers
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -208,7 +205,6 @@ void BOARD::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode, const wxPoin
|
||||||
layerDC.SetDeviceOrigin(0,0);
|
layerDC.SetDeviceOrigin(0,0);
|
||||||
layerDC.SetLogicalOrigin( 0, 0 );
|
layerDC.SetLogicalOrigin( 0, 0 );
|
||||||
layerDC.SetUserScale( 1, 1 );
|
layerDC.SetUserScale( 1, 1 );
|
||||||
|
|
||||||
if( aDrawMode == GR_COPY )
|
if( aDrawMode == GR_COPY )
|
||||||
{
|
{
|
||||||
// Use the layer bitmap itself as a mask when blitting. The bitmap
|
// Use the layer bitmap itself as a mask when blitting. The bitmap
|
||||||
|
@ -216,7 +212,8 @@ void BOARD::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode, const wxPoin
|
||||||
layerDC.SelectObject( wxNullBitmap );
|
layerDC.SelectObject( wxNullBitmap );
|
||||||
layerBitmap->SetMask( new wxMask( *layerBitmap, bgColor ) );
|
layerBitmap->SetMask( new wxMask( *layerBitmap, bgColor ) );
|
||||||
layerDC.SelectObject( *layerBitmap );
|
layerDC.SelectObject( *layerBitmap );
|
||||||
screenDC.Blit( 0, 0, bitmapWidth, bitmapHeight, &layerDC, 0, 0, wxCOPY, true );
|
screenDC.Blit( 0, 0, bitmapWidth, bitmapHeight,
|
||||||
|
&layerDC, 0, 0, wxCOPY, true );
|
||||||
}
|
}
|
||||||
else if( aDrawMode == GR_OR )
|
else if( aDrawMode == GR_OR )
|
||||||
{
|
{
|
||||||
|
@ -227,9 +224,9 @@ void BOARD::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode, const wxPoin
|
||||||
// the cpu cycles needed to create the monochromatic bitmap above, and
|
// the cpu cycles needed to create the monochromatic bitmap above, and
|
||||||
// the extra time needed to do bit indexing into the monochromatic bitmap
|
// the extra time needed to do bit indexing into the monochromatic bitmap
|
||||||
// on the blit above.
|
// on the blit above.
|
||||||
screenDC.Blit( 0, 0, bitmapWidth, bitmapHeight, &layerDC, 0, 0, wxOR );
|
screenDC.Blit( 0, 0, bitmapWidth, bitmapHeight,
|
||||||
|
&layerDC, 0, 0, wxOR );
|
||||||
}
|
}
|
||||||
|
|
||||||
// Restore actual values and clear bitmpap for next drawing
|
// Restore actual values and clear bitmpap for next drawing
|
||||||
layerDC.SetDeviceOrigin( dev_org.x, dev_org.y );
|
layerDC.SetDeviceOrigin( dev_org.x, dev_org.y );
|
||||||
layerDC.SetLogicalOrigin( logical_org.x, logical_org.y );
|
layerDC.SetLogicalOrigin( logical_org.x, logical_org.y );
|
||||||
|
@ -259,7 +256,7 @@ void BOARD::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode, const wxPoin
|
||||||
|
|
||||||
int dcode_highlight = 0;
|
int dcode_highlight = 0;
|
||||||
|
|
||||||
if( layer == ( (GERBVIEW_FRAME*) aPanel->GetParent() )->getActiveLayer() )
|
if( layer == ( (GERBVIEW_FRAME*) m_PcbFrame )->getActiveLayer() )
|
||||||
dcode_highlight = gerber->m_Selected_Tool;
|
dcode_highlight = gerber->m_Selected_Tool;
|
||||||
|
|
||||||
int layerdrawMode = GR_COPY;
|
int layerdrawMode = GR_COPY;
|
||||||
|
@ -280,7 +277,6 @@ void BOARD::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode, const wxPoin
|
||||||
|
|
||||||
if( dcode_highlight && dcode_highlight == gerb_item->m_DCode )
|
if( dcode_highlight && dcode_highlight == gerb_item->m_DCode )
|
||||||
drawMode |= GR_SURBRILL;
|
drawMode |= GR_SURBRILL;
|
||||||
|
|
||||||
gerb_item->Draw( aPanel, plotDC, drawMode );
|
gerb_item->Draw( aPanel, plotDC, drawMode );
|
||||||
doBlit = true;
|
doBlit = true;
|
||||||
}
|
}
|
||||||
|
@ -301,12 +297,14 @@ void BOARD::Draw( EDA_DRAW_PANEL* aPanel, wxDC* aDC, int aDrawMode, const wxPoin
|
||||||
layerDC.SelectObject( wxNullBitmap );
|
layerDC.SelectObject( wxNullBitmap );
|
||||||
layerBitmap->SetMask( new wxMask( *layerBitmap, bgColor ) );
|
layerBitmap->SetMask( new wxMask( *layerBitmap, bgColor ) );
|
||||||
layerDC.SelectObject( *layerBitmap );
|
layerDC.SelectObject( *layerBitmap );
|
||||||
screenDC.Blit( 0, 0, bitmapWidth, bitmapHeight, &layerDC, 0, 0, wxCOPY, true );
|
screenDC.Blit( 0, 0, bitmapWidth, bitmapHeight,
|
||||||
|
&layerDC, 0, 0, wxCOPY, true );
|
||||||
|
|
||||||
}
|
}
|
||||||
else if( aDrawMode == GR_OR )
|
else if( aDrawMode == GR_OR )
|
||||||
{
|
{
|
||||||
screenDC.Blit( 0, 0, bitmapWidth, bitmapHeight, &layerDC, 0, 0, wxOR );
|
screenDC.Blit( 0, 0, bitmapWidth, bitmapHeight,
|
||||||
|
&layerDC, 0, 0, wxOR );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -47,7 +47,7 @@ GBR_TO_PCB_EXPORTER::GBR_TO_PCB_EXPORTER( GERBVIEW_FRAME * aFrame, FILE * aFile
|
||||||
{
|
{
|
||||||
m_gerbview_frame = aFrame;
|
m_gerbview_frame = aFrame;
|
||||||
m_file = aFile;
|
m_file = aFile;
|
||||||
m_pcb = new BOARD( NULL );
|
m_pcb = new BOARD( NULL, m_gerbview_frame );
|
||||||
}
|
}
|
||||||
|
|
||||||
GBR_TO_PCB_EXPORTER::~GBR_TO_PCB_EXPORTER()
|
GBR_TO_PCB_EXPORTER::~GBR_TO_PCB_EXPORTER()
|
||||||
|
|
|
@ -44,7 +44,7 @@ GERBVIEW_FRAME::GERBVIEW_FRAME( wxWindow* father,
|
||||||
m_SelLayerBox = NULL;
|
m_SelLayerBox = NULL;
|
||||||
m_DCodeSelector = NULL;
|
m_DCodeSelector = NULL;
|
||||||
m_displayMode = 0;
|
m_displayMode = 0;
|
||||||
m_drillFileHistory.SetBaseId( ID_GERBVIEW_DRILL_FILE1 );
|
m_drillFileHistory.SetBaseId(ID_GERBVIEW_DRILL_FILE1);
|
||||||
|
|
||||||
if( DrawPanel )
|
if( DrawPanel )
|
||||||
DrawPanel->m_Block_Enable = true;
|
DrawPanel->m_Block_Enable = true;
|
||||||
|
@ -56,7 +56,7 @@ GERBVIEW_FRAME::GERBVIEW_FRAME( wxWindow* father,
|
||||||
|
|
||||||
SetScreen( ScreenPcb );
|
SetScreen( ScreenPcb );
|
||||||
|
|
||||||
SetBoard( new BOARD( NULL ) );
|
SetBoard( new BOARD( NULL, this ) );
|
||||||
GetBoard()->SetEnabledLayers( FULL_LAYERS ); // All 32 layers enabled at first.
|
GetBoard()->SetEnabledLayers( FULL_LAYERS ); // All 32 layers enabled at first.
|
||||||
GetBoard()->SetVisibleLayers( FULL_LAYERS ); // All 32 layers visible.
|
GetBoard()->SetVisibleLayers( FULL_LAYERS ); // All 32 layers visible.
|
||||||
|
|
||||||
|
@ -144,6 +144,34 @@ void GERBVIEW_FRAME::OnCloseWindow( wxCloseEvent& Event )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
double GERBVIEW_FRAME::BestZoom()
|
||||||
|
{
|
||||||
|
// gives a minimal value to zoom, if no item in list
|
||||||
|
if( GetBoard()->m_Drawings == NULL )
|
||||||
|
return 160.0;
|
||||||
|
|
||||||
|
EDA_RECT bbox;
|
||||||
|
BOARD_ITEM* item = GetBoard()->m_Drawings;
|
||||||
|
|
||||||
|
bbox = ( (GERBER_DRAW_ITEM*) item )->GetBoundingBox();
|
||||||
|
|
||||||
|
for( ; item; item = item->Next() )
|
||||||
|
{
|
||||||
|
GERBER_DRAW_ITEM* gerb_item = (GERBER_DRAW_ITEM*) item;
|
||||||
|
bbox.Merge( gerb_item->GetBoundingBox() );
|
||||||
|
}
|
||||||
|
|
||||||
|
wxSize size = DrawPanel->GetClientSize();
|
||||||
|
|
||||||
|
double x = (double) bbox.GetWidth() / (double) size.x;
|
||||||
|
double y = (double) bbox.GetHeight() / (double) size.y;
|
||||||
|
GetScreen()->SetScrollCenterPosition( bbox.Centre() );
|
||||||
|
|
||||||
|
double best_zoom = MAX( x, y );
|
||||||
|
return best_zoom;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void GERBVIEW_FRAME::LoadSettings()
|
void GERBVIEW_FRAME::LoadSettings()
|
||||||
{
|
{
|
||||||
wxConfig* config = wxGetApp().m_EDA_Config;
|
wxConfig* config = wxGetApp().m_EDA_Config;
|
||||||
|
|
|
@ -68,6 +68,7 @@ public: GERBVIEW_FRAME( wxWindow* father, const wxString& title,
|
||||||
void OnLeftClick( wxDC* DC, const wxPoint& MousePos );
|
void OnLeftClick( wxDC* DC, const wxPoint& MousePos );
|
||||||
void OnLeftDClick( wxDC* DC, const wxPoint& MousePos );
|
void OnLeftDClick( wxDC* DC, const wxPoint& MousePos );
|
||||||
bool OnRightClick( const wxPoint& MousePos, wxMenu* PopMenu );
|
bool OnRightClick( const wxPoint& MousePos, wxMenu* PopMenu );
|
||||||
|
double BestZoom();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function ReportMessage
|
* Function ReportMessage
|
||||||
|
|
|
@ -357,7 +357,8 @@ public:
|
||||||
int m_Flags; // flags for editing and other uses.
|
int m_Flags; // flags for editing and other uses.
|
||||||
|
|
||||||
unsigned long m_TimeStamp; // Time stamp used for logical links
|
unsigned long m_TimeStamp; // Time stamp used for logical links
|
||||||
int m_Selected; /* Used by block commands, and selective editing */
|
int m_Selected; /* Used by block commands, and selective
|
||||||
|
* editing */
|
||||||
|
|
||||||
// member used in undo/redo function
|
// member used in undo/redo function
|
||||||
EDA_ITEM* m_Image; // Link to an image copy to save a copy of
|
EDA_ITEM* m_Image; // Link to an image copy to save a copy of
|
||||||
|
|
|
@ -182,6 +182,7 @@ set(PCBNEW_SRCS
|
||||||
tool_pcb.cpp
|
tool_pcb.cpp
|
||||||
toolbars_update_user_interface.cpp
|
toolbars_update_user_interface.cpp
|
||||||
tracepcb.cpp
|
tracepcb.cpp
|
||||||
|
track.cpp
|
||||||
tr_modif.cpp
|
tr_modif.cpp
|
||||||
trpiste.cpp
|
trpiste.cpp
|
||||||
work.cpp
|
work.cpp
|
||||||
|
|
|
@ -39,7 +39,7 @@ void PCB_EDIT_FRAME::Attribut_Track( TRACK* track, wxDC* DC, bool Flag_On )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
DrawPanel->CrossHairOff( DC ); // Erase cursor shape
|
DrawPanel->CrossHairOff( DC ); // Erase cursor shape
|
||||||
Track = GetBoard()->MarkTrace( track, &nb_segm, NULL, NULL, true );
|
Track = MarkTrace( GetBoard(), track, &nb_segm, NULL, NULL, true );
|
||||||
DrawTraces( DrawPanel, DC, Track, nb_segm, GR_OR | GR_SURBRILL );
|
DrawTraces( DrawPanel, DC, Track, nb_segm, GR_OR | GR_SURBRILL );
|
||||||
|
|
||||||
for( ; (Track != NULL) && (nb_segm > 0); nb_segm-- )
|
for( ; (Track != NULL) && (nb_segm > 0); nb_segm-- )
|
||||||
|
|
|
@ -105,48 +105,32 @@ void PCB_BASE_FRAME::SetBoard( BOARD* aBoard )
|
||||||
double PCB_BASE_FRAME::BestZoom( void )
|
double PCB_BASE_FRAME::BestZoom( void )
|
||||||
{
|
{
|
||||||
int dx, dy;
|
int dx, dy;
|
||||||
double zx, zy;
|
double ii, jj;
|
||||||
wxSize size;
|
wxSize size;
|
||||||
wxPoint center;
|
|
||||||
|
|
||||||
if( m_Pcb != NULL && m_Pcb->ComputeBoundingBox() )
|
if( m_Pcb == NULL )
|
||||||
{
|
return 32.0;
|
||||||
|
|
||||||
|
m_Pcb->ComputeBoundingBox();
|
||||||
|
|
||||||
dx = m_Pcb->m_BoundaryBox.GetWidth();
|
dx = m_Pcb->m_BoundaryBox.GetWidth();
|
||||||
dy = m_Pcb->m_BoundaryBox.GetHeight();
|
dy = m_Pcb->m_BoundaryBox.GetHeight();
|
||||||
center = m_Pcb->m_BoundaryBox.Centre();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if( m_Draw_Sheet_Ref )
|
|
||||||
{
|
|
||||||
dx = GetScreen()->ReturnPageSize().x;
|
|
||||||
dy = GetScreen()->ReturnPageSize().y;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
dx = GetScreen()->ReturnPageSize().x;
|
|
||||||
dy = GetScreen()->ReturnPageSize().y;
|
|
||||||
}
|
|
||||||
|
|
||||||
center = wxPoint( dx / 2, dy / 2 );
|
|
||||||
}
|
|
||||||
|
|
||||||
size = DrawPanel->GetClientSize();
|
size = DrawPanel->GetClientSize();
|
||||||
|
|
||||||
if( size.x )
|
if( size.x )
|
||||||
zx = (double) dx / (double) size.x;
|
ii = (double)(dx + ( size.x / 2) ) / (double) size.x;
|
||||||
else
|
else
|
||||||
zx = 32.0;
|
ii = 32.0;
|
||||||
|
|
||||||
if ( size.y )
|
if ( size.y )
|
||||||
zy = (double) dy / (double) size.y;
|
jj = (double)( dy + (size.y / 2) ) / (double) size.y;
|
||||||
else
|
else
|
||||||
zy = 32.0;
|
jj = 32.0;
|
||||||
|
|
||||||
double bestzoom = MAX( zx, zy );
|
double bestzoom = MAX( ii, jj );
|
||||||
GetScreen()->SetScrollCenterPosition( center );
|
GetScreen()->SetScrollCenterPosition( m_Pcb->m_BoundaryBox.Centre() );
|
||||||
|
|
||||||
return bestzoom;
|
return bestzoom ;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -19,67 +19,26 @@ wxPoint BOARD_ITEM::ZeroOffset( 0, 0 );
|
||||||
BOARD_DESIGN_SETTINGS boardDesignSettings;
|
BOARD_DESIGN_SETTINGS boardDesignSettings;
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function SortPadsByXCoord
|
|
||||||
* is used to sort a pad list by x coordinate value.
|
|
||||||
*/
|
|
||||||
static int SortPadsByXCoord( const void* aRef, const void* aComp )
|
|
||||||
{
|
|
||||||
D_PAD* ref = *(LISTE_PAD*) aRef;
|
|
||||||
D_PAD* comp = *(LISTE_PAD*) aComp;
|
|
||||||
|
|
||||||
return ref->m_Pos.x - comp->m_Pos.x;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
TRACK* GetTraceByEndPoint( TRACK* aStartTrace, TRACK* aEndTrace,
|
|
||||||
const wxPoint& aPosition, int aLayerMask )
|
|
||||||
{
|
|
||||||
if( aStartTrace == NULL )
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
for( TRACK* trace = aStartTrace; trace != NULL; trace = trace->Next() )
|
|
||||||
{
|
|
||||||
if( trace->GetState( IS_DELETED | BUSY ) == 0 )
|
|
||||||
{
|
|
||||||
if( aPosition == trace->m_Start )
|
|
||||||
{
|
|
||||||
if( aLayerMask & trace->ReturnMaskLayer() )
|
|
||||||
return trace;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( aPosition == trace->m_End )
|
|
||||||
{
|
|
||||||
if( aLayerMask & trace->ReturnMaskLayer() )
|
|
||||||
return trace;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( trace == aEndTrace )
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*****************/
|
/*****************/
|
||||||
/* Class BOARD: */
|
/* Class BOARD: */
|
||||||
/*****************/
|
/*****************/
|
||||||
|
|
||||||
BOARD::BOARD( EDA_ITEM* aParent ) :
|
BOARD::BOARD( EDA_ITEM* parent, PCB_BASE_FRAME* frame ) :
|
||||||
BOARD_ITEM( (BOARD_ITEM*) aParent, TYPE_PCB ),
|
BOARD_ITEM( (BOARD_ITEM*)parent, TYPE_PCB ),
|
||||||
m_NetClasses( this )
|
m_NetClasses( this )
|
||||||
{
|
{
|
||||||
|
m_PcbFrame = frame;
|
||||||
m_Status_Pcb = 0; // Status word: bit 1 = calculate.
|
m_Status_Pcb = 0; // Status word: bit 1 = calculate.
|
||||||
SetBoardDesignSettings( &boardDesignSettings );
|
SetBoardDesignSettings(&boardDesignSettings);
|
||||||
SetColorsSettings( &g_ColorsSettings );
|
SetColorsSettings(&g_ColorsSettings);
|
||||||
m_NbNodes = 0; // Number of connected pads.
|
m_NbNodes = 0; // Number of connected pads.
|
||||||
m_NbNoconnect = 0; // Number of unconnected nets.
|
m_NbNoconnect = 0; // Number of unconnected nets.
|
||||||
|
|
||||||
m_CurrentZoneContour = NULL; // This ZONE_CONTAINER handle the
|
m_CurrentZoneContour = NULL; // This ZONE_CONTAINER handle the
|
||||||
// zone contour currently in progress
|
// zone contour currently in
|
||||||
m_NetInfo = new NETINFO_LIST( this ); // handle nets info list (name, design constraints ..
|
// progress
|
||||||
|
m_NetInfo = new NETINFO_LIST( this ); // handle nets info list (name,
|
||||||
|
// design constraints ..
|
||||||
m_NetInfo->BuildListOfNets(); // prepare pads and nets lists containers.
|
m_NetInfo->BuildListOfNets(); // prepare pads and nets lists containers.
|
||||||
|
|
||||||
for( int layer = 0; layer < NB_COPPER_LAYERS; ++layer )
|
for( int layer = 0; layer < NB_COPPER_LAYERS; ++layer )
|
||||||
|
@ -88,10 +47,12 @@ BOARD::BOARD( EDA_ITEM* aParent ) :
|
||||||
m_Layer[layer].m_Type = LT_SIGNAL;
|
m_Layer[layer].m_Type = LT_SIGNAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Initial parameters for the default NETCLASS come from the global preferences
|
// Initial parameters for the default NETCLASS come from the global
|
||||||
// within g_DesignSettings via the NETCLASS() constructor. Should the user
|
// preferences
|
||||||
// eventually load a board from a disk file, then these defaults will get
|
// within g_DesignSettings via the NETCLASS() constructor.
|
||||||
// overwritten during load.
|
// Should user eventually load a board from a disk file, then these
|
||||||
|
// defaults
|
||||||
|
// will get overwritten during load.
|
||||||
m_NetClasses.GetDefault()->SetDescription( _( "This is the default net class." ) );
|
m_NetClasses.GetDefault()->SetDescription( _( "This is the default net class." ) );
|
||||||
m_ViaSizeSelector = 0;
|
m_ViaSizeSelector = 0;
|
||||||
m_TrackWidthSelector = 0;
|
m_TrackWidthSelector = 0;
|
||||||
|
@ -103,6 +64,9 @@ BOARD::BOARD( EDA_ITEM* aParent ) :
|
||||||
|
|
||||||
BOARD::~BOARD()
|
BOARD::~BOARD()
|
||||||
{
|
{
|
||||||
|
if( m_PcbFrame->GetScreen() )
|
||||||
|
m_PcbFrame->GetScreen()->ClearUndoRedoList();
|
||||||
|
|
||||||
while( m_ZoneDescriptorList.size() )
|
while( m_ZoneDescriptorList.size() )
|
||||||
{
|
{
|
||||||
ZONE_CONTAINER* area_to_remove = m_ZoneDescriptorList[0];
|
ZONE_CONTAINER* area_to_remove = m_ZoneDescriptorList[0];
|
||||||
|
@ -123,124 +87,20 @@ BOARD::~BOARD()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void BOARD::chainMarkedSegments( wxPoint& aPosition, int aLayerMask, TRACK_PTRS* aList )
|
/*
|
||||||
{
|
* Function PushHightLight
|
||||||
TRACK* pt_segm; // The current segment being analyzed.
|
* save current hight light info for later use
|
||||||
TRACK* pt_via; // The via identified, eventually destroy
|
|
||||||
TRACK* SegmentCandidate; // The end segment to destroy (or NULL = pt_segm
|
|
||||||
int NbSegm;
|
|
||||||
|
|
||||||
if( m_Track == NULL )
|
|
||||||
return;
|
|
||||||
|
|
||||||
/* Set the BUSY flag of all connected segments, first search starting at
|
|
||||||
* aPosition
|
|
||||||
* Search ends when:
|
|
||||||
* - a pad is found (end of a track)
|
|
||||||
* - a segment end has more than one other segment end connected
|
|
||||||
* - and obviously when no connected item found
|
|
||||||
* Vias are a special case, because we must see others segment connected
|
|
||||||
* on others layers and they change the layer mask. They can be a track
|
|
||||||
* end or not
|
|
||||||
* They will be analyzer later, and vias on terminal points of the track
|
|
||||||
* will be considered as part of this track if they do not connect segments
|
|
||||||
* of an other track together and will be considered as part of an other
|
|
||||||
* track if when removing the via, the segments of that other track are
|
|
||||||
* disconnected
|
|
||||||
*/
|
*/
|
||||||
for( ; ; )
|
|
||||||
{
|
|
||||||
if( GetPadFast( aPosition, aLayerMask ) != NULL )
|
|
||||||
return;
|
|
||||||
|
|
||||||
/* Test for a via: a via changes the layer mask and can connect a lot
|
|
||||||
* of segments at location aPosition. When found, the via is just
|
|
||||||
* pushed in list. Vias will be examined later, when all connected
|
|
||||||
* segment are found and push in list. This is because when a via
|
|
||||||
* is found we do not know at this time the number of connected items
|
|
||||||
* and we do not know if this via is on the track or finish the track
|
|
||||||
*/
|
|
||||||
pt_via = m_Track->GetVia( NULL, aPosition, aLayerMask );
|
|
||||||
|
|
||||||
if( pt_via )
|
|
||||||
{
|
|
||||||
aLayerMask = pt_via->ReturnMaskLayer();
|
|
||||||
aList->push_back( pt_via );
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Now we search all segments connected to point aPosition
|
|
||||||
* if only 1 segment: this segment is candidate
|
|
||||||
* if > 1 segment:
|
|
||||||
* end of track (more than 2 segment connected at this location)
|
|
||||||
*/
|
|
||||||
pt_segm = m_Track;
|
|
||||||
SegmentCandidate = NULL;
|
|
||||||
NbSegm = 0;
|
|
||||||
|
|
||||||
while( ( pt_segm = GetTraceByEndPoint( pt_segm, NULL, aPosition, aLayerMask ) ) != NULL )
|
|
||||||
{
|
|
||||||
if( pt_segm->GetState( BUSY ) ) // already found and selected: skip it
|
|
||||||
{
|
|
||||||
pt_segm = pt_segm->Next();
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( pt_segm == pt_via ) // just previously found: skip it
|
|
||||||
{
|
|
||||||
pt_segm = pt_segm->Next();
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
NbSegm++;
|
|
||||||
|
|
||||||
if( NbSegm == 1 ) /* First time we found a connected item: pt_segm is candidate */
|
|
||||||
{
|
|
||||||
SegmentCandidate = pt_segm;
|
|
||||||
pt_segm = pt_segm->Next();
|
|
||||||
}
|
|
||||||
else /* More than 1 segment connected -> this location is an end of the track */
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( SegmentCandidate ) // A candidate is found: flag it an push it in list
|
|
||||||
{
|
|
||||||
/* Initialize parameters to search items connected to this
|
|
||||||
* candidate:
|
|
||||||
* we must analyze connections to its other end
|
|
||||||
*/
|
|
||||||
aLayerMask = SegmentCandidate->ReturnMaskLayer();
|
|
||||||
|
|
||||||
if( aPosition == SegmentCandidate->m_Start )
|
|
||||||
{
|
|
||||||
aPosition = SegmentCandidate->m_End;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
aPosition = SegmentCandidate->m_Start;
|
|
||||||
}
|
|
||||||
|
|
||||||
pt_segm = m_Track; /* restart list of tracks to analyze */
|
|
||||||
|
|
||||||
/* flag this item an push it in list of selected items */
|
|
||||||
aList->push_back( SegmentCandidate );
|
|
||||||
SegmentCandidate->SetState( BUSY, ON );
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void BOARD::PushHightLight()
|
void BOARD::PushHightLight()
|
||||||
{
|
{
|
||||||
m_hightLightPrevious = m_hightLight;
|
m_hightLightPrevious = m_hightLight;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Function PopHightLight
|
||||||
|
* retrieve a previously saved hight light info
|
||||||
|
*/
|
||||||
void BOARD::PopHightLight()
|
void BOARD::PopHightLight()
|
||||||
{
|
{
|
||||||
m_hightLight = m_hightLightPrevious;
|
m_hightLight = m_hightLightPrevious;
|
||||||
|
@ -248,6 +108,15 @@ void BOARD::PopHightLight()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function SetCurrentNetClass
|
||||||
|
* Must be called after a netclass selection (or after a netclass parameter
|
||||||
|
* change
|
||||||
|
* Initialize vias and tracks values displayed in combo boxes of the auxiliary
|
||||||
|
* toolbar and some other parameters (netclass name ....)
|
||||||
|
* @param aNetClassName = the new netclass name
|
||||||
|
* @return true if lists of tracks and vias sizes are modified
|
||||||
|
*/
|
||||||
bool BOARD::SetCurrentNetClass( const wxString& aNetClassName )
|
bool BOARD::SetCurrentNetClass( const wxString& aNetClassName )
|
||||||
{
|
{
|
||||||
NETCLASS* netClass = m_NetClasses.Find( aNetClassName );
|
NETCLASS* netClass = m_NetClasses.Find( aNetClassName );
|
||||||
|
@ -296,6 +165,10 @@ bool BOARD::SetCurrentNetClass( const wxString& aNetClassName )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function GetBiggestClearanceValue
|
||||||
|
* @return the biggest clearance value found in NetClasses list
|
||||||
|
*/
|
||||||
int BOARD::GetBiggestClearanceValue()
|
int BOARD::GetBiggestClearanceValue()
|
||||||
{
|
{
|
||||||
int clearance = m_NetClasses.GetDefault()->GetClearance();
|
int clearance = m_NetClasses.GetDefault()->GetClearance();
|
||||||
|
@ -311,6 +184,11 @@ int BOARD::GetBiggestClearanceValue()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function GetCurrentMicroViaSize
|
||||||
|
* @return the current micro via size,
|
||||||
|
* that is the current netclass value
|
||||||
|
*/
|
||||||
int BOARD::GetCurrentMicroViaSize()
|
int BOARD::GetCurrentMicroViaSize()
|
||||||
{
|
{
|
||||||
NETCLASS* netclass = m_NetClasses.Find( m_CurrentNetClassName );
|
NETCLASS* netclass = m_NetClasses.Find( m_CurrentNetClassName );
|
||||||
|
@ -319,6 +197,11 @@ int BOARD::GetCurrentMicroViaSize()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function GetCurrentMicroViaDrill
|
||||||
|
* @return the current micro via drill,
|
||||||
|
* that is the current netclass value
|
||||||
|
*/
|
||||||
int BOARD::GetCurrentMicroViaDrill()
|
int BOARD::GetCurrentMicroViaDrill()
|
||||||
{
|
{
|
||||||
NETCLASS* netclass = m_NetClasses.Find( m_CurrentNetClassName );
|
NETCLASS* netclass = m_NetClasses.Find( m_CurrentNetClassName );
|
||||||
|
@ -497,13 +380,11 @@ LAYER_T LAYER::ParseType( const char* aType )
|
||||||
return LAYER_T( -1 );
|
return LAYER_T( -1 );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int BOARD::GetCopperLayerCount() const
|
int BOARD::GetCopperLayerCount() const
|
||||||
{
|
{
|
||||||
return GetBoardDesignSettings()->GetCopperLayerCount();
|
return GetBoardDesignSettings()->GetCopperLayerCount();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void BOARD::SetCopperLayerCount( int aCount )
|
void BOARD::SetCopperLayerCount( int aCount )
|
||||||
{
|
{
|
||||||
GetBoardDesignSettings()->SetCopperLayerCount( aCount );
|
GetBoardDesignSettings()->SetCopperLayerCount( aCount );
|
||||||
|
@ -667,6 +548,13 @@ int BOARD::GetLayerColor( int aLayer )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function IsModuleLayerVisible
|
||||||
|
* expects either of the two layers on which a module can reside, and returns
|
||||||
|
* whether that layer is visible.
|
||||||
|
* @param layer One of the two allowed layers for modules: LAYER_N_FRONT or LAYER_N_BACK
|
||||||
|
* @return bool - true if the layer is visible, else false.
|
||||||
|
*/
|
||||||
bool BOARD::IsModuleLayerVisible( int layer )
|
bool BOARD::IsModuleLayerVisible( int layer )
|
||||||
{
|
{
|
||||||
if( layer==LAYER_N_FRONT )
|
if( layer==LAYER_N_FRONT )
|
||||||
|
@ -946,6 +834,23 @@ bool BOARD::ComputeBoundingBox( bool aBoardEdgesOnly )
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if( !hasItems && m_PcbFrame )
|
||||||
|
{
|
||||||
|
if( m_PcbFrame->m_Draw_Sheet_Ref )
|
||||||
|
{
|
||||||
|
area.SetOrigin( 0, 0 );
|
||||||
|
area.SetEnd( m_PcbFrame->GetScreen()->ReturnPageSize().x,
|
||||||
|
m_PcbFrame->GetScreen()->ReturnPageSize().y );
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
area.SetOrigin( -m_PcbFrame->GetScreen()->ReturnPageSize().x / 2,
|
||||||
|
-m_PcbFrame->GetScreen()->ReturnPageSize().y / 2 );
|
||||||
|
area.SetEnd( m_PcbFrame->GetScreen()->ReturnPageSize().x / 2,
|
||||||
|
m_PcbFrame->GetScreen()->ReturnPageSize().y / 2 );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
m_BoundaryBox = area;
|
m_BoundaryBox = area;
|
||||||
|
|
||||||
return hasItems;
|
return hasItems;
|
||||||
|
@ -953,6 +858,9 @@ bool BOARD::ComputeBoundingBox( bool aBoardEdgesOnly )
|
||||||
|
|
||||||
|
|
||||||
// virtual, see pcbstruct.h
|
// virtual, see pcbstruct.h
|
||||||
|
|
||||||
|
/* Display board statistics: pads, nets, connections.. count
|
||||||
|
*/
|
||||||
void BOARD::DisplayInfo( EDA_DRAW_FRAME* frame )
|
void BOARD::DisplayInfo( EDA_DRAW_FRAME* frame )
|
||||||
{
|
{
|
||||||
wxString txt;
|
wxString txt;
|
||||||
|
@ -1266,6 +1174,12 @@ SEARCH_RESULT BOARD::Visit( INSPECTOR* inspector, const void* testData,
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function FindNet
|
||||||
|
* searches for a net with the given netcode.
|
||||||
|
* @param aNetcode The netcode to search for.
|
||||||
|
* @return NETINFO_ITEM* - the net or NULL if not found.
|
||||||
|
*/
|
||||||
NETINFO_ITEM* BOARD::FindNet( int aNetcode ) const
|
NETINFO_ITEM* BOARD::FindNet( int aNetcode ) const
|
||||||
{
|
{
|
||||||
// the first valid netcode is 1 and the last is m_NetInfo->GetCount()-1.
|
// the first valid netcode is 1 and the last is m_NetInfo->GetCount()-1.
|
||||||
|
@ -1288,6 +1202,12 @@ NETINFO_ITEM* BOARD::FindNet( int aNetcode ) const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function FindNet overlaid
|
||||||
|
* searches for a net with the given name.
|
||||||
|
* @param aNetname A Netname to search for.
|
||||||
|
* @return NETINFO_ITEM* - the net or NULL if not found.
|
||||||
|
*/
|
||||||
NETINFO_ITEM* BOARD::FindNet( const wxString& aNetname ) const
|
NETINFO_ITEM* BOARD::FindNet( const wxString& aNetname ) const
|
||||||
{
|
{
|
||||||
// the first valid netcode is 1.
|
// the first valid netcode is 1.
|
||||||
|
@ -1366,125 +1286,6 @@ NETINFO_ITEM* BOARD::FindNet( const wxString& aNetname ) const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
TRACK* BOARD::CreateLockPoint( wxPoint& aPosition, TRACK* aSegment,
|
|
||||||
PICKED_ITEMS_LIST* aItemsListPicker )
|
|
||||||
{
|
|
||||||
if( aSegment->m_Start == aPosition || aSegment->m_End == aPosition )
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
/* A via is a good lock point */
|
|
||||||
if( aSegment->Type() == TYPE_VIA )
|
|
||||||
{
|
|
||||||
aPosition = aSegment->m_Start;
|
|
||||||
return aSegment;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Calculation coordinate of intermediate point relative to
|
|
||||||
* the start point of aSegment
|
|
||||||
*/
|
|
||||||
wxPoint delta = aSegment->m_End - aSegment->m_Start;
|
|
||||||
|
|
||||||
// Not yet in use:
|
|
||||||
#if 0
|
|
||||||
int ox, oy, fx, fy;
|
|
||||||
|
|
||||||
if( aRefSegm )
|
|
||||||
{
|
|
||||||
ox = aRefSegm->m_Start.x - aSegment->m_Start.x;
|
|
||||||
oy = aRefSegm->m_Start.y - aSegment->m_Start.y;
|
|
||||||
fx = aRefSegm->m_End.x - aSegment->m_Start.x;
|
|
||||||
fy = aRefSegm->m_End.y - aSegment->m_Start.y;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// calculate coordinates of aPosition relative to aSegment->m_Start
|
|
||||||
wxPoint newPoint = aPosition - aSegment->m_Start;
|
|
||||||
|
|
||||||
// newPoint must be on aSegment:
|
|
||||||
// Ensure newPoint.y/newPoint.y = delta.y/delta.x
|
|
||||||
if( delta.x == 0 )
|
|
||||||
newPoint.x = 0; /* horizontal segment*/
|
|
||||||
else
|
|
||||||
newPoint.y = wxRound(( (double)newPoint.x * delta.y ) / delta.x);
|
|
||||||
|
|
||||||
/* Create the intermediate point (that is to say creation of a new
|
|
||||||
* segment, beginning at the intermediate point.
|
|
||||||
*/
|
|
||||||
newPoint.x += aSegment->m_Start.x;
|
|
||||||
newPoint.y += aSegment->m_Start.y;
|
|
||||||
|
|
||||||
TRACK* newTrack = aSegment->Copy();
|
|
||||||
|
|
||||||
if( aItemsListPicker )
|
|
||||||
{
|
|
||||||
ITEM_PICKER picker( newTrack, UR_NEW );
|
|
||||||
aItemsListPicker->PushItem( picker );
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
DLIST<TRACK>* list = (DLIST<TRACK>*)aSegment->GetList();
|
|
||||||
wxASSERT( list );
|
|
||||||
list->Insert( newTrack, aSegment->Next() );
|
|
||||||
|
|
||||||
if( aItemsListPicker )
|
|
||||||
{
|
|
||||||
ITEM_PICKER picker( aSegment, UR_CHANGED );
|
|
||||||
picker.m_Link = aSegment->Copy();
|
|
||||||
aItemsListPicker->PushItem( picker );
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Correct pointer at the end of the new segment. */
|
|
||||||
newTrack->end = aSegment->end;
|
|
||||||
newTrack->SetState( END_ONPAD, aSegment->GetState( END_ONPAD ) );
|
|
||||||
|
|
||||||
/* Set connections info relative to the new point
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Old segment now ends at new point. */
|
|
||||||
aSegment->m_End = newPoint;
|
|
||||||
aSegment->end = newTrack;
|
|
||||||
aSegment->SetState( END_ONPAD, OFF );
|
|
||||||
|
|
||||||
/* The new segment begins at the new point. */
|
|
||||||
newTrack->m_Start = newPoint;
|
|
||||||
newTrack->start = aSegment;
|
|
||||||
newTrack->SetState( BEGIN_ONPAD, OFF );
|
|
||||||
|
|
||||||
D_PAD * pad = GetPad( newTrack, START );
|
|
||||||
|
|
||||||
if ( pad )
|
|
||||||
{
|
|
||||||
newTrack->start = pad;
|
|
||||||
newTrack->SetState( BEGIN_ONPAD, ON );
|
|
||||||
aSegment->end = pad;
|
|
||||||
aSegment->SetState( END_ONPAD, ON );
|
|
||||||
}
|
|
||||||
|
|
||||||
aPosition = newPoint;
|
|
||||||
return newTrack;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
BOARD_ITEM* BOARD::GetLockPoint( const wxPoint& aPosition, int aLayerMask )
|
|
||||||
{
|
|
||||||
for( MODULE* module = m_Modules; module; module = module->Next() )
|
|
||||||
{
|
|
||||||
D_PAD* pad = module->GetPad( aPosition, aLayerMask );
|
|
||||||
|
|
||||||
if( pad )
|
|
||||||
return pad;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* No pad has been located so check for a segment of the trace. */
|
|
||||||
TRACK* trace = GetTraceByEndPoint( m_Track, NULL, aPosition, aLayerMask );
|
|
||||||
|
|
||||||
if( trace == NULL )
|
|
||||||
trace = GetTrace( aPosition, aLayerMask );
|
|
||||||
|
|
||||||
return trace;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
MODULE* BOARD::FindModuleByReference( const wxString& aReference ) const
|
MODULE* BOARD::FindModuleByReference( const wxString& aReference ) const
|
||||||
{
|
{
|
||||||
struct FindModule : public INSPECTOR
|
struct FindModule : public INSPECTOR
|
||||||
|
@ -1519,185 +1320,20 @@ MODULE* BOARD::FindModuleByReference( const wxString& aReference ) const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
MODULE* BOARD::GetModule( const wxPoint& aPosition, int aActiveLayer,
|
// Sort nets by decreasing pad count
|
||||||
bool aVisibleOnly, bool aIgnoreLocked )
|
|
||||||
{
|
|
||||||
MODULE* pt_module;
|
|
||||||
MODULE* module = NULL;
|
|
||||||
MODULE* Altmodule = NULL;
|
|
||||||
int min_dim = 0x7FFFFFFF;
|
|
||||||
int alt_min_dim = 0x7FFFFFFF;
|
|
||||||
int layer;
|
|
||||||
|
|
||||||
pt_module = m_Modules;
|
|
||||||
|
|
||||||
for( ; pt_module; pt_module = (MODULE*) pt_module->Next() )
|
|
||||||
{
|
|
||||||
// is the ref point within the module's bounds?
|
|
||||||
if( !pt_module->HitTest( aPosition ) )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
// if caller wants to ignore locked modules, and this one is locked, skip it.
|
|
||||||
if( aIgnoreLocked && pt_module->IsLocked() )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
/* Calculate priority: the priority is given to the layer of the
|
|
||||||
* module and the copper layer if the module layer is indelible,
|
|
||||||
* adhesive copper, a layer if cmp module layer is indelible,
|
|
||||||
* adhesive component.
|
|
||||||
*/
|
|
||||||
layer = pt_module->GetLayer();
|
|
||||||
|
|
||||||
if( layer==ADHESIVE_N_BACK || layer==SILKSCREEN_N_BACK )
|
|
||||||
layer = LAYER_N_BACK;
|
|
||||||
else if( layer==ADHESIVE_N_FRONT || layer==SILKSCREEN_N_FRONT )
|
|
||||||
layer = LAYER_N_FRONT;
|
|
||||||
|
|
||||||
/* Test of minimum size to choosing the best candidate. */
|
|
||||||
|
|
||||||
EDA_RECT bb = pt_module->GetFootPrintRect();
|
|
||||||
int offx = bb.GetX() + bb.GetWidth() / 2;
|
|
||||||
int offy = bb.GetY() + bb.GetHeight() / 2;
|
|
||||||
|
|
||||||
//off x & offy point to the middle of the box.
|
|
||||||
int dist = abs( aPosition.x - offx ) + abs( aPosition.y - offy );
|
|
||||||
|
|
||||||
//int dist = MIN(lx, ly); // to pick the smallest module (kinda
|
|
||||||
// screwy with same-sized modules -- this is bad!)
|
|
||||||
|
|
||||||
if( aActiveLayer == layer )
|
|
||||||
{
|
|
||||||
if( dist <= min_dim )
|
|
||||||
{
|
|
||||||
/* better footprint shown on the active layer */
|
|
||||||
module = pt_module;
|
|
||||||
min_dim = dist;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if( aVisibleOnly && IsModuleLayerVisible( layer ) )
|
|
||||||
{
|
|
||||||
if( dist <= alt_min_dim )
|
|
||||||
{
|
|
||||||
/* better footprint shown on other layers */
|
|
||||||
Altmodule = pt_module;
|
|
||||||
alt_min_dim = dist;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( module )
|
|
||||||
{
|
|
||||||
return module;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( Altmodule )
|
|
||||||
{
|
|
||||||
return Altmodule;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
TRACK* BOARD::GetTrace( const wxPoint& aPosition, int aLayer )
|
|
||||||
{
|
|
||||||
return m_Track->GetTrace( aPosition, aLayer );
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
TRACK* BOARD::GetVia( const wxPoint& aPosition, int aLayer )
|
|
||||||
{
|
|
||||||
TRACK* track;
|
|
||||||
|
|
||||||
for( track = m_Track; track; track = track->Next() )
|
|
||||||
{
|
|
||||||
if( track->Type() != TYPE_VIA
|
|
||||||
|| track->m_Start != aPosition
|
|
||||||
|| track->GetState( BUSY | IS_DELETED ) )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if( aLayer < 0 || track->IsOnLayer( aLayer ) )
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
return track;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
D_PAD* BOARD::GetPad( TRACK* aTrace, int aEnd )
|
|
||||||
{
|
|
||||||
D_PAD* pad = NULL;
|
|
||||||
wxPoint pos;
|
|
||||||
|
|
||||||
int aLayerMask = g_TabOneLayerMask[ aTrace->GetLayer() ];
|
|
||||||
|
|
||||||
if( aEnd == START )
|
|
||||||
{
|
|
||||||
pos = aTrace->m_Start;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
pos = aTrace->m_End;
|
|
||||||
}
|
|
||||||
|
|
||||||
for( MODULE* module = m_Modules; module; module = module->Next() )
|
|
||||||
{
|
|
||||||
pad = module->GetPad( pos, aLayerMask );
|
|
||||||
|
|
||||||
if( pad != NULL )
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
return pad;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
D_PAD* BOARD::GetPad( const wxPoint& aPosition, int aLayerMask )
|
|
||||||
{
|
|
||||||
D_PAD* pad = NULL;
|
|
||||||
|
|
||||||
for( MODULE* module = m_Modules; module && ( pad == NULL ); module = module->Next() )
|
|
||||||
{
|
|
||||||
pad = module->GetPad( aPosition, aLayerMask );
|
|
||||||
}
|
|
||||||
|
|
||||||
return pad;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
D_PAD* BOARD::GetPadFast( const wxPoint& aPosition, int aLayerMask )
|
|
||||||
{
|
|
||||||
for( unsigned i=0; i<GetPadsCount(); ++i )
|
|
||||||
{
|
|
||||||
D_PAD* pad = m_NetInfo->GetPad(i);
|
|
||||||
|
|
||||||
if( pad->m_Pos != aPosition )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
/* Pad found, it must be on the correct layer */
|
|
||||||
if( pad->m_layerMask & aLayerMask )
|
|
||||||
return pad;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void BOARD::CreateSortedPadListByXCoord( std::vector<D_PAD*>* aVector )
|
|
||||||
{
|
|
||||||
aVector->insert( aVector->end(), m_NetInfo->m_PadsFullList.begin(),
|
|
||||||
m_NetInfo->m_PadsFullList.end() );
|
|
||||||
|
|
||||||
qsort( &(*aVector)[0], GetPadsCount(), sizeof( D_PAD*), SortPadsByXCoord );
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static bool s_SortByNodes( const NETINFO_ITEM* a, const NETINFO_ITEM* b )
|
static bool s_SortByNodes( const NETINFO_ITEM* a, const NETINFO_ITEM* b )
|
||||||
{
|
{
|
||||||
return b->GetNodesCount() < a->GetNodesCount();
|
return b->GetNodesCount() < a->GetNodesCount();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function ReturnSortedNetnamesList
|
||||||
|
* @param aNames An array string to fill with net names.
|
||||||
|
* @param aSortbyPadsCount : true = sort by active pads count, false = no sort
|
||||||
|
* (i.e. leave the sort by net names)
|
||||||
|
* @return int - net names count.
|
||||||
|
*/
|
||||||
int BOARD::ReturnSortedNetnamesList( wxArrayString& aNames, bool aSortbyPadsCount )
|
int BOARD::ReturnSortedNetnamesList( wxArrayString& aNames, bool aSortbyPadsCount )
|
||||||
{
|
{
|
||||||
if( m_NetInfo->GetCount() == 0 )
|
if( m_NetInfo->GetCount() == 0 )
|
||||||
|
@ -1803,6 +1439,10 @@ out:
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Function RedrawAreasOutlines
|
||||||
|
* Redraw all areas outlines on layer aLayer ( redraw all if aLayer < 0 )
|
||||||
|
*/
|
||||||
void BOARD::RedrawAreasOutlines( EDA_DRAW_PANEL* panel, wxDC* aDC, int aDrawMode, int aLayer )
|
void BOARD::RedrawAreasOutlines( EDA_DRAW_PANEL* panel, wxDC* aDC, int aDrawMode, int aLayer )
|
||||||
{
|
{
|
||||||
if( !aDC )
|
if( !aDC )
|
||||||
|
@ -1818,6 +1458,10 @@ void BOARD::RedrawAreasOutlines( EDA_DRAW_PANEL* panel, wxDC* aDC, int aDrawMode
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function RedrawFilledAreas
|
||||||
|
* Redraw all areas outlines on layer aLayer ( redraw all if aLayer < 0 )
|
||||||
|
*/
|
||||||
void BOARD::RedrawFilledAreas( EDA_DRAW_PANEL* panel, wxDC* aDC, int aDrawMode, int aLayer )
|
void BOARD::RedrawFilledAreas( EDA_DRAW_PANEL* panel, wxDC* aDC, int aDrawMode, int aLayer )
|
||||||
{
|
{
|
||||||
if( !aDC )
|
if( !aDC )
|
||||||
|
@ -1833,6 +1477,18 @@ void BOARD::RedrawFilledAreas( EDA_DRAW_PANEL* panel, wxDC* aDC, int aDrawMode,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function HitTestForAnyFilledArea
|
||||||
|
* tests if the given wxPoint is within the bounds of a filled area of this
|
||||||
|
* zone.
|
||||||
|
* the test is made on zones on layer from aStartLayer to aEndLayer
|
||||||
|
* Note: if a zone has its flag BUSY (in .m_State) is set, it is ignored.
|
||||||
|
* @param aRefPos A wxPoint to test
|
||||||
|
* @param aStartLayer the first layer to test
|
||||||
|
* @param aEndLayer the last layer (-1 to ignore it) to test
|
||||||
|
* @return ZONE_CONTAINER* return a pointer to the ZONE_CONTAINER found, else
|
||||||
|
* NULL
|
||||||
|
*/
|
||||||
ZONE_CONTAINER* BOARD::HitTestForAnyFilledArea( const wxPoint& aRefPos,
|
ZONE_CONTAINER* BOARD::HitTestForAnyFilledArea( const wxPoint& aRefPos,
|
||||||
int aStartLayer,
|
int aStartLayer,
|
||||||
int aEndLayer )
|
int aEndLayer )
|
||||||
|
@ -1863,6 +1519,19 @@ ZONE_CONTAINER* BOARD::HitTestForAnyFilledArea( const wxPoint& aRefPos,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function SetAreasNetCodesFromNetNames
|
||||||
|
* Set the .m_NetCode member of all copper areas, according to the area Net
|
||||||
|
* Name
|
||||||
|
* The SetNetCodesFromNetNames is an equivalent to net name, for fast
|
||||||
|
* comparisons.
|
||||||
|
* However the Netcode is an arbitrary equivalence, it must be set after each
|
||||||
|
* netlist read
|
||||||
|
* or net change
|
||||||
|
* Must be called after pad netcodes are calculated
|
||||||
|
* @return : error count
|
||||||
|
* For non copper areas, netcode is set to 0
|
||||||
|
*/
|
||||||
int BOARD::SetAreasNetCodesFromNetNames( void )
|
int BOARD::SetAreasNetCodesFromNetNames( void )
|
||||||
{
|
{
|
||||||
int error_count = 0;
|
int error_count = 0;
|
||||||
|
@ -1896,248 +1565,15 @@ int BOARD::SetAreasNetCodesFromNetNames( void )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
TRACK* BOARD::MarkTrace( TRACK* aTrace, int* aCount, int* aLength, int* aLengthDie, bool aReorder )
|
|
||||||
{
|
|
||||||
wxCHECK( aTrace != NULL, NULL );
|
|
||||||
|
|
||||||
int NbSegmBusy;
|
|
||||||
|
|
||||||
TRACK_PTRS trackList;
|
|
||||||
|
|
||||||
if( aCount )
|
|
||||||
*aCount = 0;
|
|
||||||
|
|
||||||
if( aLength )
|
|
||||||
*aLength = 0;
|
|
||||||
|
|
||||||
// Ensure the flag BUSY of all tracks of the board is cleared
|
|
||||||
// because we use it to mark segments of the track
|
|
||||||
for( TRACK* track = m_Track; track; track = track->Next() )
|
|
||||||
track->SetState( BUSY, OFF );
|
|
||||||
|
|
||||||
/* Set flags of the initial track segment */
|
|
||||||
aTrace->SetState( BUSY, ON );
|
|
||||||
int layerMask = aTrace->ReturnMaskLayer();
|
|
||||||
|
|
||||||
trackList.push_back( aTrace );
|
|
||||||
|
|
||||||
/* Examine the initial track segment : if it is really a segment, this is
|
|
||||||
* easy.
|
|
||||||
* If it is a via, one must search for connected segments.
|
|
||||||
* If <=2, this via connect 2 segments (or is connected to only one
|
|
||||||
* segment) and this via and these 2 segments are a part of a track.
|
|
||||||
* If > 2 only this via is flagged (the track has only this via)
|
|
||||||
*/
|
|
||||||
if( aTrace->Type() == TYPE_VIA )
|
|
||||||
{
|
|
||||||
TRACK* Segm1, * Segm2 = NULL, * Segm3 = NULL;
|
|
||||||
Segm1 = GetTraceByEndPoint( m_Track, NULL, aTrace->m_Start, layerMask );
|
|
||||||
|
|
||||||
if( Segm1 )
|
|
||||||
{
|
|
||||||
Segm2 = GetTraceByEndPoint( Segm1->Next(), NULL, aTrace->m_Start, layerMask );
|
|
||||||
}
|
|
||||||
|
|
||||||
if( Segm2 )
|
|
||||||
{
|
|
||||||
Segm3 = GetTraceByEndPoint( Segm2->Next(), NULL, aTrace->m_Start, layerMask );
|
|
||||||
}
|
|
||||||
|
|
||||||
if( Segm3 ) // More than 2 segments are connected to this via. the track" is only this via
|
|
||||||
{
|
|
||||||
if( aCount )
|
|
||||||
*aCount = 1;
|
|
||||||
|
|
||||||
return aTrace;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( Segm1 ) // search for others segments connected to the initial segment start point
|
|
||||||
{
|
|
||||||
layerMask = Segm1->ReturnMaskLayer();
|
|
||||||
chainMarkedSegments( aTrace->m_Start, layerMask, &trackList );
|
|
||||||
}
|
|
||||||
|
|
||||||
if( Segm2 ) // search for others segments connected to the initial segment end point
|
|
||||||
{
|
|
||||||
layerMask = Segm2->ReturnMaskLayer();
|
|
||||||
chainMarkedSegments( aTrace->m_Start, layerMask, &trackList );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else // mark the chain using both ends of the initial segment
|
|
||||||
{
|
|
||||||
chainMarkedSegments( aTrace->m_Start, layerMask, &trackList );
|
|
||||||
chainMarkedSegments( aTrace->m_End, layerMask, &trackList );
|
|
||||||
}
|
|
||||||
|
|
||||||
// Now examine selected vias and flag them if they are on the track
|
|
||||||
// If a via is connected to only one or 2 segments, it is flagged (is on
|
|
||||||
// the track)
|
|
||||||
// If a via is connected to more than 2 segments, it is a track end, and it
|
|
||||||
// is removed from the list
|
|
||||||
// go through the list backwards.
|
|
||||||
for( int i = trackList.size() - 1; i>=0; --i )
|
|
||||||
{
|
|
||||||
TRACK* via = trackList[i];
|
|
||||||
|
|
||||||
if( via->Type() != TYPE_VIA )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if( via == aTrace )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
via->SetState( BUSY, ON ); // Try to flag it. the flag will be cleared later if needed
|
|
||||||
|
|
||||||
layerMask = via->ReturnMaskLayer();
|
|
||||||
|
|
||||||
TRACK* track = GetTraceByEndPoint( m_Track, NULL, via->m_Start, layerMask );
|
|
||||||
|
|
||||||
// GetTrace does not consider tracks flagged BUSY.
|
|
||||||
// So if no connected track found, this via is on the current track
|
|
||||||
// only: keep it
|
|
||||||
if( track == NULL )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
/* If a track is found, this via connects also others segments of an
|
|
||||||
* other track. This case happens when the vias ends the selected
|
|
||||||
* track but must we consider this via is on the selected track, or
|
|
||||||
* on an other track.
|
|
||||||
* (this is important when selecting a track for deletion: must this
|
|
||||||
* via be deleted or not?)
|
|
||||||
* We consider here this via on the track if others segment connected
|
|
||||||
* to this via remain connected when removing this via.
|
|
||||||
* We search for all others segment connected together:
|
|
||||||
* if there are on the same layer, the via is on the selected track
|
|
||||||
* if there are on different layers, the via is on an other track
|
|
||||||
*/
|
|
||||||
int layer = track->GetLayer();
|
|
||||||
|
|
||||||
while( ( track = GetTraceByEndPoint( track->Next(), NULL,
|
|
||||||
via->m_Start, layerMask ) ) != NULL )
|
|
||||||
{
|
|
||||||
if( layer != track->GetLayer() )
|
|
||||||
{
|
|
||||||
// The via connects segments of an other track: it is removed
|
|
||||||
// from list because it is member of an other track
|
|
||||||
via->SetState( BUSY, OFF );
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Rearrange the track list in order to have flagged segments linked
|
|
||||||
* from firstTrack so the NbSegmBusy segments are consecutive segments
|
|
||||||
* in list, the first item in the full track list is firstTrack, and
|
|
||||||
* the NbSegmBusy-1 next items (NbSegmBusy when including firstTrack)
|
|
||||||
* are the flagged segments
|
|
||||||
*/
|
|
||||||
NbSegmBusy = 0;
|
|
||||||
TRACK* firstTrack;
|
|
||||||
|
|
||||||
for( firstTrack = m_Track; firstTrack; firstTrack = firstTrack->Next() )
|
|
||||||
{
|
|
||||||
// Search for the first flagged BUSY segments
|
|
||||||
if( firstTrack->GetState( BUSY ) )
|
|
||||||
{
|
|
||||||
NbSegmBusy = 1;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( firstTrack == NULL )
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
double full_len = 0;
|
|
||||||
double lenDie = 0;
|
|
||||||
|
|
||||||
if( aReorder )
|
|
||||||
{
|
|
||||||
DLIST<TRACK>* list = (DLIST<TRACK>*)firstTrack->GetList();
|
|
||||||
wxASSERT( list );
|
|
||||||
|
|
||||||
/* Rearrange the chain starting at firstTrack
|
|
||||||
* All others flagged items are moved from their position to the end
|
|
||||||
* of the flagged list
|
|
||||||
*/
|
|
||||||
TRACK* next;
|
|
||||||
|
|
||||||
for( TRACK* track = firstTrack->Next(); track; track = next )
|
|
||||||
{
|
|
||||||
next = track->Next();
|
|
||||||
|
|
||||||
if( track->GetState( BUSY ) ) // move it!
|
|
||||||
{
|
|
||||||
NbSegmBusy++;
|
|
||||||
track->UnLink();
|
|
||||||
list->Insert( track, firstTrack->Next() );
|
|
||||||
|
|
||||||
if( aLength )
|
|
||||||
full_len += track->GetLength();
|
|
||||||
|
|
||||||
if( aLengthDie ) // Add now length die.
|
|
||||||
{
|
|
||||||
// In fact only 2 pads (maximum) will be taken in account:
|
|
||||||
// that are on each end of the track, if any
|
|
||||||
if( track->GetState( BEGIN_ONPAD ) )
|
|
||||||
{
|
|
||||||
D_PAD * pad = (D_PAD *) track->start;
|
|
||||||
lenDie += (double) pad->m_LengthDie;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( track->GetState( END_ONPAD ) )
|
|
||||||
{
|
|
||||||
D_PAD * pad = (D_PAD *) track->end;
|
|
||||||
lenDie += (double) pad->m_LengthDie;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if( aLength )
|
|
||||||
{
|
|
||||||
NbSegmBusy = 0;
|
|
||||||
|
|
||||||
for( TRACK* track = firstTrack; track; track = track->Next() )
|
|
||||||
{
|
|
||||||
if( track->GetState( BUSY ) )
|
|
||||||
{
|
|
||||||
NbSegmBusy++;
|
|
||||||
track->SetState( BUSY, OFF );
|
|
||||||
full_len += track->GetLength();
|
|
||||||
|
|
||||||
// Add now length die.
|
|
||||||
// In fact only 2 pads (maximum) will be taken in account:
|
|
||||||
// that are on each end of the track, if any
|
|
||||||
if( track->GetState( BEGIN_ONPAD ) )
|
|
||||||
{
|
|
||||||
D_PAD * pad = (D_PAD *) track->start;
|
|
||||||
lenDie += (double) pad->m_LengthDie;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( track->GetState( END_ONPAD ) )
|
|
||||||
{
|
|
||||||
D_PAD * pad = (D_PAD *) track->end;
|
|
||||||
lenDie += (double) pad->m_LengthDie;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( aLength )
|
|
||||||
*aLength = wxRound( full_len );
|
|
||||||
|
|
||||||
if( aLengthDie )
|
|
||||||
*aLengthDie = wxRound( lenDie );
|
|
||||||
|
|
||||||
if( aCount )
|
|
||||||
*aCount = NbSegmBusy;
|
|
||||||
|
|
||||||
return firstTrack;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
#if defined(DEBUG)
|
#if defined(DEBUG)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function Show
|
||||||
|
* is used to output the object tree, currently for debugging only.
|
||||||
|
* @param nestLevel An aid to prettier tree indenting, and is the level
|
||||||
|
* of nesting of this object within the overall tree.
|
||||||
|
* @param os The ostream& to output to.
|
||||||
|
*/
|
||||||
void BOARD::Show( int nestLevel, std::ostream& os )
|
void BOARD::Show( int nestLevel, std::ostream& os )
|
||||||
{
|
{
|
||||||
BOARD_ITEM* p;
|
BOARD_ITEM* p;
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
/**
|
/*************************************************/
|
||||||
* @file class_board.h
|
/* class_board.h - Class BOARD to handle a board */
|
||||||
* @brief Class BOARD to handle a board
|
/*************************************************/
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef CLASS_BOARD_H
|
#ifndef CLASS_BOARD_H
|
||||||
#define CLASS_BOARD_H
|
#define CLASS_BOARD_H
|
||||||
|
@ -13,29 +12,8 @@
|
||||||
|
|
||||||
|
|
||||||
class ZONE_CONTAINER;
|
class ZONE_CONTAINER;
|
||||||
class TRACK;
|
|
||||||
|
|
||||||
|
|
||||||
#define HISTORY_MAX_COUNT 8
|
|
||||||
|
|
||||||
// Used to buffer item candidates when search for items on the same track
|
|
||||||
typedef std::vector<TRACK*> TRACK_PTRS;
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetTraceByEndPoint
|
|
||||||
* returns a trace starting at \a aStartTrace and ending at \a aEndTrace that has an
|
|
||||||
* end point at \a aPosition on \a aLayerMask.
|
|
||||||
*
|
|
||||||
* @param aStartTrace Pointer to the TRACK object to begin the search.
|
|
||||||
* @param aEndTrace Pointer to the TRACK object to end then search.
|
|
||||||
* @param aPosition The wxPoint to check the trace end points against.
|
|
||||||
* @param aLayerMask The layer or layers to search.
|
|
||||||
* @return A pointer to the TRACK or SEGVIA object if found, else NULL.
|
|
||||||
*/
|
|
||||||
TRACK* GetTraceByEndPoint( TRACK* aStartTrace, TRACK* aEndTrace,
|
|
||||||
const wxPoint& aPosition, int aLayerMask );
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Enum LAYER_T
|
* Enum LAYER_T
|
||||||
* gives the allowed types of layers, same as Specctra DSN spec.
|
* gives the allowed types of layers, same as Specctra DSN spec.
|
||||||
|
@ -63,6 +41,7 @@ struct LAYER
|
||||||
// int m_Color;
|
// int m_Color;
|
||||||
// bool m_Visible; // ? use flags in m_Color instead ?
|
// bool m_Visible; // ? use flags in m_Color instead ?
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function ShowType
|
* Function ShowType
|
||||||
* converts a LAYER_T enum to a const char*
|
* converts a LAYER_T enum to a const char*
|
||||||
|
@ -99,7 +78,8 @@ public:
|
||||||
|
|
||||||
bool operator ==( const VIA_DIMENSION& other ) const
|
bool operator ==( const VIA_DIMENSION& other ) const
|
||||||
{
|
{
|
||||||
return (m_Diameter == other.m_Diameter) && (m_Drill == other.m_Drill);
|
return (m_Diameter == other.m_Diameter)
|
||||||
|
&& (m_Drill == other.m_Drill);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -107,17 +87,14 @@ public:
|
||||||
{
|
{
|
||||||
if( m_Diameter != other.m_Diameter )
|
if( m_Diameter != other.m_Diameter )
|
||||||
return m_Diameter < other.m_Diameter;
|
return m_Diameter < other.m_Diameter;
|
||||||
|
|
||||||
return m_Drill < other.m_Drill;
|
return m_Drill < other.m_Drill;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
// Helper class to handle hight light nets
|
// Helper class to handle hight light nets
|
||||||
class HIGHT_LIGHT_INFO
|
class HIGHT_LIGHT_INFO
|
||||||
{
|
{
|
||||||
friend class BOARD;
|
friend class BOARD;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
int m_netCode; // net selected for hightlight (-1 when no net selected )
|
int m_netCode; // net selected for hightlight (-1 when no net selected )
|
||||||
bool m_hightLightOn; // hightlight active
|
bool m_hightLightOn; // hightlight active
|
||||||
|
@ -135,22 +112,20 @@ protected:
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class BOARD
|
* Class BOARD
|
||||||
* holds information pertinent to a PCBNEW printed circuit board.
|
* holds information pertinent to a PCBNEW printed circuit board.
|
||||||
*/
|
*/
|
||||||
|
#define HISTORY_MAX_COUNT 8
|
||||||
class BOARD : public BOARD_ITEM
|
class BOARD : public BOARD_ITEM
|
||||||
{
|
{
|
||||||
friend class PCB_EDIT_FRAME;
|
friend class PCB_EDIT_FRAME;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
typedef std::vector<MARKER_PCB*> MARKERS; // @todo: switch to boost:ptr_vector, and change ~BOARD()
|
typedef std::vector<MARKER_PCB*> MARKERS; // @todo: switch to boost:ptr_vector, and change ~BOARD()
|
||||||
|
|
||||||
MARKERS m_markers; ///< MARKER_PCBs for clearance problems, owned by pointer
|
MARKERS m_markers; ///< MARKER_PCBs for clearance problems, owned by pointer
|
||||||
|
|
||||||
typedef std::vector<ZONE_CONTAINER*> ZONE_CONTAINERS; // @todo: switch to boost::ptr_vector, and change ~BOARD()
|
typedef std::vector<ZONE_CONTAINER*> ZONE_CONTAINERS; // @todo: switch to boost::ptr_vector, and change ~BOARD()
|
||||||
|
|
||||||
ZONE_CONTAINERS m_ZoneDescriptorList; ///< edge zone descriptors, owned by pointer
|
ZONE_CONTAINERS m_ZoneDescriptorList; ///< edge zone descriptors, owned by pointer
|
||||||
|
|
||||||
LAYER m_Layer[NB_COPPER_LAYERS];
|
LAYER m_Layer[NB_COPPER_LAYERS];
|
||||||
|
@ -159,6 +134,7 @@ private:
|
||||||
HIGHT_LIGHT_INFO m_hightLightPrevious; // a previously stored hight light data
|
HIGHT_LIGHT_INFO m_hightLightPrevious; // a previously stored hight light data
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
PCB_BASE_FRAME* m_PcbFrame; // Window of visualization
|
||||||
EDA_RECT m_BoundaryBox; // Board size and position
|
EDA_RECT m_BoundaryBox; // Board size and position
|
||||||
int m_Status_Pcb; // Flags used in ratsnet calculation and update
|
int m_Status_Pcb; // Flags used in ratsnet calculation and update
|
||||||
int m_NbNodes; // Active pads (pads attached to a net ) count
|
int m_NbNodes; // Active pads (pads attached to a net ) count
|
||||||
|
@ -171,8 +147,8 @@ public:
|
||||||
|
|
||||||
NETINFO_LIST* m_NetInfo; // nets info list (name, design constraints ..
|
NETINFO_LIST* m_NetInfo; // nets info list (name, design constraints ..
|
||||||
|
|
||||||
std::vector<RATSNEST_ITEM> m_FullRatsnest; // Ratsnest list for the BOARD
|
std::vector<RATSNEST_ITEM> m_FullRatsnest; // Rastnest list for the BOARD
|
||||||
std::vector<RATSNEST_ITEM> m_LocalRatsnest; /* Ratsnest list relative to a given footprint
|
std::vector<RATSNEST_ITEM> m_LocalRatsnest; /* Rastnest list relative to a given footprint
|
||||||
* (used while moving a footprint) */
|
* (used while moving a footprint) */
|
||||||
|
|
||||||
ZONE_CONTAINER* m_CurrentZoneContour; // zone contour currently in progress
|
ZONE_CONTAINER* m_CurrentZoneContour; // zone contour currently in progress
|
||||||
|
@ -191,7 +167,6 @@ public:
|
||||||
std::vector <int> m_TrackWidthList; // tracks widths (max count = HISTORY_MAX_COUNT)
|
std::vector <int> m_TrackWidthList; // tracks widths (max count = HISTORY_MAX_COUNT)
|
||||||
// The first value is the current netclass track width
|
// The first value is the current netclass track width
|
||||||
unsigned m_ViaSizeSelector; // index for m_ViaSizeList to select the value
|
unsigned m_ViaSizeSelector; // index for m_ViaSizeList to select the value
|
||||||
|
|
||||||
// 0 is the index selection of the default value Netclass
|
// 0 is the index selection of the default value Netclass
|
||||||
unsigned m_TrackWidthSelector; // index for m_TrackWidthList to select the value
|
unsigned m_TrackWidthSelector; // index for m_TrackWidthList to select the value
|
||||||
|
|
||||||
|
@ -199,25 +174,9 @@ private:
|
||||||
BOARD_DESIGN_SETTINGS* m_boardDesignSettings; // Link to current design settings
|
BOARD_DESIGN_SETTINGS* m_boardDesignSettings; // Link to current design settings
|
||||||
COLORS_DESIGN_SETTINGS* m_colorsSettings; // Link to current colors settings
|
COLORS_DESIGN_SETTINGS* m_colorsSettings; // Link to current colors settings
|
||||||
|
|
||||||
/**
|
/**********************************/
|
||||||
* Function chainMarkedSegments
|
|
||||||
* add all trace segments to \a aList attached to a trace found at \a aPosition on
|
|
||||||
* \a aLayerMask.
|
|
||||||
* <p>
|
|
||||||
* The BUSY flag of all connected segments is set. Vias are also put in list but
|
|
||||||
* their flags BUSY is not set.
|
|
||||||
* </p>
|
|
||||||
* @param aPosition A wxPoint object contatining thhe reference coordinate of the
|
|
||||||
* to search.
|
|
||||||
* @param aLayerMask The allowed layers for segments to search (1 layer when starting
|
|
||||||
* point is on a segment, but more than one when starting point is
|
|
||||||
* on a via)
|
|
||||||
* @param aList The track list to fill with flagged segments.
|
|
||||||
*/
|
|
||||||
void chainMarkedSegments( wxPoint& aPosition, int aLayerMask, TRACK_PTRS* aList );
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
BOARD( EDA_ITEM* aParent );
|
BOARD( EDA_ITEM* aParent, PCB_BASE_FRAME* frame );
|
||||||
~BOARD();
|
~BOARD();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -260,8 +219,7 @@ public:
|
||||||
*/
|
*/
|
||||||
void Delete( BOARD_ITEM* aBoardItem )
|
void Delete( BOARD_ITEM* aBoardItem )
|
||||||
{
|
{
|
||||||
wxASSERT( aBoardItem ); // developers should run DEBUG versions and fix calls with NULL
|
wxASSERT( aBoardItem ); // developers should run DEBUG versions and fix such calls with NULL
|
||||||
|
|
||||||
if( aBoardItem )
|
if( aBoardItem )
|
||||||
delete Remove( aBoardItem );
|
delete Remove( aBoardItem );
|
||||||
}
|
}
|
||||||
|
@ -269,7 +227,8 @@ public:
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function Remove
|
* Function Remove
|
||||||
* removes \a aBoardItem from this BOARD and returns it to caller without deleting it.
|
* removes \a aBoardItem from this BOARD and returns it to caller without
|
||||||
|
* deleting it.
|
||||||
* @param aBoardItem The item to remove from this board.
|
* @param aBoardItem The item to remove from this board.
|
||||||
* @return BOARD_ITEM* \a aBoardItem which was passed in.
|
* @return BOARD_ITEM* \a aBoardItem which was passed in.
|
||||||
*/
|
*/
|
||||||
|
@ -288,6 +247,7 @@ public:
|
||||||
*/
|
*/
|
||||||
void DeleteZONEOutlines();
|
void DeleteZONEOutlines();
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function GetMARKER
|
* Function GetMARKER
|
||||||
* returns the MARKER at a given index.
|
* returns the MARKER at a given index.
|
||||||
|
@ -298,7 +258,6 @@ public:
|
||||||
{
|
{
|
||||||
if( (unsigned) index < m_markers.size() )
|
if( (unsigned) index < m_markers.size() )
|
||||||
return m_markers[index];
|
return m_markers[index];
|
||||||
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -497,9 +456,9 @@ public:
|
||||||
* @see enum PCB_VISIBLE
|
* @see enum PCB_VISIBLE
|
||||||
*/
|
*/
|
||||||
int GetVisibleElementColor( int aPCB_VISIBLE );
|
int GetVisibleElementColor( int aPCB_VISIBLE );
|
||||||
|
|
||||||
void SetVisibleElementColor( int aPCB_VISIBLE, int aColor );
|
void SetVisibleElementColor( int aPCB_VISIBLE, int aColor );
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function GetBoardDesignSettings
|
* Function GetBoardDesignSettings
|
||||||
* @return the current BOARD_DESIGN_SETTINGS in use
|
* @return the current BOARD_DESIGN_SETTINGS in use
|
||||||
|
@ -592,9 +551,7 @@ public:
|
||||||
|
|
||||||
/* Functions to get some items count */
|
/* Functions to get some items count */
|
||||||
int GetNumSegmTrack();
|
int GetNumSegmTrack();
|
||||||
|
|
||||||
int GetNumSegmZone();
|
int GetNumSegmZone();
|
||||||
|
|
||||||
unsigned GetNoconnectCount(); // Return the number of missing links.
|
unsigned GetNoconnectCount(); // Return the number of missing links.
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -694,36 +651,6 @@ public:
|
||||||
*/
|
*/
|
||||||
NETINFO_ITEM* FindNet( const wxString& aNetname ) const;
|
NETINFO_ITEM* FindNet( const wxString& aNetname ) const;
|
||||||
|
|
||||||
/**
|
|
||||||
* Function CreateLockPoint
|
|
||||||
* creates an intermediate point on \a aSegment
|
|
||||||
* aSegm segment is broken into 2 segments connecting point pX, pY
|
|
||||||
* After insertion:
|
|
||||||
* The new segment starts from to new point, and ends to initial aSegm ending point
|
|
||||||
* the old segment aSegm ends to new point
|
|
||||||
* Returns:
|
|
||||||
* NULL if no new point (ie if aRefPoint already corresponded at one end of aSegm
|
|
||||||
* or
|
|
||||||
* Pointer to the segment created
|
|
||||||
* Returns the exact value of aRefPoint
|
|
||||||
* If aSegm points to a via:
|
|
||||||
* Returns the exact value of aRefPoint and a pointer to the via,
|
|
||||||
* But does not create extra point
|
|
||||||
*/
|
|
||||||
TRACK* CreateLockPoint( wxPoint& aRefPoint, TRACK* aSegment,
|
|
||||||
PICKED_ITEMS_LIST* aItemsListPicker );
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetLockPoint
|
|
||||||
* returns the object at the end of a trace locacted at \a aPosition on \a aLayer.
|
|
||||||
*
|
|
||||||
* @param aPosition A wxPoint object containing the position to hit test.
|
|
||||||
* @param aLayerMask A layer or layers to mask the hit test.
|
|
||||||
* @return A pointer to the board item if found or NULL if not found.
|
|
||||||
*/
|
|
||||||
BOARD_ITEM* GetLockPoint( const wxPoint& aPosition, int aLayerMask );
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function FindModuleByReference
|
* Function FindModuleByReference
|
||||||
* searches for a MODULE within this board with the given
|
* searches for a MODULE within this board with the given
|
||||||
|
@ -735,94 +662,14 @@ public:
|
||||||
*/
|
*/
|
||||||
MODULE* FindModuleByReference( const wxString& aReference ) const;
|
MODULE* FindModuleByReference( const wxString& aReference ) const;
|
||||||
|
|
||||||
/**
|
|
||||||
* Function Locate_Prefered_Module
|
|
||||||
* locates a footprint at \a aPosition on \a aActiveLayer.
|
|
||||||
* <p>
|
|
||||||
* If several footprints are are at \a aPosition, then the priority is the closest on the
|
|
||||||
* active layer, then closest to \a aPosition. The distance is calculatedvia manhattan
|
|
||||||
* distance from the center of the bounding rectangle to \a aposition.
|
|
||||||
* </p>
|
|
||||||
* @param aPosition A wxPoint object containing the position to hit test.
|
|
||||||
* @param aActiveLayer The layer to test.
|
|
||||||
* @param aVisibleOnly Search only the visible layers if true.
|
|
||||||
* @param aIgnoreLocked Ignore locked modules when true.
|
|
||||||
* @return MODULE* The best module or NULL if none.
|
|
||||||
*/
|
|
||||||
MODULE* GetModule( const wxPoint& aPosition, int aActiveLayer,
|
|
||||||
bool aVisibleOnly, bool aIgnoreLocked = false );
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetTrace
|
|
||||||
* returns a trace segment or via at \a aPosition on \a aLayer.
|
|
||||||
*
|
|
||||||
* @param aPosition The wxPoint to HitTest() against.
|
|
||||||
* @param aLayer The layer to search. Use -1 for a don't care.
|
|
||||||
* @return A pointer to the TRACK or SEGVIA object if found, else NULL.
|
|
||||||
*/
|
|
||||||
TRACK* GetTrace( const wxPoint& aPosition, int aLayer );
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetVia
|
|
||||||
* finds the first via at \a aPosition on \a aLayer.
|
|
||||||
* @param aPosition The wxPoint to HitTest() against.
|
|
||||||
* @param aLayer The layer to search. Use -1 for a don't care.
|
|
||||||
* @return TRACK* A point a to the SEGVIA object if found, else NULL.
|
|
||||||
*/
|
|
||||||
TRACK* GetVia( const wxPoint& aPosition, int aLayer = -1 );
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetPad
|
|
||||||
* returns the pad connected to the beginning or end of \a aTrace at \a aEnd
|
|
||||||
*
|
|
||||||
* @param aTrace A pointer to the trace to test for a pad connection.
|
|
||||||
* @param aEnd The end point of \a aTrace to test for a pad connection.
|
|
||||||
* @return A pointer to a D_PAD object if connection found or NULL if not found.
|
|
||||||
*/
|
|
||||||
D_PAD* GetPad( TRACK* aTrace, int aEnd );
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetPad
|
|
||||||
* finds a pad \a aPosition on \a aLayer.
|
|
||||||
*
|
|
||||||
* @param aPosition A wxPoint object containing the position to hit test.
|
|
||||||
* @param aLayerMask A layer or layers to mask the hit test.
|
|
||||||
* @return A pointer to a D_PAD object if found or NULL if not found.
|
|
||||||
*/
|
|
||||||
D_PAD* GetPad( const wxPoint& aPosition, int aLayerMask = ALL_LAYERS );
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetPadFast
|
|
||||||
* return pad found at \a aPosition on \a aLayer uning the fast search method.
|
|
||||||
* <p>
|
|
||||||
* The fast search method only works if the pad list has already exists.
|
|
||||||
* </p>
|
|
||||||
* @param aPosition A wxPoint object containing the position to hit test.
|
|
||||||
* @param aLayer A layer or layers to mask the hit test.
|
|
||||||
* @return A pointer to a D_PAD object if found or NULL if not found.
|
|
||||||
*/
|
|
||||||
D_PAD* GetPadFast( const wxPoint& aPosition, int aLayer );
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function ReturnSortedNetnamesList
|
* Function ReturnSortedNetnamesList
|
||||||
* @param aNames An array string to fill with net names.
|
* @param aNames An array string to fill with net names.
|
||||||
* @param aSortbyPadsCount : true = sort by active pads count, false = no sort (i.e.
|
* @param aSortbyPadsCount : true = sort by active pads count, false = no sort (i.e. leave the sort by net names)
|
||||||
* leave the sort by net names)
|
|
||||||
* @return int - net names count.
|
* @return int - net names count.
|
||||||
*/
|
*/
|
||||||
int ReturnSortedNetnamesList( wxArrayString& aNames, bool aSortbyPadsCount );
|
int ReturnSortedNetnamesList( wxArrayString& aNames, bool aSortbyPadsCount );
|
||||||
|
|
||||||
/**
|
|
||||||
* Function CreateSortedPadListByXCoord
|
|
||||||
* clears then fills \a aVector with all pads on the board and sorts them by
|
|
||||||
* increasing x coordinate.
|
|
||||||
*
|
|
||||||
* @note Do not delete any pointers in \a aVector. The pointers are only references to
|
|
||||||
* pads which are owned by the BOARD.
|
|
||||||
* @param aVector Where to put the pad pointers.
|
|
||||||
*/
|
|
||||||
void CreateSortedPadListByXCoord( std::vector<D_PAD*>* aVector );
|
|
||||||
|
|
||||||
/**************************************/
|
/**************************************/
|
||||||
/**
|
/**
|
||||||
* Function relative to NetClasses: **/
|
* Function relative to NetClasses: **/
|
||||||
|
@ -831,9 +678,9 @@ public:
|
||||||
/**
|
/**
|
||||||
* Function SynchronizeNetsAndNetClasses
|
* Function SynchronizeNetsAndNetClasses
|
||||||
* copies NETCLASS info to each NET, based on NET membership in a NETCLASS.
|
* copies NETCLASS info to each NET, based on NET membership in a NETCLASS.
|
||||||
* Must be called after a Design Rules edition, or after reading a netlist (or editing
|
* Must be called after a Design Rules edition, or after reading a netlist (or editing the list of nets)
|
||||||
* the list of nets). Also this function removes the non existing nets in netclasses
|
* Also this function removes the non existing nets in netclasses and add net nets in default netclass
|
||||||
* and add net nets in default netclass (this happens after reading a netlist)
|
* (this happens after reading a netlist)
|
||||||
*/
|
*/
|
||||||
void SynchronizeNetsAndNetClasses();
|
void SynchronizeNetsAndNetClasses();
|
||||||
|
|
||||||
|
@ -914,6 +761,7 @@ public:
|
||||||
*/
|
*/
|
||||||
bool Save( FILE* aFile ) const;
|
bool Save( FILE* aFile ) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function GetClass
|
* Function GetClass
|
||||||
* returns the class name.
|
* returns the class name.
|
||||||
|
@ -1117,8 +965,8 @@ public:
|
||||||
/**
|
/**
|
||||||
* Function CombineAllAreasInNet
|
* Function CombineAllAreasInNet
|
||||||
* Checks all copper areas in net for intersections, combining them if found
|
* Checks all copper areas in net for intersections, combining them if found
|
||||||
* @param aDeletedList = a PICKED_ITEMS_LIST * where to store deleted areas (useful in
|
* @param aDeletedList = a PICKED_ITEMS_LIST * where to store deleted areas (useful in undo commands
|
||||||
* undo commands can be NULL
|
* can be NULL
|
||||||
* @param aNetCode = net to consider
|
* @param aNetCode = net to consider
|
||||||
* @param bMessageBox : if true display warning message box
|
* @param bMessageBox : if true display warning message box
|
||||||
* @param bUseUtility : if true, don't check areas if both utility flags are 0
|
* @param bUseUtility : if true, don't check areas if both utility flags are 0
|
||||||
|
@ -1133,8 +981,8 @@ public:
|
||||||
/**
|
/**
|
||||||
* Function RemoveArea
|
* Function RemoveArea
|
||||||
* remove copper area from net, and put it in a deleted list (if exists)
|
* remove copper area from net, and put it in a deleted list (if exists)
|
||||||
* @param aDeletedList = a PICKED_ITEMS_LIST * where to store deleted areas (useful in
|
* @param aDeletedList = a PICKED_ITEMS_LIST * where to store deleted areas (useful in undo commands
|
||||||
* undo commands can be NULL
|
* can be NULL
|
||||||
* @param area_to_remove = area to delete or put in deleted list
|
* @param area_to_remove = area to delete or put in deleted list
|
||||||
*/
|
*/
|
||||||
void RemoveArea( PICKED_ITEMS_LIST* aDeletedList, ZONE_CONTAINER* area_to_remove );
|
void RemoveArea( PICKED_ITEMS_LIST* aDeletedList, ZONE_CONTAINER* area_to_remove );
|
||||||
|
@ -1161,8 +1009,8 @@ public:
|
||||||
/**
|
/**
|
||||||
* Function CombineAreas
|
* Function CombineAreas
|
||||||
* If possible, combine 2 copper areas
|
* If possible, combine 2 copper areas
|
||||||
* @param aDeletedList = a PICKED_ITEMS_LIST * where to store deleted areas (useful in
|
* @param aDeletedList = a PICKED_ITEMS_LIST * where to store deleted areas (useful in undo commands
|
||||||
* undo commands can be NULL
|
* can be NULL
|
||||||
* @param area_ref = the main area (zone)
|
* @param area_ref = the main area (zone)
|
||||||
* @param area_to_combine = the zone that can be merged with area_ref
|
* @param area_to_combine = the zone that can be merged with area_ref
|
||||||
* area_ref must be BEFORE area_to_combine
|
* area_ref must be BEFORE area_to_combine
|
||||||
|
@ -1197,29 +1045,6 @@ public:
|
||||||
* @param aNetcode = netcode to analyze. if -1, analyze all nets
|
* @param aNetcode = netcode to analyze. if -1, analyze all nets
|
||||||
*/
|
*/
|
||||||
void Test_Connections_To_Copper_Areas( int aNetcode = -1 );
|
void Test_Connections_To_Copper_Areas( int aNetcode = -1 );
|
||||||
|
|
||||||
/**
|
|
||||||
* Function MarkTrace
|
|
||||||
* marks a chain of track segments connected to aTrace.
|
|
||||||
* Each segment is marked by setting the BUSY bit into m_Flags. Electrical
|
|
||||||
* continuity is detected by walking each segment, and finally the segments
|
|
||||||
* are rearranged into a contiguous chain within the given list.
|
|
||||||
*
|
|
||||||
* @param aTrace The trace segment to test for connections.
|
|
||||||
* @param aCount A pointer to an integer where to return the number of interesting
|
|
||||||
* segments.
|
|
||||||
* @param aLength A pointer to an integer where to return the length of the track
|
|
||||||
* @param aLengthDie A pointer to an integer where to return the extra lengths
|
|
||||||
* inside integrated circuits from the pads connected to this
|
|
||||||
* track to the die (if any)
|
|
||||||
* @param aReorder True to reorder the interesting segments (useful for track
|
|
||||||
* edition or deletion) in this case the flag BUSY is set (the
|
|
||||||
* user is responsible for flag clearing). False for no reorder:
|
|
||||||
* useful when we want just calculate the track length in this
|
|
||||||
* case, flags are reset
|
|
||||||
* @return A point to a TRACK object that is the first in the chain of interesting segments.
|
|
||||||
*/
|
|
||||||
TRACK* MarkTrace( TRACK* aTrace, int* aCount, int* aLength, int* aLengthDie, bool aReorder );
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // #ifndef CLASS_BOARD_H
|
#endif // #ifndef CLASS_BOARD_H
|
||||||
|
|
|
@ -819,22 +819,6 @@ D_PAD* MODULE::FindPadByName( const wxString& aPadName ) const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
D_PAD* MODULE::GetPad( const wxPoint& aPosition, int aLayerMask )
|
|
||||||
{
|
|
||||||
for( D_PAD* pad = m_Pads; pad; pad = pad->Next() )
|
|
||||||
{
|
|
||||||
/* ... and on the correct layer. */
|
|
||||||
if( ( pad->m_layerMask & aLayerMask ) == 0 )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if( pad->HitTest( aPosition ) )
|
|
||||||
return pad;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// see class_module.h
|
// see class_module.h
|
||||||
SEARCH_RESULT MODULE::Visit( INSPECTOR* inspector, const void* testData,
|
SEARCH_RESULT MODULE::Visit( INSPECTOR* inspector, const void* testData,
|
||||||
const KICAD_T scanTypes[] )
|
const KICAD_T scanTypes[] )
|
||||||
|
|
|
@ -298,16 +298,6 @@ public:
|
||||||
D_PAD* FindPadByName( const wxString& aPadName ) const;
|
D_PAD* FindPadByName( const wxString& aPadName ) const;
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetPad
|
|
||||||
* return a pad at \a aPosition on \a aLayerMask
|
|
||||||
*
|
|
||||||
* @param aPosition A wxPoint object containing the position to hit test.
|
|
||||||
* @param aLayerMask A layer or layers to mask the hit test.
|
|
||||||
* @return A pointer to a D_PAD object if found or NULL if not found.
|
|
||||||
*/
|
|
||||||
D_PAD* GetPad( const wxPoint& aPosition, int aLayerMask = ALL_LAYERS );
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function Visit
|
* Function Visit
|
||||||
* should be re-implemented for each derived class in order to handle
|
* should be re-implemented for each derived class in order to handle
|
||||||
|
|
|
@ -152,15 +152,14 @@ TRACK::TRACK( const TRACK& Source ) :
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Because of the way SEGVIA and SEGZONE are derived from TRACK and because there are
|
||||||
|
* virtual functions being used, we can no longer simply copy a TRACK and
|
||||||
|
* expect it to be a via or zone. We must construct a true SEGVIA or SEGZONE so its constructor
|
||||||
|
* can initialize the virtual function table properly. This factory type of
|
||||||
|
* function called Copy() can duplicate either a TRACK, SEGVIA, or SEGZONE.
|
||||||
|
*/
|
||||||
TRACK* TRACK::Copy() const
|
TRACK* TRACK::Copy() const
|
||||||
{
|
{
|
||||||
/* Because of the way SEGVIA and SEGZONE are derived from TRACK and because
|
|
||||||
* there are virtual functions being used, we can no longer simply copy a
|
|
||||||
* TRACK and expect it to be a via or zone. We must construct a true SEGVIA
|
|
||||||
* or SEGZONE so its constructor can initialize the virtual function table
|
|
||||||
* properly. This factory type of function called Copy() can duplicate either
|
|
||||||
* a TRACK, SEGVIA, or SEGZONE.
|
|
||||||
*/
|
|
||||||
if( Type() == TYPE_TRACK )
|
if( Type() == TYPE_TRACK )
|
||||||
return new TRACK( *this );
|
return new TRACK( *this );
|
||||||
|
|
||||||
|
@ -174,14 +173,30 @@ TRACK* TRACK::Copy() const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function GetClearance (virtual)
|
||||||
|
* returns the clearance in internal units. If \a aItem is not NULL then the
|
||||||
|
* returned clearance is the greater of this object's clearance and
|
||||||
|
* aItem's clearance. If \a aItem is NULL, then this objects
|
||||||
|
* clearance
|
||||||
|
* is returned.
|
||||||
|
* @param aItem is another BOARD_CONNECTED_ITEM or NULL
|
||||||
|
* @return int - the clearance in internal units.
|
||||||
|
*/
|
||||||
int TRACK::GetClearance( BOARD_CONNECTED_ITEM* aItem ) const
|
int TRACK::GetClearance( BOARD_CONNECTED_ITEM* aItem ) const
|
||||||
{
|
{
|
||||||
// Currently tracks have no specific clearance parameter on a per track or per
|
// Currently tracks have no specific clearance parameter
|
||||||
// segment basis. The NETCLASS clearance is used
|
// on a per track or per segment basis.
|
||||||
|
// the NETCLASS clearance is used
|
||||||
return BOARD_CONNECTED_ITEM::GetClearance( aItem );
|
return BOARD_CONNECTED_ITEM::GetClearance( aItem );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function GetDrillValue
|
||||||
|
* calculate the drill value for vias (m_Drill if > 0, or default drill value for the Netclass
|
||||||
|
* @return real drill_value
|
||||||
|
*/
|
||||||
int TRACK::GetDrillValue() const
|
int TRACK::GetDrillValue() const
|
||||||
{
|
{
|
||||||
if( Type() != TYPE_VIA )
|
if( Type() != TYPE_VIA )
|
||||||
|
@ -200,6 +215,7 @@ int TRACK::GetDrillValue() const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// return true if segment length = 0
|
||||||
bool TRACK::IsNull()
|
bool TRACK::IsNull()
|
||||||
{
|
{
|
||||||
if( ( Type() != TYPE_VIA ) && ( m_Start == m_End ) )
|
if( ( Type() != TYPE_VIA ) && ( m_Start == m_End ) )
|
||||||
|
@ -209,17 +225,24 @@ bool TRACK::IsNull()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int TRACK::IsPointOnEnds( const wxPoint& aPosition, int aDistance )
|
/* Return:
|
||||||
|
* STARTPOINT if point if near (dist = min_dist) star point
|
||||||
|
* ENDPOINT if point if near (dist = min_dist) end point
|
||||||
|
* STARTPOINT|ENDPOINT if point if near (dist = min_dist) both ends
|
||||||
|
* 0 if no
|
||||||
|
* if min_dist < 0: min_dist = track_width/2
|
||||||
|
*/
|
||||||
|
int TRACK::IsPointOnEnds( const wxPoint& point, int min_dist )
|
||||||
{
|
{
|
||||||
int result = 0;
|
int result = 0;
|
||||||
|
|
||||||
if( aDistance < 0 )
|
if( min_dist < 0 )
|
||||||
aDistance = m_Width / 2;
|
min_dist = m_Width / 2;
|
||||||
|
|
||||||
int dx = m_Start.x - aPosition.x;
|
int dx = m_Start.x - point.x;
|
||||||
int dy = m_Start.y - aPosition.y;
|
int dy = m_Start.y - point.y;
|
||||||
|
|
||||||
if( aDistance == 0 )
|
if( min_dist == 0 )
|
||||||
{
|
{
|
||||||
if( (dx == 0) && (dy == 0 ) )
|
if( (dx == 0) && (dy == 0 ) )
|
||||||
result |= STARTPOINT;
|
result |= STARTPOINT;
|
||||||
|
@ -228,14 +251,14 @@ int TRACK::IsPointOnEnds( const wxPoint& aPosition, int aDistance )
|
||||||
{
|
{
|
||||||
double dist = hypot( (double)dx, (double) dy );
|
double dist = hypot( (double)dx, (double) dy );
|
||||||
|
|
||||||
if( aDistance >= (int) dist )
|
if( min_dist >= (int) dist )
|
||||||
result |= STARTPOINT;
|
result |= STARTPOINT;
|
||||||
}
|
}
|
||||||
|
|
||||||
dx = m_End.x - aPosition.x;
|
dx = m_End.x - point.x;
|
||||||
dy = m_End.y - aPosition.y;
|
dy = m_End.y - point.y;
|
||||||
|
|
||||||
if( aDistance == 0 )
|
if( min_dist == 0 )
|
||||||
{
|
{
|
||||||
if( (dx == 0) && (dy == 0 ) )
|
if( (dx == 0) && (dy == 0 ) )
|
||||||
result |= ENDPOINT;
|
result |= ENDPOINT;
|
||||||
|
@ -244,7 +267,7 @@ int TRACK::IsPointOnEnds( const wxPoint& aPosition, int aDistance )
|
||||||
{
|
{
|
||||||
double dist = hypot( (double) dx, (double) dy );
|
double dist = hypot( (double) dx, (double) dy );
|
||||||
|
|
||||||
if( aDistance >= (int) dist )
|
if( min_dist >= (int) dist )
|
||||||
result |= ENDPOINT;
|
result |= ENDPOINT;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -308,6 +331,12 @@ EDA_RECT TRACK::GetBoundingBox() const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function Rotate
|
||||||
|
* Rotate this object.
|
||||||
|
* @param aRotCentre - the rotation point.
|
||||||
|
* @param aAngle - the rotation angle in 0.1 degree.
|
||||||
|
*/
|
||||||
void TRACK::Rotate( const wxPoint& aRotCentre, int aAngle )
|
void TRACK::Rotate( const wxPoint& aRotCentre, int aAngle )
|
||||||
{
|
{
|
||||||
RotatePoint( &m_Start, aRotCentre, aAngle );
|
RotatePoint( &m_Start, aRotCentre, aAngle );
|
||||||
|
@ -315,18 +344,29 @@ void TRACK::Rotate( const wxPoint& aRotCentre, int aAngle )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function Flip
|
||||||
|
* Flip this object, i.e. change the board side for this object
|
||||||
|
* @param aCentre - the rotation point.
|
||||||
|
*/
|
||||||
void TRACK::Flip( const wxPoint& aCentre )
|
void TRACK::Flip( const wxPoint& aCentre )
|
||||||
{
|
{
|
||||||
m_Start.y = aCentre.y - (m_Start.y - aCentre.y);
|
m_Start.y = aCentre.y - (m_Start.y - aCentre.y);
|
||||||
m_End.y = aCentre.y - (m_End.y - aCentre.y);
|
m_End.y = aCentre.y - (m_End.y - aCentre.y);
|
||||||
|
|
||||||
if( Type() != TYPE_VIA )
|
if( Type() == TYPE_VIA )
|
||||||
|
{
|
||||||
|
// Huh? Wouldn't it be better to us Type() != VIA and get rid of these brackets?
|
||||||
|
}
|
||||||
|
else
|
||||||
{
|
{
|
||||||
SetLayer( ChangeSideNumLayer( GetLayer() ) );
|
SetLayer( ChangeSideNumLayer( GetLayer() ) );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// see class_track.h
|
||||||
|
// SEGVIA and SEGZONE inherit this version
|
||||||
SEARCH_RESULT TRACK::Visit( INSPECTOR* inspector, const void* testData,
|
SEARCH_RESULT TRACK::Visit( INSPECTOR* inspector, const void* testData,
|
||||||
const KICAD_T scanTypes[] )
|
const KICAD_T scanTypes[] )
|
||||||
{
|
{
|
||||||
|
@ -360,6 +400,9 @@ bool SEGVIA::IsOnLayer( int layer_number ) const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Return the mask layer for this.
|
||||||
|
* for a via, there is more than one layer used
|
||||||
|
*/
|
||||||
int TRACK::ReturnMaskLayer()
|
int TRACK::ReturnMaskLayer()
|
||||||
{
|
{
|
||||||
if( Type() == TYPE_VIA )
|
if( Type() == TYPE_VIA )
|
||||||
|
@ -392,6 +435,14 @@ int TRACK::ReturnMaskLayer()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/** Set the .m_Layer member param:
|
||||||
|
* For a via m_Layer contains the 2 layers :
|
||||||
|
* top layer and bottom layer used by the via.
|
||||||
|
* The via connect all layers from top layer to bottom layer
|
||||||
|
* 4 bits for the first layer and 4 next bits for the secaon layer
|
||||||
|
* @param top_layer = first layer connected by the via
|
||||||
|
* @param bottom_layer = last layer connected by the via
|
||||||
|
*/
|
||||||
void SEGVIA::SetLayerPair( int top_layer, int bottom_layer )
|
void SEGVIA::SetLayerPair( int top_layer, int bottom_layer )
|
||||||
{
|
{
|
||||||
if( Shape() == VIA_THROUGH )
|
if( Shape() == VIA_THROUGH )
|
||||||
|
@ -407,6 +458,13 @@ void SEGVIA::SetLayerPair( int top_layer, int bottom_layer )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function ReturnLayerPair
|
||||||
|
* Return the 2 layers used by the via (the via actually uses
|
||||||
|
* all layers between these 2 layers)
|
||||||
|
* @param top_layer = pointer to the first layer (can be null)
|
||||||
|
* @param bottom_layer = pointer to the last layer (can be null)
|
||||||
|
*/
|
||||||
void SEGVIA::ReturnLayerPair( int* top_layer, int* bottom_layer ) const
|
void SEGVIA::ReturnLayerPair( int* top_layer, int* bottom_layer ) const
|
||||||
{
|
{
|
||||||
int b_layer = LAYER_N_BACK;
|
int b_layer = LAYER_N_BACK;
|
||||||
|
@ -448,6 +506,9 @@ TRACK* TRACK::GetBestInsertPoint( BOARD* aPcb )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Search (within the track linked list) the first segment matching the netcode
|
||||||
|
* ( the linked list is always sorted by net codes )
|
||||||
|
*/
|
||||||
TRACK* TRACK::GetStartNetCode( int NetCode )
|
TRACK* TRACK::GetStartNetCode( int NetCode )
|
||||||
{
|
{
|
||||||
TRACK* Track = this;
|
TRACK* Track = this;
|
||||||
|
@ -477,6 +538,9 @@ TRACK* TRACK::GetStartNetCode( int NetCode )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Search (within the track linked list) the last segment matching the netcode
|
||||||
|
* ( the linked list is always sorted by net codes )
|
||||||
|
*/
|
||||||
TRACK* TRACK::GetEndNetCode( int NetCode )
|
TRACK* TRACK::GetEndNetCode( int NetCode )
|
||||||
{
|
{
|
||||||
TRACK* NextS, * Track = this;
|
TRACK* NextS, * Track = this;
|
||||||
|
@ -696,226 +760,6 @@ void TRACK::Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int draw_mode, const wxPoint&
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int TRACK::GetEndSegments( int aCount, TRACK** aStartTrack, TRACK** aEndTrack )
|
|
||||||
{
|
|
||||||
TRACK* Track, * via, * segm, * TrackListEnd;
|
|
||||||
int NbEnds, layerMask, ii, ok = 0;
|
|
||||||
|
|
||||||
if( aCount <= 1 )
|
|
||||||
{
|
|
||||||
*aStartTrack = *aEndTrack = this;
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Calculation of the limit analysis. */
|
|
||||||
*aStartTrack = *aEndTrack = NULL;
|
|
||||||
TrackListEnd = Track = this;
|
|
||||||
ii = 0;
|
|
||||||
|
|
||||||
for( ; ( Track != NULL ) && ( ii < aCount ); ii++, Track = Track->Next() )
|
|
||||||
{
|
|
||||||
TrackListEnd = Track;
|
|
||||||
Track->m_Param = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Calculate the extremes. */
|
|
||||||
NbEnds = 0;
|
|
||||||
Track = this;
|
|
||||||
ii = 0;
|
|
||||||
|
|
||||||
for( ; ( Track != NULL ) && ( ii < aCount ); ii++, Track = Track->Next() )
|
|
||||||
{
|
|
||||||
if( Track->Type() == TYPE_VIA )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
layerMask = Track->ReturnMaskLayer();
|
|
||||||
via = GetVia( TrackListEnd, Track->m_Start, layerMask );
|
|
||||||
|
|
||||||
if( via )
|
|
||||||
{
|
|
||||||
layerMask |= via->ReturnMaskLayer();
|
|
||||||
via->SetState( BUSY, ON );
|
|
||||||
}
|
|
||||||
|
|
||||||
Track->SetState( BUSY, ON );
|
|
||||||
segm = GetTraceByEndPoint( this, TrackListEnd, Track->m_Start, layerMask );
|
|
||||||
Track->SetState( BUSY, OFF );
|
|
||||||
|
|
||||||
if( via )
|
|
||||||
via->SetState( BUSY, OFF );
|
|
||||||
|
|
||||||
if( segm == NULL )
|
|
||||||
{
|
|
||||||
switch( NbEnds )
|
|
||||||
{
|
|
||||||
case 0:
|
|
||||||
*aStartTrack = Track; NbEnds++;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 1:
|
|
||||||
int BeginPad, EndPad;
|
|
||||||
*aEndTrack = Track;
|
|
||||||
|
|
||||||
/* Swap ox, oy with fx, fy */
|
|
||||||
BeginPad = Track->GetState( BEGIN_ONPAD );
|
|
||||||
EndPad = Track->GetState( END_ONPAD );
|
|
||||||
|
|
||||||
Track->SetState( BEGIN_ONPAD | END_ONPAD, OFF );
|
|
||||||
|
|
||||||
if( BeginPad )
|
|
||||||
Track->SetState( END_ONPAD, ON );
|
|
||||||
|
|
||||||
if( EndPad )
|
|
||||||
Track->SetState( BEGIN_ONPAD, ON );
|
|
||||||
|
|
||||||
EXCHG( Track->m_Start, Track->m_End );
|
|
||||||
EXCHG( Track->start, Track->end );
|
|
||||||
ok = 1;
|
|
||||||
return ok;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
layerMask = Track->ReturnMaskLayer();
|
|
||||||
via = GetVia( TrackListEnd, Track->m_End, layerMask );
|
|
||||||
|
|
||||||
if( via )
|
|
||||||
{
|
|
||||||
layerMask |= via->ReturnMaskLayer();
|
|
||||||
via->SetState( BUSY, ON );
|
|
||||||
}
|
|
||||||
|
|
||||||
Track->SetState( BUSY, ON );
|
|
||||||
segm = GetTraceByEndPoint( this, TrackListEnd, Track->m_End, layerMask );
|
|
||||||
Track->SetState( BUSY, OFF );
|
|
||||||
|
|
||||||
if( via )
|
|
||||||
via->SetState( BUSY, OFF );
|
|
||||||
|
|
||||||
if( segm == NULL )
|
|
||||||
{
|
|
||||||
switch( NbEnds )
|
|
||||||
{
|
|
||||||
case 0:
|
|
||||||
int BeginPad, EndPad;
|
|
||||||
*aStartTrack = Track;
|
|
||||||
NbEnds++;
|
|
||||||
|
|
||||||
/* Swap ox, oy with fx, fy */
|
|
||||||
BeginPad = Track->GetState( BEGIN_ONPAD );
|
|
||||||
EndPad = Track->GetState( END_ONPAD );
|
|
||||||
|
|
||||||
Track->SetState( BEGIN_ONPAD | END_ONPAD, OFF );
|
|
||||||
|
|
||||||
if( BeginPad )
|
|
||||||
Track->SetState( END_ONPAD, ON );
|
|
||||||
|
|
||||||
if( EndPad )
|
|
||||||
Track->SetState( BEGIN_ONPAD, ON );
|
|
||||||
|
|
||||||
EXCHG( Track->m_Start, Track->m_End );
|
|
||||||
EXCHG( Track->start, Track->end );
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 1:
|
|
||||||
*aEndTrack = Track;
|
|
||||||
ok = 1;
|
|
||||||
return ok;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return ok;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
TRACK* TRACK::GetTrace( const wxPoint& aPosition, int aLayer )
|
|
||||||
{
|
|
||||||
for( TRACK* track = this; track; track = track->Next() )
|
|
||||||
{
|
|
||||||
int layer = track->GetLayer();
|
|
||||||
|
|
||||||
if( track->GetState( BUSY | IS_DELETED ) )
|
|
||||||
{
|
|
||||||
// D( printf( "track %p is BUSY | IS_DELETED. BUSY=%d IS_DELETED=%d\n",
|
|
||||||
// track, track->GetState( BUSY ),
|
|
||||||
// track->GetState( IS_DELETED ) );)
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( GetBoard()->GetBoardDesignSettings()->IsLayerVisible( layer ) == false )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if( track->Type() == TYPE_VIA ) /* VIA encountered. */
|
|
||||||
{
|
|
||||||
if( track->HitTest( aPosition ) )
|
|
||||||
return track;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if( (g_TabOneLayerMask[layer] & aLayer) == 0 )
|
|
||||||
continue; /* Segments on different layers. */
|
|
||||||
|
|
||||||
if( track->HitTest( aPosition ) )
|
|
||||||
return track;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
TRACK* TRACK::GetVia( const wxPoint& aPosition, int aLayer )
|
|
||||||
{
|
|
||||||
TRACK* track;
|
|
||||||
|
|
||||||
for( track = this; track; track = track->Next() )
|
|
||||||
{
|
|
||||||
if( track->Type() != TYPE_VIA )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if( !track->HitTest( aPosition ) )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if( track->GetState( BUSY | IS_DELETED ) )
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if( aLayer < 0 )
|
|
||||||
break;
|
|
||||||
|
|
||||||
if( track->IsOnLayer( aLayer ) )
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
return track;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
TRACK* TRACK::GetVia( TRACK* aEndTrace, const wxPoint& aPosition, int aLayer )
|
|
||||||
{
|
|
||||||
TRACK* trace;
|
|
||||||
|
|
||||||
for( trace = this; trace != NULL; trace = trace->Next() )
|
|
||||||
{
|
|
||||||
if( trace->Type() == TYPE_VIA )
|
|
||||||
{
|
|
||||||
if( aPosition == trace->m_Start )
|
|
||||||
{
|
|
||||||
if( trace->GetState( BUSY | IS_DELETED ) == 0 )
|
|
||||||
{
|
|
||||||
if( aLayer & trace->ReturnMaskLayer() )
|
|
||||||
return trace;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( trace == aEndTrace )
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void SEGVIA::Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int draw_mode, const wxPoint& aOffset )
|
void SEGVIA::Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int draw_mode, const wxPoint& aOffset )
|
||||||
{
|
{
|
||||||
int color;
|
int color;
|
||||||
|
@ -986,10 +830,8 @@ void SEGVIA::Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int draw_mode, const wxPoint
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
GRCircle( &panel->m_ClipBox, DC, m_Start + aOffset,radius, 0, color );
|
GRCircle( &panel->m_ClipBox, DC, m_Start + aOffset,radius, 0, color );
|
||||||
|
|
||||||
if ( fast_draw )
|
if ( fast_draw )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
GRCircle( &panel->m_ClipBox, DC, m_Start + aOffset, inner_radius, 0, color );
|
GRCircle( &panel->m_ClipBox, DC, m_Start + aOffset, inner_radius, 0, color );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -997,8 +839,8 @@ void SEGVIA::Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int draw_mode, const wxPoint
|
||||||
if( DisplayOpt.m_DisplayViaMode != VIA_HOLE_NOT_SHOW )
|
if( DisplayOpt.m_DisplayViaMode != VIA_HOLE_NOT_SHOW )
|
||||||
{
|
{
|
||||||
if( (DisplayOpt.m_DisplayViaMode == ALL_VIA_HOLE_SHOW) // Display all drill holes requested
|
if( (DisplayOpt.m_DisplayViaMode == ALL_VIA_HOLE_SHOW) // Display all drill holes requested
|
||||||
|| ( (drill_radius > 0 ) && !IsDrillDefault() ) ) // Or Display non default holes
|
|| ( (drill_radius > 0 ) && !IsDrillDefault() ) ) // Or Display non default holes requested
|
||||||
{ // requested.
|
{
|
||||||
if( fillvia )
|
if( fillvia )
|
||||||
{
|
{
|
||||||
bool blackpenstate = false;
|
bool blackpenstate = false;
|
||||||
|
@ -1135,6 +977,7 @@ void SEGVIA::Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int draw_mode, const wxPoint
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// see class_track.h
|
||||||
void TRACK::DisplayInfo( EDA_DRAW_FRAME* frame )
|
void TRACK::DisplayInfo( EDA_DRAW_FRAME* frame )
|
||||||
{
|
{
|
||||||
wxString msg;
|
wxString msg;
|
||||||
|
@ -1148,7 +991,7 @@ void TRACK::DisplayInfo( EDA_DRAW_FRAME* frame )
|
||||||
{
|
{
|
||||||
int trackLen = 0;
|
int trackLen = 0;
|
||||||
int lenDie = 0;
|
int lenDie = 0;
|
||||||
board->MarkTrace( this, NULL, &trackLen, &lenDie, false );
|
MarkTrace( board, this, NULL, &trackLen, &lenDie, false );
|
||||||
msg = frame->CoordinateToString( trackLen );
|
msg = frame->CoordinateToString( trackLen );
|
||||||
frame->AppendMsgPanel( _( "Track Len" ), msg, DARKCYAN );
|
frame->AppendMsgPanel( _( "Track Len" ), msg, DARKCYAN );
|
||||||
|
|
||||||
|
@ -1183,6 +1026,13 @@ void TRACK::DisplayInfo( EDA_DRAW_FRAME* frame )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Function DisplayInfoBase
|
||||||
|
* has knowledge about the frame and how and where to put status information
|
||||||
|
* about this object into the frame's message panel.
|
||||||
|
* Display info about the track segment only, and does not calculate the full track length
|
||||||
|
* @param frame A EDA_DRAW_FRAME in which to print status information.
|
||||||
|
*/
|
||||||
void TRACK::DisplayInfoBase( EDA_DRAW_FRAME* frame )
|
void TRACK::DisplayInfoBase( EDA_DRAW_FRAME* frame )
|
||||||
{
|
{
|
||||||
wxString msg;
|
wxString msg;
|
||||||
|
@ -1298,6 +1148,12 @@ void TRACK::DisplayInfoBase( EDA_DRAW_FRAME* frame )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function HitTest
|
||||||
|
* tests if the given wxPoint is within the bounds of this object.
|
||||||
|
* @param refPos A wxPoint to test
|
||||||
|
* @return bool - true if a hit, else false
|
||||||
|
*/
|
||||||
bool TRACK::HitTest( const wxPoint& refPos )
|
bool TRACK::HitTest( const wxPoint& refPos )
|
||||||
{
|
{
|
||||||
int radius = m_Width >> 1;
|
int radius = m_Width >> 1;
|
||||||
|
@ -1324,6 +1180,13 @@ bool TRACK::HitTest( const wxPoint& refPos )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function HitTest (overlaid)
|
||||||
|
* tests if the given EDA_RECT intersect this object.
|
||||||
|
* For now, an ending point must be inside this rect.
|
||||||
|
* @param refArea an EDA_RECT to test
|
||||||
|
* @return bool - true if a hit, else false
|
||||||
|
*/
|
||||||
bool TRACK::HitTest( EDA_RECT& refArea )
|
bool TRACK::HitTest( EDA_RECT& refArea )
|
||||||
{
|
{
|
||||||
if( refArea.Contains( m_Start ) )
|
if( refArea.Contains( m_Start ) )
|
||||||
|
@ -1368,6 +1231,13 @@ wxString TRACK::GetSelectMenuText() const
|
||||||
|
|
||||||
#if defined(DEBUG)
|
#if defined(DEBUG)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function Show
|
||||||
|
* is used to output the object tree, currently for debugging only.
|
||||||
|
* @param nestLevel An aid to prettier tree indenting, and is the level
|
||||||
|
* of nesting of this object within the overall tree.
|
||||||
|
* @param os The ostream& to output to.
|
||||||
|
*/
|
||||||
void TRACK::Show( int nestLevel, std::ostream& os )
|
void TRACK::Show( int nestLevel, std::ostream& os )
|
||||||
{
|
{
|
||||||
NestedSpace( nestLevel, os ) << '<' << GetClass().Lower().mb_str() <<
|
NestedSpace( nestLevel, os ) << '<' << GetClass().Lower().mb_str() <<
|
||||||
|
@ -1388,6 +1258,13 @@ void TRACK::Show( int nestLevel, std::ostream& os )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function Show
|
||||||
|
* is used to output the object tree, currently for debugging only.
|
||||||
|
* @param nestLevel An aid to prettier tree indenting, and is the level
|
||||||
|
* of nesting of this object within the overall tree.
|
||||||
|
* @param os The ostream& to output to.
|
||||||
|
*/
|
||||||
void SEGVIA::Show( int nestLevel, std::ostream& os )
|
void SEGVIA::Show( int nestLevel, std::ostream& os )
|
||||||
{
|
{
|
||||||
const char* cp;
|
const char* cp;
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
/**
|
/*******************************************************************/
|
||||||
* @file class_track.h
|
/* class_track.h: definitions relatives to tracks, vias and zones */
|
||||||
* @brief Class definitions for tracks, vias, and zones.
|
/*******************************************************************/
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef CLASS_TRACK_H
|
#ifndef CLASS_TRACK_H
|
||||||
#define CLASS_TRACK_H
|
#define CLASS_TRACK_H
|
||||||
|
@ -17,9 +16,6 @@
|
||||||
* to the near neighbor internal layer */
|
* to the near neighbor internal layer */
|
||||||
#define VIA_NOT_DEFINED 0 /* not yet used */
|
#define VIA_NOT_DEFINED 0 /* not yet used */
|
||||||
|
|
||||||
#define IGNORE_LAYERS -1
|
|
||||||
|
|
||||||
|
|
||||||
/***/
|
/***/
|
||||||
|
|
||||||
class TRACK : public BOARD_CONNECTED_ITEM
|
class TRACK : public BOARD_CONNECTED_ITEM
|
||||||
|
@ -145,50 +141,6 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetEndSegments
|
|
||||||
* get the end points connected to the track.
|
|
||||||
*
|
|
||||||
* @param aCount The maximum number of connected segments to test.
|
|
||||||
* @param aStartTrack The beginning segment connected to the trace.
|
|
||||||
* @param aEndTrack The end segment connected to the trace.
|
|
||||||
* @return A 1 if the end points are valid or a 0 when a trace is a closed loop.
|
|
||||||
*/
|
|
||||||
int GetEndSegments( int aCount, TRACK** aStartTrack, TRACK** aEndTrack );
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetTrace
|
|
||||||
* returns a trace segment or via at \a aPosition on \a aLayer starting from this
|
|
||||||
* trace.
|
|
||||||
*
|
|
||||||
* @param aPosition The wxPoint to HitTest() against.
|
|
||||||
* @param aLayer The layer to search. Use -1 for a don't care.
|
|
||||||
* @return A pointer to the TRACK or SEGVIA object if found, else NULL.
|
|
||||||
*/
|
|
||||||
TRACK* GetTrace( const wxPoint& aPosition, int aLayer );
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetVia
|
|
||||||
* finds the first SEGVIA object at \a aPosition on \a aLayer starting at the trace.
|
|
||||||
*
|
|
||||||
* @param aPosition The wxPoint to HitTest() against.
|
|
||||||
* @param aLayer The layer to match, pass -1 for a don't care.
|
|
||||||
* @return A pointer to a TRACK object ( actually a SEGVIA ) if found, else NULL.
|
|
||||||
*/
|
|
||||||
TRACK* GetVia( const wxPoint& aPosition, int aLayer = IGNORE_LAYERS );
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Function GetVia
|
|
||||||
* finds the first SEGVIA object at \a aPosition on \a aLayer starting at the trace
|
|
||||||
* and ending at \a aEndTrace.
|
|
||||||
*
|
|
||||||
* @param aEndTrace Pointer to the last TRACK object to end search.
|
|
||||||
* @param aPosition The wxPoint to HitTest() against.
|
|
||||||
* @param aLayer The layer to match, pass -1 for a don't care.
|
|
||||||
* @return A pointer to a TRACK object ( actually a SEGVIA ) if found, else NULL.
|
|
||||||
*/
|
|
||||||
TRACK* GetVia( TRACK* aEndTrace, const wxPoint& aPosition, int aLayer );
|
|
||||||
|
|
||||||
/* Display on screen: */
|
/* Display on screen: */
|
||||||
void Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int aDrawMode,
|
void Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int aDrawMode,
|
||||||
const wxPoint& aOffset = ZeroOffset );
|
const wxPoint& aOffset = ZeroOffset );
|
||||||
|
@ -246,12 +198,7 @@ public:
|
||||||
*/
|
*/
|
||||||
int ReturnMaskLayer();
|
int ReturnMaskLayer();
|
||||||
|
|
||||||
/**
|
int IsPointOnEnds( const wxPoint& point, int min_dist = 0 );
|
||||||
* Function IsPointOnEnds
|
|
||||||
* returns #STARTPOINT or #ENDPOINT if the start or end point is within \a aDistance
|
|
||||||
* of \a aPosition otherwise 0 is returned.
|
|
||||||
*/
|
|
||||||
int IsPointOnEnds( const wxPoint& aPosition, int aDistance = 0 );
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function IsNull
|
* Function IsNull
|
||||||
|
@ -404,6 +351,7 @@ public:
|
||||||
void Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int aDrawMode,
|
void Draw( EDA_DRAW_PANEL* panel, wxDC* DC, int aDrawMode,
|
||||||
const wxPoint& aOffset = ZeroOffset );
|
const wxPoint& aOffset = ZeroOffset );
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function IsOnLayer
|
* Function IsOnLayer
|
||||||
* tests to see if this object is on the given layer. Is virtual
|
* tests to see if this object is on the given layer. Is virtual
|
||||||
|
@ -413,25 +361,7 @@ public:
|
||||||
*/
|
*/
|
||||||
bool IsOnLayer( int aLayer ) const;
|
bool IsOnLayer( int aLayer ) const;
|
||||||
|
|
||||||
/**
|
|
||||||
* Function SetLayerPair
|
|
||||||
* set the .m_Layer member for a via m_Layer contains the 2 layers :
|
|
||||||
* top layer and bottom layer used by the via.
|
|
||||||
* The via connect all layers from top layer to bottom layer
|
|
||||||
* 4 bits for the first layer and 4 next bits for the second layer
|
|
||||||
* @param top_layer = first layer connected by the via
|
|
||||||
* @param bottom_layer = last layer connected by the via
|
|
||||||
*/
|
|
||||||
void SetLayerPair( int top_layer, int bottom_layer );
|
void SetLayerPair( int top_layer, int bottom_layer );
|
||||||
|
|
||||||
/**
|
|
||||||
* Function ReturnLayerPair
|
|
||||||
* return the 2 layers used by the via (the via actually uses all layers between
|
|
||||||
* these 2 layers)
|
|
||||||
*
|
|
||||||
* @param top_layer = pointer to the first layer (can be null)
|
|
||||||
* @param bottom_layer = pointer to the last layer (can be null)
|
|
||||||
*/
|
|
||||||
void ReturnLayerPair( int* top_layer, int* bottom_layer ) const;
|
void ReturnLayerPair( int* top_layer, int* bottom_layer ) const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -857,26 +857,43 @@ bool ZONE_CONTAINER::HitTest( const wxPoint& refPos )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool ZONE_CONTAINER::HitTestForCorner( const wxPoint& aPosition, int aMinDistance )
|
/**
|
||||||
|
* Function HitTestForCorner
|
||||||
|
* tests if the given wxPoint near a corner, or near the segment define by 2 corners.
|
||||||
|
* Choose the nearest corner
|
||||||
|
* "near" means grid size (or CORNER_MIN_DIST if grid is not known)
|
||||||
|
* Set m_CornerSelection to corner index in .m_Poly->corner or -1 if no corner found
|
||||||
|
* @return true if a corner found
|
||||||
|
* @param refPos : A wxPoint to test
|
||||||
|
*/
|
||||||
|
bool ZONE_CONTAINER::HitTestForCorner( const wxPoint& refPos )
|
||||||
{
|
{
|
||||||
m_CornerSelection = -1; // Set to not found
|
m_CornerSelection = -1; // Set to not found
|
||||||
|
|
||||||
int x, y;
|
#define CORNER_MIN_DIST 100 // distance (in internal units) to detect a corner in a zone outline
|
||||||
int closestDistance = aMinDistance;
|
int min_dist = CORNER_MIN_DIST + 1;
|
||||||
|
|
||||||
|
if( GetBoard() && GetBoard()->m_PcbFrame )
|
||||||
|
{
|
||||||
|
// Use grid size because it is known
|
||||||
|
wxRealPoint grid = GetBoard()->m_PcbFrame->DrawPanel->GetGrid();
|
||||||
|
min_dist = wxRound( MIN( grid.x, grid.y ) );
|
||||||
|
}
|
||||||
|
|
||||||
|
wxPoint delta;
|
||||||
unsigned lim = m_Poly->corner.size();
|
unsigned lim = m_Poly->corner.size();
|
||||||
|
|
||||||
for( unsigned item_pos = 0; item_pos < lim; item_pos++ )
|
for( unsigned item_pos = 0; item_pos < lim; item_pos++ )
|
||||||
{
|
{
|
||||||
x = aPosition.x - m_Poly->corner[item_pos].x;
|
delta.x = refPos.x - m_Poly->corner[item_pos].x;
|
||||||
y = aPosition.y - m_Poly->corner[item_pos].y;
|
delta.y = refPos.y - m_Poly->corner[item_pos].y;
|
||||||
|
|
||||||
// Calculate a distance:
|
// Calculate a distance:
|
||||||
int dist = MAX( abs( x ), abs( y ) );
|
int dist = MAX( abs( delta.x ), abs( delta.y ) );
|
||||||
|
|
||||||
if( dist < closestDistance ) // this corner is a candidate:
|
if( dist < min_dist ) // this corner is a candidate:
|
||||||
{
|
{
|
||||||
m_CornerSelection = item_pos;
|
m_CornerSelection = item_pos;
|
||||||
closestDistance = dist;
|
min_dist = dist;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -884,13 +901,31 @@ bool ZONE_CONTAINER::HitTestForCorner( const wxPoint& aPosition, int aMinDistanc
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool ZONE_CONTAINER::HitTestForEdge( const wxPoint& aPosition, int aMinDistance )
|
/**
|
||||||
|
* Function HitTestForEdge
|
||||||
|
* tests if the given wxPoint near a corner, or near the segment define by 2 corners.
|
||||||
|
* choose the nearest segment
|
||||||
|
* "near" means grid size (or EDGE_MIN_DIST if grid is not known)
|
||||||
|
* Set m_CornerSelection to -1 if nothing found, or index of the starting corner of edge
|
||||||
|
* in .m_Poly->corner
|
||||||
|
* @return true if found
|
||||||
|
* @param refPos : A wxPoint to test
|
||||||
|
*/
|
||||||
|
bool ZONE_CONTAINER::HitTestForEdge( const wxPoint& refPos )
|
||||||
{
|
{
|
||||||
unsigned lim = m_Poly->corner.size();
|
unsigned lim = m_Poly->corner.size();
|
||||||
|
|
||||||
m_CornerSelection = -1; // Set to not found
|
m_CornerSelection = -1; // Set to not found
|
||||||
|
|
||||||
int closestDistance = aMinDistance;
|
#define EDGE_MIN_DIST 200 // distance (in internal units) to detect a zone outline
|
||||||
|
int min_dist = EDGE_MIN_DIST+1;
|
||||||
|
|
||||||
|
if( GetBoard() && GetBoard()->m_PcbFrame )
|
||||||
|
{
|
||||||
|
// Use grid size because it is known
|
||||||
|
wxRealPoint grid = GetBoard()->m_PcbFrame->DrawPanel->GetGrid();
|
||||||
|
min_dist = wxRound( MIN( grid.x, grid.y ) );
|
||||||
|
}
|
||||||
|
|
||||||
unsigned first_corner_pos = 0;
|
unsigned first_corner_pos = 0;
|
||||||
|
|
||||||
|
@ -910,17 +945,17 @@ bool ZONE_CONTAINER::HitTestForEdge( const wxPoint& aPosition, int aMinDistance
|
||||||
}
|
}
|
||||||
|
|
||||||
/* test the dist between segment and ref point */
|
/* test the dist between segment and ref point */
|
||||||
int dist = (int) GetPointToLineSegmentDistance( aPosition.x,
|
int dist = (int) GetPointToLineSegmentDistance( refPos.x,
|
||||||
aPosition.y,
|
refPos.y,
|
||||||
m_Poly->corner[item_pos].x,
|
m_Poly->corner[item_pos].x,
|
||||||
m_Poly->corner[item_pos].y,
|
m_Poly->corner[item_pos].y,
|
||||||
m_Poly->corner[end_segm].x,
|
m_Poly->corner[end_segm].x,
|
||||||
m_Poly->corner[end_segm].y );
|
m_Poly->corner[end_segm].y );
|
||||||
|
|
||||||
if( dist < closestDistance )
|
if( dist < min_dist )
|
||||||
{
|
{
|
||||||
m_CornerSelection = item_pos;
|
m_CornerSelection = item_pos;
|
||||||
closestDistance = dist;
|
min_dist = dist;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -12,10 +12,6 @@
|
||||||
#include "class_zone_setting.h"
|
#include "class_zone_setting.h"
|
||||||
|
|
||||||
|
|
||||||
#define CORNER_MIN_DIST 100 // distance (in internal units) to detect a corner in a zone outline
|
|
||||||
#define EDGE_MIN_DIST 200 // distance (in internal units) to detect a zone outline
|
|
||||||
|
|
||||||
|
|
||||||
/* a small class used when filling areas with segments */
|
/* a small class used when filling areas with segments */
|
||||||
class SEGMENT
|
class SEGMENT
|
||||||
{
|
{
|
||||||
|
@ -250,23 +246,21 @@ public:
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function HitTestForCorner
|
* Function HitTestForCorner
|
||||||
* tests if \a aPosition is with \a aDistance a zone corner.
|
* tests if the given wxPoint near a corner
|
||||||
* Set m_CornerSelection to -1 if nothing found, or index of corner
|
* Set m_CornerSelection to -1 if nothing found, or index of corner
|
||||||
* @return true if found
|
* @return true if found
|
||||||
* @param aPosition A wxPoint to test
|
* @param refPos : A wxPoint to test
|
||||||
* @param aMinDistance The minimum distance with \a aPosition that will still yield a hit.
|
|
||||||
*/
|
*/
|
||||||
bool HitTestForCorner( const wxPoint& aPosition, int aMinDistance = CORNER_MIN_DIST );
|
bool HitTestForCorner( const wxPoint& refPos );
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function HitTestForEdge
|
* Function HitTestForEdge
|
||||||
* tests if the given wxPoint is near a segment defined by 2 corners.
|
* tests if the given wxPoint is near a segment defined by 2 corners.
|
||||||
* Set m_CornerSelection to -1 if nothing found, or index of the starting corner of vertice
|
* Set m_CornerSelection to -1 if nothing found, or index of the starting corner of vertice
|
||||||
* @return true if found
|
* @return true if found
|
||||||
* @param aPosition A wxPoint to test
|
* @param refPos : A wxPoint to test
|
||||||
* @param aMinDistance The minimum distance with \a aPosition that will still yield a hit.
|
|
||||||
*/
|
*/
|
||||||
bool HitTestForEdge( const wxPoint& aPosition, int aMinDistance = EDGE_MIN_DIST );
|
bool HitTestForEdge( const wxPoint& refPos );
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function HitTest (overlayed)
|
* Function HitTest (overlayed)
|
||||||
|
|
|
@ -153,7 +153,7 @@ void clean_vias( BOARD * aPcb )
|
||||||
if( track->m_Shape != VIA_THROUGH )
|
if( track->m_Shape != VIA_THROUGH )
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
D_PAD* pad = aPcb->GetPadFast( track->m_Start, ALL_CU_LAYERS );
|
D_PAD* pad = Fast_Locate_Pad_Connecte( aPcb, track->m_Start, ALL_CU_LAYERS );
|
||||||
|
|
||||||
if( pad && (pad->m_layerMask & EXTERNAL_LAYERS) == EXTERNAL_LAYERS ) // redundant Via
|
if( pad && (pad->m_layerMask & EXTERNAL_LAYERS) == EXTERNAL_LAYERS ) // redundant Via
|
||||||
{
|
{
|
||||||
|
@ -225,7 +225,7 @@ static void DeleteUnconnectedTracks( PCB_EDIT_FRAME* frame, wxDC* DC )
|
||||||
|
|
||||||
D_PAD* pad;
|
D_PAD* pad;
|
||||||
|
|
||||||
pad = frame->GetBoard()->GetPadFast( segment->m_Start, masklayer );
|
pad = Fast_Locate_Pad_Connecte( frame->GetBoard(), segment->m_Start, masklayer );
|
||||||
|
|
||||||
if( pad != NULL )
|
if( pad != NULL )
|
||||||
{
|
{
|
||||||
|
@ -233,7 +233,7 @@ static void DeleteUnconnectedTracks( PCB_EDIT_FRAME* frame, wxDC* DC )
|
||||||
type_end |= START_ON_PAD;
|
type_end |= START_ON_PAD;
|
||||||
}
|
}
|
||||||
|
|
||||||
pad = frame->GetBoard()->GetPadFast( segment->m_End, masklayer );
|
pad = Fast_Locate_Pad_Connecte( frame->GetBoard(), segment->m_End, masklayer );
|
||||||
|
|
||||||
if( pad != NULL )
|
if( pad != NULL )
|
||||||
{
|
{
|
||||||
|
@ -601,7 +601,8 @@ static TRACK* AlignSegment( BOARD* Pcb, TRACK* pt_ref, TRACK* pt_segm, int extre
|
||||||
if( extremite == START )
|
if( extremite == START )
|
||||||
{
|
{
|
||||||
/* We do not have a pad */
|
/* We do not have a pad */
|
||||||
if( Pcb->GetPadFast( pt_ref->m_Start, g_TabOneLayerMask[pt_ref->GetLayer()] ) )
|
if( Fast_Locate_Pad_Connecte( Pcb, pt_ref->m_Start,
|
||||||
|
g_TabOneLayerMask[pt_ref->GetLayer()] ) )
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
/* change the common point coordinate of pt_segm tu use the other point
|
/* change the common point coordinate of pt_segm tu use the other point
|
||||||
|
@ -620,7 +621,8 @@ static TRACK* AlignSegment( BOARD* Pcb, TRACK* pt_ref, TRACK* pt_segm, int extre
|
||||||
else /* extremite == END */
|
else /* extremite == END */
|
||||||
{
|
{
|
||||||
/* We do not have a pad */
|
/* We do not have a pad */
|
||||||
if( Pcb->GetPadFast( pt_ref->m_End, g_TabOneLayerMask[pt_ref->GetLayer()] ) )
|
if( Fast_Locate_Pad_Connecte( Pcb, pt_ref->m_End,
|
||||||
|
g_TabOneLayerMask[pt_ref->GetLayer()] ) )
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
/* change the common point coordinate of pt_segm tu use the other point
|
/* change the common point coordinate of pt_segm tu use the other point
|
||||||
|
@ -780,7 +782,7 @@ static void Gen_Raccord_Track( PCB_EDIT_FRAME* frame, wxDC* DC )
|
||||||
{
|
{
|
||||||
TRACK* newTrack;
|
TRACK* newTrack;
|
||||||
|
|
||||||
other = frame->GetBoard()->GetTrace( other, segment->m_Start, layerMask );
|
other = GetTrace( other, segment->m_Start, layerMask );
|
||||||
|
|
||||||
if( other == NULL )
|
if( other == NULL )
|
||||||
break;
|
break;
|
||||||
|
@ -829,7 +831,7 @@ static void Gen_Raccord_Track( PCB_EDIT_FRAME* frame, wxDC* DC )
|
||||||
{
|
{
|
||||||
TRACK* newTrack;
|
TRACK* newTrack;
|
||||||
|
|
||||||
other = frame->GetBoard()->GetTrace( other, segment->m_End, layerMask );
|
other = GetTrace( other, segment->m_End, layerMask );
|
||||||
|
|
||||||
if( other == NULL )
|
if( other == NULL )
|
||||||
break;
|
break;
|
||||||
|
@ -978,7 +980,7 @@ void ConnectDanglingEndToPad( PCB_EDIT_FRAME* frame, wxDC* DC )
|
||||||
if( frame->DrawPanel->m_AbortRequest )
|
if( frame->DrawPanel->m_AbortRequest )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
pad = frame->GetBoard()->GetPad( segment, START );
|
pad = Locate_Pad_Connecte( frame->GetBoard(), segment, START );
|
||||||
|
|
||||||
if( pad )
|
if( pad )
|
||||||
{
|
{
|
||||||
|
@ -1002,7 +1004,7 @@ void ConnectDanglingEndToPad( PCB_EDIT_FRAME* frame, wxDC* DC )
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pad = frame->GetBoard()->GetPad( segment, END );
|
pad = Locate_Pad_Connecte( frame->GetBoard(), segment, END );
|
||||||
|
|
||||||
if( pad )
|
if( pad )
|
||||||
{
|
{
|
||||||
|
|
|
@ -562,6 +562,28 @@ static D_PAD* SuperFast_Locate_Pad_Connecte( BOARD* aPcb, LISTE_PAD* pt_liste,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function SortPadsByXCoord
|
||||||
|
* is used to Sort a pad list by x coordinate value.
|
||||||
|
*/
|
||||||
|
static int SortPadsByXCoord( const void* pt_ref, const void* pt_comp )
|
||||||
|
{
|
||||||
|
D_PAD* ref = *(LISTE_PAD*) pt_ref;
|
||||||
|
D_PAD* comp = *(LISTE_PAD*) pt_comp;
|
||||||
|
|
||||||
|
return ref->m_Pos.x - comp->m_Pos.x;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void CreateSortedPadListByXCoord( BOARD* aBoard, std::vector<D_PAD*>* aVector )
|
||||||
|
{
|
||||||
|
aVector->insert( aVector->end(), aBoard->m_NetInfo->m_PadsFullList.begin(),
|
||||||
|
aBoard->m_NetInfo->m_PadsFullList.end() );
|
||||||
|
|
||||||
|
qsort( &(*aVector)[0], aBoard->GetPadsCount(), sizeof( D_PAD*), SortPadsByXCoord );
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/* search connections between tracks and pads, and propagate pad net codes to the track segments
|
/* search connections between tracks and pads, and propagate pad net codes to the track segments
|
||||||
* This is a 2 pass computation.
|
* This is a 2 pass computation.
|
||||||
* First:
|
* First:
|
||||||
|
@ -600,7 +622,7 @@ void PCB_BASE_FRAME::RecalculateAllTracksNetcode()
|
||||||
/**************************************************************/
|
/**************************************************************/
|
||||||
/* Pass 1: search the connections between track ends and pads */
|
/* Pass 1: search the connections between track ends and pads */
|
||||||
/**************************************************************/
|
/**************************************************************/
|
||||||
m_Pcb->CreateSortedPadListByXCoord( &sortedPads );
|
CreateSortedPadListByXCoord( m_Pcb, &sortedPads );
|
||||||
|
|
||||||
/* Reset variables and flags used in computation */
|
/* Reset variables and flags used in computation */
|
||||||
pt_trace = m_Pcb->m_Track;
|
pt_trace = m_Pcb->m_Track;
|
||||||
|
|
|
@ -176,7 +176,7 @@ void PCB_EDIT_FRAME::Remove_One_Track( wxDC* DC, TRACK* pt_segm )
|
||||||
if( pt_segm == NULL )
|
if( pt_segm == NULL )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
TRACK* trackList = GetBoard()->MarkTrace( pt_segm, &segments_to_delete_count,
|
TRACK* trackList = MarkTrace( GetBoard(), pt_segm, &segments_to_delete_count,
|
||||||
NULL, NULL, true );
|
NULL, NULL, true );
|
||||||
|
|
||||||
if( segments_to_delete_count == 0 )
|
if( segments_to_delete_count == 0 )
|
||||||
|
|
|
@ -411,7 +411,7 @@ void DRC::testPad2Pad()
|
||||||
{
|
{
|
||||||
std::vector<D_PAD*> sortedPads;
|
std::vector<D_PAD*> sortedPads;
|
||||||
|
|
||||||
m_pcb->CreateSortedPadListByXCoord( &sortedPads );
|
CreateSortedPadListByXCoord( m_pcb, &sortedPads );
|
||||||
|
|
||||||
// find the max size of the pads (used to stop the test)
|
// find the max size of the pads (used to stop the test)
|
||||||
int max_size = 0;
|
int max_size = 0;
|
||||||
|
@ -420,8 +420,7 @@ void DRC::testPad2Pad()
|
||||||
{
|
{
|
||||||
D_PAD* pad = sortedPads[i];
|
D_PAD* pad = sortedPads[i];
|
||||||
|
|
||||||
// m_ShapeMaxRadius is the radius value of the circle containing the pad.
|
if( pad->m_ShapeMaxRadius > max_size ) // m_ShapeMaxRadius is the radius value of the circle containing the pad
|
||||||
if( pad->m_ShapeMaxRadius > max_size )
|
|
||||||
max_size = pad->m_ShapeMaxRadius;
|
max_size = pad->m_ShapeMaxRadius;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1002,7 +1002,7 @@ void PCB_EDIT_FRAME::Process_Special_Functions( wxCommandEvent& event )
|
||||||
wxPoint pos = GetScreen()->GetCrossHairPosition();
|
wxPoint pos = GetScreen()->GetCrossHairPosition();
|
||||||
track->Draw( DrawPanel, &dc, GR_XOR );
|
track->Draw( DrawPanel, &dc, GR_XOR );
|
||||||
PICKED_ITEMS_LIST itemsListPicker;
|
PICKED_ITEMS_LIST itemsListPicker;
|
||||||
TRACK* newtrack = GetBoard()->CreateLockPoint( pos, track, &itemsListPicker );
|
TRACK* newtrack = CreateLockPoint( GetBoard(), pos, track, &itemsListPicker );
|
||||||
SaveCopyInUndoList( itemsListPicker, UR_UNSPECIFIED );
|
SaveCopyInUndoList( itemsListPicker, UR_UNSPECIFIED );
|
||||||
track->Draw( DrawPanel, &dc, GR_XOR );
|
track->Draw( DrawPanel, &dc, GR_XOR );
|
||||||
newtrack->Draw( DrawPanel, &dc, GR_XOR );
|
newtrack->Draw( DrawPanel, &dc, GR_XOR );
|
||||||
|
|
|
@ -166,7 +166,7 @@ void PCB_EDIT_FRAME::Edit_Track_Width( wxDC* aDC, TRACK* aTrackSegment )
|
||||||
if( aTrackSegment == NULL )
|
if( aTrackSegment == NULL )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
pt_track = GetBoard()->MarkTrace( aTrackSegment, &nb_segm, NULL, NULL, true );
|
pt_track = MarkTrace( GetBoard(), aTrackSegment, &nb_segm, NULL, NULL, true );
|
||||||
|
|
||||||
PICKED_ITEMS_LIST itemsListPicker;
|
PICKED_ITEMS_LIST itemsListPicker;
|
||||||
bool change = false;
|
bool change = false;
|
||||||
|
|
|
@ -33,7 +33,7 @@ void PCB_EDIT_FRAME::ExChange_Track_Layer( TRACK* pt_segm, wxDC* DC )
|
||||||
|
|
||||||
l1 = Route_Layer_TOP; l2 = Route_Layer_BOTTOM;
|
l1 = Route_Layer_TOP; l2 = Route_Layer_BOTTOM;
|
||||||
|
|
||||||
pt_track = GetBoard()->MarkTrace( pt_segm, &nb_segm, NULL, NULL, true );
|
pt_track = MarkTrace( GetBoard(), pt_segm, &nb_segm, NULL, NULL, true );
|
||||||
|
|
||||||
if ( DC )
|
if ( DC )
|
||||||
DrawTraces( DrawPanel, DC, pt_track, nb_segm, GR_XOR );
|
DrawTraces( DrawPanel, DC, pt_track, nb_segm, GR_XOR );
|
||||||
|
@ -87,8 +87,8 @@ void PCB_EDIT_FRAME::ExChange_Track_Layer( TRACK* pt_segm, wxDC* DC )
|
||||||
|
|
||||||
for( ; ii < nb_segm; pt_segm = pt_segm->Next(), ii++ )
|
for( ; ii < nb_segm; pt_segm = pt_segm->Next(), ii++ )
|
||||||
{
|
{
|
||||||
pt_segm->start = GetBoard()->GetPad( pt_segm, START );
|
pt_segm->start = Locate_Pad_Connecte( GetBoard(), pt_segm, START );
|
||||||
pt_segm->end = GetBoard()->GetPad( pt_segm, END );
|
pt_segm->end = Locate_Pad_Connecte( GetBoard(), pt_segm, END );
|
||||||
}
|
}
|
||||||
|
|
||||||
test_1_net_connexion( DC, pt_track->GetNet() );
|
test_1_net_connexion( DC, pt_track->GetNet() );
|
||||||
|
@ -113,7 +113,7 @@ bool PCB_EDIT_FRAME::Other_Layer_Route( TRACK* aTrack, wxDC* DC )
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Avoid more than one via on the current location: */
|
/* Avoid more than one via on the current location: */
|
||||||
if( GetBoard()->GetVia( g_CurrentTrackSegment->m_End, g_CurrentTrackSegment->GetLayer() ) )
|
if( Locate_Via( GetBoard(), g_CurrentTrackSegment->m_End, g_CurrentTrackSegment->GetLayer() ) )
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
for( TRACK* segm = g_FirstTrackSegment; segm; segm = segm->Next() )
|
for( TRACK* segm = g_FirstTrackSegment; segm; segm = segm->Next() )
|
||||||
|
@ -277,7 +277,7 @@ void PCB_EDIT_FRAME::DisplayNetStatus( wxDC* DC )
|
||||||
int layerMask = (1 << getActiveLayer());
|
int layerMask = (1 << getActiveLayer());
|
||||||
wxPoint pos = GetScreen()->RefPos( true );
|
wxPoint pos = GetScreen()->RefPos( true );
|
||||||
|
|
||||||
pt_segm = GetBoard()->GetTrace( pos, layerMask );
|
pt_segm = GetTrace( GetBoard(), GetBoard()->m_Track, pos, layerMask );
|
||||||
|
|
||||||
if( pt_segm == NULL )
|
if( pt_segm == NULL )
|
||||||
GetBoard()->DisplayInfo( this );
|
GetBoard()->DisplayInfo( this );
|
||||||
|
|
|
@ -104,7 +104,7 @@ TRACK* PCB_EDIT_FRAME::Begin_Route( TRACK* aTrack, wxDC* DC )
|
||||||
GetBoard()->SetHightLightNet(0);
|
GetBoard()->SetHightLightNet(0);
|
||||||
|
|
||||||
// Search for a starting point of the new track, a track or pad
|
// Search for a starting point of the new track, a track or pad
|
||||||
LockPoint = GetBoard()->GetLockPoint( pos, layerMask );
|
LockPoint = LocateLockPoint( GetBoard(), pos, layerMask );
|
||||||
|
|
||||||
if( LockPoint ) // An item (pad or track) is found
|
if( LockPoint ) // An item (pad or track) is found
|
||||||
{
|
{
|
||||||
|
@ -120,7 +120,7 @@ TRACK* PCB_EDIT_FRAME::Begin_Route( TRACK* aTrack, wxDC* DC )
|
||||||
{
|
{
|
||||||
TrackOnStartPoint = (TRACK*) LockPoint;
|
TrackOnStartPoint = (TRACK*) LockPoint;
|
||||||
GetBoard()->SetHightLightNet( TrackOnStartPoint->GetNet() );
|
GetBoard()->SetHightLightNet( TrackOnStartPoint->GetNet() );
|
||||||
GetBoard()->CreateLockPoint( pos, TrackOnStartPoint, &s_ItemsListPicker );
|
CreateLockPoint( GetBoard(), pos, TrackOnStartPoint, &s_ItemsListPicker );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else // no starting point, but a filled zone area can exist. This is
|
else // no starting point, but a filled zone area can exist. This is
|
||||||
|
@ -247,7 +247,7 @@ TRACK* PCB_EDIT_FRAME::Begin_Route( TRACK* aTrack, wxDC* DC )
|
||||||
|
|
||||||
newTrack->SetState( BEGIN_ONPAD | END_ONPAD, OFF );
|
newTrack->SetState( BEGIN_ONPAD | END_ONPAD, OFF );
|
||||||
|
|
||||||
oneBeforeLatest->end = GetBoard()->GetPad( oneBeforeLatest, END );
|
oneBeforeLatest->end = Locate_Pad_Connecte( GetBoard(), oneBeforeLatest, END );
|
||||||
|
|
||||||
if( oneBeforeLatest->end )
|
if( oneBeforeLatest->end )
|
||||||
{
|
{
|
||||||
|
@ -451,7 +451,7 @@ bool PCB_EDIT_FRAME::End_Route( TRACK* aTrack, wxDC* DC )
|
||||||
* This helps to reduce the computing time */
|
* This helps to reduce the computing time */
|
||||||
|
|
||||||
/* Attaching the end of the track. */
|
/* Attaching the end of the track. */
|
||||||
BOARD_ITEM* LockPoint = GetBoard()->GetLockPoint( pos, layerMask );
|
BOARD_ITEM* LockPoint = LocateLockPoint( GetBoard(), pos, layerMask );
|
||||||
|
|
||||||
if( LockPoint ) /* End of trace is on a pad. */
|
if( LockPoint ) /* End of trace is on a pad. */
|
||||||
{
|
{
|
||||||
|
@ -466,7 +466,8 @@ bool PCB_EDIT_FRAME::End_Route( TRACK* aTrack, wxDC* DC )
|
||||||
GetBoard()->SetHightLightNet( adr_buf->GetNet() );
|
GetBoard()->SetHightLightNet( adr_buf->GetNet() );
|
||||||
|
|
||||||
/* Possible establishment of a hanging point. */
|
/* Possible establishment of a hanging point. */
|
||||||
LockPoint = GetBoard()->CreateLockPoint( g_CurrentTrackSegment->m_End,
|
LockPoint = CreateLockPoint( GetBoard(),
|
||||||
|
g_CurrentTrackSegment->m_End,
|
||||||
adr_buf,
|
adr_buf,
|
||||||
&s_ItemsListPicker );
|
&s_ItemsListPicker );
|
||||||
}
|
}
|
||||||
|
@ -1049,7 +1050,7 @@ void DeleteNullTrackSegments( BOARD* pcb, DLIST<TRACK>& aTrackList )
|
||||||
while( track != NULL )
|
while( track != NULL )
|
||||||
{
|
{
|
||||||
TRACK* next_track = track->Next();
|
TRACK* next_track = track->Next();
|
||||||
LockPoint = pcb->GetPad( track, END );
|
LockPoint = Locate_Pad_Connecte( pcb, track, END );
|
||||||
|
|
||||||
if( LockPoint )
|
if( LockPoint )
|
||||||
{
|
{
|
||||||
|
|
|
@ -555,7 +555,7 @@ void PCB_EDIT_FRAME::OnHotKey( wxDC* aDC, int aHotkeyCode, const wxPoint& aPosit
|
||||||
if( !itemCurrentlyEdited )
|
if( !itemCurrentlyEdited )
|
||||||
{
|
{
|
||||||
pos = screen->RefPos( true );
|
pos = screen->RefPos( true );
|
||||||
module = GetBoard()->GetModule( pos, screen->m_Active_Layer, true );
|
module = Locate_Prefered_Module( GetBoard(), pos, screen->m_Active_Layer, true );
|
||||||
}
|
}
|
||||||
else if( GetCurItem()->Type() == TYPE_MODULE )
|
else if( GetCurItem()->Type() == TYPE_MODULE )
|
||||||
{
|
{
|
||||||
|
@ -641,7 +641,7 @@ bool PCB_EDIT_FRAME::OnHotkeyDeleteItem( wxDC* aDC )
|
||||||
if( ItemFree )
|
if( ItemFree )
|
||||||
{
|
{
|
||||||
wxPoint pos = GetScreen()->RefPos( false );
|
wxPoint pos = GetScreen()->RefPos( false );
|
||||||
MODULE* module = GetBoard()->GetModule( pos, ALL_LAYERS, false );
|
MODULE* module = Locate_Prefered_Module( GetBoard(), pos, ALL_LAYERS, false );
|
||||||
|
|
||||||
if( module == NULL )
|
if( module == NULL )
|
||||||
return false;
|
return false;
|
||||||
|
@ -659,20 +659,15 @@ bool PCB_EDIT_FRAME::OnHotkeyDeleteItem( wxDC* aDC )
|
||||||
if( ItemFree )
|
if( ItemFree )
|
||||||
{
|
{
|
||||||
item = PcbGeneralLocateAndDisplay();
|
item = PcbGeneralLocateAndDisplay();
|
||||||
|
|
||||||
if( item == NULL )
|
if( item == NULL )
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if( (item->Type() == TYPE_MODULE) && !IsOK( this, _( "Delete module?" ) ) )
|
if( (item->Type() == TYPE_MODULE) && !IsOK( this, _( "Delete module?" ) ) )
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
RemoveStruct( item, aDC );
|
RemoveStruct( item, aDC );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
OnModify();
|
OnModify();
|
||||||
SetCurItem( NULL );
|
SetCurItem( NULL );
|
||||||
|
|
|
@ -40,7 +40,7 @@ bool PCB_EDIT_FRAME::Clear_Pcb( bool aQuery )
|
||||||
|
|
||||||
// delete the old BOARD and create a new BOARD so that the default
|
// delete the old BOARD and create a new BOARD so that the default
|
||||||
// layer names are put into the BOARD.
|
// layer names are put into the BOARD.
|
||||||
SetBoard( new BOARD( NULL ) );
|
SetBoard( new BOARD( NULL, this ) );
|
||||||
SetCurItem( NULL );
|
SetCurItem( NULL );
|
||||||
|
|
||||||
/* clear filename, to avoid overwriting an old file */
|
/* clear filename, to avoid overwriting an old file */
|
||||||
|
|
|
@ -13,6 +13,246 @@
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/* Locates a via point pX, pY
|
||||||
|
* If layer < 0 will be located via whatever layer
|
||||||
|
* If layer = 0 .. 15 Via will be located according to its type:
|
||||||
|
* - Traverse: all layers
|
||||||
|
* - = Blind between layers useful
|
||||||
|
* - Blind idem
|
||||||
|
* Entry: coord point of reference, layer
|
||||||
|
* Output: NULL if not via
|
||||||
|
* (* TRACK) address via
|
||||||
|
*/
|
||||||
|
TRACK* Locate_Via( BOARD* Pcb, const wxPoint& pos, int layer )
|
||||||
|
{
|
||||||
|
TRACK* track;
|
||||||
|
|
||||||
|
for( track = Pcb->m_Track; track; track = track->Next() )
|
||||||
|
{
|
||||||
|
if( track->Type() != TYPE_VIA )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( track->m_Start != pos )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( track->GetState( BUSY | IS_DELETED ) )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( layer < 0 )
|
||||||
|
break;
|
||||||
|
|
||||||
|
if( track->IsOnLayer( layer ) )
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return track;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TRACK* Locate_Via_Area( TRACK* aStart, const wxPoint& pos, int layer )
|
||||||
|
{
|
||||||
|
TRACK* track;
|
||||||
|
|
||||||
|
for( track = aStart; track; track = track->Next() )
|
||||||
|
{
|
||||||
|
if( track->Type() != TYPE_VIA )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( !track->HitTest(pos) )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( track->GetState( BUSY | IS_DELETED ) )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( layer < 0 )
|
||||||
|
break;
|
||||||
|
|
||||||
|
if( track->IsOnLayer( layer ) )
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return track;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Locate the pad CONNECTED to a track
|
||||||
|
* input: ptr_trace: pointer to the segment of track
|
||||||
|
* Extr = flag = START -> beginning of the test segment
|
||||||
|
* END -> end of the segment to be tested
|
||||||
|
* Returns:
|
||||||
|
* A pointer to the description of the pad if found.
|
||||||
|
* NULL pointer if pad NOT FOUND
|
||||||
|
*/
|
||||||
|
D_PAD* Locate_Pad_Connecte( BOARD* Pcb, TRACK* ptr_trace, int extr )
|
||||||
|
{
|
||||||
|
D_PAD* ptr_pad = NULL;
|
||||||
|
wxPoint ref_pos;
|
||||||
|
|
||||||
|
int aLayerMask = g_TabOneLayerMask[ptr_trace->GetLayer()];
|
||||||
|
|
||||||
|
if( extr == START )
|
||||||
|
{
|
||||||
|
ref_pos = ptr_trace->m_Start;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ref_pos = ptr_trace->m_End;
|
||||||
|
}
|
||||||
|
|
||||||
|
for( MODULE* module = Pcb->m_Modules; module; module = module->Next() )
|
||||||
|
{
|
||||||
|
ptr_pad = Locate_Pads( module, ref_pos, aLayerMask );
|
||||||
|
|
||||||
|
if( ptr_pad != NULL )
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return ptr_pad;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Locate a pad pointed to by the coordinates ref_pos.x, ref_pos.y
|
||||||
|
* aLayerMask is allowed layers ( bitmap mask)
|
||||||
|
* Returns:
|
||||||
|
* Pointer to a pad if found or NULL
|
||||||
|
*/
|
||||||
|
D_PAD* Locate_Any_Pad( BOARD* Pcb, const wxPoint& ref_pos, int aLayerMask )
|
||||||
|
{
|
||||||
|
D_PAD* pad = NULL;
|
||||||
|
|
||||||
|
for( MODULE* module=Pcb->m_Modules; module && ( pad == NULL ); module = module->Next() )
|
||||||
|
{
|
||||||
|
if( aLayerMask )
|
||||||
|
pad = Locate_Pads( module, ref_pos, aLayerMask );
|
||||||
|
else
|
||||||
|
pad = Locate_Pads( module, ref_pos, ALL_LAYERS );
|
||||||
|
}
|
||||||
|
|
||||||
|
return pad;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Locate the pad pointed to by the coordinate ref_pos.x,, ref_pos.y
|
||||||
|
* Input:
|
||||||
|
* - the footprint to test
|
||||||
|
* - masque_layer layer(s) (bit_masque) which must be the pad
|
||||||
|
* Returns:
|
||||||
|
* A pointer to the pad if found or NULL
|
||||||
|
*/
|
||||||
|
D_PAD* Locate_Pads( MODULE* module, const wxPoint& ref_pos, int aLayerMask )
|
||||||
|
{
|
||||||
|
for( D_PAD* pt_pad = module->m_Pads; pt_pad; pt_pad = pt_pad->Next() )
|
||||||
|
{
|
||||||
|
/* ... and on the correct layer. */
|
||||||
|
if( ( pt_pad->m_layerMask & aLayerMask ) == 0 )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( pt_pad->HitTest( ref_pos ) )
|
||||||
|
return pt_pad;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function Locate_Prefered_Module
|
||||||
|
* locates a footprint by its bounding rectangle. If several footprints
|
||||||
|
* are possible, then the priority is: the closest on the active layer, then
|
||||||
|
* closest.
|
||||||
|
* The current mouse or cursor coordinates are grabbed from the active window
|
||||||
|
* to perform hit-testing.
|
||||||
|
* distance is calculated via manhattan distance from the center of the
|
||||||
|
* bounding rectangle to the cursor position.
|
||||||
|
*
|
||||||
|
* @param aPcb The BOARD to search within.
|
||||||
|
* @param aPosition Flag bits, tuning the search, see pcbnew.h
|
||||||
|
* @param aActiveLayer Layer to test.
|
||||||
|
* @param aVisibleOnly Search only the visible layers if true.
|
||||||
|
* @param aIgnoreLocked Ignore locked modules when true.
|
||||||
|
* @return MODULE* The best module or NULL if none.
|
||||||
|
*/
|
||||||
|
MODULE* Locate_Prefered_Module( BOARD* aPcb, const wxPoint& aPosition, int aActiveLayer,
|
||||||
|
bool aVisibleOnly, bool aIgnoreLocked )
|
||||||
|
{
|
||||||
|
MODULE* pt_module;
|
||||||
|
MODULE* module = NULL;
|
||||||
|
MODULE* Altmodule = NULL;
|
||||||
|
int min_dim = 0x7FFFFFFF;
|
||||||
|
int alt_min_dim = 0x7FFFFFFF;
|
||||||
|
int layer;
|
||||||
|
|
||||||
|
pt_module = aPcb->m_Modules;
|
||||||
|
|
||||||
|
for( ; pt_module; pt_module = (MODULE*) pt_module->Next() )
|
||||||
|
{
|
||||||
|
// is the ref point within the module's bounds?
|
||||||
|
if( !pt_module->HitTest( aPosition ) )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
// if caller wants to ignore locked modules, and this one is locked, skip it.
|
||||||
|
if( aIgnoreLocked && pt_module->IsLocked() )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
/* Calculate priority: the priority is given to the layer of the
|
||||||
|
* module and the copper layer if the module layer is indelible,
|
||||||
|
* adhesive copper, a layer if cmp module layer is indelible,
|
||||||
|
* adhesive component.
|
||||||
|
*/
|
||||||
|
layer = pt_module->GetLayer();
|
||||||
|
|
||||||
|
if( layer==ADHESIVE_N_BACK || layer==SILKSCREEN_N_BACK )
|
||||||
|
layer = LAYER_N_BACK;
|
||||||
|
else if( layer==ADHESIVE_N_FRONT || layer==SILKSCREEN_N_FRONT )
|
||||||
|
layer = LAYER_N_FRONT;
|
||||||
|
|
||||||
|
/* Test of minimum size to choosing the best candidate. */
|
||||||
|
|
||||||
|
EDA_RECT bb = pt_module->GetFootPrintRect();
|
||||||
|
int offx = bb.GetX() + bb.GetWidth() / 2;
|
||||||
|
int offy = bb.GetY() + bb.GetHeight() / 2;
|
||||||
|
|
||||||
|
//off x & offy point to the middle of the box.
|
||||||
|
int dist = abs( aPosition.x - offx ) + abs( aPosition.y - offy );
|
||||||
|
|
||||||
|
//int dist = MIN(lx, ly); // to pick the smallest module (kinda
|
||||||
|
// screwy with same-sized modules -- this is bad!)
|
||||||
|
|
||||||
|
if( aActiveLayer == layer )
|
||||||
|
{
|
||||||
|
if( dist <= min_dim )
|
||||||
|
{
|
||||||
|
/* better footprint shown on the active layer */
|
||||||
|
module = pt_module;
|
||||||
|
min_dim = dist;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if( aVisibleOnly && aPcb->IsModuleLayerVisible( layer ) )
|
||||||
|
{
|
||||||
|
if( dist <= alt_min_dim )
|
||||||
|
{
|
||||||
|
/* better footprint shown on other layers */
|
||||||
|
Altmodule = pt_module;
|
||||||
|
alt_min_dim = dist;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if( module )
|
||||||
|
{
|
||||||
|
return module;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( Altmodule )
|
||||||
|
{
|
||||||
|
return Altmodule;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* return true if the dist between p1 and p2 < max_dist
|
* return true if the dist between p1 and p2 < max_dist
|
||||||
* Currently in test (currently rasnest algos work only if p1 == p2)
|
* Currently in test (currently rasnest algos work only if p1 == p2)
|
||||||
|
@ -25,9 +265,7 @@ int dist;
|
||||||
dist = abs(p1.x - p2.x) + abs (p1.y - p2.y);
|
dist = abs(p1.x - p2.x) + abs (p1.y - p2.y);
|
||||||
dist *= 7;
|
dist *= 7;
|
||||||
dist /= 10;
|
dist /= 10;
|
||||||
|
if ( dist < max_dist ) return true;
|
||||||
if ( dist < max_dist )
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
if ( p1 == p2 ) return true;
|
if ( p1 == p2 ) return true;
|
||||||
|
@ -181,3 +419,168 @@ suite1:
|
||||||
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* 1 - Locate segment of track leading from the mouse.
|
||||||
|
* 2 - Locate segment of track point by point
|
||||||
|
* ref_pos.x, ref_pos.y.r
|
||||||
|
*
|
||||||
|
* The search begins to address start_adresse
|
||||||
|
*/
|
||||||
|
TRACK* GetTrace( BOARD* aPcb, TRACK* start_adresse, const wxPoint& ref_pos, int LayerMask )
|
||||||
|
{
|
||||||
|
for( TRACK* track = start_adresse; track; track = track->Next() )
|
||||||
|
{
|
||||||
|
int layer = track->GetLayer();
|
||||||
|
|
||||||
|
if( track->GetState( BUSY | IS_DELETED ) )
|
||||||
|
{
|
||||||
|
// D( printf( "track %p is BUSY | IS_DELETED. BUSY=%d IS_DELETED=%d\n",
|
||||||
|
// track, track->GetState( BUSY ),
|
||||||
|
// track->GetState( IS_DELETED ) );)
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( aPcb->GetBoardDesignSettings()->IsLayerVisible( layer ) == false )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( track->Type() == TYPE_VIA ) /* VIA encountered. */
|
||||||
|
{
|
||||||
|
if( track->HitTest( ref_pos ) )
|
||||||
|
return track;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if( (g_TabOneLayerMask[layer] & LayerMask) == 0 )
|
||||||
|
continue; /* Segments on different layers. */
|
||||||
|
|
||||||
|
if( track->HitTest( ref_pos ) )
|
||||||
|
return track;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* 1 - Locate zone area by the mouse.
|
||||||
|
* 2 - Locate zone area by point
|
||||||
|
* def_pos.x, ref_pos.y.r
|
||||||
|
*
|
||||||
|
* If layer == -1, tst layer is not
|
||||||
|
*
|
||||||
|
* The search begins to address start_adresse
|
||||||
|
*/
|
||||||
|
TRACK* Locate_Zone( TRACK* start_adresse, const wxPoint& ref_pos, int layer )
|
||||||
|
{
|
||||||
|
for( TRACK* Zone = start_adresse; Zone; Zone = Zone->Next() )
|
||||||
|
{
|
||||||
|
if( (layer != -1) && (Zone->GetLayer() != layer) )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( Zone->HitTest( ref_pos ) )
|
||||||
|
return Zone;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Find the pad center px, py,
|
||||||
|
* The layer INDICATED BY aLayerMask (bitwise)
|
||||||
|
* (Runway end)
|
||||||
|
* The list of pads must already exist.
|
||||||
|
*
|
||||||
|
* Returns:
|
||||||
|
* NULL if no pad located.
|
||||||
|
* Pointer to the structure corresponding descr_pad if pad found
|
||||||
|
* (Good position and good layer).
|
||||||
|
*/
|
||||||
|
D_PAD* Fast_Locate_Pad_Connecte( BOARD* Pcb, const wxPoint& ref_pos, int aLayerMask )
|
||||||
|
{
|
||||||
|
for( unsigned i=0; i<Pcb->GetPadsCount(); ++i )
|
||||||
|
{
|
||||||
|
D_PAD* pad = Pcb->m_NetInfo->GetPad(i);
|
||||||
|
|
||||||
|
if( pad->m_Pos != ref_pos )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
/* Pad found, it must be on the correct layer */
|
||||||
|
if( pad->m_layerMask & aLayerMask )
|
||||||
|
return pad;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Locate segment with one end that coincides with the point x, y
|
||||||
|
* Data on layers by masklayer
|
||||||
|
* Research is done to address start_adr has end_adr
|
||||||
|
* If end_adr = NULL, end search list
|
||||||
|
* The segments of track marks with the flag are not IS_DELETED or taken
|
||||||
|
* into account
|
||||||
|
*/
|
||||||
|
TRACK* GetTrace( TRACK* start_adr, TRACK* end_adr, const wxPoint& ref_pos, int MaskLayer )
|
||||||
|
{
|
||||||
|
TRACK* PtSegm;
|
||||||
|
|
||||||
|
if( start_adr == NULL )
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
for( PtSegm = start_adr; PtSegm != NULL; PtSegm = PtSegm->Next() )
|
||||||
|
{
|
||||||
|
if( PtSegm->GetState( IS_DELETED | BUSY ) == 0 )
|
||||||
|
{
|
||||||
|
if( ref_pos == PtSegm->m_Start )
|
||||||
|
{
|
||||||
|
if( MaskLayer & PtSegm->ReturnMaskLayer() )
|
||||||
|
return PtSegm;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( ref_pos == PtSegm->m_End )
|
||||||
|
{
|
||||||
|
if( MaskLayer & PtSegm->ReturnMaskLayer() )
|
||||||
|
return PtSegm;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if( PtSegm == end_adr )
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Locates via through the point x, y, on layer data by masklayer.
|
||||||
|
* Search is done to address start_adr has end_adr.
|
||||||
|
* If end_adr = NULL, end search list
|
||||||
|
* Vias whose parameter has the State or IS_DELETED bit BUSY = 1 are ignored
|
||||||
|
*/
|
||||||
|
TRACK* Fast_Locate_Via( TRACK* start_adr, TRACK* end_adr, const wxPoint& pos, int MaskLayer )
|
||||||
|
{
|
||||||
|
TRACK* PtSegm;
|
||||||
|
|
||||||
|
for( PtSegm = start_adr; PtSegm != NULL; PtSegm = PtSegm->Next() )
|
||||||
|
{
|
||||||
|
if( PtSegm->Type() == TYPE_VIA )
|
||||||
|
{
|
||||||
|
if( pos == PtSegm->m_Start )
|
||||||
|
{
|
||||||
|
if( PtSegm->GetState( BUSY | IS_DELETED ) == 0 )
|
||||||
|
{
|
||||||
|
if( MaskLayer & PtSegm->ReturnMaskLayer() )
|
||||||
|
return PtSegm;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if( PtSegm == end_adr )
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
|
@ -153,7 +153,7 @@ bool Magnetize( BOARD* m_Pcb, PCB_EDIT_FRAME* frame, int aCurrentTool, wxSize gr
|
||||||
if( doPad )
|
if( doPad )
|
||||||
{
|
{
|
||||||
int layer_mask = g_TabOneLayerMask[screen->m_Active_Layer];
|
int layer_mask = g_TabOneLayerMask[screen->m_Active_Layer];
|
||||||
D_PAD* pad = m_Pcb->GetPad( pos, layer_mask );
|
D_PAD* pad = Locate_Any_Pad( m_Pcb, pos, layer_mask );
|
||||||
|
|
||||||
if( pad )
|
if( pad )
|
||||||
{
|
{
|
||||||
|
@ -171,7 +171,7 @@ bool Magnetize( BOARD* m_Pcb, PCB_EDIT_FRAME* frame, int aCurrentTool, wxSize gr
|
||||||
int layer = screen->m_Active_Layer;
|
int layer = screen->m_Active_Layer;
|
||||||
|
|
||||||
for( TRACK* via = m_Pcb->m_Track;
|
for( TRACK* via = m_Pcb->m_Track;
|
||||||
via && (via = via->GetVia( *curpos, layer )) != NULL;
|
via && (via = Locate_Via_Area( via, *curpos, layer )) != NULL;
|
||||||
via = via->Next() )
|
via = via->Next() )
|
||||||
{
|
{
|
||||||
if( via != currTrack ) // a via cannot influence itself
|
if( via != currTrack ) // a via cannot influence itself
|
||||||
|
@ -193,7 +193,7 @@ bool Magnetize( BOARD* m_Pcb, PCB_EDIT_FRAME* frame, int aCurrentTool, wxSize gr
|
||||||
{
|
{
|
||||||
int layer_mask = g_TabOneLayerMask[layer];
|
int layer_mask = g_TabOneLayerMask[layer];
|
||||||
|
|
||||||
TRACK* track = m_Pcb->m_Track->GetTrace( pos, layer_mask );
|
TRACK* track = GetTrace( m_Pcb, m_Pcb->m_Track, pos, layer_mask );
|
||||||
|
|
||||||
if( !track || track->Type() != TYPE_TRACK )
|
if( !track || track->Type() != TYPE_TRACK )
|
||||||
{
|
{
|
||||||
|
|
|
@ -127,9 +127,10 @@ FOOTPRINT_EDIT_FRAME::FOOTPRINT_EDIT_FRAME( wxWindow* father,
|
||||||
UpdateTitle();
|
UpdateTitle();
|
||||||
|
|
||||||
if( g_ModuleEditor_Pcb == NULL )
|
if( g_ModuleEditor_Pcb == NULL )
|
||||||
g_ModuleEditor_Pcb = new BOARD( NULL );
|
g_ModuleEditor_Pcb = new BOARD( NULL, this );
|
||||||
|
|
||||||
SetBoard( g_ModuleEditor_Pcb );
|
SetBoard( g_ModuleEditor_Pcb );
|
||||||
|
GetBoard()->m_PcbFrame = this;
|
||||||
|
|
||||||
if( s_screenModule == NULL )
|
if( s_screenModule == NULL )
|
||||||
s_screenModule = new PCB_SCREEN();
|
s_screenModule = new PCB_SCREEN();
|
||||||
|
|
|
@ -1019,15 +1019,14 @@ bool PCB_EDIT_FRAME::PlaceDraggedOrMovedTrackSegment( TRACK* Track, wxDC* DC )
|
||||||
* (only pad connection must be tested, track connection will be
|
* (only pad connection must be tested, track connection will be
|
||||||
* tested by test_1_net_connexion() ) */
|
* tested by test_1_net_connexion() ) */
|
||||||
int layerMask = g_TabOneLayerMask[Track->GetLayer()];
|
int layerMask = g_TabOneLayerMask[Track->GetLayer()];
|
||||||
Track->start = GetBoard()->GetPadFast( Track->m_Start, layerMask );
|
Track->start = Fast_Locate_Pad_Connecte( GetBoard(), Track->m_Start, layerMask );
|
||||||
|
|
||||||
if( Track->start )
|
if( Track->start )
|
||||||
Track->SetState( BEGIN_ONPAD, ON );
|
Track->SetState( BEGIN_ONPAD, ON );
|
||||||
else
|
else
|
||||||
Track->SetState( BEGIN_ONPAD, OFF );
|
Track->SetState( BEGIN_ONPAD, OFF );
|
||||||
|
|
||||||
Track->end = GetBoard()->GetPadFast( Track->m_End, layerMask );
|
Track->end = Fast_Locate_Pad_Connecte( GetBoard(), Track->m_End, layerMask );
|
||||||
|
|
||||||
if( Track->end )
|
if( Track->end )
|
||||||
Track->SetState( END_ONPAD, ON );
|
Track->SetState( END_ONPAD, ON );
|
||||||
else
|
else
|
||||||
|
@ -1055,3 +1054,147 @@ bool PCB_EDIT_FRAME::PlaceDraggedOrMovedTrackSegment( TRACK* Track, wxDC* DC )
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Find the point "attachment" of the end of a trace.
|
||||||
|
* This may be a TBP or another segment of the trace
|
||||||
|
* Returns:
|
||||||
|
* - Pointer to the PAD or:
|
||||||
|
* - Pointer to the segment or:
|
||||||
|
* - NULL
|
||||||
|
* Parameters:
|
||||||
|
* - position to test
|
||||||
|
* - mask layers to be tested
|
||||||
|
*/
|
||||||
|
BOARD_ITEM* LocateLockPoint( BOARD* Pcb, wxPoint pos, int LayerMask )
|
||||||
|
{
|
||||||
|
for( MODULE* module = Pcb->m_Modules; module; module = module->Next() )
|
||||||
|
{
|
||||||
|
D_PAD* pad = Locate_Pads( module, pos, LayerMask );
|
||||||
|
|
||||||
|
if( pad )
|
||||||
|
return pad;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* No pad has been located so check for a segment of the trace. */
|
||||||
|
TRACK* ptsegm = GetTrace( Pcb->m_Track, NULL, pos, LayerMask );
|
||||||
|
|
||||||
|
if( ptsegm == NULL )
|
||||||
|
ptsegm = GetTrace( Pcb, Pcb->m_Track, pos, LayerMask );
|
||||||
|
|
||||||
|
return ptsegm;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Create an intermediate point on a segment
|
||||||
|
* aSegm segment is broken into 2 segments connecting point pX, pY
|
||||||
|
* After insertion:
|
||||||
|
* The new segment starts from to new point, and ends to initial aSegm ending point
|
||||||
|
* the old segment aSegm ends to new point
|
||||||
|
* Returns:
|
||||||
|
* NULL if no new point (ie if aRefPoint already corresponded at one end of aSegm
|
||||||
|
* or
|
||||||
|
* Pointer to the segment created
|
||||||
|
* Returns the exact value of aRefPoint
|
||||||
|
* If aSegm points to a via:
|
||||||
|
* Returns the exact value of aRefPoint and a pointer to the via,
|
||||||
|
* But does not create extra point
|
||||||
|
*/
|
||||||
|
TRACK* CreateLockPoint( BOARD* aPcb,
|
||||||
|
wxPoint& aRefPoint,
|
||||||
|
TRACK* aSegm,
|
||||||
|
PICKED_ITEMS_LIST* aItemsListPicker )
|
||||||
|
{
|
||||||
|
if( aSegm->m_Start == aRefPoint || aSegm->m_End == aRefPoint )
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
/* A via is a good lock point */
|
||||||
|
if( aSegm->Type() == TYPE_VIA )
|
||||||
|
{
|
||||||
|
aRefPoint = aSegm->m_Start;
|
||||||
|
return aSegm;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Calculation coordinate of intermediate point relative to
|
||||||
|
* the start point of aSegm
|
||||||
|
*/
|
||||||
|
wxPoint delta = aSegm->m_End - aSegm->m_Start;
|
||||||
|
|
||||||
|
// Not yet in use:
|
||||||
|
#if 0
|
||||||
|
int ox, oy, fx, fy;
|
||||||
|
|
||||||
|
if( aRefSegm )
|
||||||
|
{
|
||||||
|
ox = aRefSegm->m_Start.x - aSegm->m_Start.x;
|
||||||
|
oy = aRefSegm->m_Start.y - aSegm->m_Start.y;
|
||||||
|
fx = aRefSegm->m_End.x - aSegm->m_Start.x;
|
||||||
|
fy = aRefSegm->m_End.y - aSegm->m_Start.y;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// calculate coordinates of aRefPoint relative to aSegm->m_Start
|
||||||
|
wxPoint newPoint = aRefPoint - aSegm->m_Start;
|
||||||
|
// newPoint must be on aSegm:
|
||||||
|
// Ensure newPoint.y/newPoint.y = delta.y/delta.x
|
||||||
|
if( delta.x == 0 )
|
||||||
|
newPoint.x = 0; /* horizontal segment*/
|
||||||
|
else
|
||||||
|
newPoint.y = wxRound(( (double)newPoint.x * delta.y ) / delta.x);
|
||||||
|
|
||||||
|
/* Create the intermediate point (that is to say creation of a new
|
||||||
|
* segment, beginning at the intermediate point.
|
||||||
|
*/
|
||||||
|
newPoint.x += aSegm->m_Start.x;
|
||||||
|
newPoint.y += aSegm->m_Start.y;
|
||||||
|
|
||||||
|
TRACK* newTrack = aSegm->Copy();
|
||||||
|
|
||||||
|
if( aItemsListPicker )
|
||||||
|
{
|
||||||
|
ITEM_PICKER picker( newTrack, UR_NEW );
|
||||||
|
aItemsListPicker->PushItem( picker );
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
DLIST<TRACK>* list = (DLIST<TRACK>*)aSegm->GetList();
|
||||||
|
wxASSERT( list );
|
||||||
|
list->Insert( newTrack, aSegm->Next() );
|
||||||
|
|
||||||
|
if( aItemsListPicker )
|
||||||
|
{
|
||||||
|
ITEM_PICKER picker( aSegm, UR_CHANGED );
|
||||||
|
picker.m_Link = aSegm->Copy();
|
||||||
|
aItemsListPicker->PushItem( picker );
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Correct pointer at the end of the new segment. */
|
||||||
|
newTrack->end = aSegm->end;
|
||||||
|
newTrack->SetState( END_ONPAD, aSegm->GetState( END_ONPAD ) );
|
||||||
|
|
||||||
|
/* Set connections info relative to the new point
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Old segment now ends at new point. */
|
||||||
|
aSegm->m_End = newPoint;
|
||||||
|
aSegm->end = newTrack;
|
||||||
|
aSegm->SetState( END_ONPAD, OFF );
|
||||||
|
|
||||||
|
/* The new segment begins at the new point. */
|
||||||
|
newTrack->m_Start = newPoint;
|
||||||
|
newTrack->start = aSegm;
|
||||||
|
newTrack->SetState( BEGIN_ONPAD, OFF );
|
||||||
|
|
||||||
|
D_PAD * pad = Locate_Pad_Connecte( aPcb, newTrack, START );
|
||||||
|
|
||||||
|
if ( pad )
|
||||||
|
{
|
||||||
|
newTrack->start = pad;
|
||||||
|
newTrack->SetState( BEGIN_ONPAD, ON );
|
||||||
|
aSegm->end = pad;
|
||||||
|
aSegm->SetState( END_ONPAD, ON );
|
||||||
|
}
|
||||||
|
|
||||||
|
aRefPoint = newPoint;
|
||||||
|
return newTrack;
|
||||||
|
}
|
||||||
|
|
|
@ -48,8 +48,7 @@ bool PCB_EDIT_FRAME::OnRightClick( const wxPoint& aMousePos, wxMenu* aPopMenu )
|
||||||
{
|
{
|
||||||
if( item && item->m_Flags )
|
if( item && item->m_Flags )
|
||||||
{
|
{
|
||||||
AddMenuItem( aPopMenu, ID_POPUP_CANCEL_CURRENT_COMMAND, _( "Cancel" ),
|
AddMenuItem( aPopMenu, ID_POPUP_CANCEL_CURRENT_COMMAND, _( "Cancel" ), KiBitmap( cancel_xpm ) );
|
||||||
KiBitmap( cancel_xpm ) );
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -167,8 +166,7 @@ bool PCB_EDIT_FRAME::OnRightClick( const wxPoint& aMousePos, wxMenu* aPopMenu )
|
||||||
HK_MOVE_ITEM );
|
HK_MOVE_ITEM );
|
||||||
AddMenuItem( aPopMenu, ID_POPUP_PCB_MOVE_DRAWING_REQUEST,
|
AddMenuItem( aPopMenu, ID_POPUP_PCB_MOVE_DRAWING_REQUEST,
|
||||||
msg, KiBitmap( move_xpm ) );
|
msg, KiBitmap( move_xpm ) );
|
||||||
AddMenuItem( aPopMenu, ID_POPUP_PCB_EDIT_DRAWING, _( "Edit Drawing" ),
|
AddMenuItem( aPopMenu, ID_POPUP_PCB_EDIT_DRAWING, _( "Edit Drawing" ), KiBitmap( edit_xpm ) );
|
||||||
KiBitmap( edit_xpm ) );
|
|
||||||
AddMenuItem( aPopMenu, ID_POPUP_PCB_DELETE_DRAWING,
|
AddMenuItem( aPopMenu, ID_POPUP_PCB_DELETE_DRAWING,
|
||||||
_( "Delete Drawing" ), KiBitmap( delete_xpm ) );
|
_( "Delete Drawing" ), KiBitmap( delete_xpm ) );
|
||||||
|
|
||||||
|
@ -295,8 +293,7 @@ bool PCB_EDIT_FRAME::OnRightClick( const wxPoint& aMousePos, wxMenu* aPopMenu )
|
||||||
case ID_TRACK_BUTT:
|
case ID_TRACK_BUTT:
|
||||||
if ( ! locate_track ) // This menu is already added when a track is located
|
if ( ! locate_track ) // This menu is already added when a track is located
|
||||||
AddMenuItem( aPopMenu, Append_Track_Width_List( GetBoard() ),
|
AddMenuItem( aPopMenu, Append_Track_Width_List( GetBoard() ),
|
||||||
ID_POPUP_PCB_SELECT_WIDTH, _( "Select Track Width" ),
|
ID_POPUP_PCB_SELECT_WIDTH, _( "Select Track Width" ), KiBitmap( width_track_xpm ) );
|
||||||
KiBitmap( width_track_xpm ) );
|
|
||||||
|
|
||||||
AddMenuItem( aPopMenu, ID_POPUP_PCB_SELECT_CU_LAYER,
|
AddMenuItem( aPopMenu, ID_POPUP_PCB_SELECT_CU_LAYER,
|
||||||
_( "Select Working Layer" ), KiBitmap( select_w_layer_xpm ) );
|
_( "Select Working Layer" ), KiBitmap( select_w_layer_xpm ) );
|
||||||
|
@ -378,8 +375,7 @@ bool PCB_EDIT_FRAME::OnRightClick( const wxPoint& aMousePos, wxMenu* aPopMenu )
|
||||||
*/
|
*/
|
||||||
void PCB_EDIT_FRAME::createPopUpBlockMenu( wxMenu* menu )
|
void PCB_EDIT_FRAME::createPopUpBlockMenu( wxMenu* menu )
|
||||||
{
|
{
|
||||||
AddMenuItem( menu, ID_POPUP_CANCEL_CURRENT_COMMAND, _( "Cancel Block" ),
|
AddMenuItem( menu, ID_POPUP_CANCEL_CURRENT_COMMAND, _( "Cancel Block" ), KiBitmap( cancel_xpm ) );
|
||||||
KiBitmap( cancel_xpm ) );
|
|
||||||
AddMenuItem( menu, ID_POPUP_ZOOM_BLOCK, _( "Zoom Block" ), KiBitmap( zoom_area_xpm ) );
|
AddMenuItem( menu, ID_POPUP_ZOOM_BLOCK, _( "Zoom Block" ), KiBitmap( zoom_area_xpm ) );
|
||||||
menu->AppendSeparator();
|
menu->AppendSeparator();
|
||||||
AddMenuItem( menu, ID_POPUP_PLACE_BLOCK, _( "Place Block" ), KiBitmap( apply_xpm ) );
|
AddMenuItem( menu, ID_POPUP_PLACE_BLOCK, _( "Place Block" ), KiBitmap( apply_xpm ) );
|
||||||
|
@ -408,8 +404,7 @@ void PCB_EDIT_FRAME::createPopupMenuForTracks( TRACK* Track, wxMenu* PopMenu )
|
||||||
{
|
{
|
||||||
if( Track->Type() == TYPE_VIA )
|
if( Track->Type() == TYPE_VIA )
|
||||||
{
|
{
|
||||||
AddMenuItem( PopMenu, ID_POPUP_PCB_MOVE_TRACK_NODE, _( "Drag Via" ),
|
AddMenuItem( PopMenu, ID_POPUP_PCB_MOVE_TRACK_NODE, _( "Drag Via" ), KiBitmap( move_xpm ) );
|
||||||
KiBitmap( move_xpm ) );
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -490,10 +485,10 @@ void PCB_EDIT_FRAME::createPopupMenuForTracks( TRACK* Track, wxMenu* PopMenu )
|
||||||
// Delete control:
|
// Delete control:
|
||||||
PopMenu->AppendSeparator();
|
PopMenu->AppendSeparator();
|
||||||
wxMenu* track_mnu = new wxMenu;
|
wxMenu* track_mnu = new wxMenu;
|
||||||
AddMenuItem( PopMenu, track_mnu, ID_POPUP_PCB_DELETE_TRACK_MNU, _( "Delete" ),
|
AddMenuItem( PopMenu, track_mnu, ID_POPUP_PCB_DELETE_TRACK_MNU, _( "Delete" ), KiBitmap( delete_xpm ) );
|
||||||
KiBitmap( delete_xpm ) );
|
|
||||||
|
|
||||||
msg = AddHotkeyName( Track->Type()==TYPE_VIA ? _( "Delete Via" ) : _( "Delete Segment" ),
|
msg = AddHotkeyName( Track->Type()==TYPE_VIA ?
|
||||||
|
_( "Delete Via" ) : _( "Delete Segment" ),
|
||||||
g_Board_Editor_Hokeys_Descr, HK_BACK_SPACE );
|
g_Board_Editor_Hokeys_Descr, HK_BACK_SPACE );
|
||||||
|
|
||||||
AddMenuItem( track_mnu, ID_POPUP_PCB_DELETE_TRACKSEG, msg, KiBitmap( delete_line_xpm ) );
|
AddMenuItem( track_mnu, ID_POPUP_PCB_DELETE_TRACKSEG, msg, KiBitmap( delete_line_xpm ) );
|
||||||
|
@ -502,8 +497,7 @@ void PCB_EDIT_FRAME::createPopupMenuForTracks( TRACK* Track, wxMenu* PopMenu )
|
||||||
{
|
{
|
||||||
msg = AddHotkeyName( _( "Delete Track" ), g_Board_Editor_Hokeys_Descr, HK_DELETE );
|
msg = AddHotkeyName( _( "Delete Track" ), g_Board_Editor_Hokeys_Descr, HK_DELETE );
|
||||||
AddMenuItem( track_mnu, ID_POPUP_PCB_DELETE_TRACK, msg, KiBitmap( delete_track_xpm ) );
|
AddMenuItem( track_mnu, ID_POPUP_PCB_DELETE_TRACK, msg, KiBitmap( delete_track_xpm ) );
|
||||||
AddMenuItem( track_mnu, ID_POPUP_PCB_DELETE_TRACKNET, _( "Delete Net" ),
|
AddMenuItem( track_mnu, ID_POPUP_PCB_DELETE_TRACKNET, _( "Delete Net" ), KiBitmap( delete_net_xpm ) );
|
||||||
KiBitmap( delete_net_xpm ) );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add global edition command
|
// Add global edition command
|
||||||
|
@ -517,8 +511,7 @@ void PCB_EDIT_FRAME::createPopupMenuForTracks( TRACK* Track, wxMenu* PopMenu )
|
||||||
// Add lock/unlock flags menu:
|
// Add lock/unlock flags menu:
|
||||||
track_mnu = new wxMenu;
|
track_mnu = new wxMenu;
|
||||||
|
|
||||||
AddMenuItem( PopMenu, track_mnu, ID_POPUP_PCB_SETFLAGS_TRACK_MNU, _( "Set Flags" ),
|
AddMenuItem( PopMenu, track_mnu, ID_POPUP_PCB_SETFLAGS_TRACK_MNU, _( "Set Flags" ), KiBitmap( flag_xpm ) );
|
||||||
KiBitmap( flag_xpm ) );
|
|
||||||
track_mnu->Append( ID_POPUP_PCB_LOCK_ON_TRACKSEG, _( "Locked: Yes" ), wxEmptyString, true );
|
track_mnu->Append( ID_POPUP_PCB_LOCK_ON_TRACKSEG, _( "Locked: Yes" ), wxEmptyString, true );
|
||||||
track_mnu->Append( ID_POPUP_PCB_LOCK_OFF_TRACKSEG, _( "Locked: No" ), wxEmptyString, true );
|
track_mnu->Append( ID_POPUP_PCB_LOCK_OFF_TRACKSEG, _( "Locked: No" ), wxEmptyString, true );
|
||||||
|
|
||||||
|
@ -564,19 +557,14 @@ void PCB_EDIT_FRAME::createPopUpMenuForZones( ZONE_CONTAINER* edge_zone, wxMenu*
|
||||||
|
|
||||||
AddMenuItem( aPopMenu, zones_menu, -1, _( "Zones" ), KiBitmap( add_zone_xpm ) );
|
AddMenuItem( aPopMenu, zones_menu, -1, _( "Zones" ), KiBitmap( add_zone_xpm ) );
|
||||||
|
|
||||||
// Use grid size because it is known
|
if( edge_zone->HitTestForCorner( GetScreen()->RefPos( true ) ) )
|
||||||
wxRealPoint grid = DrawPanel->GetGrid();
|
|
||||||
|
|
||||||
if( edge_zone->HitTestForCorner( GetScreen()->RefPos( true ),
|
|
||||||
wxRound( MIN( grid.x, grid.y ) ) ) )
|
|
||||||
{
|
{
|
||||||
AddMenuItem( zones_menu, ID_POPUP_PCB_MOVE_ZONE_CORNER,
|
AddMenuItem( zones_menu, ID_POPUP_PCB_MOVE_ZONE_CORNER,
|
||||||
_( "Move Corner" ), KiBitmap( move_xpm ) );
|
_( "Move Corner" ), KiBitmap( move_xpm ) );
|
||||||
AddMenuItem( zones_menu, ID_POPUP_PCB_DELETE_ZONE_CORNER,
|
AddMenuItem( zones_menu, ID_POPUP_PCB_DELETE_ZONE_CORNER,
|
||||||
_( "Delete Corner" ), KiBitmap( delete_xpm ) );
|
_( "Delete Corner" ), KiBitmap( delete_xpm ) );
|
||||||
}
|
}
|
||||||
else if( edge_zone->HitTestForEdge( GetScreen()->RefPos( true ),
|
else if( edge_zone->HitTestForEdge( GetScreen()->RefPos( true ) ) )
|
||||||
wxRound( MIN( grid.x, grid.y ) ) ) )
|
|
||||||
{
|
{
|
||||||
AddMenuItem( zones_menu, ID_POPUP_PCB_ADD_ZONE_CORNER,
|
AddMenuItem( zones_menu, ID_POPUP_PCB_ADD_ZONE_CORNER,
|
||||||
_( "Create Corner" ), KiBitmap( add_corner_xpm ) );
|
_( "Create Corner" ), KiBitmap( add_corner_xpm ) );
|
||||||
|
@ -594,8 +582,7 @@ void PCB_EDIT_FRAME::createPopUpMenuForZones( ZONE_CONTAINER* edge_zone, wxMenu*
|
||||||
_( "Add Cutout Area" ), KiBitmap( add_zone_cutout_xpm ) );
|
_( "Add Cutout Area" ), KiBitmap( add_zone_cutout_xpm ) );
|
||||||
zones_menu->AppendSeparator();
|
zones_menu->AppendSeparator();
|
||||||
|
|
||||||
AddMenuItem( zones_menu, ID_POPUP_PCB_FILL_ZONE, _( "Fill Zone" ),
|
AddMenuItem( zones_menu, ID_POPUP_PCB_FILL_ZONE, _( "Fill Zone" ), KiBitmap( fill_zone_xpm ) );
|
||||||
KiBitmap( fill_zone_xpm ) );
|
|
||||||
|
|
||||||
if( edge_zone->m_FilledPolysList.size() > 0 )
|
if( edge_zone->m_FilledPolysList.size() > 0 )
|
||||||
{
|
{
|
||||||
|
@ -658,8 +645,7 @@ void PCB_EDIT_FRAME::createPopUpMenuForFootprints( MODULE* aModule, wxMenu* menu
|
||||||
if( !flags )
|
if( !flags )
|
||||||
{
|
{
|
||||||
msg = AddHotkeyName( _( "Edit" ), g_Board_Editor_Hokeys_Descr, HK_EDIT_ITEM );
|
msg = AddHotkeyName( _( "Edit" ), g_Board_Editor_Hokeys_Descr, HK_EDIT_ITEM );
|
||||||
AddMenuItem( sub_menu_footprint, ID_POPUP_PCB_EDIT_MODULE, msg,
|
AddMenuItem( sub_menu_footprint, ID_POPUP_PCB_EDIT_MODULE, msg, KiBitmap( edit_module_xpm ) );
|
||||||
KiBitmap( edit_module_xpm ) );
|
|
||||||
sub_menu_footprint->AppendSeparator();
|
sub_menu_footprint->AppendSeparator();
|
||||||
AddMenuItem( sub_menu_footprint, ID_POPUP_PCB_DELETE_MODULE,
|
AddMenuItem( sub_menu_footprint, ID_POPUP_PCB_DELETE_MODULE,
|
||||||
_( "Delete Module" ), KiBitmap( delete_module_xpm ) );
|
_( "Delete Module" ), KiBitmap( delete_module_xpm ) );
|
||||||
|
@ -739,10 +725,8 @@ void PCB_EDIT_FRAME::createPopUpMenuForFpPads( D_PAD* Pad, wxMenu* menu )
|
||||||
sub_menu_Pad = new wxMenu;
|
sub_menu_Pad = new wxMenu;
|
||||||
AddMenuItem( menu, sub_menu_Pad, -1, msg, KiBitmap( pad_xpm ) );
|
AddMenuItem( menu, sub_menu_Pad, -1, msg, KiBitmap( pad_xpm ) );
|
||||||
|
|
||||||
AddMenuItem( sub_menu_Pad, ID_POPUP_PCB_MOVE_PAD_REQUEST, _( "Move" ),
|
AddMenuItem( sub_menu_Pad, ID_POPUP_PCB_MOVE_PAD_REQUEST, _( "Move" ), KiBitmap( move_pad_xpm ) );
|
||||||
KiBitmap( move_pad_xpm ) );
|
AddMenuItem( sub_menu_Pad, ID_POPUP_PCB_DRAG_PAD_REQUEST, _( "Drag" ), KiBitmap( drag_pad_xpm ) );
|
||||||
AddMenuItem( sub_menu_Pad, ID_POPUP_PCB_DRAG_PAD_REQUEST, _( "Drag" ),
|
|
||||||
KiBitmap( drag_pad_xpm ) );
|
|
||||||
|
|
||||||
AddMenuItem( sub_menu_Pad, ID_POPUP_PCB_EDIT_PAD, _( "Edit" ), KiBitmap( options_pad_xpm ) );
|
AddMenuItem( sub_menu_Pad, ID_POPUP_PCB_EDIT_PAD, _( "Edit" ), KiBitmap( options_pad_xpm ) );
|
||||||
sub_menu_Pad->AppendSeparator();
|
sub_menu_Pad->AppendSeparator();
|
||||||
|
@ -806,17 +790,14 @@ void PCB_EDIT_FRAME::createPopUpMenuForTexts( TEXTE_PCB* Text, wxMenu* menu )
|
||||||
_( "Reset Size" ), KiBitmap( reset_text_xpm ) );
|
_( "Reset Size" ), KiBitmap( reset_text_xpm ) );
|
||||||
|
|
||||||
sub_menu_Text->AppendSeparator();
|
sub_menu_Text->AppendSeparator();
|
||||||
AddMenuItem( sub_menu_Text, ID_POPUP_PCB_DELETE_TEXTEPCB, _( "Delete" ),
|
AddMenuItem( sub_menu_Text, ID_POPUP_PCB_DELETE_TEXTEPCB, _( "Delete" ), KiBitmap( delete_text_xpm ) );
|
||||||
KiBitmap( delete_text_xpm ) );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void PCB_EDIT_FRAME::createPopUpMenuForMarkers( MARKER_PCB* aMarker, wxMenu* aPopMenu )
|
void PCB_EDIT_FRAME::createPopUpMenuForMarkers( MARKER_PCB* aMarker, wxMenu* aPopMenu )
|
||||||
{
|
{
|
||||||
AddMenuItem( aPopMenu, ID_POPUP_PCB_DELETE_MARKER, _( "Delete Marker" ),
|
AddMenuItem( aPopMenu, ID_POPUP_PCB_DELETE_MARKER, _( "Delete Marker" ), KiBitmap( delete_xpm ) );
|
||||||
KiBitmap( delete_xpm ) );
|
AddMenuItem( aPopMenu, ID_POPUP_PCB_GETINFO_MARKER, _( "Marker Error Info" ), KiBitmap( info_xpm ) );
|
||||||
AddMenuItem( aPopMenu, ID_POPUP_PCB_GETINFO_MARKER, _( "Marker Error Info" ),
|
|
||||||
KiBitmap( info_xpm ) );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -277,11 +277,10 @@ PCB_EDIT_FRAME::PCB_EDIT_FRAME( wxWindow* parent, const wxString& title,
|
||||||
m_HotkeysZoomAndGridList = g_Board_Editor_Hokeys_Descr;
|
m_HotkeysZoomAndGridList = g_Board_Editor_Hokeys_Descr;
|
||||||
|
|
||||||
m_RecordingMacros = -1;
|
m_RecordingMacros = -1;
|
||||||
|
|
||||||
for ( int i = 0; i < 10; i++ )
|
for ( int i = 0; i < 10; i++ )
|
||||||
m_Macros[i].m_Record.clear();
|
m_Macros[i].m_Record.clear();
|
||||||
|
|
||||||
SetBoard( new BOARD( NULL ) );
|
SetBoard( new BOARD( NULL, this ) );
|
||||||
|
|
||||||
// Create the PCB_LAYER_WIDGET *after* SetBoard():
|
// Create the PCB_LAYER_WIDGET *after* SetBoard():
|
||||||
|
|
||||||
|
@ -418,7 +417,6 @@ PCB_EDIT_FRAME::PCB_EDIT_FRAME( wxWindow* parent, const wxString& title,
|
||||||
PCB_EDIT_FRAME::~PCB_EDIT_FRAME()
|
PCB_EDIT_FRAME::~PCB_EDIT_FRAME()
|
||||||
{
|
{
|
||||||
m_RecordingMacros = -1;
|
m_RecordingMacros = -1;
|
||||||
|
|
||||||
for( int i = 0; i < 10; i++ )
|
for( int i = 0; i < 10; i++ )
|
||||||
m_Macros[i].m_Record.clear();
|
m_Macros[i].m_Record.clear();
|
||||||
|
|
||||||
|
|
209
pcbnew/protos.h
209
pcbnew/protos.h
|
@ -1,11 +1,16 @@
|
||||||
/**
|
/***********/
|
||||||
* @file pcbnew/protos.h
|
/* protos.h */
|
||||||
*/
|
/***********/
|
||||||
|
|
||||||
#ifndef PROTO_H
|
#ifndef PROTO_H
|
||||||
#define PROTO_H
|
#define PROTO_H
|
||||||
|
|
||||||
|
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
|
||||||
|
class COMMAND;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Function SwapData
|
* Function SwapData
|
||||||
* Used in undo / redo command:
|
* Used in undo / redo command:
|
||||||
|
@ -17,6 +22,24 @@
|
||||||
void SwapData( BOARD_ITEM* aItem, BOARD_ITEM* aImage );
|
void SwapData( BOARD_ITEM* aItem, BOARD_ITEM* aImage );
|
||||||
|
|
||||||
|
|
||||||
|
/*******************/
|
||||||
|
/* PAD_CONNECT.CPP */
|
||||||
|
/*******************/
|
||||||
|
|
||||||
|
class D_PAD;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function CreateSortedPadListByXCoord
|
||||||
|
* first empties then fills the vector with all pads and sorts them by
|
||||||
|
* increasing x coordinate. The vector only holds pointers to the pads and
|
||||||
|
* those pointers are only references to pads which are owned by the BOARD
|
||||||
|
* through other links.
|
||||||
|
* @param aBoard Which board to gather pads from.
|
||||||
|
* @param aVector Where to put the pad pointers.
|
||||||
|
*/
|
||||||
|
void CreateSortedPadListByXCoord( BOARD* aBoard, std::vector<D_PAD*>* aVector );
|
||||||
|
|
||||||
|
|
||||||
/***************/
|
/***************/
|
||||||
/* TRPISTE.CPP */
|
/* TRPISTE.CPP */
|
||||||
/***************/
|
/***************/
|
||||||
|
@ -43,6 +66,31 @@ void DrawTraces( EDA_DRAW_PANEL* panel,
|
||||||
/* LOCATE.CPP : */
|
/* LOCATE.CPP : */
|
||||||
/****************/
|
/****************/
|
||||||
|
|
||||||
|
/* Find a pad by it's name om the module. */
|
||||||
|
TRACK* Locate_Via( BOARD* Pcb, const wxPoint& pos, int layer = -1 );
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function Locate_Via_Area
|
||||||
|
* finds the first SEGVIA which covers the given aPos with a matching layer.
|
||||||
|
* @param aStart The starting TRACK or SEGVIA in the BOARD's list.
|
||||||
|
* @param aPos The wxPoint to HitTest() against.
|
||||||
|
* @param aLayer The layer to match, pass -1 for a don't care.
|
||||||
|
* @return TRACK* - actually a SEGVIA* if found, else NULL.
|
||||||
|
*/
|
||||||
|
TRACK* Locate_Via_Area( TRACK* aStart, const wxPoint& aPos, int aLayer = ALL_LAYERS );
|
||||||
|
|
||||||
|
/* Locates the center through the point x, y, on layer data
|
||||||
|
* by masquelayer.
|
||||||
|
* Search is done to address start_adr has end_adr (not included)
|
||||||
|
*/
|
||||||
|
TRACK* Fast_Locate_Via( TRACK* start_adr, TRACK* end_adr, const wxPoint& pos, int masquelayer );
|
||||||
|
|
||||||
|
/* Locates the center through the point x, y, on layer data
|
||||||
|
* by masquelayer.
|
||||||
|
* Search is done to address start_adr has end_adr (not included)
|
||||||
|
*/
|
||||||
|
TRACK* GetTrace( TRACK* start_adr, TRACK* end_adr, const wxPoint& ref_pos, int masquelayer );
|
||||||
|
|
||||||
/* Search for segment connected to the segment edge by
|
/* Search for segment connected to the segment edge by
|
||||||
* Ptr_piste:
|
* Ptr_piste:
|
||||||
* If int = START, the point of beginning of the segment is used
|
* If int = START, the point of beginning of the segment is used
|
||||||
|
@ -52,6 +100,86 @@ void DrawTraces( EDA_DRAW_PANEL* panel,
|
||||||
*/
|
*/
|
||||||
TRACK* GetConnectedTrace( TRACK* aTrace, TRACK* pt_base, TRACK* pt_lim, int extr );
|
TRACK* GetConnectedTrace( TRACK* aTrace, TRACK* pt_base, TRACK* pt_lim, int extr );
|
||||||
|
|
||||||
|
/*
|
||||||
|
* 1 - Locate segment of track leading from the mouse.
|
||||||
|
* 2 - Locate segment of track point by point.
|
||||||
|
* Ref_pX, ref_pY.
|
||||||
|
*
|
||||||
|
* If layer <0 the layer is not tested.
|
||||||
|
*
|
||||||
|
* The search begins to address start_adresse
|
||||||
|
*/
|
||||||
|
TRACK* GetTrace( BOARD* aPcb, TRACK* start_adresse, const wxPoint& ref_pos, int layer );
|
||||||
|
|
||||||
|
/* Locate pad connected to the beginning or end of a segment
|
||||||
|
* Input: pointer to the segment, and flag = START or END
|
||||||
|
* Returns:
|
||||||
|
* A pointer to the description of the patch if pad was found.
|
||||||
|
* NULL pointer if pad was not found.
|
||||||
|
*/
|
||||||
|
D_PAD* Locate_Pad_Connecte( BOARD* aPcb, TRACK* ptr_segment, int extr );
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Locate pad pointed to by the coordinate ref_pX,, ref_pY or the current
|
||||||
|
* cursor position, search done on all tracks.
|
||||||
|
* Entry:
|
||||||
|
* - Mouse coord (Curseur_X and Curseur_Y)
|
||||||
|
* Or ref_pX, ref_pY
|
||||||
|
* Returns:
|
||||||
|
* Pointer to the pad if found
|
||||||
|
* NULL pointer if pad not found
|
||||||
|
*/
|
||||||
|
D_PAD* Locate_Any_Pad( BOARD* aPcb, const wxPoint& aPosition, int aLayerMask = ALL_LAYERS );
|
||||||
|
|
||||||
|
/* Locate pad pointed to by the coordinate ref_pX,, ref_pY or the cursor
|
||||||
|
* position of the current footprint.
|
||||||
|
* Input:
|
||||||
|
* - The module to search.
|
||||||
|
* - Layer to search or -1 to search all layers.
|
||||||
|
* Returns:
|
||||||
|
* A pointer to the pad if found otherwise NULL.
|
||||||
|
*/
|
||||||
|
D_PAD* Locate_Pads( MODULE* Module, const wxPoint& ref_pos, int layer );
|
||||||
|
|
||||||
|
/* Locate a footprint by its bounding rectangle. */
|
||||||
|
MODULE* Locate_Prefered_Module( BOARD* aPcb, const wxPoint& aPosition, int aActiveLayer,
|
||||||
|
bool aVisibleOnly, bool aIgnoreLocked = false );
|
||||||
|
|
||||||
|
/* Locate a pad pointed to by the cursor on the footprint.
|
||||||
|
* Module.
|
||||||
|
* Input:
|
||||||
|
* - Module to search.
|
||||||
|
* Returns:
|
||||||
|
* A pointer to the pad if found otherwise NULL.
|
||||||
|
*/
|
||||||
|
D_PAD* Locate_Pads( MODULE* Module, int typeloc );
|
||||||
|
|
||||||
|
/* Locate a trace segment at the current cursor position.
|
||||||
|
* The search begins to address start_adresse.
|
||||||
|
*/
|
||||||
|
TRACK* GetTrace( TRACK* start_adresse, int typeloc );
|
||||||
|
|
||||||
|
DRAWSEGMENT* Locate_Segment_Pcb( BOARD* Pcb, int LayerSearch, int typeloc );
|
||||||
|
|
||||||
|
/* Locate pad containing the point px, py, layer on layer.
|
||||||
|
*
|
||||||
|
* The list of pads must already exist.
|
||||||
|
*
|
||||||
|
* Returns:
|
||||||
|
* Pointer to the pad if found, otherwise NULL.
|
||||||
|
*/
|
||||||
|
D_PAD* Fast_Locate_Pad_Connecte( BOARD* Pcb, const wxPoint& ref_pos, int layer );
|
||||||
|
|
||||||
|
/*
|
||||||
|
* 1 - Locate trace segment at the current cursor position.
|
||||||
|
* 2 - Locate trace segment at the given coordinates ref_pos.
|
||||||
|
*
|
||||||
|
* If layer == -1, check all layers.
|
||||||
|
*
|
||||||
|
* The search begins to address start_adresse
|
||||||
|
*/
|
||||||
|
TRACK* Locate_Zone( TRACK* start_adresse, const wxPoint& ref_pos, int layer );
|
||||||
|
|
||||||
|
|
||||||
/*************/
|
/*************/
|
||||||
/* MODULES.C */
|
/* MODULES.C */
|
||||||
|
@ -76,9 +204,84 @@ void ShowNewTrackWhenMovingCursor( EDA_DRAW_PANEL* aPanel, wxDC* aDC, const wxPo
|
||||||
void CalculateSegmentEndPoint( const wxPoint& aPosition, int ox, int oy, int* fx, int* fy );
|
void CalculateSegmentEndPoint( const wxPoint& aPosition, int ox, int oy, int* fx, int* fy );
|
||||||
|
|
||||||
|
|
||||||
|
/*****************/
|
||||||
|
/* TRACK.CPP : */
|
||||||
|
/*****************/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function MarkTrace
|
||||||
|
* marks a chain of track segments, connected to aTrackList.
|
||||||
|
* Each segment is marked by setting the BUSY bit into m_Flags. Electrical
|
||||||
|
* continuity is detected by walking each segment, and finally the segments
|
||||||
|
* are rearranged into a contiguous chain within the given list.
|
||||||
|
*
|
||||||
|
* @param aPcb = the board to analyze
|
||||||
|
* @param aStartSegm - The first interesting segment within a list of track
|
||||||
|
* segment of aPcb
|
||||||
|
* @param aSegmCount = a pointer to an integer where to return the number of
|
||||||
|
* interesting segments
|
||||||
|
* @param aTrackLen = a pointer to an integer where to return the lenght of the
|
||||||
|
* track
|
||||||
|
* @param aLengthDie = a pointer to an integer where to return the extra lengths inside
|
||||||
|
* integrated circuits from the pads connected to this track to the
|
||||||
|
* die (if any)
|
||||||
|
* @param aReorder = true for reorder the interesting segments (useful for
|
||||||
|
* track edition/deletion) in this case the flag BUSY is
|
||||||
|
* set (the user is responsible of flag clearing). False
|
||||||
|
* for no reorder : useful when we want just calculate the
|
||||||
|
* track length in this case, flags are reset
|
||||||
|
* @return TRACK* the first in the chain of interesting segments.
|
||||||
|
*/
|
||||||
|
TRACK* MarkTrace( BOARD* aPcb,
|
||||||
|
TRACK* aStartSegm,
|
||||||
|
int* aSegmCount,
|
||||||
|
int* aTrackLen,
|
||||||
|
int* aLengthDie,
|
||||||
|
bool aReorder );
|
||||||
|
|
||||||
|
/* Calculate end coordinate of a trace.
|
||||||
|
* Returns 1 if OK, 0 if trace looped back on itself.
|
||||||
|
* The coord are returned StartTrack-> ox, oy
|
||||||
|
* And EndTrack-> fx, fy if OK
|
||||||
|
* The segments are drawn consecutively.
|
||||||
|
*/
|
||||||
|
int ReturnEndsTrack( TRACK* RefTrack, int NbSegm, TRACK** StartTrack, TRACK** EndTrack );
|
||||||
|
|
||||||
|
|
||||||
/***************/
|
/***************/
|
||||||
/***************/
|
/***************/
|
||||||
|
|
||||||
|
/* Routine to find the point "attachment" at the end of a trace.
|
||||||
|
* This may be a PAD or another trace segment.
|
||||||
|
* Returns:
|
||||||
|
* - Pointer to the PAD or:
|
||||||
|
* - Pointer to the segment or:
|
||||||
|
* - NULL
|
||||||
|
* Parameters:
|
||||||
|
* - aPos - coordinate point test
|
||||||
|
* ALayerMask of mask layers to be tested
|
||||||
|
*/
|
||||||
|
BOARD_ITEM* LocateLockPoint( BOARD* aPcb, wxPoint aPos, int aLayerMask );
|
||||||
|
|
||||||
|
/* Create an intermediate point on a segment
|
||||||
|
* aSegm segment is broken into 2 segments connecting point pX, pY
|
||||||
|
* After insertion:
|
||||||
|
* The new segment starts from to new point, and ends to initial aSegm ending point
|
||||||
|
* the old segment aSegm ends to new point
|
||||||
|
* Returns:
|
||||||
|
* NULL if no new point (ie if aRefPoint already corresponded at one end of aSegm
|
||||||
|
* or
|
||||||
|
* Pointer to the segment created
|
||||||
|
* Returns the exact value of aRefPoint
|
||||||
|
* If aSegm points to a via:
|
||||||
|
* Returns the exact value of aRefPoint and a pointer to the via,
|
||||||
|
* But does not create extra point
|
||||||
|
*/
|
||||||
|
TRACK* CreateLockPoint( BOARD* aPcb,
|
||||||
|
wxPoint& aRefPoint,
|
||||||
|
TRACK* aSegm,
|
||||||
|
PICKED_ITEMS_LIST* aItemsListPicker );
|
||||||
|
|
||||||
|
|
||||||
/****************/
|
/****************/
|
||||||
/* CONTROLE.CPP */
|
/* CONTROLE.CPP */
|
||||||
|
|
|
@ -1268,12 +1268,14 @@ static void AddNewTrace( PCB_EDIT_FRAME* pcbframe, wxDC* DC )
|
||||||
g_CurrentTrackList.PushBack( newTrack );
|
g_CurrentTrackList.PushBack( newTrack );
|
||||||
}
|
}
|
||||||
|
|
||||||
g_FirstTrackSegment->start = pcbframe->GetBoard()->GetPad( g_FirstTrackSegment, START );
|
g_FirstTrackSegment->start = Locate_Pad_Connecte( pcbframe->GetBoard(),
|
||||||
|
g_FirstTrackSegment, START );
|
||||||
|
|
||||||
if( g_FirstTrackSegment->start )
|
if( g_FirstTrackSegment->start )
|
||||||
g_FirstTrackSegment->SetState( BEGIN_ONPAD, ON );
|
g_FirstTrackSegment->SetState( BEGIN_ONPAD, ON );
|
||||||
|
|
||||||
g_CurrentTrackSegment->end = pcbframe->GetBoard()->GetPad( g_CurrentTrackSegment, END );
|
g_CurrentTrackSegment->end = Locate_Pad_Connecte( pcbframe->GetBoard(),
|
||||||
|
g_CurrentTrackSegment, END );
|
||||||
|
|
||||||
if( g_CurrentTrackSegment->end )
|
if( g_CurrentTrackSegment->end )
|
||||||
g_CurrentTrackSegment->SetState( END_ONPAD, ON );
|
g_CurrentTrackSegment->SetState( END_ONPAD, ON );
|
||||||
|
|
|
@ -10,6 +10,8 @@
|
||||||
#include "protos.h"
|
#include "protos.h"
|
||||||
|
|
||||||
static void ListSetState( EDA_ITEM* Start, int NbItem, int State, int onoff );
|
static void ListSetState( EDA_ITEM* Start, int NbItem, int State, int onoff );
|
||||||
|
extern int ReturnEndsTrack( TRACK* RefTrack, int NbSegm,
|
||||||
|
TRACK** StartTrack, TRACK** EndTrack );
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -52,7 +54,7 @@ int PCB_EDIT_FRAME::EraseRedundantTrack( wxDC* aDC,
|
||||||
if( aNewTrack->Type() == TYPE_VIA && ( aNewTrackSegmentsCount > 1 ) )
|
if( aNewTrack->Type() == TYPE_VIA && ( aNewTrackSegmentsCount > 1 ) )
|
||||||
aNewTrack = aNewTrack->Next();
|
aNewTrack = aNewTrack->Next();
|
||||||
|
|
||||||
aNewTrack = GetBoard()->MarkTrace( aNewTrack, &aNewTrackSegmentsCount, NULL, NULL, true );
|
aNewTrack = MarkTrace( GetBoard(), aNewTrack, &aNewTrackSegmentsCount, NULL, NULL, true );
|
||||||
wxASSERT( aNewTrack );
|
wxASSERT( aNewTrack );
|
||||||
|
|
||||||
#if 0 && defined(DEBUG)
|
#if 0 && defined(DEBUG)
|
||||||
|
@ -90,7 +92,7 @@ int PCB_EDIT_FRAME::EraseRedundantTrack( wxDC* aDC,
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if( aNewTrack->GetEndSegments( aNewTrackSegmentsCount, &StartTrack, &EndTrack ) == 0 )
|
if( ReturnEndsTrack( aNewTrack, aNewTrackSegmentsCount, &StartTrack, &EndTrack ) == 0 )
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if( ( StartTrack == NULL ) || ( EndTrack == NULL ) )
|
if( ( StartTrack == NULL ) || ( EndTrack == NULL ) )
|
||||||
|
@ -108,7 +110,7 @@ int PCB_EDIT_FRAME::EraseRedundantTrack( wxDC* aDC,
|
||||||
endmasklayer = EndTrack->ReturnMaskLayer();
|
endmasklayer = EndTrack->ReturnMaskLayer();
|
||||||
|
|
||||||
/* There may be a via or a pad on the end points. */
|
/* There may be a via or a pad on the end points. */
|
||||||
pt_segm = m_Pcb->m_Track->GetVia( NULL, start, startmasklayer );
|
pt_segm = Fast_Locate_Via( m_Pcb->m_Track, NULL, start, startmasklayer );
|
||||||
|
|
||||||
if( pt_segm )
|
if( pt_segm )
|
||||||
startmasklayer |= pt_segm->ReturnMaskLayer();
|
startmasklayer |= pt_segm->ReturnMaskLayer();
|
||||||
|
@ -120,7 +122,7 @@ int PCB_EDIT_FRAME::EraseRedundantTrack( wxDC* aDC,
|
||||||
startmasklayer |= pt_pad->m_layerMask;
|
startmasklayer |= pt_pad->m_layerMask;
|
||||||
}
|
}
|
||||||
|
|
||||||
pt_segm = m_Pcb->m_Track->GetVia( NULL, end, endmasklayer );
|
pt_segm = Fast_Locate_Via( m_Pcb->m_Track, NULL, end, endmasklayer );
|
||||||
|
|
||||||
if( pt_segm )
|
if( pt_segm )
|
||||||
endmasklayer |= pt_segm->ReturnMaskLayer();
|
endmasklayer |= pt_segm->ReturnMaskLayer();
|
||||||
|
@ -139,7 +141,7 @@ int PCB_EDIT_FRAME::EraseRedundantTrack( wxDC* aDC,
|
||||||
/* A segment must be connected to the starting point, otherwise
|
/* A segment must be connected to the starting point, otherwise
|
||||||
* it is unnecessary to analyze the other point
|
* it is unnecessary to analyze the other point
|
||||||
*/
|
*/
|
||||||
pt_segm = GetTraceByEndPoint( bufStart, bufEnd, start, startmasklayer );
|
pt_segm = GetTrace( bufStart, bufEnd, start, startmasklayer );
|
||||||
|
|
||||||
if( pt_segm == NULL ) /* Not connected to the track starting point. */
|
if( pt_segm == NULL ) /* Not connected to the track starting point. */
|
||||||
{
|
{
|
||||||
|
@ -154,7 +156,7 @@ int PCB_EDIT_FRAME::EraseRedundantTrack( wxDC* aDC,
|
||||||
*/
|
*/
|
||||||
for( pt_del = bufStart, nbconnect = 0; ; )
|
for( pt_del = bufStart, nbconnect = 0; ; )
|
||||||
{
|
{
|
||||||
pt_segm = GetTraceByEndPoint( pt_del, bufEnd, end, endmasklayer );
|
pt_segm = GetTrace( pt_del, bufEnd, end, endmasklayer );
|
||||||
|
|
||||||
if( pt_segm == NULL )
|
if( pt_segm == NULL )
|
||||||
break;
|
break;
|
||||||
|
@ -209,7 +211,7 @@ int PCB_EDIT_FRAME::EraseRedundantTrack( wxDC* aDC,
|
||||||
nbconnect--;
|
nbconnect--;
|
||||||
pt_del->SetState( IS_LINKED, OFF );
|
pt_del->SetState( IS_LINKED, OFF );
|
||||||
|
|
||||||
pt_del = GetBoard()->MarkTrace( pt_del, &nb_segm, NULL, NULL, true );
|
pt_del = MarkTrace( GetBoard(), pt_del, &nb_segm, NULL, NULL, true );
|
||||||
|
|
||||||
/* Test if the marked track is redundant, i.e. if one of marked segments
|
/* Test if the marked track is redundant, i.e. if one of marked segments
|
||||||
* is connected to the starting point of the new track.
|
* is connected to the starting point of the new track.
|
||||||
|
|
|
@ -0,0 +1,541 @@
|
||||||
|
/*****************
|
||||||
|
* track.cpp
|
||||||
|
*****************/
|
||||||
|
|
||||||
|
#include "fctsys.h"
|
||||||
|
|
||||||
|
#include "common.h"
|
||||||
|
#include "pcbnew.h"
|
||||||
|
|
||||||
|
#include "protos.h"
|
||||||
|
|
||||||
|
/* Functions to recognize a track.
|
||||||
|
* A track is a list of connected segments (or/and vias)
|
||||||
|
* from a starting to an ending point
|
||||||
|
* starting and ending points are a pad or a point with more than 2 segments
|
||||||
|
*connected
|
||||||
|
* (and obviously a dangling segment end)
|
||||||
|
*/
|
||||||
|
|
||||||
|
typedef std::vector<TRACK*> TRACK_PTRS; // buffer of item candidates when
|
||||||
|
// search for items on the same track
|
||||||
|
|
||||||
|
|
||||||
|
/* Local functions */
|
||||||
|
static void ChainMarkedSegments( BOARD* Pcb,
|
||||||
|
wxPoint ref_pos,
|
||||||
|
int masklayer,
|
||||||
|
TRACK_PTRS* aList );
|
||||||
|
|
||||||
|
|
||||||
|
TRACK* MarkTrace( BOARD* aPcb,
|
||||||
|
TRACK* aStartSegm,
|
||||||
|
int* aSegmCount,
|
||||||
|
int* aTrackLen,
|
||||||
|
int* aLengthDie,
|
||||||
|
bool aReorder )
|
||||||
|
{
|
||||||
|
int NbSegmBusy;
|
||||||
|
|
||||||
|
TRACK_PTRS trackList;
|
||||||
|
|
||||||
|
if( aSegmCount )
|
||||||
|
*aSegmCount = 0;
|
||||||
|
|
||||||
|
if( aTrackLen )
|
||||||
|
*aTrackLen = 0;
|
||||||
|
|
||||||
|
if( aStartSegm == NULL )
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
// Ensure the flag BUSY of all tracks of the board is cleared
|
||||||
|
// because we use it to mark segments of the track
|
||||||
|
for( TRACK* track = aPcb->m_Track; track; track = track->Next() )
|
||||||
|
track->SetState( BUSY, OFF );
|
||||||
|
|
||||||
|
/* Set flags of the initial track segment */
|
||||||
|
aStartSegm->SetState( BUSY, ON );
|
||||||
|
int layerMask = aStartSegm->ReturnMaskLayer();
|
||||||
|
|
||||||
|
trackList.push_back( aStartSegm );
|
||||||
|
|
||||||
|
/* Examine the initial track segment : if it is really a segment, this is
|
||||||
|
* easy.
|
||||||
|
* If it is a via, one must search for connected segments.
|
||||||
|
* If <=2, this via connect 2 segments (or is connected to only one
|
||||||
|
* segment) and this via and these 2 segments are a part of a track.
|
||||||
|
* If > 2 only this via is flagged (the track has only this via)
|
||||||
|
*/
|
||||||
|
if( aStartSegm->Type() == TYPE_VIA )
|
||||||
|
{
|
||||||
|
TRACK* Segm1, * Segm2 = NULL, * Segm3 = NULL;
|
||||||
|
Segm1 = GetTrace( aPcb->m_Track, NULL, aStartSegm->m_Start, layerMask );
|
||||||
|
|
||||||
|
if( Segm1 )
|
||||||
|
{
|
||||||
|
Segm2 = GetTrace( Segm1->Next(), NULL, aStartSegm->m_Start, layerMask );
|
||||||
|
}
|
||||||
|
|
||||||
|
if( Segm2 )
|
||||||
|
{
|
||||||
|
Segm3 = GetTrace( Segm2->Next(), NULL, aStartSegm->m_Start, layerMask );
|
||||||
|
}
|
||||||
|
|
||||||
|
if( Segm3 ) // More than 2 segments are connected to this via. the track" is only this via
|
||||||
|
{
|
||||||
|
if( aSegmCount )
|
||||||
|
*aSegmCount = 1;
|
||||||
|
|
||||||
|
return aStartSegm;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( Segm1 ) // search for others segments connected to the initial segment start point
|
||||||
|
{
|
||||||
|
layerMask = Segm1->ReturnMaskLayer();
|
||||||
|
ChainMarkedSegments( aPcb, aStartSegm->m_Start, layerMask, &trackList );
|
||||||
|
}
|
||||||
|
|
||||||
|
if( Segm2 ) // search for others segments connected to the initial segment end point
|
||||||
|
{
|
||||||
|
layerMask = Segm2->ReturnMaskLayer();
|
||||||
|
ChainMarkedSegments( aPcb, aStartSegm->m_Start, layerMask, &trackList );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else // mark the chain using both ends of the initial segment
|
||||||
|
{
|
||||||
|
ChainMarkedSegments( aPcb, aStartSegm->m_Start, layerMask, &trackList );
|
||||||
|
ChainMarkedSegments( aPcb, aStartSegm->m_End, layerMask, &trackList );
|
||||||
|
}
|
||||||
|
|
||||||
|
// Now examine selected vias and flag them if they are on the track
|
||||||
|
// If a via is connected to only one or 2 segments, it is flagged (is on
|
||||||
|
// the track)
|
||||||
|
// If a via is connected to more than 2 segments, it is a track end, and it
|
||||||
|
// is removed from the list
|
||||||
|
// go through the list backwards.
|
||||||
|
for( int i = trackList.size() - 1; i>=0; --i )
|
||||||
|
{
|
||||||
|
TRACK* via = trackList[i];
|
||||||
|
|
||||||
|
if( via->Type() != TYPE_VIA )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if( via == aStartSegm )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
via->SetState( BUSY, ON ); // Try to flag it. the flag will be cleared later if needed
|
||||||
|
|
||||||
|
layerMask = via->ReturnMaskLayer();
|
||||||
|
|
||||||
|
TRACK* track = GetTrace( aPcb->m_Track, NULL, via->m_Start, layerMask );
|
||||||
|
|
||||||
|
// GetTrace does not consider tracks flagged BUSY.
|
||||||
|
// So if no connected track found, this via is on the current track
|
||||||
|
// only: keep it
|
||||||
|
if( track == NULL )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
/* If a track is found, this via connects also others segments of an
|
||||||
|
* other track. This case happens when the vias ends the selected
|
||||||
|
* track but must we consider this via is on the selected track, or
|
||||||
|
* on an other track.
|
||||||
|
* (this is important when selecting a track for deletion: must this
|
||||||
|
* via be deleted or not?)
|
||||||
|
* We consider here this via on the track if others segment connected
|
||||||
|
* to this via remain connected when removing this via.
|
||||||
|
* We search for all others segment connected together:
|
||||||
|
* if there are on the same layer, the via is on the selected track
|
||||||
|
* if there are on different layers, the via is on an other track
|
||||||
|
*/
|
||||||
|
int layer = track->GetLayer();
|
||||||
|
|
||||||
|
while( ( track = GetTrace( track->Next(), NULL, via->m_Start, layerMask ) ) != NULL )
|
||||||
|
{
|
||||||
|
if( layer != track->GetLayer() )
|
||||||
|
{
|
||||||
|
// The via connects segments of an other track: it is removed
|
||||||
|
// from list because it is member of an other track
|
||||||
|
via->SetState( BUSY, OFF );
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Rearrange the track list in order to have flagged segments linked
|
||||||
|
* from firstTrack so the NbSegmBusy segments are consecutive segments
|
||||||
|
* in list, the first item in the full track list is firstTrack, and
|
||||||
|
* the NbSegmBusy-1 next items (NbSegmBusy when including firstTrack)
|
||||||
|
* are the flagged segments
|
||||||
|
*/
|
||||||
|
NbSegmBusy = 0;
|
||||||
|
TRACK* firstTrack;
|
||||||
|
|
||||||
|
for( firstTrack = aPcb->m_Track; firstTrack; firstTrack = firstTrack->Next() )
|
||||||
|
{
|
||||||
|
// Search for the first flagged BUSY segments
|
||||||
|
if( firstTrack->GetState( BUSY ) )
|
||||||
|
{
|
||||||
|
NbSegmBusy = 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if( firstTrack == NULL )
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
double full_len = 0;
|
||||||
|
double lenDie = 0;
|
||||||
|
|
||||||
|
if( aReorder )
|
||||||
|
{
|
||||||
|
DLIST<TRACK>* list = (DLIST<TRACK>*)firstTrack->GetList();
|
||||||
|
wxASSERT( list );
|
||||||
|
|
||||||
|
/* Rearrange the chain starting at firstTrack
|
||||||
|
* All others flagged items are moved from their position to the end
|
||||||
|
* of the flagged list
|
||||||
|
*/
|
||||||
|
TRACK* next;
|
||||||
|
|
||||||
|
for( TRACK* track = firstTrack->Next(); track; track = next )
|
||||||
|
{
|
||||||
|
next = track->Next();
|
||||||
|
|
||||||
|
if( track->GetState( BUSY ) ) // move it!
|
||||||
|
{
|
||||||
|
NbSegmBusy++;
|
||||||
|
track->UnLink();
|
||||||
|
list->Insert( track, firstTrack->Next() );
|
||||||
|
|
||||||
|
if( aTrackLen )
|
||||||
|
full_len += track->GetLength();
|
||||||
|
|
||||||
|
if( aLengthDie ) // Add now length die.
|
||||||
|
{
|
||||||
|
// In fact only 2 pads (maximum) will be taken in account:
|
||||||
|
// that are on each end of the track, if any
|
||||||
|
if( track->GetState( BEGIN_ONPAD ) )
|
||||||
|
{
|
||||||
|
D_PAD * pad = (D_PAD *) track->start;
|
||||||
|
lenDie += (double) pad->m_LengthDie;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( track->GetState( END_ONPAD ) )
|
||||||
|
{
|
||||||
|
D_PAD * pad = (D_PAD *) track->end;
|
||||||
|
lenDie += (double) pad->m_LengthDie;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if( aTrackLen )
|
||||||
|
{
|
||||||
|
NbSegmBusy = 0;
|
||||||
|
|
||||||
|
for( TRACK* track = firstTrack; track; track = track->Next() )
|
||||||
|
{
|
||||||
|
if( track->GetState( BUSY ) )
|
||||||
|
{
|
||||||
|
NbSegmBusy++;
|
||||||
|
track->SetState( BUSY, OFF );
|
||||||
|
full_len += track->GetLength();
|
||||||
|
|
||||||
|
// Add now length die.
|
||||||
|
// In fact only 2 pads (maximum) will be taken in account:
|
||||||
|
// that are on each end of the track, if any
|
||||||
|
if( track->GetState( BEGIN_ONPAD ) )
|
||||||
|
{
|
||||||
|
D_PAD * pad = (D_PAD *) track->start;
|
||||||
|
lenDie += (double) pad->m_LengthDie;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( track->GetState( END_ONPAD ) )
|
||||||
|
{
|
||||||
|
D_PAD * pad = (D_PAD *) track->end;
|
||||||
|
lenDie += (double) pad->m_LengthDie;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if( aTrackLen )
|
||||||
|
*aTrackLen = wxRound( full_len );
|
||||||
|
|
||||||
|
if( aLengthDie )
|
||||||
|
*aLengthDie = wxRound( lenDie );
|
||||||
|
|
||||||
|
if( aSegmCount )
|
||||||
|
*aSegmCount = NbSegmBusy;
|
||||||
|
|
||||||
|
return firstTrack;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function used by MarkTrace
|
||||||
|
* - Set the BUSY flag of connected segments, the first search point is
|
||||||
|
* ref_pos on layers allowed in masque_layer
|
||||||
|
* - Put segments fount in aList
|
||||||
|
* Vias are put in list but their flags BUSY is not set
|
||||||
|
* @param aPcb = the board
|
||||||
|
* @param aRef_pos = the reference coordinate of the starting search
|
||||||
|
* @param aLayerMask = the allowed layers for segments to search
|
||||||
|
* (1 layer when starting point is on a segment, but more than one when
|
||||||
|
* starting point is on a via)
|
||||||
|
* @param aList = the track list to fill with points of segments flagged
|
||||||
|
*/
|
||||||
|
static void ChainMarkedSegments( BOARD* aPcb,
|
||||||
|
wxPoint aRef_pos,
|
||||||
|
int aLayerMask,
|
||||||
|
TRACK_PTRS* aList )
|
||||||
|
{
|
||||||
|
TRACK* pt_segm, // The current segment being analyzed.
|
||||||
|
* pt_via, // The via identified, eventually destroy
|
||||||
|
|
||||||
|
* SegmentCandidate; // The end segment to destroy (or NULL =
|
||||||
|
// pt_segm
|
||||||
|
int NbSegm;
|
||||||
|
|
||||||
|
if( aPcb->m_Track == NULL )
|
||||||
|
return;
|
||||||
|
|
||||||
|
/* Set the BUSY flag of all connected segments, first search starting at
|
||||||
|
* aRef_pos
|
||||||
|
* Search ends when:
|
||||||
|
* - a pad is found (end of a track)
|
||||||
|
* - a segment end has more than one other segment end connected
|
||||||
|
* - and obviously when no connected item found
|
||||||
|
* Vias are a special case, because we must see others segment connected
|
||||||
|
* on others layers and they change the layer mask. They can be a track
|
||||||
|
* end or not
|
||||||
|
* They will be analyzer later, and vias on terminal points of the track
|
||||||
|
* will be considered as part of this track if they do not connect segments
|
||||||
|
* of an other track together and will be considered as part of an other
|
||||||
|
* track if when removing the via, the segments of that other track are
|
||||||
|
* disconnected
|
||||||
|
*/
|
||||||
|
for( ; ; )
|
||||||
|
{
|
||||||
|
if( Fast_Locate_Pad_Connecte( aPcb, aRef_pos, aLayerMask ) != NULL )
|
||||||
|
return;
|
||||||
|
|
||||||
|
/* Test for a via: a via changes the layer mask and can connect a lot
|
||||||
|
* of segments at location aRef_pos. When found, the via is just
|
||||||
|
* pushed in list. Vias will be examined later, when all connected
|
||||||
|
* segment are found and push in list. This is because when a via
|
||||||
|
* is found we do not know at this time the number of connected items
|
||||||
|
* and we do not know if this via is on the track or finish the track
|
||||||
|
*/
|
||||||
|
pt_via = Fast_Locate_Via( aPcb->m_Track, NULL, aRef_pos, aLayerMask );
|
||||||
|
|
||||||
|
if( pt_via )
|
||||||
|
{
|
||||||
|
aLayerMask = pt_via->ReturnMaskLayer();
|
||||||
|
|
||||||
|
aList->push_back( pt_via );
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Now we search all segments connected to point aRef_pos
|
||||||
|
* if only 1 segment: this segment is candidate
|
||||||
|
* if > 1 segment:
|
||||||
|
* end of track (more than 2 segment connected at this location)
|
||||||
|
*/
|
||||||
|
pt_segm = aPcb->m_Track; SegmentCandidate = NULL;
|
||||||
|
NbSegm = 0;
|
||||||
|
|
||||||
|
while( ( pt_segm = GetTrace( pt_segm, NULL, aRef_pos, aLayerMask ) ) != NULL )
|
||||||
|
{
|
||||||
|
if( pt_segm->GetState( BUSY ) ) // already found and selected: skip it
|
||||||
|
{
|
||||||
|
pt_segm = pt_segm->Next();
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( pt_segm == pt_via ) // just previously found: skip it
|
||||||
|
{
|
||||||
|
pt_segm = pt_segm->Next();
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
NbSegm++;
|
||||||
|
|
||||||
|
if( NbSegm == 1 ) /* First time we found a connected item: pt_segm is candidate */
|
||||||
|
{
|
||||||
|
SegmentCandidate = pt_segm;
|
||||||
|
pt_segm = pt_segm->Next();
|
||||||
|
}
|
||||||
|
else /* More than 1 segment connected -> this location is an end of the track */
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if( SegmentCandidate ) // A candidate is found: flag it an push it in list
|
||||||
|
{
|
||||||
|
/* Initialize parameters to search items connected to this
|
||||||
|
* candidate:
|
||||||
|
* we must analyze connections to its other end
|
||||||
|
*/
|
||||||
|
aLayerMask = SegmentCandidate->ReturnMaskLayer();
|
||||||
|
|
||||||
|
if( aRef_pos == SegmentCandidate->m_Start )
|
||||||
|
{
|
||||||
|
aRef_pos = SegmentCandidate->m_End;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
aRef_pos = SegmentCandidate->m_Start;
|
||||||
|
}
|
||||||
|
|
||||||
|
pt_segm = aPcb->m_Track; /* restart list of tracks to analyze */
|
||||||
|
|
||||||
|
/* flag this item an push it in list of selected items */
|
||||||
|
aList->push_back( SegmentCandidate );
|
||||||
|
SegmentCandidate->SetState( BUSY, ON );
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Calculate the end points coordinates of a track (a list of connected
|
||||||
|
* segments)
|
||||||
|
* RefTrack is a segment of the track
|
||||||
|
* return 1 if OK, 0 when a track is a closed loop
|
||||||
|
* and the beginning and the end of the track in *StartTrack and *EndTrack
|
||||||
|
* Modify *StartTrack en *EndTrack :
|
||||||
|
* (*StartTrack)->m_Start coordinate is the beginning of the track
|
||||||
|
* (*EndTrack)->m_End coordinate is the end of the track
|
||||||
|
* Segments connected must be consecutive in list
|
||||||
|
*/
|
||||||
|
int ReturnEndsTrack( TRACK* RefTrack, int NbSegm, TRACK** StartTrack, TRACK** EndTrack )
|
||||||
|
{
|
||||||
|
TRACK* Track, * via, * segm, * TrackListEnd;
|
||||||
|
int NbEnds, layerMask, ii, ok = 0;
|
||||||
|
|
||||||
|
if( NbSegm <= 1 )
|
||||||
|
{
|
||||||
|
*StartTrack = *EndTrack = RefTrack;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Calculation of the limit analysis. */
|
||||||
|
*StartTrack = *EndTrack = NULL;
|
||||||
|
TrackListEnd = Track = RefTrack; ii = 0;
|
||||||
|
|
||||||
|
for( ; ( Track != NULL ) && ( ii < NbSegm ); ii++, Track = Track->Next() )
|
||||||
|
{
|
||||||
|
TrackListEnd = Track;
|
||||||
|
Track->m_Param = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Calculate the extremes. */
|
||||||
|
NbEnds = 0; Track = RefTrack; ii = 0;
|
||||||
|
|
||||||
|
for( ; ( Track != NULL ) && ( ii < NbSegm ); ii++, Track = Track->Next() )
|
||||||
|
{
|
||||||
|
if( Track->Type() == TYPE_VIA )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
layerMask = Track->ReturnMaskLayer();
|
||||||
|
via = Fast_Locate_Via( RefTrack, TrackListEnd, Track->m_Start, layerMask );
|
||||||
|
|
||||||
|
if( via )
|
||||||
|
{
|
||||||
|
layerMask |= via->ReturnMaskLayer();
|
||||||
|
via->SetState( BUSY, ON );
|
||||||
|
}
|
||||||
|
|
||||||
|
Track->SetState( BUSY, ON );
|
||||||
|
segm = GetTrace( RefTrack, TrackListEnd, Track->m_Start, layerMask );
|
||||||
|
Track->SetState( BUSY, OFF );
|
||||||
|
|
||||||
|
if( via )
|
||||||
|
via->SetState( BUSY, OFF );
|
||||||
|
|
||||||
|
if( segm == NULL )
|
||||||
|
{
|
||||||
|
switch( NbEnds )
|
||||||
|
{
|
||||||
|
case 0:
|
||||||
|
*StartTrack = Track; NbEnds++;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 1:
|
||||||
|
int BeginPad, EndPad;
|
||||||
|
*EndTrack = Track;
|
||||||
|
|
||||||
|
/* Swap ox, oy with fx, fy */
|
||||||
|
BeginPad = Track->GetState( BEGIN_ONPAD );
|
||||||
|
EndPad = Track->GetState( END_ONPAD );
|
||||||
|
|
||||||
|
Track->SetState( BEGIN_ONPAD | END_ONPAD, OFF );
|
||||||
|
|
||||||
|
if( BeginPad )
|
||||||
|
Track->SetState( END_ONPAD, ON );
|
||||||
|
|
||||||
|
if( EndPad )
|
||||||
|
Track->SetState( BEGIN_ONPAD, ON );
|
||||||
|
|
||||||
|
EXCHG( Track->m_Start, Track->m_End );
|
||||||
|
EXCHG( Track->start, Track->end );
|
||||||
|
ok = 1;
|
||||||
|
return ok;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
layerMask = Track->ReturnMaskLayer();
|
||||||
|
via = Fast_Locate_Via( RefTrack, TrackListEnd, Track->m_End, layerMask );
|
||||||
|
|
||||||
|
if( via )
|
||||||
|
{
|
||||||
|
layerMask |= via->ReturnMaskLayer();
|
||||||
|
via->SetState( BUSY, ON );
|
||||||
|
}
|
||||||
|
|
||||||
|
Track->SetState( BUSY, ON );
|
||||||
|
segm = GetTrace( RefTrack, TrackListEnd, Track->m_End, layerMask );
|
||||||
|
Track->SetState( BUSY, OFF );
|
||||||
|
|
||||||
|
if( via )
|
||||||
|
via->SetState( BUSY, OFF );
|
||||||
|
|
||||||
|
if( segm == NULL )
|
||||||
|
{
|
||||||
|
switch( NbEnds )
|
||||||
|
{
|
||||||
|
case 0:
|
||||||
|
int BeginPad, EndPad;
|
||||||
|
*StartTrack = Track;
|
||||||
|
NbEnds++;
|
||||||
|
|
||||||
|
/* Swap ox, oy with fx, fy */
|
||||||
|
BeginPad = Track->GetState( BEGIN_ONPAD );
|
||||||
|
EndPad = Track->GetState( END_ONPAD );
|
||||||
|
|
||||||
|
Track->SetState( BEGIN_ONPAD | END_ONPAD, OFF );
|
||||||
|
|
||||||
|
if( BeginPad )
|
||||||
|
Track->SetState( END_ONPAD, ON );
|
||||||
|
|
||||||
|
if( EndPad )
|
||||||
|
Track->SetState( BEGIN_ONPAD, ON );
|
||||||
|
|
||||||
|
EXCHG( Track->m_Start, Track->m_End );
|
||||||
|
EXCHG( Track->start, Track->end );
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 1:
|
||||||
|
*EndTrack = Track;
|
||||||
|
ok = 1;
|
||||||
|
return ok;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return ok;
|
||||||
|
}
|
Loading…
Reference in New Issue