python玩转树莓派(四) RPI.GPIO

RPi.GPIO官方文档地址: https://sourceforge.net/p/raspberry-gpio-python/wiki/BasicUsage/

一. 导入RPI.GPIO

import RPi.GPIO as GPIO

二. 指定引脚编号方式

RPi.GPIO中的Raspberry Pi上的IO引脚编号有两种方法。第一种是使用BOARD编号系统。这是指Raspberry Pi板的P1接头上的引脚号。使用此编号系统的优点是,无论RPi的主板版本如何,您的硬件将始终可以工作。您无需重新连接连接器或更改代码。
第二个编号系统是BCM编号。这是一种较低级别的工作方式-指Broadcom SOC上的通道号。您必须始终使用哪个通道号转到RPi板上的哪个引脚的图表。您的脚本可能会在Raspberry Pi板的修订版之间中断。

三. 引脚输入输出基本用法

1. 输入输出模式

GPIO.IN 输入模式
GPIO.OUT 输出模式

2. 设置引脚的输入输出模式

GPIO.setup(引脚, 模式)
也可以同时设置多个引脚 (用列表或元组表示)
GPIO.setup(引脚s, 模式)

ledPin = 11
GPIO.setup(ledPin,GPIO.OUT)

ledPins = (11,12)
GPIO.setup(ledPins,GPIO.OUT)

3. 高低电平

GPIO.HIGH 高电平
GPIO.LOW 低电平

4. 输出高低电平

GPIO.output(引脚,电平)
同上也可以同时设置多个引脚

import RPi.GPIO as GPIO
GPIO.setmode(GPIO.BOARD)
ledPin = 11

GPIO.setup(ledPin,GPIO.OUT)
GPIO.output(ledPin,GPIO.HIGH)

5. 输入高低电平

GPIO.input(引脚)
返回0 / GPIO.LOW / False或1 / GPIO.HIGH / True。

6. 清理

在任何程序的最后,清理您可能使用过的所有资源都是好习惯。

GPIO.cleanup()
GPIO.cleanup(channel)
GPIO.cleanup( (channel1, channel2) )

GPIO.cleanup()通过将您使用过的所有通道返回到输入而没有上拉/下拉,可以通过短路引脚来避免意外损坏RPi。

7.综合举例: 按下按键LED灯亮

import RPi.GPIO as GPIO
import time
GPIO.setmode(GPIO.BOARD)
ledPin = 11
keyPin = 12
GPIO.setup(ledPin,GPIO.OUT)
GPIO.setup(keyPin,GPIO.IN)

while True:
    if GPIO.input(keyPin):
        GPIO.output(ledPin,GPIO.HIGH)
        time.sleep(0.01)
    else:
        GPIO.output(ledPin,GPIO.LOW)

四. Input 输入 详解

1. 读取高低电平方式

这种方式我们之前已经使用过了:
GPIO.input(keyPin)
现在我们来学习其它方式

2. 初始化配置拉高/拉低

我们知道在引脚浮空状态下,引脚电平是无序的0,1乱跳.

这时, 如果我们配置一下默认拉高或拉低就可以避免浮空状态
方法如下:

GPIO.setup(keyPin,GPIO.IN,pull_up_down = GPIO.PUD_UP)
GPIO.setup(keyPin,GPIO.IN,pull_up_down = GPIO.PUD_DOWN)

3. 读取上升沿/下降沿

GPIO.RISING 上升沿
GPIO.FALLING 下降沿
GPIO.BOTH 上升沿/下降沿

3.1 wait_for_edge()函数 //阻塞

wait_for_edge()函数设计用于阻止程序的执行,直到检测到边缘。
返回值: 触发上升沿/下降沿的引脚号,没有则返回None

import RPi.GPIO as GPIO
GPIO.setmode(GPIO.BOARD)
keyPin = 12
GPIO.setup(keyPin,GPIO.IN)

