Added support for variants to the PcbDraw output.

This commit is contained in:
Salvador E. Tropea 2020-09-04 18:08:22 -03:00
parent dab7baa2d4
commit d09400d49d
12 changed files with 161 additions and 19 deletions

View File

@ -25,6 +25,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- Drawings removed from *.Adhes
- Components crossed in *.Fab
- STEP (3D) support for variants.
- PcbDraw support for variants.
### Fixed
- Virtual components are always excluded from position files.

View File

@ -110,6 +110,8 @@ gen_ref:
mv "$(REFDIR)no_inductor/test_v5-schematic_(no_L).pdf" $(REFDIR)
rmdir $(REFDIR)no_inductor/
src/kibot -b tests/board_samples/kibom-variant_4.kicad_pcb -c tests/yaml_samples/pdf_variant_1.kibot.yaml -d $(REFDIR)
src/kibot -b tests/board_samples/kibom-variant_3.kicad_pcb -c tests/yaml_samples/pcbdraw_variant_1.kibot.yaml -d $(REFDIR)
src/kibot -b tests/board_samples/kibom-variant_3.kicad_pcb -c tests/yaml_samples/pcbdraw_variant_2.kibot.yaml -d $(REFDIR)
cp -a $(REFILL).ok $(REFILL)
doc:

View File

@ -725,6 +725,8 @@ Next time you need this list just use an alias, like this:
- `options`: [dict] Options for the `pcbdraw` output.
* Valid keys:
- `bottom`: [boolean=false] render the bottom side of the board (default is top side).
- `dnf_filter`: [string|list(string)=''] Name of the filter to mark components as not fitted.
A short-cut to use for simple cases where a variant is an overkill.
- `dpi`: [number=300] [10,1200] dots per inch (resolution) of the generated image.
- `format`: [string='svg'] [svg,png,jpg] output format. Only used if no `output` is specified.
- `highlight`: [list(string)=[]] list of components to highlight.
@ -734,7 +736,7 @@ Next time you need this list just use an alias, like this:
- `output`: [string='%f-%i%v.%x'] name for the generated file. Affected by global options.
- `placeholder`: [boolean=false] show placeholder for missing components.
- `remap`: [dict|None] replacements for PCB references using components (lib:component).
- `show_components`: [string|list(string)=none] [none,all] list of components to draw, can be also a string for none or all.
- `show_components`: [list(string)|string=none] [none,all] list of components to draw, can be also a string for none or all.
The default is none.
- `style`: [string|dict] PCB style (colors). An internal name, the name of a JSON file or the style options.
* Valid keys:
@ -748,6 +750,7 @@ Next time you need this list just use an alias, like this:
- `pads`: [string='#b5ae30'] color for the exposed pads (metal finish).
- `silk`: [string='#f0f0f0'] color for the silk screen.
- `vcut`: [string='#bf2600'] color for the V-CUTS.
- `variant`: [string=''] Board variant to apply.
- `vcuts`: [boolean=false] render V-CUTS on the Cmts.User layer.
- `warnings`: [string='visible'] [visible,all,none] using visible only the warnings about components in the visible side are generated.

View File

@ -531,6 +531,9 @@ outputs:
options:
# [boolean=false] render the bottom side of the board (default is top side)
bottom: false
# [string|list(string)=''] Name of the filter to mark components as not fitted.
# A short-cut to use for simple cases where a variant is an overkill
dnf_filter: ''
# [number=300] [10,1200] dots per inch (resolution) of the generated image
dpi: 300
# [string='svg'] [svg,png,jpg] output format. Only used if no `output` is specified
@ -549,7 +552,7 @@ outputs:
placeholder: false
# [dict|None] replacements for PCB references using components (lib:component)
remap:
# [string|list(string)=none] [none,all] list of components to draw, can be also a string for none or all.
# [list(string)|string=none] [none,all] list of components to draw, can be also a string for none or all.
# The default is none
show_components: none
# [string|dict] PCB style (colors). An internal name, the name of a JSON file or the style options
@ -574,6 +577,8 @@ outputs:
silk: '#f0f0f0'
# [string='#bf2600'] color for the V-CUTS
vcut: '#bf2600'
# [string=''] Board variant to apply
variant: ''
# [boolean=false] render V-CUTS on the Cmts.User layer
vcuts: false
# [string='visible'] [visible,all,none] using visible only the warnings about components in the visible side are generated

