parent
1a73dd5e29
commit
dad1f91439
2
Makefile
2
Makefile
|
|
@ -70,7 +70,7 @@ test_docker_local_1:
|
|||
# Run in the same directory to make the __pycache__ valid
|
||||
# Also change the owner of the files to the current user (we run as root like in GitHub)
|
||||
docker run --rm -v $(CWD):$(CWD) --workdir="$(CWD)" setsoft/kicad_auto_test:latest \
|
||||
/bin/bash -c "flake8 . --count --statistics ; python3-coverage run -a src/kibot --help-outputs > /dev/null; pytest-3 --log-cli-level debug -k 'test_erc_warning_2' --test_dir output ; $(PY_COV) html; chown -R $(USER_ID):$(GROUP_ID) output/ tests/board_samples/ tests/.config/kiplot/plugins/__pycache__/ tests/test_plot/fake_pcbnew/__pycache__/ tests/.config/kibot/plugins/__pycache__/ .coverage htmlcov/"
|
||||
/bin/bash -c "flake8 . --count --statistics ; python3-coverage run -a src/kibot --help-outputs > /dev/null; pytest-3 --log-cli-level debug -k 'test_step_2' --test_dir output ; $(PY_COV) html; chown -R $(USER_ID):$(GROUP_ID) output/ tests/board_samples/ tests/.config/kiplot/plugins/__pycache__/ tests/test_plot/fake_pcbnew/__pycache__/ tests/.config/kibot/plugins/__pycache__/ .coverage htmlcov/"
|
||||
#$(PY_COV) report
|
||||
#x-www-browser htmlcov/index.html
|
||||
rm .coverage
|
||||
|
|
|
|||
|
|
@ -55,11 +55,17 @@ def un_quote(val):
|
|||
return val
|
||||
|
||||
|
||||
def expand_env(val, env):
|
||||
def expand_env(val, env, extra_env, used_extra=None):
|
||||
""" Expand KiCad environment variables """
|
||||
if used_extra is None:
|
||||
used_extra = [False]
|
||||
used_extra[0] = False
|
||||
for var in re.findall(r'\$\{(\S+)\}', val):
|
||||
if var in env:
|
||||
val = val.replace('${'+var+'}', env[var])
|
||||
elif var in extra_env:
|
||||
val = val.replace('${'+var+'}', extra_env[var])
|
||||
used_extra[0] = True
|
||||
else:
|
||||
logger.error('Unable to expand `{}` in `{}`'.format(var, val))
|
||||
return val
|
||||
|
|
@ -80,14 +86,14 @@ class LibAlias(object):
|
|||
self.descr = None
|
||||
|
||||
@staticmethod
|
||||
def parse(options, cline, env):
|
||||
def parse(options, cline, env, extra_env):
|
||||
m = LibAlias.libs_re.match(options)
|
||||
if not m:
|
||||
raise KiConfError('Malformed lib entry', SYM_LIB_TABLE, cline, options)
|
||||
lib = LibAlias()
|
||||
lib.name = un_quote(m.group(1))
|
||||
lib.legacy = m.group(2) == 'Legacy'
|
||||
lib.uri = os.path.abspath(expand_env(un_quote(m.group(3)), env))
|
||||
lib.uri = os.path.abspath(expand_env(un_quote(m.group(3)), env, extra_env))
|
||||
lib.options = un_quote(m.group(4))
|
||||
lib.descr = un_quote(m.group(5))
|
||||
return lib
|
||||
|
|
@ -337,7 +343,7 @@ class KiConf(object):
|
|||
while line and line[0] != ')':
|
||||
m = re.match(r'\s*\(lib\s*(.*)\)', line)
|
||||
if m:
|
||||
alias = LibAlias.parse(m.group(1), cline, KiConf.kicad_env)
|
||||
alias = LibAlias.parse(m.group(1), cline, KiConf.kicad_env, {})
|
||||
if GS.debug_level > 1:
|
||||
logger.debug('- Adding lib alias '+str(alias))
|
||||
KiConf.lib_aliases[alias.name] = alias
|
||||
|
|
@ -375,5 +381,7 @@ class KiConf(object):
|
|||
# Load the project's table
|
||||
KiConf.load_lib_aliases(os.path.join(KiConf.dirname, SYM_LIB_TABLE))
|
||||
|
||||
def expand_env(name):
|
||||
return os.path.abspath(expand_env(un_quote(name), KiConf.kicad_env))
|
||||
def expand_env(name, used_extra=None):
|
||||
if used_extra is None:
|
||||
used_extra = [False]
|
||||
return os.path.abspath(expand_env(un_quote(name), KiConf.kicad_env, GS.load_pro_variables(), used_extra))
|
||||
|
|
|
|||
|
|
@ -106,6 +106,7 @@ class Base3DOptions(VariantOptions):
|
|||
# List of models we already downloaded
|
||||
downloaded = set()
|
||||
self.undo_3d_models = {}
|
||||
extra_debug = GS.debug_level > 3
|
||||
# Look for all the footprints
|
||||
for m in GS.get_modules():
|
||||
ref = m.GetReference()
|
||||
|
|
@ -118,8 +119,13 @@ class Base3DOptions(VariantOptions):
|
|||
for m3d in models_l:
|
||||
if m3d.m_Filename.endswith(DISABLE_TEXT):
|
||||
# Skip models we intentionally disabled using a bogus name
|
||||
if extra_debug:
|
||||
logger.debug("- Skipping {} (disabled)".format(m3d.m_Filename))
|
||||
continue
|
||||
full_name = KiConf.expand_env(m3d.m_Filename)
|
||||
used_extra = [False]
|
||||
full_name = KiConf.expand_env(m3d.m_Filename, used_extra)
|
||||
if extra_debug:
|
||||
logger.debug("- Expanded {} -> {}".format(m3d.m_Filename, full_name))
|
||||
if not os.path.isfile(full_name):
|
||||
# Missing 3D model
|
||||
if full_name not in downloaded:
|
||||
|
|
@ -148,6 +154,14 @@ class Base3DOptions(VariantOptions):
|
|||
if replace:
|
||||
m3d.m_Filename = replace
|
||||
models_replaced = True
|
||||
else: # File was found
|
||||
if used_extra[0]:
|
||||
# The file is there, but we got it expanding a user defined text
|
||||
# This is completely valid for KiCad, but kicad2step doesn't support it
|
||||
m3d.m_Filename = full_name
|
||||
if not models_replaced and extra_debug:
|
||||
logger.debug('- Modifying models with text vars')
|
||||
models_replaced = True
|
||||
# Push the models back
|
||||
for model in models_l:
|
||||
models.push_front(model)
|
||||
|
|
@ -182,11 +196,12 @@ class Base3DOptions(VariantOptions):
|
|||
This mechanism uses the MTEXT attributes. """
|
||||
# The magic text is %variant:slot1,slot2...%
|
||||
field_regex = re.compile(r'\%([^:]+):(.*)\%')
|
||||
if GS.debug_level > 3:
|
||||
extra_debug = GS.debug_level > 3
|
||||
if extra_debug:
|
||||
logger.debug("{} 3D models that aren't for this variant".format('Enable' if enable else 'Disable'))
|
||||
len_disable = len(DISABLE_TEXT)
|
||||
for m in GS.get_modules():
|
||||
if GS.debug_level > 3:
|
||||
if extra_debug:
|
||||
logger.debug("Processing module " + m.GetReference())
|
||||
# Look for text objects
|
||||
for gi in m.GraphicalItems():
|
||||
|
|
@ -207,7 +222,7 @@ class Base3DOptions(VariantOptions):
|
|||
while not models.empty():
|
||||
m_objs.insert(0, models.pop())
|
||||
for i, m3d in enumerate(m_objs):
|
||||
if GS.debug_level > 3:
|
||||
if extra_debug:
|
||||
logger.debug('- {} {} {}'.format(i+1, i+1 in slots, m3d.m_Filename))
|
||||
if i+1 not in slots:
|
||||
if enable:
|
||||
|
|
|
|||
|
|
@ -3,3 +3,4 @@ print_err.pro
|
|||
test_v5/
|
||||
zone-refill.pro
|
||||
fp-info-cache
|
||||
*-bak
|
||||
|
|
|
|||
|
|
@ -105,7 +105,7 @@
|
|||
(net 2 "Net-(C1-Pad1)") (tstamp a1823eb2-fb0d-4ed8-8b96-04184ac3a9d5))
|
||||
(pad "2" smd roundrect locked (at 0.9375 0) (size 0.975 1.4) (layers "F.Cu" "F.Paste" "F.Mask") (roundrect_rratio 0.25)
|
||||
(net 1 "GND") (tstamp 03c52831-5dc5-43c5-a442-8d23643b46fb))
|
||||
(model "${KIPRJMOD}/../../data/R_0805_2012Metric.step"
|
||||
(model "${MYVAR}/R_0805_2012Metric.step"
|
||||
(offset (xyz 0 0 0))
|
||||
(scale (xyz 1 1 1))
|
||||
(rotate (xyz 0 0 0))
|
||||
|
|
|
|||
|
|
@ -0,0 +1,220 @@
|
|||
{
|
||||
"board": {
|
||||
"design_settings": {
|
||||
"defaults": {
|
||||
"board_outline_line_width": 0.049999999999999996,
|
||||
"copper_line_width": 0.19999999999999998,
|
||||
"copper_text_italic": false,
|
||||
"copper_text_size_h": 1.5,
|
||||
"copper_text_size_v": 1.5,
|
||||
"copper_text_thickness": 0.3,
|
||||
"copper_text_upright": false,
|
||||
"courtyard_line_width": 0.049999999999999996,
|
||||
"dimension_precision": 4,
|
||||
"dimension_units": 3,
|
||||
"dimensions": {
|
||||
"arrow_length": 1270000,
|
||||
"extension_offset": 500000,
|
||||
"keep_text_aligned": true,
|
||||
"suppress_zeroes": false,
|
||||
"text_position": 0,
|
||||
"units_format": 1
|
||||
},
|
||||
"fab_line_width": 0.09999999999999999,
|
||||
"fab_text_italic": false,
|
||||
"fab_text_size_h": 1.0,
|
||||
"fab_text_size_v": 1.0,
|
||||
"fab_text_thickness": 0.15,
|
||||
"fab_text_upright": false,
|
||||
"other_line_width": 0.09999999999999999,
|
||||
"other_text_italic": false,
|
||||
"other_text_size_h": 1.0,
|
||||
"other_text_size_v": 1.0,
|
||||
"other_text_thickness": 0.15,
|
||||
"other_text_upright": false,
|
||||
"pads": {
|
||||
"drill": 0.762,
|
||||
"height": 1.524,
|
||||
"width": 1.524
|
||||
},
|
||||
"silk_line_width": 0.12,
|
||||
"silk_text_italic": false,
|
||||
"silk_text_size_h": 1.0,
|
||||
"silk_text_size_v": 1.0,
|
||||
"silk_text_thickness": 0.15,
|
||||
"silk_text_upright": false,
|
||||
"zones": {
|
||||
"45_degree_only": true,
|
||||
"min_clearance": 0.508
|
||||
}
|
||||
},
|
||||
"diff_pair_dimensions": [
|
||||
{
|
||||
"gap": 0.0,
|
||||
"via_gap": 0.0,
|
||||
"width": 0.0
|
||||
}
|
||||
],
|
||||
"drc_exclusions": [],
|
||||
"meta": {
|
||||
"filename": "board_design_settings.json",
|
||||
"version": 2
|
||||
},
|
||||
"rule_severities": {
|
||||
"annular_width": "error",
|
||||
"clearance": "error",
|
||||
"copper_edge_clearance": "error",
|
||||
"courtyards_overlap": "error",
|
||||
"diff_pair_gap_out_of_range": "error",
|
||||
"diff_pair_uncoupled_length_too_long": "error",
|
||||
"drill_out_of_range": "error",
|
||||
"duplicate_footprints": "warning",
|
||||
"extra_footprint": "warning",
|
||||
"footprint_type_mismatch": "error",
|
||||
"hole_clearance": "error",
|
||||
"hole_near_hole": "error",
|
||||
"invalid_outline": "error",
|
||||
"item_on_disabled_layer": "error",
|
||||
"items_not_allowed": "error",
|
||||
"length_out_of_range": "error",
|
||||
"malformed_courtyard": "error",
|
||||
"microvia_drill_out_of_range": "error",
|
||||
"missing_courtyard": "ignore",
|
||||
"missing_footprint": "warning",
|
||||
"net_conflict": "warning",
|
||||
"npth_inside_courtyard": "ignore",
|
||||
"padstack": "error",
|
||||
"pth_inside_courtyard": "ignore",
|
||||
"shorting_items": "error",
|
||||
"silk_over_copper": "warning",
|
||||
"silk_overlap": "warning",
|
||||
"skew_out_of_range": "error",
|
||||
"through_hole_pad_without_hole": "error",
|
||||
"too_many_vias": "error",
|
||||
"track_dangling": "warning",
|
||||
"track_width": "error",
|
||||
"tracks_crossing": "error",
|
||||
"unconnected_items": "error",
|
||||
"unresolved_variable": "error",
|
||||
"via_dangling": "warning",
|
||||
"zone_has_empty_net": "error",
|
||||
"zones_intersect": "error"
|
||||
},
|
||||
"rules": {
|
||||
"allow_blind_buried_vias": false,
|
||||
"allow_microvias": false,
|
||||
"max_error": 0.005,
|
||||
"min_clearance": 0.0,
|
||||
"min_copper_edge_clearance": 0.024999999999999998,
|
||||
"min_hole_clearance": 0.25,
|
||||
"min_hole_to_hole": 0.25,
|
||||
"min_microvia_diameter": 0.19999999999999998,
|
||||
"min_microvia_drill": 0.09999999999999999,
|
||||
"min_silk_clearance": 0.0,
|
||||
"min_through_hole_diameter": 0.2032,
|
||||
"min_track_width": 0.127,
|
||||
"min_via_annular_width": 0.049999999999999996,
|
||||
"min_via_diameter": 0.4572,
|
||||
"use_height_for_length_calcs": true
|
||||
},
|
||||
"track_widths": [
|
||||
0.0,
|
||||
0.1524,
|
||||
0.3048,
|
||||
0.635
|
||||
],
|
||||
"via_dimensions": [
|
||||
{
|
||||
"diameter": 0.0,
|
||||
"drill": 0.0
|
||||
},
|
||||
{
|
||||
"diameter": 0.508,
|
||||
"drill": 0.254
|
||||
},
|
||||
{
|
||||
"diameter": 0.889,
|
||||
"drill": 0.508
|
||||
}
|
||||
],
|
||||
"zones_allow_external_fillets": false,
|
||||
"zones_use_no_outline": true
|
||||
},
|
||||
"layer_presets": []
|
||||
},
|
||||
"boards": [],
|
||||
"cvpcb": {
|
||||
"equivalence_files": []
|
||||
},
|
||||
"libraries": {
|
||||
"pinned_footprint_libs": [],
|
||||
"pinned_symbol_libs": []
|
||||
},
|
||||
"meta": {
|
||||
"filename": "light_control.kicad_pro",
|
||||
"version": 1
|
||||
},
|
||||
"net_settings": {
|
||||
"classes": [
|
||||
{
|
||||
"bus_width": 12.0,
|
||||
"clearance": 0.1524,
|
||||
"diff_pair_gap": 0.25,
|
||||
"diff_pair_via_gap": 0.25,
|
||||
"diff_pair_width": 0.2,
|
||||
"line_style": 0,
|
||||
"microvia_diameter": 0.3,
|
||||
"microvia_drill": 0.1,
|
||||
"name": "Default",
|
||||
"pcb_color": "rgba(0, 0, 0, 0.000)",
|
||||
"schematic_color": "rgba(0, 0, 0, 0.000)",
|
||||
"track_width": 0.1524,
|
||||
"via_diameter": 0.508,
|
||||
"via_drill": 0.254,
|
||||
"wire_width": 6.0
|
||||
},
|
||||
{
|
||||
"bus_width": 12.0,
|
||||
"clearance": 0.1524,
|
||||
"diff_pair_gap": 0.25,
|
||||
"diff_pair_via_gap": 0.25,
|
||||
"diff_pair_width": 0.2,
|
||||
"line_style": 0,
|
||||
"microvia_diameter": 0.3,
|
||||
"microvia_drill": 0.1,
|
||||
"name": "Power",
|
||||
"nets": [],
|
||||
"pcb_color": "rgba(0, 0, 0, 0.000)",
|
||||
"schematic_color": "rgba(0, 0, 0, 0.000)",
|
||||
"track_width": 0.635,
|
||||
"via_diameter": 0.889,
|
||||
"via_drill": 0.508,
|
||||
"wire_width": 6.0
|
||||
}
|
||||
],
|
||||
"meta": {
|
||||
"version": 2
|
||||
},
|
||||
"net_colors": null
|
||||
},
|
||||
"pcbnew": {
|
||||
"last_paths": {
|
||||
"gencad": "",
|
||||
"idf": "",
|
||||
"netlist": "",
|
||||
"specctra_dsn": "",
|
||||
"step": "",
|
||||
"vrml": ""
|
||||
},
|
||||
"page_layout_descr_file": ""
|
||||
},
|
||||
"schematic": {
|
||||
"legacy_lib_dir": "",
|
||||
"legacy_lib_list": []
|
||||
},
|
||||
"sheets": [],
|
||||
"text_variables": {
|
||||
"MYVAR": "tests/data",
|
||||
"PRUEBITA": "Hola!"
|
||||
}
|
||||
}
|
||||
|
|
@ -39,11 +39,15 @@ def test_step_1(test_dir):
|
|||
|
||||
def test_step_2(test_dir):
|
||||
prj = 'bom_fake_models'
|
||||
yaml = 'step_simple_2'
|
||||
if context.ki6():
|
||||
yaml += '_k6'
|
||||
ctx = context.TestContext(test_dir, 'STEP_2', prj, 'step_simple_2', STEP_DIR)
|
||||
ctx.run()
|
||||
# Check all outputs are there
|
||||
ctx.expect_out_file(os.path.join(STEP_DIR, prj+'-3D.step'))
|
||||
ctx.clean_up()
|
||||
ctx.search_err(['Missing 3D model for C1', 'Could not add 3D model to C1'], invert=True)
|
||||
ctx.clean_up(keep_project=True)
|
||||
|
||||
|
||||
def test_step_3(test_dir):
|
||||
|
|
|
|||
|
|
@ -0,0 +1,19 @@
|
|||
kiplot:
|
||||
version: 1
|
||||
|
||||
preflight:
|
||||
set_text_variables:
|
||||
- name: "MYVAR"
|
||||
text: "tests/data"
|
||||
|
||||
outputs:
|
||||
- name: Step
|
||||
comment: "Generate 3D model (STEP)"
|
||||
type: step
|
||||
dir: 3D
|
||||
options:
|
||||
metric_units: false
|
||||
origin: "3.2,-10" # "grid" or "drill" o "X,Y" i.e. 3.2,-10
|
||||
no_virtual: true # exclude 3D models for components with 'virtual' attribute
|
||||
min_distance: 0.0004 # Minimum distance between points to treat them as separate ones (default 0.01 mm)
|
||||
#output: project.step
|
||||
Loading…
Reference in New Issue