#use-added-syntax(jitx)
defpackage props :
  import core
  import collections
  import math
  import jitx
  import jitx/commands

  import ocdb/utils/symbols
  import ocdb/utils/box-symbol
  import ocdb/utils/landpatterns
  import ocdb/utils/defaults
  import ocdb/utils/generic-components

; Our previously-defined components
pcb-pad rect-smd-pad :
  type = SMD
  val pad-shape = Rectangle(0.75, 1.0)
  shape = pad-shape
  layer(SolderMask(Top)) = pad-shape
  layer(Paste(Top)) = pad-shape

pcb-landpattern polarized-chip-landpattern :
  pad a : rect-smd-pad at loc(1.0, 0.0)
  pad c : rect-smd-pad at loc(-1.0, 0.0)
  layer(Courtyard(Top)) = Rectangle(3.0, 2.0)
  layer(Silkscreen("pol", Top)) = Line(0.30, [Point((- 1.5), (- 1.0)) Point((- 1.5), 1.0)])
  layer(Silkscreen("values", Top)) = Text(">REF", 0.7, C, loc(0.0, -1.2))

pcb-component photodiode :
  pin a 
  pin c
  landpattern = polarized-chip-landpattern(a => polarized-chip-landpattern.a, 
                                           c => polarized-chip-landpattern.c)
  val sym = diode-sym(DiodePhoto)
  symbol =                             sym(a => sym.a, 
                                           c => sym.c)                                           
  reference-prefix = "D"
  property(self.responsivity) = 125.0e-6 / 1000.0 ; Current out / light in @850nm (A / lux) 

pcb-component op-amp :
  pin-properties :
    [pin:Ref | pads:Int ...]
    [in+     | 3 ]
    [in-     | 4 ]
    [out     | 1 ]
    [v+      | 5 ]
    [v-      | 2 ]
  assign-landpattern(SOT95P280X145-5N)
  symbol = op-amp-sym(self.in+ => op-amp-sym.in+
                      self.in- => op-amp-sym.in-
                      self.out => op-amp-sym.out
                      self.v-  => op-amp-sym.v-
                      self.v+  => op-amp-sym.v+)

pcb-module transimpedance-amplifier (rf:Double, cf:Double):
  pin input
  pin output
  pin vdd
  pin gnd

  inst op-amp:op-amp
  inst decoupling-cap : ceramic-cap(10.0e-6)

  ; Connect module pins and decoupling to op-amp power pins. 
  net (vdd op-amp.v+ decoupling-cap.p[1])
  net (gnd op-amp.v- decoupling-cap.p[2])

  ; Add and connect feedback network
  inst r : chip-resistor(closest-std-val(rf, 1.0))
  inst c : ceramic-cap(cf)

  net (gnd    op-amp.in+)
  net (input, op-amp.in-, r.p[1] c.p[1])
  net (output op-amp.out, r.p[2] c.p[2])

  schematic-group(self) = trans-amp

pcb-module amplified-photodiode ( photodiode:Instantiable, 
                                  supply-voltage:Double, 
                                  lux-at-full-range:Double, 
                                  target-bandwidth:Double) :
  pin output
  pin vdd
  pin gnd

  inst pd : photodiode
  
  ; Calculate 1% gain resistor TIDU535
  val max-light-current = property(pd.responsivity) * lux-at-full-range
  val target-gain-resistance = closest-std-val(supply-voltage / max-light-current, 1.0)

  ; Calculate feedback capacitor for stability at bandwidth
  val cf = closest-std-val(1.0 / (2.0 * PI * target-gain-resistance * target-bandwidth) * 0.9, 10.0)

  inst amp : transimpedance-amplifier(target-gain-resistance, cf)
  net (pd.c amp.input)
  net (output amp.output)
  net (gnd pd.a amp.gnd)
  net (vdd amp.vdd)

  schematic-group(pd) = schematic-group(amp)

; New code
pcb-bundle i2c:
  pin sda
  pin scl

pcb-component thermocouple-amplifier :
  manufacturer = "Microchip"
  mpn = "MCP9600"
  description = "Thermocouple EMF to Temperature Converter, ±1.5°C Maximum Accuracy"
  port i2c-node : i2c
  pin-properties :
    [pin:Ref      | pads:Int ...         | side:Dir     ]
    [GND      | 1, 3, 5, 6, 7, 9, 10, 13, 17, 18, 21 | Down  ]
    [Vin+     | 2               | Right   ]
    [Vin-     | 4               | Right   ]
    [Vdd      | 8               | Up      ]
    [Alert[1] | 11              | Left    ]
    [Alert[2] | 12              | Left    ]
    [Alert[3] | 14              | Left    ]
    [Alert[4] | 15              | Left    ]
    [ADDR     | 16              | Left    ]
    [i2c-node.scl  | 19              | Left    ]
    [i2c-node.sda  | 20              | Left    ]

  make-box-symbol()
  assign-landpattern(qfn-landpattern(0.65, 5.0, 20, 0.3, 0.4, [3.25 3.25]))

pcb-component microcontroller :
  port i2c-controller : i2c 
  pin-properties :
    [pin:Ref | pads:Int ... | side:Dir]
    [i2c-controller.scl   | 1 | Right]
    [i2c-controller.sda   | 2 | Right]
    for i in 3 to 14 do :
      [PA[i]   | i + 1 | Right]
    [vdd       | 15 | Up]
    [gnd       | 16 | Down]
  make-box-symbol()
  assign-landpattern(soic127p-landpattern(16))

pcb-module my-design :
  inst K : thermocouple-amplifier                                       
  inst mcu : microcontroller
  net (K.i2c-node, mcu.i2c-controller)

  inst high-sensitivity-photodiode : amplified-photodiode(photodiode, 3.3, 500.0,  1.0e6)
  net (high-sensitivity-photodiode.output mcu.PA[4])

  inst connector : pin-header(3) 

    ; Set up power connections
  net GND (high-sensitivity-photodiode.gnd connector.p[1] mcu.gnd K.GND)
  net VDD (high-sensitivity-photodiode.vdd connector.p[2] mcu.vdd K.Vdd)

  symbol(GND) = ocdb/utils/symbols/ground-sym
  symbol(VDD) = ocdb/utils/symbols/supply-sym

make-default-board(my-design, 4, Rectangle(25.0, 10.0))
view-board()
view-schematic()