'm168-test-capacitor-rc-timing-direct.bas
'  Direct read capacitive humidity sensor from Micro controller.
'  which reduces the parts costs.  The basic capacitive sensors start
'  at about $3.50 while the voltage or freq out tend to start at $15
'  and run to over $30.  My favorite is the SHT11 and SHT75 but they
'  start at $30.    The same approach can be used
'  to sense change in capacitance for other circuits
'  such as strain gauges.
'
'  This design provides easy field program calibration capability through
'  serial line which the other sensors do not.   Simply send command to
'  calibrate and current reading near the sensor.  It will compare that to
'  current values and save reading in eprom.  Allows for easy field
'  calibaration.
'
'  Tested on Mega168 but only used 18% of program space so should run
'  in 4K and 8K devices just fine. Probably better implemented with
'  a AVRTiny which could be mounted right on the sensor and then hold
'  1 wire conversation back to master controller.
'
'
' HCH sensor typical response curve 298Pf at 0%RH upto 358pf @ 100%. Interestingly
' got numbers very close to this range from loop counter with 10M resistor.
' http://www.honeywell-sensor.com.cn/prodinfo/sensor_humidity_moisture/datasheet/HCH-1000.pdf
' http://mouser.com/ProductDetail/Honeywell/HCH-1000-002/?qs=yJVtgANCw01Gp3IHDXhPcA%3d%3d
'
'

' ******
' **** Enhancments ***
' ******



'$regfile = "m64def.dat"
$regfile = "m16def.dat"
$crystal = 8000000
$hwstack = 64                                               ' default use 32 for the hardware stack
$swstack = 60                                               ' default use 10 for the SW stack
$framesize = 80                                             ' default use 40 for the frame space




dim tfloat as single
dim tsingle as single
dim tlong as long
dim tword as word

dim r_dif as single
dim p_dif as single
dim rdif_per_perc as single

Declare Function read_humidity_sensor() As Word
Declare Function conv_count_to_humidity(cnt as Word, byval low_r as word, byval low_p as word, cnt_per_perc as Single) As Single
Declare Function read_humdity_avg() as Word


Open "comd.1:9600,8,N,1,inverted" For Output As #1
Open "comd.0:9600,8,N,1,inverted" For Input As #2


Const bon = 1
Const boff = 0

Config Portd.5 = Output
Config Portd.4 = input
config portd.6 = output

rc_charge alias portd.5
rc_read alias pind.4
led alias portd.6
rc_charge = boff


'const chi_r = 1121   ' count reading at high humidity
'const chi_p = 100     ' percentage reading taken at
const chi_r = 1093  ' count reading at high humidity
const chi_p = 75.3  ' percentage reading taken at


'const lo_r = 1045 ' count reading at low humidity
'const lo_p = 33   ' RH percentage at low humidity reading
const clo_r = 1009 ' count reading at low humidity
const clo_p = 41 ' RH percentage at low humidity reading


const clo_no_sens = 400 ' if reading is lower than this assume no sensor present
                        ' no sensor is typically about 19

r_dif =   chi_r - clo_r
p_dif =   chi_p - clo_p
rdif_per_perc =  r_dif / p_dif

print #1, "m168-test-capacitor-rc-timing-direct.v.02.bas"

print #1, "cnt per percent = ";   rdif_per_perc

Dim calc_p as single




Do
  tword = read_humdity_avg()
  print #1, " 2avg="; tword;
  calc_p = conv_count_to_humidity(tword, clo_r, clo_p, rdif_per_perc)
  print #1, " avg%=";Fusing(calc_p , "-###.#")
  Waitms 500
Loop


Function read_humdity_avg() as Word  ' add another layer of averages
  const num_avg = 1 '9
  dim ci as byte
  dim tread as long
  tread = 0
  for ci = 1 to num_avg
    tword = read_humidity_sensor()
    tread = tread + tword
  next ci
  tread = tread / num_avg
  read_humdity_avg = tread
  'waitms 300
end function


'Function test_pass_pin(byval aPin as byte) as word
'  dim tt as byte
'end function

Function conv_count_to_humidity(cnt as Word, byval low_r as word, byval low_p as word, cnt_per_perc as Single) As Single
 'Convert Avg reading to Percentage
  dim ddelta as single
  dim dmult as single
  dim tperc as single
  ddelta = cnt - low_r
  '  how far are we above low calibration reading
  dmult = ddelta / cnt_per_perc
  '  how many units of percentage dose delta reading work out to.
  tperc = low_p + dmult
  conv_count_to_humidity = tperc
end function


Function read_humidity_sensor() As Word
  const num_to_read = 12
  const wait_between_read = 8
  Dim ri as  Byte ' index 2
  Dim tot_read as word ' accumulator 2
  Dim tcnt as  Word


  'Take first reading to leave sensor in correct state
   Bitwait rc_read, reset  ' wait until read low
   waitms wait_between_read ' Stabilize a bit under the diode state.
   set rc_charge
   while rc_read < bon ' Manual loop to see how long it takes to
   wend
   reset rc_charge

  ' Take multiple readings in a row and average them.
  ' for any single reading.
  tot_read = 0
  for ri = 1 to num_to_read
    reset rc_charge
    Bitwait rc_read, reset  ' wait until read low
    waitms wait_between_read ' Give time to discharge thorugh diode.
    tcnt = 0
    set led
    set rc_charge
    while rc_read < bon ' Manual loop to see how long it takes to
      tcnt = tcnt + 1   ' Charge the capacitor
    wend
    reset rc_charge
    reset led
    tot_read = tot_read + tcnt
    'waitms 100
  next ri
  tot_read = tot_read / num_to_read
  read_humidity_sensor = tot_read
end function