View File

@ -13,7 +13,10 @@ from .misc import PCBDRAW, PCBDRAW_ERR, URL_PCBDRAW
from .kiplot import check_script
from .error import KiPlotConfigurationError
from .gs import (GS)
from .optionable import (BaseOptions, Optionable)
from .optionable import BaseOptions, Optionable
from .registrable import RegOutput
from .kiplot import load_sch
from .fil_base import BaseFilter, apply_fitted_filter
from .macros import macros, document, output_class # noqa: F401
from . import log
@ -136,6 +139,11 @@ class PcbDrawOptions(BaseOptions):
""" [svg,png,jpg] output format. Only used if no `output` is specified """
self.output = GS.def_global_output
""" name for the generated file """
self.variant = ''
""" Board variant to apply """
self.dnf_filter = Optionable
""" [string|list(string)=''] Name of the filter to mark components as not fitted.
A short-cut to use for simple cases where a variant is an overkill """
super().__init__()
def config(self):
@ -150,10 +158,15 @@ class PcbDrawOptions(BaseOptions):
self.highlight = None
else:
self.highlight = ','.join(self.highlight)
# Variants
self.variant = RegOutput.check_variant(self.variant)
self.dnf_filter = BaseFilter.solve_filter(self.dnf_filter, 'dnf_filter')
# Filter
if isinstance(self.show_components, type):
self.show_components = ''
elif isinstance(self.show_components, str):
if self.variant or self.dnf_filter:
logger.warning('Ambiguous list of components to show `{}` vs variant/filter'.format(self.show_components))
if self.show_components == 'none':
self.show_components = ''
else:
@ -204,6 +217,39 @@ class PcbDrawOptions(BaseOptions):
f.close()
return f.name
def get_filtered_refs(self):
if not self.dnf_filter and not self.variant:
return []
load_sch()
# Get the components list from the schematic
comps = GS.sch.get_components()
# Apply the filter
apply_fitted_filter(comps, self.dnf_filter)
# Apply the variant
if self.variant:
# Apply the variant
self.variant.filter(comps)
return [c.ref for c in comps if c.fitted]
def _append_output(self, cmd, output):
svg = None
if self.format == 'svg':
cmd.append(output)
else:
# PNG and JPG outputs are unreliable
if shutil.which(SVG2PNG) is None:
logger.warning('`{}` not installed, using unreliable PNG/JPG conversion'.format(SVG2PNG))
logger.warning('If you experiment problems install `librsvg2-bin` or equivalent')
cmd.append(output)
elif shutil.which(CONVERT) is None:
logger.warning('`{}` not installed, using unreliable PNG/JPG conversion'.format(CONVERT))
logger.warning('If you experiment problems install `imagemagick` or equivalent')
cmd.append(output)
else:
svg = _get_tmp_name('.svg')
cmd.append(svg)
return svg
def run(self, output_dir, board):
check_script(PCBDRAW, URL_PCBDRAW, '0.6.0')
# Output file name
@ -231,6 +277,10 @@ class PcbDrawOptions(BaseOptions):
if self.highlight:
cmd.extend(['-a', self.highlight])
if self.show_components is not None:
to_add = ','.join(self.get_filtered_refs())
if self.show_components and to_add:
self.show_components += ','
self.show_components += to_add
cmd.extend(['-f', self.show_components])
if self.vcuts:
cmd.append('-v')
@ -247,22 +297,7 @@ class PcbDrawOptions(BaseOptions):
tmp_remap = None
# The board & output
cmd.append(GS.pcb_file)
svg = None
if self.format == 'svg':
cmd.append(output)
else:
# PNG and JPG outputs are unreliable
if shutil.which(SVG2PNG) is None:
logger.warning('`{}` not installed, using unreliable PNG/JPG conversion'.format(SVG2PNG))
logger.warning('If you experiment problems install `librsvg2-bin` or equivalent')
cmd.append(output)
elif shutil.which(CONVERT) is None:
logger.warning('`{}` not installed, using unreliable PNG/JPG conversion'.format(CONVERT))
logger.warning('If you experiment problems install `imagemagick` or equivalent')
cmd.append(output)
else:
svg = _get_tmp_name('.svg')
cmd.append(svg)
svg = self._append_output(cmd, output)
# Execute and inform is successful
_run_command(cmd, tmp_remap, tmp_style)
if svg is not None:

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.2 KiB

