aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTrygve Laugstøl <trygvis@inamo.no>2018-07-14 15:00:49 +0200
committerTrygve Laugstøl <trygvis@inamo.no>2018-07-14 15:00:49 +0200
commit68b2f9bd888f86766fea254d6253f3b1e88cc8a4 (patch)
tree5103abc40c4e0b309588179d2b0f3720ddfc8e66
parentc5476aba69eded6ccc1343247219ea754e08e3ff (diff)
downloadee-python-68b2f9bd888f86766fea254d6253f3b1e88cc8a4.tar.gz
ee-python-68b2f9bd888f86766fea254d6253f3b1e88cc8a4.tar.bz2
ee-python-68b2f9bd888f86766fea254d6253f3b1e88cc8a4.tar.xz
ee-python-68b2f9bd888f86766fea254d6253f3b1e88cc8a4.zip
wip
-rw-r--r--demo/doit/.gitignore4
-rw-r--r--demo/doit/demo-cache.lib71
-rw-r--r--demo/doit/demo.kicad_pcb1
-rw-r--r--demo/doit/demo.pro33
-rw-r--r--demo/doit/demo.sch77
-rw-r--r--demo/doit/demo/demo.pro33
-rw-r--r--demo/doit/dodo.py14
-rw-r--r--requirements.txt5
-rw-r--r--setup.py2
-rw-r--r--src/ee/fact/__init__.py49
-rw-r--r--src/ee/fact/doit.py14
-rw-r--r--src/ee/kicad/doit.py125
-rwxr-xr-xsrc/ee/kicad/export_gerber.py259
-rw-r--r--src/ee/tools/digikey_download_facts.py2
-rw-r--r--test/test_digikey.py3
15 files changed, 688 insertions, 4 deletions
diff --git a/demo/doit/.gitignore b/demo/doit/.gitignore
new file mode 100644
index 0000000..47aa48a
--- /dev/null
+++ b/demo/doit/.gitignore
@@ -0,0 +1,4 @@
+gerber.zip
+gerber
+.doit.db
+components
diff --git a/demo/doit/demo-cache.lib b/demo/doit/demo-cache.lib
new file mode 100644
index 0000000..e81b633
--- /dev/null
+++ b/demo/doit/demo-cache.lib
@@ -0,0 +1,71 @@
+EESchema-LIBRARY Version 2.4
+#encoding utf-8
+#
+# Device:Battery_Cell
+#
+DEF Device:Battery_Cell BT 0 0 N N 1 F N
+F0 "BT" 100 100 50 H V L CNN
+F1 "Device:Battery_Cell" 100 0 50 H V L CNN
+F2 "" 0 60 50 V I C CNN
+F3 "" 0 60 50 V I C CNN
+DRAW
+S -90 70 90 60 0 1 0 F
+S -62 47 58 27 0 1 0 F
+P 2 0 1 0 0 30 0 0 N
+P 2 0 1 0 0 70 0 100 N
+P 2 0 1 10 20 135 60 135 N
+P 2 0 1 10 40 155 40 115 N
+X + 1 0 200 100 D 50 50 1 1 P
+X - 2 0 -100 100 U 50 50 1 1 P
+ENDDRAW
+ENDDEF
+#
+# Device:C
+#
+DEF Device:C C 0 10 N Y 1 F N
+F0 "C" 25 100 50 H V L CNN
+F1 "Device:C" 25 -100 50 H V L CNN
+F2 "" 38 -150 50 H I C CNN
+F3 "" 0 0 50 H I C CNN
+$FPLIST
+ C_*
+$ENDFPLIST
+DRAW
+P 2 0 1 20 -80 -30 80 -30 N
+P 2 0 1 20 -80 30 80 30 N
+X ~ 1 0 150 110 D 50 50 1 1 P
+X ~ 2 0 -150 110 U 50 50 1 1 P
+ENDDRAW
+ENDDEF
+#
+# Device:R
+#
+DEF Device:R R 0 0 N Y 1 F N
+F0 "R" 80 0 50 V V C CNN
+F1 "Device:R" 0 0 50 V V C CNN
+F2 "" -70 0 50 V I C CNN
+F3 "" 0 0 50 H I C CNN
+$FPLIST
+ R_*
+$ENDFPLIST
+DRAW
+S -40 -100 40 100 0 1 10 N
+X ~ 1 0 150 50 D 50 50 1 1 P
+X ~ 2 0 -150 50 U 50 50 1 1 P
+ENDDRAW
+ENDDEF
+#
+# power:GND
+#
+DEF power:GND #PWR 0 0 Y Y 1 F P
+F0 "#PWR" 0 -250 50 H I C CNN
+F1 "power:GND" 0 -150 50 H V C CNN
+F2 "" 0 0 50 H I C CNN
+F3 "" 0 0 50 H I C CNN
+DRAW
+P 6 0 1 0 0 0 0 -50 50 -50 0 -100 -50 -50 0 -50 N
+X GND 1 0 0 0 D 50 50 1 1 W N
+ENDDRAW
+ENDDEF
+#
+#End Library
diff --git a/demo/doit/demo.kicad_pcb b/demo/doit/demo.kicad_pcb
new file mode 100644
index 0000000..02c8ecb
--- /dev/null
+++ b/demo/doit/demo.kicad_pcb
@@ -0,0 +1 @@
+(kicad_pcb (version 4) (host kicad "dummy file") )
diff --git a/demo/doit/demo.pro b/demo/doit/demo.pro
new file mode 100644
index 0000000..152769c
--- /dev/null
+++ b/demo/doit/demo.pro
@@ -0,0 +1,33 @@
+update=22/05/2015 07:44:53
+version=1
+last_client=kicad
+[general]
+version=1
+RootSch=
+BoardNm=
+[pcbnew]
+version=1
+LastNetListRead=
+UseCmpFile=1
+PadDrill=0.600000000000
+PadDrillOvalY=0.600000000000
+PadSizeH=1.500000000000
+PadSizeV=1.500000000000
+PcbTextSizeV=1.500000000000
+PcbTextSizeH=1.500000000000
+PcbTextThickness=0.300000000000
+ModuleTextSizeV=1.000000000000
+ModuleTextSizeH=1.000000000000
+ModuleTextSizeThickness=0.150000000000
+SolderMaskClearance=0.000000000000
+SolderMaskMinWidth=0.000000000000
+DrawSegmentWidth=0.200000000000
+BoardOutlineThickness=0.100000000000
+ModuleOutlineThickness=0.150000000000
+[cvpcb]
+version=1
+NetIExt=net
+[eeschema]
+version=1
+LibDir=
+[eeschema/libraries]
diff --git a/demo/doit/demo.sch b/demo/doit/demo.sch
new file mode 100644
index 0000000..a805e83
--- /dev/null
+++ b/demo/doit/demo.sch
@@ -0,0 +1,77 @@
+EESchema Schematic File Version 4
+EELAYER 26 0
+EELAYER END
+$Descr A4 11693 8268
+encoding utf-8
+Sheet 1 1
+Title ""
+Date ""
+Rev ""
+Comp ""
+Comment1 ""
+Comment2 ""
+Comment3 ""
+Comment4 ""
+$EndDescr
+$Comp
+L Device:R R?
+U 1 1 5B431328
+P 4400 2600
+F 0 "R?" V 4193 2600 50 0000 C CNN
+F 1 "10k" V 4284 2600 50 0000 C CNN
+F 2 "" V 4330 2600 50 0001 C CNN
+F 3 "~" H 4400 2600 50 0001 C CNN
+ 1 4400 2600
+ 0 1 1 0
+$EndComp
+$Comp
+L Device:Battery_Cell BT?
+U 1 1 5B431438
+P 3700 2900
+F 0 "BT?" H 3818 2996 50 0000 L CNN
+F 1 "9V" H 3818 2905 50 0000 L CNN
+F 2 "" V 3700 2960 50 0001 C CNN
+F 3 "~" V 3700 2960 50 0001 C CNN
+ 1 3700 2900
+ 1 0 0 -1
+$EndComp
+$Comp
+L Device:C C?
+U 1 1 5B4314AB
+P 5000 2850
+F 0 "C?" H 5115 2896 50 0000 L CNN
+F 1 "1u" H 5115 2805 50 0000 L CNN
+F 2 "" H 5038 2700 50 0001 C CNN
+F 3 "~" H 5000 2850 50 0001 C CNN
+ 1 5000 2850
+ 1 0 0 -1
+$EndComp
+Wire Wire Line
+ 3700 3000 3700 3100
+Wire Wire Line
+ 5000 3100 5000 3000
+$Comp
+L power:GND #PWR?
+U 1 1 5B4315FE
+P 3700 3200
+F 0 "#PWR?" H 3700 2950 50 0001 C CNN
+F 1 "GND" H 3705 3027 50 0000 C CNN
+F 2 "" H 3700 3200 50 0001 C CNN
+F 3 "" H 3700 3200 50 0001 C CNN
+ 1 3700 3200
+ 1 0 0 -1
+$EndComp
+Wire Wire Line
+ 3700 3200 3700 3100
+Connection ~ 3700 3100
+Wire Wire Line
+ 3700 2700 3700 2600
+Wire Wire Line
+ 5000 2600 5000 2700
+Wire Wire Line
+ 3700 2600 4250 2600
+Wire Wire Line
+ 3700 3100 5000 3100
+Wire Wire Line
+ 4550 2600 5000 2600
+$EndSCHEMATC
diff --git a/demo/doit/demo/demo.pro b/demo/doit/demo/demo.pro
new file mode 100644
index 0000000..152769c
--- /dev/null
+++ b/demo/doit/demo/demo.pro
@@ -0,0 +1,33 @@
+update=22/05/2015 07:44:53
+version=1
+last_client=kicad
+[general]
+version=1
+RootSch=
+BoardNm=
+[pcbnew]
+version=1
+LastNetListRead=
+UseCmpFile=1
+PadDrill=0.600000000000
+PadDrillOvalY=0.600000000000
+PadSizeH=1.500000000000
+PadSizeV=1.500000000000
+PcbTextSizeV=1.500000000000
+PcbTextSizeH=1.500000000000
+PcbTextThickness=0.300000000000
+ModuleTextSizeV=1.000000000000
+ModuleTextSizeH=1.000000000000
+ModuleTextSizeThickness=0.150000000000
+SolderMaskClearance=0.000000000000
+SolderMaskMinWidth=0.000000000000
+DrawSegmentWidth=0.200000000000
+BoardOutlineThickness=0.100000000000
+ModuleOutlineThickness=0.150000000000
+[cvpcb]
+version=1
+NetIExt=net
+[eeschema]
+version=1
+LibDir=
+[eeschema/libraries]
diff --git a/demo/doit/dodo.py b/demo/doit/dodo.py
new file mode 100644
index 0000000..4c8748a
--- /dev/null
+++ b/demo/doit/dodo.py
@@ -0,0 +1,14 @@
+from ee.kicad.doit import KicadDoitTasks
+
+prj = "demo"
+sch = "{}.sch".format(prj)
+kicad_pcb = "{}.kicad_pcb".format(prj)
+
+def task_kicad():
+ args = {
+ "sch": sch,
+ "kicad_pcb": kicad_pcb,
+ "gerber_dir": "gerber",
+ "components_dir": "components",
+ }
+ yield KicadDoitTasks(**args).tasks()
diff --git a/requirements.txt b/requirements.txt
index 9caed1b..75008d0 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -6,7 +6,6 @@ lockfile==0.12.2
lxml==3.8.0
matplotlib==2.0.2
mpmath==0.19
-mypy==0.521
numpy==1.13.1
pandas==0.20.3
parsec==3.3
@@ -15,3 +14,7 @@ pytest==3.3.1
requests==2.18.4
sympy==1.0
tox==2.9.1
+
+# for development
+jupyter==1.0.0
+doit==0.30.3
diff --git a/setup.py b/setup.py
index 0470b81..b13b857 100644
--- a/setup.py
+++ b/setup.py
@@ -12,11 +12,11 @@ setup(name='ee',
install_requires=[
'ansicolors',
'cachecontrol',
+ 'configclass',
'lockfile',
'lxml',
'matplotlib',
'mpmath',
- 'mypy',
'numpy',
'pandas',
'parsec',
diff --git a/src/ee/fact/__init__.py b/src/ee/fact/__init__.py
new file mode 100644
index 0000000..5c6d789
--- /dev/null
+++ b/src/ee/fact/__init__.py
@@ -0,0 +1,49 @@
+class Fact(object):
+ def __init__(self, kind):
+ self._kind = kind
+ self._domains = {}
+
+ @property
+ def kind() -> str:
+ return self._kind
+
+ def attr(self, domain: str, key: str):
+ try:
+ return self._domains[domain][key]
+ except KeyError:
+ pass
+
+ def set(self, domain: str, key: str, value: str):
+ _kv(domain)[key] = value
+
+ def _kv(self, domain: str):
+ try:
+ kv = self._domains[domain]
+ except KeyError:
+ kv = {}
+ self._domains[domain] = kv
+
+ return kv
+
+ def view(self, domain: str):
+ return FactKv(self, domain, self._kv(domain))
+
+ def write(self, output):
+ import configparser
+ ini = configparser.ConfigParser(interpolation = None)
+ for domain, kv in self._domains.items():
+ ini.add_section(domain)
+ for key, value in kv.items():
+ ini.set(domain, key, value)
+
+ ini.write(output)
+
+
+class FactKv(object):
+ def __init__(self, fact, domain, kv):
+ self._fact = fact
+ self._domain = domain
+ self._kv = kv
+
+ def set(self, key, value):
+ self._kv[key] = value
diff --git a/src/ee/fact/doit.py b/src/ee/fact/doit.py
new file mode 100644
index 0000000..f922cf1
--- /dev/null
+++ b/src/ee/fact/doit.py
@@ -0,0 +1,14 @@
+
+
+def uptodate_if_isdir(path):
+ def do_check():
+ return os.path.isdir(path)
+ return do_check
+
+def uptodate_if_older_than(dependency, *targets):
+ def do_check():
+ dep_mtime = os.stat(dependency).st_mtime
+ mtimes = [os.stat(t).st_mtime for t in targets if os.path.isfile(t)]
+ target_mtime = max(mtimes) if mtimes else 0
+ return dep_mtime < target_mtime
+ return do_check
diff --git a/src/ee/kicad/doit.py b/src/ee/kicad/doit.py
new file mode 100644
index 0000000..44abc61
--- /dev/null
+++ b/src/ee/kicad/doit.py
@@ -0,0 +1,125 @@
+import os.path
+from doit.exceptions import TaskFailed
+from doit.tools import check_timestamp_unchanged
+from configclass import Config
+
+class KicadDoitTasks(object):
+ config = Config({
+ "sch": None,
+ "kicad_pcb": None,
+ "gerber_dir": None,
+ "gerber_zip": None,
+ "components_dir": None,
+ })
+
+ def __init__(self, *args, **kwargs):
+ self.config = self.config.make(kwargs)
+
+ def echo(*args, **kwargs):
+ print("_task: args={}, kwars={}".format(args, kwargs))
+
+ def tasks(self, *args, **kwargs):
+ import ee.kicad
+ kicad_pcb = self.config["kicad_pcb"]
+ sch = self.config["sch"]
+ tasks = []
+
+ gerber_dir = self.config["gerber_dir"]
+ if gerber_dir:
+ gerber_zip = self.config["gerber_zip"] or "{}.zip".format(gerber_dir)
+ #print("gerber_zip={}".format(gerber_zip))
+
+ eg = next((p for p in (os.path.join(p, "export_gerber.py") for p in ee.kicad.__path__) if os.path.isfile(p)), None)
+ if not eg:
+ raise Exception("Could not find export_gerber.py")
+
+ # TODO: replace with python
+ mkdir = "mkdir -p {}".format(gerber_dir)
+ export_gerber = " ".join([
+ eg,
+ "--pcb", kicad_pcb,
+ "--output-directory", gerber_dir,
+ "--protel-extensions",
+ ])
+ def make_zip():
+ import zipfile
+ from pathlib import Path
+ with zipfile.ZipFile(gerber_zip, "w") as z:
+ for p in Path(gerber_dir).iterdir():
+ if not p.is_file():
+ continue
+ z.write(p, arcname=p.relative_to(gerber_dir))
+
+ tasks.append({
+ "name": "kicad_gerber",
+ "targets": [gerber_zip],
+ "actions": [mkdir, export_gerber, make_zip],
+ "file_dep": [kicad_pcb],
+ })
+
+ components_dir = self.config["components_dir"]
+ if sch and components_dir:
+ tasks.append(task_sch_to_component_files(sch, components_dir))
+
+ for t in tasks:
+ yield t
+
+
+def task_sch_to_component_files(sch, components_dir):
+ def action():
+ import ee.kicad
+ from ee.kicad.model import Component, ComponentField
+ import csv
+ import configparser
+ from ee.fact import Fact
+
+ schematics = ee.kicad.read_schematics(sch)
+ cs = [c for c in schematics.components]
+ os.makedirs(components_dir, exist_ok=True)
+ # TODO: remove directory?
+ for c in cs:
+ path = os.path.join(components_dir, "{}.ini".format(c.timestamp))
+ ini = configparser.ConfigParser(interpolation = None)
+ if os.path.isfile(path) and ini.read(path) != [path]:
+ print("Could not load component file: {}".format(path))
+ return False
+# if ini.has_section("kicad-schematic"):
+# ini.remove_section("kicad-schematic")
+# ini.add_section("kicad-schematic")
+# ini.set("kicad-schematic", "ref", c.ref)
+# ini.set("kicad-schematic", "ref-type", c.ref_type)
+ fact = Fact("schematic-symbol")
+ ks = fact.view("kicad-schematic")
+ ks.set("ref", c.ref)
+ ks.set("ref-type", c.ref_type)
+ if c.has_ref_num:
+# ini.set("kicad-schematic", "ref-num", str(c.ref_num))
+ ks.set("ref-num", str(c.ref_num))
+# ini.set("kicad-schematic", "value", c.value)
+ ks.set("value", c.value)
+ if c.footprint:
+# ini.set("kicad-schematic", "footprint", c.footprint)
+ ks.set("footprint", c.footprint)
+
+ fields = [f for f in c.fields if f.value and f.name not in ComponentField.names]
+
+ if fields:
+# if ini.has_section("kicad-fields"):
+# ini.remove_section("kicad-fields")
+# ini.add_section("kicad-fields")
+ kf = fact.kv("kicad-fields")
+ for f in fields:
+ kf.set(f.name, str(f.value))
+
+ with open(path, "w", newline="") as f:
+# ini.write(f)
+ fact.write(f)
+
+ component_files_cookie = "{}/components.cookie".format(components_dir)
+ gen_cookie = "date > %(targets)s"
+ return {
+ "name": "sch_to_component_files",
+ "file_dep": [sch],
+ "actions": [action, gen_cookie],
+ "targets": [component_files_cookie],
+ }
diff --git a/src/ee/kicad/export_gerber.py b/src/ee/kicad/export_gerber.py
new file mode 100755
index 0000000..511f9ee
--- /dev/null
+++ b/src/ee/kicad/export_gerber.py
@@ -0,0 +1,259 @@
+#!/usr/bin/env python
+from __future__ import print_function
+import sys
+import os
+import argparse
+from pcbnew import *
+
+def layer_name_parser(s):
+ parts = s.split('=')
+ if len(parts) != 2:
+ raise argparse.ArgumentTypeError("Invalid layer renaming: " + s)
+ else:
+ return parts
+
+parser = argparse.ArgumentParser(description='KiCAD PCB to GERBER converter')
+
+parser.add_argument('--pcb',
+ required=True,
+ dest='pcb',
+ action='store',
+ help='A foo.kicad_pcb file')
+
+parser.add_argument('--output-directory',
+ required=True,
+ dest='output_directory',
+ action='store',
+ help='Directory to store output files')
+
+parser.add_argument('--detect-files-only',
+ dest='detect_files_only',
+ action='store',
+ help='Don\'t create the GERBER files, just write a list of to be created')
+
+parser.add_argument('--create-drill-map-file',
+ dest='create_drill_map_file',
+ action='store_true',
+ help='Create drill map file')
+
+parser.add_argument('--protel-extensions',
+ dest='protel_extensions',
+ action='store_true',
+ help='Use Protel filename extensions instead of .gbr')
+
+parser.add_argument('--extended-gerber-attributes',
+ dest='extended_gerber_attributes',
+ action='store_true',
+ help='Use extended Gerber attributes')
+
+parser.add_argument('--uppercase-extensions',
+ action='store_true',
+ help='Uppercase all extensions')
+
+parser.add_argument('--layer-extension',
+ dest='layer_extensions',
+ metavar='LAYER_AND_EXTENSION',
+ action='append',
+ type=layer_name_parser,
+ help='Set the file extension of a KiCAD layer. Format: <KiCAD Layer>=<extension>, example: F.SilkS=GSILK')
+
+args = parser.parse_args()
+# print "args: " + str(args)
+# print "args.name_layer: " + str(args.name_layers)
+
+renames = {}
+if args.layer_extensions is not None:
+ for s in args.layer_extensions:
+ renames[s[0]] = s[1]
+# print("renames: " + str(renames))
+
+board = LoadBoard(args.pcb)
+
+class Plan:
+ def __init__(self, layerNum, layerName, description):
+ self.layerNum = layerNum
+ self.layerName = layerName
+ self.description = description
+ self.postfix = ""
+ self.ext = None
+
+ @staticmethod
+ def standard(layerNum, description):
+ layerName = board.GetLayerName(layerNum)
+ return Plan(layerNum, layerName, description)
+
+ @staticmethod
+ def copper(layerNum):
+ layerName = board.GetLayerName(layerNum)
+ description = "Copper Layer " + layerName
+ return Plan(layerNum, layerName, description)
+
+plot_plan = [Plan.standard(layerNum, description) for (layerNum, description) in [
+ (F_SilkS, "Silk front"),
+ (F_Mask, "Mask front"),
+ (F_Paste, "Paste front"),
+ (B_SilkS, "Silk bottom"),
+ (B_Mask, "Mask bottom"),
+ (B_Paste, "Paste bottom"),
+ (Edge_Cuts, "Edges")]]
+
+layers = board.GetEnabledLayers()
+for layerNum in layers.CuStack():
+ plot_plan.append(Plan.copper(layerNum))
+
+pctl = PLOT_CONTROLLER(board)
+popt = pctl.GetPlotOptions()
+
+output_directory = args.output_directory
+popt.SetOutputDirectory(output_directory)
+
+if not os.path.isdir(output_directory):
+ try:
+ os.makedirs(output_directory)
+ except:
+ print("Could not make output directory", file=sys.stderr)
+ sys.exit(1)
+
+# A nasty hack to get the base filename
+pctl.SetLayer(F_Cu)
+pctl.OpenPlotfile("", PLOT_FORMAT_GERBER, "")
+filename = pctl.GetPlotFileName()
+try:
+ os.remove(filename)
+except:
+ pass
+pctl.ClosePlot()
+
+# "Use protel filename extensions", default=False
+popt.SetUseGerberProtelExtensions(args.protel_extensions)
+
+basename = os.path.splitext(filename)[0]
+
+drlFileOut = drlFile = basename + "-PTH.drl"
+drlNpthFileOut = drlNpthFile = basename + "-NPTH.drl"
+
+if args.uppercase_extensions:
+ n, e = os.path.splitext(drlFileOut)
+ drlFileOut = n + e.upper()
+ n, e = os.path.splitext(drlNpthFileOut)
+ drlNpthFileOut = n + e.upper()
+
+values = vars(args)
+for plan in plot_plan:
+ pctl.SetLayer(plan.layerNum)
+ pctl.OpenPlotfile("", PLOT_FORMAT_GERBER, plan.description)
+ filename = pctl.GetPlotFileName()
+ pctl.ClosePlot()
+ # By opening and closing the plot we create an empty plot file.
+ try:
+ os.remove(filename)
+ except:
+ pass
+
+ filename, ext = os.path.splitext(filename)
+ if args.uppercase_extensions:
+ ext = ext.upper()
+
+ if plan.layerName in renames:
+ ext = "." + renames[plan.layerName]
+
+ # if plan.arg is not None:
+ # newExt = values[plan.arg]
+ # if newExt is not None:
+ # ext = "." + newExt
+
+ plan.postfix = plan.layerName
+ plan.filename = basename + "-" + plan.postfix + ext
+
+ # print "filename = " + plan.filename + ", postfix=" + plan.postfix
+ # print "filename: " + plan.filename
+
+if args.detect_files_only:
+ with open(args.detect_files_only, "w") as f:
+ for plan in plot_plan:
+ print(plan.filename, file=f)
+
+ print(drlFileOut, file=f)
+ print(drlNpthFileOut, file=f)
+ sys.exit(0)
+
+# Set some important plot options:
+popt.SetPlotFrameRef(False)
+
+# "Default line width (mm)", default=0.1mm
+popt.SetLineWidth(FromMM(0.1))
+
+popt.SetAutoScale(False)
+
+# "Mirrored plot", default=False. Not applicable for Gerber
+popt.SetMirror(False)
+
+# "Include extended attributes", default=False
+popt.SetUseGerberAttributes(args.extended_gerber_attributes)
+
+# "Drill marks"
+popt.SetDrillMarksType(PCB_PLOT_PARAMS.NO_DRILL_SHAPE)
+
+# "Scaling"
+popt.SetScale(1)
+
+# "Use auxilary axis as origin"
+popt.SetUseAuxOrigin(False)
+
+# This by gerbers only (also the name is truly horrid!)
+popt.SetSubtractMaskFromSilk(False)
+
+for plan in plot_plan:
+ pctl.SetLayer(plan.layerNum)
+
+ # print "filename = " + plan.filename + ", postfix=" + plan.postfix
+ pctl.OpenPlotfile(plan.postfix, PLOT_FORMAT_GERBER, plan.description)
+
+ actualFilename = pctl.GetPlotFileName()
+ expectedFilename = plan.filename
+
+ if expectedFilename != actualFilename:
+ os.rename(actualFilename, expectedFilename)
+
+ pctl.PlotLayer()
+ pctl.ClosePlot()
+
+drlwriter = EXCELLON_WRITER(board)
+drlwriter.SetMapFileFormat(PLOT_FORMAT_GERBER)
+
+# "Drill file options"
+
+# "Mirror y axis", default=False
+mirror = False
+
+# "Minimal header", default=True
+minimalHeader = True
+
+offset = wxPoint(0, 0)
+
+# "Merge PTH and NPTH into one file", default=False
+mergeNPTH = False
+drlwriter.SetOptions(mirror, minimalHeader, offset, mergeNPTH)
+
+metricFmt = True
+drlwriter.SetFormat(metricFmt)
+
+genDrl = True
+genMap = args.create_drill_map_file
+
+drlwriter.CreateDrillandMapFilesSet(pctl.GetPlotDirName(), genDrl, genMap)
+
+# This has to be verified that this is the right way to do it.
+if False:
+# Check that the drill files actually was generated
+ if not os.path.isfile(drlFile):
+ print("No drill file generated: {}".format(drlFile), file=sys.stderr)
+
+ if not os.path.isfile(drlNpthFile):
+ print("No drill file generated: {}".format(drlNpthFile), file=sys.stderr)
+
+if drlFile != drlFileOut:
+ os.rename(drlFile, drlFileOut)
+
+if drlNpthFile != drlNpthFileOut:
+ os.rename(drlNpthFile, drlNpthFileOut)
diff --git a/src/ee/tools/digikey_download_facts.py b/src/ee/tools/digikey_download_facts.py
index 923b996..54ff640 100644
--- a/src/ee/tools/digikey_download_facts.py
+++ b/src/ee/tools/digikey_download_facts.py
@@ -46,7 +46,7 @@ parser.add_argument("--force",
args = parser.parse_args()
digikey = dk.Digikey()
-client = dk.DigikeyClient(digikey, on_download=log.debug)
+client = dk.DigikeyClient(digikey, event_handler=lambda kind, msg: (log.debug if kind == "on-download" else log.info)(msg))
repo = dk.DigikeyRepository(digikey, args.out)
diff --git a/test/test_digikey.py b/test/test_digikey.py
index e0cc9ff..051c66f 100644
--- a/test/test_digikey.py
+++ b/test/test_digikey.py
@@ -1,3 +1,4 @@
+import configparser
import ee.digikey as dk
import io
import os.path
@@ -8,7 +9,7 @@ from itertools import groupby
basedir = os.path.dirname(os.path.abspath(__file__))
digikey = dk.Digikey()
-client = dk.DigikeyClient(digikey, on_download=print)
+client = dk.DigikeyClient(digikey, event_handler=lambda kind, msg: print("{}:{}".format(kind, msg)))
@pytest.mark.digikey