Create a new footprint via the KiCad 7 Python API

I want to have a function that replaces the circles of a board with non-plated through holes of the same diameter and position.

I can iterate over the circles and delete them, but I don’t know how to create footprints for the through-hole pads.

def circles_to_holes(board):
    for drawing in board.GetDrawings():
        if drawing.GetShape() == pcbnew.S_CIRCLE:
            # footprint = pcbnew.Footprint(board)
            # footprint.SetPosition(drawing.GetPosition())
            # footprint.SetOrientation(drawing.GetOrientation())
            # footprint.SetLayerID(pcbnew.F_Cu)
            # footprint.SetAttribute(pcbnew.FP_Attribute.HOLE_NOT_PLATED)
            # footprint.SetShape(pcbnew.PAD_SHAPE_CIRCLE)
            # footprint.SetSize(drawing.GetRadius() * 2, drawing.GetRadius() * 2)
            # footprint.SetDrill(drawing.GetRadius() * 2)
            # board.Add(footprint)
            board.Remove(drawing)

ChatGPT and GitHub Copilot generated the commented-out lines, but pcbnew.Footprint(board) throws AttributeError: module 'pcbnew' has no attribute 'Footprint', and I haven’t found the method in the API documentation to create footprints.

Try capital FOOTPRINT

I don’t know KiCad scripting but be aware that ChatGPT doesn’t have data more recent than 2021 (unless they’ve released a new version with bigger data) so may be using an old binding and KiCad is evolving quickly.

Maybe have a look at how the footprint wizard does it?

Thanks, guys! I’m almost there, but the commented-out lines throw:

  • TypeError: in method 'PAD_SetSize', argument 2 of type 'VECTOR2I const &'
  • TypeError: in method 'PAD_SetDrillSize', argument 2 of type 'VECTOR2I const &'

Same error when using wxSize instead of wxSizeMM.

def circles_to_holes(board):
    for drawing in board.GetDrawings():
        if drawing.GetShape() == pcbnew.S_CIRCLE:
            footprint = pcbnew.FOOTPRINT(board)
            footprint.SetPosition(drawing.GetPosition())
            pad = pcbnew.PAD(footprint)
            pad.SetShape(pcbnew.PAD_SHAPE_CIRCLE)
            # pad.SetSize(pcbnew.wxSizeMM(drawing.GetRadius() * 2, drawing.GetRadius() * 2))
            # pad.SetDrillSize(pcbnew.wxSizeMM(drawing.GetRadius() * 2, drawing.GetRadius() * 2))
            pad.SetAttribute(pcbnew.PAD_ATTRIB_NPTH)
            footprint.Add(pad)
            board.Add(footprint)
            board.Remove(drawing)

The error is literally telling you to use VECTOR2I and not wxSize

1 Like

@qu1ck Thanks! It hasn’t occurred to me to use VECTOR2I despite the error message because every example I saw used wxSize. The following code works:

def circles_to_holes(board):
    for drawing in board.GetDrawings():
        if drawing.GetShape() == pcbnew.S_CIRCLE:
            footprint = pcbnew.FOOTPRINT(board)
            footprint.SetPosition(drawing.GetPosition())
            pad = pcbnew.PAD(footprint)
            pad.SetShape(pcbnew.PAD_SHAPE_CIRCLE)
            pad.SetSize(pcbnew.VECTOR2I(drawing.GetRadius() * 2, drawing.GetRadius() * 2))
            pad.SetDrillSize(pcbnew.VECTOR2I(drawing.GetRadius() * 2, drawing.GetRadius() * 2))
            pad.SetAttribute(pcbnew.PAD_ATTRIB_NPTH)
            footprint.Add(pad)
            board.Add(footprint)
            board.Remove(drawing)
1 Like

It is important to note that at this time KiCad does not have a stable Python API, only bindings that are subject to change with every major version release. For this reason, if you are working from examples you have found online, you cannot expect them to work directly unless they were made with the same KiCad major version you are using. If they were made with an older version, you can expect to need to refactor them to use the newer bindings.

2 Likes

Keep in mind that python binding can (and do) change even between patch releases.

But bindings have more significant changes between major releases. You can look at the bindings documentation at:
for V5 at KiCad Pcbnew Python Scripting: pcbnew Namespace Reference
for V6 at KiCad Pcbnew Python Scripting: pcbnew Namespace Reference
for V7.?.? at KiCad Pcbnew Python Scripting: pcbnew Namespace Reference

So when looking at the examples online keep in mind that they have most likely been written for an old version

1 Like

Gotcha, guys. My script works with KiCad 7.0.2

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.