View File

@ -69,6 +69,7 @@ def test_pcbdraw_miss_rsvg(caplog, monkeypatch):
o.style = ''
o.remap = None
o.format = 'jpg'
o.config()
cov.load()
cov.start()
o.run('', None)
@ -87,6 +88,7 @@ def test_pcbdraw_miss_convert(caplog, monkeypatch):
o.style = ''
o.remap = None
o.format = 'jpg'
o.config()
cov.load()
cov.start()
o.run('', None)
@ -94,3 +96,37 @@ def test_pcbdraw_miss_convert(caplog, monkeypatch):
cov.save()
assert 'using unreliable PNG/JPG' in caplog.text, caplog.text
assert 'imagemagick' in caplog.text, caplog.text
def test_pcbdraw_variant_1():
prj = 'kibom-variant_3'
ctx = context.TestContext('test_pcbdraw_variant_1', prj, 'pcbdraw_variant_1', '')
ctx.run()
# Check all outputs are there
fname = prj+'-top.png'
ctx.expect_out_file(fname)
ctx.compare_image(fname)
ctx.clean_up()
def test_pcbdraw_variant_2():
prj = 'kibom-variant_3'
ctx = context.TestContext('test_pcbdraw_variant_2', prj, 'pcbdraw_variant_2', '')
ctx.run()
# Check all outputs are there
fname = prj+'-top-C1.png'
ctx.expect_out_file(fname)
ctx.compare_image(fname)
ctx.clean_up()
def test_pcbdraw_variant_3():
prj = 'kibom-variant_3'
ctx = context.TestContext('test_pcbdraw_variant_1', prj, 'pcbdraw_variant_3', '')
ctx.run()
# Check all outputs are there
fname = prj+'-top.png'
ctx.expect_out_file(fname)
ctx.compare_image(fname)
assert ctx.search_err("Ambiguous list of components to show .?none.? vs variant/filter")
ctx.clean_up()

View File

@ -13,6 +13,7 @@ outputs:
mirror: True
vcuts: True
warnings: all
show_components: all
- name: PcbDraw
comment: "PcbDraw test bottom"

View File

@ -0,0 +1,18 @@
# Example KiBot config file
kibot:
version: 1
variants:
- name: 'default'
comment: 'Default variant'
type: ibom
variants_blacklist: T2,T3
outputs:
- name: 'pcbdraw_default'
comment: "PcbDraw w/variant"
type: pcbdraw
options:
variant: default
format: png

View File

@ -0,0 +1,22 @@
# Example KiBot config file
kibot:
version: 1
variants:
- name: 'default'
comment: 'Default variant'
type: ibom
file_id: '-C1'
variants_blacklist: T2,T3
outputs:
- name: 'pcbdraw_default'
comment: "PcbDraw w/variant"
type: pcbdraw
options:
variant: default
format: png
# This isn't a good idea, but works
show_components:
- 'C1'

View File

@ -0,0 +1,19 @@
# Example KiBot config file
kibot:
version: 1
variants:
- name: 'default'
comment: 'Default variant'
type: ibom
variants_blacklist: T2,T3
outputs:
- name: 'pcbdraw_default'
comment: "PcbDraw w/variant"
type: pcbdraw
options:
variant: default
format: png
# This is incoherent: all or filtered?
show_components: none