JLC2KiCadLib 1.0.33__tar.gz → 1.0.36__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of JLC2KiCadLib might be problematic. Click here for more details.

Files changed (23) hide show
  1. jlc2kicadlib-1.0.36/JLC2KiCadLib/__version__.py +1 -0
  2. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/footprint/footprint.py +1 -1
  3. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/footprint/footprint_handlers.py +129 -117
  4. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/footprint/model3d.py +1 -1
  5. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/symbol/symbol.py +1 -2
  6. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/symbol/symbol_handlers.py +5 -0
  7. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib.egg-info/PKG-INFO +1 -1
  8. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/PKG-INFO +1 -1
  9. jlc2kicadlib-1.0.33/JLC2KiCadLib/__version__.py +0 -1
  10. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/JLC2KiCadLib.py +0 -0
  11. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/__init__.py +0 -0
  12. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/footprint/__init__.py +0 -0
  13. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/helper.py +0 -0
  14. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib/symbol/__init__.py +0 -0
  15. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib.egg-info/SOURCES.txt +0 -0
  16. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib.egg-info/dependency_links.txt +0 -0
  17. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib.egg-info/entry_points.txt +0 -0
  18. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib.egg-info/requires.txt +0 -0
  19. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/JLC2KiCadLib.egg-info/top_level.txt +0 -0
  20. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/LICENSE +0 -0
  21. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/README.md +0 -0
  22. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/setup.cfg +0 -0
  23. {jlc2kicadlib-1.0.33 → jlc2kicadlib-1.0.36}/setup.py +0 -0
@@ -0,0 +1 @@
1
+ __version__ = "1.0.36"
@@ -17,7 +17,7 @@ def create_footprint(
17
17
  skip_existing,
18
18
  models,
19
19
  ):
20
- logging.info("creating footprint ...")
20
+ logging.info("Creating footprint ...")
21
21
 
