@@ -27,10 +27,15 @@ In practice the generator is useful for low frequencies,
2727Note: this class generates float values, performance wise this can be optimized,
2828to achieve higher speeds at cost of accuracy / precision.
2929
30+ As always, feedback and ideas are welcome.
3031
31- #### Performance
3232
33- Indication of what performance can be expected (based upon 0.2.1 version).
33+ ### Performance
34+
35+ You always have to verify your own performance measurements to see if
36+ your requirements are met by this library.
37+
38+ ** Indication** of what performance can be expected (based upon 0.2.1 version).
3439Note that the values need to be transported to a DAC or serial port too.
3540Numbers based on performance example, for one single signal.
3641
@@ -72,55 +77,67 @@ have become slightly slower.
7277| Arduino UNO | 16 MHz | square | 57 | 1000 Hz |
7378| Arduino UNO | 16 MHz | random_DC | 68 | 500 Hz |
7479
80+ See ** functionGeneratorPerformance.ino**
81+
7582
76- #### Accuracy
83+ ### Accuracy
7784
7885If the time parameter ** t** grows large, the internal math may have rounding
7986problems after some time. This can and will affect the quality of the output.
87+ It is advised to reset ** t** after a number (e.g. 100) full periods
8088
8189Needs further investigations.
8290
91+ ### Related
92+
93+ - https://github.com/RobTillaart/AD9833 hardware waveform generator.
94+ - https://github.com/RobTillaart/AD985X hardware waveform generator.
95+ - https://github.com/RobTillaart/functionGenerator software waveform generator.
96+ - https://pages.mtu.edu/~suits/notefreqs.html frequency table for notes.
97+
8398
8499## Interface
85100
86101``` cpp
87102#include " functionGenerator.h"
88103```
89104
90- #### Constructor
105+ ### Constructor
91106
92107- ** funcgen(float period = 1.0, float amplitude = 1.0, float phase = 0.0, float yShift = 0.0)**
93108All parameters (except duty cycle) can be set in the constructor but also later in configuration.
94109Default dutyCycle is 50%.
95110
96111
97- #### Configuration
112+ ### Configuration
98113
99- - ** void setPeriod(float period = 1.0)** set the period of the wave in seconds.
114+ - ** void setPeriod(float period = 1.0)** set the period of the wave in seconds.
115+ This is the inverse of the frequency.
100116- ** float getPeriod()** returns the set period.
101- - ** void setFrequency(float frequency = 1.0)** set the frequency of the wave in Hertz (1/s).
117+ - ** void setFrequency(float frequency = 1.0)** set the frequency of the wave in Hertz (1/s).
118+ This is the inverse of the period.
102119- ** float getFrequency()** returns the set frequency in Hertz.
103- - ** void setAmplitude(float amplitude = 1.0)** sets the amplitude of the wave.
120+ - ** void setAmplitude(float amplitude = 1.0)** sets the amplitude of the wave.
104121The range is from ** -amplitude** to ** +amplitude** .
105122Setting the amplitude to 0 gives effectively a zero signal.
106123Setting the amplitude to a negative value effectively inverts the signal.
107124- ** float getAmplitude()** returns the set amplitude.
108- - ** void setPhase(float phase = 0.0)** shifts the phase of the wave.
125+ - ** void setPhase(float phase = 0.0)** shifts the phase of the wave.
109126Will only be noticeable when compared with other waves.
110127Phase is also known as the X- or horizontal shift.
111128- ** float getPhase()** returns the set phase.
112- - ** void setYShift(float yShift = 0.0)** sets an Y-shift or vertical offset in amplitude.
129+ - ** void setYShift(float yShift = 0.0)** sets an Y-shift or vertical offset in amplitude.
113130This allows to set e.g. the zero level.
114131- ** float getYShift()** returns the set Y-shift.
115- - ** void setDutyCycle(float percentage = 100)** sets the duty cycle of the signal.
132+ - ** void setDutyCycle(float percentage = 100)** sets the duty cycle of the signal.
116133Experimental, not all waveforms have a duty cycle or interpret it differently, see below.
117134Duty cycle must be between 0 and 100% and will be clipped otherwise.
118- - ** float getDutyCycle()** returns the set duty cycle.
119- - ** void setRandomSeed(uint32_t a, uint32_t b = 314159265)** sets the initial seeds for the
135+ - ** float getDutyCycle()** returns the set (clipped) duty cycle.
136+ - ** void setRandomSeed(uint32_t a, uint32_t b = 314159265)** sets the initial seeds for the
120137(Marsaglia) random number generator. The first is mandatory, the second is optional.
121138
122139
123- #### Wave forms
140+ ### Wave forms
124141
125142The variable t == time in seconds.
126143
@@ -129,11 +146,12 @@ The variable t == time in seconds.
129146 - mode == 1 ==> sawtooth |\\ . Effectively equals inverting the amplitude.
130147- ** float triangle(float t)** triangle form, duty cycle default 50%.
131148- ** float square(float t)** square wave with duty cycle default 50%.
132- - ** float sinus(float t)** sinus wave, has no duty cycle.
149+ - ** float sinus(float t)** sinus wave, has no duty cycle.
133150- ** float stair(float t, uint16_t steps = 8, uint8_t mode = 0)** defaults to 8 steps up.
134151 - mode = 0 ==> steps up
135152 - mode = 1 ==> steps down. Effectively equals inverting the amplitude.
136- - ** float random()** random noise generation.
153+ - ** float random()** random noise generation between 0 and amplitude.
154+ Uses Marsaglia random generator.
137155- ** float line()** constant voltage line.
138156Height depends on the YShift and amplitude.
139157- ** float zero()** constant zero.
@@ -142,7 +160,29 @@ The functions **line()** and **zero()** can be used to drive a constant voltage
142160from a DAC and can be used to calibrate the generator / DAC combination.
143161
144162
145- #### Duty Cycle
163+ Experimental 0.2.7
164+
165+ - ** float sinusDiode(float t)** sinus wave, only positive pulses.
166+ (better name welcome).
167+ - ** float sinusRectified(float t)** sinus wave, with "abs(negative pulses)".
168+ (better name welcome).
169+ - ** float trapezium1(float t)** trapezium wave.
170+ DutyCycle changes steepness of the falling and rising edge.
171+ The wave changes from a square wave, via trapezium to a triangle wave.
172+ - ** float trapezium2(float t)** trapezium wave.
173+ DutyCycle changes duration HIGH vs LOW, wave stays trapezium like.
174+ Note at 50% DC the two trapezium functions are identical.
175+ - ** float heartBeat(float t)** simplified heartbeat wave.
176+ To get a regular BPM heartbeat one should ** setFrequency(BPM/60.0)** e.g 72/60 = 1.2.
177+ - ** float freeWave(float t, int16_t arr, int16_t N)** define a free wave form.
178+ It uses an array of ** N+1** values, dividing a full period in ** N** equidistant steps.
179+ The last value should equal the first value to have a smooth transition.
180+ The values of the array normally vary between -10000 and +10000 to manage
181+ the set the relative amplitude in small steps.
182+ These are scaled back to -1.0 to +1.0 times the amplitude.
183+
184+
185+ ### Duty Cycle
146186
147187Since 0.2.5 the library has ** experimental** support for duty cycle.
148188The meaning of duty cycle differs per wave form.
@@ -160,7 +200,16 @@ with respect to previous value.
160200Implemented as a weighed average between new and previous value.
161201Made a separate function as handling the duty cycle slows performance substantial.
162202Initial starts at zero and can be adjusted with ** YShift()** .
203+ - ** float trapezium1(float t)** The duty cycle changes the steepness of the rising
204+ and falling edges. This changes the form from square wave to trapezium to triangle.
205+ The length of the HIGH LOW level go from 0 to half a period.
206+ - ** float trapezium2(float t)** The duty cycle determines the length of the HIGH level,
207+ which is 0 for 0% DC and half a period for 100% DC.
208+ The rising and falling edges stay same.
209+ - ** float heartBeat(float t)** The duty cycle determines the part of the period
210+ that the signal ~ zero.
163211
212+ ### No duty cycle
164213
165214The other functions need to be investigated what duty cycle means.
166215Current ideas that are ** NOT** implemented:
@@ -171,41 +220,52 @@ Think of it as the halve of the triangle wave.
171220- ** stair()** like sawtooth??
172221- ** line()** has no period so does not make sense (yet).
173222- ** zero()** has no period so does not make sense (yet).
174-
175- Feedback and ideas are welcome.
176-
223+ - ** float sinusDiode(float t) **
224+ - ** float sinusRectified(float t) **
225+ - ** float freeWave(float t, int16_t arr, int16_t N) **
177226
178227## Future
179228
180-
181229#### Must
182230
183- - documentation
184- - quality of signals - after substantial time t
185- - max freq per wave form etc.
186- Should this be in the library?
187-
231+ - improve documentation
232+ - reorganize
233+ - section per function might be better.
188234
189235#### Should
190236
191237- smart reseed needed for random().
192- - initialize random generator with compile time.
193-
238+ - initialize random generator with compile file + date + time.
239+ - use function values for seed bits.
240+ - stand-alone functions in separate .h
241+ - clean up code
194242
195243#### Could
196244
197- - waves
198- - trapezium wave (could merge square and triangle and sawtooth)
199- - white noise, pink noise etc.
200- - RC function curve.
245+ - ASDR wave
246+ - https://en.wikipedia.org/wiki/Envelope_(music)
247+ - ** float ADSR(float t, float A, float D, float S, float R)**
248+ - ADSR are percentages, A + D + R < 1.0
249+ - S = % of amplitude.
201250- external clock to synchronize two or more software function generators.
202- - stand-alone functions in separate .h
203251- check for synergy with https://github.com/RobTillaart/AD985X
204252- investigate performance.
205253 - algorithms for DAC specific gains e.g. 10-12-16 bit.
206254 - improve performance sin() lookup table.
207255 - add float variable for ``` _perDC = _period * _dutyCycle ```
208256 - do we need ** freq4** ? not since DC.
257+ - heartBeat
258+ - small noise/variation parameter on amplitude and frequency.
259+ - reduce footprint ==> wrapper around freeWave()
260+ - waves
261+ - white noise, pink noise (better done with hardware)
262+ - min() + max() => return +-amplitude + yshift?
263+ - RC function curve.
264+ - Gamma curve.
265+ - create a function table? with what?
266+ - create an example program to sample an arbitrary wave form
267+ - output in the right format.
268+ - slow sampling vs real time.
209269
210270
211271#### Examples
@@ -228,6 +288,8 @@ Feedback and ideas are welcome.
228288 - ** float stairDC()**
229289- Bezier curve? (too complex)
230290- record a signal and play back ==> separate class
291+ - document max frequency per wave form etc.
292+ Should this be in the library? differs per board.
231293
232294
233295## Support
0 commit comments