PWM stands for pulse width modulation. As the name suggests, there is a “pulse” and with “width”, we mess(“modulation”). The idea here is to change the width of the pulse, resulting in another pulse that meets our needs.
With digital systems like Arduino, Galileo/Edison, most often, we are dealing with two discrete voltage levels, 0 (GND, logical low) or 1 (logical high, represented by 5 V, 3.3V or 1.8V). PWM is one of the means of achieving (keep in mind the raw output is still digital. The pulse that is being generated still toggles between logical low and logical high) voltages between the two designated logical voltage levels. You could use PWMs to generate signals for driving things like speaker, buzzers etc.. PWMs are also used to control servo motors.
The basic principle behind PWM is that we turn on and off the voltage so fast across a device such that, due to the physical limitations of the device across which the PWM is applied, perceives the voltage as something between logic 0 (GND) and logic high (Vcc).
There are two parameters in the pulse that can be controlled to achieve the desired effect, period and duty cycle. Period is the time interval after which a wave or signal would repeat itself. In a pure digital system, we can generate only two(binary) voltage levels, either logical 0 or logical 1. This kind of signal is called square wave.
So going by the definition of period, the following shows how period is measured (the time interval after which pattern repeats)
The other thing that can be controlled is the duty cycle. Duty cycle defines the amount of time the signal stays “on”. It is measured in terms of percentage. In the above images, the duty cycle is said to be 50% because the signal stays on for half the time in any given period. The key here is, if you increase the duty cycle, the output voltage perceived would be somewhere nearer to logical high (say 5V). Conversely, decreasing the duty cycle results the perceived voltage to tend to 0. Hence 100% duty cycle would mean that the signal stays on all the time, which means the output voltage is Vcc and 0% duty cycle means that the output voltage is 0V.
mraa provides methods “period_us” to control the period and “write” to control the duty cycle
In the script below, we are going to control the intensity of LED connected at D5
The intensity with which LED glows depends on the amount of voltage applied across the LED.
In the script, using PWM, the intensity with which the LED glows is increased to maximum and once it reaches that point, the intensity is reduced until the LED turns off. This cycle keeps repeating within an infinite loop.
#!/usr/bin/pythonimport mraaimport time"""This script demonstrates the usage of mraa library for configuring andusing a pin as PWMsetup:The LED is connected port D5Demo:start the application in the command line by using following command:python pwm.pyThe LED would start with off state then gradually increases it's intensity to maximum and then decreses it's intensity until it turns offand repeats the cycle.You can exit this demo by hitting ctrl+c"""PWM_PIN = 5pwm = mraa.Pwm(PWM_PIN)"""Control the period with"period_us"+----------------+ +----------------+ | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | + +----------------+ +----------------+ ^ ^ | | |<---------- Period ------------->| | ^ | | | | | pwm.period_us(5000)"""pwm.period_us(5000) # Set the period as 5000 us or 5mspwm.enable(True) # enable PWMvalue = 0delta = 0.05 # Used to manipulate duty cycle of the pulsewhile 1: if (value >= 1): # Itensity at max, need to reduce the duty cycle, set -ve delta value = 1 delta = -0.05 elif (value <=0): value = 0 # Intensity at lowest, set a +ve delta delta = 0.05"""Control the duty cycle with"write"+------+ +------+ | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | + +----------------------------+ +---------------------------+ ^ ^ | | |<---->| ^ | | pwm.write(0.2)"""pwm.write(value) # Set the duty cycle value = value + delta time.sleep(0.5)
In the above script, instance for the selected PWM pin, pin 5 is created using
pwm = mraa.Pwm(PWM_PIN)
Then set the period using (the period is in terms of us)
Once that is done, start outputting the pulse train at the selected pin :
and finally, the duty cycle is controlled using the write() api:
On github, you can find the code here: https://github.com/navin-bhaskar/Python-on-Galileo...