22
22
  (
23
23
  footprint_name,
@@ -1,9 +1,19 @@
1
1
  import json
2
2
  import logging
3
- from math import pow, acos, pi
3
+ from math import pow, acos, pi, sqrt
4
4
  import re
5
5
 
6
- from KicadModTree import *
6
+ from KicadModTree import (
7
+ Line,
8
+ Pad,
9
+ Polygon,
10
+ Vector2D,
11
+ Arc,
12
+ Circle,
13
+ RectFill,
14
+ Text,
15
+ RectLine,
16
+ )
7
17
  from .model3d import get_WrlModel, get_StepModel
8
18
 
9
19
  __all__ = [
@@ -79,106 +89,113 @@ def h_PAD(data, kicad_mod, footprint_info):
79
89
  """
80
90
  Append a pad to the footprint
81
91
 
82
- data : {
92
+ data : [
83
93
  0 : shape type
84
94
  1 : pad position x
85
- 1 : pad position y
95
+ 2 : pad position y
86
96
  3 : pad size x
87
97
  4 : pad size y
88
- 5 :
98
+ 5 : layer
89
99
  6 : pad number
90
100
  7 : drill size
91
- 8 :
92
- }
101
+ 8 : Polygon nodes "skipped for some shapes"
102
+ 9 : rotation
103
+ 10 :
104
+ 11 : drill offset
105
+ 12 :
106
+ 13 :
107
+ 14 :
108
+ 15 :
109
+ 16 :
110
+ 17 : ? position
111
+ ]
93
112
  """
94
- # pylint: disable=unused-argument
95
-
96
- shape_correspondance = {
97
- "OVAL": "SHAPE_OVAL",
98
- "RECT": "SHAPE_RECT",
99
- "ELLIPSE": "SHAPE_CIRCLE",
100
- "POLYGON": "SHAPE_CUSTOM",
101
- }
102
113
 
103
- data[1] = mil2mm(data[1])
104
- data[2] = mil2mm(data[2])
105
- data[3] = mil2mm(data[3])
106
- data[4] = mil2mm(data[4])
107
- data[7] = mil2mm(data[7])
114
+ # PAD layer definition
115
+ TOPLAYER = "1"
116
+ BOTTOMLAYER = "2"
117
+ MULTILAYER = "11"
108
118
 
109
- at = [data[1], data[2]]
110
- size = [data[3], data[4]]
119
+ shape_type = data[0]
120
+ at = [mil2mm(data[1]), mil2mm(data[2])]
121
+ size = [mil2mm(data[3]), mil2mm(data[4])]
122
+ layer = data[5]
111
123
  pad_number = data[6]
124
+ drill_diameter = float(mil2mm(data[7])) * 2
125
+ drill_size = drill_diameter
126
+
127
+ # Some shape do not have coordinates, insert empty data to realign later index
128
+ if shape_type in ["ELLIPSE"]:
129
+ data.insert(8, "")
130
+
131
+ rotation = float(data[9])
132
+ drill_offset = float(mil2mm(data[11]))
133
+
112
134
  primitives = ""
113
135
 
114
- if data[5] == "1":
136
+ if layer == MULTILAYER:
137
+ pad_type = Pad.TYPE_THT
138
+ pad_layer = Pad.LAYERS_THT
139
+ elif layer == TOPLAYER:
115
140
  pad_type = Pad.TYPE_SMT
116
141
  pad_layer = Pad.LAYERS_SMT
117
- drill_size = 1
142
+ elif layer == BOTTOMLAYER:
143
+ pad_type = Pad.TYPE_SMT
144
+ pad_layer = ["B.Cu", "B.Mask", "B.Paste"]
118
145
  else:
119
- pad_type = Pad.TYPE_THT
120
- pad_layer = Pad.LAYERS_THT
121
- drill_size = data[7] * 2
146
+ logging.warning(
147
+ f"footprint, h_PAD: Unrecognized pad layer. Using default SMT layer for pad {pad_number}"
148
+ )
149
+ pad_type = Pad.TYPE_SMT
150
+ pad_layer = Pad.LAYERS_SMT
122
151
 
123
152
  if data[0] == "OVAL":
124
- shape = getattr(Pad, "SHAPE_OVAL")
125
- rotation = float(data[9])
126
- data[11] = mil2mm(data[11])
153
+ shape = Pad.SHAPE_OVAL
127
154
 
128
- if data[11] == 0:
129
- drill_size = data[7] * 2
130
- elif (data[7] * 2 < data[11]) ^ (
155
+ if drill_offset == 0:
156
+ drill_size = drill_diameter
157
+ elif (drill_diameter < drill_offset) ^ (
131
158
  size[0] > size[1]
132
159
  ): # invert the orientation of the drill hole if not in the same orientation as the pad shape
133
- drill_size = [data[7] * 2, data[11]]
160
+ drill_size = [drill_diameter, drill_offset]
134
161
  else:
135
- drill_size = [data[11], data[7] * 2]
162
+ drill_size = [drill_offset, drill_diameter]
136
163
 
137
164
  elif data[0] == "RECT":
138
- shape = getattr(Pad, "SHAPE_RECT")
139
- rotation = float(data[9])
140
- data[11] = mil2mm(data[11])
165
+ shape = Pad.SHAPE_RECT
141
166
 
142
- if data[5] == "1":
143
- drill_size = 1
144
- elif float(data[11]) == 0: # Check if the hole is oval
145
- pass
167
+ if drill_offset == 0:
168
+ drill_size = drill_diameter
146
169
  else:
147
- drill_size = [data[7] * 2, data[11]]
170
+ drill_size = [drill_diameter, drill_offset]
148
171
 
149
172
  elif data[0] == "ELLIPSE":
150
- shape = getattr(Pad, "SHAPE_CIRCLE")
151
- # if pad is a circle, no rotation is specified
152
- rotation = 0
173
+ shape = Pad.SHAPE_CIRCLE
153
174
 
154
175
  elif data[0] == "POLYGON":
155
- shape = getattr(Pad, "SHAPE_CUSTOM")
156
- data[11] = mil2mm(data[11])
157
- rotation = float(data[9])
176
+ shape = Pad.SHAPE_CUSTOM
158
177
  points = []
159
178
  for i, coord in enumerate(data[8].split(" ")):
160
179
  points.append(mil2mm(coord) - at[i % 2])
161
180
  primitives = [Polygon(nodes=zip(points[::2], points[1::2]))]
162
181
  size = [0.1, 0.1]
163
- rotation = 0
164
182
 
165
- if float(data[11]) == 0: # Check if the hole is oval
183
+ if drill_offset == 0: # Check if the hole is oval
166
184
  drill_size = 1
167
185
  else:
168
- drill_size = [data[7] * 2, data[11]]
186
+ drill_size = [drill_diameter, drill_offset]
169
187
 
170
188
  else:
171
189
  logging.error(
172
- "footprint handler, pad : no correspondance found, using default SHAPE_OVAL"
190
+ f"footprint handler, pad : no correspondance found, using default SHAPE_OVAL for pad {pad_number}"
173
191
  )
174
- shape = getattr(Pad, "SHAPE_OVAL")
175
- rotation = float(data[9])
192
+ shape = Pad.SHAPE_OVAL
176
193
 
177
194
  # update footprint borders
178
- footprint_info.max_X = max(footprint_info.max_X, data[1])
179
- footprint_info.min_X = min(footprint_info.min_X, data[1])
180
- footprint_info.max_Y = max(footprint_info.max_Y, data[2])
181
- footprint_info.min_Y = min(footprint_info.min_Y, data[2])
195
+ footprint_info.max_X = max(footprint_info.max_X, at[0])
196
+ footprint_info.min_X = min(footprint_info.min_X, at[0])
197
+ footprint_info.max_Y = max(footprint_info.max_Y, at[1])
198
+ footprint_info.min_Y = min(footprint_info.min_Y, at[1])
182
199
 
183
200
  kicad_mod.append(
184
201
  Pad(
@@ -196,49 +213,50 @@ def h_PAD(data, kicad_mod, footprint_info):
196
213
 
197
214
 
198
215
  def h_ARC(data, kicad_mod, footprint_info):
199
- # append an Arc to the footprint
216
+ """
217
+ append an Arc to the footprint
218
+ """
219
+ # pylint: disable=unused-argument
220
+
200
221
  try:
201
- # parse the data
202
- if data[2][0] == "M":
203
- startX, startY, midX, midY, _, reversed, direction, endX, endY = [
204
- val
205
- for val in data[2]
206
- .replace("M", "")
207
- .replace("A", "")
208
- .replace(",", " ")
209
- .split(" ")
210
- if val
211
- ]
212
- elif data[3][0] == "M":
213
- startX, startY, midX, midY, _, reversed, direction, endX, endY = [
214
- val
215
- for val in data[3]
216
- .replace("M", "")
217
- .replace("A", "")
218
- .replace(",", " ")
219
- .split(" ")
220
- if val
221
- ]
222
+
223
+ # "S$xx" is sometimes inserted at index 2 ?
224
+ if "$" in data[2]:
225
+ svg_path = data[3]
222
226
  else:
223
- logging.warning(
224
- "footprint handler, h_ARC : failed to parse footprint ARC data"
225
- )
227
+ svg_path = data[2]
228
+
229
+ # Regular expression to match ARC pattern
230
+ # coordinates can sometime be separated by a "," instead of a space, therefore we match it using [\s,*?]
231
+ pattern = r"M\s*([\d\.\-]+)[\s,*?]([\d\.\-]+)\s?A\s*([\d\.\-]+)[\s,*?]([\d\.\-]+) ([\d\.\-]+) (\d) (\d) ([\d\.\-]+)[\s,*?]([\d\.\-]+)"
232
+
233
+ match = re.search(pattern, svg_path)
234
+
235
+ if not match:
236
+ logging.error("footprint handler, h_ARC: Failed to parse ARC")
237
+ return
238
+
239
+ # Extract values
240
+ start_x, start_y = float(match.group(1)), float(match.group(2))
241
+ rx, ry = float(match.group(3)), float(match.group(4))
242
+ _ = float(match.group(5)) # rotation ?
243
+ large_arc_flag = int(match.group(6))
244
+ sweep_flag = int(match.group(7))
245
+ end_x, end_y = float(match.group(8)), float(match.group(9))
246
+
226
247
  width = data[0]
227
248
 
228
249
  width = mil2mm(width)
229
- startX = mil2mm(startX)
230
- startY = mil2mm(startY)
231
- midX = mil2mm(midX)
232
- midY = mil2mm(midY)
233
- endX = mil2mm(endX)
234
- endY = mil2mm(endY)
235
-
236
- if midX != midY:
237
- logging.warning("Unexpected arc, midX != midY")
238
-
239
- start = [startX, startY]
240
- end = [endX, endY]
241
- if direction == "0":
250
+ start_x = mil2mm(start_x)
251
+ start_y = mil2mm(start_y)
252
+ mid_x = mil2mm(rx)
253
+ mid_y = mil2mm(ry)
254
+ end_x = mil2mm(end_x)
255
+ end_y = mil2mm(end_y)
256
+
257
+ start = [start_x, start_y]
258
+ end = [end_x, end_y]
259
+ if sweep_flag == 0:
242
260
  start, end = end, start
243
261
 
244
262
  # find the midpoint of start and end
@@ -247,12 +265,12 @@ def h_ARC(data, kicad_mod, footprint_info):
247
265
  vec1 = Vector2D(mid[0] - start[0], mid[1] - start[1])
248
266
 
249
267
  # create vector that's normal to vec1:
250
- length_squared = pow(midX, 2) - pow(vec1.distance_to((0, 0)), 2)
268
+ length_squared = mid_x * mid_y - pow(vec1.distance_to((0, 0)), 2)
251
269
  if length_squared < 0:
252
270
  length_squared = 0
253
- reversed = "1"
271
+ large_arc_flag = 1
254
272
 
255
- if reversed == "1":
273
+ if large_arc_flag == 1:
256
274
  vec2 = vec1.rotate(-90)
257
275
  else:
258
276
  vec2 = vec1.rotate(90)
@@ -285,25 +303,19 @@ def h_ARC(data, kicad_mod, footprint_info):
285
303
  try:
286
304
  layer = layer_correspondance[data[1]]
287
305
  except KeyError:
288
- logging.warning("footprint handler, h_ARC : layer correspondance not found")
289
- layer = "F.SilkS"
290
- if reversed == "1":
291
- kicad_mod.append(
292
- Arc(
293
- start=start,
294
- end=end,
295
- width=width,
296
- angle=360 - angle,
297
- center=cen,
298
- layer=layer,
299
- )
300
- )
301
- else:
302
- kicad_mod.append(
303
- Arc(start=start, end=end, width=width, center=cen, layer=layer)
306
+ logging.warning(
307
+ "footprint handler, h_ARC : layer correspondance not found. Adding arc on default F.Silks layer"
304
308
  )
309
+ layer = "F.SilkS"
305
310
 
306
- except Exception as e:
311
+ if large_arc_flag == 1:
312
+ angle = 360 - angle
313
+
314
+ kicad_mod.append(
315
+ Arc(start=start, end=end, width=width, center=cen, layer=layer)
316
+ )
317
+
318
+ except Exception:
307
319
  logging.exception("footprint handler, h_ARC: failed to add ARC")
308
320
 
309
321
 
@@ -2,7 +2,7 @@ import requests
2
2
  import logging
3
3
  import os
4
4
  import re
5
- from KicadModTree import *
5
+ from KicadModTree import Model
6
6
 
7
7
  wrl_header = """#VRML V2.0 utf8
8
8
  #created by JLC2KiCad_lib using the JLCPCB library
@@ -4,7 +4,6 @@ import re
4
4
  import os
5
5
  import logging
6
6
 
7
- from KicadModTree import *
8
7
  from .symbol_handlers import *
9
8
 
10
9
 
@@ -91,7 +90,7 @@ def create_symbol(
91
90
 
92
91
  filename = f"{output_dir}/{symbol_path}/{library_name}.kicad_sym"
93
92
 
94
- logging.info(f"creating symbol {component_title} in {library_name}")
93
+ logging.info(f"Creating symbol {component_title} in {library_name}")
95
94
 
96
95
  kicad_symbol.drawing += f'''\n (symbol "{component_title}_1"'''
97
96
 
@@ -109,6 +109,11 @@ def h_P(data, translation, kicad_symbol):
109
109
  length = round(mil2mm(abs(float(data[8].split("h")[-1]))), 3)
110
110
  elif rotation == 90 or rotation == 270:
111
111
  length = mil2mm(abs(float(data[8].split("v")[-1])))
112
+ else:
113
+ length = 2.54
114
+ logging.warning(
115
+ f'symbol : pin number {pinNumber} : "{pinName}" failed to find length. Using Default length'
116
+ )
112
117
 
113
118
  try:
114
119
  # If on pin name/number is not hidden, show set the synmbol hide property to 0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: JLC2KiCadLib
3
- Version: 1.0.33
3
+ Version: 1.0.36
4
4
  Summary: JLC2KiCad_lib is a python script that generate a component library (symbol, footprint and 3D model) for KiCad from the JLCPCB/easyEDA library.
5
5
  Home-page: https://github.com/TousstNicolas/JLC2KiCad_lib
6
6
  Author: TousstNicolas
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: JLC2KiCadLib
3
- Version: 1.0.33
3
+ Version: 1.0.36
4
4
  Summary: JLC2KiCad_lib is a python script that generate a component library (symbol, footprint and 3D model) for KiCad from the JLCPCB/easyEDA library.
5
5
  Home-page: https://github.com/TousstNicolas/JLC2KiCad_lib
6
6
  Author: TousstNicolas
@@ -1 +0,0 @@
1
- __version__ = "1.0.33"
File without changes
File without changes
File without changes
File without changes