Digital To Analogue Converter

Fork of ADCandticker_sample by William Marsh

Revision:
2:9e3a110b66ee
Parent:
1:126dd2f5fc2d
--- a/main.cpp	Wed Jan 24 21:55:43 2018 +0000
+++ b/main.cpp	Fri Feb 09 15:57:42 2018 +0000
@@ -3,29 +3,82 @@
 //   Revised for mbed 5
 
 #include "mbed.h"
+#include "sineTable.h"
+
 
 
 Ticker tick;                // Ticker for reading analog
 AnalogIn ain(A0) ;          // Analog input
-DigitalOut led1(LED_RED);   // Red LED
+DigitalOut led1(PTA12);
+DigitalOut led2(PTA4);
+DigitalOut led3(PTA5);
+DigitalOut led4(PTC8);
+DigitalOut led5(PTC9);
+Serial pc(USBTX, USBRX); // tx, rx, for debugging
+
+DigitalIn b1(PTD0, PullUp);
+
+volatile int pressEvent = 0 ;  // Variabe set by the polling thread
+
+AnalogOut ao(PTE30) ;  // Analog output
+
+// Function called periodically
+// Write new value to AnalogOut 
+volatile int index = 0 ; // index into array of sin values
+void writeAout() {
+    ao.write_u16(sine[index]) ;
+    index = (index + 1) % 64 ;   
+}
 
-Serial pc(USBTX, USBRX); // tx, rx, for debugging
+enum buttonPos { up, down, bounce }; // Button positions
+void polling()
+{
+    buttonPos pos = up ;
+    int bcounter = 0 ;
+
+    switch (pos) {
+        case up :
+            if (!b1.read()) {    // now down
+                pressEvent = 1 ;  // transition occurred
+                pos = down ;
+            }
+            break ;
+        case down :
+            if (b1 == 1) { // no longer down
+                bcounter = 3 ; // wait four cycles
+                pos = bounce ;
+            }
+            break ;
+        case bounce :
+            if (b1 == 0) { // down again - button has bounced
+                pos = down ;   // no event
+            } else if (bcounter == 0) {
+                pos = up ;     // delay passed - reset to up
+            } else {
+                bcounter-- ;   // continue waiting
+            }
+            break ;
+
+    }
+}
 
 // Message type
 typedef struct {
-  uint16_t analog; /* Analog input value */
+    uint16_t analog; /* Analog input value */
 } message_t;
 
 // Mail box
 Mail<message_t, 2> mailbox;
 
 // Function called every 10ms to read ADC
-// Low pass filter  
+// Low pass filter
 // Every 10th value is sent to mailbox
 volatile int samples = 0 ;
-volatile uint16_t smoothed = 0 ; 
-void readA0() {
-    smoothed = (smoothed >> 1) + (ain.read_u16() >> 1) ;
+volatile uint16_t smoothed = 0 ;
+void readA0()
+{
+    polling();
+    smoothed = (smoothed >> 1) + (ain.read_u16() >> 1) ; // divided by 2 - reduce the signal noise
     samples++ ;
     if (samples == 10) {
         // send to thread
@@ -35,12 +88,13 @@
             mailbox.put(mess); // fails but does not block if full
         }
         samples = 0;
-    }       
+    }
 }
 
 // Write voltage digits
 //   v  Voltage as scale int, e.g. 3.30 is 330
-void vToString(int v, char* s) {    
+void vToString(int v, char* s)
+{
     s[3] = '0' + (v % 10) ;
     v = v / 10 ;
     s[2] = '0' + (v % 10) ;
@@ -51,24 +105,94 @@
 // Main program
 //   Initialise variables
 //   Attach ISR for ticker
-//   Procss messages from mailbox    
-int main() {
-    led1 = 1 ; // turn off 
+//   Procss messages from mailbox
+int main()
+{
+    led1 = 1 ; // turn off
     int volts = 0 ;
-    const int threshold = 100 ;
+    int threshold = 100 ; // 1 vol
     int counter = 0 ;
     char vstring[] = "X.XX\r\n" ;
+    
+    int update_us = 1000 ; // 1ms
 
-    tick.attach_us(callback(&readA0), 10000); // ticks every 10ms
+    tick.attach_us(callback(&readA0), 10000); // ticks every 10ms -> 10000 micro second
+
+
     while (true) {
-        osEvent evt = mailbox.get(); // wait for mail 
+        
+
+        
+        osEvent evt = mailbox.get(); // wait for mail
+
+        if (pressEvent) {
+            pressEvent = 0 ; // clear the event variable
+            threshold = volts;
+
+        }
+
+        // every 100 ms this loop operates
         if (evt.status == osEventMail) {
             message_t* mess = (message_t*)evt.value.p ;
-            volts = (mess->analog * 330) / 0xffff ;
+            volts = (mess->analog * 330) / 0xffff ; // 2 ^ 16
             mailbox.free(mess) ;  // free the message space
-            if (volts > threshold) led1 = 0 ; else led1 = 1 ;
+
+            int f = (1+49*volts/threshold);
+            if(f<1)
+                f =1;
+            else if(f>50)
+                f=50;
+            
+            update_us = 1/(64*f);
+            tick.attach_us(callback(&writeAout), update_us); // setup ticker to write to AnalogOut
+            
+            
+            if(volts < (threshold / 6)) {
+                led1 = 1;
+                led2 = 1;
+                led3 = 1;
+                led4 = 1;
+                led5 = 1;
+            }
+            if((volts > (threshold * 1/ 6))&&(volts < (threshold * 2/ 6))) {
+                led1 = 0;
+                led2 = 1;
+                led3 = 1;
+                led4 = 1;
+                led5 = 1;
+            }
+            if((volts > (threshold * 2/ 6))&&(volts < (threshold * 3/ 6))) {
+                led1 = 0;
+                led2 = 0;
+                led3 = 1;
+                led4 = 1;
+                led5 = 1;
+            }
+            if((volts > (threshold * 3/ 6))&&(volts < (threshold * 4/ 6))) {
+                led1 = 0;
+                led2 = 0;
+                led3 = 0;
+                led4 = 1;
+                led5 = 1;
+            }
+            if((volts > (threshold * 4/ 6))&&(volts < (threshold * 5/ 6))) {
+                led1 = 0;
+                led2 = 0;
+                led3 = 0;
+                led4 = 0;
+                led5 = 1;
+            }
+            if(volts > (threshold * 5/ 6)) {
+                led1 = 0;
+                led2 = 0;
+                led3 = 0;
+                led4 = 0;
+                led5 = 0;
+            }
             vToString(volts, vstring) ;
             counter++ ;
+
+            // every 1 s this loop will operate
             if (counter == 10) {  // limit bandwidth of serial
                 pc.printf(vstring) ;
                 counter = 0 ;