Added: patch from Rok Markovic, and some changes in printing functions

This commit is contained in:
charras 2009-01-15 14:32:29 +00:00
parent f64b282778
commit 962b8b0ead
7 changed files with 191 additions and 30 deletions

View File

@ -5,6 +5,17 @@ Started 2007-June-11
Please add newer entries at the top, list the date and your name with
email address.
2009-Jan-15 UPDATE Jean-Pierre Charras <jean-pierre.charras@inpg.fr>
================================================================================
++Pcbnew:
Added: patch from Rok Markovic (rok@kanardia.eu) to remove unused stubs in thermal pads
Modified: print boards when printing in color mode layers on one sheet:
now printed in OR mode like drawings on screen
Also in SVG mode, but OR mode seems not work inSVG mode.
2009-Jan-11 UPDATE Jean-Pierre Charras <jean-pierre.charras@inpg.fr>
================================================================================
++Pcbnew:

View File

@ -328,7 +328,7 @@ void D_PAD::Draw( WinEDA_DrawPanel* panel, wxDC* DC, int draw_mode, const wxPoin
{
blackpenstate = GetGRForceBlackPenState();
GRForceBlackPen( false );
color = WHITE;
color = g_DrawBgColor;
}
else
color = BLACK; // or DARKGRAY;

View File

@ -629,6 +629,9 @@ void TRACK::Draw( WinEDA_DrawPanel* panel, wxDC* DC, int draw_mode, const wxPoin
m_End.x, m_End.y, m_Width, color );
}
if( g_IsPrinting )
return;
// Show clearance for tracks, not for zone segments
if( ShowClearance( this ) )
{
@ -643,7 +646,7 @@ void TRACK::Draw( WinEDA_DrawPanel* panel, wxDC* DC, int draw_mode, const wxPoin
* - only tracks with a length > 10 * thickness are eligible
* and, of course, if we are not printing the board
*/
if( Type() == TYPE_ZONE || g_IsPrinting )
if( Type() == TYPE_ZONE )
return;
#define THRESHOLD 10

View File

@ -50,8 +50,22 @@ void WinEDA_DrawPanel::PrintPage( wxDC* aDC, bool aPrint_Sheet_Ref, int aPrintMa
DisplayOpt.DisplayZonesMode = 0;
m_PrintIsMirrored = aPrintMirrorMode;
if( ( g_DrawBgColor == BLACK ) && (GetGRForceBlackPenState( ) == false) )
{ // One can use the OR mode in this case, and we draw a black background to draw board in OR mode, like on screen
// But because black background are very expensive to draw, we draw in black only the minimun area.
drawmode = GR_OR;
EDA_Rect rect = frame->GetBoard()->m_BoundaryBox;
rect.Inflate( 2000, 2000 ); // Margin in 1/10000 inch around the board to draw the black background.
GRSetDrawMode( aDC, GR_COPY );
// draw in black the minimum page area:
GRFilledRect( &m_ClipBox, aDC, rect.GetX(), rect.GetY(),
rect.GetEnd().x, rect.GetEnd().y, g_DrawBgColor, g_DrawBgColor );
}
/* Print the pcb graphic items (texts, ...) */
GRSetDrawMode( aDC, drawmode );
for( BOARD_ITEM* item = Pcb->m_Drawings; item; item = item->Next() )
{
switch( item->Type() )
@ -106,24 +120,6 @@ void WinEDA_DrawPanel::PrintPage( wxDC* aDC, bool aPrint_Sheet_Ref, int aPrintMa
Print_Module( this, aDC, Module, drawmode, aPrintMaskLayer );
}
/* Print via holes in white color*/
pt_piste = Pcb->m_Track;
int rayon = g_DesignSettings.m_ViaDrill / 2;
int color = WHITE;
bool blackpenstate = GetGRForceBlackPenState( );
GRForceBlackPen( false );
for( ; pt_piste != NULL; pt_piste = pt_piste->Next() )
{
if( ( aPrintMaskLayer & pt_piste->ReturnMaskLayer() ) == 0 )
continue;
if( pt_piste->Type() == TYPE_VIA ) /* VIA rencontree */
{
GRSetDrawMode( aDC, drawmode );
GRFilledCircle( &m_ClipBox, aDC, pt_piste->m_Start.x, pt_piste->m_Start.y,
rayon, 0, color, color );
}
}
GRForceBlackPen( blackpenstate );
/* Draw filled areas (i.e. zones) */
for( int ii = 0; ii < Pcb->GetAreaCount(); ii++ )
@ -135,6 +131,25 @@ void WinEDA_DrawPanel::PrintPage( wxDC* aDC, bool aPrint_Sheet_Ref, int aPrintMa
zone->DrawFilledArea( this, aDC, drawmode );
}
/* Print via holes in bg color: Not sure it is good for buried or blind vias */
pt_piste = Pcb->m_Track;
int color = g_DrawBgColor;
bool blackpenstate = GetGRForceBlackPenState( );
GRForceBlackPen( false );
GRSetDrawMode( aDC, GR_COPY );
for( ; pt_piste != NULL; pt_piste = pt_piste->Next() )
{
if( ( aPrintMaskLayer & pt_piste->ReturnMaskLayer() ) == 0 )
continue;
if( pt_piste->Type() == TYPE_VIA ) /* VIA rencontree */
{
int rayon = g_DesignSettings.m_ViaDrill / 2;
GRFilledCircle( &m_ClipBox, aDC, pt_piste->m_Start.x, pt_piste->m_Start.y,
rayon, 0, color, color );
}
}
GRForceBlackPen( blackpenstate );
if( aPrint_Sheet_Ref )
m_Parent->TraceWorkSheet( aDC, GetScreen(), g_PlotLine_Width );

View File

@ -295,6 +295,132 @@ void ZONE_CONTAINER::AddClearanceAreasPolygonsToPolysList( BOARD* aPcb )
delete booleng;
}
// Now we remove all unused thermal stubs.
#define REMOVE_UNUSED_THERMAL_STUBS // Can be commented to skip unused thermal stubs calculations
#ifdef REMOVE_UNUSED_THERMAL_STUBS
// first compute endindex for TestPointInsidePolygon
unsigned int indexstart = 0, indexend;
for( indexend = 0; indexend < m_FilledPolysList.size(); indexend++ )
{
if( m_FilledPolysList[indexend].end_contour ) // end of a filled sub-area found
{
break;
}
}
/* Second, Add the main (corrected) polygon (i.e. the filled area using only one outline)
* in GroupA in Bool_Engine to do a BOOL_A_SUB_B operation
* All areas to remove will be put in GroupB in Bool_Engine
*/
booleng = new Bool_Engine();
ArmBoolEng( booleng, true );
/* Add the main corrected polygon (i.e. the filled area using only one outline)
* in GroupA in Bool_Engine
*/
CopyPolygonsFromFilledPolysListToBoolengine( booleng, GROUP_A );
/*
* Test and add polygons to remove thermal stubs.
*/
for( MODULE* module = aPcb->m_Modules; module; module = module->Next() )
{
for( D_PAD* pad = module->m_Pads; pad != NULL; pad = pad->Next() )
{
// check
if( pad->IsOnLayer( GetLayer() )
&& pad->GetNet() == GetNet()
&& m_PadOption == THERMAL_PAD )
{
item_boundingbox = pad->GetBoundingBox();
item_boundingbox.Inflate( m_ThermalReliefGapValue, m_ThermalReliefGapValue );
if( !(item_boundingbox.Intersects( zone_boundingbox )) )
continue;
// test point
int dx = (pad->m_Size.x / 2) + m_ThermalReliefGapValue;
int dy = (pad->m_Size.y / 2) + m_ThermalReliefGapValue;
// compute north, south, west and east points for zone connection.
wxPoint ptTest[4];
ptTest[0] = wxPoint(0, dy+m_ZoneMinThickness/2);
ptTest[1] = wxPoint(0, -(dy+m_ZoneMinThickness/2));
ptTest[2] = wxPoint( dx+m_ZoneMinThickness/2, 0);
ptTest[3] = wxPoint(-(dx+m_ZoneMinThickness/2), 0);
// This is CIRCLE pad tweak (for circle pads the thermal stubs are at 45 deg)
float fAngle = 0.0;
if ( pad->m_PadShape == PAD_CIRCLE)
fAngle = 450.0;
// Test all sides
for (int i=0; i<4; i++) {
// rotate point
RotatePoint( &ptTest[i], pad->m_Orient + fAngle );
// translate point
ptTest[i] += pad->ReturnShapePos();
if ( TestPointInsidePolygon( m_FilledPolysList, indexstart,
indexend, ptTest[i].x, ptTest[i].y ) == false)
{
// polygon buffer
std::vector<wxPoint> corners_buffer;
// polygons are rectangles with width of copper bridge value
const int iDTRC = m_ThermalReliefCopperBridgeValue / 2;
switch (i) {
case 0:
corners_buffer.push_back( wxPoint( -iDTRC, dy) );
corners_buffer.push_back( wxPoint( +iDTRC, dy) );
corners_buffer.push_back( wxPoint( +iDTRC, iDTRC ) );
corners_buffer.push_back( wxPoint( -iDTRC, iDTRC ) );
break;
case 1:
corners_buffer.push_back( wxPoint( -iDTRC, -dy ) );
corners_buffer.push_back( wxPoint( +iDTRC, -dy ) );
corners_buffer.push_back( wxPoint( +iDTRC, -iDTRC ) );
corners_buffer.push_back( wxPoint( -iDTRC, -iDTRC ) );
break;
case 2:
corners_buffer.push_back( wxPoint( dx, -iDTRC ) );
corners_buffer.push_back( wxPoint( dx, iDTRC ) );
corners_buffer.push_back( wxPoint( +iDTRC, iDTRC ) );
corners_buffer.push_back( wxPoint( +iDTRC, -iDTRC ) );
break;
case 3:
corners_buffer.push_back( wxPoint( -dx, -iDTRC ) );
corners_buffer.push_back( wxPoint( -dx, iDTRC ) );
corners_buffer.push_back( wxPoint( -iDTRC, iDTRC ) );
corners_buffer.push_back( wxPoint( -iDTRC, -iDTRC ) );
break;
}
// add computed polygon to group_B
if( booleng->StartPolygonAdd( GROUP_B ) )
{
for( unsigned ic = 0; ic < corners_buffer.size(); ic++ )
{
wxPoint cpos = corners_buffer[ic];
RotatePoint( &cpos, pad->m_Orient + fAngle ); // Rotate according to module orientation
cpos += pad->ReturnShapePos(); // Shift origin to position
booleng->AddPoint( cpos.x, cpos.y );
}
booleng->EndPolygonAdd();
}
}
}
}
}
}
/* compute copper areas */
booleng->Do_Operation( BOOL_A_SUB_B );
/* put these areas in m_FilledPolysList */
m_FilledPolysList.clear();
CopyPolygonsFromBoolengineToFilledPolysList( booleng );
delete booleng;
#endif
// Remove insulated islands:
if( GetNet() > 0 )
Test_For_Copper_Island_And_Remove_Insulated_Islands( aPcb );

View File

@ -64,7 +64,7 @@ WinEDA_PrintFrame::WinEDA_PrintFrame( WinEDA_DrawFrame* parent, wxWindowID id, c
m_Config = wxGetApp().m_EDA_Config;
if ( m_Config )
{
m_Config->Read(wxT("PrintPenWidth"), &g_PlotLine_Width);
m_Config->Read(OPTKEY_PLOT_LINEWIDTH_VALUE, &g_PlotLine_Width);
}

View File

@ -268,11 +268,9 @@ void WinEDA_PrintFrame::OnClosePrintDialog()
/* called when WinEDA_PrintFrame is closed
*/
{
wxConfig* Config = wxGetApp().m_EDA_Config;
if( Config )
if( m_Config )
{
Config->Write( OPTKEY_PLOT_LINEWIDTH_VALUE, g_PlotLine_Width );
m_Config->Write( OPTKEY_PLOT_LINEWIDTH_VALUE, g_PlotLine_Width );
}
if( m_FineAdjustXscaleOpt )
@ -282,16 +280,16 @@ void WinEDA_PrintFrame::OnClosePrintDialog()
SetPenWidth();
#ifdef PCBNEW
if( Config )
if( m_Config )
{
Config->Write( OPTKEY_PRINT_X_FINESCALE_ADJ, m_XScaleAdjust );
Config->Write( OPTKEY_PRINT_Y_FINESCALE_ADJ, m_YScaleAdjust );
Config->Write( OPTKEY_PRINT_SCALE, s_Scale_Select );
m_Config->Write( OPTKEY_PRINT_X_FINESCALE_ADJ, m_XScaleAdjust );
m_Config->Write( OPTKEY_PRINT_Y_FINESCALE_ADJ, m_YScaleAdjust );
m_Config->Write( OPTKEY_PRINT_SCALE, s_Scale_Select );
wxString layerKey;
for( int layer = 0; layer<NB_LAYERS; ++layer )
{
layerKey.Printf( OPTKEY_LAYERBASE, layer );
Config->Write( layerKey, m_BoxSelecLayer[layer]->IsChecked() );
m_Config->Write( layerKey, m_BoxSelecLayer[layer]->IsChecked() );
}
}
#endif
@ -765,8 +763,15 @@ void EDA_Printout::DrawPage()
panel->m_ClipBox.SetSize( wxSize( 0x7FFFFF0, 0x7FFFFF0 ) );
g_IsPrinting = TRUE;
int bg_color = g_DrawBgColor;
#ifdef PCBNEW
// background color can left BLACK only when drawing the full board at once, in color mode
// Switch it to WHITE in others cases
if ( s_Print_Black_and_White || ( m_PrintFrame->m_PagesOption->GetSelection() != 1 ) )
g_DrawBgColor = WHITE;
if( m_Print_Sheet_Ref )
m_Parent->TraceWorkSheet( dc, ActiveScreen, 0 );
@ -816,6 +821,7 @@ void EDA_Printout::DrawPage()
panel->PrintPage( dc, m_Print_Sheet_Ref, s_PrintMaskLayer, s_PrintMirror );
#endif
g_DrawBgColor = bg_color;
g_IsPrinting = FALSE;
panel->m_ClipBox = tmp;