channel = GPIO.wait_for_edge(keyPin, GPIO.RISING,timeout=10000)
if channel:
    print("detected GPIO.RISING on :" ,channel)
else:
    print("can not detected GPIO.RISING")
3.2 add_event_detect() 添加事件 //非阻塞

3.2要和3.3或者3.4一起用实现非阻塞式pin脚输入

  • 与3.3一起用时:
    GPIO.add_event_detect(keyPin, GPIO.RISING)为某个PIN添加RISING事件
  • 与3.4一起用时:
    GPIO.add_event_detect(keyPin, GPIO.RISING,my_callback)为某个PIN添加RISING事件并传入回调函数

同时, 还可以设置软件防抖
GPIO.add_event_detect(channel, GPIO.RISING, my_callback, bouncetime=200)

3.3 event_detected()函数 //非阻塞

event_detected()函数设计用于与其他工作一起循环使用,但与轮询不同,在CPU忙于处理其他事情时,不会错过输入状态的变化。

import RPi.GPIO as GPIO
import time
GPIO.setmode(GPIO.BOARD)
ledPin = 11
keyPin = 12
GPIO.setup(ledPin,GPIO.OUT)
GPIO.setup(keyPin,GPIO.IN)


GPIO.add_event_detect(keyPin, GPIO.RISING)

while True:
    if GPIO.event_detected(keyPin):
        print("detected GPIO.RISING on :" ,keyPin)
    GPIO.output(ledPin,GPIO.HIGH)
    time.sleep(1)
    GPIO.output(ledPin,GPIO.LOW)
    time.sleep(1)
3.4 触发回调函数 //非阻塞

这是我更喜欢的方式, 为一个按键的上升沿/下降沿事件绑定一个回调函数

import RPi.GPIO as GPIO
import time
GPIO.setmode(GPIO.BOARD)
ledPin = 11
keyPin = 12
GPIO.setup(ledPin,GPIO.OUT)
GPIO.setup(keyPin,GPIO.IN)

def acallback(channel):
    print("callback detected GPIO.RISING on :" ,channel)
GPIO.add_event_detect(keyPin, GPIO.RISING,acallback)

while True:
    GPIO.output(ledPin,GPIO.HIGH)
    time.sleep(1)
    GPIO.output(ledPin,GPIO.LOW)
    time.sleep(1)
3.5 删除事件监测

不再希望检测边缘事件,则可以删除它们:
GPIO.remove_event_detect(channel)

五. output 输出 详解

1. 输出高低电平方式

这种方式我们之前已经使用过了:
GPIO.output(keyPin,GPIO.HIGH)

六. PWM

1. 创建PWM实例

p = GPIO.PWM(channel, frequency), channel代表引脚, frequency代表频率

在创建之前要初始化输出,模式

2. 开启PWM

p.start(dc) dc是初始占空比 取值在0~100之间
例如:
我让LED灯的频率是 0.5Hz,那么它的一个PWM周期就是2秒, 然后设置占空比是50(50%), 那么LED会一秒闪烁

import RPi.GPIO as GPIO
import time

GPIO.setmode(GPIO.BOARD)
ledPin = 11
GPIO.setup(ledPin,GPIO.OUT)

p = GPIO.PWM(ledPin, 0.5)
p.start(50)
while True:
    pass

3. 更改频率

p.ChangeFrequency (freq)

4. 更改占空比

p.ChangeDutyCycle(dc)

5. 停止PWM

p.stop()

6. 举例 : 呼吸灯

import RPi.GPIO as GPIO
import time

GPIO.setmode(GPIO.BOARD)
ledPin = 11
GPIO.setup(ledPin,GPIO.OUT)

p = GPIO.PWM(ledPin, 50)
p.start(0)

while True:
    for i in range(0,100):
        p.ChangeDutyCycle(i)
        time.sleep(0.02)
    for i in range(100,0,-1):
        p.ChangeDutyCycle(i)
        time.sleep(0.02)

你可能感兴趣的:(python玩转树莓派(四) RPI.GPIO)