def BuildThisFootprint(self):

        pad_pitch = self.pads["pitch"]
        pad_length = self.pads["length"]
        # offset allows to define how much of the pad is outside of the package
        pad_offset = self.pads["offset"]
        pad_width = self.pads["width"]

        v_pitch = self.package["height"]
        h_pitch = self.package["width"]

        pads_per_row = int(self.pads["n"] // 4)

        row_len = (pads_per_row - 1) * pad_pitch

        pad_shape = pcbnew.PAD_SHAPE_OVAL if self.pads[
            "oval"] else pcbnew.PAD_SHAPE_RECT

        h_pad = PA.PadMaker(self.module).SMDPad(pad_length,
                                                pad_width,
                                                shape=pad_shape,
                                                rot_degree=90.0)
        v_pad = PA.PadMaker(self.module).SMDPad(pad_length,
                                                pad_width,
                                                shape=pad_shape)

        h_pitch = h_pitch / 2 - pad_length + pad_offset + pad_length / 2
        v_pitch = v_pitch / 2 - pad_length + pad_offset + pad_length / 2

        #left row
        pin1Pos = pcbnew.wxPoint(-h_pitch, 0)
        array = PA.PadLineArray(h_pad, pads_per_row, pad_pitch, True, pin1Pos)
        array.SetFirstPadInArray(1)
        array.AddPadsToModule(self.draw)

        #bottom row
        pin1Pos = pcbnew.wxPoint(0, v_pitch)
        array = PA.PadLineArray(v_pad, pads_per_row, pad_pitch, False, pin1Pos)
        array.SetFirstPadInArray(pads_per_row + 1)
        array.AddPadsToModule(self.draw)

        #right row
        pin1Pos = pcbnew.wxPoint(h_pitch, 0)
        array = PA.PadLineArray(h_pad, pads_per_row, -pad_pitch, True, pin1Pos)
        array.SetFirstPadInArray(2 * pads_per_row + 1)
        array.AddPadsToModule(self.draw)

        #top row
        pin1Pos = pcbnew.wxPoint(0, -v_pitch)
        array = PA.PadLineArray(v_pad, pads_per_row, -pad_pitch, False,
                                pin1Pos)
        array.SetFirstPadInArray(3 * pads_per_row + 1)
        array.AddPadsToModule(self.draw)

        lim_x = self.package["width"] / 2
        lim_y = self.package["height"] / 2
        inner = (row_len / 2) + pad_pitch

        # epad
        epad_width = self.epad["width"]
        epad_length = self.epad["length"]

        epad_ny = self.epad["x divisions"]
        epad_nx = self.epad["y divisions"]

        epad_via_drill = self.epad["thermal vias drill"]

        # Create a central exposed pad?
        if self.epad['epad'] == True:

            epad_num = self.pads['n'] + 1

            epad_w = epad_length / epad_nx
            epad_l = epad_width / epad_ny

            # Create the epad
            epad = PA.PadMaker(self.module).SMDPad(epad_w,
                                                   epad_l,
                                                   shape=pcbnew.PAD_SHAPE_RECT)
            epad.SetLocalSolderPasteMargin(-1 * self.epad['paste margin'])
            # set pad layers
            layers = pcbnew.LSET(pcbnew.F_Mask)
            layers.AddLayer(pcbnew.F_Cu)
            layers.AddLayer(pcbnew.F_Paste)
            epad.SetName(epad_num)

            array = PA.EPADGridArray(epad, epad_ny, epad_nx, epad_l, epad_w,
                                     pcbnew.wxPoint(0, 0))
            array.SetFirstPadInArray(epad_num)
            array.AddPadsToModule(self.draw)

            if self.epad['thermal vias']:

                # create the thermal via
                via_diam = min(epad_w, epad_l) / 2
                via_drill = min(via_diam / 2, epad_via_drill)
                via = PA.PadMaker(self.module).THRoundPad(via_diam, via_drill)
                layers = pcbnew.LSET.AllCuMask()
                layers.AddLayer(pcbnew.B_Mask)
                layers.AddLayer(pcbnew.F_Mask)
                via.SetLayerSet(layers)

                via_array = PA.EPADGridArray(via, epad_ny, epad_nx, epad_l,
                                             epad_w, pcbnew.wxPoint(0, 0))
                via_array.SetFirstPadInArray(epad_num)
                via_array.AddPadsToModule(self.draw)

        # Draw the package outline on the F.Fab layer
        bevel = min(pcbnew.FromMM(1.0), self.package['width'] / 2,
                    self.package['height'] / 2)

        self.draw.SetLayer(pcbnew.F_Fab)

        w = self.package['width']
        h = self.package['height']

        self.draw.BoxWithDiagonalAtCorner(0, 0, w, h, bevel)

        # Silkscreen
        self.draw.SetLayer(pcbnew.F_SilkS)

        offset = self.draw.GetLineThickness()
        clip = row_len / 2 + self.pads['pitch']

        self.draw.SetLineThickness(
            pcbnew.FromMM(0.12))  #Default per KLC F5.1 as of 12/2018
        self.draw.Polyline([[clip, -h / 2 - offset],
                            [w / 2 + offset, -h / 2 - offset],
                            [w / 2 + offset, -clip]])  # top right
        self.draw.Polyline([[clip, h / 2 + offset],
                            [w / 2 + offset, h / 2 + offset],
                            [w / 2 + offset, clip]])  # bottom right
        self.draw.Polyline([[-clip, h / 2 + offset],
                            [-w / 2 - offset, h / 2 + offset],
                            [-w / 2 - offset, clip]])  # bottom left

        # Add pin-1 indication as per IPC-7351C
        self.draw.Line(-clip, -h / 2 - offset, -w / 2 - pad_length / 2,
                       -h / 2 - offset)
        self.draw.SetLineThickness(offset)  #Restore default

        # Courtyard
        cmargin = self.package["margin"]
        self.draw.SetLayer(pcbnew.F_CrtYd)

        sizex = (lim_x + cmargin) * 2 + pad_length
        sizey = (lim_y + cmargin) * 2 + pad_length

        # round size to nearest 0.1mm, rectangle will thus land on a 0.05mm grid
        sizex = pcbnew.PutOnGridMM(sizex, 0.1)
        sizey = pcbnew.PutOnGridMM(sizey, 0.1)
        # set courtyard line thickness to the one defined in KLC
        thick = self.draw.GetLineThickness()
        self.draw.SetLineThickness(pcbnew.FromMM(0.05))
        self.draw.Box(0, 0, sizex, sizey)
        # restore line thickness to previous value
        self.draw.SetLineThickness(pcbnew.FromMM(thick))

        #reference and value
        text_size = self.GetTextSize()  # IPC nominal
        text_offset = sizey / 2 + text_size

        self.draw.Value(0, text_offset, text_size)
        self.draw.Reference(0, -text_offset, text_size)

        # set SMD attribute
        self.module.SetAttributes(pcbnew.MOD_SMD)
    def BuildThisFootprint(self):
        pads = self.parameters["Pads"]
        body = self.parameters["Body"]
        num_pads = pads[self.pad_count_key]
        pad_length = pads[self.pad_length_key]
        pad_width = pads[self.pad_width_key]
        row_pitch = pads[self.row_spacing_key]
        pad_pitch = pads[self.pad_pitch_key]
        num_rows = pads[self.row_count_key]

        pads_per_row = num_pads // num_rows

        # add in the pads
        pad = self.GetPad()

        array = RowedGridArray(pad, pads_per_row, num_rows, pad_pitch, row_pitch)
        array.AddPadsToModule(self.draw)

        # draw the Silk Screen
        Hsize = pad_pitch * (num_pads / num_rows - 1)
        Vsize = row_pitch * (num_rows - 1)
        pin1_posY = -Vsize / 2
        pin1_posX = -Hsize / 2

        pad_length = pads[self.pad_length_key]
        pad_width = pads[self.pad_width_key]

        ssx_offset = -pad_width / 2 - body[self.outline_x_margin_key]
        ssy_offset = -pad_length / 2 - body[self.outline_y_margin_key]

        if body[self.silkscreen_inside_key]:
            ssy_offset *= -1

        ssx = -pin1_posX - ssx_offset
        ssy = -pin1_posY - ssy_offset

        cmargin = self.draw.GetLineThickness()
        self.draw.SetLineThickness( pcbnew.FromMM( 0.12 ) ) #Default per KLC F5.1 as of 12/2018
        self.DrawBox(ssx, ssy)

        # Courtyard
        self.draw.SetLayer(pcbnew.F_CrtYd)
        cclearance = pcbnew.FromMM(0.25)
        sizex = (-pin1_posX + cclearance) * 2 + pad_width
        sizey = (-pin1_posY + cclearance) * 2 + pad_length
        # round size to nearest 0.02mm, rectangle will thus land on a 0.01mm grid
        sizex = pcbnew.PutOnGridMM(sizex, 0.02)
        sizey = pcbnew.PutOnGridMM(sizey, 0.02)
        # set courtyard line thickness to the one defined in KLC
        self.draw.SetLineThickness(pcbnew.FromMM(0.05))
        self.draw.Box(0, 0, sizex, sizey)
        # restore line thickness to previous value
        self.draw.SetLineThickness(pcbnew.FromMM(cmargin))

        #reference and value
        text_size = self.GetTextSize()  # IPC nominal

        if num_rows == 1:
            text_py = ssy + text_size
            self.draw.Value(0, -text_py, text_size)
            self.draw.Reference(0, text_py, text_size)
        else:
            text_px = ssx + text_size
            # self.draw.Value(text_px, 0, text_size, orientation_degree=90)
            self.draw.Value(0, 0, text_size)
            self.draw.Reference(-text_px, 0, text_size, orientation_degree=90)

        # set the attribute
        if self.GetName() == "S-DIP":
            self.module.SetAttributes(pcbnew.MOD_DEFAULT)
        elif self.GetName() == "SOIC":
            self.module.SetAttributes(pcbnew.MOD_CMS)
Exemple #3
0
    def BuildThisFootprint(self):

        pad_count = self.pads['pad count']
        pad_Vsize = self.pads['pad height']
        pad_Hsize = self.pads['pad width']
        line_pitch = self.pads['line spacing']
        pad_pitch = self.pads['pitch']
        line_count = self.pads['line count']

        if line_count == 1:
            singleline = True
        else:
            singleline = False

        # add in the pads
        pad = self.GetPad()

        array = PA.PadZGridArray(pad, pad_count, line_count, line_pitch,
                                 pad_pitch)
        array.AddPadsToModule(self.draw)

        # draw the Silk Screen
        pads_per_line = pad_count // line_count
        row_length = pad_pitch * (pads_per_line - 1)  # fenceposts
        ssx_offset = pad_Hsize / 2 + self.body['outline x margin']
        ssy_offset = pad_Vsize / 2 + self.body['outline y margin']

        pin1posX = pad_pitch * (pad_count - 1) / 2
        pin1posY = line_pitch * (line_count - 1) / 2
        leftx = pin1posX + ssx_offset
        lowy = pin1posY + ssy_offset

        cornery = lowy

        # body inside pads is possible only for 2 rows.
        # for other values, there is no room
        linew = self.draw.GetLineThickness()
        if self.body['silkscreen inside'] and line_count == 2:
            cornery = pin1posY - ssy_offset
            if cornery < linew:
                cornery = linew

        thick = self.draw.GetLineThickness()
        self.draw.SetLineThickness(
            pcbnew.FromMM(0.12))  #Default per KLC F5.1 as of 12/2018
        self.DrawBox(leftx * 2, cornery * 2)

        # Courtyard
        cmarginx = self.body['courtyard margin']
        cmarginy = cmarginx
        self.draw.SetLayer(pcbnew.F_CrtYd)
        sizex = (pin1posX + cmarginx) * 2 + pad_Hsize + thick
        sizey = (pin1posY + cmarginy) * 2 + pad_Vsize + thick
        # round size to nearest 0.1mm, rectangle will thus land on a 0.05mm grid
        sizex = pcbnew.PutOnGridMM(sizex, 0.1)
        sizey = pcbnew.PutOnGridMM(sizey, 0.1)
        # set courtyard line thickness to the one defined in KLC
        self.draw.SetLineThickness(pcbnew.FromMM(0.05))
        self.draw.Box(0, 0, sizex, sizey)
        # restore line thickness to previous value
        self.draw.SetLineThickness(pcbnew.FromMM(thick))

        #reference and value
        text_size = self.GetTextSize()  # IPC nominal
        t_posy = lowy + text_size

        self.draw.Value(0, t_posy, text_size)
        self.draw.Reference(0, -t_posy, text_size)

        # set SMD attribute
        if self.GetName() == "ZIP":
            self.module.SetAttributes(pcbnew.PAD_ATTRIB_PTH)
        elif self.GetName() == "ZOIC":
            self.module.SetAttributes(pcbnew.PAD_ATTRIB_SMD)
Exemple #4
0
    def BuildThisFootprint(self):
        pads = self.parameters["Pads"]
        body = self.parameters["Body"]
        numPads = pads[self.padCountKey]
        padLength = pads[self.padLengthKey]
        rowPitch = pads[self.rowSpacingKey]
        padPitch = pads[self.padPitchKey]
        staggerOffset = pads[self.staggerOffsetKey]

        drawWithLock = body[self.withLockKey]
        numRows = 2

        # Use value to fill the modules description
        desc = self.GetValue()
        self.module.SetDescription(desc)
        self.module.SetAttributes(1)

        # add in the pads
        pad = self.GetPad()

        array = PadStaggeredZGridArray(pad, numPads, numRows, rowPitch,
                                       padPitch, staggerOffset)
        array.AddPadsToModule(self.draw)

        # Draw connector outlineChassis
        width = pcbnew.FromMM(1.92) + (numPads * padPitch) / 2
        height = pcbnew.FromMM(5)

        # Left part
        #  --
        #  |
        #  ----
        self.draw.Polyline([
            (-width / 2 + pcbnew.FromMM(0.5), -height / 2),
            (-width / 2, -height / 2), (-width / 2, height / 2),
            (-width / 2 + pcbnew.FromMM(0.5) + padPitch / 2, height / 2)
        ])

        if drawWithLock:
            # Right part with pol slot
            #  ----
            #     [
            #    --
            self.draw.Polyline([(width / 2 - pcbnew.FromMM(0.5) - padPitch / 2,
                                 -height / 2), (width / 2, -height / 2),
                                (width / 2, -height / 2 + pcbnew.FromMM(1.25)),
                                (width / 2 - pcbnew.FromMM(0.7),
                                 -height / 2 + pcbnew.FromMM(1.25)),
                                (width / 2 - pcbnew.FromMM(0.7),
                                 height / 2 - pcbnew.FromMM(1.25)),
                                (width / 2, height / 2 - pcbnew.FromMM(1.25)),
                                (width / 2, height / 2),
                                (width / 2 - pcbnew.FromMM(0.5), height / 2)])
        else:
            # Right part without pol slot
            #  ----
            #     |
            #    --
            self.draw.Polyline([(width / 2 - pcbnew.FromMM(0.5) - padPitch / 2,
                                 -height / 2), (width / 2, -height / 2),
                                (width / 2, height / 2),
                                (width / 2 - pcbnew.FromMM(0.5), height / 2)])

        # Courtyard
        self.draw.SetLayer(pcbnew.F_CrtYd)
        self.draw.SetLineThickness(pcbnew.FromMM(0.05))
        boxW = width + pcbnew.FromMM(0.5)
        boxH = rowPitch + padLength + pcbnew.FromMM(0.5)

        # Round courtyard positions to 0.1 mm, rectangle will thus land on a 0.05mm grid
        pcbnew.PutOnGridMM(boxW, pcbnew.FromMM(0.10))
        pcbnew.PutOnGridMM(boxH, pcbnew.FromMM(0.10))
        self.draw.Box(0, 0, boxW, boxH)

        #reference and value
        text_size = pcbnew.FromMM(1.0)  # According KLC
        text_offset = boxH / 2 + text_size

        self.draw.Value(0, text_offset, text_size)
        self.draw.Reference(0, -text_offset, text_size)
    def BuildThisFootprint(self):
        p = self.parameters
        pad_count = int(p["Pads"]["n"])
        pad_width = p["Pads"]["width"]
        pad_height = p["Pads"]["height"]
        pad_pitch = p["Pads"]["pitch"]
        shl_width = p["Shield"]["width"]
        shl_height = p["Shield"]["height"]
        shl_to_pad = p["Shield"]["shield_to_pad"]
        shl_from_top = p["Shield"]["from_top"]

        offsetX = pad_pitch * (pad_count - 1) / 2
        size_pad = pcbnew.wxSize(pad_width, pad_height)
        size_shld = pcbnew.wxSize(shl_width, shl_height)
        size_text = self.GetTextSize()  # IPC nominal

        # Gives a position and size to ref and value texts:
        textposy = pad_height / 2 + pcbnew.FromMM(1) + self.GetTextThickness()
        angle_degree = 0.0
        self.draw.Reference(0, textposy, size_text, angle_degree)

        textposy = textposy + size_text + self.GetTextThickness()
        self.draw.Value(0, textposy, size_text)

        # create a pad array and add it to the module
        for n in range(0, pad_count):
            xpos = pad_pitch * n - offsetX
            pad = self.smdRectPad(self.module, size_pad,
                                  pcbnew.wxPoint(xpos, 0), str(n + 1))
            self.module.Add(pad)

        # Mechanical shield pads: left pad and right pad
        xpos = -shl_to_pad - offsetX
        pad_s0_pos = pcbnew.wxPoint(xpos, shl_from_top)
        pad_s0 = self.smdRectPad(self.module, size_shld, pad_s0_pos, "0")
        xpos = (pad_count - 1) * pad_pitch + shl_to_pad - offsetX
        pad_s1_pos = pcbnew.wxPoint(xpos, shl_from_top)
        pad_s1 = self.smdRectPad(self.module, size_shld, pad_s1_pos, "0")

        self.module.Add(pad_s0)
        self.module.Add(pad_s1)

        # add footprint outline
        self.draw.SetLineThickness(
            pcbnew.FromMM(0.12))  #Default per KLC F5.1 as of 12/2018
        linewidth = self.draw.GetLineThickness()
        margin = linewidth

        # upper line
        posy = -pad_height / 2 - linewidth / 2 - margin
        xstart = -pad_pitch * 0.5 - offsetX
        xend = pad_pitch * pad_count + xstart
        min_y = posy
        max_y = posy
        self.draw.Line(xstart, posy, xend, posy)

        # lower line
        posy = pad_height / 2 + linewidth / 2 + margin
        max_y = max(max_y, posy)
        self.draw.Line(xstart, posy, xend, posy)

        # around left mechanical pad (the outline around right pad is mirrored/y axix)
        yend = pad_s0_pos.y + shl_height / 2 + margin
        max_y = max(max_y, yend)
        self.draw.Line(xstart, posy, xstart, yend)
        self.draw.Line(-xstart, posy, -xstart, yend)

        posy = yend
        xend = pad_s0_pos.x - (shl_width / 2 + linewidth + margin * 2)
        max_x = -xend
        self.draw.Line(xstart, posy, xend, posy)

        # right pad side
        self.draw.Line(-xstart, posy, -xend, yend)

        # set SMD attribute
        self.module.SetAttributes(pcbnew.MOD_SMD)

        # vertical segment at left of the pad
        xstart = xend
        yend = posy - (shl_height + linewidth + margin * 2)
        self.draw.Line(xstart, posy, xend, yend)

        # right pad side
        self.draw.Line(-xstart, posy, -xend, yend)
        max_y = max(max_y, posy)
        min_y = min(min_y, yend)

        # horizontal segment above the pad
        xstart = xend
        xend = -pad_pitch * 0.5 - offsetX
        posy = yend
        self.draw.Line(xstart, posy, xend, yend)

        # right pad side
        self.draw.Line(-xstart, posy, -xend, yend)

        # vertical segment above the pad
        xstart = xend
        yend = -pad_height / 2 - linewidth / 2 - margin
        min_y = min(min_y, yend)
        self.draw.Line(xstart, posy, xend, yend)

        # right pad side
        self.draw.Line(-xstart, posy, -xend, yend)

        # Courtyard
        self.draw.SetLayer(pcbnew.F_CrtYd)
        max_x = max_x + linewidth + margin
        min_y = min_y - linewidth - margin
        max_y = max_y + linewidth + margin

        # round size to nearest 0.1mm, rectangle will thus land on a 0.05mm grid
        max_x = pcbnew.PutOnGridMM(max_x, 0.05)
        max_y = pcbnew.PutOnGridMM(max_y, 0.05)
        min_y = pcbnew.PutOnGridMM(min_y, 0.05)

        # set courtyard line thickness to the one defined in KLC
        self.draw.SetLineThickness(pcbnew.FromMM(0.05))
        self.draw.Line(-max_x, min_y, max_x, min_y)
        self.draw.Line(max_x, min_y, max_x, max_y)
        self.draw.Line(-max_x, max_y, max_x, max_y)
        self.draw.Line(-max_x, min_y, -max_x, max_y)
    def BuildThisFootprint(self):

        pad_pitch = self.pads["pitch"]
        pad_length = self.pads["length"]
        pad_width = self.pads["width"]

        v_pitch = self.pads["vertical spacing"]
        h_pitch = self.pads["horizontal spacing"]

        pads_per_col = int(self.pads["nx"])
        pads_per_row = int(self.pads["ny"])

        row_len = (pads_per_row - 1) * pad_pitch
        col_len = (pads_per_col - 1) * pad_pitch

        pad_shape = pcbnew.PAD_SHAPE_OVAL if self.pads["oval"] else pcbnew.PAD_SHAPE_RECT

        h_pad = PA.PadMaker(self.module).SMDPad( pad_length, pad_width,
                                                 shape=pad_shape, rot_degree=90.0)
        v_pad = PA.PadMaker(self.module).SMDPad( pad_length, pad_width, shape=pad_shape)

        #left row
        pin1Pos = pcbnew.wxPoint(-h_pitch / 2, 0)
        array = PA.PadLineArray(h_pad, pads_per_row, pad_pitch, True, pin1Pos)
        array.SetFirstPadInArray(1)
        array.AddPadsToModule(self.draw)

        #bottom row
        pin1Pos = pcbnew.wxPoint(0, v_pitch / 2)
        array = PA.PadLineArray(v_pad, pads_per_col, pad_pitch, False, pin1Pos)
        array.SetFirstPadInArray( pads_per_row + 1)
        array.AddPadsToModule(self.draw)

        #right row
        pin1Pos = pcbnew.wxPoint(h_pitch / 2, 0)
        array = PA.PadLineArray(h_pad, pads_per_row, -pad_pitch, True,
                                pin1Pos)
        array.SetFirstPadInArray( pads_per_row + pads_per_col + 1)
        array.AddPadsToModule(self.draw)

        #top row
        pin1Pos = pcbnew.wxPoint(0, -v_pitch / 2)
        array = PA.PadLineArray(v_pad, pads_per_col, -pad_pitch, False,
                                pin1Pos)
        array.SetFirstPadInArray( 2*pads_per_row + pads_per_col + 1)
        array.AddPadsToModule(self.draw)

        offset = pcbnew.FromMM(0.15)

        x = self.parameters["Package"]["width"] / 2 + offset
        y = self.parameters["Package"]["height"] / 2 + offset
        innerY = (row_len / 2) + pad_pitch
        innerX = (col_len / 2) + pad_pitch

        # Add outline to F_Fab layer
        self.draw.SetLayer(pcbnew.F_Fab)
        thick = self.draw.GetLineThickness()

        bevel = min( pcbnew.FromMM(1.0), self.package['width']/2, self.package['height']/2 )

        w = self.package['width']
        h = self.package['height']

        # outermost limits of pins
        right_edge = (h_pitch + pad_length) / 2
        left_edge = -right_edge

        bottom_edge = (v_pitch + pad_length) / 2
        top_edge = -bottom_edge

        self.draw.SetLineThickness( pcbnew.FromMM( 0.1 ) ) #Default per KLC F5.2 as of 12/2018
        self.draw.BoxWithDiagonalAtCorner(0, 0, w, h, bevel)

        # Draw silkscreen
        self.draw.SetLayer( pcbnew.F_SilkS )
        self.draw.SetLineThickness( pcbnew.FromMM( 0.12 ) ) #Default per KLC F5.1 as of 12/2018

        #top left - as per IPC-7351C
        self.draw.Polyline([(-innerX, -y), (-x, -y), (-x, -innerY), (left_edge, -innerY)])
        # top right
        self.draw.Polyline([(innerX, -y), (x, -y), (x, -innerY)])
        # bottom left
        self.draw.Polyline([(-innerX, y), (-x, y), (-x, innerY)])
        # bottom right
        self.draw.Polyline([(innerX, y), (x, y), (x, innerY)])

        # Courtyard
        cmargin = self.parameters["Package"]["courtyard margin"]
        self.draw.SetLayer( pcbnew.F_CrtYd )
        sizex = ( right_edge + cmargin ) * 2
        sizey = ( bottom_edge + cmargin ) * 2
        # round size to nearest 0.1mm, rectangle will thus land on a 0.05mm grid
        sizex = pcbnew.PutOnGridMM( sizex, 0.1 )
        sizey = pcbnew.PutOnGridMM( sizey, 0.1 )

        self.draw.SetLineThickness( pcbnew.FromMM( 0.05 ) ) #Default per KLC F5.3 as of 12/2018
        self.draw.Box( 0, 0, sizex, sizey )
        # restore line thickness to previous value
        self.draw.SetLineThickness(pcbnew.FromMM(thick))

        #reference and value
        text_size = self.GetTextSize()  # IPC nominal
        text_offset = v_pitch / 2 + text_size + pad_length / 2

        self.draw.Value(0, text_offset, text_size)
        self.draw.Reference(0, -text_offset, text_size)

        # set SMD attribute
        self.module.SetAttributes(pcbnew.MOD_CMS)
    def BuildThisFootprint(self):

        pads = self.parameters["Pads"]

        rows = pads["rows"]
        cols = pads["columns"]
        pad_size = pads["size"]
        pad_size = pcbnew.wxSize(pad_size, pad_size)
        pad_pitch = pads["pitch"]

        # add in the pads
        pad = PA.PadMaker(self.module).SMTRoundPad(pads["size"])

        pin1_pos = pcbnew.wxPoint(-((cols - 1) * pad_pitch) / 2,
                                  -((rows - 1) * pad_pitch) / 2)

        array = BGAPadGridArray(pad, cols, rows, pad_pitch, pad_pitch)
        array.AddPadsToModule(self.draw)

        # Draw box outline on F.Fab layer
        self.draw.SetLayer(pcbnew.F_Fab)
        ssx = self.parameters['Package']['width'] / 2
        ssy = self.parameters['Package']['length'] / 2

        # Bevel should be 1mm nominal but we'll allow smaller values
        if pcbnew.ToMM(ssx) < 1:
            bevel = ssx
        else:
            bevel = pcbnew.FromMM(1)

        # Box with 1mm bevel as per IPC7351C
        self.draw.SetLineThickness( pcbnew.FromMM( 0.1 ) ) #Default per KLC F5.2 as of 12/2018
        self.draw.BoxWithDiagonalAtCorner(0, 0, ssx*2, ssy*2, bevel)

        # Add IPC markings to F_Silk layer
        self.draw.SetLayer( pcbnew.F_SilkS )
        self.draw.SetLineThickness( pcbnew.FromMM( 0.12 ) ) #Default per KLC F5.1 as of 12/2018
        offset = self.draw.GetLineThickness()
        len_x  = 0.5 * ssx
        len_y  = 0.5 * ssy

        edge = [
            [ ssx + offset - len_x, -ssy - offset],
            [ ssx + offset, -ssy - offset],
            [ ssx + offset, -ssy - offset + len_y],
               ]

        # Draw three square edges
        self.draw.Polyline(edge)
        self.draw.Polyline(edge, mirrorY=0)
        self.draw.Polyline(edge, mirrorX=0, mirrorY=0)

        # Draw pin-1 marker
        bevel += offset
        pin1 = [
            [ -ssx - offset + len_x, -ssy - offset],
            [ -ssx - offset + bevel, -ssy - offset],
            [ -ssx - offset, -ssy - offset + bevel],
            [ -ssx - offset, -ssy - offset + len_y],
                ]

        # Remove lines if the package is too small
        if bevel > len_x:
            pin1 = pin1[1:]

        if bevel > len_y:
            pin1 = pin1[:-1]

        self.draw.Polyline(pin1)

        # Draw a circle in the bevel void
        self.draw.Circle( -ssx, -ssy, pcbnew.FromMM(0.2), filled=True)

        # Courtyard
        cmargin = self.parameters['Package']['margin']
        self.draw.SetLayer(pcbnew.F_CrtYd)
        sizex = (ssx + cmargin) * 2
        sizey = (ssy + cmargin) * 2

        # round size to nearest 0.1mm, rectangle will thus land on a 0.05mm grid
        sizex = pcbnew.PutOnGridMM(sizex, 0.1)
        sizey = pcbnew.PutOnGridMM(sizey, 0.1)

        # set courtyard line thickness to the one defined in KLC
        self.draw.SetLineThickness(pcbnew.FromMM(0.05))
        self.draw.Box(0, 0, sizex, sizey)
        # restore line thickness to previous value
        self.draw.SetLineThickness(pcbnew.FromMM(cmargin))

        #reference and value
        text_size = self.GetTextSize()  # IPC nominal
        ypos = ssy + text_size
        self.draw.Value(0, ypos, text_size)
        self.draw.Reference(0, -ypos, text_size)

        # set SMD attribute
        self.module.SetAttributes(pcbnew.MOD_CMS)
Exemple #8
0
    def BuildThisFootprint(self):
        pads = self.parameters["Pads"]

        pad_pitch = pads["pitch"]
        pad_length = pads["length"]
        pad_width = pads["width"]

        v_pitch = pads["pitch"]
        h_pitch = pads["pitch"]

        pads_per_row = pads["n"] // 4

        row_len = (pads_per_row - 1) * pad_pitch

        pad_shape = pcbnew.PAD_SHAPE_OVAL if pads["oval"] else pcbnew.PAD_SHAPE_RECT

        h_pad = PA.PadMaker(self.module).SMDPad( pad_length, pad_width,
                                                 shape=pad_shape, rot_degree=90.0)
        v_pad = PA.PadMaker(self.module).SMDPad( pad_length, pad_width, shape=pad_shape)

        #left row
        pin1Pos = pcbnew.wxPoint(-h_pitch / 2, 0)
        array = PA.PadLineArray(h_pad, pads_per_row, pad_pitch, True, pin1Pos)
        array.SetFirstPadInArray(1)
        array.AddPadsToModule(self.draw)

        #bottom row
        pin1Pos = pcbnew.wxPoint(0, v_pitch / 2)
        array = PA.PadLineArray(v_pad, pads_per_row, pad_pitch, False, pin1Pos)
        array.SetFirstPadInArray(pads_per_row + 1)
        array.AddPadsToModule(self.draw)

        #right row
        pin1Pos = pcbnew.wxPoint(h_pitch / 2, 0)
        array = PA.PadLineArray(h_pad, pads_per_row, -pad_pitch, True,
                                pin1Pos)
        array.SetFirstPadInArray(2*pads_per_row + 1)
        array.AddPadsToModule(self.draw)

        #top row
        pin1Pos = pcbnew.wxPoint(0, -v_pitch / 2)
        array = PA.PadLineArray(v_pad, pads_per_row, -pad_pitch, False,
                                pin1Pos)
        array.SetFirstPadInArray(3*pads_per_row + 1)
        array.AddPadsToModule(self.draw)

        lim_x = self.parameters["Package"]["width"] / 2
        lim_y = self.parameters["Package"]["height"] / 2
        inner = (row_len / 2) + pad_pitch

        #top left - diagonal
        self.draw.Line(-lim_x, -inner, -inner, -lim_y)
        # top right
        self.draw.Polyline([(inner, -lim_y), (lim_x, -lim_y), (lim_x, -inner)])
        # bottom left
        self.draw.Polyline([(-inner, lim_y), (-lim_x, lim_y), (-lim_x, inner)])
        # bottom right
        self.draw.Polyline([(inner, lim_y), (lim_x, lim_y), (lim_x, inner)])

        # Courtyard
        cmargin = self.parameters["Package"]["courtyard margin"]
        self.draw.SetLayer(pcbnew.F_CrtYd)
        sizex = (lim_x + cmargin) * 2 + pad_length
        sizey = (lim_y + cmargin) * 2 + pad_length
        # round size to nearest 0.1mm, rectangle will thus land on a 0.05mm grid
        sizex = pcbnew.PutOnGridMM(sizex, 0.1)
        sizey = pcbnew.PutOnGridMM(sizey, 0.1)
        # set courtyard line thickness to the one defined in KLC
        thick = self.draw.GetLineThickness()
        self.draw.SetLineThickness(pcbnew.FromMM(0.05))
        self.draw.Box(0, 0, sizex, sizey)
        # restore line thickness to previous value
        self.draw.SetLineThickness(pcbnew.FromMM(thick))

        #reference and value
        text_size = self.GetTextSize()  # IPC nominal
        text_offset = v_pitch / 2 + text_size + pad_length / 2

        self.draw.Value(0, text_offset, text_size)
        self.draw.Reference(0, -text_offset, text_size)

        # set SMD attribute
        self.module.SetAttributes(pcbnew.MOD_CMS)