PNS_ITEMSET& PNS_ITEMSET::FilterLayers( int aStart, int aEnd )
{
    ItemVector newItems;
    PNS_LAYERSET l;

    if( aEnd < 0 )
        l = PNS_LAYERSET( aStart );
    else
        l = PNS_LAYERSET( aStart, aEnd );

    BOOST_FOREACH( PNS_ITEM * item, m_items )

    if( item->GetLayers().Overlaps( l ) )
        newItems.push_back( item );

    m_items = newItems;
    return *this;
}
Example #2
0
PNS_ITEM* PNS_ROUTER::syncTrack( TRACK* aTrack )
{
    PNS_SEGMENT* s =
        new PNS_SEGMENT( SEG( aTrack->GetStart(), aTrack->GetEnd() ), aTrack->GetNetCode() );

    s->SetWidth( aTrack->GetWidth() );
    s->SetLayers( PNS_LAYERSET( aTrack->GetLayer() ) );
    s->SetParent( aTrack );
    return s;
}
PNS_ITEMSET& PNS_ITEMSET::FilterLayers( int aStart, int aEnd, bool aInvert )
{
    ENTRIES newItems;
    PNS_LAYERSET l;

    if( aEnd < 0 )
        l = PNS_LAYERSET( aStart );
    else
        l = PNS_LAYERSET( aStart, aEnd );

    for( const ENTRY& ent : m_items )
    {
        if( ent.item->Layers().Overlaps( l ) ^ aInvert )
        {
            newItems.push_back( ent );
        }
    }

    m_items = newItems;

    return *this;
}
Example #4
0
PNS_ITEM* PNS_ROUTER::syncVia( VIA* aVia )
{
    LAYER_ID top, bottom;
    aVia->LayerPair( &top, &bottom );
    PNS_VIA* v = new PNS_VIA(
            aVia->GetPosition(),
            PNS_LAYERSET( top, bottom ),
            aVia->GetWidth(),
            aVia->GetDrillValue(),
            aVia->GetNetCode(),
            (PNS_VIA_TYPE)aVia->GetViaType() );

    v->SetParent( aVia );

    return v;
}
Example #5
0
PNS_ITEM* PNS_ROUTER::syncPad( D_PAD* aPad )
{
    PNS_LAYERSET layers( 0, MAX_CU_LAYERS - 1 );

    // ignore non-copper pads
    if ( (aPad->GetLayerSet() & LSET::AllCuMask()).none() )
        return NULL;

    switch( aPad->GetAttribute() )
    {
    case PAD_ATTRIB_STANDARD:
        break;

    case PAD_ATTRIB_SMD:
    case PAD_ATTRIB_HOLE_NOT_PLATED:
    case PAD_ATTRIB_CONN:
        {
            LSET lmsk = aPad->GetLayerSet();
            bool is_copper = false;

            for( int i = 0; i < MAX_CU_LAYERS; i++ )
            {
                if( lmsk[i] )
                {
                    is_copper = true;
                    if( aPad->GetAttribute() != PAD_ATTRIB_HOLE_NOT_PLATED )
                        layers = PNS_LAYERSET( i );
                    break;
                }
            }

            if( !is_copper )
                return NULL;
        }
        break;

    default:
        TRACE( 0, "unsupported pad type 0x%x", aPad->GetAttribute() );
        return NULL;
    }

    PNS_SOLID* solid = new PNS_SOLID;

    solid->SetLayers( layers );
    solid->SetNet( aPad->GetNetCode() );
    solid->SetParent( aPad );

    wxPoint wx_c = aPad->ShapePos();
    wxSize  wx_sz = aPad->GetSize();
    wxPoint offset = aPad->GetOffset();

    VECTOR2I c( wx_c.x, wx_c.y );
    VECTOR2I sz( wx_sz.x, wx_sz.y );

    RotatePoint( &offset, aPad->GetOrientation() );

    solid->SetPos( VECTOR2I( c.x - offset.x, c.y - offset.y ) );
    solid->SetOffset ( VECTOR2I ( offset.x, offset.y ) );

    double orient = aPad->GetOrientation() / 10.0;

    if( aPad->GetShape() == PAD_SHAPE_CIRCLE )
    {
        solid->SetShape( new SHAPE_CIRCLE( c, sz.x / 2 ) );
    }
    else
    {
        if( orient == 0.0 || orient == 90.0 || orient == 180.0 || orient == 270.0 )
        {
            if( orient == 90.0 || orient == 270.0 )
                sz = VECTOR2I( sz.y, sz.x );

            switch( aPad->GetShape() )
            {
            case PAD_SHAPE_OVAL:
                if( sz.x == sz.y )
                    solid->SetShape( new SHAPE_CIRCLE( c, sz.x / 2 ) );
                else
                {
                    VECTOR2I delta;

                    if( sz.x > sz.y )
                        delta = VECTOR2I( ( sz.x - sz.y ) / 2, 0 );
                    else
                        delta = VECTOR2I( 0, ( sz.y - sz.x ) / 2 );

                    SHAPE_SEGMENT* shape = new SHAPE_SEGMENT( c - delta, c + delta,
                                                              std::min( sz.x, sz.y ) );
                    solid->SetShape( shape );
                }
                break;

            case PAD_SHAPE_RECT:
                solid->SetShape( new SHAPE_RECT( c - sz / 2, sz.x, sz.y ) );
                break;

            case PAD_SHAPE_TRAPEZOID:
            {
                wxPoint coords[4];
                aPad->BuildPadPolygon( coords, wxSize( 0, 0 ), aPad->GetOrientation() );
                SHAPE_CONVEX* shape = new SHAPE_CONVEX();

                for( int ii = 0; ii < 4; ii++ )
                {
                    shape->Append( wx_c + coords[ii] );
                }

                solid->SetShape( shape );
                break;
            }

            default:
                TRACEn( 0, "unsupported pad shape" );
                delete solid;
                return NULL;
            }
        }
        else
        {
            switch( aPad->GetShape() )
            {
            // PAD_SHAPE_CIRCLE already handled above

            case PAD_SHAPE_OVAL:
                if( sz.x == sz.y )
                    solid->SetShape( new SHAPE_CIRCLE( c, sz.x / 2 ) );
                else
                {
                    wxPoint start;
                    wxPoint end;
                    wxPoint corner;

                    SHAPE_CONVEX* shape = new SHAPE_CONVEX();

                    int w = aPad->BuildSegmentFromOvalShape( start, end, 0.0, wxSize( 0, 0 ) );

                    if( start.y == 0 )
                        corner = wxPoint( start.x, -( w / 2 ) );
                    else
                        corner = wxPoint( w / 2, start.y );

                    RotatePoint( &start, aPad->GetOrientation() );
                    RotatePoint( &corner, aPad->GetOrientation() );
                    shape->Append( wx_c + corner );

                    for( int rot = 100; rot <= 1800; rot += 100 )
                    {
                        wxPoint p( corner );
                        RotatePoint( &p, start, rot );
                        shape->Append( wx_c + p );
                    }

                    if( end.y == 0 )
                        corner = wxPoint( end.x, w / 2 );
                    else
                        corner = wxPoint( -( w / 2 ), end.y );

                    RotatePoint( &end, aPad->GetOrientation() );
                    RotatePoint( &corner, aPad->GetOrientation() );
                    shape->Append( wx_c + corner );

                    for( int rot = 100; rot <= 1800; rot += 100 )
                    {
                        wxPoint p( corner );
                        RotatePoint( &p, end, rot );
                        shape->Append( wx_c + p );
                    }

                    solid->SetShape( shape );
                }
                break;

            case PAD_SHAPE_RECT:
            case PAD_SHAPE_TRAPEZOID:
            {
                wxPoint coords[4];
                aPad->BuildPadPolygon( coords, wxSize( 0, 0 ), aPad->GetOrientation() );

                SHAPE_CONVEX* shape = new SHAPE_CONVEX();
                for( int ii = 0; ii < 4; ii++ )
                {
                    shape->Append( wx_c + coords[ii] );
                }

                solid->SetShape( shape );
                break;
            }

            default:
                TRACEn( 0, "unsupported pad shape" );
                delete solid;

                return NULL;
            }
        }
    }
    return solid;
}