Announcements

Ever wondered how you could shape the future in collaboration with others? Join us at OktoberTech Asia Pacific and get inspired. Click here to sign up FREE of charge.

Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

PSoC™ 5, 3 & 1 Forum Discussions

mwors7
Level 2
10 replies posted 10 sign-ins 5 replies posted
Level 2

Hi Community,

I am currently using the PSoC5 filter block in a design.

The process I want to implement is:

ADC -> bandpass filter -> take absolute value of output -> low pass filter -> desired output

Therefore, I currently have an interrupt on end of conversion of ADC which writes the ADC value into CHANNEL A of a filter block which is designed as a bandpass filter. I then implement a check of if values are below zero, and if they are I mirror them to take the absolute signal. Up to this part is fine.

I then want to write the absolute signal into a low pass filter which I have setup in CHANNEL B of the filter block. However when I read results from channel B, I just get 0's. I was wondering if it is possible to stream the filtered value from channel A into channel B? Or if anyone has any suggestions.

 

I have attached my project files in a compressed zip folder.

 

Thanks,

 

mwors7

0 Likes
1 Solution
mwors7
Level 2
10 replies posted 10 sign-ins 5 replies posted
Level 2

Dear community, 

I managed to solve the problem myself. All I did was change the low pass filter from a biquad butterworth to a fir Blackman window.

Seemed to do the trick. Not sure why butterworth responded so strangely still though. 

Cheers

mwors7

View solution in original post

0 Likes
8 Replies
odissey1
Level 9
First comment on KBA 1000 replies posted 750 replies posted
Level 9

mwors7,

I havn't looked into your code. But typically, to measure AC (sine) signal amplitude there are better ways. One is to use Hilbert filter to restore complimentary (cosine) part of the signal, and simply calculate Ampl= sqrt(sine^2 + cosine^2). 

      Another approach is to calculate RMS of the signal as shown in this example

RMS measurement using window function 

Both techniques work for non-sine signals. The Hilbert filter is popular for high frequencies (20khz), while windowing is for low (60Hz).

   In certain cases, when frequency and phase of the signal are fixed, the lock-in approach can provide superior sensitivity. See, for example this demo:

PSoC Today! - Synchronous Detection Detail 

/odissey1

mwors7
Level 2
10 replies posted 10 sign-ins 5 replies posted
Level 2

Thanks for your reply @odissey1,

Eventually, this will be used to find the linear envelopes of EMG muscle signals, where currently the golden standard tehchnique is the procedure stated (bandpass filter, rectify, low pass filter). I will look into the methods you suggested, however do you know whether I can pass values previously filtered by channel A into channel B? At the moment I have the block set up for interrupt on filter complete. I then have two flags for channel A interrupt and channel B interrupt, if channel A (band pass filter) interrupt flag is positive I do the rectification code and filter_write to channel B (low pass filter), if channel B flag is positive I simply read what should be the low pass filter value and print it to terminal through UART, however that doesn't seem to be working.

Thanks again for your reply, 

 

Mwors7

0 Likes
mwors7
Level 2
10 replies posted 10 sign-ins 5 replies posted
Level 2

@odissey1 

Hi Odissey1,

Sorry to bother you but do you have any suggestions for how I can put the output of filter channel A (then some processing) and back into filter channel B?

0 Likes
mwors7
Level 2
10 replies posted 10 sign-ins 5 replies posted
Level 2

Dear community, 

I managed to solve the problem myself. All I did was change the low pass filter from a biquad butterworth to a fir Blackman window.

Seemed to do the trick. Not sure why butterworth responded so strangely still though. 

Cheers

mwors7

0 Likes
odissey1
Level 9
First comment on KBA 1000 replies posted 750 replies posted
Level 9

Glad you found a solution. Attached below a demo project showing envelope extraction using Filter. I cleaned up your project and removed all external interrupts as unnecessary.

The ADC is now using its internal interrupt. It is also configured for external sampling at 500Hz, as at 2kHz internal sampling rate the UART is unable to handle the load. You may consider decimating output signal, as the envelope is rather slow changing, compared to the sampling rate.

The Filter channels A and B are both configured for Polling mode: on each input sample they produce one output sample (with delay). The Filter can operate in either FIR or Biquad modes, but I find FIR output is more smooth.

The AC signal and its envelope are visualized using freeware SerialPlot charting software and SerialPlot custom component (imported into the project):

 SerialPlot: interface to real-time data charts 

Project includes Optional test signal generator, which produces 0-1V sine output at 40Hz, followed by a DC offset 0.5V at 50% duty cycle to mimic EMG signal.

/odissey1

Figure 1. Project schematic. ADC is configured for internal interrupt. Filter is set to Polling mode.

ADC_Filter_01a_A.png

Figure 2. UART output to chart plotting using SerialPlot custom component 

ADC_Filter_01a_UART.png

Figure 3. Optional test signal generator using WaveDAC8. Configured to produce 0-1V sine output at 40Hz, followed by a DC offset 0.5V at 50% duty cycle.   

ADC_Filter_01a_SignalGen.png

Figure 4. Project annotation using PSoC Annotation Library v1.0 . Opamp_1 and VDAC_1 represent optional signal generator. Using internal signal generator requires a single wire connection between Pins 3[7] and 0[1]. Connection to the SerialPlot is virtual, it appears as a COM port and needs no physical connection.

ADC_Filter_01a_KIT-059.png

Figure 5. Real-time signals visualization using freeware SerialPlot charting software. Blue line - Filter Channel A output (DC removed), Red line - Filter Channel B output (envelope).  Essential SerialPlot settings are shown in the bottom panel: CustomFrame, #Channels, Frame Size, etc.

ADC_Filter_01a_SerialPlot.png

odissey1
Level 9
First comment on KBA 1000 replies posted 750 replies posted
Level 9

I may also recommend a paper by R. Lyons  on envelope detection techniques:

Digital Envelope Detection: The Good, the Bad, and the Ugly 

https://www.dsprelated.com/showarticle/938.php

0 Likes
mwors7
Level 2
10 replies posted 10 sign-ins 5 replies posted
Level 2

Hi @odissey1 ,

Thank you very much for all this information! It is great. The code you have made looks a lot more efficient than mine. Thanks again,

 

mwors7

0 Likes
odissey1
Level 9
First comment on KBA 1000 replies posted 750 replies posted
Level 9

mwors7,

I drafted a demo project, showing usage of the Hilbert transformer technique for envelope detection. 

Envelope Detection using a Hilbert transformer method (PSoC5) 

The goal of the project was maximizing sampling rate for speech processing. So, the ADC sampling is done at 93kHz. I believe you needed only 2kHz sampling rate, which simplifies ADC setting (internal clock can be used).

Note that the Hilbert Filter is a band pass filter, which bands can be adjusted like any other FIR filters. It automatically rejects the DC offset and can be set for the bandwidth of interest. Like any FIR filter it also delays signal by (N-1)/2 sampling clocks.

/odissey1

Figure 1. Scope traces: Blue - input signal, Yellow - envelope output, Cyan - reference. AM amplitude 1.0V, amplitude modulation 50%, AM frequency 2.33 kHz (PWM Period=10). Carrier frequency 23.3 kHz. 

HilbertEnvDetector_VDAC_01b_upload_PWM10_0.5-1.0V.png 

0 Likes