divert(-1)
  libcct.m4

* Circuit_macros Version 11.0.1, copyright (c) 2026 J. D. Aplevich under     *
* the LaTeX Project Public Licence in file Licence.txt. The files of       *
* this distribution may be redistributed or modified provided that this    *
* copyright notice is included and provided that modifications are clearly *
* marked to distinguish them from this distribution.  There is no warranty *
* whatsoever for these files.                                              *

define(`libcct_')
ifdef(`libgen_',,`include(libgen.m4)divert(-1)')

`==============================================================================
HINTS:

THE ARGUMENTS of circuit elements are optional; if omitted, default values
   are assumed.

TWO-TERMINAL ELEMENTS are constructed as follows, with variations:

   # Draw the initial invisible line (default length rp_len), and set the
   #   direction cosines:
   eleminit_(`$1')

   # Element body height and width
   define(`m4v',...)define(`m4h',...)

   # Visible lines:
   { line to rvec_(rp_len/2-m4h/2,0)
   # The body drawn within a block:
     {[ element body lines ] with .internal position at Here }
     line to rvec_(rp_len/2-m4h/2,0) }

   # Some elements overlay a block to define the body size.
   {[box invis ht_ m4v wid_ m4h ] at rvec_(rp_len/2,0)}

   # The final invisible line:
   line to rvec_(rp_len,0) invis

A side effect of the eleminit_ macro is to change the current drawing angle.

NON-TWO-TERMINAL ELEMENTS are usually constructed within a block:

   set dimension parameters
   [ set size and direction from the initial linespec argument if any
     set orientation (left or right)
     draw internal elements
     define internal locations
     ]

   If there is a linespec argument, it determines orientation
   but not the placement of the element, since [] blocks are placed
   as if they were boxes.

==============================================================================

DEBUGGING: The statement
     print "`$0'($@)" ;
   inserted into a macro will display the macro name and current arguments
   provided the arguments do not contain double quotes.  The line
   `# $0'($@) will write a comment containing the same information into the
   .pic output.  Similarly, the m4 macro m4msg( text ) will display the
   text during m4 processing.

==============================================================================
CUSTOMIZATIONS:

   The non-two-terminal circuit elements enclosed in [] blocks allow
   a final argument not shown in the argument list.  The last argument is
   expanded just before exit from the [] block to allow custom additions
   to the elements.

   Subcomponents of some circuit elements are drawn selectively according
   to a "dna_" string and a sequence of calls to sc_draw(`dna_',arg2,arg3,arg4).
   If the second argument of sc_draw is a substring of the first, it is deleted
   from the first and the third argument is expanded, otherwise the fourth
   argument (which may be null) is expanded.

==============================================================================
 This file redefines default arrow dimensions and the dotrad_ macro.
=============================================================================='

                                `capacitor( linespec,chars,R,height,wid )
                                 Arg2 chars:
                                  [d]F or blank: flat plates; d=hatched fill
                                  [d]C = polarized, curved plate; d=variable
                                  CP = constant phase
                                  E = polarized rectangular plates
                                  K = filled rectangular plates
                                  M = rectangular plates
                                  N = one rectangular plate
                                  P = alternate polarized
                                  + = polarity sign to right of drawing dir
                                  +L =polarity sign to left
                                 arg3 = R: reversed orientation
                                 arg4 = height (defaults F: dimen_/3;
                                          C,P: dimen_/4; E,K: dimen_/5)
                                 arg5 = wid (defaults F: height*0.3;
                                          C,P: height*0.4; E,K: height) '
define(`capacitor',
`ifelse(`$3',R,`reversed(`capacitor',`$1',`$2',,shift(shift(shift($@))))',
 `eleminit_(`$1')
  define(`dna_',`ifelse(`$2',,F,`$2')')dnl
 { sc_draw(`dna_',F,
   `define(`m4cht',`ifelse(`$4',,`dimen_/3',`($4)')')dnl
    define(`m4cwd',`ifelse(`$5',,`m4cht*0.3',`($5)')')dnl
      line to rvec_(rp_len/2-m4cwd/2,0)
      {line from rvec_(0,-m4cht/2) \
          to rvec_(0,m4cht/2)}
      ifelse(m4a,d,`for_(1,3,1,{line from rvec_(0,m4cwd*(m4x-5/2)) \
        to rvec_(m4cwd,m4cwd*(m4x-3/2))})')
      move to rvec_(m4cwd,0)
      {line from rvec_(0,-m4cht/2) \
          to rvec_(0,m4cht/2)}
      line to rvec_(rp_len/2-m4cwd/2,0) ')
  sc_draw(`dna_',CP,
   `define(`m4cht',`ifelse(`$4',,`dimen_/3',`($4)')')dnl
    define(`m4cwd',`ifelse(`$5',,`m4cht*0.8',`($5)')')dnl
    line to rvec_(rp_len/2,0)
    {line from rvec_(-m4cwd/2,m4cht/2) to Here \
       then to rvec_(-m4cwd/2,-m4cht/2) }
    {line from rvec_(0,m4cht/2) to rvec_(m4cwd/2,0) \
       then to rvec_(0,-m4cht/2) }
    line from rvec_(m4cwd/2,0) to rvec_(rp_len/2,0)
   ')
  sc_draw(`dna_',C,
   `define(`m4cht',`ifelse(`$4',,`dimen_/4',`($4)')')dnl
    define(`m4cwd',`ifelse(`$5',,`m4cht*0.4',`($5)')')dnl
    define(`m4cr',`dimen_*0.25')dnl
     line to rvec_(rp_len/2-m4cwd/2,0)
     {line from rvec_(0,-m4cht/2) \
          to rvec_(0,m4cht/2)}
     {arc cw ifelse(m4a,d,-> wid lthick*4 ht lthick*5) \
        from rvec_(m4cwd,-m4cht/2) \
          to rvec_(m4cwd,m4cht/2) \
        with .c at rvec_(m4cwd+sqrt((m4cr)^2-(m4cht/2)^2),0) }
     line from last arc.c+vec_(-m4cr,0) \
          to rvec_(rp_len/2+m4cwd/2,0) ')
  sc_draw(`dna_',P,
   `define(`m4cht',`ifelse(`$4',,`dimen_/4',`($4)')')dnl
    define(`m4cwd',`ifelse(`$5',,`m4cht*0.4',`($5)')')dnl
    define(`m4cr',`dimen_*0.25')dnl
     line to rvec_(rp_len/2-m4cwd/2,0)
     {line from rvec_(m4cwd,-m4cht/2) \
          to rvec_(0,-m4cht/2) \
        then to rvec_(0,m4cht/2) \
        then to rvec_(m4cwd,m4cht/2) }
     {line from rvec_(m4cwd*2/3,-m4cht*3/8) \
          to rvec_(m4cwd*2/3,m4cht*3/8)}
     line from rvec_(m4cwd*2/3,0) \
          to rvec_(rp_len/2+m4cwd/2,0) ')
  sc_draw(`dna_',E,
   `define(`m4cht',`ifelse(`$4',,`dimen_/5',`($4)')')dnl
    define(`m4cwd',`ifelse(`$5',,`m4cht',`($5)')')dnl
    define(`m4cs',`(m4cwd/3.2)')dnl
     line to rvec_(rp_len/2-m4cwd/2,0)
     m4linethicktemp = linethick; thinlines_
     { lbox(m4cs,m4cht) }
     move to rvec_(m4cwd,0)
     {ifsvg(`lbox(-m4cs,m4cht,fill_(0))',`m4fshade(m4fill,lbox(-m4cs,m4cht))')}
     linethick_(m4linethicktemp)
     line to rvec_(rp_len/2-m4cwd/2,0) ')
  sc_draw(`dna_',M,
   `define(`m4cht',`ifelse(`$4',,`dimen_/5',`($4)')')dnl
    define(`m4cwd',`ifelse(`$5',,`m4cht',`($5)')')dnl
    define(`m4cs',`(m4cwd/3.2)')dnl
     line to rvec_(rp_len/2-m4cwd/2,0)
     m4linethicktemp = linethick; thinlines_
     { lbox(m4cs,m4cht) }
     move to rvec_(m4cwd,0)
     { lbox(-m4cs,m4cht) }
     linethick_(m4linethicktemp)
     line to rvec_(rp_len/2-m4cwd/2,0) ')
  sc_draw(`dna_',K,
   `define(`m4cht',`ifelse(`$4',,`dimen_/5',`($4)')')dnl
    define(`m4cwd',`ifelse(`$5',,`m4cht',`($5)')')dnl
    define(`m4cs',`(m4cwd/3.2)')dnl
      line to rvec_(rp_len/2-m4cwd/2,0)
      {ifsvg(`lbox(m4cs,m4cht,fill_(0))',`m4fshade(m4fill,lbox(m4cs,m4cht))')}
      move to rvec_(m4cwd,0)
      {ifsvg(`lbox(-m4cs,m4cht,fill_(0))',`m4fshade(m4fill,lbox(-m4cs,m4cht))')}
      line to rvec_(rp_len/2-m4cwd/2,0) ')
  sc_draw(`dna_',N,
   `define(`m4cht',`ifelse(`$4',,`dimen_/5',`($4)')')dnl
    define(`m4cwd',`ifelse(`$5',,`m4cht*2/3',`($5)')')dnl
    define(`m4cs',`(m4cwd/3.2*3/2)')dnl
      line to rvec_(rp_len/2-m4cwd/2,0)
      { lbox(m4cs,m4cht) }
      move to rvec_(m4cwd,0)
      {line from rvec_(0,m4cht/2) to rvec_(0,-m4cht/2) }
      line to rvec_(rp_len/2-m4cwd/2,0) ')
  }
  ifinstr(`$2',+L,
   `{ move to rvec_(rp_len/2-m4cwd/2-m4cht/3,m4cht/3)
      {line thick 0.5 from rvec_(m4cht/6,0) \
          to rvec_(-m4cht/6,0)}
      line thick 0.5 from rvec_(0,m4cht/6) \
          to rvec_(0,-m4cht/6)}',
   `$2',+,
   `{ move to rvec_(rp_len/2-m4cwd/2-m4cht/3,-m4cht/3)
      {line thick 0.5 from rvec_(m4cht/6,0) \
          to rvec_(-m4cht/6,0)}
      line thick 0.5 from rvec_(0,m4cht/6) \
          to rvec_(0,-m4cht/6)}')
  {[box invis ht_ m4cht wid_ m4cwd ] at rvec_(rp_len/2,0)}
  line to rvec_(rp_len,0) invis ')')

                                `resistor( linespec, cycles, chars, cycle wid )
                                 chars: AC: complex element
                                        E: ebox
                                        ES: ebox with slash
                                        EX: ebox with full-size X
                                        F: FDNR (freq-dependent neg resistor)
                                        Q: offset
                                        H: squared
                                        LD: light dependent
                                        LDE: light dependent ebox
                                        N: IEEE (default)
                                        B: not burnable
                                        T: thermistor
                                        V: varistor variant
                                        R: to right of drawing direction
                                 Alternative: resistor( linespec, keys )
                                 keys:  type=chars; as above
                                        wdth=expr; body width
                                        cycles=expr;
                                        lgth=expr; default cycles*wdth
                                        body=attributes; box body
                                        env=attributes; envelope '
define(`resistor',`eleminit_(`$1')
 pushkeys_(`$2',`type:ifelse(`$3',,N,`$3',R,N,`$3'):N;
   wdth:ifelse(`$4',,(dimen_/6),`($4)');
   cycles:ifinstr(`$2',=,3,ifelse(`$2',,3,(`$2')));
   lgth:(m4`'cycles)*(m4`'wdth);
   body::N; env::N;')
 if m4lgth > rp_len then { eleminit_(to rvec_(m4lgth,0)) }
 M4S: last line.start; M4E: last line.end; M4C: last line.c
 pushdef(`m4ng',sc_draw(`m4type',R,-))dnl
ifelse(
 m4type,N, # Default resistor:
  `pushdef(`m4nN',`eval(2*m4cycles)') m4Rh=m4lgth/m4nN/2
   { line from M4S to M4C+vec_(-m4nN*m4Rh,0)\
     for_(2,m4nN,2,
       `then to M4C+vec_(eval(2*m4x-3-m4nN)*m4Rh, m4wdth/2) \
        then to M4C+vec_(eval(2*m4x-1-m4nN)*m4Rh,-m4wdth/2) \')dnl
        then to M4C+vec_(m4nN*m4Rh, 0) \
        then to M4E   # Maybe replace for obtuse directions:
     [box invis ht_ m4wdth wid_ m4lgth] at 2nd last line.c
     popdef(`m4nN')}',
 m4type,Q,
  `pushdef(`m4nN',`eval(2*m4cycles)') m4Rh=m4lgth/m4nN/2
   { line from M4S to M4C+vec_(-m4nN*m4Rh,0)\
     for_(2,m4nN,2,
      `then to M4C+vec_(eval(2*m4x-2-m4nN)*m4Rh, m4ng`'m4wdth) \
       then to M4C+vec_(eval(2*m4x-m4nN)*m4Rh,0) \')dnl
       then to M4C+vec_(m4nN*m4Rh, 0) \
       then to M4E
     [box invis ht_ m4wdth wid_ m4lgth] at M4C + vec_(0,m4ng`'m4wdth/2)
     popdef(`m4nN')}',
 m4type,ES,
  `ebox(`$1',lgth=m4lgth;wdth=ifinstr(`$2',wdth=,m4wdth,dimen_/5);body=m4body)
   {line from last line.c+vec_( dimen_/2*0.3, m4ng`'dimen_/5/2) \
           to last line.c+vec_(-dimen_/2*0.3,ifelse(m4ng,-,,-)dimen_/5/2)}',
 m4type,EX,
  `ebox(`$1',lgth=m4lgth;wdth=ifinstr(`$2',wdth=,m4wdth,dimen_/5);body=m4body)
   {line from last line.c+vec_( m4lgth/2, m4wdth/2) \
           to last line.c+vec_(-m4lgth/2,-m4wdth/2)}
   {line from last line.c+vec_(-m4lgth/2, m4wdth/2) \
           to last line.c+vec_( m4lgth/2,-m4wdth/2)}',
 m4type,F,
  `pushdef(`m4cht',ifinstr(`$2',hght=,m4hght,dimen_/3))dnl
   pushdef(`m4cwd',ifinstr(`$2',wdth=,m4wdth,m4cht*0.9))dnl
   {line to rvec_(rp_len/2-m4cwd/2,0)
     {[for i=0 to m4cycles do {line from vec_(i*m4cwd/m4cycles,0) \
         to vec_(i*m4cwd/m4cycles,m4cht)}] at M4C}
     line from rvec_(m4cwd,0) to rvec_(rp_len/2+m4cwd/2,0)
   popdef(`m4cht',`m4cwd')}',
 m4type,H,
  `pushdef(`m4nH',`eval(2*m4cycles-1)') m4Rh=m4lgth/m4nH
   pushdef(`m4v',m4ng`'ifinstr(`$2',hght=,m4hght,m4Rh*7/6))dnl
   { line from M4S to M4C+vec_(-m4nH/2*m4Rh,0)\
     for_(1,m4cycles,1,
      `then to M4C+vec_(((m4x-1)*2-m4nH/2)*m4Rh,m4v) \
       then to M4C+vec_(((m4x-1)*2+1-m4nH/2)*m4Rh,m4v) \
       then to M4C+vec_(((m4x-1)*2+1-m4nH/2)*m4Rh,0) \
       ifelse(m4x,m4cycles,,
        `then to M4C+vec_((m4x*2-m4nH/2)*m4Rh,0)') \') then to M4E
     [move from M4C+vec_(-m4nH/2*m4Rh,0) to M4C+vec_(m4nH/2*m4Rh,m4v) \
       then to M4C+vec_(m4nH/2*m4Rh,m4v) then to M4C+vec_(-m4nH/2*m4Rh,0)] \
       at M4C+vec_(0,m4v/2) popdef(`m4nH',`m4v') }',
 m4type,LD,
  `Circle: circle diam m4lgth at M4C m4env
   em_arrows(N,rp_ang*rtod_-45 ifelse(m4ng,-,+90),Circle.rad) \
    with .Head at M4C+vec_(Rect_(Circle.rad,135 ifelse(m4ng,-,+90)))
   resistor(from M4S to M4E,wdth=m4wdth*3/4)
   [box invis wid Circle.diam ht Circle.diam] at Circle ',
 m4type,LDE,
  `Circle: circle diam m4lgth at M4C m4env
   em_arrows(N,rp_ang*rtod_-45 ifelse(m4ng,-,+90),Circle.rad) \
    with .Head at M4C+vec_(Rect_(Circle.rad,135 ifelse(m4ng,-,+90)))
   ebox(from M4S to M4E,lgth=Circle.diam*3/4;wdth=Circle.diam*3/8;body=m4body)
   [box invis wid Circle.diam ht Circle.diam] at Circle ',
 m4type,T,
  `{ tl=m4lgth/2+m4wdth; move to M4C
     Env: spline ifdpic(ctension_) from rvec_(ifdpic(0,-tl*3/40),m4wdth*4/3)\
     to rvec_( tl/3,m4wdth*4/3) then to rvec_( tl,m4wdth*8/9) \
     then to rvec_( tl,-m4wdth*8/9) then to rvec_( tl/3,-m4wdth*4/3) \
     then to rvec_(-tl/3,-m4wdth*4/3) then to rvec_(-tl,-m4wdth*8/9) \
     then to rvec_(-tl,m4wdth*8/9) then to rvec_(-tl/3,m4wdth*4/3) \
     then to rvec_(ifdpic(0,tl*3/40),m4wdth*4/3) m4env }
   ifinstr(`$2',=,
    `resistor(`$1',patsubst(`$2',type=T),`$3',`$4')',
    `resistor(`$1',`$2',patsubst(`$3',T),`$4')')
   [box invis wid_ 2*tl ht_ m4wdth*8/3] at M4C ',
 m4type,V,
  `{line to rvec_(max(0,rp_len/2-m4lgth/2),0)
    pushdef(`m4Vline',line to rvec_(0,ifelse(m4ng,-,,-)`'m4lgth/4) \
        then to rvec_(m4lgth,m4ng`'m4lgth/4) \
        then to rvec_(m4lgth,0) then to Here)dnl
     {[ifelse(m4body,,`m4fshade(m4fill,m4Vline)',`m4Vline m4body')] at M4C }
    line from rvec_(m4lgth,0) to rvec_(max(0,rp_len/2+m4lgth/2),0)
    popdef(`m4Vline') } ',
 m4type,B,
  `ifinstr(`$2',=,
    `resistor(`$1',patsubst(`$2',type=B),`$3',`$4')',
    `resistor(`$1',`$2',patsubst(`$3',B),`$4')')
   m4lbwd = last [].wid_+lthick*2; m4lbht = last [].ht_+lthick*2
   [lbox(m4lbwd+lthick*4,m4lbht+lthick*4,thick linethick/2) m4body] at M4C
   [lbox(m4lbwd,m4lbht,thick 0.4 m4body)] at M4C',
 m4type,AC,
  `ebox(`$1',lgth=m4lgth;wdth=ifinstr(`$2',wdth=,m4wdth,dimen_/5);body=m4body)
   { ACsymbol(at last [],m4wdth*3.5/4,m4wdth/2,R)
     [] wid 2nd last [].wid ht 2nd last [].ht at 2nd last [] } ')
 ifelse(m4type,E, 
  `ebox(`$1',lgth=m4lgth;wdth=ifinstr(`$2',wdth=,m4wdth,dimen_/5);body=m4body)')
 line invis from M4S to M4E')
 popdef(`m4type',`m4wdth',`m4cycles',`m4body',`m4env',`m4lgth',`m4ng')dnl
 ')

                         `potentiometer(linespec, cycles,
                            fractional pos, length, fractional pos, length,...)
                          Resistor in a block, tapped at fractional positions
                          with specified (possibly negative) arrow lengths.
                          Taps are labelled T1, T2, ...'
define(`potentiometer',`[R: resistor(`$1',`$2')
  define(`m4n',`ifelse(`$2',,3,(`$2'))')dnl
  Start: R.start; End: R.end; C: R.c
  m4pot_arrows(1,ifelse(`$3',,0.5,`$3'),ifelse(`$4',,`dimen_*5/12',`$4'),
    shift(shift(shift(shift($@)))))] ')
define(`m4pot_arrows',`ifelse(`$2',,,`FrP: C+vec_((`$2'-0.5)*m4n*dimen_/6,0)
  T`$1': FrP + vec_(0,ifelse(`$3',,`dimen_*5/12',`$3'))
  x = (`$2')*4*m4n+1; x = (int(x)%4)+(x-int(x))
  {arrow from T`$1' to FrP+vec_(0,dimen_/12*(1-(x-2)*sign(x-2)))}
  m4pot_arrows(incr($1),shift(shift(shift($@))))')')

                         `KelvinR(cycles,[R],cycle wid)
                          IEEE resistor with kelvin taps added'
define(`KelvinR',`[
  M4R: resistor(,`$1',,`$3')
  Start: M4S; End: M4E; C: M4C
  pushdef(`m4ng',`ifinstr(`$2',R,-)')dnl
  m4Kelw = ifelse(`$3',,dimen_/6,`($3)')
  m4KelN = 2*ifelse(`$1',,3,(`$1'))
  { dot(at C+vec_(-m4KelN*m4Kelw/4,0),lthick)
    line to C+vec_((-m4KelN-1)*m4Kelw/4,m4ng`'m4Kelw/2) \
     then to C+vec_((-m4KelN-1)*m4Kelw/4,m4ng`'m4Kelw)
    T1: Here
    dot(at C+vec_(m4KelN*m4Kelw/4,0),lthick)
    line to C+vec_((m4KelN+1)*m4Kelw/4,m4ng`'m4Kelw/2) \
     then to C+vec_((m4KelN+1)*m4Kelw/4,m4ng`'m4Kelw)
    T2: Here }
  `$4' popdef(`m4ng') ]') ')

                         `FTcap(chars)
                          Feed-through capacitor; composite element
                          derived from a two-terminal element.
                          Defined points: .Start, .End, .C
                          chars: A|B|C|D element type'
define(`FTcap',`[ define(`FTctyp',`ifelse(`$1',,A,`$1')')dnl
  ifelse(FTctyp,A,
   `capacitor(to vec_(dimen_*2/3,0))
    Start: last line.start; End: last line.end; C: last line.c
    Conductor: line from C+vec_(0,dimen_/3) to C+vec_(0,-dimen_/3)
    T1: last line.start; T2: last line.end',
  FTctyp,B,
   `capacitor(to vec_(dimen_*2/3,0),C)
    Start: last line.start; End: last line.end; C: last line.c
    r = last arc.rad-hlth
    T1: (0.5 between 2nd line.end and last arc.c-vec_(r,0)) + vec_(0,dimen_/3)
    T2: T1+(0,-dimen_*2/3)
    Conductor: line from T1 to T2',
  FTctyp,C,
   `line to vec_(dimen_*2/3,0)
    Start: last line.start; End: last line.end; C: last line.c
    rp_a = rp_ang
    capacitor(from C to C-vec_(0,dimen_/10),C)
    point_(rp_a)
    line from last line.end to last line.end-vec_(0,dimen_/3)
    T: Here',
  FTctyp,D,
   `Start: Here
    capacitor(to rvec_(dimen_/3,0),C)
    C: Here
    { line to rvec_(0,-dimen_/3); T: Here }
    End: rvec_(dimen_/3,0)
    rp_a = rp_ang
    capacitor(from End to Here,C)
    point_(rp_a)')
  `$2' ]')

                         `addtaps([ahead | type=ahead;name=Name],
                            fractional pos, length, fractional pos, length,...)
                          ahead = blank or one of . - <- -> <->
                          Tap names are Tap1, Tap2, ...  or
                          Name1, Name2, ... if specified'
define(`addtaps',`
ifelse(`$2',,`undefine(`m4tap_x')popdef(`m4type',`m4name')',
 `ifdef(`m4tap_x',`define(`m4tap_x',incr(m4tap_x))',
  `define(`m4tap_x',1) dnl 1st time through
   M4tap_w: last [].w_; M4tap_e: last [].e_
   pushkeys_(`$1',type::N; name:Tap:N)dnl
   ifelse(m4type,,`ifinstr(`$1',=,,`poppushdef(`m4type',`$1')')')dnl
   M4tap_xy: (last [].wid_,last [].ht_)')
  {define(`m4tapl',`ifelse(`$3',,`dimen_/3',`$3')')dnl
  move to (`$2' between M4tap_w and M4tap_e) + vec_(0,sign(m4tapl)*M4tap_xy.y/2)
  ifinstr(m4type,.,`{dot(,lthick)}');dnl
  line ifelse(m4type,.,,m4type,-,,m4type) to rvec_(0,m4tapl)
  m4name`'m4tap_x: Here }
  addtaps(,shift(shift(shift($@))))')')

                         `tapped(`two-terminal element', . | <- | -> | <-> ,
                            fractional pos, length, fractional pos, length,...)
                          Draw the two-terminal element and taps in a [] block'
define(`tapped',`[ $1
  Start: last line.start; End: last line.end; C: last line.c
  addtaps(shift($@)) ]')

                         `shielded(`two-terminal element',L|U, line attributes )
                            L= shield left half (wrt drawing direction)
                            R= shield right half (default both halves)'
define(`shielded',`[ $1
  Start: last line.start; End: last line.end; C: last line.c
  W: last line.c - vec_(last [].wid_/2+dimen_/8,0)
  E: last line.c + vec_(last [].wid_/2+dimen_/8,0)
  NW: last [].nw_ + vec_(-dimen_/8,dimen_/8)
  NE: last [].ne_ + vec_(dimen_/8,dimen_/8)
  SE: last [].se_ + vec_(dimen_/8,-dimen_/8)
  SW: last [].sw_ + vec_(-dimen_/8,-dimen_/8)
  ifinstr(`$2',L,`line from W to NW then to NE then to E dashed `$3'',
   `$2',R,`line from W to SW then to SE then to E dashed `$3'',
   `line from W to NW then to NE then to SE then to SW then to W dashed `$3'')
  `$4']')

                         `b_current( label, above_|below_, O[ut],
                            S[tart]|E[nd], frac )
                          Branch current for last-drawn element.  The arrowhead
                          is drawn frac (default 2/3) of the way between
                          the line end and element body.'
define(`b_current',
 `define(`m4y',`ifelse(`$5',,2/3,`($5)')')dnl
  define(`m4v',`ifinstr(`$4',E,
   `ifinstr(`$3',O,-)',`ifinstr(`$3',O,,-)')arrowht')dnl
  define(`m4h',`(rp_len-last [].wid_)/2')
  { move to last line.start+vec_(ifinstr(`$4',E,`rp_len-')dnl
    ifinstr(`$3',O,`(m4h-arrowht)*m4y',`(m4h*m4y+arrowht/3)'),0)
    arrow <- m4c_l to rvec_(m4v,0) ifelse(`$1',,,
   `m4lstring(`$1',"sp_`iflatex(`$ `$1'$',`$1')'sp_") \
     ifelse(`$2',,`above_',`$2')')}')

                                `larrow( label, <-, separation )
                                 Arrow alongside the left of the last-drawn
                                 element'
define(`larrow',`define(`m4h',`min(lin_leng(last line),linewid)/2')dnl
 define(`m4v',`ifelse(`$3',,`5pt__',`($3)')')dnl
 {arrow `$2' from last [].n_+vec_(-m4h,m4v) \
    to last [].n_+vec_(m4h,m4v) \
  m4lstring(`$1',"sp_`iflatex(`$ `$1'$',` $1')'sp_") above_}')

                                `rarrow( label, <-, separation )
                                 Arrow alongside the right of the last-drawn
                                 element'
define(`rarrow',`define(`m4h',`min(lin_leng(last line),linewid)/2')dnl
 define(`m4v',`ifelse(`$3',,`5pt__',`($3)')')dnl
 {arrow `$2' from last [].s_+vec_(-m4h,-m4v) \
    to last [].s_+vec_(m4h,-m4v) \
  m4lstring(`$1',"sp_`iflatex(`$ `$1'$',` $1')'sp_") below_}')

                                `inductor( linespec, W|L, cycles, M|P|K[n],
                                   loop wid )
                                 W=wide arcs (default narrow); L=looped arcs
                                 arg3= integer (number of loops)
                                 arg4= M[n]=metal core
                                       P[n]=(ferrite) powder core (dashed lines)
                                       K[n]=long-dashed core lines
                                       n=integer (default 2 lines)
                                 arg5 loop wid defaults W,L: dimen_/5,
                                                      other: dimen_/8'
define(`inductor',`eleminit_(`$1')
 define(`m4hlw',`ifelse(`$5',,`dimen_/10',`($5)/2')')dnl half loop wid
 define(`m4n',`ifelse(`$3',,4,`$3')')dnl
 ifelse(`$2',W, `define(`m4wd',((2*m4n-2)*m4c2t+2*m4ct)*m4hlw)',
        `$2',L, `define(`m4wd',(m4n+1)*m4hlw)',
    `define(`m4ht',`ifelse(`$5',,`dimen_/16',(`$5')/2)')dnl half other loop wid
     define(`m4wd',m4n*m4ht*2)')dnl
 { line to rvec_((rp_len-m4wd)/2,0)
   {M4coil: [ S: Here;
    ifelse(`$2',W,`define(`m4ht',`(1+m4st)*m4hlw')dnl
      define(`m4dp',`(m4s2t-m4st)*m4hlw') round
      arc cw from Here to rvec_(vscal_(m4hlw,m4ct+m4c2t,m4st-m4s2t)) \
         with .c at rvec_(vscal_(m4hlw,m4ct,m4st)); round
      for m4i=3 to m4n do { arc cw from Here to rvec_(vscal_(m4hlw,2*m4c2t,0)) \
         with .c at rvec_(vscal_(m4hlw,m4c2t,m4s2t)); round }
      arc cw from Here to rvec_(vscal_(m4hlw,m4ct+m4c2t,m4s2t-m4st)) \
         with .c at rvec_(vscal_(m4hlw,m4c2t,m4s2t)); round ',
    `$2',L,`define(`m4ht',`m4hlw*10/8')define(`m4dp',`m4hlw/2')dnl
      round; spline ifdpic(0.55) to rvec_(0,m4ht) \
      for_(1,m4n,1,`\
       then to rvec_((m4x+0.3)*m4hlw, m4ht) \
       then to rvec_((m4x+0.3)*m4hlw,-m4dp) \
       then to rvec_((m4x-0.3)*m4hlw,-m4dp) \
       then to rvec_((m4x-0.3)*m4hlw, m4ht) \')\
       then to rvec_(m4wd,m4ht) \
       then to rvec_(m4wd,0); round ',
    `define(`m4dp',0)dnl
      ifelse(ifpstricks(T)`'ifmpost(T)`'ifpgf(T)`'ifsvg(T),T,
        `define(`m4y')',`undefine(`m4y')')dnl
      ifdef(`m4y',`{line to rvec_(0,-hlth)};')
      for m4i=1 to m4n do {
        arc cw from Here to rvec_(m4ht*2,0) with .c at rvec_(m4ht,0)
        ifdef(`m4y',`{line to rvec_(0,-hlth)}') } ') ] with .S at Here }
    ifelse(ifinstr(`$4',M,T,`$4',P,T,`$4',K,T),T,
     `define(`m4nL',ifelse(len(`$4'),1,2,substr(`$4',1)))dnl
      define(`m4hs',`(dimen_/24+(m4nL-1)*dimen_/16)')dnl
      { m4m_core(M4coil.S+vec_(m4wd/2,0), m4wd, m4ht+dimen_/24, dimen_/16,
        ifinstr( `$4',P,`dashed m4wd/(2*m4n+1)',
                 `$4',K,`dashed m4wd/(2*m4n+1)*3'), m4nL)
      [ box invis wid M4coil.wid ht M4coil.ht at M4coil
        M: move from M4Core`'m4nL.start to M4Core`'m4nL.end ] \
        with .M.c at M4Core`'m4nL.c }')
   line from rvec_(m4wd,0) to rvec_((rp_len+m4wd)/2,0) }
   line to rvec_(rp_len,0) invis ')
                               `m4m_core(bottom center, length, ht offset,
                                 separation, linetype, nlines)
                                 nlines=lines for the metal core'
define(`m4m_core',`for_(1,`$6',1,`{M4Core`'m4x: line \
   from `$1'+vec_(-(`$2')/2,`$3'+(`$4')*(m4x-1)) \
     to `$1'+vec_( (`$2')/2,`$3'+(`$4')*(m4x-1)) `$5''})')
define(`m4ct',`Cos(25)')define(`m4st',`Sin(25)')
define(`m4c2t',`Cos(50)')define(`m4s2t',`Sin(50)')

                                `transformer( linespec, L|R, np,
                                  [A|M[n]|P[n]|K[n]][W|L][D1|D2|D12|D21], ns )
                                 2-winding transformer or choke:
                                 np = number of primary arcs
                                 ns = number of secondary arcs
                                 A = air core;
                                 M[n] = metal core (default); n=number of lines
                                 P[n] = powder (dashed) core
                                 K[n] = long dashed core
                                 W = wide windings; L = looped windings
                                 D1: phase dots at P1 and S1 ends; D2: dots
                                 at P2 and S2 ends; D12: dots at P1 and S2
                                 ends; D21: dots at P2 and S1 ends'
define(`transformer', `[ P1: Here define(`m4drt',m4_dir_)
 define(`m4WL',`ifinstr(`$4',W,W,`$4',L,L)')dnl
 define(`m4np',`ifelse(`$3',,4,(`$3'))')dnl
 define(`m4ns',`ifelse(`$5',,4,(`$5'))')dnl
 ifelse(`$1',,`mvw = max(\
  ifelse(m4WL,W,`dimen_/5*((m4np-1)*m4c2t+m4ct)',`m4np*dimen_/8'),dimen_*2/3)
  move to P1+vec_(mvw,0)',
  move `$1' )
 P2: Here
 TP: 0.5 between P1 and P2
 L1: inductor(from ifelse(`$2',R,`P2 to P1',`P1 to P2'),m4WL,`$3')
 define(`m4WP',m4wd)dnl
 define(`m4t',`ifelse(m4WL,W,((2*m4ns-2)*m4c2t+2)*m4hlw,m4WL,L,(m4ns+1)*m4hlw,
                      m4ns*m4ht*2)')dnl
 ifinstr(`$4',A,
  `move to last line.c+vec_(0,m4ht*ifelse(m4WL,W,3,m4WL,L,3,4))',
  `define(`m4LL',`regexp(`$4',[MPK]\([0-9][0-9]*\),\1)')dnl
   define(`m4nL',`ifelse(m4LL,,2,m4LL)')dnl
   m4m_core(rvec_(-(rp_len/2),0), max(m4wd,m4t), m4ht+dimen_/12, dimen_/8,
     ifinstr( `$4',P,`dashed m4wd/(2*m4n+1)',
              `$4',K,`dashed m4wd/(2*m4n+1)*3'), m4nL)
   move to last line.c+vec_(0,m4ht+dimen_/12) ')
 TS: Here
 S2: rvec_( ifelse(`$2',R,-)(ifelse(`$5',,rp_len/2,m4t/2)), 0 )
 S1: 2 between S2 and Here
 L2: inductor(from ifelse(`$2',R,`S1 to S2',`S2 to S1'),m4WL,`$5')
 rpoint_(from P1 to P2) define(`m4WS',m4wd)
 ifinstr(`$4',D1,
   `m4trdot(P1,P2,-,m4WP,ifelse(`$2',R,-),D1:)
    ifinstr(`$4',D12,`m4trdot(S1,S2, ,m4WS,ifelse(`$2',R,,-),D2:)',
                     `m4trdot(S1,S2,-,m4WS,ifelse(`$2',R,,-),D2:)')',
  `$4',D2,
   `m4trdot(P1,P2,,m4WP,ifelse(`$2',R,-),D1:)
    ifinstr(`$4',D21,`m4trdot(S1,S2,-,m4WS,ifelse(`$2',R,,-),D2:)',
                     `m4trdot(S1,S2, ,m4WS,ifelse(`$2',R,,-),D2:)')')
  m4xpand(m4drt`'_)
 `$6' ]')
define(`m4trdot',`{`$6'dot(at (0.5 between `$1' and `$2') \
      +vec_(`$3'((`$4')/2+m4hlw),`$5'dimen_/16), dotrad_/2)}')

                                `delay( linespec, width, attributes or keys )
                                 keys:
                                     wdth=expr;
                                     lgth=expr;
                                     type=A|S;
                                     body=attributes; e.g. shaded '
define(`delay',`eleminit_(`$1')
 pushkeys_(`$3',`wdth:ifelse(`$2',,delay_rad_*2,`$2'); lgth:m4`'wdth*5/6;
   type:A:N; body::N;') dnl
 ifinstr(`$3',=,,`ifelse(m4body,,`poppushdef(`m4body',`$3')')')dnl
 ifelse(m4type,S,`popdef(`m4lgth',`m4wdth')dnl
   pushkeys_(`$3',`lgth:dimen_*6/5; wdth:m4`'lgth/4')')dnl
 { line to rvec_(rp_len/2-m4lgth/2,0)
   {ifelse(m4type,A,`[ W: Here
      line from rvec_(m4wdth/3,-m4wdth/2) to rvec_(0,-m4wdth/2) \
        then to rvec_(0,m4wdth/2) then to rvec_(m4wdth/3,m4wdth/2) m4body
      arc cw to rvec_(0,-m4wdth) with .c at rvec_(0,-m4wdth/2) m4body ]',
    m4type,S,
     `rotbox(m4lgth,m4wdth,m4body,r=m4wdth/2,
       {rotbox(m4wdth/4,m4wdth,) with .W at rvec_(-m4lgth+m4wdth/2,0)})')\
   with .W at Here }
   line from rvec_(m4lgth,0) to rvec_(rp_len/2+m4lgth/2,0) }
 line to rvec_(rp_len,0) invis dnl
 popdef(`m4wd',`m4wdth',`m4type',`m4body') ')

                                `xtal( linespec, keys ) (2-terminal crystal)
                                 keys:
                                   type=N (default) or R (round);
                                 type N keys:
                                   lgth=expr; (body length)
                                   wdth=expr; (body width)
                                   bxwd=expr; (body inner box width)
                                   box= box attributes; (shaded ...) 
                                 type R keys:
                                   outerdiam=expr;
                                   innerdiam=expr;
                                   outer= outer circle attributes; (dotted ...)
                                   inner= inner circle attributes; (shaded ...)'
define(`xtal',`eleminit_(`$1') pushkey_(`$2',type,N,N)
 ifelse(m4type,R,`pushkeys_(`$2',`outerdia:dimen_/3;innerdia:m4`'outerdia*0.4;
     outer::N; inner::N;') define(`m4wd',m4outerdia) ',
  `pushkeys_(`$2',`wdth:dimen_/4; lgth:m4wdth*2/3; bxwd:m4lgth/2; box::N;')dnl
   define(`m4wd',m4lgth) ')
 { line to rvec_(rp_len/2-m4wd/2,0)
   {[ Orig: Here; ifelse(m4type,R,
    `{circle diam m4outerdia at rvec_(m4outerdia/2,0) m4outer}
     {circle diam m4innerdia at rvec_(m4outerdia/2,0) m4inner}
     popdef(`m4type',`m4outerdia',`m4innerdia',`m4outer',`m4inner') ',
    `{line from rvec_(0,-m4wdth/3) \
            to rvec_(0,m4wdth/3)}
     { move to rvec_(m4lgth/2-m4bxwd/2,0)
       line to rvec_(0,m4wdth/2) \
         then to rvec_(m4bxwd,m4wdth/2) \
         then to rvec_(m4bxwd,-m4wdth/2) \
         then to rvec_(0,-m4wdth/2) \
         then to Here m4box }
     move to rvec_(m4lgth,0)
     {line from rvec_(0,-m4wdth/3) \
            to rvec_(0,m4wdth/3)}
     popdef(`m4type',`m4wdth',`m4lgth',`m4bxwd',`m4box')') ] with .Orig at Here}
   line from rvec_(m4wd,0) to rvec_(rp_len/2+m4wd/2,0) }
 line to rvec_(rp_len,0) invis ')

                  `source( linespec, chars,
                       diameter, R, attributes, body name)
                    chars:
                     AC = AC source;
                     B = bulb;
                     F = fluorescent;
                     G = generator;
                     H = step function;
                     I = current source;
                     i = alternate current source;
                     ii = double arrowhead current source;
                     ti = truncated-bar current source;
                     dci = DC current source;
                     L = lamp;
                     N = neon; NA = neon 2; NB = neon 3;
                     P = pulse;
                     Q = charge;
                     R = ramp;
                     S[C[r]|E[r]] = sinusoid;
                       SC = quarter arc; SE = arc; r = right orientation;
                     T = triangle;
                     U = square-wave;
                     V = voltage source;
                     v = alternate voltage source;
                     tv = truncated bar voltage source;
                     dcv = DC voltage source;
                     X = interior X;
                     other = custom interior label or waveform;
                     arg 4: R = reversed polarity; 
                     arg 5 modifies the circle with e.g., color or fill
                     arg 6 names the body [] block'
define(`source',`ifelse(`$4',R,
 `reversed(`source',`$1',`$2',`$3',,shift(shift(shift(shift($@)))))',
 `eleminit_(`$1')
 define(`m4h',ifelse(`$3',,`sourcerad_',`($3)/2'))dnl
 ifelse(
 `$2',G,`m4_sourceGQ(`$6',$@)',
 `$2',Q,`m4_sourceGQ(`$6',$@)',
 `{ line to rvec_(rp_len/2-m4h,0)
    move to rvec_(m4h,0)
  { Src_C: circle rad m4h ifelse(`$2',dci,invis) `$5' at Here }
  ifelse(`$2',,,
  `$2',F,`{ line from rvec_(-m4h,0) \
          to rvec_(-m4h/2,0)}
          { line from rvec_(-m4h/2,-m4h/2) \
          to rvec_(-m4h/2,m4h/2)}
          { line from rvec_(m4h/2,-m4h/2) \
          to rvec_(m4h/2,m4h/2)}
          { line from rvec_(m4h,0) \
          to rvec_(m4h/2,0)}',
  `$2',I,`{arrow from rvec_(-m4h*3/4,0) \
          to rvec_(m4h*3/4,0)}',
  `$2',dci,`{arrow from rvec_(-m4h*3/4,0) \
          to rvec_(m4h*3/4,0)}
          ifdef(`dcigapangle_',,`define(`dcigapangle_',20)')dnl
          {arc from Src_C+vec_(Rect_(m4h,270+dcigapangle_/2)) \
            to Src_C+(Rect_(m4h,90-dcigapangle_/2)) with .c at Src_C}
          {arc from Src_C+vec_(Rect_(m4h,90+dcigapangle_/2)) \
            to Src_C+(Rect_(m4h,270-dcigapangle_/2)) with .c at Src_C} ',
  `$2',ti,`{line thick 2*linethick from rvec_(0,-m4h) \
          to rvec_(0,m4h) chop m4h/4}',
  `$2',ii,`{line from rvec_(-m4h,0) \
          to rvec_(m4h,0)}
          {line thick 1.2*linethick from rvec_(m4h/12,-m4h*0.45) \
          to rvec_(m4h*5/6,0) \
          then to rvec_(m4h/12,m4h*0.45)}
          {line thick 1.2*linethick from rvec_(-m4h*3/4,-m4h*0.45) \
          to Here \
          then to rvec_(-m4h*3/4,m4h*0.45)}',
  `$2',i,`{line from rvec_(0,-m4h) \
          to rvec_(0,m4h)}',
  `$2',B,`{line from rvec_(-m4h,0) \
          to rvec_(-m4h*2/3,0)
           round
           arc ccw to rvec_(m4h*12/12,0) with .c at rvec_(m4h*12/24,0)
           arc ccw to rvec_(-m4h*2/3,0) with .c at rvec_(-m4h*1/3,0)
           arc ccw to rvec_(m4h*12/12,0) with .c at rvec_(m4h*12/24,0)
           round
           line to rvec_(m4h/3,0)}',
  `$2',H,`{ line from Here+(-m4h/2,-m4h/3) \
          to Here+(0,-m4h/3) \
             then to Here+(0,m4h/3) \
             then to Here+(m4h/2,m4h/3) }',
  `$2',L,`{line from rvec_(-m4h,0) \
          to rvec_(-m4h/4,0)
           round
           spline to rvec_(m4h/12,m4h*2/3) \
             then to rvec_(m4h*5/12,m4h*2/3) \
             then to rvec_(m4h/2,0)
           round
           line to rvec_(m4h*3/4,0)}',
  `$2',NA,`{ line from rvec_(-m4h,0) \
          to rvec_(-m4h/5,0)
          { line to  rvec_(0,m4h) with .c at Here } }
          { line from rvec_(m4h,0) \
          to rvec_(m4h/5,0)
          { line to  rvec_(0,m4h) with .c at Here } }
          { dot(at rvec_(-m4h/2,-m4h/2)) } ',
  `$2',dcv,`{ line to  rvec_(0,m4h) with .c at rvec_(-m4h/5,0) }
          { line to  rvec_(0,m4h) with .c at rvec_(m4h/5,0) } ',
  `$2',NB,`{ line from rvec_(-m4h,0) \
          to rvec_(-m4h/2,0)
          { line to  rvec_(0,m4h) with .c at Here } }
          { line from rvec_(m4h,0) \
          to rvec_(m4h/2,0)
          { dot(,,1) } }
          { dot(at rvec_(0,-m4h/2)) } ',
  `$2',N,`{ {line from rvec_(-m4h,0) \
          to rvec_(-m4h/2,0)}
            for_(70,250,180,
            `{ line from rvec_(Rect_(m4h/2,-m4x)) \
                 to rvec_(Rect_(m4h/2,m4x))
               round }
             { arc cw from rvec_(Rect_(m4h/2,m4x)) \
                 to rvec_(Rect_(m4h/2,-m4x)) \
                 with .c at Here
               round }')
             {line from rvec_(m4h/2,0) \
          to rvec_(m4h,0)}}',
  `$2',V,`{"ifsvg(-,`\scriptsize$-$')" at rvec_(-m4h/2,0) ifsvg(+(0,textht/10))}
          {"ifsvg(svg_small(+),`\scriptsize$+$')" \
              at rvec_( m4h/2,0) ifsvg(+(0,textht/10))}',
  `$2',tv,`{line thick 2*linethick from rvec_(-m4h,0) \
          to rvec_(m4h,0) chop m4h/4}',
  `$2',v,`{line from rvec_(-m4h,0) \
          to rvec_(m4h,0)}',
  `$2',AC,`{ACsymbol(,,,AR)}',
  `$2',P,`{ line from Here+(-m4h/2,-m4h/4) \
        to Here+(-m4h/4,-m4h/4) \
            then to Here+(-m4h/4,m4h/4) \
            then to Here+(m4h/4,m4h/4) \
            then to Here+(m4h/4,-m4h/4) \
            then to Here+(m4h/2,-m4h/4) }',
  `$2',U,`{ line from Here+(-m4h/2,0) \
        to Here+(-m4h/2,m4h/3) \
            then to Here+(0,m4h/3) \
            then to Here+(0,-m4h/3) \
            then to Here+(m4h/2,-m4h/3) \
            then to Here+(m4h/2,0) }',
  `$2',R,`{ line from Here+(-m4h*2/3,-m4h/3) \
        to Here+(m4h/3,m4h/2) \
            then to Here+(m4h/3,-m4h/3) }',
  `$2',SCr,`{ arc cw from rvec_(-m4h,0) \
     to rvec_(0,-m4h) \
     with .c at rvec_(-m4h,-m4h) }',
  `$2',SC,`{ arc from rvec_(-m4h,0) \
     to rvec_(0,m4h) \
     with .c at rvec_(-m4h,m4h) }',
  `$2',SEr,`{ arc cw from Cintersect(Here,m4h,rvec_(0,-2*m4h),1.8*m4h,R) \
     to Cintersect(Here,m4h,rvec_(0,-2*m4h),1.8*m4h) \
     with .c at rvec_(0,-2*m4h) }',
  `$2',SE,`{ arc from Cintersect(Here,m4h,rvec_(0,2*m4h),1.8*m4h) \
     to Cintersect(Here,m4h,rvec_(0,2*m4h),1.8*m4h,R) \
     with .c at rvec_(0,2*m4h) }',
  `$2',S,`{ACsymbol(,,,R)}',
  `$2',T,`{ line from Here+(-m4h*3/4,-m4h/4) \
        to Here+(-m4h/4,m4h/4) \
            then to Here+(m4h/4,-m4h/4) \
            then to Here+(m4h*3/4,m4h/4) }',
  `$2',X,`define(`m4v',`m4h/sqrt(2)')dnl
    {line from rvec_(-m4v,m4v) \
          to rvec_(m4v,-m4v)}
    {line from rvec_(-m4v,-m4v) \
          to rvec_(m4v,m4v)}',
  `{$2}' )
  line from rvec_(m4h,0) \
          to rvec_(rp_len/2,0)}
  {ifelse(`$6',,,`$6':)[box invis ht_ m4h*2 wid_ m4h*2] at rvec_(rp_len/2,0)}')
  line to rvec_(rp_len,0) invis ')')
                    `Internal to source macro:'
define(`m4_sourceGQ',
 `m4sh = m4h*3/4
  m4sv = sqrt((m4h)^2-m4sh^2)
  { line to rvec_(rp_len/2-(m4h+m4sh),0)
   {ifelse(`$1',,,`$1':)[ Cx: rvec_(m4h,0)
     ifelse(`$6',,,
      `{circle invis rad m4h `$6' with .c at Cx}
       {circle invis rad m4h `$6' with .c at Cx+vec_(m4sh*2,0)}')
     L: Cx+vec_(m4sh, m4sv) 
     R: Cx+vec_(m4sh,-m4sv)
     M1: Cx-vec_(m4h/6,0)
     C1: circle rad m4h with .c at Cx `$5'
     C2: ifelse(`$3',G,`circle rad m4h',`arc rad m4h from R to L') \
       `$5' with .c at C1 +vec_(m4sh*2,0)
     M2: C2+vec_(m4h/6,0)
     ] at rvec_(m4h+m4sh,0)}
   line from rvec_((m4h+m4sh)*2,0) \
           to rvec_(rp_len/2+(m4h+m4sh),0) } ')

                    `indicator( source arg1-arg6, keys )
                     keys:
                       len=expr;
                       ray=attributes; '
 define(`indicator',`source($@) pushdef(`m4s',`last [].wid*5/8')
   pushkeys_(`$7',`len:last [].wid/2; ray::N;')dnl
   for ta=45 to 315 by 90 do {{ line from last []+vec_(Rect_(m4s,ta)) \
     to last []+vec_(Rect_(m4s+m4len,ta)) m4ray }}
   popdef(`m4len',`m4ray',`m4s') ')

                    `ttmotor( linespec, string, diameter, brushwid, brushht )'
 define(`ttmotor',`eleminit_(`$1')
  pushdef(`m4r',ifelse(`$3',,`sourcerad_',`($3)/2'))dnl
  pushdef(`m4w',ifelse(`$4',,`sourcerad_/4',`($4)'))dnl
  pushdef(`m4h',ifelse(`$5',,`sourcerad_/2',`($5)'))dnl
  pushdef(`m4cr',`(m4r-sqrt(max(m4r*m4r-m4h*m4h/4,0)))')dnl
  { line to rvec_(max(rp_len/2-m4r-m4w,0),0)
    {[{ line from rvec_(m4w+m4cr,m4h/2) \
          to rvec_(0,m4h/2) \
        then to rvec_(0,-m4h/2) \
        then to rvec_(m4w+m4cr,-m4h/2) }
    { TTM_C: circle rad m4r \
       at rvec_(m4w+m4r,0) ifelse(`$2',,,`m4lstring($2,"$2")') }
    move to rvec_((m4w+m4r)*2,0)
    { line from rvec_(-m4w-m4cr,m4h/2) \
          to rvec_(0,m4h/2) \
        then to rvec_(0,-m4h/2) \
        then to rvec_(-m4w-m4cr,-m4h/2) }] at rvec_(m4r+m4w,0)}
    line from rvec_((m4w+m4r)*2,0) to rvec_(max(rp_len/2+m4r+m4w,0), 0) }
  line invis to rvec_(rp_len,0) popdef(`m4r',`m4w',`m4h',`m4cr') ')

                                `consource( linespec ,V|I|tv|v|ti|i|P, R,
                                   attributes )
                                 Controlled source
                                 Arg3:
                                  V= voltage
                                  I= current
                                  v= voltage type 2
                                  tv= voltage type 3
                                  i= current type 2
                                  ti= current type 3
                                  P= proximity sensor
                                 arg 4 can be used to modify the body with e.g.
                                   color, fill, or ;internal symbols
                                   e.g. consource(,,,; "S" at C)'
define(`consource',`ifelse(`$3',R,
 `reversed(`consource',`$1',`$2',,shift(shift(shift($@))))',
 `eleminit_(`$1')
  {line to rvec_(rp_len/2-csdim_,0)
    {[ N: rvec_(csdim_,csdim_)
       S: rvec_(csdim_,-csdim_)
       E: rvec_(2*csdim_,0)
       W: Here; C: rvec_(csdim_,0) 
     {line to N then to E then to S then to W `$4'}
     ifelse(`$2',I,
      `{arrow to E chop csdim_/4}',
     `$2',ti,
      `{line thick 2*linethick from N to S chop csdim_/4}',
     `$2',i,
      `{line from N to S}',
     `$2',V,
      `{"iflatex(`\scriptsize$-$',-)" \
        at rvec_(csdim_*0.5,0) ifsvg(+(0,textht/10))}
       {"iflatex(`\scriptsize$+$',+)" \
        at rvec_(csdim_*1.5,0) ifsvg(+(0,textht/10))}',
     `$2',tv,
      `{line thick 2*linethick to E chop csdim_/4} ',
     `$2',v,
      `{line to E} ',
     `$2',P,
      `{ Proxim(2*csdim_) at rvec_(csdim_,0) }') ] with .W at Here}
    line from last [].E to rvec_(rp_len/2+csdim_,0)}
  line to rvec_(rp_len,0) invis ')')

                  `geiger( linespec, r, diameter, R, attributes, body name)
                   Arguments as for source except arg2 r = right orientation '
define(`geiger',`pushdef(`m4h',ifelse(`$3',,`sourcerad_',`($3)/2'))dnl
 pushdef(`m4R',`ifelse(`$4',R,+180)')dnl
 source(`$1',F,shift(shift($@)))
 {dot(at rvec_(-rp_len/2,0)+vec_(Rect_(m4h*2/3,ifelse(`$2',r,,-)110 m4R)))}
 {"iflatex($+$,+)" at rvec_(-rp_len/2,0) \
   +vec_(Rect_(m4h*3/2,ifelse(`$2',r,,-)30 m4R))}
 {em_arrows(ND,rp_ang*rtod_ ifelse(`$2',r,+,-)135 m4R,m4h) with .Head \
   at rvec_(-rp_len/2,0)+vec_(Rect_(m4h*5/4,ifelse(`$2',r,-)45 m4R))} dnl
 popdef(`m4h',`m4R') ')

                        `Proxim(size, U|D|L|R|degrees, attributes)
                          Proximity symbol
                          Arg2 default: current direction'
define(`Proxim',`[
 define(`m4prwid',`ifelse(`$1',,(dimen_/2),`($1)')')dnl
 setdir_(ifelse(`$2',,`ifdef(`m4a_',rp_ang*rtod_,0)',`$2'))
 M4PRN: rvec_(0, m4prwid/2)
 M4PRE: rvec_(m4prwid/2,0)
 M4PRS: rvec_(0,-m4prwid/2)
 M4PRW: rvec_(-m4prwid/2,0)
 { line from 1/2 between M4PRN and M4PRE to M4PRE then to M4PRS \
    then to M4PRW then to M4PRN then to 1/2 between M4PRN and M4PRE `$3' }
 { line from 1/4 between M4PRW and M4PRN to 1/4 between M4PRE and M4PRN }
 { line from 1/4 between M4PRW and M4PRS to 1/4 between M4PRE and M4PRS }
 `$4'; resetdir_ ]')

                        `Magn(len, ht, U|D|L|R|degrees)
                          Magnetic relay action symbol'
define(`Magn',`[
 define(`m4mawi2',`ifelse(`$1',,(dimen_/4),`(($1)/2)')')dnl
 define(`m4mah2',`ifelse(`$2',,(dimen_/8),`(($2)/2)')')dnl
 setdir_(ifelse(`$3',,`ifdef(`m4a_',rp_ang*rtod_,0)',`$3'))
 m4fshade(0, line from vec_( 0, m4mah2) \
                    to vec_( m4mawi2, m4mah2) \
               then to vec_( m4mawi2,-m4mah2) \
               then to vec_( m4mawi2/2,-m4mah2) \
               then to vec_( m4mawi2/2,0) \
               then to vec_(-m4mawi2/2,0) \
               then to vec_(-m4mawi2/2,-m4mah2) \
               then to vec_(-m4mawi2,-m4mah2) \
               then to vec_(-m4mawi2, m4mah2) \
               then to vec_( 0, m4mah2))
 `$4'; resetdir_ ]')

                                `battery( linespec, n, R )
                                 Arg 3: reversed polarity'
define(`battery',`ifelse(`$3',R,
 `reversed(`battery',`$1',`$2',,shift(shift(shift($@))))',
 `eleminit_(`$1')
  define(`m4n',`ifelse(`$2',,1,(`$2'))')define(`m4cs',`dimen_/12')dnl
  define(`m4wd',`m4cs*(m4n*2-1)')define(`m4ht',`dimen_/2')dnl
  { line to rvec_(rp_len/2-m4wd/2,0)
    for m4i = 0 to 2*(m4n-1) by 2 do {
      { line from rvec_(m4i*m4cs,m4ht/4) \
        to rvec_(m4i*m4cs,-m4ht/4) }
      { line from rvec_((m4i+1)*m4cs,m4ht/2) \
        to rvec_((m4i+1)*m4cs,-m4ht/2) } }
    line from rvec_(m4wd,0) \
          to rvec_(rp_len/2+m4wd/2,0) }
  {[box invis ht_ m4ht wid_ m4wd] at rvec_(rp_len/2,0)}
  line to rvec_(rp_len,0) invis ')')

                                `ebox(linespec, length, ht, greyvalue,
                                   box attributes)
                                 Length and ht (of the element) are relative to
                                 the direction of linespec'
                                Alternative:
                                `ebox(linespec, keys)
                                 keys:
                                   lgth=expr; wdth=expr;
                                   text="centered text";
                                   box=box attributes; e.g. shaded "green"
                                   body=box attributes; as above'
define(`ebox',`eleminit_(`$1')
 {ifinstr(`$2',=,
   `pushkeys_(`$2',`lgth:dimen_/2; wdth:dimen_/5; text::N; box::N; body::N')
    line to rvec_(max(0,rp_len/2-m4lgth/2),0); M4ebC: rvec_(m4lgth/2,0)
    lbox(m4lgth,m4wdth,m4box m4body)
    ifelse(m4text,,,`{m4text at M4ebC};')',
   `pushdef(`m4lgth',`ifelse(`$2',,dimen_/2,`$2')')dnl
    pushdef(`m4wdth',`ifelse(`$3',,dimen_/5,`$3')')dnl
    line to rvec_(max(0,rp_len/2-m4lgth/2),0)
    ifelse(`$4',,`lbox(m4lgth,m4wdth,`$5')',
                 `m4fshade(`$4',lbox(m4lgth,m4wdth,`$5'))')')
  line to rvec_(max(0,rp_len/2-m4lgth/2),0)}
 {[ box invis ht_ m4wdth wid_ m4lgth ] at rvec_(rp_len/2,0)}
  popdef(`m4wdth',`m4lgth')dnl
  ifinstr(`$2',=,`popdef(`m4text',`m4box',`m4body')')dnl
  line to rvec_(rp_len,0) invis ')

                                `fuse( linespec, chars, wid, ht, attributes )
                                 chars dA|B|C|D|S|SB|HB|HC or dA (=D)'
define(`fuse',`eleminit_(`$1')
  pushdef(`m4fusetype',`ifelse(`$2',,A,`$2',D,dA,`$2')')dnl
  pushdef(`m4ht',ifelse(`$4',,`dimen_/5'ifinstr(`$2',H,*5/3),`($4)'))dnl
  pushdef(`m4d',ifinstr(`$2',H,`m4ht/5',0))dnl
  pushdef(`m4wd',ifelse(`$3',,`m4ht*2',`($3)'))dnl
  {line to rvec_(max(0,rp_len/2-m4wd/2),0)
  sc_draw(`m4fusetype',HB,
   `{move to rvec_(m4d,0); lbox(m4wd-2*m4d,m4ht-2*m4d)}
    {lbox(m4wd,m4ht,`$5')}
    line to rvec_(m4wd+max(0,rp_len/2-m4wd/2),0)')
  sc_draw(`m4fusetype',HC,
   `{move to rvec_(m4d,0); {lbox(m4wd-2*m4d,m4ht-2*m4d,`$5')}
    {line from rvec_((m4wd-2*m4d)/5,m4ht/2-m4d) \
            to rvec_((m4wd-2*m4d)/5,-m4ht/2+m4d)}
    line from rvec_((m4wd-2*m4d)*4/5,m4ht/2-m4d) \
            to rvec_((m4wd-2*m4d)*4/5,-m4ht/2+m4d) }
    {lbox(m4wd,m4ht)}
    move to rvec_(m4wd,0); line to rvec_(max(0,rp_len/2-m4wd/2),0)')
  sc_draw(`m4fusetype',A,
   `arc  cw to rvec_(m4ht,0) rad m4ht/2 with .c at rvec_(m4ht/2,0)dnl
    ifelse(m4a,d,`; {dot(at last arc.start,,1)}')
    arc ccw to rvec_(m4ht,0) rad m4ht/2 with .c at rvec_(m4ht/2,0)
    line to rvec_(max(0,rp_len/2-m4wd/2),0)dnl
    ifelse(m4a,d,`; dot(at last line.start,,1)')')
  sc_draw(`m4fusetype',SB,
   `{lbox(m4wd,m4ht,`$5')}
    {line to rvec_(m4wd+max(0,rp_len/2-m4wd/2),0)}
    {m4fshade(m4fill,lbox(m4wd/5,m4ht))}
    move to rvec_(m4wd,0); line to rvec_(max(0,rp_len/2-m4wd/2),0)')
  sc_draw(`m4fusetype',B,
   `{lbox(m4wd,m4ht,`$5')}
    line to rvec_(m4wd+max(0,rp_len/2-m4wd/2),0)')
  sc_draw(`m4fusetype',C,
   `{lbox(m4wd,m4ht,`$5')}
    {line from rvec_(m4wd/5,-m4ht/2) \
          to rvec_(m4wd/5,m4ht/2)}
    {line from rvec_(m4wd*4/5,-m4ht/2) \
          to rvec_(m4wd*4/5,m4ht/2)}
    move to rvec_(m4wd,0); line to rvec_(max(0,rp_len/2-m4wd/2),0)')
  sc_draw(`m4fusetype',S,
   `{lbox(m4wd,m4ht,`$5')}
    {m4fshade(m4fill,lbox(m4wd/5,m4ht))}
    move to rvec_(m4wd,0); line to rvec_(max(0,rp_len/2-m4wd/2),0)')
  }
  {[box invis ht_ m4ht wid_ m4wd] at rvec_(rp_len/2,0)}
   popdef(`m4wd',`m4d',`m4ht',`m4fusetype')dnl
   line to rvec_(rp_len,0) invis ')

                                `arrester( linespec,
                                   [chars][D[L|R]],
                                   body len[:arrowhead ht],
                                   body ht[:arrowhead wid],
                                   attributes )
                                 arg2 chars:
                                   G= spark gap (default)
                                   g= general (dots)
                                   E= gas discharge
                                   S= box enclosure
                                   C= carbon block
                                   A= electrolytic cell
                                   H= horn gap
                                   P= protective gap
                                   s= sphere gap
                                   F= film element
                                   M= multigap
                                 modifiers:
                                   R= right orientation
                                   L= left orientation
                                   D= 3-terminal element for S, E only with
                                      terminals A, B, G'
define(`arrester',
 `define(`m4rdna',`patsubst(`$2',D\|L\|R)')dnl
  ifelse(m4rdna,,`define(`m4rdna',G)')dnl
  define(`m4rL',ifinstr(`$2',L,-))dnl
  define(`m4rR',ifinstr(`$2',R,-))dnl
  define(`m4aht',`(m4Rightstr(`$3',arrowht*2/3))')dnl
  define(`m4awd',`(m4Rightstr(`$4',
    ifelse(m4rdna,g,dotrad_*2,m4rdna,M,dotrad_*2,arrowwid*4/3)))')dnl
  define(`m4wd',`(ifinstr(        dnl body length
    m4rdna,C,`m4Leftstr(`$3',dimen_/3)',
    m4rdna,F,`m4Leftstr(`$3',dimen_/3)',
    m4rdna,s,`m4Leftstr(`$3',dimen_/4)',
    m4rdna,E,`m4Leftstr(`$3',dimen_*5/8)',
    `m4Leftstr(`$3',dimen_/2)'))')dnl
  define(`m4ht',`(ifinstr(        dnl body height
    Loopover_(`Z',`ifinstr(m4rdna,Z,T)',C,A,s),T,`m4Leftstr(`$4',dimen_/4)',
    m4rdna,F,`m4Leftstr(`$4',dimen_/3)',
    `m4Leftstr(`$4',dimen_/5)'))')dnl
  ifinstr(`$2',D,
   `[ define(`m4LL',m4rL)dnl
      ifinstr(m4rdna,S,
       `R: arrester(ifelse(`$1',,`to rvec_(m4wd*2,0)',`$1'),m4rdna,
          shift(shift($@)))
        Gb: line from R.c+vec_(0,m4LL m4ht/2) to R.c+vec_(0,m4LL (-m4ht*3/2))
        A: R.start; B: R.end; C: R.c; G: Here ',
      m4rdna,E,
       `R: arrester(ifelse(`$1',,`to rvec_(m4wd*8/5,0)',`$1'),m4rdna,
          shift(shift($@)))
        Gb: line from R.c+vec_(0,m4LL m4wd/8) to R.c+vec_(0,m4LL (-m4wd*3/4))
        A: R.start; B: R.end; C: R.c; G: Here ',
      `M4ErrorMsg(`D argument of Arrester() applies to types S, E only!') ')
      `$6' ]',
   `eleminit_(`$1',elen_)           dnl 2-terminal elements:
    {line to rvec_(max(0,rp_len/2-m4wd/2),0)
    {[ Orig: Here
    ifinstr(m4rdna,G,`
      {sarrow(to rvec_(m4aht,0),\
        wdth=m4awd;lgth=m4aht;head=shaded "black" `$5';)}
      move to rvec_(m4wd,0)
      sarrow(to rvec_(-m4aht,0),\
        wdth=m4awd;lgth=m4aht;head=shaded "black" `$5';)',
    m4rdna,g,
     `{dot(at rvec_(m4awd/2,0),rad=m4awd/2;circle=fill_(0) `$5')}
      dot(at rvec_(m4wd-m4awd/2,0),rad=m4awd/2;circle=fill_(0) `$5')',
    m4rdna,M,
     `{dot(at rvec_(m4awd/2,0),rad=m4awd/2;circle=fill_(0) `$5')}
      {dot(at rvec_(m4wd/2,0),rad=m4awd/2;circle=fill_(0) `$5')}
      dot(at rvec_(m4wd-m4awd/2,0),rad=m4awd/2;circle=fill_(0) `$5')',
    m4rdna,C,
     `lbox(m4wd/3,m4ht,`$5'); move to rvec_(m4wd/3,0)
      lbox(m4wd/3,m4ht,`$5')',
    m4rdna,A,
     `{line to rvec_(m4wd/4,0)}
      for_(1,3,1,`line from rvec_(0,m4ht/2) to rvec_(m4wd/4,0) \
        then to rvec_(0,-m4ht/2); move to rvec_(m4wd/4,m4ht/2)
        ifelse(m4x,3,,move to rvec_(m4wd/8,0))') ',
    m4rdna,H,
     `line to rvec_(m4ht,0); round
      {arc ifelse(m4rR,-,,c)cw from Here to rvec_(-m4ht,m4rR m4ht) \
        with .c at rvec_(-m4ht,0)}
      move to rvec_(m4wd-2*m4ht,0); round
      {arc ifelse(m4rR,-,c)cw from Here to rvec_(m4ht,m4rR m4ht) \
        with .c at rvec_(m4ht,0)}
      line to rvec_(m4ht,0)',
    m4rdna,P,`
      {sarrow(to rvec_(m4aht,0),wdth=m4awd;lgth=m4aht; `$5';)}
      move to rvec_(m4wd,0)
      sarrow(to rvec_(-m4aht,0),wdth=m4awd;lgth=m4aht; `$5';)',
    m4rdna,s,
     `{line to rvec_(m4ht/2*(sqrt(2)-1),0)}
      {arc from rvec_(0,-m4ht/2) to rvec_(0,m4ht/2) \
        with .c at rvec_(-m4ht/2,0)}
      move to rvec_(m4wd,0)
      {arc from rvec_(0,m4ht/2) to rvec_(0,-m4ht/2) \
        with .c at rvec_(m4ht/2,0)}
      {line to rvec_(-m4ht/2*(sqrt(2)-1),0)}',
    m4rdna,F,
     `{line from rvec_(0,m4ht/2) to rvec_(0,-m4ht/2)}
      {line from rvec_(m4wd/2,m4ht/2) to rvec_(m4wd/2,-m4ht/2)}
      line from rvec_(m4wd,m4ht/2) to rvec_(m4wd,-m4ht/2)',
    m4rdna,S,
      `{lbox(m4wd,m4ht,`$5')}
       sarrow(to rvec_(m4wd/2,0),\
        wdth=m4awd;lgth=m4aht;head=shaded "black";) ',
    m4rdna,E,
     `{circle diam m4wd at rvec_(m4wd/2,0) `$5'}
      {sarrow(to rvec_(m4wd*3/8,0),\
        wdth=m4awd;lgth=m4aht;head=fill_(0);)}
      {sarrow(from rvec_(m4wd,0) to rvec_(m4wd*5/8,0),\
        wdth=m4awd;lgth=m4aht;head=fill_(0);)}
      dot(at rvec_(m4wd*6/8,m4wd/4),dotrad_*2/3) ')
      ] with .Orig at Here }
    line from rvec_(m4wd,0) to rvec_(max(0,rp_len/2+m4wd/2),0) }
    line invis to rvec_(rp_len,0)') ')

                                `memristor( linespec, wid, ht, attributes )'
define(`memristor',`eleminit_(`$1')
  define(`m4ht',ifelse(`$3',,`dimen_/5',`($3)'))define(`m4htx',`m4ht/4')dnl
  define(`m4wd',ifelse(`$2',,`dimen_/2',`($2)'))define(`m4wdx',`m4wd*4/25')dnl
  { line to rvec_(max(0,rp_len/2-m4wd/2),0)
    {[lbox(m4wd,m4ht,`$4')] at rvec_(m4wd/2,0)}
    line to rvec_(m4wdx,0) \
       then to rvec_(m4wdx,m4htx) \
       then to rvec_(m4wdx*2,m4htx) \
       then to rvec_(m4wdx*2,-m4htx) \
       then to rvec_(m4wdx*3,-m4htx) \
       then to rvec_(m4wdx*3,m4htx) \
       then to rvec_(m4wdx*4,m4htx) \
       then to rvec_(m4wdx*4,0) \
       then to rvec_(m4wdx*5,0)
    m4fshade(m4fill,lbox(m4wd/4,m4ht))
    line to rvec_(max(0,rp_len/2-m4wd/2),0) }
  line invis to rvec_(rp_len,0)')

                            `pvcell( linespec, wid, ht, attributes )'
define(`pvcell',`eleminit_(`$1')
  define(`m4wd',ifelse(`$2',,`dimen_/2',`($2)'))dnl 
  define(`m4ht',ifelse(`$3',,`dimen_/5',`($3)'))dnl
  { line to rvec_(max(0,rp_len/2-m4wd/2),0)
    {[lbox(m4wd,m4ht,`$4')] at rvec_(m4wd/2,0)}
    {line from rvec_(0,-m4ht/2) to rvec_(m4wd/3,0) then to rvec_(0,m4ht/2)}
    move to rvec_(m4wd,0); line to rvec_(max(0,rp_len/2-m4wd/2),0) }
  line invis to rvec_(rp_len,0)')

                                `heater( linespec, nparts|keys, wid, ht,
                                  boxspec|[E[R][T]] )
                                 If arg5 contains E, draws an
                                 heatere(linespec,keys,[R][T]) otherwise a
                                 heatert(linespec,nparts,wid,ht,boxspec)'
define(`heater',`ifinstr(`$5',E,
 `heatere(`$1',`$2',`$5')',
 `heatert($@)')')

                                `heatere( linespec, keys, [R|T] )
                                 R: right orientation
                                 T: truncates leads to the width of the body
                                 keys: (for body)
                                   lgth=expr;
                                   wdth=expr; (default lgth*2/5)
                                   cycles=expr;
                                   line=attributes'
define(`heatere',
`pushkeys_(`$2',`lgth:dimen_/2; wdth:m4`'lgth*2/5; cycles:3; line::N;')dnl
 ifinstr(`$3',R,`pushdef(`m4ng',-)pushdef(`m4cw')pushdef(`m4ccw',cw)',
                `pushdef(`m4ng')  pushdef(`m4cw',cw)pushdef(`m4ccw')')dnl
 eleminit_(ifinstr(`$3',T,m4wdth,`$1'))
 { line to rvec_(rp_len/2-m4wdth/2,0); round
 {[S: Here; r = m4lgth/(4*m4cycles+1)
   arc m4cw m4line to rvec_(r,m4ng`'r) with .c at rvec_(r,0)
   for i=1 to m4cycles do { arc m4ccw m4line to rvec_(0,m4ng`'2*r) \
     with .c at rvec_(0,m4ng`'r)
     arc m4cw m4line to rvec_(0,m4ng`'2*r) with .c at rvec_(0,m4ng`'r) }
   line m4line to rvec_(m4wdth-2*r,0)
   for i=1 to m4cycles do {arc m4cw m4line to rvec_(0,m4ng`'(-2*r)) \
     with .c at rvec_(0,m4ng`'(-r))
     arc m4ccw m4line to rvec_(0,m4ng`'(-2*r)) with .c at rvec_(0,m4ng`'(-r)) }
   arc m4cw m4line to rvec_(r,m4ng`'(-r)) with .c at rvec_(0,m4ng`'(-r)); round
   ] with .S at Here }
 line from rvec_(m4wdth,0) to rvec_(rp_len/2+m4wdth/2,0) }
 line invis to rvec_(rp_len,0)dnl
 popdef(`m4lgth',`m4wdth',`m4cycles',`m4line',`m4ng',`m4cw',`m4ccw') ')

                                `heatert(linespec, nparts|keys, wid,ht,boxspec)
                                 keys: parts=expr;
                                       lgth=expr;
                                       wdth=expr;
                                       box=attributes;
                                 args 3-5 unused if any key is given
                                 arg5= body attributes'
define(`heatert',`eleminit_(`$1')
  ifelse(regexp(`$2',`parts=\|lgth=\|wdth=\|box='),-1, dnl not very elegant
   `pushdef(`m4parts',ifelse(`$2',,4,`$2'))dnl
    pushdef(`m4lgth',ifelse(`$3',,`dimen_/2',`($3)'))dnl
    pushdef(`m4wdth',ifelse(`$4',,`dimen_/5',`($4)'))dnl
    pushdef(`m4box',`$5')',
   `pushkeys_(`$2',`parts:4; lgth:dimen_/2; wdth:dimen_/5; box::N')')dnl
  { line to rvec_(max(0,rp_len/2-m4lgth/2),0)
    {[lbox(m4lgth,m4wdth,m4box)] at rvec_(m4lgth/2,0)}
    for m4ix=1 to m4parts-1 do {
      {line from rvec_(m4ix*m4lgth/(m4parts),m4wdth/2) \
          to rvec_(m4ix*m4lgth/(m4parts),-m4wdth/2) m4box}}
    line from rvec_(m4lgth,0) \
          to rvec_(max(0,rp_len/2+m4lgth/2),0) }
  line invis to rvec_(rp_len,0) popdef(`m4parts',`m4lgth',`m4wdth',`m4box')')

                                `lamp(linespec,[R][T],attributes)'
define(`lamp',`pushdef(`m4ng',`ifinstr(`$2',R,-)')pushdef(`m4hw',`dimen_/10')dnl
pushdef(`m4dp',(m4ng`'m4hw/2))pushdef(`m4ht',(m4ng`'dimen_/8))dnl
eleminit_(ifinstr(`$2',T,m4hw*2,`$1'))
 { [ circle rad dimen_/5 `$3' ] at rvec_(rp_len/2,m4ng`'dimen_/3.2) }
 { line to rvec_(rp_len/2-m4hw,0) \
     then to rvec_(rp_len/2-m4hw,m4ng`'dimen_/3.2)
   spline ifdpic(ctension_) to rvec_(0,m4ht) \
      then to rvec_(1.3*m4hw, m4ht) \
      then to rvec_(1.3*m4hw,-m4dp) \
      then to rvec_(0.7*m4hw,-m4dp) \
      then to rvec_(0.7*m4hw, m4ht) \
      then to rvec_(2*m4hw,m4ht) \
      then to rvec_(2*m4hw,0)
   line to rvec_(0,-(m4ng`'dimen_/3.2)) \
      then to rvec_(rp_len/2-m4hw,-(m4ng`'dimen_/3.2)) }
   line invis to rvec_(rp_len,0) popdef(`m4ng',`m4hw',`m4dp',`m4ht') ')

                                `thermocouple(linespec, wid, ht, L|R [T])
                                 T=truncated leads; 
                                 R=right orientation'
define(`thermocouple',`pushdef(`m4wd',ifelse(`$2',,`dimen_/5',`($2)'))dnl
   eleminit_(ifinstr(`$4',T,m4wd,`$1'))
   pushdef(`m4ht',ifelse(`$3',,`dimen_/2',`($3)'))dnl
   pushdef(`m4ths',`ifinstr(`$4',R,-)')dnl
   {line to rvec_(max(0,rp_len/2-m4wd/2),0) \
    then to rvec_(max(0,rp_len/2-m4wd/2),m4ths`'(m4ht-m4wd/2)) \
    then to rvec_(rp_len/2,m4ths`'m4ht) \
    then to rvec_(max(0,rp_len/2-m4wd/2)+m4wd,m4ths`'(m4ht-m4wd/2)) \
    then to rvec_(max(0,rp_len/2-m4wd/2)+m4wd,0) \
    then to rvec_(rp_len,0)}
  { dot(at rvec_(rp_len/2,m4ths`'m4ht)) }
  {[box invis ht_ m4ht wid_ m4wd] at rvec_(rp_len/2,m4ths`'m4ht/2)}
   line to rvec_(rp_len,0) invis popdef(`m4wd',`m4ht',`m4ths')')

                                `cbreaker( linespec, L|R, D|Th|TS, body name )
                                 circuit breaker to left or right of linespec,
                                 D=with dots; Th=thermal; TS=squared thermal
                                 Default body bounding box name is Br'
define(`cbreaker',`ifinstr(`$3',T,
   `tbreaker($@)',
   `mbreaker($@)')')

define(`tbreaker',`eleminit_(`$1') define(`m4ho',0)
 {ifinstr(`$3',TS,
  `define(`m4h',`dimen_/5')define(`m4v',`m4h/2')define(`m4ho',`m4v/2')dnl
   m4j = max(0,rp_len/2-m4h/2)
   line to rvec_(m4j,0) \
    then to rvec_(m4j,ifelse(`$2',R,-)m4h/2) \
    then to rvec_(m4j+m4h,ifelse(`$2',R,-)m4h/2) \
    then to rvec_(m4j+m4h,0) \
    then to rvec_(m4j*2+m4h,0) ',
  `define(`m4h',`dimen_*2/5')define(`m4v',`m4h/2')define(`m4ho',0)dnl
   m4j = max(0,rp_len/2-m4h/2)
   line to rvec_(m4j,0)
   {round
    arc cw to rvec_( m4h/4,0)+vec_(Rect_(m4h/4,-75)) with .c at rvec_( m4h/4,0)}
   move to rvec_(m4h,0)
   {round
    arc cw to rvec_(-m4h/4,0)+vec_(Rect_(m4h/4,105)) with .c at rvec_(-m4h/4,0)}
   line to rvec_(m4j,0)
 ') }
 {ifelse(`$4',,Br,`$4'):[box invis ht_ m4v wid_ m4h ] at rvec_(rp_len/2,ifelse(`$2',R,-)m4ho) }
  line to rvec_(rp_len,0) invis ')

define(`mbreaker',`eleminit_(`$1') define(`m4R',`ifelse(`$2',R,-)')
  define(`m4h',`dimen_/3') define(`m4cr',`((m4h+2*dimen_/32)*5/8)')dnl
  define(`m4ht',`(m4cr-sqrt(m4cr^2-(m4h/2+dimen_/32)^2)+dimen_/16)')dnl
  {line to rvec_(max(0,rp_len/2-m4h/2),0)
  {ifelse(`$3',D,`dot(,,1)
   move to rvec_(0,m4R`'dotrad_);')dnl
   arc ifelse(`$2',R,c)cw from rvec_(-dimen_/32,m4R`'dimen_/16) \
     to rvec_(m4h+dimen_/32,m4R`'dimen_/16) rad m4cr \
     with .c at rvec_(m4h/2,m4R`'(m4ht-m4cr))}
  {line from rvec_(m4h,0) \
          to rvec_(m4h+max(0,rp_len/2-m4h/2),0)
   ifelse(`$3',D,`dot(at last line.start,,1)') }
  ifelse(`$4',,Br,`$4'): [box invis ht_ m4ht ifelse(`$3',D,`+2*dotrad_') \
    wid_ m4h+dimen_/16] at rvec_(m4h/2,m4R`'(m4ht/2)) }
  line to rvec_(rp_len,0) invis ')

                            `jumper(linespec,chars|keys)
                             Two-terminal solder jumper with named body parts.
                             chars: character sequence normally beginning
                              with C and ending with D specifying the jumper
                              components and their attribs: C is first, D last,
                              E is empty (blank) gap, J is filled gap, B is
                              box component.
                              The components are named T1, T2, ... 
                              e.g. CED is a simple open jumper (default);
                              CJD closed; CEBED three-contact open;
                              CJBED three-contact open and closed.
                             keys:
                                   type=chars as above;
                                   body=attributes; (e.g. fill_(0.5))
                                   wdth=expr;
                                   name=chars; body name'
define(`jumper',`eleminit_(`$1')
 pushkeys_(`$2',`type:m4typ:N; body:fill_(0):N; wdth:dimen_/5; name::N;')dnl
 ifelse(m4type,m4typ,
  `poppushdef(`m4type',`ifelse(`$2',,CED,`ifinstr(`$2',=,CED,`$2')')')')dnl
 pushdef(`m4r',m4wdth/2) pushdef(`m4lgth',`m4r*len(m4type)')dnl
 { line to rvec_(rp_len/2-m4lgth/2,0)
   { line from rvec_(m4lgth,0) to rvec_(rp_len/2+m4lgth/2,0) }
   {ifelse(m4name,,,m4name:) [ S: Here
      for_(1,len(m4type),1,`define(`m4ch',`substr(m4type,decr(m4x),1)')dnl
        T`'m4x: ifelse(m4ch,C, 
         `[ arc to rvec_(0,-m4wdth) with .c at rvec_(0,-m4r) m4body
            round(,,m4body); L: line to rvec_(0,m4wdth) m4body; round(,,m4body)
            ] with .L.c at rvec_(m4r,0); move to last [].L.c ',
        m4ch,J,`rotbox(m4r,m4r,m4body)',
        m4ch,B,`rotbox(m4r,m4wdth,m4body)',
        m4ch,E,`move to rvec_(m4r,0)',
        m4ch,D,`[ arc to rvec_(0,m4wdth) with .c at rvec_(0,m4r) m4body
         round(,,m4body); L: line to rvec_(0,-m4wdth) m4body; round(,,m4body)
         ] with .L.c at Here; move to T`'m4x.L.c+vec_(m4r,0)')')
      ] with .S at Here } }
 line invis to rvec_(rp_len,0) undefine(`m4ch') dnl
 popdef(`m4type',`m4body',`m4wdth',`m4name',`m4r',`m4lgth') ')

                                `gap( linespec,fill,A )
                                 Gap with filled dots e.g.
                                 gap(down_ linewid/2,1); rlabel(+,v_1,-)
                                 A: chopped arrow between dots'
define(`gap',`eleminit_(`$1')
  dot(,,ifelse(`$2',,0,`$2')); dot(at last line.end,,ifelse(`$2',,0,`$2'))
  ifelse(`$3',A,
   `{arrow from last line.start to last line.end chop dotrad_*3}')
  {[box invis ht_ 0 wid_ min(rp_len,(dimen_*4/9+rp_len)/3)] at last line.c}
  ')

                                `arrowline( linespec )
                                 line with midpoint arrowhead
                                 e.g. arrowline(up 1 dotted); llabel(,I_2)'
define(`arrowline',`line ifelse(`$1',,`to rvec_(elen_,0)',`$1')
  { eleminit_(from last line.start to last line.end) }
  { arrow from last line.start to last line.end \
      chop lin_leng(last line)/2-arrowht/2
   [box invis ht_ arrowwid wid_ arrowht] at last line.c }')

                          `ground( at position, T|stem length, N|F|S|L|P[A]|E,
                                     D|U|L|R|degrees)
                                 T=truncated stem; N=normal ground,
                                 F=frame, S=signal, L=low-noise, P=protective,
                                 E=European; PA=protective alternate
                                 Down (default), Up, Left, Right, angle (deg)'
define(`ground',`box invis ht 0 wid 0 with .c ifelse(`$1',,`at Here',`$1')
  define(`m4v',`dimen_/6')define(`m4h',`dimen_/16')dnl
  {setdir_(ifelse(`$4',,-90,`$4'))
  ifelse(`$2',,`line from last box.c to rvec_(dimen_/4,0)',
    `$2',T,,`line from last box.c to rvec_(`$2',0)')
  ifelse(`$3',F,
    `{line from rvec_(dimen_/8,m4v-dimen_/12) \
          to rvec_(0,m4v) \
       then to rvec_(0,-m4v) \
       then to rvec_(dimen_/8,-m4v-dimen_/12)}
     line to rvec_(dimen_/8,-dimen_/12)',
  `$3',S,
    `{line to rvec_(0,m4v) \
       then to rvec_(m4v*1.5,0) \
       then to rvec_(0,-m4v) \
       then to Here }',
  `$3',Q,
    `{shade(0,line to rvec_(0,m4v) \
       then to rvec_(m4v*1.5,0) \
       then to rvec_(0,-m4v) \
       then to Here) }',
  `$3',L,
    `{move to rvec_(m4h,0)
      arc cw rad m4v*3/2 from rvec_(Rect_(m4v*3/2,-60)) \
        to rvec_(Rect_(m4v*3/2,60)) with .c at Here}
     ground(,T,,`$4')',
  `$3',PA,
    `{Grnd_T: line to rvec_(0,m4v*1.6) \
       then to rvec_(5.5*m4h,0) \
       then to rvec_(0,-m4v*1.6) \
       then to Here}
     ground(at rvec_(m4h,0),T,,`$4')',
  `$3',P,
    `{Grnd_C: circle rad m4v*3/2 at rvec_(m4h,0)}
     ground(,T,,`$4')',
  `$3',E,
    `{line from rvec_(0,m4v*2/3) \
          to rvec_(0,-m4v*2/3) thick linethick*2}',
  `{line from rvec_(0,m4v) \
          to rvec_(0,-m4v)}
   {line from rvec_(m4h,dimen_/9) \
          to rvec_(m4h,-dimen_/9)}
   line from rvec_(2*m4h,dimen_/14) \
          to rvec_(2*m4h,-dimen_/14)')
   resetdir_} ')

                        `antenna(at, position, T|stem length, A|D|F|L|P|S|T,
                                   U|D|L|R|degrees)
                                 arg2=T: truncate stem
                                 arg3=A aerial, D dipole, F fork, L loop,
                                      P phased, S diamond, T triangle
                                 arg4=drawing direction '
define(`antenna',`[ T: Here
  define(`m4v',`dimen_/2')define(`m4h',`dimen_/12')dnl
  define(`m4atype',ifelse(`$3',,A,`$3'))dnl
  setdir_(ifelse(`$4',,90,`$4'))
  ifelse(
  m4atype,A,
   `ifelse(`$2',,`move to rvec_(m4h*2,0)', `$2',T,, `move to rvec_(`$2',0)')
    { line from rvec_(m4v*3/4, m4v*sqrt(3)/4) to Here \
        then to rvec_(m4v*3/4,-m4v*sqrt(3)/4) }
    line from rvec_(m4v*3/4,0) \
        to T',
  m4atype,D,
   `T1: rvec_(0,m4h); T2: rvec_(0,-m4h)
    ifelse(`$2',,`move to rvec_(m4v,0)', `$2',T,, `move to rvec_(`$2',0)')
    { line from T1 to rvec_(0,m4h) \
       then to rvec_(0,m4h*3) }
    { line from T2 to rvec_(0,-m4h) \
       then to rvec_(0,-m4h*3) }',
  m4atype,F,
   `ifelse(`$2',,`move to rvec_(m4h*2,0)', `$2',T,, `move to rvec_(`$2',0)')
    { line from rvec_(m4v*3/4,m4v*sqrt(3)/4) \
          to rvec_(0,m4v*sqrt(3)/4) \
        then to rvec_(0,-m4v*sqrt(3)/4) \
        then to rvec_(m4v*3/4,-m4v*sqrt(3)/4)}
    line from rvec_(m4v*3/4,0) \
        to T',
  m4atype,L,
   `T1: rvec_(0,m4h); T2: rvec_(0,-m4h)
    ifelse(`$2',,`move to rvec_(m4h*2,0)', `$2',T,, `move to rvec_(`$2',0)')
    line from T1 to rvec_(0,m4h) \
       then to rvec_(0,m4v/2) \
       then to rvec_(m4v-m4h,m4v/2) \
       then to rvec_(m4v-m4h,-m4v/2+m4h) \
       then to rvec_(m4h,-m4v/2+m4h) \
       then to rvec_(m4h,m4v/2-m4h) \
       then to rvec_(m4v,m4v/2-m4h) \
       then to rvec_(m4v,-m4v/2) \
       then to rvec_(0,-m4v/2) \
       then to rvec_(0,-m4h) \
       then to T2',
  m4atype,P,
   `ifelse(`$2',,`move to rvec_(m4h*2/3,0)', `$2',T,, `move to rvec_(`$2',0)')
    line from T to Here
    { line from rvec_(0,-m4v/3) \
          to rvec_(0,m4v/3) }
    { line from rvec_(m4h,-m4v*2/3) \
          to rvec_(m4h,m4v*2/3) }',
  m4atype,S,
   `T1: rvec_(0,m4h); T2: rvec_(0,-m4h)
    ifelse(`$2',,`move to rvec_(m4h*2,0)', `$2',T,, `move to rvec_(`$2',0)')
    line from T1 to rvec_(0,m4h) \
       then to rvec_(m4v*3/4-m4h,m4v*3/4) \
       then to rvec_(2*m4v*3/4-m4h,0) \
       then to rvec_(m4v*3/4-m4h,-m4v*3/4) \
       then to rvec_(0,-m4h) \
       then to T2',
  m4atype,T,
   `ifelse(`$2',,`move to rvec_(m4h*2,0)', `$2',T,, `move to rvec_(`$2',0)')
    line to rvec_(m4v*3/4,m4v*sqrt(3)/4) \
      then to rvec_(m4v*3/4,-m4v*sqrt(3)/4) \
      then to Here
    line from rvec_(m4v*3/4,0) \
        to T')
   `$5'; resetdir_ ] with .T ifelse(`$1',,`at Here',`$1')
 move to last [].T')

                        `r_stub(at position, keys ) # microstrip radial stub
                         keys:
                           dir=U|D|L|R|degrees; (default U) drawing direction
                           irad=expr; inner radius
                           orad=expr; outer radius
                           angle=expr; (degrees) sector angle
                           outline=outline attributes; (but not thickness)
                           fill=internal shade color;
                           stem=T[I]|stem attributes; T means no stem,
                            TI means no stem and no inner arc '
define(`r_stub',`[ C: Here
 pushkeys_(`$2',`dir:U:N; orad:dimen_*2/3; irad:m4`'orad/4; angle:75;
                 outline::N; fill::N; stem::N;') setdir_(m4dir)
 Li: vec_(Rect_(m4irad,m4angle/2));  Lo: vec_(Rect_(m4orad,m4angle/2))
 Ro: vec_(Rect_(m4orad,-m4angle/2)); Ri: vec_(Rect_(m4irad,-m4angle/2))
  ifelse(m4fill,,,`arc from (Ri+Ro)/2 to (Li+Lo)/2 with .c at C \
    thick (m4orad-m4irad)/(1bp__) colored m4fill')
  ifinstr(m4stem,TI,`move to Li',
   `arc from Ri to Li with .c at C m4outline; round(,last arc.thick,m4outline)')
  line to Lo m4outline; round(,last line.thick,m4outline)
  arc cw to Ro with .c at C m4outline; round(,last arc.thick,m4outline)
  line to Ri m4outline; ifinstr(m4stem,TI,,`round(,last line.thick,m4outline)')
 ifinstr(m4stem,T,,`line from C to vec_(m4irad,0) patsubst(m4stem,TI+)')
 `$3' popdef(`m4stem',`m4fill',`m4outline',`m4angle',`m4irad',`m4orad',`m4dir')
 resetdir_ ] ifelse(`$1',,`with .C at Here',`$1') ')

                           `heatsink(at position, keys, U|D|L|R|degrees)
                             keys: lgth=expr; hght=expr; fin=attributes;
                                base=attributes; fincount=expr;
                          Arg3: drawing direction (default: R)'
define(`heatsink',`[ setdir_(`$3',R)
 pushkeys_(`$2',`lgth:dimen_*3/4; hght:m4`'lgth/3; fin::N;
   base::N; fincount:6;')dnl
 SW: (0,0); NW: vec_(0,m4hght); SE: vec_(m4lgth,0); NE: vec_(m4lgth,m4hght)
  B: line from SW to SE m4base
  T: line from SE+(NE-SE)/4 to SW+(NW-SW)/4 m4base
  for i=0 to m4fincount-1 do {
    move to (0.5+i)/m4fincount between T.end and T.start 
    line to Here+(NW-SW)*3/4 m4base m4fin }
 `$4'; resetdir_ popdef(`m4lgth',`m4hght',`m4fin',`m4base',`m4fincount')
 ] ifelse(`$1',,`at Here',`$1')')

                           `adjust(at position,keys)
                            Adjustment screw in a [] block
                            keys:
                             size=expr;
                             angle=degrees; slot angle
                             slotwid=expr; slot width
                             circle=attributes; shade, outline etc'
define(`adjust',`[ pushkeys_(`$2',
   `size:dimen_/4; angle:60; circle::N; slotwid:m4`'size/3')
  C: circle diam m4size at (0,0) m4circle
  ap = asin(m4slotwid/m4size)*rtod_
  line from (Rect_(m4size/2,m4angle-ap)) to (Rect_(m4size/2,m4angle-180+ap))
  line from (Rect_(m4size/2,m4angle+180-ap)) to (Rect_(m4size/2,m4angle+ap))
  popdef(`m4size',`m4angle',`m4circle',`m4slotwid')
  ] ifelse(`$1',,`at Here',`$1') ')

                                `switch( linespec,L|R,[O|C][D],L|B|D,attribs )
                                 Wrapper for bswitch, lswitch, dswitch
                                 R=right orientation (default L=left)
                                 if arg4=blank or L:
                                 arg3 = [O|C][D][K][A]
                                   D = circle at contact and hinge (dD = hinge
                                       only, uD = contact only)
                                   K=closed switch;
                                   A=arrowhead on switch blade;
                                   O=opening arrow; C=closing arrow
                                 if arg4=B (button switch): arg3 = O|C
                                   O=normally open; C=normally closed;
                                 if arg4=D: arg3 = same as for dswitch and
                                 arg5 is arg4 of dswitch GC or GX'
define(`switch',`ifelse(
 `$4',, `lswitch(`$1',`$2',`$3')',
 `$4',L,`lswitch(`$1',`$2',`$3')',
 `$4',B,`bswitch(`$1',`$2',`$3')',
 `$4',D,`define(`m4qna_',`$3')dnl
  define(`m4rna_',W`'ifinstr(`$2',C,dBK,B)`'m4qna_)dnl
  dswitch(`$1',`$2',m4rna_,`$5')')')

                                `bswitch( linespec,L|R,chars ) pushbutton switch
                                 R=right orientation (default L=left)
                                 chars: O= normally open, C=normally closed'
define(`bswitch',`eleminit_(`$1') dnl
 define(`m4h',`dimen_/3') define(`m4cs',`0.069186*dimen_')dnl (2.5pt)
 define(`m4v',`ifelse(`$2',R,-m4cs,m4cs)')define(`dna_',`$3') dnl
 {line to rvec_(rp_len/2-m4h/2,0) chop 0 chop m4cs}
 { Bsw_T1: circle rad m4cs at rvec_(rp_len/2-m4h/2,0); move to last circle
   { Bsw_T2: circle rad m4cs at rvec_(m4h,0) }; ifelse(`$4',,,`{`$4'}')
   sc_draw(`dna_',C,dnl
    `{ line from rvec_(-m4cs,-(m4v)) \
          to rvec_(m4h+m4cs,-(m4v)) }
     { line from rvec_(m4h/2,-(m4v)) \
          to rvec_(m4h/2,m4v*3) }
     {[box invis ht_ 4*m4cs wid_ m4h+2*m4cs] at rvec_(m4h/2,m4v)}',
    `{ line from rvec_(-m4cs,m4v*2.5) \
          to rvec_(m4h+m4cs,m4v*2.5) }
     { line from rvec_(m4h/2,m4v*2.5) \
          to rvec_(m4h/2,m4v*4.5) }
     {[box invis ht_ 5.5*m4cs wid_ m4h+2*m4cs] at rvec_(m4h/2,m4v*1.75)}')
   line from rvec_(m4h,0) \
          to rvec_(m4h/2+rp_len/2,0) chop m4cs chop 0 }
 line to rvec_(rp_len,0) invis ')

                                `lswitch( linespec,L|R,chars ) knife switch
                                 R=right orientation (default L=left)
                                 chars=[O|C][[ud]D][K][A]
                                   D = circle at contact and hinge (dD = hinge
                                       only, uD = contact only)
                                   K=closed switch;
                                   A=arrowhead on switch blade;
                                   O=opening arrow; C=closing arrow'
define(`lswitch',`eleminit_(`$1') dnl
 define(`m4v',`dimen_/4')define(`m4cs',`dimen_/4*Sin(10)')dnl
 define(`dna_',`$3')define(`m4d',-1)define(`m4k',15)dnl
 m4t1 = arrowht; m4t2 = arrowwid;
 arrowht = dimen_/0.75*0.08; arrowwid = dimen_/0.75*0.053
 {line to rvec_(rp_len/2-dimen_/6,0)
  sc_draw(`dna_',K,`define(`m4k',25)dnl
    {{ifinstr(`$3',A,arrow m4c_l,line) \
     to LCtangent(Here,rvec_(dimen_/3,0),dotrad_,`$2') chop 0 chop -dotrad_}
     line from rvec_(dimen_/3,0) to rvec_(dimen_/3,ifelse(`$2',R,-)dotrad_)}',
   `{ifinstr(`$3',A,arrow m4c_l,line) \
      to rvec_(dimen_/4,ifelse(`$2',R,-)dimen_/4)}')
  sc_draw(`dna_',C,`{ arc <- m4c_l ifelse(`$2',R,,`c')cw \
      from rvec_(Rect_(dimen_/4,ifelse(`$2',R,,-)m4k))\
      to rvec_(Rect_(dimen_/4,ifelse(`$2',R,-)60)) \
      with .c at rvec_(Rect_(-dimen_/4,ifelse(`$2',R,-)(60-m4k)/2)) }')
  sc_draw(`dna_',O, `{ arc -> m4c_l ifelse(`$2',R,,`c')cw \
      from rvec_(Rect_(dimen_/4,ifelse(`$2',R,,-)10))\
      to rvec_(Rect_(dimen_/4,ifelse(`$2',R,-)75)) \
      with .c at rvec_(Rect_(-dimen_/4,ifelse(`$2',R,-)(75-10)/2)) }') }
 {{line from rvec_(rp_len/2+dimen_/6,0) \
          to rvec_(rp_len,0) }
  sc_draw(`dna_',D,
   `ifelse(m4a,u,,`dot(at rvec_(rp_len/2-dimen_/6,0),,1)')
    ifelse(m4a,d,,`dot(at last line.start,,1)')') }
 { [box invis ht_ dimen_/4+m4cs wid_ dimen_/3] \
     with .c at rvec_(rp_len/2,ifelse(`$2',R,-)(m4v-(m4cs))/2)}
 arrowht = m4t1 ; arrowwid = m4t2;  ifelse(`$4',,,`{`$4'}')
 line to rvec_(rp_len,0) invis ')

                                `dswitch(linespec, R, W[ud]B chars, attributes)
                                 Comprehensive IEEE-IEC single-pole switch:
                                 arg2=R: orient to the right of drawing dir
                                 arg4 is a key-value sequence for the body of
                                 GC and GX attributes in arg4:
                                   GC keys: diam, circle
                                   GX keys: lgth, wdth, box, text
                                 arg 3:
                                   blank means WB by default
                                   B=contact blade open
                                   Bc=contact blade closed
                                   Bm= mirror blade
                                   Bo=contact blade more widely open
                                   dB=contact blade to the right of direction
                                   C = external operating mechanism
                                   Cb = circuit breaker function (IEC S00219)
                                   Co = contactor function (IEC S00218)
                                   D = circle at contact and hinge (dD = hinge
                                       only, uD = contact only)
                                   DI = Disconnector; isolator (IEC S00288)
                                   E = emergency button
                                   EL = early close (or late open)
                                   LE = late close (or early open)
                                   F = fused
                                   GC = disk control mechanism, attribs:
                                    diam=expr; circle=circle attribs;
                                   GX = box control mechanism, attribs:
                                    lgth=expr;wdth=expr;box=box attr; text=char;
                                   H = time delay closing
                                   uH = time delay opening
                                   HH = time delay opening and closing
                                   K=vertical closing contact line
                                     use WdBK for a normally-closed switch
                                   L = limit
                                   M = maintained (latched)
                                   MM = momentary contact on make
                                   MR = momentary contact on release
                                   MMR = momentary contact on make and release
                                   O = hand operation button
                                   P = pushbutton
                                   Pr[T|M] = proximity [touch-sensitive or
                                       magnetically controlled]
                                   R = time-delay operating arm
                                   Sd = Switch-disconnector
                                   Th = thermal control linkage
                                   Tr = tripping
                                   W = baseline with gap
                                   Y = pull switch
                                   Z = turn switch'
define(`dswitch',`eleminit_(`$1')
define(`dna_',ifelse(`$3',,WB,`$3')`')dnl
define(`m4R',`ifelse(`$2',R,-)')define(`m4sc',`dimen_/24')dnl
 M4CC: last line.c
 sc_draw(`dna_',W,
  `{ line from M4CC+vec_( 4*m4sc,0) to last line.end }
   { line to   M4CC+vec_(-4*m4sc,0) }')
 {[ tr_xy_init(,m4sc,m4R)
  T: M4_xyO; B: T
  sc_draw(`dna_',Bm,
   `define(`m4c',ifelse(m4a,d,-))dnl
    B: line from tr_xy(-4,0) \
          to tr_xy(5.0,m4c`'4.5)
    line invis from B.start to B.end chop 0 chop -m4_xyU*5/4
    m4fshade(0,circle rad m4_xyU*5/4 at last line .end)')
  sc_draw(`dna_',Bo,
   `define(`m4c',ifelse(m4a,d,-))dnl
    B: line from tr_xy(-4,0) \
          to tr_xy(4,m4c`'13/sqrt(3))')
  sc_draw(`dna_',Bc,
   `B: line from tr_xy(-4,0) \
          to tr_xy( 4,0)')
  sc_draw(`dna_',B,
   `define(`m4c',ifelse(m4a,d,-))dnl
    B: line from tr_xy(-4,0) \
          to tr_xy(5.0,m4c`'4.5)')
  sc_draw(`dna_',Cb,
   `line from tr_xy(2,-2) to tr_xy(6, 2)
    line from tr_xy(2, 2) to tr_xy(6,-2)')
  sc_draw(`dna_',Co,`ifelse(m4R,-,
   `arc ifelse(m4c,-,,c)cw from tr_xy(4,0) \
          to tr_xy(8,0) with .c at tr_xy(6,0)',
   `arc ifelse(m4c,-,c)cw from tr_xy(4,0) \
          to tr_xy(8,0) with .c at tr_xy(6,0)') ')
  sc_draw(`dna_',GC,
   `pushkeys_(`$4',`diam:12*m4sc;circle::N;text::N')dnl
    line from B.c to B.c+ta_xy(0,4)
    GC: circle diam m4diam m4circle dnl
      ifelse(m4text,,,`m4lstring(m4text,"m4text")') \
      at Here+ta_xy(0,m4diam/2/(m4sc)) popdef(`m4diam',`m4circle',`m4text')')
  sc_draw(`dna_',GX,
   `pushkeys_(`$4',`lgth:10*m4sc;wdth:10*m4sc;box::N;text::N')dnl
    line from B.c to B.c+ta_xy(0,4)
    GX: rotbox(m4lgth,m4wdth,m4box) at Here+ta_xy(0,m4lgth/2/(m4sc))
    ifelse(m4text,,,`m4lstring(m4text,"m4text") at GX.C') dnl
    popdef(`m4lgth',`m4wdth',`m4box',`m4text')')
  sc_draw(`dna_',C,
   `T: B.c+ta_xy(0,ifelse(m4a,d,-)12)
    C: line dashed from B.c to T ')
  sc_draw(`dna_',DI,
   `DI: line from tr_xy(4,2) to tr_xy(4,-2)')
  sc_draw(`dna_',EL,
   `EL: line from 0.99 along_(B) to B.end \
      then to B.end + ta_xy(vperp(B,m4c`'2.5,R))')
  sc_draw(`dna_',LE,
   `LE: line from 0.99 along_(B) \
        to B.end \
      then to B.end + ta_xy(vperp(B,m4c`'2.5))')
  sc_draw(`dna_',K,
   `K: line from tr_xy(4,0) \
          to tr_xy(4,m4c`'5)')
  sc_draw(`dna_',F,
   `DT: 1/8 along_(B); DQ: 5/8 along_(B)
    F: line from DT to DT + ta_xy(neg_(m4c)1/2,1) \
      then to DQ + ta_xy(neg_(m4c)1/2,1) \
      then to DQ + ta_xy(m4c`'1/2,-1) \
      then to DT + ta_xy(m4c`'1/2,-1) \
      then to DT ')
  sc_draw(`dna_',L,
   `DT: Along_(B,8*m4sc-2.5*dotrad_) define(`m4e',ifelse(m4a,d,-))
     line from B.start \
      to DT + ta_xy(neg_(m4e)1,ifelse(m4c,m4e,,-)2) \
      then to Along_(B,8*m4sc-3/2*dotrad_)
#   DT: 11/16 along_(B) define(`m4e',ifelse(m4a,d,-))
#   line from 5/16 along_(B) \
#     to DT + ta_xy(neg_(m4e)1,ifelse(m4c,m4e,,-)2) \
#     then to DT
')
  sc_draw(`dna_',Sd,
   `dot(at tr_xy(4,0),m4_xyU*3/2,1)
    line from tr_xy(4,2)+vec_(m4_xyU*3/2,0) \
      to tr_xy(4,-2)+vec_(m4_xyU*3/2,0)')
  sc_draw(`dna_',Th,
   `define(`m4t',ifelse(m4a,d,-))dnl
    T: B.c+ta_xy(0,m4t`'12)
    line from B.c to B.c+ta_xy(0,m4t`'4.5) \
       then to B.c+ta_xy(3,m4t`'4.5) \
       then to B.c+ta_xy(3,m4t`'7.5) \
       then to B.c+ta_xy(0,m4t`'7.5) \
       then to T ')
  sc_draw(`dna_',Tr,
   `m4angtmp = rp_ang; point_(lin_ang(B))
    DT1: 0.4 along_(B); DT2: 0.65 along_(B)
    m4dTr = distance(DT1,DT2)
    move to DT1+vec_(0,m4c`'m4dTr/2)
    m4fshade(0,lbox(m4dTr,m4dTr))
    point_(m4angtmp) ')
  sc_draw(`dna_',PrM,
   `T: Proxim(dimen_/3) at B.c+ta_xy(0,ifelse(m4a,d,-)8)
    line dashed dimen_/16 from B.c to T chop 0 chop dimen_/6
    Magn(dimen_/3,dimen_/6) at T+vec_(0,ifelse(m4a,d,-)dimen_/4)')
  sc_draw(`dna_',MMR,
   `line from tr_xy(6,1.16) \
          to tr_xy(4,0) \
       then to tr_xy(6,-1.16)')
  sc_draw(`dna_',MM,
   `MM: line from tr_xy(5,0) \
          to tr_xy(4,0) \
       then to tr_xy(6,1.16)')
  sc_draw(`dna_',MR,
   `MR: line from tr_xy(5,0) \
          to tr_xy(4,0) \
       then to tr_xy(6,-1.16)')
  sc_draw(`dna_',M,
   `define(`m4t',ifelse(m4a,d,-))dnl
    T: B.c+ta_xy(0,m4t`'12)
    line dashed 1.5*m4sc from B.c to B.c+ta_xy(0,m4t`'4.5)
    line to B.c+ta_xy(-3,m4t`'6) \
       then to B.c+ta_xy(0,m4t`'7.5)
    line dashed 1.5*m4sc to T ')
  sc_draw(`dna_',O,
   `line from T + ta_xy(-2.5,0) \
        to T + ta_xy(2.5,0) ')
  sc_draw(`dna_',PrT,
   `T: Proxim(dimen_/3) at B.c+ta_xy(0,ifelse(m4a,d,-)8)
    line dashed dimen_/16 from B.c to T chop 0 chop dimen_/6
    line to rvec_(dimen_/4,0) with .c at T+vec_(0,ifelse(m4a,d,-)dimen_/6)')
  sc_draw(`dna_',Pr,
   `T: Proxim(dimen_/3) at B.c+ta_xy(0,ifelse(m4a,d,-)8)
    line dashed dimen_/16 from B.c to T chop 0 chop dimen_/6 ')
  sc_draw(`dna_',P,
   `line from T + ta_xy(-2.5,-2.5) \
           to T + ta_xy(-2.5,0) \
      then to T + ta_xy(2.5,0) \
      then to T + ta_xy(2.5,-2.5) ')
  sc_draw(`dna_',Y,
   `line from T + ta_xy(-2.5,2.5) \
           to T + ta_xy(-2.5,0) \
      then to T + ta_xy(2.5,0) \
      then to T + ta_xy(2.5,2.5) ')
  sc_draw(`dna_',Z,
   `line from T + ta_xy(-2.5,-2.5) \
           to T + ta_xy(-2.5,0) \
      then to T + ta_xy(2.5,0) \
      then to T + ta_xy(2.5,2.5) ')
  sc_draw(`dna_',R,
   `define(`m4t',ifelse(m4a,d,-))dnl
    DT: 5/12 along_(B); DQ: 7/12 along_(B)
    line from DT to DT + ta_xy(0,m4t`'12)
    line from DQ to DQ + ta_xy(0,m4t`'(neg_(m4c)sqrt(3)/2+12))
    T: 1/2 between Here and 2nd last line.end ')
  sc_draw(`dna_',HH,
   `arc ifelse(m4R,-,c)cw \
      from T+ta_xy(3,3/2) \
        to T+ta_xy(-3,3/2) with .c at T+ta_xy(0,4.0)
    arc ifelse(m4R,,c)cw \
      from T+ta_xy(3,-3/2) \
        to T+ta_xy(-3,-3/2) \
      with .c at T+ta_xy(0,-4.0) ')
  sc_draw(`dna_',H,
   `define(`m4t',ifelse(m4a,d,-))dnl
    arc ifelse(m4t,m4R,,c)cw \
      from T+ta_xy(3,m4t`'3/2) \
        to T+ta_xy(-3,m4t`'3/2) \
      with .c at T + ta_xy(0,m4t`'4.0) ')
  sc_draw(`dna_',E,
   `line from T + ta_xy(-2.5,0) \
        to T + ta_xy(2.5,0)
    arc ifelse(m4R,-,,c)cw to last line.start with .c at T + ta_xy(0,-1.5) ')
  sc_draw(`dna_',D,
   `ifelse(m4a,u,,`dot(at tr_xy(-4,0),,1)')
    ifelse(m4a,d,,`dot(at tr_xy(4,0),,1)')')
  ] with .M4_xyO at M4CC }
 line to rvec_(rp_len,0) invis ')

                           `RotarySwitch( start degrees:end degrees, keys )
                            Ccw arc of switch points in a [ ] block 
                            keys:
                             poles=integer;
                              The centre pole is labeled C and the others
                              are labeled P1, P2, ...
                             circle=attributes; rad, fill, ...;
                             rad=expr; arc radius, default dimen_
                             wipers=wipers_pec & wipers_pec &...;
                              wipers_pec: nil|B[:degrees:length]
                             wline=attributes; wiper attributes (default ->)
                             segments=segspec & segspec &...;
                              segspec is start deg:end deg[:radius:thickness]
                            Default RotarySwitch(-45:45,poles=4;wipers=B:45)'
define(`RotarySwitch',`[ setdir_(rp_ang*rtod_)
  sang = m4Leftstr(`$1',-45)
  eang = m4Rightstr(`$1',-sang)
  pushkeys_(`$2',`poles:4:N; rad:dimen_; wipers::N; segments::N;
   circle:rad dotrad_*3/2 fill_(1):N; wline:->:N')dnl
  ifelse(m4wipers,,`poppushdef(`m4wipers',B:eang)')dnl
 C: circle rad dotrad_*3/2 fill_(1) m4circle
  pushdef(`npoles',eval(m4poles))dnl
  for_(1,npoles,1,`P`'m4x: circle rad dotrad_*3/2 fill_(1) m4circle \
   at C+vec_(Rect_(m4rad,sang+(m4x-1)/(npoles-1)*(eang-sang)))')dnl
 Arc: arc invis from P1 to P`'npoles with .c at C
  foreach_(`wiper',`ifinstr(wiper,nil,,wiper,B,
   `stacksplit_(`RSstack',wiper,:) stackreverse_(`RSstack') popdef(`RSstack')
    rs_deg = ifelse(RSstack,`RSstack',eang,RSstack); popdef(`RSstack')
    rs_len = ifelse(RSstack,`RSstack',m4rad,RSstack); popdef(`RSstack')
   Wiper`'m4Lx: line from C to C+vec_(Rect_(rs_len,rs_deg)) \
      chop C.rad m4wline')',
   patsubst(m4wipers,&,`,'))
  foreach_(`segment',`ifdef(`darrow_',,`include(darrow.m4)')dnl
    stacksplit_(`RSstack',segment,:) stackreverse_(`RSstack')dnl
    rs_start = RSstack; popdef(`RSstack')
    rs_end = RSstack; popdef(`RSstack')
    rs_rad = ifelse(RSstack,`RSstack',m4rad-C.rad*2,RSstack); popdef(`RSstack')
    rs_thk = ifelse(RSstack,`RSstack',C.diam,RSstack); popdef(`RSstack')
   Seg`'m4Lx: darc(C,rs_rad,rs_start*dtor_,rs_end*dtor_,rs_thk,,,|-|)
    resetdir_ ',
   patsubst(m4segments,&,`,'))
  popdef(`m4poles',`m4rad',`m4wipers',`m4segments',`m4circle',`m4wline',
   `npoles')dnl
  `$3' ] ')

                                `amp( linespec,size, attributes )
                                 Amplifier'
define(`amp',`eleminit_(`$1') define(`m4wd',`ifelse(`$2',,`dimen_',`($2)')')dnl
 {line to rvec_(max(0,rp_len/2-m4wd/2),0)
  {[ End: vec_(m4wd,0); line from End \
      to vec_(0,m4wd/2) \
    then to vec_(0,-m4wd/2) \
    then to End `$3'] with .End at rvec_(m4wd,0) }
  line from rvec_(m4wd,0) to rvec_(max(m4wd,rp_len/2+m4wd/2),0) }
 line to rvec_(max(rp_len,m4wd),0) invis ')

                                `integrator( linespec,size,attributes )'
define(`integrator',`eleminit_(`$1')
 define(`m4wd',`ifelse(`$2',,`dimen_',`($2)')')dnl
 {[ In: Here
  {line from rvec_(m4wd/4,m4wd/2) \
          to rvec_(0,m4wd/2) \
       then to rvec_(0,-m4wd/2) \
       then to rvec_(m4wd/4,-m4wd/2) `$3' }
   line from rvec_(m4wd*5/4,0) \
          to rvec_(m4wd/4,m4wd/2) \
     then to rvec_(m4wd/4,-m4wd/2) \
     then to rvec_(m4wd*5/4,0) `$3' ; Out: Here ] with .In at Here}
 {line from rvec_(m4wd*5/4,0) to rvec_(max(rp_len,m4wd*5/4),0) }
 line to rvec_(max(rp_len,m4wd*5/4),0) invis ')

                                `opamp(linespec,
                                  - label, + label, size|keys, chars)
                                  keys= lgth=expr;
                                        wdth=expr;
                                        body=attributes;
                                   drawn as a []:
                                   defined positions:
                                     W, N, E, S, Out, E1, E2, In1, In2
                                   size: expr (default lgth equals wdth)
                                   chars:
                                     P: power connections V1,V2
                                     R: labels at In1,In2 swapped
                                     T: truncated point '
define(`opamp',
`[ pushdef(`m4dlgth',`ifinstr(`$4',=,dimen_,ifelse(`$4',,dimen_,`($4)'))')dnl
   pushkeys_(`$4',`body::N; lgth:m4dlgth; wdth:m4`'lgth;')dnl
   pushdef(`dna_',`$5')dnl
 ifelse(`$1',,`lgt=elen_',`eleminit_(`$1'); lgt=max(rp_len,m4lgth)')
 W: Here
 N: vec_(0,m4wdth/2)
 S: vec_(0,-m4wdth/2)
 E: vec_(m4lgth,0)
 C: vec_(m4lgth/2,0)
 { sc_draw(`dna_',T,
    `line to N then to 0.75 between N and E \
       then to 0.75 between S and E then to S then to W m4body
     line from 0.75 between W and E to E',
    `line to N then to E then to S then to W m4body; move to E')
   if lgt > m4lgth then { line to rvec_(lgt-m4lgth,0) }
 Out: Here }
 NE: vec_(m4lgth/2,m4wdth/4); E1: NE
 SE: vec_(m4lgth/2,-m4wdth/4); E2: SE
 In1: vec_(0,m4wdth/4)
 In2: vec_(0,-m4wdth/4)
   { move to In`'ifinstr(dna_,R,2,1)
     ifelse(`$2',,"iflatex(`{\scriptsize$-$}',-)" \
       at rvec_(4pt__,0) ifsvg(+(0,textht/10)),m4lstring(`$2',"`$2'"))}
   { move to In`'ifinstr(dna_,R,1,2)
     ifelse(`$3',,"iflatex(`{\scriptsize$+$}',+)" \
       at rvec_(4pt__,0) ifsvg(+(0,textht/10)),m4lstring(`$3',"`$3'"))}
 sc_draw(`dna_',P,
   `{line from E1 to (vec_(m4lgth/2,m4wdth/4+m4wdth/8));    V1: Here}
    {line from E2 to (vec_(m4lgth/2,-(m4wdth/4+m4wdth/8))); V2: Here}')
 `$6' popdef(`m4dlgth',`dna_',`m4lgth',`m4wdth',`m4body')] ')

                                `dac(width,height,nIn,nN,nOut,nS)'
define(`dac',`[
  define(`dac_ht',`ifelse(`$2',,(dimen_),`$2')')dnl
  define(`dac_wd',`ifelse(`$1',,(dimen_+dac_ht/2),`$1')')dnl
In: Here
C:  rvec_((dac_wd-dac_ht/2)/2,0)
NE: rvec_(dac_wd-dac_ht/2, dac_ht/2)
Out:rvec_(dac_wd,0)
SE: rvec_(dac_wd-dac_ht/2,-dac_ht/2)
NW: rvec_(0,dac_ht/2)
SW: rvec_(0,-dac_ht/2)
  define(`m4dn',ifelse(`$3',,1,`eval($3)'))dnl
  for_(1,m4dn,1,`In`'m4x: NW-vec_(0,dac_ht*(2*m4x-1)/(2*m4dn))')dnl
  define(`m4dn',ifelse(`$4',,1,`eval($4)'))dnl
  for_(1,m4dn,1,`N`'m4x: NW+vec_((dac_wd-dac_ht/2)*m4x/(m4dn+1),0)')dnl
  define(`m4dn',ifelse(`$5',,1,`eval($5)'))dnl
  for_(1,m4dn,1,`r = eval(2*m4x-1)/eval(m4dn*2)
    Out`'m4x: Out-vec_(ifelse(eval((2*m4x-1)<m4dn),1,,-)dac_ht*(0.5-r),
      dac_ht*(0.5-r))')dnl
  define(`m4dn',ifelse(`$6',,1,`eval($6)'))dnl
  for_(1,m4dn,1,`S`'m4x: SW+vec_((dac_wd-dac_ht/2)*m4x/(m4dn+1),0)')dnl
  line to NW then to NE then to Out then to SE then to SW then to Here
  `$7']')

                                `adc(width,height,nIn,nN,nOut,nS)'
define(`adc',`[
  define(`adc_ht',`ifelse(`$2',,(dimen_),`$2')')dnl
  define(`adc_wd',`ifelse(`$1',,(dimen_+adc_ht/2),`$1')')dnl
In: Here
C:  rvec_(adc_ht/4+adc_wd/2,0)
NE: rvec_(adc_wd, adc_ht/2)
Out:rvec_(adc_wd,0)
SE: rvec_(adc_wd,-adc_ht/2)
NW: rvec_(adc_ht/2, adc_ht/2)
SW: rvec_(adc_ht/2,-adc_ht/2)
  define(`m4dn',ifelse(`$3',,1,`eval($3)'))dnl
  for_(1,m4dn,1,`r = eval(2*m4x-1)/eval(m4dn*2)
    In`'m4x: In+vec_(ifelse(eval((2*m4x-1)<m4dn),1,,-)adc_ht*(0.5-r),
      adc_ht*(0.5-r))')dnl
  define(`m4dn',ifelse(`$4',,1,`eval($4)'))dnl
  for_(1,m4dn,1,`N`'m4x: NW+vec_((adc_wd-adc_ht/2)*m4x/(m4dn+1),0)')dnl
  define(`m4dn',ifelse(`$5',,1,`eval($5)'))dnl
  for_(1,m4dn,1,`Out`'m4x: NE-vec_(0,adc_ht*(2*m4x-1)/(2*m4dn))')dnl
  define(`m4dn',ifelse(`$6',,1,`eval($6)'))dnl
  for_(1,m4dn,1,`S`'m4x: SW+vec_((adc_wd-adc_ht/2)*m4x/(m4dn+1),0)')dnl
  line from Out to SE then to SW then to In then to NW then to NE then to Out
  `$7']')

                               `diode(linespec,
                               B|b|CR|D|F|G|L|LE[R]|P[R]|S|Sh|SI|T|U|V|v|w|Z|z|
                                 chars,[R][E])
                                 Adding K to arg2 draws open arrowheads
                                 Adding M draws a mid-arrowhead crossbar
                                 Arg 3: R=reversed polarity, E=enclosure'
define(`diode',
`ifinstr(`$3',R,
 `reversed(`diode',`$1',`$2',patsubst(`$3',R),shift(shift(shift($@))))',
 `pushdef(`dma_',`$2')dnl
  pushdef(`m4ahd',ifinstr(dma_,K,,f))dnl
  ifinstr(dma_,M,`poppushdef(`m4ahd',m4ahd`'M)')dnl
  poppushdef(`dma_',patsubst(dma_,`K\|M'))dnl
  ifinstr(dma_,SI,`poppushdef(`dma_',`patsubst($2,SI)')dnl
    sidac(`$1',ifelse(dma_`$3',,,env=dma_`$3'))',
 `pushdef(`m4cts',`ifelse(
    dma_,,LACR,
    dma_,B,uLAZQuR,
    dma_,b,uLAzoQuR,
    dma_,CR,LACRrb,
    dma_,D,LuAHdQR,
    dma_,F,LFR,
    dma_,G,uLAQuR,
    dma_,LER,LdEACR,
    dma_,LE,LuEACR,
    dma_,L,LAcCR,
    dma_,P,LuPACR,
    dma_,PR,LdPACR,
    dma_,Sh,LFcCR,
    dma_,S,LASR,
    dma_,T,LATR,
    dma_,U,LA`'ifinstr(`$3',R,d,u)`'CR,
    dma_,V,LACXdR,
    dma_,v,LACvdR,
    dma_,w,LAdvXdR,
    dma_,Z,LAZR,
    dma_,z,LAzR,
    dma_)')
  ifelse(dma_,Sh,`poppushdef(`m4ahd')',
         dma_,L, `poppushdef(`m4ahd',xtract(m4ahd,M))')
  eleminit_(`$1')
  m4gen_d(m4cts,m4ahd)
  ifinstr(`$3',E,`pushdef(`m4dh',`dimen_*0.7')pushdef(`m4dv',`m4dh')dnl
    { Diode_Env: circle diam m4dh at rvec_(rp_len/2,0) }')
  pushdef(`m4dm',
   `ifelse(dma_,S,`m4dv/4',
           dma_,Z,`(m4dv/4-lthick/2)',
           dma_,z,`(m4dv/4-lthick/2)',
           dma_,v,`m4dv/4',
           dma_,w,`m4dv/4',
                  0)')dnl
 { [ box invis ht_ m4dv+lthick*sqrt(3) wid_ m4dh+lthick + m4dm
     ] at rvec_(rp_len/2+m4dm/2,0) }
 line invis to rvec_(rp_len,0)
 ifinstr(`$3',E,`popdef(`m4dh',`m4dv')')popdef(`m4cts')')dnl
 popdef(`dma_',`m4ahd')')')

                               `m4gen_d(chars,[f][R][M][E]):
                                 *This is an internal macro, subject to change*
                                 *General: [u|d] for shift, R for orientation*
                                 [u|d]A[c] arrowhead shifted up, down, or 0
                                 [u|d]F[c] arrowhead open-sided (Shockley)
                                 [u|d]B bar (gate) at arrowhead centre
                                 [u|d]BB long bar (gate) at arrowhead centre
                                 [u|d]C vertical bar at right of arrowhead
                                    u: with limiter bar on left; d on right
                                 [u|d]D vertical bar at right of arrowhead
                                    with bar at [top|bottom]
                                 [u|d]E em_arrows out
                                 [u|d]F half arrowhead shifted
                                 G gate for scr(,B), label G
                                 rb current regulator bars
                                 H double-length vertical bars
                                 [u]I bar for IGCT
                                 [u]L  left stem, uL = shortened
                                 M mid-arrow crossbar
                                 [d]N thyristor gate at anode, label Ga
                                    d adds bar
                                 [u|d]P em_arrows
                                 [u|d]Q[c] shifted left arrowhead [centerline]
                                 [u]R  right stem, uR = shortened
                                 S S-shape vertical bar
                                 T T-diode vertical bar
                                 W Thyristor gate from cathode, label G
                                 X varicap diode-capacitor
                                 [u|d]v varicap diode-capacitor curved plate
                                 Y bilateral core
                                 Z zener bar
                                 z zener bar angled
                                 zo zener bar outlined
                                arg 2: f= fill the arrowhead
                                       M=arrowhead crossbar
                                       R=right orientation
                                       E=envelope flag '
define(`m4gen_d',`{dnl
  define(`m4dv',`dimen_/6')define(`m4dh',sqrt(3)*m4dv/2)dnl
  define(`ddna_',`ifelse(`$1',,`LACR',`$1')')dnl
  define(`ddf_',`ifelse(`$1',,f,`$2')')dnl
  define(`m4tR',`ifinstr(`$2',R,(-1),1)')dnl
  define(`m4dy',`lthick*(sqrt(3)-1)/2')dnl
  M4_s: last line.start; M4_e: last line.end
  sc_draw(`ddna_',L,dnl            left stem, uL = shortened
   `line from M4_s to 0.5 between M4_s and M4_e \
      chop 0 chop m4dh`'ifelse(m4a,,/2)')
  dnl                              Elements drawn from left of body
  sc_draw(`ddna_',E,dnl            EM radiation arrows pointing out
   `ifelse(m4a,d,
     `{em_arrows(,rp_ang*rtod_-135) with .Tail at rvec_(-m4dh*0.3,-m4dv*0.8)}',
     `{em_arrows(,rp_ang*rtod_+135) with .Tail at rvec_(-m4dh*0.3,m4dv*0.8)}')')
  sc_draw(`ddna_',P,dnl            EM radiation arrows
   `ifelse(m4a,d,
     `{em_arrows(,rp_ang*rtod_+45) with .Head at rvec_(-m4dh*0.3,-m4dv*0.8)}',
     `{em_arrows(,rp_ang*rtod_-45) with .Head at rvec_(-m4dh*0.3, m4dv*0.8)}')')
  sc_draw(`ddna_',G,dnl            SCR gate
   `{Gm: line to ifinstr(`$2',E,2,3/2) between Here and \
     rvec_(m4dh,ifelse(m4a,d,-)m4dv/2) ifinstr(`$2',E,`then to \
       rvec_(m4dh*2,ifelse(m4a,d,-)sqrt((4*dimen_/10)^2-(m4dh*2)^2))')
     G: Here}')
  sc_draw(`ddna_',F,dnl            half arrowhead shifted up, down, or 0
   `sc_draw(`ddna_',Fc,`define(`m4Fc')')sc_draw(`ddna_',F,`undefine(`m4Fc')')dnl
    define(`m4dn',`ifelse(m4a,u,m4dv/2,m4a,d,-m4dv/2,0)')
    define(`m4dFline',`Gm: line from rvec_(0,m4tR*m4dn) \
           to rvec_(0,m4tR*(m4dn+m4dv/2)) \
      then to rvec_(m4dh-lthick/2,m4tR*m4dn) \
      then to rvec_(0,m4tR*m4dn)')
    { ifinstr(ddf_,f,`m4fshade(m4fill,m4dFline)',`m4dFline')
    line to ifinstr(`$2',E,
     `rvec_(0,-(m4tR*sqrt((dimen_*0.7/2)^2-(m4dh/2)^2)))',
     `rvec_(0,-(m4tR*m4dv/2))')
     G: Here }
    ifdef(`m4Fc',`{line from rvec_(0,m4tR*m4dn) to rvec_(m4dh,m4tR*m4dn)}')
    move to rvec_(m4dh,0) ')
  ifinstr(ddna_,A,dnl              Arrowhead shifted up, down, or 0
   `sc_draw(`ddna_',Ac,`define(`m4Ac')')sc_draw(`ddna_',A,`undefine(`m4Ac')')dnl
    define(`m4dn',`ifelse(m4a,u,m4dv/2,m4a,d,-m4dv/2,0)')dnl
    define(`m4dFline',`line from rvec_(0,m4dn) \
             to rvec_(0,m4dn+m4dv/2) \
        then to rvec_(m4dh-lthick/2,m4dn) \
        then to rvec_(0,m4dn-m4dv/2) \
        then to rvec_(0,m4dn)')
    { ifinstr(ddf_,f,`m4fshade(m4fill,m4dFline)',`m4dFline')}
    ifdef(`m4Ac',`{line from rvec_(0,m4dn) to rvec_(m4dh,m4dn)}')
    ifinstr(`$2',M,`{line from rvec_(m4dh/2,m4dn+m4dv/2) \
                               to rvec_(m4dh/2,m4dn-m4dv/2)}')
    move to rvec_(m4dh,0) ')
  sc_draw(`ddna_',B,dnl            Perp bar at arrowhead centre
   `{ifelse(m4a,u,dnl              from arrow edge or across the centre line
     `Gm: line from        rvec_(-m4dh/2, m4dv/4) \
        to ifinstr(`$2',E,`rvec_(-m4dh/2, dimen_*0.35)',
                          `rvec_(-m4dh/2, m4dv*5/4+m4dy)')',
     m4a,d,
     `Gm: line from        rvec_(-m4dh/2,-m4dv/4) \
        to ifinstr(`$2',E,`rvec_(-m4dh/2,-dimen_*0.35)',
                          `rvec_(-m4dh/2,-m4dv*5/4-m4dy)')',
     `Gm: line from rvec_(-m4dh/2,-m4dv/2-m4dy) \
                 to rvec_(-m4dh/2, m4dv/2+m4dy)
      G: Gm.c')
     ifelse(m4a,,,G: last line.end) }')
  sc_draw(`ddna_',C,dnl            Vertical bar
   `{ line from ifelse(m4a,d,`rvec_(m4dh/2,m4tR*(-m4dv/2-m4dy-m4dh/2)) to') dnl
     rvec_(0,m4tR*(-m4dv/2-m4dy)) \
       to rvec_(0,m4tR*(m4dv/2+m4dy)) ifelse(m4a,u,
      `to rvec_(m4dh/2,m4tR*(m4dv/2+m4dy+m4dh/2))') }')
  sc_draw(`ddna_',D,dnl            Vertical bar with horiz tail
   `{ line from rvec_(0,m4tR*( m4dv/2+m4dy)) \
             to rvec_(0,m4tR*(-m4dv/2-m4dy)) \
        then to rvec_(m4dh/2,m4tR*(-m4dv/2-m4dy)) }')
  m4gen_d2($@)dnl
  m4gen_d3($@)dnl
`$3'}') dnl              macro split to keep within m4 buffer size
  define(`m4gen_d2',`dnl
  dnl                             Elements drawn at right of body
  sc_draw(`ddna_',rb,dnl            Current regulator bars
   `{line from rvec_(-m4dv/4,-m4dv/2-m4dy) \
            to rvec_( m4dv/4,-m4dv/2-m4dy)}
    {line from rvec_(-m4dv/4,m4dv/2+m4dy) \
            to rvec_( m4dv/4,m4dv/2+m4dy)}')
  sc_draw(`ddna_',H,dnl            Double length double vertical bars
   `{line from rvec_(0,-m4dv-m4dy) \
            to rvec_(0, m4dv+m4dy)}
    {line from rvec_(-m4dh,-m4dv-m4dy) \
            to rvec_(-m4dh, m4dv+m4dy)}
    move to rvec_(-m4dh,0)')
  sc_draw(`ddna_',I,dnl            Double length double vertical bars
   `TA: rvec_(0,m4tR*(-m4dv/2)); TB: rvec_(-m4dh/2,m4tR*(-m4dv/4)); TC: Here
    {line from TB to TA; mitre_(TB,TA,TC)} ')
  sc_draw(`ddna_',N,dnl            thyristor gate at anode, label Ga
   `{TA: rvec_(-m4dh,-m4tR*m4dv/4); TB: rvec_(-m4dh*2,-m4tR*m4dv*3/4)
     Gam: line from TA to TB ifinstr(`$2',E,`then to \
       rvec_(-m4dh*2,-m4tR*sqrt((dimen_*0.7/2)^2-(m4dh*3/2)^2))')
     Ga: Here}; ifelse(m4a,d,
     `TC: TB-TA; {[line to (-TC.y,TC.x)/2] at 2/3 between TA and TB} ')')
  sc_draw(`ddna_',S,dnl            S-shape vertical bar
   `{line from rvec_(-m4dv/4,-m4dv/3) \
            to rvec_(-m4dv/4,-m4dv/2-m4dy) \
       then to rvec_(0,-m4dv/2-m4dy) \
       then to rvec_(0, m4dv/2+m4dy) \
       then to rvec_(m4dv/4,m4dv/2+m4dy) \
       then to rvec_(m4dv/4,m4dv/3)}')
  sc_draw(`ddna_',T,dnl            T-diode vertical bar
   `{line from rvec_(-m4dv/4,-m4dv/2-m4dy) \
            to rvec_(0,-m4dv/2-m4dy) \
       then to rvec_(0, m4dv/2+m4dy) \
       then to rvec_(-m4dv/4,m4dv/2+m4dy)}')
  sc_draw(`ddna_',v,dnl            Variable capacitor curved plate
   `ifelse(m4a,d,`define(`m4drad',`sqrt((m4dv/2+m4dy)^2+(m4dv)^2*3/4)')dnl
      {arc cw from rvec_(-(m4drad-m4dv*sqrt(3)/2), m4dv/2+m4dy) \
                to rvec_(-(m4drad-m4dv*sqrt(3)/2),-m4dv/2-m4dy) \
       with .c at rvec_(-m4drad,0)}',
     `{arc cw from rvec_(m4dv/3,-m4dv/2-m4dy) \
                to rvec_(m4dv/3, m4dv/2+m4dy) \
       with .c at rvec_(m4dv/3+m4dv*sqrt(3)/2,0)}
      {line from rvec_(m4dv/3+m4dv*sqrt(3)/2-last arc.rad,0) \
            to rvec_(m4dv/4,0)}')')
  sc_draw(`ddna_',W,dnl            cathode gate
   `TA: rvec_(0,m4tR*m4dv/4); TB: rvec_(m4dh,m4tR*m4dv*3/4); TC: TB-TA
    TE: rvec_(m4dh,m4tR*sqrt((dimen_*0.7/2)^2-(m4dh*3/2)^2))
    {Gm: line from TA to TB ifinstr(`$2',E,`then to TE') ifelse(m4a,u,
        `then to rvec_(m4dh,m4tR*m4dv/2) then to Here')
     ifelse(m4a,d,`[line to (-TC.y,TC.x)/2] at 2/3 between TA and TB')}
     G: ifinstr(`$2',E,TE,TB)')
  sc_draw(`ddna_',X,dnl            Variable capacitor plate
   `{line from rvec_(m4dv/4,-m4dv/2-m4dy) \
            to rvec_(m4dv/4, m4dv/2+m4dy)}')
  sc_draw(`ddna_',Z,dnl            Zener bar
   `{line from rvec_(-m4dv/4,-m4dv/2-m4dy) \
            to rvec_(0,-m4dv/2-m4dy) \
       then to rvec_(0, m4dv/2+m4dy) \
       then to rvec_(m4dv/4,m4dv/2+m4dy)}')
  sc_draw(`ddna_',zo,dnl           Outlined zener bar
   `{line from rvec_(-m4dv/4,-m4dv/2-m4dy-lthick*2) \
            to rvec_( lthick*0.7,-m4dv/2-m4dy) \
       then to rvec_( lthick*0.7, m4dv/2+m4dy+lthick) }
    {line from rvec_( m4dv/4, m4dv/2+m4dy+lthick*2) \
            to rvec_(-lthick*0.7, m4dv/2+m4dy) \
       then to rvec_(-lthick*0.7,-m4dv/2-m4dy-lthick) }')
  sc_draw(`ddna_',z,dnl            Zener bar
   `{line from rvec_(-m4dv/4,-m4dv/2-m4dy) \
            to rvec_(0,      -m4dv/3-m4dy) \
       then to rvec_(0,       m4dv/3+m4dy) \
       then to rvec_( m4dv/4, m4dv/2+m4dy)}')
  ifinstr(ddna_,Q,dnl              left arrowhead
   `sc_draw(`ddna_',Qc,`define(`m4Qc')')sc_draw(`ddna_',Q,`undefine(`m4Qc')')dnl
    define(`m4dn',`ifelse(m4a,u,m4dv/2,m4a,d,-m4dv/2,0)')dnl
    {move to rvec_(m4dh,0)
    define(`m4dFline',`line from rvec_(0,m4dn) \
             to rvec_(0,m4dn+m4dv/2) \
        then to rvec_(-(m4dh-lthick/2),m4dn) \
        then to rvec_(0,m4dn-m4dv/2) \
        then to rvec_(0,m4dn) ')
    ifinstr(ddf_,f,`m4fshade(m4fill,m4dFline)',`m4dFline')}
    ifdef(`m4Qc',`{line from rvec_(0,m4dn) \
      to rvec_(-(m4dh-lthick/2),m4dn)}')
    move to rvec_(m4dh,0)')dnl
') dnl              macro split to keep within m4 buffer size
  define(`m4gen_d3',`dnl
  sc_draw(`ddna_',Y,dnl            Bilateral switch
   `define(`m4vt',`(m4tR*m4dv/2)')dnl
      line from rvec_(0,-m4vt) to Here
      define(`m4dFline',`line to rvec_(0,m4vt) \
        then to rvec_(2*m4dh,0) \
        then to rvec_(2*m4dh,-m4vt) then to Here ')
      ifinstr(ddf_,f,`m4fshade(m4fill,m4dFline)',`m4dFline')
      line from rvec_(2*m4dh,m4vt) to rvec_(2*m4dh,0)
      { Gm: line from rvec_(-m4dh,m4vt) \
          to ifinstr(`$2',E,`rvec_(-m4dh,-m4tR*dimen_*0.35)',
                            `rvec_(-m4dh,-m4tR*m4dv*5/4)')
        G: Here }')
  sc_draw(`ddna_',R,dnl            right stem, uR = shortened
   `line from 0.5 between M4_s and M4_e to M4_e \
      chop m4dh ifelse(m4a,,/2,m4a,d,/2+m4dv/4) chop 0')
  ') dnl

                           `sidac( linespec, keys ) Silicon bilateral switch
                            (Silicon Diode for Alternating Current)
                            keys:
                               size= expr;
                               env= E|attributes; (envelope attributes
                                                   except for size; E=nonblank)
                               symbol= attributes; (e.g. outlined "red")
                               name= body name;'
define(`sidac',`pushkeys_(`$2',
 `size:sourcerad_*2;env::N;symbol::N;name::N;')dnl
  eleminit_(`$1') pushdef(`sid',m4size/4)
  {line to rvec_(rp_len/2-sid,0)}
  {line from rvec_(rp_len/2+sid,0) to 2nd last line.end}
  {ifelse(m4name,,,m4name:) [ dnl
   ifelse(m4env,,,`circle diam m4size at (0,0) patsubst(m4env,E)')
    {line from vec_(-sid,-sid) to vec_(-sid,sid) \
    then to vec_(sid,-sid) then to vec_(sid,sid) m4symbol}
  {T: line from vec_(0,-sid) to vec_(0,sid) m4symbol } ] at rvec_(rp_len/2,0)}
  line invis to 3rd last line.end dnl
  popdef(`m4size',`m4env',`m4symbol',`m4name',`sid') ')

                                `em_arrows( type|keys,angle,length )
                                 type=N|I|E [D|T]
                                   N=nonionizing, I=ionizing, E=simple;
                                   D=dot on arrow stem; T=anchor tail
                                 keys: type=chars as above;
                                       lgth=expr;
                                       sep=expr; arrow separation
                                       angle=degrees; absolute direction'
define(`em_arrows',`[
  pushkeys_(`$1',`type:m4typ:N; angle:ifelse(`$2',,135,`($2)')*dtor_')dnl
  ifelse(m4type,m4typ,`poppushdef(`m4type',`ifelse(`$1',,N,`$1')')')dnl
  arrowhead = em_arrowhead
  sc_draw(`m4type',N,
  `pushkeys_(`$1',lgth:ifelse(`$3',,dimen_*0.46,`$3'); sep:em_arrowwid*9/8)dnl
   { A1: arrow m4c_l to rrot_(m4lgth,0,m4angle) wid em_arrowwid ht em_arrowht}
   move to rrot_(0,-m4sep,m4angle)
   { A2: arrow m4c_l to rrot_(m4lgth,0,m4angle) wid em_arrowwid ht em_arrowht}')
  sc_draw(`m4type',I,
  `pushkeys_(`$1',lgth:ifelse(`$3',,dimen_*0.46,`$3'); sep:em_arrowwid*9/8)dnl
   m4em_serp(A1)
   move to rrot_(0,-m4sep,m4angle); m4em_serp(A2)')
  sc_draw(`m4type',E,
  `pushkeys_(`$1',lgth:ifelse(`$3',,dimen_*0.25,`$3'); sep:dimen_/8)dnl
   { A1: line to rrot_(m4lgth,0,m4angle) \
       then to rrot_(m4lgth-dimen_/18,dimen_/18,m4angle) }
   move to rrot_(0,-m4sep,m4angle)
   { A2: line to rrot_(m4lgth,0,m4angle) \
       then to rrot_(m4lgth-dimen_/18,dimen_/18,m4angle) }')
  sc_draw(`m4type',D,`dot(at A1.start); dot(at A2.start)')
  sc_draw(`m4type',T,`m4em_anchor(A1.start); m4em_anchor(A2.start)')
  Tail: 0.5 between A1.start and A2.start
  Head: 0.5 between A1.end and A2.end
  `$4' popdef(`m4typ',`m4type',`m4angle',`m4lgth',`m4sep') ]')
define(`m4em_serp',`{{`$1': line invis to rrot_(m4lgth,0,m4angle)}
  for i=1 to (m4lgth-em_arrowht*3/4)/(em_arrowwid) do {
    if i%2 then {define m4cw {cw}} else {define m4cw {ccw}}
    arc m4cw to rrot_(em_arrowwid,0,m4angle) \
      with .c at rrot_((em_arrowwid)/2,0,m4angle) }; round
    arrow m4c_l to `$1'.end wid em_arrowwid ht em_arrowht*3/4 }')
define(`m4em_anchor',`{ move to `$1'
  {arc cw to rrot_(0,em_arrowwid/2,m4angle) \
     with .c at rrot_(0,em_arrowwid/4,m4angle)}
  {arc to rrot_(0,-arrowwid/2,m4angle) \
     with .c at rrot_(0,-arrowwid/4,m4angle)}}')

                                `thyristor(linespec,
                                   DIAC|DIAC2|DIAC3|ETO|RCT|RCTA|GTO|GTOP|GTON|
                                   GTS|IEC|IGCT|MTO|SBS|SCR|SCS|SIDAC|SUS|
                                   Sch|Sch2 [chars])
                                 Composite element in [ ] block
                                 (To place as two-terminal, see thyristor_t()).
                                 chars:
                                   K: use open arrowheads
                                   E: adds envelope
                                   R: right orientation 
                                   A: arrowhead
                                   F: half arrowhead
                                   U: centre line in arrowhead
                                   B: bidirectional diode
                                   H: perpendicular gate, endpoint G
                                   N: anode gate, endpoint Ga
                                   V: perpendicular gate at arrowhead centre'
define(`thyristor',
 `pushdef(`m4thtype') foreach_(`M4T',
   `ifelse(index(`$2',M4T),-1,,`poppushdef(`m4thtype',M4T)')dnl',
    DIAC,DIAC2,DIAC3,ETO,RCT,RCTA,GTO,GTOP,GTON,GTS,
    IEC,IGCT,MTO,SBS,SCR,SCS,SIDAC,SUS,Sch,Sch2)dnl
  pushdef(`m4thx',patsubst(`$2',m4thtype))dnl             delete the type code
  pushdef(`m4thf',`ifinstr(m4thx,R,R)')dnl                         orientation
  poppushdef(`m4thf',m4thf`'xtract(m4thx,E))dnl                       envelope
  poppushdef(`m4thx',patsubst(m4thx,R\|E))dnl
  pushdef(`m4thAc',xtract(m4thx,F,A))dnl                            centerline
  poppushdef(`m4thAc',patsubst(m4thAc,F,Fc))dnl
  poppushdef(`m4thAc',ifelse(m4thAc,,A,m4thAc)`'ifinstr(m4thx,U,c))dnl centerln
  poppushdef(`m4thf',m4thf`'ifinstr(m4thx,F,,m4thx,K,,f))dnl              fill
  ifelse(m4thtype,, dnl                                           no type code
   `[pushdef(`m4thyd',`dimen_*0.7') eleminit_(`$1',m4thyd)
     A: last line.start; K: last line.end; T1:A; T2:K
     pushdef(`m4tha',`patsubst(patsubst(patsubst(patsubst(m4thx,UA,Ac),V,B),
      H,ifinstr(m4thf,R,d,u)B),U,Ac)')dnl
     ifelse(xtract(m4tha,A,F,Q),,`poppushdef(`m4tha',m4tha`'A)dnl
      poppushdef(`m4thf',m4thf`'ifinstr(m4thx,K,,f))')dnl
     ifelse(xtract(m4tha,B,G,H,N,W),,`poppushdef(`m4tha',m4tha`'W)')dnl
     m4gen_d(LR`'ifinstr(m4tha,uC,u,m4tha,dC,d)`'C`'m4tha,m4thf)
     ifinstr(m4thf,E,`Env: circle diam m4thyd with .c at rvec_(rp_len/2,0)')
    `$3' popdef(`m4thyd',`m4tha') undefine(`m4dv',`m4dh') ]',
 `ifelse(xtract(m4thtype,IEC,Sch,DIAC3),,
 `[define(`m4thyd',`dimen_*0.7') eleminit_(`$1',m4thyd)dnl
`#' m4thtype
#m4msg(|`$2'|m4thtype|m4thx|m4thf|)
   A: last line.start; K: last line.end; T1:A; T2:K
   ifelse(m4thtype,DIAC,`ifinstr(m4thf,R,
     `m4gen_d(LdG'xtract(m4thx,G)`dA`'m4thAc`'HuQ`'m4thAc`'R,m4thf)',
     `m4gen_d( LG'xtract(m4thx,G)`uA`'m4thAc`'HdQ`'m4thAc`'R,m4thf)')',
    m4thtype,DIAC2,
     `m4gen_d(LdA`'m4thAc`'HuQ`'m4thAc`'R,m4thf,{move to rvec_(-rp_len/2,0)
       Gm: line to rvec_(0,(m4dn+m4dv+lthick/2)*2) with .c at Here
       G: Gm.`'ifinstr(m4thf,R,start,end)})',
    m4thtype,ETO,
     `m4gen_d(LCRW`'m4thAc,m4thf,
       M4To: rvec_(-rp_len/2+m4dh*3/2,ifinstr(m4thf,R,,-)m4dv/3)
       {line from Here to rvec_(m4dh*2/3,0) with .c at M4To}
       {line from M4To to M4To+vec_(0,ifinstr(m4thf,R,,-)m4dv); Go: Here})',
    m4thtype,RCT,
     `pushdef(`m4nthf',`ifinstr(m4thf,R,patsubst(m4thf,R),m4thf`'R)')dnl
      m4gen_d(LDRW`'m4thAc,m4nthf) popdef(`m4nthf')',
    m4thtype,RCTA, `m4gen_d(LDRN`'m4thAc,m4thf)',
    m4thtype,GTO, `m4gen_d(LCRuW`'m4thAc,m4thf)',
    m4thtype,GTOP, `m4gen_d(LCRdW`'m4thAc,m4thf)',
    m4thtype,GTON, `m4gen_d(LCRdN`'m4thAc,m4thf)',
    m4thtype,GTS, `m4gen_d(LCRdW`'m4thAc,m4thf)',
    m4thtype,IGCT, `m4gen_d(LCRdWI`'m4thAc,m4thf)',
    m4thtype,MTO,`m4gen_d(LCRW`'m4thAc,m4thf,
      M4To: rvec_(-rp_len/2+m4dh*3/4,ifinstr(m4thf,R,,-)(m4dv/3+m4dy))
      {line from M4To-vec_(0,m4dv/6) to M4To+vec_(0,m4dv/6)}
      {line from M4To \
       to rvec_(-rp_len/2+m4dh*3/2,ifinstr(m4thf,R,,-)m4dv*3/4) ifinstr(m4thf,E,
        `then to rvec_(-rp_len/2+m4dh*3/2,
         ifinstr(m4thf,R,,-)sqrt((dimen_*0.7/2)^2-(m4dh*3/2)^2))'); Go: Here})',
    m4thtype,SBS, `m4gen_d(uLYuR,patsubst(m4thf,f))
      {line from rvec_(rp_len/2+m4dh,0) to rvec_(rp_len/2-m4dh,0)} ',
    m4thtype,SCR, `m4gen_d(LCRW`'m4thAc,m4thf)',
    m4thtype,SCS, `m4gen_d(LCRWN`'m4thAc,m4thf)',
    m4thtype,SIDAC, `m4gen_d(LCRE`'m4thAc,m4thf)',
    m4thtype,SUS, `m4gen_d(LFR,m4thf)')
    ifinstr(m4thf,E,`Env: circle diam m4thyd with .c at rvec_(rp_len/2,0)')
    `$3']',
  ``#' m4thtype
   ifelse(m4thtype,IEC,`bi_trans(`$1',
      ifinstr(m4thf,R,,R),uEdCBUT,xtract(m4thf,E),A:E;K:C;G:T;`$3')',
    m4thtype,Sch,`bi_trans(`$1',
      ifinstr(m4thf,R,,R),uECBUdV,xtract(m4thf,E),A:E;K:C;G:T;`$3')',
    m4thtype,Sch2,`bi_trans(`$1',
      ifinstr(m4thf,R,,R),uEBUuT,xtract(m4thf,E),
      C0: tr_xy(3,8); Cm: line from C0 to tr_xy(1.2,4)
     {arrow from 3/4 between Cm.start and Cm.end \
              to 1/4 between Cm.start and Cm.end}
      A:E;K:Cm.start;G:T;`$3')',
    m4thtype,DIAC3,`bi_trans(`$1',
      ifinstr(m4thf,R,,R),BdEdCBU,xtract(m4thf,E),A:E;K:C;G:B;`$3')')')dnl
  popdef(`m4thtype',`m4thx',`m4thf',`m4thAc') ') ')

                                `thyristor_t(linespec, thyristor chars], label)
                                 A wrapper to place thyristor(linespec,...)
                                 as a two-terminal element with arg3
                                 as label of the [] block (see also scr())'
define(`thyristor_t',`eleminit_(`$1')
  M4_thyS: last line.start; M4_thyE: last line.end
  ifelse(`$3',,,`$3:') thyristor(from M4_thyS to M4_thyE,`$2',`$4') \
    with .A at M4_thyS; line invis from M4_thyS to M4_thyE')

                                `scr(linespec, [R][E][chars], label) and similar
                                 Place thyristor as a two-term element with
                                 arg 3 as label of the [] block'
define(`scr',`eleminit_(`$1'); M4_scrS: last line.start; M4_scrE: last line.end
  ifelse(`$3',,,`$3:') thyristor(from M4_scrS to M4_scrE,SCR`'`$2',`$4') \
    with .A at M4_scrS; line invis from M4_scrS to M4_scrE')
define(`scs',`eleminit_(`$1'); M4_scsS: last line.start; M4_scsE: last line.end
  ifelse(`$3',,,`$3:') thyristor(from M4_scsS to M4_scsE,SCS`'`$2',`$4') \
    with .A at M4_scsS; line invis from M4_scsS to M4_scsE')
define(`sus',`eleminit_(`$1'); M4_susS: last line.start; M4_susE: last line.end
  ifelse(`$3',,,`$3:') thyristor(from M4_susS to M4_susE,SUS`'`$2',`$4') \
    with .A at M4_susS; line invis from M4_susS to M4_susE')
define(`sbs',`eleminit_(`$1'); M4_sbsS: last line.start; M4_sbsE: last line.end
  ifelse(`$3',,,`$3:') thyristor(from M4_sbsS to M4_sbsE,SBS`'`$2',`$4') \
    with .A at M4_sbsS; line invis from M4_sbsS to M4_sbsE')
define(`gto',`eleminit_(`$1'); M4_gtoS: last line.start; M4_gtoE: last line.end
  ifelse(`$3',,,`$3:') thyristor(from M4_gtoS to M4_gtoE,GTO`'`$2',`$4') \
    with .A at M4_gtoS; line invis from M4_gtoS to M4_gtoE')
define(`gts',`eleminit_(`$1'); M4_gtsS: last line.start; M4_gtsE: last line.end
  ifelse(`$3',,,`$3:') thyristor(from M4_gtsS to M4_gtsE,GTS`'`$2',`$4') \
    with .A at M4_gtsS; line invis from M4_gtsS to M4_gtsE')

                                `tgate( linespec, [B][R|L] ) Transmission gate
                                 B= box form
                                 L= left orientation'
define(`tgate',`[ eleminit_(`$1') pushdef(`m4tgm',ifinstr(`$2',L,-))
 A: last line.start
 B: last line.end
 C: last line.center
  ifinstr(`$2',B,
   `ebox(from A to B,,dimen_/5)
 Gb: C+vec_(0,m4tgm`'dimen_/5/2)
    L1: line from 2 between Gb and C to 4 between Gb and C',
   `m4gen_d(uLAQuR) pushdef(`m4dv',`dimen_/6')pushdef(`m4dh',sqrt(3)*m4dv/2)
    Circle: circle thick max(4pt__,linethick/2) rad m4dh/4 \
      at C+vec_(0,m4tgm`'m4dh/4*4/3)
    L2: line from last circle+vec_(0,m4tgm`'m4dh/4) \
        to C+vec_(0,m4tgm`'m4dh*3/2)
 Gb: Here
    L3: line from C to C-vec_(0,m4tgm`'m4dh) popdef(`m4dv',`m4dh')')
 G: Here
  `$3' popdef(`m4tgm')]')
                                `ptrans( linespec, [R|L] ) Pass transistor
                                 L= left orientation'
define(`ptrans',`[ eleminit_(`$1') define(`m4ptm',ifinstr(`$2',L,-))
  define(`m4pv',`dimen_/6')define(`m4pwd',m4pv*2)dnl
 A: last line.start; Start: A
 B: last line.end; End: B
 C: last line.center
    La1: line to rvec_(rp_len/2-m4pwd/2,0)
    { La2: line to rvec_(m4pwd,m4pv) \
       then to rvec_(m4pwd,neg_(m4pv)) \
       then to Here }
    { La3: line from rvec_(m4pwd,0) \
          to rvec_(0,m4pv) \
       then to rvec_(0,neg_(m4pv)) \
       then to rvec_(m4pwd,0)
    Circle: circle thick max(4pt__,linethick/2) rad m4pv/4 \
      at C+vec_(0,m4ptm`'m4pv*5/6)
    La4: line from last circle+vec_(0,m4ptm`'m4pv/4) \
        to C+vec_(0,m4ptm`'m4pv*2)
 Gb:Here
    La5: line from C-vec_(0,m4ptm`'m4pv/2) \
        to C-vec_(0,m4ptm`'m4pv*3/2)
 G: Here }
    La6: line from rvec_(m4pwd,0) \
        to B
  `$3']')
                                `tline( linespec, wid, len ) Transmission line'
define(`tline',`eleminit_(`$1')
   define(`m4v',`ifelse(`$2',,`dimen_/6',`($2)')')dnl
   define(`m4h',`ifelse(`$3',,`dimen_*2/3',min(rp_len-m4v/2,`$3'))')dnl
   {line from last line.c+vec_(m4h/2+m4v/4,0) \
        to last line.end}
   {line to 2nd last line.c+vec_(-m4h/2,0); round
   [ifdpic(
    `line from rvec_(0,-m4v/2) \
          to rvec_(m4h,-m4v/2)
     spline 0.5523 to rvec_(m4v/4,0) \
       then to rvec_(m4v/4,m4v) \
          to rvec_(0,m4v)
     line to rvec_(-m4h,0)
     spline 0.5523 to rvec_(-m4v/4,0) \
       then to rvec_(-m4v/4,-m4v) \
       then to rvec_(m4v/4,-m4v) \
       then to rvec_(m4v/4,0) \
       then to Here',
    `line from rvec_(m4v/4,-m4v/2) \
          to rvec_(m4h-m4v/4,-m4v/2)
     spline to rvec_(m4v/2,0) \
       then to rvec_(m4v/2,m4v) \
       then to rvec_(0,m4v)
     line to rvec_(-m4h+m4v/2,0)
     spline to rvec_(-m4v/2,0) \
       then to rvec_(-m4v/2,-m4v) \
       then to rvec_(0,-m4v)\
       then to Here \
       then to rvec_(-m4v/2,0) \
       then to rvec_(-m4v/2,-m4v)\
       then to rvec_(0,-m4v)')] with .c at rvec_(m4h/2,0) }
   line to 3rd last line.end invis ')

define(`m4_U',`dimen_/10')      `Semiconductor grid size'
define(`m4_Aht',`m4_U*10/6')    `Semiconductor arrowhead ht and wd'
define(`m4_Awd',`m4_U*10/9')

                                `Bipolar transistor bi_tr(linespec, L|R, P, E)'
define(`bi_tr',`bi_trans(`$1',`$2',ifelse(`$3',P,u,d)EBCBU,`$4',`$5')')

                                `Darlington(L|R, chars)
                                 arg2:
                                   E= envelope
                                   P= p-type,
                                   B1= internal base lead,
                                   R1= Q1 bias resistor; E1= ebox,
                                   R2= Q2 bias resistor; E2= ebox,
                                   D= damper diode
                                   Z= zener bias diode
                                 This macro would be somewhat simpler if the
                                 joints had not been mitred (using Along_ and
                                 mitre_)'
define(`Darlington', `[ rpoint_(dimen_/10) define(`m4DR',`ifinstr(`$1',R,-)')
   define(`m4Da',`$2') pushdef(`dimen_',((dimen_)*0.8))dnl Smaller internals
   hp_ang = rp_ang
   Q1: bi_trans(,`$1',ifinstr(m4Da,P,u,d)ECBU)
   E: Q1.E
   Q1B: line from Q1.Bulk.c to Q1.Bulk.c + vec_(0,m4DR`'m4_U)
   Q2: bi_trans(,`$1',ifinstr(m4Da,P,u,d)EBCBU) with .E at Here
   Mitre_(Q1B,Q2.Em0)
   B: Q2.B
   T: Q2.C+(Q2.Bulk.c.x-Q2.B.x,Q2.Bulk.c.y-Q2.B.y)
   QC: intersect_(Q2.C,T,Q1.E,Q1.C)
   C: QC
   L1: line from Along_(Q2.Cm0,hlth) to Q2.C then to QC then to Q1.C \
     then to Along_(Q1.Cm0,hlth)
   define(`m4DE1')sc_draw(`m4Da',E1,`define(`m4DE1',E)define(`m4Da',R1`'m4Da)')
   define(`m4DE2')sc_draw(`m4Da',E2,`define(`m4DE2',E)define(`m4Da',R2`'m4Da)')
   ifinstr(m4Da,E,
    `Env: circle rad 7.75*m4_U at Q1.Bulk.c+vec_(1.5*m4_U,m4DR`'(-0.1*m4_U))
     line from Q1.E to Q1.E+vec_(-2.2*m4_U,0); E: Here
     Mitre_(last line,Q1.Em0)
     line from QC to QC+vec_(2.2*m4_U,0); C: Here
     pushdef(`dotrad_',(dotrad_/2))dnl
     ifelse(ifinstr(m4Da,B1,T,m4Da,R1,T,m4Da,R2,T),T,`dot(at Q2.E)')
     ifelse(ifinstr(m4Da,R2,T,m4Da,Z,T),T,
      `M4D1: dot(at Q2.Bulk.c+vec_(0,m4DR`'m4_U))')
     ifelse(ifinstr(m4Da,B1,T,m4Da,R1,T),T,`ifinstr(m4Da,R2,
      `M4D2: dot(at Q2.E+vec_(-m4_U,0))')')
     ifinstr(m4Da,B1,
      `ifinstr(m4Da,R1,`dot(at Q2.E-vec_(3*m4_U,0))')
       B1: Q2.E+vec_(-3*m4_U,m4DR`'5.2*m4_U)
       line from B1 to Q2.E+vec_(-3*m4_U,0); corner')
     ifinstr(m4Da,Z,`dot(at QC+vec_(m4_U*3/2,0))')
     dot(at QC)
     ifinstr(m4Da,D,`dot(at Q1.E)')
     ifinstr(m4Da,R1,`dot(at Q1.E-vec_(m4_U,0))')
     popdef(`dotrad_')',
    `ifinstr(m4Da,B1,`move to Q2.E-vec_(3*m4_U,0); line to rvec_(-m4_U,0)
     B1: Here')') 
   ifelse(ifinstr(m4Da,B1,T,m4Da,R1,T,m4Da,R2,T),T,
    `line from Q2.E to Q2.E-vec_(m4_U,0)
     ifelse(ifinstr(m4Da,B1,T,m4Da,R1,T),T,
      `line to rvec_(-2*m4_U,0)
       ifinstr(m4Da,R1,
        `line to rvec_(-m4_U,0); corner pushdef(`dimen_',((dimen_)*0.6))
         R1: resistor(to Q1.E+vec_(-m4_U/0.6,0),,m4DE1) popdef(`dimen_')
         ifinstr(m4Da,E,,`corner;E: Here; line from Q1.E to E')
         point_(hp_ang)')')')
   ifinstr(m4Da,R2,
    `line from M4D1 to M4D1+vec_(-4*m4_U,0); corner
     pushdef(`dimen_',((dimen_)*0.6))dnl
     R2: resistor(to M4D2,,m4DE2) popdef(`dimen_')
     point_(hp_ang)')
   ifinstr(m4Da,D,
    `DE: Q1.E + vec_(m4_U*3/2,m4DR`'(-m4_U*3/2))
     DS: QC - vec_(m4_U*3/2,m4DR`'m4_U*3/2)
     line from Q1.E to DE
     line from QC to DS
     mitre_(DS,DE,Q1.E)
     mitre_(DE,DS,QC)
     Diode: diode(ifinstr(m4Da,P,`from DS to DE',`from DE to DS'))
     point_(hp_ang)')
   ifinstr(m4Da,Z,
    `ifinstr(m4Da,E,,
      `line from QC to QC+vec_(m4_U*3/2,0); corner; C: Here')
     move to Q2.Bulk.c+vec_(0,m4DR`'m4_U)
     line to rvec_(2*m4_U,0) then to rvec_(4.5*m4_U,m4DR`'(-2*m4_U)) \
       then to rvec_(4.5*m4_U,m4DR`'(-2*m4_U-lthick/4))
     Zener: diode(ifinstr(m4Da,P,`to QC+vec_(m4_U*3/2,0)',
      `from QC+vec_(m4_U*3/2,0) to Here'),Z)
     point_(hp_ang)')
   popdef(`dimen_') `$4' ]')

                                `igbt(linespec, L|R, [L][[d]D])
                                 Arg 3: L = 2nd gate type, D = parallel diode,
                                 dD = dotted connections'
define(`igbt',`bi_trans(`$1',`$2',ifinstr(`$3',L,,GH)CBUdE`$3',,`$4')')

                                `Customizable bi_trans(linespec, L|R, chars, E)
                                 chars
                                   BU=bulk line
                                   B=base line and label
                                   uEn|dEn=emitters E0 to En
                                   uE|dE=emitter line
                                   Cn|uCn|dCn=collectors C0 to Cn (arrow u or d)
                                   C|uC|dC=collector line (arrow u or d)
                                   uT|dT=trigger line
                                   uV|dV=trigger line at emitter
                                   G=gate line and location
                                   H=gate line
                                   L=L-gate line and location
                                   S=Schottky
                                   [d]D=named parallel diode, d=connection dots'
define(`bi_trans',
 `define(`m4R',`ifelse(`$2',R,-)')define(`dna_',`ifelse(`$3',,BCuEBU,`$3')')dnl
  define(`m4n',0)define(`m4dE',)dnl
[ ifelse(`$1',,`tr_xy_init(,m4_U,m4R); E: tr_xy(-3,0); C: tr_xy(3,0)',
   `eleminit_(`$1'); tr_xy_init(last line.c,m4_U,m4R)
    E: last line.start; line from E to tr_xy(-3,0) \
        then to tr_xy(-3,0) + vec_( lthick*0.15,m4R`'lthick/3)
    C: E+vec_(rp_len,0); line from C to tr_xy(3,0) \
        then to tr_xy( 3,0) + vec_(-lthick*0.15,m4R`'lthick/3)')
  Bulk: line sc_draw(`dna_',BU,,invis) from tr_xy(-2,4) \
         to tr_xy(2,4)
  sc_draw(`dna_',B,
   `B: tr_xy(0,6.5); line from B to tr_xy(0,4)')
  for_(1,8,1,
   `sc_draw(`dna_',E`'m4x,`define(`m4n',m4x*1.5) define(`m4dE',m4a)
    m4bi_Em(m4x,m4a,E)
    line from tr_xy(-2,4) \
          to tr_xy(-2-m4n,4)
    Bulk: line invis from tr_xy(-2-m4n,4) \
        to Bulk.end')')
  sc_draw(`dna_',E,
   `define(`m4dE',m4a) m4bi_Em(0,m4a,E)')
  for_(1,8,1,
   `sc_draw(`dna_',C`'m4x,`define(`m4n',m4x*1.5)
    m4bi_Em(m4x,m4a,C)
    line from tr_xy(2,4) \
          to tr_xy(2+m4n,4)
    Bulk: line invis from Bulk.start to tr_xy(2+m4n,4)')')
  sc_draw(`dna_',C,
   `m4bi_Em(0,m4a,C)')
  sc_draw(`dna_',S,
   `Bulk: line invis from Bulk.start+ta_xy(-1,0) \
        to Bulk.end+ta_xy(1,0)
    S1: line from Bulk.end+ta_xy(-1,0) \
        to Bulk.end \
      then to Bulk.end+ta_xy(0,-0.5) \
       then to Bulk.end+ta_xy(-0.5,-0.5)
    S2: line from Bulk.start+ta_xy(1,0) \
        to Bulk.start \
      then to Bulk.start+ta_xy(0,0.5) \
       then to Bulk.start+ta_xy(0.5,0.5)')
  sc_draw(`dna_',T,
   `Tm: line from tr_xy(0,4) \
          to tr_xy(2/3,(4 ifelse(m4a,u,+,-)4/1.8*2/3))
    T: Here')
  sc_draw(`dna_',V,
   `Tm: line from tr_xy(0,4) \
          to tr_xy(-2/3,(4 ifelse(m4a,u,+,-)4/1.8*2/3))
    T: Here')
  sc_draw(`dna_',G,
   `G: tr_xy(0,6.5); line from G to tr_xy(0,4.7)')
  sc_draw(`dna_',H,
   `H1: line from tr_xy(-2,4.7) \
          to tr_xy(2,4.7)')
  sc_draw(`dna_',L,
   `G: tr_xy(-1.5,6.2); line from G to tr_xy(-1.5,4.7) \
       then to tr_xy(1.5,4.7)')
  sc_draw(`dna_',D,
   `D1: line from tr_xy(-5,0) \
          to tr_xy(-5,-4)
    D2: line from tr_xy( 5,0) \
          to tr_xy( 5,-4)
    ifelse(m4a,d,`dot(at tr_xy( 5,0)); dot(at tr_xy(-5,0))')
    Diode: diode(ifelse(m4dE,d,from,to) tr_xy(-5,-4) \
                 ifelse(m4dE,d,to,from) tr_xy( 5,-4))
    ifelse(m4dE,d,,rp_ang = rp_ang + pi_)
    ifelse(`$1',,`E: tr_xy(-5,0); line from E to tr_xy(-3,0);
                  C: tr_xy(5,0);  line from C to tr_xy(3,0)')')
  ifinstr(`$4',E,
   `A1: arc ifelse(`$2',R,c)cw from Bulk.end+ta_xy(-2,2.5) \
      to Bulk.end+ta_xy(-2,-5.5) with .c at Bulk.end+ta_xy(-2,-1.5)
    L1: line to Bulk.start+ta_xy(2,-5.5)
    A2: arc ifelse(`$2',R,c)cw to Bulk.start+ta_xy(2,2.5) \
      with .c at Bulk.start+ta_xy(2,-1.5)
    L2: line to Bulk.end+ta_xy(-2,2.5)')
  `$5'; manhattan ] ')
                                `emitters E0 ... En or collectors C0 ... Cn'
define(`m4bi_Em',
   ``$3'`$1': tr_xy(ifelse(`$3',E,-)(3+(`$1')*1.5),0)
    `$3'm`$1': line from `$3'`$1' to tr_xy(ifelse(`$3',E,-)(1.2+(`$1')*1.5),4)
    ifelse(`$2',,,`arrow m4c_l ht m4_Aht wid m4_Awd ifelse(`$2',d,<-) \
      from 1/4 between `$3'm`$1'.start and `$3'm`$1'.end \
      to 3/4 between `$3'm`$1'.start and `$3'm`$1'.end ')
    ifelse(eval(`$1'>0),1,`m4bi_Em(eval(`$1'-1),`$2',`$3')')')

                                `Unijunction transistor ujt(linespec, R,P,E)
                                   Bulk and terminals B1, B2, E defined
                                   arg 2: drawn to the right of curr direction
                                   arg 3: P-channel, default N
                                   arg 4: envelope'
define(`ujt',
`[ ifelse(`$1',,,`eleminit_($1)')
B1: Here
   ifelse(`$1',,,`line to rvec_(rp_len/2-m4_U*2,0)')
   Bl1: line to rvec_(0,ifelse(`$2',R,-)3.5*m4_U)
Bulk: line from rvec_(-m4_U*0.5,0) \
          to rvec_(m4_U*4.5,0)
   Bl2: line from Bulk.end+vec_(-m4_U/2,0) \
      to Bulk.end+vec_(-m4_U/2,ifelse(`$2',R,,-)3.5*m4_U) ifelse(`$1',,,`\
      then to Bulk.c+vec_(rp_len/2,ifelse(`$2',R,,-)3.5*m4_U)')
B2: Here
E:  Bulk.c+vec_(2*m4_U,ifelse(`$2',R,-)3.5*m4_U)
    E1: line from E to Bulk.center
    {arrow m4c_l from last line.ifelse(`$3',P,`end to 1',`start to 7')/8 \
      between last line.start and last line.end wid m4_Awd ht m4_Aht }
    ifelse(`$4',E,dnl
      `Env: circle rad 4*m4_U with .c at Bulk.c')
   `$5'; manhattan ] ')

                        `FETS:     j_fet(linespec, R, P, E )
                                   e_fet(linespec, R, P, E|S )
                                   d_fet(linespec, R, P, E|S )
                                   c_fet(linespec, R, P )
                                   g_fet(linespec, R, P, shade spec )
                                   with terminals S, D, G.
                                   arg 2: G pin drawn to right of curr direction
                                   arg 3: P-channel, default N
                                   arg 4: envelope or simplified'
define(`j_fet',`mosfet(`$1',`$2',ifelse(`$3',P,u,d)GSDF,`$4',`$5')')
                                  `Enhancement-mode FET e_fet(linespec,R,P,S,E)'
define(`e_fet',`mosfet(`$1',`$2',
  ifelse(`$4',S,`TFD'ifelse(`$3',P,u,d)S,`LEDSQ'ifelse(`$3',P,d,u)B),
    `$4',`$5')')
                                  `Depletion-mode FET d_fet(linespec,R,P,S,E)'
define(`d_fet',`mosfet(`$1',`$2',
  ifelse(`$4',S,`TFDR'ifelse(`$3',P,u,d)S,`LFDSQ'ifelse(`$3',P,d,u)B),
    `$4',`$5')')
                                  `Simplified switching c_fet(linespec,R,P)
                                   arg 3: negated G pin'
define(`c_fet',`mosfet(`$1',`$2',`ZSDF'ifelse(`$3',P,d)T,,`$4')')

                                  `Graphene FET g_fet(linespec,R,P,shadespec)'
define(`g_fet',`mosfet(`$1',`$2',ifinstr(`$3',P,d,u)SKTF,`$4',`$5') ')

                                  `Fe_fet(linespec,R,chars) FET with
                                    superimposed ferroelectric symbol:
                                    arg1, arg2, arg3 are as for mosfet'
define(`Fe_fet',`mosfet(`$1',`$2',ifelse(`$3',,SDFT,`$3'),,
  variable(,NN,60,dimen_/3,
    at (0.5 between S and D)+vec_(0,ifelse(`$2',R,-)4*m4_U)); `$4')')

 ` The comprehensive mosfet(linespec,R,BDEFGHKLMPOQRSTXZ,E)
   Every drawn component is controlled by a letter or letter pair in arg 3;
   adding or changing elements is easily done by adding a test for a letter
   or letter sequence. The modifiers u and d are optional:
                               udB: center bulk connection pin; u or d arrow
                                 D: D pin and lead
                                 E: dashed substrate
                                 F: solid-line substrate
                               udG: G pin to substrate at source; u or d arrow
                               udH: G pin to substrate at center; u or d arrow
                                 K: graphene hexagon
                                 L: G pin to channel (kept for compatibility
                                    for now; the same as dM below)
                               udM: G pin to channel center or
                                    u: pin at drain end, d: pin at source end
                               udMn: gates G0 to Gn as above
                               dPy: parallel diode, d=reverse direction
                               dPz: parallel zener diode, d=reverse direction
                                 O: connection dots on parallel diode
                                 Q: connect B pin to S pin
                                 R: thick channel
                               udS: S pin and lead; u or d arrow
                                dT: G pin to center of channel d: not circle
                                 X: XMOSFET terminal
                                 Z: simplified complementary MOS
                                 arg 2: body drawn to right of curr direction
                                 arg 4: envelope'
define(`mosfet',
 `define(`m4R',`ifelse(`$2',R,-)')dnl               right orientation flag
  define(`dna_',`ifelse(`$3',,DSEdMuBQ,`$3')@')dnl
  define(`m4s',ifinstr(dna_,Z,2.5,3.5))dnl          size parameter
  define(`m4hs',2.5)define(`m4hhx',m4hs*sqrt(3))dnl hex side len
  define(`m4K',ifinstr(dna_,K,K))dnl
[ ifelse(`$1',,
   `tr_xy_init(,m4_U,m4R); ifinstr(dna_,K,
     `S: tr_xy(-m4hs,0); D: tr_xy(m4hs,0); W: S; E: D
      tr_xy_init(tr_xy(0,m4hhx/2-m4s),m4_U,m4R)',
     `S: tr_xy(-2,0); D: tr_xy(2,0)') ',
   `eleminit_(`$1'); tr_xy_init(last line.c,m4_U,m4R)
    ifinstr(dna_,K,
     `S: last line.start; D: last line.end;
      W: tr_xy(-m4hs,0); line from S to W
      E: tr_xy( m4hs,0); line from D to E
      tr_xy_init(tr_xy(0,m4hhx/2-m4s),m4_U,m4R)',
     `S: last line.start; line from S to tr_xy(-2,0) \
           then to tr_xy(-2,0)+vec_(0,m4R`'lthick)
      D: S+vec_(rp_len,0); line from D to tr_xy(2,0) \
         then to tr_xy(2,0)+vec_(0,m4R`'lthick)')')
  sc_draw(`dna_',B,
   `B: tr_xy(0,0); Bl: line from B to tr_xy(0,m4s)
    ifelse(m4a,,,`arrow m4c_l ht m4_Aht wid m4_Awd ifelse(m4a,d,<-) \
      from tr_xy(0,m4s/2)-vec_(0,m4R`'m4_Aht/2) \
        to tr_xy(0,m4s/2)+vec_(0,m4R`'m4_Aht/2) ')')
  sc_draw(`dna_',D,
   `Dl: line from tr_xy(2,0) \
          to tr_xy(2,m4s)')
  sc_draw(`dna_',E,
   `Channel: line invis from tr_xy(-2.5,m4s) \
          to tr_xy(2.5,m4s)
    line from tr_xy(-2.5,m4s) \
          to tr_xy(-1,m4s)
    line from tr_xy(-0.5,m4s) \
          to tr_xy(0.5,m4s)
    line from tr_xy(1,m4s) \
          to tr_xy(2.5,m4s)')
  sc_draw(`dna_',F,
   `Channel: line from ifinstr(dna_,Z,
     `tr_xy(-2,m4s) \
          to tr_xy(2,m4s)',
     `tr_xy(-2.5,m4s) \
          to tr_xy(2.5,m4s)')')
  sc_draw(`dna_',G,
   `G: tr_xy(-2,(m4s+3.5))
    ifelse(m4a,,`Gl: line from tr_xy(-2,m4s) \
        to G',
           m4a,d,`Gl: arrow m4c_l from G to tr_xy(-2,m4s) ht m4_Aht wid m4_Awd',
           m4a,u,`Gl: line from tr_xy(-2,m4s) \
        to G; arrow m4c_l ht m4_Aht wid m4_Awd \
             from tr_xy(-2,(m4s+3-m4_Aht/(m4_U))) \
          to tr_xy(-2,(m4s+3))')')
  sc_draw(`dna_',H,
   `G: tr_xy(0,(m4s+4))
    ifelse(m4a,,`Hl: line from tr_xy(0,m4s) \
        to G',
           m4a,d,`Hl: arrow m4c_l from G to tr_xy(0,m4s) ht m4_Aht wid m4_Awd',
           m4a,u,`Hl: line from tr_xy(0,m4s) \
        to G; arrow m4c_l ht m4_Aht wid m4_Awd \
             from tr_xy(0,(m4s+3-m4_Aht/(m4_U))) \
          to tr_xy(0,(m4s+3))')')
  sc_draw(`dna_',K,
   `NW: W+ta_xy( m4hs/2, m4hhx/2)
    SW: W+ta_xy( m4hs/2,-m4hhx/2)
    SE: E+ta_xy(-m4hs/2,-m4hhx/2)
    NE: E+ta_xy(-m4hs/2, m4hhx/2)
    Kl: line from NW \
     to W then to SW then to SE then to E then to NE then to NW `$4'')
  sc_draw(`dna_',L,
   `G: tr_xy(-2,(m4s+3.5))
    Ll: line from tr_xy(2,(m4s+1)) \
          to tr_xy(-2,(m4s+1)) \
          then to G')
  for_(1,4,1,
   `sc_draw(`dna_',M`'m4x,`m4mo_Mm(m4x,m4a,`$4',ifinstr(dna_,Z,2,2.5))')')
  sc_draw(`dna_',M,`ifelse(
    m4a,, `G: tr_xy(0,(m4s+4))
           Glh: line from tr_xy(2,(m4s+1)) \
          to tr_xy(-2,(m4s+1))
           Glv: line from tr_xy(0,(m4s+1)) \
        to G',
    m4a,u,`G: tr_xy(2,(m4s+3.5))
           Gl: line from tr_xy(-2,(m4s+1)) \
          to tr_xy(2,(m4s+1)) \
          then to G',
    m4a,d,`G: tr_xy(-2,(m4s+3.5))
           Gl: line from tr_xy(2,(m4s+1)) \
          to tr_xy(-2,(m4s+1)) \
          then to G')')
  sc_draw(`dna_',Py,`pushdef(`m4pdd_mosfet')')
  sc_draw(`dna_',Pz,`pushdef(`m4pdd_mosfet',Z)')
  ifdef(`m4pdd_mosfet',
   `define(`m4q',m4a)dnl
    Diode: diode(ifelse(m4q,d,to,from) tr_xy(-2,-2) \
                 ifelse(m4q,d,from,to) tr_xy( 2,-2),m4pdd_mosfet)
    ifelse(m4q,d,rp_ang = rp_ang + pi_)
    sc_draw(`dna_',O,`{dot(at tr_xy(-2,0)); dot(at tr_xy(2,0))}') 
    line from tr_xy(-2,0) \
          to tr_xy(-2,-2) \
      then to tr_xy(2,-2) \
      then to tr_xy(2,0)
    popdef(`m4pdd_mosfet')')
  sc_draw(`dna_',Q,
   `Ql: line from tr_xy(0,0)+vec_(0,m4R`'lthick) \
          to tr_xy(0,0) \
      then to tr_xy(-2,0) \
      then to tr_xy(-2,0)+vec_(0,m4R`'lthick)')
  sc_draw(`dna_',R,
   `Rl: line thick 2*linethick from tr_xy(-2,m4s)\
         -vec_(0,m4R`'lthick*3/2) \
          to tr_xy(2,m4s)-vec_(0,m4R`'lthick*3/2) ')
  sc_draw(`dna_',S,`ifelse(m4K,K,
   `Sl: arrow m4c_l ht m4_Aht*2/3 wid m4_Awd \
     from ifelse(m4a,u,NW to W,W to NW)',
   `Sl: line from tr_xy(-2,0) \
          to tr_xy(-2,m4s)
    ifelse(m4a,,,`arrow m4c_l ht m4_Aht wid m4_Awd ifelse(m4a,d,<-) \
      from tr_xy(-2,m4s/2)-vec_(0,m4R`'m4_Aht/2) \
        to tr_xy(-2,m4s/2)+vec_(0,m4R`'m4_Aht/2) ')')')
  sc_draw(`dna_',T,
   `Tl: line from tr_xy(-2,(m4s+1)) \
          to tr_xy(2,(m4s+1))
    ifelse(m4a,d,`Nt: circle rad m4_U*2/3 with .c at tr_xy(0,(m4s+1+2/3))')
    Gl: line from tr_xy(0,`(m4s+1'`ifelse(m4a,d,+4/3))') \
           to tr_xy(0,(m4s+4)); G: Here')
  sc_draw(`dna_',X,dnl          From Matteo Agostinelli
   `B: tr_xy(0,0); Xv: line from B to tr_xy(0,m4s-1)
       Xh: line from tr_xy(-1.5,m4s-1) \
          to tr_xy(1.5,m4s-1)')
  ifelse(`$4',E,`Env: circle rad 4*m4_U with .c at tr_xy(0,m4s)')
  `$5'; manhattan ] ')
define(`m4mo_Mm',dnl                 (m4n,m4a,[E])
 `define(`m4mo_d',`eval((`$1')*2+1)')dnl
  for_(0,`$1',1,
   `define(`m4moc',`ifelse(`$2',u,
     ` (`$4')-`$4'*4*m4x/m4mo_d',`-`$4'+`$4'*4*m4x/m4mo_d')')dnl
    ifinstr(`$3',E,
     `M4moM: move from tr_xy(m4moc,m4s) to tr_xy(m4moc,m4s+1)
      G`'m4x: LCintersect(M4moM,tr_xy(0,m4s),4*m4_U,R)',
     `G`'m4x: tr_xy(m4moc,m4s+4)')
    Gm`'m4x: line from G`'m4x to tr_xy(m4moc,m4s+1) \
      then to tr_xy(m4moc`'ifelse(`$2',u,-,+)2*`$4'/m4mo_d,m4s+1) ') ')

                               `Macro-internal coordinates adjusted for L|R'
define(`ta_xy',`vec_(vscal_(m4_xyU,`$1',ifelse(`$2',0,0,m4_xyS`($2)')))')
                               `Relative adjusted macro-internal coordinates'
define(`tr_xy',`M4_xyO+vec_(vscal_(m4_xyU,`$1',ifelse(`$2',0,0,m4_xyS`($2)')))')
                               `Initialize tr_xy_init(origin,unit,-)'
define(`tr_xy_init',
`M4_xyO: ifelse(`$1',,Here,`$1')
define(`m4_xyU',`$2')dnl
define(`m4_xyS',`$3')')

                               `Extract substring plus preceding char if u or d'
define(`m4_dna',`define(`m4I_',index($1,`$2'))dnl
ifelse(m4I_,-1,`define(`m4t',0)',`define(`m4t',eval(m4I_+len($2)))dnl
define(`m4a',ifelse(substr($1,decr(m4I_),1),u,`define(`m4I_',decr(m4I_))'u,
                    substr($1,decr(m4I_),1),d,`define(`m4I_',decr(m4I_))'d))dnl
define(`$1',substr($1,0,m4I_)`'substr($1,m4t))')')dnl

                               `Conditional subcomponent draw
                                sc_draw(dna string, substring, iftrue, iffalse)'
define(`sc_draw',`m4_dna(`$1',`$2')ifelse(m4I_,-1,`$4',`$3')')

                               `(r|l|c)label( label, label, label,
                                  relative position, block name )
                                Element labels at the start, centre, and end
                                of the last [] block (or a named [] block)
                                in the current direction.  Labels are
                                spaced and treated as math, but copied
                                literally if double quoted or defined
                                by sprintf.
                                Arg4 can be above, below, left, right
                                to supplement the default position.
                                Arg5 is the optional name of a [] block
                                and is last [] by default.'
                               `The hash (pound sign) is used in svg text so
                                we temporarily turn off comments for svg' 
define(`rlabel',`ifsvg(`changecom(,)')dnl
m4label(`$1',`$2',`$3',.s_,below_,`$4',`$5')`'ifsvg(`changecom(`#',)')')

define(`llabel',`ifsvg(`changecom(,)')dnl
m4label(`$1',`$2',`$3',.n_,above_,`$4',`$5')`'ifsvg(`changecom(`#',)')')

define(`clabel',`ifsvg(`changecom(,)')dnl
m4label(`$1',`$2',`$3',,,`$4',`$5')`'ifsvg(`changecom(`#',)')')
                   labels at centre and both ends of an element `dimen_' long
define(`m4label',`dnl
 ifelse(`$1',,,
  `{m4lstring(`$1',"sp_`'iflatex(`$ `$1'$',`$1')`'sp_") \
     at ifelse(`$7',,last [],`$7').w_ $5 rjust_ $6};')dnl
 ifelse(`$2',,,
  `{m4lstring(`$2',"sp_`'iflatex(`$ `$2'$',`$2')`'sp_") \
     at ifelse(`$7',,last [],`$7')$4 $5 $6};')dnl
 ifelse(`$3',,,
  `{m4lstring(`$3',"sp_`'iflatex(`$ `$3'$',`$3')`'sp_") \
     at ifelse(`$7',,last [],`$7').e_ $5 ljust_ $6};')dnl
 ')
                               `dlabel(long,lateral,label,label,label,chars)
                                Labels for oblique or aligned elements
                                long, lateral: dispacement from center
                                    with respect to drawing direction
                                chars:
                                  X displacement is from the centre of the last
                                    line rather than the centre of the last []
                                  L,R,A,B align labels ljust, rjust, above,
                                    or below (absolute) respectively'
define(`dlabel',`ifsvg(`changecom(,)')dnl
 define(`m4long_',`ifelse(`$1',,`dimen_',`($1)')')dnl
 define(`m4lat_',`ifelse(`$2',,`10bp__',`($2)')')dnl
 ifelse(`$3',,,
  `{m4lstring(`$3',"iflatex(`$ `$3'$',` $3')") \
     at last ifinstr(`$6',X,line,[]).c+vec_(-m4long_,m4lat_) \
     ifinstr(`$6',L,ljust,`$6',R,rjust) dnl
     ifinstr(`$6',A,above,`$6',B,below) };') dnl
 ifelse(`$4',,,
  `{m4lstring(`$4',"iflatex(`$ `$4'$',` $4')") \
     at last ifinstr(`$6',X,line,[]).c+vec_(0,m4lat_) \
     ifinstr(`$6',L,ljust,`$6',R,rjust) dnl
     ifinstr(`$6',A,above,`$6',B,below) };') dnl
 ifelse(`$5',,,
  `{m4lstring(`$5',"iflatex(`$ `$5'$',` $5')") \
     at last ifinstr(`$6',X,line,[]).c+vec_(m4long_,m4lat_) \
     ifinstr(`$6',L,ljust,`$6',R,rjust) dnl
     ifinstr(`$6',A,above,`$6',B,below) };') ifsvg(`changecom(`#',)')')

                              `eleminit_( linespec, default length )
                               compute element direction and length.
				               eleminit_ defines the position, length,
				               and angle of two-terminal elements.  It calls
                               rpoint_ with its linespec or circuit-element
                               default. The rpoint_ macro draws the invisible
                               line determined by its argument, calculates the
                               length and angle, and gives the angle to the
                               point_ macro to set the rotation parameters used
                               by vec_ and rvec_.'
define(`eleminit_',
 `rpoint_(ifelse(`$1',,`to rvec_(ifelse(`$2',,`elen_',`$2'),0)',`$1'))')

                              `parallel_(`elementspec', `elementspec', ...
                               Parallel combination of two-terminal elements
                               in a [] block. Each elementspec is quoted and
                               of the form
                               [Sep=val;][Label:] element; [attributes]
                               where an attribute is of the form
                                [llabel(...);]|[rlabel(...);][b_current(...);]
                               Sep=val; in the first branch sets the default
                               separation of all branches to val; in a later
                               element Sep=val; applies only to that branch.
                               An element may have normal arguments but should
                               not change the drawing direction.
                               An argument may also be series_(args) or
                               parallel_(args) without attributes or quotes.
                               example:
                               define(`elen_',dimen_) setdir_(Down)
                               parallel_(
                                 `resistor;llabel(,R);inductor(,W);llabel(,L)',
                                 `capacitor;rlabel(,C)')
'
define(`parallel_',
`[ ifdef(`m4rp_ang',rp_ang = m4rp_ang;) pwid = 0
 stackargs_(`m4parR',$@) stackexec_(`m4parR',`m4parS')dnl
 define(`m4br',0) define(`m4parsep',`m4sepdefault')dnl
 stackdo_(`m4parS',
  `define(`m4pel',m4parS)
   pushkey_(m4pel,Sep,m4parsep)dnl
   ifelse(m4br,0,`define(`m4parsep',m4Sep)')dnl
   ifinstr(m4pel,Sep=,`define(`m4pel',substr(m4pel,eval(index(m4pel,;)+1)))')
   E`'eval(m4br+1): [
     Start: Here
     m4pel
     End: Here
     C: 0.5 between Start and End
     ] ifelse(m4br,0,,`with .C at C`'m4br-vec_(0,m4Sep)')
   define(`m4br',incr(m4br))dnl
   Start`'m4br: E`'m4br.Start; End`'m4br: E`'m4br.End; C`'m4br: E`'m4br.C
   pwid = max(pwid,distance(Start`'m4br,End`'m4br))
   ')
 U: Vdiff_(End1,Start1)
 d = vlength(U.x,U.y); if d==0 then { d=1 } else { d = 1/d }
 Unit: Vsprod_(U,d)
 line from C1-(Vsprod_(Unit,pwid/2)) to C`'m4br-(Vsprod_(Unit,pwid/2)) \
   chop -lthick/2
 Start: last line.c
 line from C1+Vsprod_(Unit,pwid/2) to C`'m4br+Vsprod_(Unit,pwid/2) \
   chop -lthick/2
 End: last line.c; C: 0.5 between Start and End
 for_(1,m4br,1,`
   line from Start`'m4x to C`'m4x-Vsprod_(Unit,pwid/2)
   line from   End`'m4x to C`'m4x+Vsprod_(Unit,pwid/2)')
 ] with .Start at Here; move to last [].End
')

define(`m4sepdefault',`dimen_') `Default separation in the parallel_ macro'
define(`m4lendefault',`dimen_') `Default length in the series_ macro'

                              `series_(elementspec, elementspec, ... )
                               Series combination in a [] block of elements
                               with shortened default length
                               An elementspec is of the form
                                [Label:] element; [attributes]
                               where an attribute is of the form
                                [llabel(...);]|[rlabel(...);][b_current(...);]
                               Internal points Start, End, and C are defined
                               automatically.'
define(`series_',
`[ pushdef(`elen_',m4lendefault)dnl
 stackargs_(`m4serR',$@) stackexec_(`m4serR',`m4serS')dnl
 ifdef(`m4rp_ang',rp_ang = m4rp_ang;) Start: Here
 stackdo_(`m4serS',`m4serS
') End: Here;
 C: 0.5 between Start and End
 popdef(`elen_')] with .Start at Here; move to last [].End
')

                                `reversed(`macro name in quotes', macro args)
                                 reverse polarity of two-terminal element'
define(`reversed',`eleminit_(`$2')
  $1(from last line.end to last line.start,shift(shift($@)))
  rp_ht = -rp_ht; rp_wid = -rp_wid; rp_ang = rp_ang - pi_
  line invis to last line.start ')

                                `resized(factor,`macro name in quotes',args)
                                 multiply element body size by factor'
define(`resized',`pushdef(`dimen_',(dimen_)*(`$1'))dnl
  $2(shift(shift($@))) popdef(`dimen_')')

                                `variable(`element', type, [+|-]angle,
                                   length, at position)
                                 overlaid arrow or line on two-terminal element
                                 to show variablility:
                                 type = [A|P|L|[u]N|[u]NN][C|S]
                                 A=arrow; P=preset; L=linear; N=nonlinear;
                                 NN=symmetric nonlinear, u changes direction;
                                 C=continuous; S=setpwise.
                                 If arg3 begins with + or -, then the argument
                                 (typically -45) is relative to the current
                                 drawing angle. If arg5 is blank the symbol
                                 is placed over the last []'
define(`variable',`$1
 {[ define(`dna_',ifelse($2,,A,$2)`')define(`m4sgn',regexp(`$3',^ *[+-]))dnl
   ang = ifelse(m4sgn,-1,,rp_ang*rtod_) ifelse(`$3',,45,`$3')
   define(`m4a2',`ifelse(m4sgn,0,rp_ang-pi_/2,0)') dnl
   define(`m4a3',`ifelse(m4sgn,0,rp_ang,pi_/2)') dnl
   define(`m4tip',`dimen_/8')dnl
   T: (Rect_(ifelse(`$4',,`dimen_*0.8',`$4'),ang))
   sc_draw(`dna_',P,`Line: line to T; C: Line.c
     [line to (Rect_(m4tip,ang-90))] at Line.end')
   sc_draw(`dna_',L,`Line: line to T; C: Line.c')
   sc_draw(`dna_',NN,`C: 1/2 between Here and T
     ifelse(m4a,u,`Line: line  from Here+(rect_(-m4tip,m4a3)) to Here \
                     then to T then to T+(rect_( m4tip,m4a3))',
                  `Line: line from  Here+(rect_(-m4tip,m4a2)) to Here \
                     then to T then to T+(rect_( m4tip,m4a2))')')
   sc_draw(`dna_',N,`C: 1/2 between Here and T
     ifelse(m4a,u,`Line: line to T then to T+(rect_(m4tip,m4a3))',
                  `Line: line from T to Here \
                    then to Here+(rect_(-m4tip,m4a2))')')
   sc_draw(`dna_',A,`Line: arrow to T; C: Line.c')
   sc_draw(`dna_',C,`move to T+(dimen_*0.10,-dimen_*0.06)
     line to Here+(Rect_(m4tip,ang))')
   sc_draw(`dna_',S,`move to T+(dimen_*0.10,-dimen_*0.12)
     line up dimen_*0.06 then right dimen_*0.12 then up dimen_*0.06')
   `$6'] with .C ifelse(`$5',,at last [].c,`$5') } ')

                                `Line hopping over named ordered lines,
                                 diverting left or right:
                                crossover(linespec,
                                  [L|R][:line attributes],
                                  line_name,line_name,...)
                                attributes are outlined "color" dotted ...
                                #define(`hoprad_',`dimen_/12')'
define(`crossover',`eleminit_(`$1')
  define(`m4attribs',ifinstr(`$2',:,`patsubst(`$2',^.*:)'))dnl
  define(`m4divert',`patsubst(`$2',:.*)')dnl
  define(`m4_lt2',`ifelse(ifpstricks(T)`'ifmpost(T)`'ifpgf(T)`'ifsvg(T),T,
   `hlth',0)')dnl
  M4Start: last line.start; M4End: last line.end
  Loopover_(`M4',`line m4attribs to intersect_(M4Start,M4End,M4.start,M4.end) \
      chop 0 chop hoprad_-m4_lt2
    ifelse(`m4_lt2',0,,`move to rvec_(-m4_lt2,0)')
    arc m4attribs ifelse(m4divert,R,c)cw to rvec_(2*hoprad_,0) \
      with .c at rvec_(hoprad_,0)
    ifelse(`m4_lt2',0,,`move to rvec_(-m4_lt2,0)')', shift(shift($@)))
  line m4attribs to M4End ')

                                `NPDT(npoles,chars) Double throw switch
                                 chars:
                                   R = right orientation'
define(`NPDT',`[define(`m4np',`ifelse(`$1',,1,`$1')')dnl
define(`m4xR',ifinstr(`$2',R,R))define(`m4SR',ifelse(m4xR,R,-))dnl
  for_(1,m4np,1,
   `{ L`'ifelse(eval(m4np>1),1,m4x): dot(at rvec_(-dimen_/3,0),,1) }
    { X: Here
      T`'ifelse(eval(m4np>1),1,m4x): circle invis rad dotrad_ at X
      lswitch(from X to X+vec_(dimen_/3,0),m4xR,D)
      R`'ifelse(eval(m4np>1),1,m4x): circle invis rad dotrad_ at Here }
    ifelse(eval(m4x<m4np),1,`move to rvec_(0,m4SR`'dimen_/2)') ')
  ifelse(eval(m4np>1),1,`move to vec_(dimen_/6,m4SR`'dimen_/10)
    DL: line dashed to rvec_(0,m4SR`'(m4np-3/4)*dimen_/2)') 
`$3']')


                                `relay(npoles,chars,attributes)
                                 arg1: Number of poles (max 10)
                                 chars:
                                   any of the relaycoil options and:
                                   O = normally open
                                   C = normally closed
                                   P = three-position
                                   none of above = double-throw (default)
                                   L = drawn left (default)
                                   R = drawn to right of drawing direction
                                   Th = thermal '
define(`relay',`[ define(`m4pm',`ifinstr(`$2',R,-)')dnl
  Coil: relaycoil(`$2',,,,`$3') define(`m4rel',rcdna_)
  V1: Coil.V1
  V2: Coil.V2
  sc_draw(m4rel,Th,
   `{move to Coil #rvec_(-dimen_/8,0)
    line from rvec_(-dimen_/20,dimen_/6) \
    to rvec_(-dimen_/20,dimen_/20) \
      then to rvec_(dimen_/20,dimen_/20) \
    then to rvec_(dimen_/20,-dimen_/20) \
      then to rvec_(-dimen_/20,-dimen_/20) \
    then to rvec_(-dimen_/20,-dimen_/6)}')
  Cs: contacts(ifelse(`$1',,1,`$1'),D`'m4rel) with .O1 at Coil.B2 + \
     vec_(ifinstr(m4rel,P,-dimen_/5,0)+dimen_/4,m4pm`'(dimen_/4+dimen_/5))
  for_(1,ifelse(`$1',,1,`$1'),1,
   `P`'m4x: Cs.P`'m4x
    C`'m4x: Cs.C`'m4x
    O`'m4x: Cs.O`'m4x')
  `$4'] ')

                                `contacts(npoles,chars)
                                 chars:
                                   P= three position
                                   O|C= normally open, normally closed (default)
                                   R= right orientation (default left)
                                   I= open circles for contacts
                                   T= T contacts
                                   U= U contacts
                                   D= dashed line across armatures'
                                `e.g. contacts(1,5,O)'
define(`contacts',`[
  define(`m4np',`ifelse(`$1',,1,`$1')')dnl
  ifelse(eval(m4np>10),1,`define(`m4np',10)')dnl
  for_(1,m4np,1,
   `K`'m4x: contact(`$2') with .O at Here
    P`'m4x: circle invis rad dotrad_ at last [].P
    C`'m4x: last [].C
    O`'m4x: last [].O
    ifelse(m4x,m4np,,`move to last[].C+vec_(0,m4pm dimen_/4)')')
  ifelse(eval(m4np>1),1,`ifinstr(`$2',D,
   `DL: line dashed from K1.A.c to K`'m4np.A.c chop -dimen_/10')')
  `$3'] ')

                                `contact(chars [,R]) Relay contact switch
                                 Arg 2 deprecated, kept for compatibility
                                 chars:
                                  O|C= normally open, normally closed (default)
                                  I= open dots for contacts
                                  X= filled dots
                                  P= three position
                                  R= right orientation (default left)
                                  T= T contacts
                                  U = line contact'
define(`contact',`[ dnl
  define(`m4pm',`ifelse(ifinstr(`$1',R,R,`$2',R,R),R,-)')dnl
  define(`m4dr',`dotrad_')define(`m4TL',dimen_/12)dnl
  define(`m4fll',`ifinstr(`$1',X,,1)')dnl
  P: dot(,m4dr,m4fll)
  T: P+vec_(dimen_/2-dimen_/12,0)
  ifinstr(`$1',P,`ifinstr(
  `$1',I,
   `{C: dot(at T+vec_(0,m4pm`'(dimen_/8+m4dr*2+lthick/2)),m4dr,m4fll)}
    {O: dot(at T-vec_(0,m4pm`'(dimen_/8+m4dr*2+lthick/2)),m4dr,m4fll)}
    A: line from P to ifinstr(
     `$1',O,`(LCtangent(P,O,dotrad_+lthick/2)) chop m4dr chop -m4dr',
     `$1',C,`(LCtangent(P,C,dotrad_+lthick/2,R)) chop m4dr chop -m4dr',
     `P+vec_(dimen_/2,0) chop m4dr chop 0')',
  `$1',U,
   `{C: T+vec_(m4TL*2,m4pm`'(dimen_/6))
     line from C to C-vec_(2*m4TL,0)}
    {O: T+vec_(m4TL*2,m4pm`'(-dimen_/6))
     line from O to O-vec_(2*m4TL,0)}
    A: line from P to ifinstr(
     `$1',O,`O-vec_(2*m4TL-dimen_/27,0) chop m4dr chop -m4dr',
     `$1',C,`C-vec_(2*m4TL-dimen_/27,0) chop m4dr chop -m4dr',
     `P+vec_(dimen_/2,0) chop m4dr chop 0')',
  `$1',T,
   `{CC: T+vec_(0,m4pm`'(dimen_/8+m4TL*2/3))
     C: line from CC+vec_(0,-m4TL) to CC+vec_(0,m4TL) } 
    {OO: T-vec_(0,m4pm`'(dimen_/8+m4TL*2/3))
     O: line from OO+vec_(0,-m4TL) to OO+vec_(0,m4TL) } 
     A: line from P to ifinstr(
      `$1',O,`1/6 between O.end and O.start chop m4dr chop -m4dr',
      `$1',C,`1/6 between C.start and C.end chop m4dr chop -m4dr',
      `P+vec_(dimen_/2,0) chop m4dr chop 0')',
   `{AC: arrow m4c_l <- ht dimen_/6 wid dimen_/6 \
      from T+vec_(0,m4pm`'dimen_/8) to T+vec_(0,m4pm`'dimen_*3/8) \
      then to T+vec_(dimen_/5,m4pm`'dimen_*3/8)
     C: Here}
    {AO: arrow m4c_l <- ht dimen_/6 wid dimen_/6 \
      from T-vec_(0,m4pm`'dimen_/8) to T+vec_(0,-(m4pm`'dimen_*3/8)) \
      then to T+vec_(dimen_/5,-(m4pm`'dimen_*3/8))
     O: Here}
    A: line from P to ifinstr(
     `$1',O,`AO.start chop m4dr chop -m4dr',
     `$1',C,`AC.start chop m4dr chop -m4dr',
     `P+vec_(dimen_/2,0) chop m4dr chop 0')') ', # end of P
   `A: line from P to P+vec_(dimen_/2,0) chop m4dr chop 0
    define(`m4CO',
     `ifinstr(`$1',C,`ifinstr(`$1',O,O)C',`ifinstr(`$1',O,O,OC)')')dnl
    ifinstr(m4CO,C,
    `move to T
     ifinstr(
     `$1',I,
      `{ C: dot(at rvec_(0,m4pm`'(m4dr+lthick/2)),m4dr,m4fll) }
       ifinstr(m4CO,O,,`O: Here')',
     `$1',U,
      `{C: T+vec_(m4TL*2,m4pm`'(dimen_/6))
       line from C to C-vec_(2*m4TL,0)}
       ifinstr(m4CO,O,,`O: Here')',
     `$1',T,
      `CC: rvec_(0,m4pm`'(m4TL*2/3))
       { C: line from CC+vec_(0,-m4TL) to CC+(0,m4TL) }
       ifinstr(m4CO,O,,`O: T') ',
     `{AC: arrow m4c_l <- ht dimen_/6 wid dimen_/6 \
       to rvec_(0,m4pm`'dimen_/4) \
       then to rvec_(dimen_/5,m4pm`'dimen_/4)
      C: Here }
      O:rvec_(dimen_/5,0)') ')
    ifinstr(m4CO,O,
    `move to T+vec_(0,-(m4pm`'dimen_/8))
     ifinstr(
     `$1',I,
      `{O: dot(at rvec_(0,m4pm`'(-m4dr*2)),m4dr,m4fll) }
       ifinstr(m4CO,C,,`C: T ')',
     `$1',U,
      `{O: T+vec_(m4TL*2,m4pm`'(-dimen_/6))
       line from O to O-vec_(2*m4TL,0)}
       ifinstr(m4CO,C,,`C: T ')',
     `$1',T,
      `{ OO: (rvec_(0,m4pm`'(-m4TL*2/3)))
       O: line from OO+vec_(0,-m4TL) to OO+vec_(0,m4TL)}
       ifinstr(m4CO,C,,`C: T ')',
     `{AO: arrow m4c_l <- ht dimen_/6 wid dimen_/6 \
       to rvec_(0,-(m4pm`'dimen_/4)) \
       then to rvec_(dimen_/5,-(m4pm`'dimen_/4))
       O: Here }
       ifinstr(m4CO,C,,`C: T+vec_(dimen_/5,0)') ') ')
    ')
 `$3'] ')

                            `relaycoil( chars, wid, ht, U|D|L|R|degrees,
                              attributes )
                             chars: (see IEC 60617 S00305 - S00319)
                              X or default: external lines from A2 and B2
                              AX external lines at positions A1,A3
                              BX external lines at positions B1,B3
                              NX no lines at positions A1,A2,A3,B1,B2,B3
                              SO slow operating
                              SOR slow operating and release
                              SR slow release
                              S  diagonal slash
                              HS high speed
                              NAC unaffected by AC current
                              AC AC current
                              ML mechanically latched
                              MR mechanically resonant
                              PC pulse counter
                              PO polarized
                              RM remanent
                              RH remanent
                              TH thermal
                              EL electronic'
define(`relaycoil',`[ ifelse(`$4',,,`setdir_(`$4')')
 define(`m4wd',ifelse(`$2',,`dimen_/4',`($2)'))dnl 
 define(`m4ht',ifelse(`$3',,`dimen_/2',`($3)'))dnl
 define(`m4LL',`ifinstr(`$4',NX,0,dimen_/3)')dnl
 define(`rcdna_',ifinstr(`$1',AX,,`$1',BX,,`$1',X,,X)`$1')dnl
 { lbox( m4wd, m4ht, `$5' ) }
 { A1: rvec_(0,m4ht/4)
   A2: Here; V1: A2
   A3: rvec_(0,-m4ht/4) }
 { B1: rvec_(m4wd,m4ht/4)
   B2: rvec_(m4wd,0); V2: B2
   B3: rvec_(m4wd,-m4ht/4) }
   sc_draw(`rcdna_',AX,
    `{ line from A1 to A1+vec_(-dimen_/3,0); V1: Here
       line from A3 to A3+vec_(-dimen_/3,0); V2: Here }')
   sc_draw(`rcdna_',BX,
    `{ line from B1 to B1+vec_( dimen_/3,0); V1: Here
       line from B3 to B3+vec_( dimen_/3,0); V2: Here }')
   sc_draw(`rcdna_',NX)
   sc_draw(`rcdna_',X,
    `{ line to rvec_(-dimen_/3,0); V1: Here
      move to B2; line to rvec_(dimen_/3,0); V2: Here }')
   sc_draw(`rcdna_',SOR,
    `{ move to rvec_(0,-(m4ht*5/8)); {lbox(m4wd,m4ht/4)}
       {line from rvec_(0,-m4ht/8) to rvec_(m4wd, m4ht/8)}
       {line from rvec_(0, m4ht/8) to rvec_(m4wd,-m4ht/8)}
       {move to rvec_(0,-(m4ht)*3/8); m4fshade(0,lbox(m4wd,m4ht/4))}
       {move to rvec_(0,-(m4ht)/8)
        {line to rvec_(0,-m4ht/8)}
        {line from rvec_(m4wd,0) to rvec_(m4wd,-m4ht/8)}} }')
   sc_draw(`rcdna_',SO,
    `{ move to rvec_(0,-(m4ht*5/8)); {lbox(m4wd,m4ht/4)}
       {line from rvec_(0,-m4ht/8) to rvec_(m4wd, m4ht/8)}
       {line from rvec_(0, m4ht/8) to rvec_(m4wd,-m4ht/8)} }')
   sc_draw(`rcdna_',SR,
    `{ move to rvec_(0,-(m4ht*5/8)); m4fshade(0,lbox(m4wd,m4ht/4)) }')
   sc_draw(`rcdna_',HS,
    `{ move to rvec_(0,-(m4ht*5/8)); lbox(m4wd,m4ht/4) }
     { move to rvec_(m4wd/2,-(m4ht/2)); line to rvec_(0,-m4ht/4)} ')
   sc_draw(`rcdna_',S,
    `{ line from rvec_(0,m4ht/2) to rvec_(m4wd,-m4ht/2)}')
   sc_draw(`rcdna_',NAC,
    `{ m4fshade(0,lbox(m4wd/4,m4ht)) }
     { move to rvec_(m4wd*3/4,0); m4fshade(0,lbox(m4wd/4,m4ht)) } ')
   sc_draw(`rcdna_',AC,
    `{ move to rvec_(0,-(m4ht*3/4)); { lbox(m4wd,m4ht/2) }
       move to rvec_(m4wd/2,0)
       ifgpic(
        `arc rad m4wd/3 cw from Here-(m4wd*2/3,0) \
         to Here with .c at Here-(m4wd/3,0)
         arc rad m4wd/3 ccw from Here to Here+(m4wd*2/3,0) with .c \
           at Here+(m4wd/3,0)',
        ` sinusoid(m4wd/3,twopi_/(m4wd*2/3),pi_/2,-m4wd/3,m4wd/3) \
           with .Origin at Here ') }')
   sc_draw(`rcdna_',ML,
    `{ move to rvec_(0,-(m4ht*11/16)); { lbox(m4wd,m4ht*3/8) }
       line from rvec_(0,m4ht*3/16) to rvec_(m4wd/2,-m4ht*3/16) \
         then to rvec_(m4wd,m4ht*3/16) } ')
   sc_draw(`rcdna_',MR,
    `{ move to rvec_(m4wd/2,m4ht/2)
       { m4tmp = rp_ang; dashline(to rvec_(0,m4ht*3/4),,m4ht*3/16,m4ht*3/32)
         point_(m4tmp)}
       move to rvec_(0,m4ht*3/8)
       ifgpic(
        `arc rad m4wd/2 cw from rvec_(-m4wd/2,0) \
         to Here with .c at rvec_(-m4wd/4,-m4wd/4)
         arc rad m4wd/2 ccw from Here to rvec_(m4wd/2,0) with .c \
           at rvec_(m4wd/4,m4wd/4)',
        `sinusoid(m4wd/6,twopi_/(m4wd),pi_/2,-m4wd/2,m4wd/2) \
           with .Origin at Here ') } ')
   sc_draw(`rcdna_',PC,
    `{ move to rvec_(0,m4ht/2+m4wd/2)
       { lbox(m4wd,m4wd) }
       circle diam m4wd/2 at rvec_(m4wd/2,0) } ')
   sc_draw(`rcdna_',PO,
    `{ move to rvec_(0,-(m4ht*5/8)); { lbox(m4wd,m4ht/4) }
       m4fshade(0, line to rvec_(0,m4ht/8) \
                then to rvec_(m4wd,m4ht/8) \
                then to rvec_(m4wd,-m4ht/8) \
                then to rvec_(m4wd*3/4,-m4ht/8) \
                then to rvec_(m4wd*3/4,0) \
                then to rvec_(m4wd/4,0) \
                then to rvec_(m4wd/4,-m4ht/8) \
                then to rvec_(0,-m4ht/8) \
                then to Here) } ')
   sc_draw(`rcdna_',RM,
    `{ move to rvec_(0,-(m4ht*5/8)); { lbox(m4wd,m4ht/4) }
       line from rvec_(0,m4ht/8) to rvec_(m4wd,-m4ht/8) }')
   sc_draw(`rcdna_',RH,
    `{ move to rvec_(0,-(m4ht*11/16)); { lbox(m4wd,m4ht*3/8) }
       line from rvec_(m4wd/4,m4ht/8) \
         to rvec_(m4wd/4,m4ht/32) \
         to rvec_(m4wd*3/4,-m4ht/32) \
         to rvec_(m4wd*3/4,-m4ht/8) }')
   sc_draw(`rcdna_',TH,
    `{  line to rvec_(m4wd/4,0) then to rvec_(m4wd/4,m4ht/4) \
        then to rvec_(m4wd*3/4,m4ht/4) \
        then to rvec_(m4wd*3/4,0) \
        then to rvec_(m4wd,0) }')
   sc_draw(`rcdna_',EL,
    `{ { line from rvec_(m4wd/4,0) to rvec_(m4wd*3/4,0) }
       { line from rvec_(m4wd*3/8,0) to rvec_(m4wd*3/16,m4ht*3/16) }
       { line from rvec_(m4wd*5/8,0) to rvec_(m4wd*13/16,m4ht*3/16) }
       { line from rvec_(m4wd/2,0) to rvec_(m4wd/2,-m4ht/4) } }')
   `$6'] ')

                                `reed(linespec,wid,ht,box attributes,[R][C])
                                 Enclosed two-terminal reed contact;
                                 R=right orientation;
                                 C=closed;
                                 e.g. reed(,,dimen_/5,shaded "lightgreen"'
define(`reed',`eleminit_(`$1')
   define(`m4wd',ifelse(`$2',,`dimen_*0.8',`($2)'))dnl
   define(`m4ht',ifelse(`$3',,`dimen_*0.3',`($3)'))dnl
   define(`m4ng',`ifinstr(`$5',R,-)')dnl
   {line to rvec_(max(0,rp_len/2-m4wd/2),0)
    {rotbox(m4wd,m4ht,$4,r=m4ht/2)}
    {line to rvec_(m4wd*0.2,0) then to \
      rvec_(m4wd*0.6,m4ng`'ifinstr(`$5',C,lthick,m4ht/3))} 
    line from rvec_(m4wd*0.5,0) to rvec_(m4wd,0)
    line to rvec_(max(0,rp_len/2-m4wd/2),0)}
  {[box invis ht_ m4ht wid_ m4wd] at rvec_(rp_len/2,0)}
   line to rvec_(rp_len,0) invis ')

                     `ccoax(at location,M|F,diameter,attributes)'
define(`ccoax',`[define(`m4cd',ifelse(`$3',,`dimen_*0.4',`$3'))dnl
  S: circle diam m4cd `$4'
  C: circle diam m4cd/3 fill_(ifinstr(`$2',F,1,0)) at S
  `$5'] with .c ifelse(`$1',,`at Here',`$1')')

                          `tconn( linespec, chars|keys, wid)
                           terminal connector with head in a [] block
                           chars:
                             O=node (circle); OF=filled circle
                             > (default) | >> | < | << | A | AA | M
                             A or AA signify arc or double arc
                             M signifies male bar contact
                             arg3 is head width or circle diam
                           keys:
                             type=chars as above;
                             wdth=expr; head width;
                             lgth=expr; type M head length;
                             sep=expr; double head separation
                             head=attributes; except lgth, wdth'
define(`tconn',`eleminit_(`$1',dimen_*3/4)
  pushkeys_(`$2',
   `type:m4typ:N; lgth:m4nl; wdth:dimen_/6; sep:dimen_/8; head::N')
  ifelse(m4type,m4typ,`poppushdef(`m4type',ifelse(`$2',,>,`$2'))')dnl
  ifelse(m4lgth,(m4nl),`poppushdef(`m4lgth',ifelse(`$3',,(dimen_/2),`($3)/2'))')
 M4Ss: last line.start;  M4Se: last line.end
 ifelse(ifinstr(m4type,0,O,`ifinstr(m4type,OF,O,m4type)'),O,
   `{popdef(`m4wdth')pushdef(`m4wdth',ifelse(`$3',,dimen_/5,`$3'))dnl
     line to last line.end chop 0 chop m4wdth
    [circle diam m4wdth ifinstr(m4type,OF,`fill_(0)') m4head] \
     at rvec_(m4wdth/2,0)}',
 m4type,AA,
   `{line to last line.end chop 0 chop m4sep+m4wdth
    [{A: arc from rvec_(0,m4wdth) to rvec_(0,-m4wdth) with .c at Here m4head}
     arc from rvec_(m4sep,m4wdth) to rvec_(m4sep,-m4wdth) \
        with .c at rvec_(m4sep,0) m4head] with .A.c at rvec_(m4wdth,0) }',
 m4type,A,
   `{line to last line.end chop 0 chop m4wdth
    [A:arc from rvec_(0,m4wdth) to rvec_(0,-m4wdth) with .c at Here m4head] \
      with .A.c at rvec_(m4wdth,0) }',
 m4type,<<,
   `{line to last line.end chop 0 chop m4sep+m4wdth
    [S: Here; {line from rvec_(m4wdth,m4wdth) to S \
       then to rvec_(m4wdth,-m4wdth) m4head}; move to rvec_(m4sep,0)
     line from rvec_(m4wdth,m4wdth) to Here then to rvec_(m4wdth,-m4wdth) \
       m4head ] with .S at Here }',
 m4type,<,
   `{line to last line.end chop 0 chop m4wdth
    [S: Here; line from rvec_(m4wdth,m4wdth) to S \
       then to rvec_(m4wdth,-m4wdth) m4head] with .S at Here }',
 m4type,>>,
   `{line to last line.end chop 0 chop m4sep
    [S: Here; {line from rvec_(-m4wdth,m4wdth) to S \
       then to rvec_(-m4wdth,-m4wdth) m4head}; move to rvec_(m4sep,0)
     line from rvec_(-m4wdth,m4wdth) to Here then to rvec_(-m4wdth,-m4wdth) \
       m4head ] with .S at Here }',
 m4type,M,
   `{line to last line.end chop 0 chop m4lgth
    [ S: Here; NW: rvec_(0,m4wdth/2); SW: rvec_(0,-m4wdth/2)
      NE: rvec_(m4lgth,m4wdth/2); SE: rvec_(m4lgth,-m4wdth/2)
      L: line thick 0 to NW then to NE then to SE then to SW then to Here \
        ifelse(m4head,,fill_(0),m4head) ] with .S at Here}',
 `{line to last line.end
  [S: Here; line from rvec_(-m4wdth,m4wdth) to S \
     then to rvec_(-m4wdth,-m4wdth) m4head ] with .S at Here }')
  line invis to M4Se popdef(`m4type',`m4lgth',`m4wdth',`m4sep',`m4head') ')

                          `Pconn( [-]n, U|D|L|R|degrees[:length], chars|keys )
                           Multiple tconn connectors named T1 to Tn
                             in a [ ] block
                           Negative arg1: reverses contact pin numbers
                             n to 1 instead of 1 to n
                           chars as for tconn:
                             O=node (circle); OF=filled circle
                             > (default) | >> | < | << | A | AA | M
                             A or AA signify arc or double arc
                             M signifies male bar contact
                           keys as for tconn (plus pitch=):
                             type=chars as above;
                             wdth=expr; head width
                             lgth=expr; type M head length
                             sep=expr; double head separation
                             head=attributes; except lgth, wdth
                             pitch=expr; pin separation'
define(`Pconn',`[
  pushkeys_(`$3', `type:m4typ:N; lgth:dimen_/2; wdth:dimen_/6;
    sep:dimen_/8; head::N; pitch:m4`'wdth*2')
  ifelse(m4type,m4typ,`poppushdef(`m4type',ifelse(`$3',,M,`$3'))')dnl
  setdir_(patsubst(`$2',:.*)) pushdef(`m4pinlen',`regexp(`$2',:\(.*\),\1)')dnl
  pushdef(`m4m',`ifelse(index(`$1',-),0,-)')dnl
  pushdef(`m4nn',`ifelse(`$1',,2,index(`$1',-),0,neg_(`$1'),`$1')')dnl
  for_(1,m4nn,1,`T`'m4x: tconn(ifelse(m4pinlen,,,to rvec_(m4pinlen,0)),
    ifinstr(`$3',=,`$3',m4type))
   ifelse(m4x,m4nn,,`move to T`'m4x.start-vec_(0,m4m`'m4pitch)') ')
  popdef(`m4type',`m4lgth',`m4wdth',`m4sep',`m4head',`m4pitch',`m4m',`m4nn',
   `m4pinlen') ]')

                          `tbox( text,wid,ht,<|>|<>,attributes )
                           Pointed terminal box.
                           text is placed at centre of rectangle in math mode
                           unless it starts with a double quote or sprintf
                           arg4= > point on right end (default)
                                 < point on left end; <> both ends
                           Defaults: wid dimen_*2/3 ht dimen_/3 
                           type= eg dotted outlined "red"
                           eg tbox(`$V_2$', 30pt__, 15pt__,,fill_(0.9) )' 
define(`tbox',`[ define(`m4td',`ifelse(`$4',,>,`$4')')
  pushdef(`m4tw2',`ifelse(`$2',,(dimen_*0.4),`(($2)/2)')')dnl
  pushdef(`m4th2',`ifelse(`$3',,(dimen_/6),`(($3)/2)')')dnl
  N: vec_(0,m4th2)
  NE: N+vec_(m4tw2 ifinstr(m4td,>,-m4th2),0)
  E: vec_(m4tw2,0)
  SE: NE+vec_(0,-m4th2*2)
  NW: N-vec_(m4tw2 ifinstr(m4td,<,-m4th2),0)
  W: vec_(-m4tw2,0)
  SW: NW+vec_(0,-m4th2*2)
  C: 0.5 between SW and NE
  line from N to NE ifinstr(m4td,>,then to E) then to SE \
    then to SW ifinstr(m4td,<,then to W) then to NW then to N `$5'
  move to C
  ifelse(`$1',,,`m4lstring(`$1',`"iflatex(`$ `$1'$',` $1')"')')
  `$6' popdef(`m4th2') popdef(`m4tw2') ]')

                          `pconnex(R|L|U|D|degrees,chars,attributes)
                           arg1: drawing direction
                           chars:
                            R: right orientation
                            M|F: male, female
                            A[B]|AC: 115V 3-prong, B=box (default), C=circle
                            P: PC connector
                            D: 2-pin connector
                            G[B]|GC: 3-pin, B=default, C=circle
                            J: 110V 2-pin '
define(`pconnex',
 `[ define(`m4sgn',ifinstr(`$2',F,,-))define(`m4R_',ifinstr(`$2',R,-))dnl
  setdir_(`$1')
  define(`m4na_',`ifelse(`$2',,A,`$2')')dnl
  ifinstr(m4na_,A,`
    Base: ifinstr(m4na_,AC,`circle diam dimen_ `$3'',
              `[lbox(dimen_,dimen_,`$3') ]')
    N: m4pconpin(dimen_/12,dimen_*0.3,m4na_) \
          at Base+vec_(m4sgn`'(-dimen_*0.2),m4R_`'dimen_*0.15)
    H: m4pconpin(dimen_/12,dimen_*0.25,m4na_) \
          at Base+vec_(m4sgn`'(dimen_*0.2),m4R_`'dimen_*0.15)
    gd = dimen_/12
    G: [ifelse(ifgpic(T)`'ifinstr(m4na_,F,,T),TT,
        `circle fill_(m4fill) rad gd at vec_(0,m4R_`'gd/2)
         box fill_(m4fill) wid 2*gd ht gd at vec_(0,0)',
        `arc ifinstr(m4na_,R,,c)cw rad gd from vec_(gd,m4R_`'gd/2) \
           to vec_(-gd,m4R_`'gd/2) with .c \
           at vec_(0,m4R_`'gd/2) ifinstr(m4na_,F,,
            `ifdef(`r_',`shaded rgbstring(r_,g_,b_)',`fill_(m4fill)')')
         line from vec_(-gd,m4R_`'gd/2) \
            to vec_(-gd,m4R_`'(-gd/2)) \
            then to vec_(gd,m4R_`'(-gd/2)) \
            then to vec_(gd,m4R_`'gd/2) ifinstr(m4na_,F,,
             `ifdef(`r_',`shaded rgbstring(r_,g_,b_)',`fill_(m4fill)')')')
         ] at Base+vec_(0,m4R_`'(-dimen_*0.25))',
  m4na_,P,
   `wd = dimen_; hd = wd*3/4
    Base: [line to vec_(-wd/2,0) \
      then to vec_(-wd/2,-hd*2/3) \
      then to vec_(-wd/2+hd/3,-hd) \
      then to vec_(wd/2-hd/3,-hd) \
      then to vec_(wd/2,-hd*2/3) \
      then to vec_(wd/2,0) \
      then to Here `$3']
    N: m4pconpin(dimen_/12,dimen_*0.25,m4na_) \
          at Base+vec_(m4sgn`'(-dimen_*0.2),m4R_`'dimen_*0.15)
    H: m4pconpin(dimen_/12,dimen_*0.25,m4na_) \
          at Base+vec_(m4sgn`'(dimen_*0.2),m4R_`'dimen_*0.15)
    G: m4pconpin(dimen_/12,dimen_*0.20,m4na_) \
          at Base+vec_(0,m4R_`'(-dimen_*0.15))',
  m4na_,D,
   `wd = dimen_*1.2; hd = wd/2
    Base: [rotbox(wd,hd,,r=hd/2,`$3')]
    H: m4pcrpin(dimen_/6,m4na_) at Base.c+vec_( (wd-hd)/2,0)
    N: m4pcrpin(dimen_/6,m4na_) at Base.c+vec_(-(wd-hd)/2,0)',
  m4na_,G,
   `wd = dimen_*1.3; hd = dimen_*1.2
    Base: ifinstr(m4na_,GC,`circle diam wd',
     `[line to vec_(wd/2,0) \
      then to vec_(wd/2,-hd*0.3) \
       then to vec_(hd*0.15,-hd) \
      then to vec_(-hd*0.15,-hd)\
       then to vec_(-wd/2,-hd*0.3) \
      then to vec_(-wd/2,0) \
      then to Here ]')
    H: m4pconpin(dimen_*0.25,dimen_/8,m4na_) \
         at Base.c+vec_(-dimen_/3,dimen_*0.3)
    N: m4pconpin(dimen_*0.25,dimen_/8,m4na_) \
         at Base.c+vec_( dimen_/3,dimen_*0.3)
    G: m4pconpin(dimen_/8,dimen_*0.25,m4na_) \
         at Base.c+vec_(0,-dimen_/3)',
  m4na_,J,
   `wd = dimen_; hd = wd/2
    Base: [line to vec_(wd/2,0) \
      then to vec_(wd/2,hd) \
      then to vec_(-wd/2,hd) \
      then to vec_(-wd/2,0) \
      then to Here ]
    H: m4pconpin(dimen_/12,dimen_*0.25,m4na_) at Base.c+vec_( wd/4,0)
    N: m4pconpin(dimen_/12,dimen_*0.25,m4na_) at Base.c+vec_(-wd/4,0)
    ')
  `$4' ; resetdir_ ]')
define(`m4pconpin',`[ifinstr(`$3',F,`lbox(`$1',`$2')',
 `m4fshade(m4fill,lbox(`$1',`$2'))')]')
define(`m4pcrpin',`[ifinstr(`$2',F,`circle diam `$1'',
 `m4fshade(m4fill,circle diam `$1')')]')

                                `m4fshade(gray value,closed curve) internal'
ifelse(m4picprocessor,gpic,
 `define(`m4fshade',`shade(ifelse(`$1',,0,`$1'),`$2')')',
m4postprocessor,xfig,
 `define(`m4fshade',``$2' fill ifelse(`$1',,0,`$1')')',
`define(`m4fshade',``$2' dnl
  ifdef(`r_',`shaded rgbstring(r_,g_,b_)',`fill ifelse(`$1',,0,`$1')')')')

                          `Header(1|2,rows,wid,ht,type)
                            arg1: number of columns
                            arg2: pins per column
                            arg3,4: custom wid, ht
                            arg5: eg fill_(0.9)'
define(`Header',
`[define(`m4Hm',`ifelse(`$2',,2,`$2')')define(`m4Hn',`ifelse(`$1',,1,`$1')')dnl
  define(`m4Hw',`ifelse(`$3',,`m4Hn*L_unit*3',`($3)')')dnl
  define(`m4Hh',`ifelse(`$4',,`m4Hm*L_unit*3',`($4)')')dnl
  Block: rotbox(m4Hw,m4Hh,`$5')
  define(`m4Hct',1)dnl
  for_(1,m4Hm,1,
   `HeaderPin(Block.NW+vec_(L_unit*3/2,-(m4x-1/2)*m4Hh/m4Hm),
     eval(m4Hct-1), P`'m4Hct,w) define(`m4Hct',incr(m4Hct))
    ifelse(m4Hn,2,`HeaderPin(Block.NE+vec_(-L_unit*3/2,-(m4x-1/2)*m4Hh/m4Hm),
        1, P`'m4Hct,e) define(`m4Hct',incr(m4Hct))') ')
  `$6' ]')
                          `HeaderPin(location,type,Picname,
                            n|e|s|w,length)'
define(`HeaderPin',`define(`m4Hpl',`ifelse(`$5',,`lg_plen*L_unit',`$5')')dnl
  move to `$1'
  line to ifelse(`$4',n,`rvec_(0,m4Hpl)',
   `$4',e,`rvec_(m4Hpl,0)',`$4',s,`rvec_(0,-m4Hpl)',`rvec_(-m4Hpl,0)')
  ifelse(`$3',,,`$3': Here)
  ifelse(`$3',,,Pin`$3':) ifelse(`$2',0,
   `rotbox(L_unit,L_unit,fill_(1))',
   `circle diam L_unit fill_(1)') at last line.start ')

                    `nport(box specs; other commands,
                       nw,nn,ne,ns,
                       space ratio,pin lgth,style,other commands)
                     Default is a standard-box twoport.  Args 2 to 5 are
                     the number of ports to be drawn on w, n, e, s sides.
                     The port pins are named by side, number, and by a or b pin,
                     e.g. W1a, W1b, W2a, ... .  Arg 6 specifies the ratio of
                     port width to interport space (default 2), and arg 7 is
                     the pin length.  Set arg 8 to N to omit the dots on
                     the port pins. Arguments 1 and 9 allow customizations'
define(`nport',`[Box: box `$1'
  r = ifelse(`$6',,2.0,`$6')
  plg = ifelse(`$7',,`dimen_/4',`$7')
#                           `West side'
  define(`m4n',`ifelse(`$2'`$3'`$4'`$5',,1,`$2',,0,`($2)')')
  d = Box.ht/(m4n*(r+1)+1)
  move to Box.nw+(0,-d); down_
  m4portpins(-plg,d*r,d,W,`$8')
#                           `North side'
  define(`m4n',`($3)')
  ifelse(`$3',,,`d = Box.wid/(m4n*(r+1)+1)
  move to Box.nw+(d,0); right_
  m4portpins(plg,d*r,d,N,`$8')')
#                           `East side'
  define(`m4n',`ifelse(`$2'`$3'`$4'`$5',,1,`$4',,0,`($4)')')
  d = Box.ht/(m4n*(r+1)+1)
  move to Box.ne+(0,-d); down_
  m4portpins(plg,d*r,d,E,`$8')
#                           `South side'
  define(`m4n',`($5)')
  ifelse(`$5',,,`d = Box.wid/(m4n*(r+1)+1)
  move to Box.sw+(d,0); right_
  m4portpins(-plg,d*r,d,S,`$8')')
  `$9' undefine(`m4n')]')
define(`m4portpins',`for_(1,m4n,1,
 `{ if (`$1' != 0) then { line to rvec_(0,`$1') }
   `$4'`'m4x`'a: ifelse(xtract(`$5',N),N,Here,`dot') }
  move to rvec_(`$2',0)
  { if (`$1' != 0) then { line to rvec_(0,`$1') }
   `$4'`'m4x`'b: ifelse(xtract(`$5',N),N,Here,`dot') }
  ifelse(m4x,m4n,,`move to rvec_(`$3',0)')')')

                          `gyrator(box specs,space ratio,pin lgth,style)
                           Gyrator two-port wrapper for nport
                           e.g. gyrator(ht boxwid invis,,0,N)'
define(`gyrator',
 `define(`m4dna_',ifelse(xtract(`$4',V)`'xtract(`$4',H),,H`$4',`$4')`')dnl
  sc_draw(`m4dna_',H,
   `nport(ifelse(`$1',,wid boxht,`$1'),1,,1,,`$2',`$3',`$4',
      line from (Box,W1a)+(-Box.wid/2,0) \
        left -Box.wid/4 then down W1a.y-W1b.y then right -Box.wid/4
        arcd(Box+(-Box.wid/4,0),(W1a.y-W1b.y)/3,-90,-270)
      line from (Box,W1a)+(Box.wid/2,0) \
        left Box.wid/4 then down W1a.y-W1b.y then right Box.wid/4
        arcd(Box+(Box.wid/4,0),(W1a.y-W1b.y)/3,90,270)
     `$5')')dnl
  sc_draw(`m4dna_',V,
   `nport(ifelse(`$1',,wid boxht,`$1'),,1,,1,`$2',`$3',`$4',
      line from (N1a,Box)+(0,-Box.ht/2) \
        down -Box.ht/4 then right N1b.x-N1a.x then up -Box.ht/4
        arcd(Box+(0,-Box.ht/4),(N1b.x-N1a.x)/3,-90+90,-90+270)
      line from (N1a,Box)+(0,Box.ht/2) \
        down Box.ht/4 then right N1b.x-N1a.x then up Box.ht/4
        arcd(Box+(0,Box.ht/4),(N1b.x-N1a.x)/3,90+90,90+270)
     `$5')') ')
                                `proximity(linespec)'
define(`proximity',`consource(`$1',P)')
                                `nullator(linespec, wid, ht, attributes)'
define(`nullator',`eleminit_(`$1')
   pushdef(`m4wd',ifelse(`$2',,`dimen_/2',`($2)'))dnl
   pushdef(`m4ht',ifelse(`$3',,`dimen_/4',`($3)'))dnl
   {line to rvec_(max(0,rp_len/2-m4wd/2),0)
    move to rvec_(m4wd/2,0)
    { spline ifdpic(0.58) from rvec_(ifdpic(0,-m4wd/20),m4ht/2) \
      to rvec_(m4wd/20*3,m4ht/2) \
      then to rvec_(m4wd/2,m4ht/4) \
      then to rvec_(m4wd/2,-m4ht/4) \
      then to rvec_(m4wd/20*3,-m4ht/2) \
      then to rvec_(-m4wd/20*3,-m4ht/2) \
      then to rvec_(-m4wd/2,-m4ht/4) \
      then to rvec_(-m4wd/2,m4ht/4) \
      then to rvec_(-m4wd/20*3,m4ht/2) \
      then to rvec_(ifdpic(0,m4wd/20),m4ht/2) `$4'
      }
    line from rvec_(m4wd/2,0) \
          to rvec_(max(0,rp_len/2),0)}
  {[box invis ht_ m4ht wid_ m4wd] at rvec_(rp_len/2,0)}
   line to rvec_(rp_len,0) invis popdef(`m4wd',`m4ht') ')
                                `norator(linespec, wid, ht, attributes)'
define(`norator',`eleminit_(`$1')
   pushdef(`m4wd',ifelse(`$2',,`dimen_/2',`($2)'))dnl
   pushdef(`m4ht',ifelse(`$3',,`dimen_/4',`($3)'))dnl
   {line to rvec_(max(0,rp_len/2-m4wd/2),0)
    move to rvec_(m4wd/2,0)
    for i=-1 to 1 by 2 do { {
      spline to rvec_(i*m4wd/4,m4ht/2) \
      then to rvec_(i*m4wd/2,m4ht/2) \
      then to rvec_(i*m4wd/2,-m4ht/2) \
      then to rvec_(i*m4wd/4,-m4ht/2) \
      then to Here `$4' } }
    line from rvec_(m4wd/2,0) \
          to rvec_(max(0,rp_len/2),0)}
  {[box invis ht_ m4ht wid_ m4wd] at rvec_(rp_len/2,0)}
   line to rvec_(rp_len,0) invis popdef(`m4wd',`m4ht') ')

                        `ACsymbol(at position, len, ht, [n:][A]U|D|L|R|degrees,
                            attributes)
                          Arg4: drawing direction (default: current direction)
                          Arg4 contains A: use arcs instead of sinusoid
                          A convenience for drawing a stack of n 1-cycle
                          sinusoids (default 1)
                          e.g.  source; ACsymbol(at last [])'
define(`ACsymbol',`[ Origin: Here
 pushdef(`m4range',`ifelse(`$2',,(dimen_/3),`($2)')')dnl
 pushdef(`m4ACd',`patsubst(ifinstr(`$4',:,`patsubst(`$4',.*:)',`$4'),A)')dnl
 setdir_(ifelse(m4ACd,,`ifdef(`m4a_',rp_ang*rtod_,0)',m4ACd))
 Start: rvec_(-m4range/2,0)
 End:   rvec_( m4range/2,0)
 pushdef(`m4n',`ifinstr(`$4',:,`eval(patsubst(`$4',:.*))',1)')dnl
 pushdef(`m4amp',`ifelse(`$3',,`m4range/6',`($3)/2')')dnl
 for_(1,m4n,1,`move to Origin+vec_(0,((m4n+1)/2-m4x)*m4range/3)
   ifinstr(ifgpic(A,`$4'),A,
    `{ S`'m4x: [ Origin: Here
       { arc ccw to rvec_(-m4range/2,0) \
         with .c at rvec_(-m4range/4,-max(m4range/4-m4amp,0)) }
       { arc ccw to rvec_( m4range/2,0) \
         with .c at rvec_( m4range/4, max(m4range/4-m4amp,0)) }] dnl
       with .Origin at Here }',
    `{ S`'m4x: sinusoid(m4amp,twopi_/m4range,pi_/2,
      -m4range/2,m4range/2,`$5') with .Origin at Here } ')')
 `$6'; resetdir_ popdef(`m4amp',`m4n',`m4ACd',`m4range')] dnl
   with .Origin ifelse(`$1',,`at Here',`$1')')

                        `Deltasymbol(at position, keys, U|D|L|R|degrees,
                           attributes)
                          keys: size=expr;
                                type=C|O (default C for Closed, O means open);
                          Arg3: drawing direction (default: Up)'
define(`Deltasymbol',`[ sq3 = sqrt(3)
 pushkeys_(`$2',size:dimen_/10; type:C:N )dnl
 setdir_(`$3',U)
 ifinstr(m4type,C,
  `line `$4' from vec_(vscal_(m4size,-sq3,0)) to \
     vec_(vscal_(m4size,-sq3,1)) then to Here \
     then to vec_(vscal_(m4size,-sq3,-1)) \
     then to vec_(vscal_(m4size,-sq3,0))',
  `line `$4' from vec_(vscal_(m4size,-sq3/2,-1/2)) \
     to vec_(vscal_(m4size,-sq3,-1)) \
     then to vec_(vscal_(m4size,-sq3,1)) \
     then to vec_(vscal_(m4size,-sq3/2,1/2)) ')
 C: vec_(vscal_(m4size,-(sq3+1/sq3)/2,0)); N: C
  resetdir_ popdef(`m4size',`m4type') ] ifelse(`$1',,`at Here',`$1')')

                        `Ysymbol(at position, keys, U|D|L|R|degrees, attributes)
                          keys: size=expr; type=G[L] (grounded,
                            L puts the ground on the left);
                          Arg3: drawing direction (default: Up)'
define(`Ysymbol',`[ sq3 = sqrt(3)
 pushkeys_(`$2',`size:dimen_/10:; type::N')dnl
 setdir_(`$3',U)
 C: Here; N: C
 line from vec_(vscal_(m4size,-2/sq3,0)) to C
 { line `$4' from vec_(vscal_(m4size,1/sq3,1)) to C \
     then to vec_(vscal_(m4size,1/sq3,-1)) }
 ifelse(m4type,,,`line `$4' ifinstr(m4type,L,left_,right_) m4size*3/2
   corner(,`$4'); pushdef(`dimen_',m4size*4) ground popdef(`dimen_') ')
 `$5'; resetdir_ popdef(`m4size',`m4type') ] ifelse(`$1',,`at Here',`$1')')
                        `Wyesymbol(at position, keys, U|D|L|R|degrees)
                         Synonym for Ysymbol'
define(`Wyesymbol',`Ysymbol($@)')

                        `DCsymbol(at position, len, ht, U|D|L|R|degrees,
                           attributes)
                          Arg4: drawing direction (default: current direction)'
define(`DCsymbol',`[
 pushdef(`m4wid',`ifelse(`$2',,(dimen_/3),`($2)')')dnl
 pushdef(`m4ht',`ifelse(`$3',,`(m4wid/5)',`($3)')')
 setdir_(ifelse(`$4',,`ifdef(`m4a_',rp_ang*rtod_,0)',`$4'))
 Origin: rvec_(m4wid/2, m4ht/2)
 {line `$5' to rvec_(m4wid,0)}
 dashline(from rvec_(0, m4ht) to rvec_(m4wid, m4ht),`$5',m4wid/4,m4wid/8) 
 `$6'; resetdir_ popdef(`m4ht',`m4wid') ] \
   with .Origin ifelse(`$1',,`at Here',`$1')')

                    `n-terminal box
                     nterm(box specs; other commands,
                       nw,nn,ne,ns,
                       pin lgth,style,other commands)
                     The default is three-terminal.  Args 2 to 5 are
                     the number of pins to be drawn on W, N, E, S sides.
                     The pins are named by side and number, e.g. W1, W2, N1, ...
                     Arg 6 is the pin length.  Set arg 7 to N to omit the dots
                     on the pins. Arguments 1 and 8 allow customizations, e.g.
                     nterm(,,,,,,N,
                           "$a$" at Box.w ljust
                           "$b$" at Box.e rjust
                           "$c$" at Box.s above) '
define(`nterm',`[Box: box ifelse(`$1',,wid dimen_ ht dimen_*2/3,`$1')
  plg = ifelse(`$6',,`dimen_/4',`$6')
#                           `West side'
  define(`m4n',`ifelse(`$2'`$3'`$4'`$5',,1,`$2',,0,`($2)')')
  d = Box.ht/(m4n+1)
  move to Box.nw+(0,-d); down_
  m4termpins(-plg,d,W,`$7')
#                           `North side'
  define(`m4n',`($3)') ifelse(`$3',,,
  `d = Box.wid/(m4n+1)
  move to Box.nw+(d,0); right_
  m4termpins(plg,d,N,`$7')')
#                           `East side'
  define(`m4n',`ifelse(`$2'`$3'`$4'`$5',,1,`$4',,0,`($4)')')
  d = Box.ht/(m4n+1)
  move to Box.ne+(0,-d); down_
  m4termpins(plg,d,E,`$7')
#                           `South side'
  define(`m4n',`ifelse(`$2'`$3'`$4'`$5',,1,`$5',,0,`($5)')')
  d = Box.wid/(m4n+1)
  move to Box.sw+(d,0); right_
  m4termpins(-plg,d,S,`$7')
  `$8' undefine(`m4n')]')
define(`m4termpins',`for_(1,m4n,1,
 `{ if (`$1' != 0) then { line to rvec_(0,`$1') }
   `$3'`'m4x: ifelse(xtract(`$4',N),N,Here,`dot') }
  ifelse(m4x,m4n,,`move to rvec_(`$2',0)')')')

                          `speaker(U|D|L|R|degrees, vert size, type, attributes)
                           type=H horn'
define(`speaker',`[setdir_($1,R)
  pushdef(`m4v',`ifelse(`$2',,`dimen_/3',`($2)/4')')dnl
  pushdef(`m4h',`m4v*sqrt(2)')dnl
 ifelse(`$3',H,
  `{H1: line from rvec_(m4h,m4v/2) \
          to rvec_(m4h*3/2,m4v*7/8) \
    then to rvec_(m4h*3/2,-m4v*7/8) \
      then to rvec_(m4h,-m4v/2) `$4'}',
  `{H1: line from rvec_(m4h,m4v) \
          to rvec_(m4h*2,m4v*2) \
    then to rvec_(m4h*2,-m4v*2) \
      then to rvec_(m4h,-m4v) `$4'}')
 {lbox(m4h,m4v*2,`$4')}
 {Box: box invis ht_ m4v*2 wid_ m4h at rvec_(m4h/2,0)}
  In1: rvec_(0,m4v/2)
  In2: Here
  In3: rvec_(0,-m4v/2)
  In4: rvec_(m4h/4,m4v)
  In5: rvec_(m4h*3/4,m4v)
  In6: rvec_(m4h/4,-m4v)
  In7: rvec_(m4h*3/4,-m4v)
  `$5'; resetdir_ popdef(`m4v',`m4h') ]')

                                `bell(U|D|L|R|degrees, vert size, attributes)'
define(`bell',`[setdir_($1,R)
  pushdef(`m4h',`ifelse(`$2',,`dimen_/2',`($2)')')dnl
 {lbox(m4h,m4h,`$3')}
 {Box: box invis ht_ m4h wid_ m4h at rvec_(m4h/2,0)}
 {Circle: circle diameter m4h at rvec_(m4h*3/2,0) `$3'}
  In1: rvec_(0,m4h/4)
  In2: Here
  In3: rvec_(0,-m4h/4)
  `$4'; resetdir_ popdef(`m4h') ]')
                                `microphone(A|U|D|L|R|degrees, vert size,
                                   attributes)
                                  Arg1= A, upright mic
                                  Thanks to Arnold Knott'
define(`microphone',`ifinstr(`$1',A,
 `[ pushdef(`m4sfact',`(ifelse(`$2',,dimen_,(`$2'))*8/5)')
  circlerad = m4sfact/1000
  cspace = m4sfact/100
  bwd = m4sfact/10
  bht = m4sfact/4+bwd
  Stand: line up m4sfact/5
  { arc from Here+(-bwd,bwd) to Here+(bwd,bwd) with .c at Here+(0,bwd)
    line up m4sfact/4-bwd from last arc.start
    line up m4sfact/4-bwd from last arc.end }
  Head: box rad bwd/2 ht bht wid bwd with .s at Here+(0,bwd/2) `$3'
  Inner: box rad bwd/2 ht bht/2+bwd/2 wid bwd with .n at Head.n
  move to Inner.s+(0,bwd/2)
  for i=1 to 4 do {
    for j=-1 to 1 do {
      { circle at Here+(3*j*cspace,(abs(j)-3)*cspace) }
      if j != 0 then {{ circle at Here+(j*3/2*cspace,0) }} }
    move up 5*cspace }; popdef(`m4sfact')]',
 `[setdir_($1,R)
   pushdef(`m4h',`ifelse(`$2',,`dimen_/2',`($2)')')dnl
  {L1: line from rvec_(m4h,-m4h/2) \
           to rvec_(m4h,m4h/2)}
  {Circle: circle diameter m4h at rvec_(m4h/2,0) `$3'}
   In1: rvec_(m4h*(2-sqrt(3))/4,m4h/4)
   In2: Here
   In3: rvec_(m4h*(2-sqrt(3))/4,-m4h/4)
   `$4'; resetdir_ popdef(`m4h') ]')')

                                `buzzer(U|D|L|R|degrees, vert size,[C],
                                   attributes)'
define(`buzzer',`[setdir_($1,R)
 ifelse(`$3',,
 `pushdef(`m4h',`ifelse(`$2',,`dimen_/2',`($2)')')dnl
   {L1: line from rvec_(m4h,0) \
          to rvec_(m4h,m4h/2) \
     then to rvec_(0,m4h/2) \
      then to rvec_(0,-m4h/2) \
     then to rvec_(m4h,-m4h/2) \
      then to rvec_(m4h,0) `$4'}
   {Box: box invis ht_ m4h wid_ m4h at rvec_(m4h/2,0)}
   {L2: line from rvec_(m4h,m4h/2) \
          to rvec_(m4h,m4h/2)+vec_(Rect_(m4h,-75))}
   In1: rvec_(0,m4h/4)
   In2: Here
   In3: rvec_(0,-m4h/4) popdef(`m4h')',
 `$3',C,`pushdef(`m4h',`ifelse(`$2',,`(dimen_/3)',`(($2)/2)')')dnl
   {Face: line from rvec_(m4h,-m4h) \
          to rvec_(m4h,m4h)}
   {arc ccw from Face.end to Face.start with .c at Face.c `$4'}
   In1: rvec_(m4h-sqrt(m4h^2-(m4h/3)^2),m4h/3)
   In2: Here
   In3: rvec_(m4h-sqrt(m4h^2-(m4h/3)^2),-m4h/3) popdef(`m4h') ')
 `$5'; resetdir_ ]')
                                `earphone(U|D|L|R|degrees, size, [C][R],
                                  attributes)
                                 earphone pair if arg3 contains C'
define(`earphone',`[ setdir_($1,R)
  pushdef(`m4h',`ifelse(`$2',,`dimen_',`($2)')')dnl
  ifinstr(`$3',C,
   `L: circle diam m4h*0.4 `$4'
    R: circle diam m4h*0.4 at L+vec_(m4h,0) `$4'
    C: 0.5 between L and R
    N: C+(vscal_(m4h/2,Vperp(L,R)))
    Lx: Cintersect(L,L.rad,C,m4h/2,`$3')
    Rx: Cintersect(C,m4h/2,R,R.rad,`$3')
    arc ifinstr(`$3',R,c)cw rad m4h/2 from Lx to Rx with .c at C',
   `{lbox(m4h/3,m4h/2,`$4')}
    {Box: box invis ht_ m4h/2 wid_ m4h/3 at rvec_(m4h/6,0)}
    {L1: line thick 2*linethick from rvec_(m4h/3+lthick,-m4h/3) \
           to rvec_(m4h/3+lthick, m4h/3) }
    In1: rvec_(0,m4h/8)
    In2: Here
    In3: rvec_(0,-m4h/8)')
  `$5'; resetdir_ popdef(`m4h') ]')

                               `Signal-flow graph macros: labeled node,
                                directed labeled chopped straight line,
                                directed labeled chopped arc, and a self
                                loop.  All are contained in [] blocks.'

                               `Signal-flow graph initialization macro
                         sfg_init(line len, node rad, arrowhd len, arrowhd wid)'
ifdef(`sfg_init',,
`define(`sfg_init',`cct_init
  sfg_wid = ifelse(`$1',,`(linewid/0.75*(2.5+0.25)/4)',(`$1'))# default line len
  sfg_rad = ifelse(`$2',,(0.25/4/2),(`$2'))  # node radius
  sfg_aht = ifelse(`$3',,(0.25/4),(`$3'))    # arrow height (arrowhead length)
  sfg_awid = ifelse(`$4',,`sfg_aht',(`$4'))  # arrowhead width
  ')')
                               `sfgline(linespec,
                                        text,sfgabove|sfgbelow|ljust|rjust,
                                        attributes)
                                Draw a straight line with linespec, chopped by
                                node radius, with optional label'
define(`sfgline',`eleminit_(`$1',sfg_wid)
[ L1: line to rvec_(rp_len,0) chop sfg_rad `$4'
Start: last line.start
End: Here
  move to last line.c
  ifelse(ifinstr(`$4',->,T,`$4',<-,T),,
   `{ arrow m4c_l ht sfg_aht wid sfg_awid from rvec_(-sfg_aht/2,0) \
        to rvec_(sfg_aht/2,0) `$4' }')
  ifelse(`$2',,,`m4lstring(`$2',"iflatex(`$ `$2'$',` $2')") \
    ifelse(`$3',,`sfgabove',`$3')')
  ] with .Start at rvec_(sfg_rad,0)
  move to last [].End
  ')
                               `Like above_ or below_ but adding extra space
                                to put text above or below arrowheads or nodes'
define(`sfgabove',`at Here+(0,sfg_awid/2) above')
define(`sfgbelow',`at Here+(0,-sfg_awid/2) below')

                               `sfgnode(at pos,text,above_,circle attributes)
                                Node: a white circle, possibly labelled. The
                                default label position is inside if the
                                diameter is bigger than textht and textwid'
define(`sfgnode',
 `[C: circle fill_(1) rad sfg_rad ifelse(`$4',,`thick 0.5',`$4')] with .c \
    ifelse(`$1',,`at rvec_(sfg_rad,0)',`$1')
  move to last [].c
  ifelse(`$2',,,`if 2*sfg_rad > Max(textwid,textht,10pt__) \
    then { {m4lstring(`$2',`"iflatex(`$ `$2'$',` $2')"') `$3'} } \
  else { {  m4lstring(`$2',`"iflatex(`$ `$2'$',` $2')"') \
    ifelse(`$3',,`sfgabove',`$3')} }')
  ')
                               `sfgarc(linespec,label,above_,cw|ccw,sfact,
                                  attributes)
                                An arc between nodes at the endpoints of the
                                linespec.  The resulting positions Start, End,
                                C (arc center) and M (arc midpoint) are defined.
                                The fifth argument scales the arc height above
                                its chord.'
define(`sfgarc',`eleminit_(`$1',sfg_wid)
[ Start: Here
  End: Start + vec_(rp_len,0)
    chordht = (rp_len/sqrt(2)-rp_len/2)ifelse(`$5',,,`*($5)')
    arcrd = (chordht^2+(rp_len)^2/4)/chordht/2
  C: 0.5 between Start and End; C: C+vec_(0,ifelse(`$4',ccw,,-)(arcrd-chordht))
  M: C + vec_( 0,ifelse(`$4',ccw,-)arcrd)
  ifelse(ifinstr(`$1',->,T,`$1',<-,T),,
   `arc `$6' -> m4c_l ifelse(`$4',ccw,ccw,cw) \
      from Cintersect(Start,sfg_rad,C,arcrd,ifelse(`$4',ccw,R)) \
      to Cintersect(C,arcrd,M,sfg_aht/2,ifelse(`$4',ccw,,R)) \
      ht sfg_aht wid sfg_awid with .c at C `$6'
    arc m4c_l ifelse(`$4',ccw,ccw,cw) from M \
      to Cintersect(C,arcrd,End,sfg_rad,ifelse(`$4',ccw,R)) with .c at C `$6'',
   `arc m4c_l patsubst(patsubst(`$1',.*<-,<-),->.*$,->) ifelse(`$4',ccw,ccw,cw)\
      from Cintersect(Start,sfg_rad,C,arcrd,ifelse(`$4',ccw,R)) \
      to Cintersect(C,arcrd,End,sfg_rad,ifelse(`$4',ccw,R)) with .c at C `$6'')
  ifelse(`$2',,,`move to M; m4lstring(`$2',"iflatex(`$ `$2'$',` $2')") \
    ifelse(`$3',,`sfgabove',`$3')')
  ] with .Start at last line.start
  move to last line.end
  ')
                `sfgself(at position,U|D|L|R|degrees,label,above_,cw|ccw,sfact,
                         [-> | <- | <->], attributes)
                                A teardrop-shaped self-loop drawn at "angle"
                                degrees from "positon". The resulting Origin
                                and M (arc midpoint) are defined.  The sixth
                                argument scales the loop. The seventh puts
                                the arrowhead at the beginning, end, or both'
define(`sfgself',`[ Origin: Here
  setdir_(`$2',U)
  d = ifelse(`$6',,,`($6)*') sfg_wid/2; d = d * max(1,sfg_rad/(0.3605*d))
  { m4sfgselfcurve(-, `$8' \
      ifelse(`$5',ccw,`ifinstr(`$7',<-,<-)',`ifinstr(`$7',->,<-)'))
    M: Here
    ifelse(`$7',,`{ arrow `$8' m4c_l from rvec_(0,ifelse(`$5',cw,,-)sfg_aht/2) \
           to rvec_(0,ifelse(`$5',cw,-)sfg_aht/2) ht sfg_aht wid sfg_awid }')
    ifelse(`$3',,,`{m4lstring(`$3',`"iflatex(`$ `$3'$',` $3')"') \
        ifelse(`$4',,`sfgabove',`$4')}') }
  m4sfgselfcurve(, `$8' \
      ifelse(`$5',ccw,`ifinstr(`$7',->,<-)',`ifinstr(`$7',<-,<-)'))
  resetdir_ ] with .Origin ifelse(`$1',,at Here,`$1')
  move to last [].Origin
  ')
define(`m4sfgselfcurve',`spline `$2' m4c_l from rvec_(Rect_(sfg_rad,`$1'30)) \
  to rvec_(0.3*d,`$1'0.2*d) \
      then to rvec_(0.6*d,`$1'0.35*d) \
  then to rvec_(0.9*d,`$1'0.35*d) \
  then to rvec_(d,`$1'0.2*d) \
      then to rvec_(d,0)')

                     `winding( L|R, winding diam, pitch, nturns,
                        core wid, "core color")
                      The complete spline is drawn in the current drawing
                      direction, then parts of it are overwritten with the
                      background color (default white).
                      Arg 1 contains R for right-handed winding.'
define(`winding',`[ pushdef(`m4rt',`ifinstr(`$1',R,-)')
  w_diam = ifelse(`$2',,`dimen_',`$2')
  pitch = abs(ifelse(`$3',,w_diam/4,`$3'))
  nturns = int(abs(ifelse(`$4',,2,`$4')))
  core_w = ifelse(`$5',,w_diam*3/4,`$5')
  W: spline from (0,0) to vec_(0,w_diam) \
    then to vec_(m4rt`'pitch/2,w_diam) \
    then to vec_(m4rt`'pitch/2,0)
  for i=1 to nturns-1 do {
    continue to vec_(m4rt`'i*pitch,0) \
    then to vec_(m4rt`'i*pitch,w_diam) \
    then to vec_(m4rt`'(i+1/2)*pitch,w_diam) \
    then to vec_(m4rt`'(i+1/2)*pitch,0) \
    }
  if core_w > 0 then {
    dx = sign(pitch)*(linethick+0.5)/2 bp__
    vx = pitch*min(core_w/w_diam/8+dx/pitch,0.25)
    for i=0 to nturns-1 do {
      line color ifelse(`$6',,rgbstring(1,1,1),`$6') \
        thick max(core_w/(1bp__)-linethick,0) \
        from vec_(m4rt`'(i*pitch-dx),w_diam/2) \
          to vec_(m4rt`'(i*pitch+vx),w_diam/2)
      dx = vx }
    }
  T1: W.ifinstr(`$1',R,end,start); Start: T1
  T2: W.ifinstr(`$1',R,start,end); End: T2
  `$7' popdef(`m4rt') ]')

                     `arcwinding( winding diam, startdeg, enddeg, nturns,
                        core centre rad, core wdth, "core color")
                      The complete spline is drawn, then parts of it are
                      overwritten with the background color (default
                      white). Negative arg5 puts winding ends at the outside.
                      Ex: W: arcwinding(1.2,-20,20,8, -1,0.8)'
define(`arcwinding',`[ C: Here
  start_ang = ifelse(`$2',,67.5,`$2')
  end_ang = ifelse(`$3',,112.5,`$3')
  nturns = int(abs(ifelse(`$4',,(end_ang-start_ang)/10,`$4')))
  rad_ctr = ifelse(`$5',,`dimen_',`$5')
  core_w = abs(ifelse(`$6',,rad_ctr/2,`$6'))
  if rad_ctr < 0 then { start_ang += 180; end_ang += 180 }
  w_diam = ifelse(`$1',,`core_w*3/2',`$1')
  w_i=(rad_ctr-w_diam/2)
  w_o=(rad_ctr+w_diam/2)
  d_ang = (end_ang-start_ang)/(nturns-1/2)
  W: spline from (Rect_(w_i,start_ang)) to (Rect_(w_o,start_ang)) \
    then to (Rect_(w_o,start_ang+d_ang/2)) \
    then to (Rect_(w_i,start_ang+d_ang/2))
  for i=1 to nturns-1 do {
    continue to (Rect_(w_i,start_ang+i*d_ang)) \
    then to (Rect_(w_o,start_ang+i*d_ang)) \
    then to (Rect_(w_o,start_ang+(i+1/2)*d_ang)) \
    then to (Rect_(w_i,start_ang+(i+1/2)*d_ang))
    }
  if core_w > 0 then {
    da = abs(d_ang)/4
    for i=1 to nturns do {
      arc color ifelse(`$7',,rgbstring(1,1,1),`$7') \
        thick max(core_w/(1bp__)-2*linethick,0) \
        from (Rect_(rad_ctr,start_ang+(i-1/2)*d_ang-da)) \
          to (Rect_(rad_ctr,start_ang+(i-1/2)*d_ang+da)) \
        with .c at C }
    }
  T1: W.start; Start: T1
  T2: W.end; End: T2
  `$8' ]')

                     `tstrip(U|D|L|R|degrees, n, chars)
                      Terminal strip
                      n=integer number of terminals (default 4)
                      chars:
                       I invisible terminals
                       C circle terminals (default)
                       D dot terminals
                       O omitted internal lines
                       box=attributes;
                       wid=val; total strip width
                       ht=val; strip height '
define(`tstrip',`[ setdir_(`$1')
  define(`m4n',`ifelse(`$2',,4,`eval($2)')')dnl
  ifelse(eval(m4n<1),1,`define(`m4n',1)')dnl
  pushkeys_(`$3',`ht:dimen_/2; wid:m4n*m4`'ht*0.6; box::N;')
  {Box: [shade(1,lbox(m4wid,m4ht,m4box))] }
  bw = m4wid/(m4n)
  ifinstr(`$3',O,,`for i=1 to m4n-1 do {
   {move to rvec_(i*bw,-m4ht/2); line to rvec_(0,m4ht)}}')
  for_(1,m4n,1,`{T`'m4x: ifinstr(`$3',I,`rvec_((m4x-0.5)*bw,0)',
   `dot(at rvec_((m4x-0.5)*bw,0),,ifinstr(`$3',D,0,1))')
    {L`'m4x: T`'m4x+vec_(0,m4ht/2)}; {R`'m4x: T`'m4x+vec_(0,-m4ht/2)} }')
  `$4' popdef(`m4wid',`m4ht',`m4box')
  resetdir_ ]')

                     `jack(U|D|L|R|degrees, chars [;keys])
                      Phone jack; arg1 sets drawing direction
                      chars: A sequence of letters L, S, C, each
                        possibly followed by M, B, MB, or BM, e.g. LLMSBM
                       L draws a long contac arm, M adds a Make contact,
                        B a Break contact, and MB or BM adds both
                       S similarly draws a short contact
                       C adds a central medium contact
                      also:
                       X=bring aux contacts to external dots
                       R=right jack orientation wrt to drawing direction
                      keys: dots=dot keys; (default circle=fill_(1))
                            arrowht=expr; (dimen_/8)
                            sleeve=attributes; e.g. shaded "red"
                            sleeveht=expr; (4.5*arrowht)
                            sleevewid=expr; (sleeveht/6)
                            armlen=expr; len of long armature (dimen_*.75) '
define(`jack',`[ setdir_(`$1')
  pushkeys_(`$2',`dots:circle=fill_(1):N;
    arm::N; armlen:dimen_*0.75; arrowht:dimen_/8;
    sleeve::N; sleeveht:m4`'arrowht*4.5; sleevewid:m4`'sleeveht/6; ')dnl
  pushdef(`dna_',`$2') pushdef(`rght',sc_draw(`dna_',R,-)1)dnl
  pushdef(`m4extrn',sc_draw(`dna_',X,X)) pushdef(`m4vd',`dimen_/16')dnl
  ifelse(dna_,,`define(`dna_',L)')
  Sleeve: [lbox(m4sleevewid,m4sleeveht,m4sleeve)]
  F: Sleeve+vec_(m4sleevewid/2,0)
  Ctr: (2 between F and Sleeve)+vec_(-(m4armlen+m4vd), 0);
  G: Sleeve+vec_(0,-m4sleeveht/2*(rght)); Sx: G+(Ctr-Sleeve)
  H: 2 between G and Sleeve; Lx: H+(Ctr-Sleeve)
  Q: Ctr; m4jcontacts(dna_,L,rght,,m4armlen)
  Q: Ctr; m4jcontacts(dna_,C,rght,,m4armlen)
  Q: Ctr; m4jcontacts(dna_,S,neg_(rght),,m4armlen)
  ifelse(m4extrn,X,`ifelse(rght,-1,
   `T: Sleeve + (Lx-Ctr)+((Between_(G,H,dimen_/6))-G)
    line from H to T then to T+(Ctr-Sleeve); H: dot(,m4dots); ',
   `T: Sleeve + (Sx-Ctr)+((Between_(H,G,dimen_/6))-H)
    line from G to T then to T+(Ctr-Sleeve); G: dot(,m4dots); ')')
  `$3'; resetdir_ popdef(`m4dots',`m4arm', `m4armlen', `m4arrowht',
    `m4sleeve', `m4sleeveht', `m4sleevewid',`dna_', `rght', `m4extrn', `m4vd')
  ] ')
                     `m4jcontacts(dna_, L|S|C, 1|-1, blank|n, armlen)'
define(`m4jcontacts',`ifinstr(`$1',`$2',
 `pushdef(`dna_',$1) pushdef(`m4code',regexp(dna_,$2\(M\|B\|MB\|BM\)?,\&))dnl
  sc_draw(`dna_',m4code,
   `pushdef(`armln',`ifelse(`$2',S,0.55/0.75*,`$2',C,0.65/0.75*)'`$5')dnl
    pushdef(`connht',`ifelse($4,,3,ifelse(m4code,$2`'B,4.5,3))')dnl
    $2`'x: Q ifelse(`$2',C,,
     `+vec_(0,$3*ifelse(`$4',,m4sleeveht/2,connht*m4arrowht)); Q: $2`'x')
    $2`'$4: dot(at Q,m4dots)
    Armature: line chop last [].wid/2 chop 0 to rvec_(armln-2*m4vd,0) dnl
    ifelse($4,,`then to rvec_(armln-m4vd,neg_(`$3')*m4vd) \
      then to rvec_(armln,0)')
    Contact: Q+vec_(m4arrowht*2,0)
    ifelse($4,,,`Connector: [lbox(m4vd,connht*m4arrowht,m4sleeve)] \
        at last []+vec_(armln-3*m4vd,neg_(`$3')*connht*m4arrowht/2)')
    ifinstr(m4code,M,`$2`'M`'$4: Contact+vec_(0,`$3'*m4arrowht*1.9)
      $2`'M`'$4`'A: arrow m4c_l <- ht m4arrowht wid m4arrowht \
        from Contact+vec_(0,`$3'*m4arrowht*0.4) \
        to $2`'M`'$4 ifelse(m4extrn,X,`then to $2`'$4+vec_(0,`$3'*m4arrowht*1.9)
        $2`'M`'$4: dot(,m4dots)'); $2`'x: $2`'M`'$4')
    ifinstr(m4code,B,`$2`'B`'$4: Contact+vec_(0,neg_(`$3')*m4arrowht*1.5)
      $2`'B`'$4`'A: arrow m4c_l <- ht m4arrowht wid m4arrowht from Contact \
      to $2`'B`'$4 dnl
      ifelse(m4extrn,X,`then to $2`'$4+vec_(0,neg_(`$3')*m4arrowht*1.5)
        $2`'B`'$4:dot(,m4dots)')')
    m4jcontacts(dna_,$2,$3,ifelse($4,,1,`incr($4)'),`$5')
    popdef(`armln',`connht')')
  popdef(`m4code',`dna_')')')

                     `plug(U|D|L|R|degrees, chars)
                      Phone plug; arg1 sets drawing direction
                      chars:
                       2|3= two|three conductor
                       R= right orientation wrt drawing direction '
define(`plug',`[ setdir_(`$1')
  s=ifinstr(`$2',R,-1,1)
  ght = ifinstr(`$2',3,`dimen_*0.5',`dimen_*0.4')
  A: Here
  AA: line to rvec_(dimen_*0.3,0) \
      then to rvec_(dimen_*0.3,s*ght/3) \
    then to rvec_(dimen_*0.7,s*ght/3); TA: dot(,,1)
  ifinstr(`$2',3,`
    C: A+vec_(0,s*ght/2)
    TC: line from C to C+vec_(dimen_*0.6,0); TC: Here
    B: 2 between A and C',`B: A+vec_(0,s*ght)')
  BB: line from B to B+vec_(dimen_*0.3,0) \
    then to B+vec_(dimen_*0.3,-s*ght/3) \
    then to B+vec_(dimen_*0.6,-s*ght/3); TB: Here
  `$3'; resetdir_ ]')

                     `A dabble in quantum circuits:
                      SQUID(n,diameter,initial angle,cw|ccw)
                      Superconducting quantum interface device with
                      n junctions labeled J1, ... Jn placed around a
                      circle with initial angle -90 deg (by default)
                      with respect to the current drawing direction. The
                      default diameter is dimen_'
define(`SQUID',
`[ pushdef(`m4sqn',`ifelse(`$1',,2,`$1')')dnl
 pushdef(`m4ssz',`ifelse(`$2',,`dimen_',`$2')')dnl
 pushdef(`m4sof',`ifelse(`$3',,-90,`$3')')dnl
 pushdef(`m4ssg',`ifelse(`$4',,+,`$4',ccw,+,-)(m4x-1)/(m4sqn)*360')dnl
 pushdef(`m4sxlen',C.rad/4)dnl
 C: circle diam m4ssz
 for_(1,m4sqn,1,
  `move to C+vec_(Rect_(C.rad,m4sof`'m4ssg))
   J`'m4x: Here
   { line from rvec_(Rect_(m4sxlen,m4sof`'m4ssg+45)) \
            to rvec_(Rect_(m4sxlen,m4sof`'m4ssg+225)) }
   { line from rvec_(Rect_(m4sxlen,m4sof`'m4ssg-45)) \
            to rvec_(Rect_(m4sxlen,m4sof`'m4ssg-225)) }')
 `$5' popdef(`m4sqn',`m4ssz',`m4sof',`m4ssg',`m4sxlen') ]')

                     `Ladder logic:'
                           `l_contact( linespec,keys )
                            keys:
                              wid=expr; (default dimen_/6)
                              ht=expr; (default dimen_/3)
                              type=P|N|NC; (pos|neg|no contact|(def blank)'
define(`l_contact',`pushkeys_(`$2',wid:dimen_/4.5;ht:dimen_/3;type::N;)dnl
  eleminit_(`$1')
  {{line to rvec_(rp_len/2-m4wid/2,0)}
   {line from rvec_(rp_len/2+m4wid/2,0) to rvec_(rp_len,0)}
   [{line from Here to rvec_(0,m4ht)}
    {line from rvec_(m4wid,0) to rvec_(m4wid,m4ht)}
    ifelse(m4type,,, m4type,NC,
     `{line from Here to rvec_(m4wid*1.5,m4ht/1.2) \
        with .c at rvec_(m4wid/2,m4ht/2)}',
    `{"m4type" with .c at rvec_(m4wid/2,m4ht/2)}') ] \
      at rvec_(rp_len/2,0)}
  line invis to rvec_(rp_len,0) popdef(`m4wid',`m4ht',`m4type') ')

                           `l_coil( linespec,keys )
                            keys:
                              size=expr; (default dimen_/3)
                              type=P|N|S|NC; (pos|neg|set latch|negated)'
define(`l_coil',`pushkeys_(`$2',size:sourcerad_*7/4;type::N;)dnl
  eleminit_(`$1')
   {line to rvec_(rp_len/2-m4size/2*5/4,0)}
   {line from rvec_(rp_len/2+m4size/2*5/4,0) to rvec_(rp_len,0)}
   {[ C1: vec_(-m4size/8,0); C2: vec_(m4size/8,0); Dx: Rect_(m4size/2,75)
     arc from C1+vec_(-Dx.x,Dx.y) to C1-vec_(Dx.x,Dx.y) with .c at C1
     arc from C2+vec_(Dx.x,-Dx.y) to C2+vec_(Dx.x,Dx.y) with .c at C2
    ifelse(m4type,,, m4type,NC,
     `{line from 1st arc.end to 2nd arc.end chop m4size/10}',
    `{"m4type" with .c at (0,0)}')
    ] at rvec_(rp_len/2,0)}
  line invis to rvec_(rp_len,0) popdef(`m4size',`m4type') ')

`==============================================================================
                                Customizations:
                                The size and style parameters below can be
                                tweaked, and the cct_init macro modified.'

                                Size and style parameters:
define(`dimen_',`linewid')           `Default element body size unit'

define(`sourcerad_',`(0.25*dimen_)') `Source element default radius'
define(`csdim_',`(0.3*dimen_)')      `Controlled Source width/2'
define(`elen_',`(1.5*dimen_)')       `Default element length'
define(`delay_rad_',`(0.35*dimen_)') `Delay elements'
define(`dotrad_',`(0.04*dimen_)')    `Redefine dot size for circuits'
define(`m4fill',0)                   `Default fill for diode, fuse, ...'
define(`em_arrowwid',`(dimen_/9)')   `em_arrows arrowhead width'
define(`em_arrowht',`(dimen_/7)')    `em_arrows arrowhead ht'
define(`em_arrowhead',1)             `em_arrows arrowhead style'
define(`hoprad_',`dimen_/12')        `arc radius for crossover macro'

right_
divert(0)dnl
