一、接口简介
通用输入/输出(General Purpose Input/Output),简单的传感器使用这个API,如运动探测器、距离探测器,和电平开关使用一个二进制值-高或者低来报告它们的状态。 它引脚提供了可编程的接口,来读取二进制输入设备的状态(如开关按钮)或者控制二进制输出设备的开关状态(例如LED等)。
你可以配置GPIO引脚为具有高低状态的输入或者输出:
作为输入:外部源决定这个状态,你的app可以读取当前的值或者对状态的变化做出反应。
作为输出:你的app配置引脚的状态。
二、使用步骤
对于GPIO接口的操作,主要有如下几个步骤:
1.打开连接
创建PeripheralManagerService对象,使用你要打开的端口的名称调用openGpio()方法打开指定端口的连接。
使用DIRECTION_IN模式调用setDirection()方法配置端口为输入。
使用ACTIVE_HIGHT或者ACTIVE_LOW调用setActiveType()方法,配置高(接近LOREF)或者低(接近zero)电压状态作为true(活动的)返回。
使用getValue()方法返回当前状态。
GPIO端口被配置为输入后,当它的状态在高和低之间改变时会通知你的app。注册这些改变事件:
在活动的端口连接添加一个GpioCallback。
使用setEdgeTriggerType()方法声明触发中断事件的状态变化。边缘触发器支持下面的四个类型:
EDGE_NONE:没有中断事件,这个是默认的值。
EDGE_RISING:从低到高过渡中断。
EDGE_FALLING:从高到底过渡中断。
EDGE_BOTH:在所有状态转换中断。
onGpioEdge()方法返回true意味着这个监听器会持续获取端口的每个状态改变事件。
当你的app不在监听输入事件的时候,注销所有中断Handler。
使用DIRECTIOIN_OUT_INITIALLY_HIGHT或者DIRECTION_OUT_INITIALLY_LOW模式调用setDirection()方法配置它为输出。这些模式确保了端口的初始化状态在配置时间正确设置。
配置高 (接近IOREF)或者低(接近zero)电压信号作为true(活动)返回,使用ACTIVE_HIGHT或者ACTIVE_LOW调用setActiveType()方法。
使用setValue方法来设置当前状态。
当完成GPIO端口通信,使用close()方法关闭连接并释放资源。
这里我们演示一个案例,通过BCM21监听开关按钮的开关产生的输入信号,从而通过BCM5输出信号控制LED灯的开关。
1.电路搭建
2.代码编写
GpioDemo\app\src\main\java\com\chengxiang\gpiodemo\MainActivity.java
通过按钮的开关,来控制LED等的亮和灭。
提示1:在实验的过程中,发现使用BCM6引脚会报错如下:
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: com.google.android.things.pio.PioException: android.os.ServiceSpecificException: BCM6 driver failure
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: at com.google.android.things.pio.GpioImpl.setDirection(GpioImpl.java:64)
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: at com.chengxiang.gpiodemo.MainActivity.onCreate(MainActivity.java:39)
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: at android.app.Activity.performCreate(Activity.java:6662)
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1118)
处理1:更换BCM5接口即正常,目前只能猜测是否是things系统还是预览版,存在一些bug造成。
欢迎大家关注“Android Things开发”微信公众号和加入讨论QQ群,在这里你可以获得Android Things相关的最新资讯,并且第一时间获得我的技术文章,和大家交流开发心得和遇到的问题噢!
通用输入/输出(General Purpose Input/Output),简单的传感器使用这个API,如运动探测器、距离探测器,和电平开关使用一个二进制值-高或者低来报告它们的状态。 它引脚提供了可编程的接口,来读取二进制输入设备的状态(如开关按钮)或者控制二进制输出设备的开关状态(例如LED等)。
你可以配置GPIO引脚为具有高低状态的输入或者输出:
作为输入:外部源决定这个状态,你的app可以读取当前的值或者对状态的变化做出反应。
作为输出:你的app配置引脚的状态。
二、使用步骤
对于GPIO接口的操作,主要有如下几个步骤:
1.打开连接
创建PeripheralManagerService对象,使用你要打开的端口的名称调用openGpio()方法打开指定端口的连接。
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Attempt to access the GPIO try { PeripheralManagerService manager = new PeripheralManagerService(); mGpio = manager.openGpio(GPIO_NAME); } catch (IOException e) { Log.w(TAG, "Unable to access GPIO", e); } }2.读取输入
使用DIRECTION_IN模式调用setDirection()方法配置端口为输入。
使用ACTIVE_HIGHT或者ACTIVE_LOW调用setActiveType()方法,配置高(接近LOREF)或者低(接近zero)电压状态作为true(活动的)返回。
使用getValue()方法返回当前状态。
public void configureInput(Gpio gpio) throws IOException { gpio.setDirection(Gpio.DIRECTION_IN); gpio.setActiveType(Gpio.ACTIVE_HIGH); if (gpio.getValue()) { } else { } }3.监听输入变化
GPIO端口被配置为输入后,当它的状态在高和低之间改变时会通知你的app。注册这些改变事件:
在活动的端口连接添加一个GpioCallback。
使用setEdgeTriggerType()方法声明触发中断事件的状态变化。边缘触发器支持下面的四个类型:
EDGE_NONE:没有中断事件,这个是默认的值。
EDGE_RISING:从低到高过渡中断。
EDGE_FALLING:从高到底过渡中断。
EDGE_BOTH:在所有状态转换中断。
onGpioEdge()方法返回true意味着这个监听器会持续获取端口的每个状态改变事件。
当你的app不在监听输入事件的时候,注销所有中断Handler。
public void configureInput(Gpio gpio) throws IOException { gpio.setDirection(Gpio.DIRECTION_IN); gpio.setActiveType(Gpio.ACTIVE_LOW); gpio.setEdgeTriggerType(Gpio.EDGE_BOTH); gpio.registerGpioCallback(mGpioCallback); } private GpioCallback mGpioCallback = new GpioCallback() { @Override public boolean onGpioEdge(Gpio gpio) { if (mDevice.getValue()) { } else { } return true; } @Override public void onGpioError(Gpio gpio, int error) { Log.w(TAG, gpio + ": Error event " + error); } }; @Override protected void onStop() { super.onStop(); // Interrupt events no longer necessary mGpio.unregisterGpioCallback(mGpioCallback); }4.写入输出
使用DIRECTIOIN_OUT_INITIALLY_HIGHT或者DIRECTION_OUT_INITIALLY_LOW模式调用setDirection()方法配置它为输出。这些模式确保了端口的初始化状态在配置时间正确设置。
配置高 (接近IOREF)或者低(接近zero)电压信号作为true(活动)返回,使用ACTIVE_HIGHT或者ACTIVE_LOW调用setActiveType()方法。
使用setValue方法来设置当前状态。
public void configureOutput(Gpio gpio) throws IOException { gpio.setDirection(Gpio.DIRECTION_OUT_INITIALLY_HIGH); gpio.setActiveType(Gpio.ACTIVE_LOW); gpio.setValue(true); }5.关闭连接
当完成GPIO端口通信,使用close()方法关闭连接并释放资源。
@Override protected void onDestroy() { super.onDestroy(); if (mGpio != null) { try { mGpio.close(); mGpio = null; } catch (IOException e) { Log.w(TAG, "Unable to close GPIO", e); } } }二、案例演示
这里我们演示一个案例,通过BCM21监听开关按钮的开关产生的输入信号,从而通过BCM5输出信号控制LED灯的开关。
1.电路搭建
2.代码编写
GpioDemo\app\src\main\java\com\chengxiang\gpiodemo\MainActivity.java
public class MainActivity extends AppCompatActivity { //输入和输出GPIO引脚名称 private static final String GPIO_IN_NAME = "BCM21"; private static final String GPIO_OUT_NAME = "BCM5"; //输入和输出Gpio private Gpio mGpioIn; private Gpio mGpioOut; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); PeripheralManagerService manager = new PeripheralManagerService(); try { //打开并设置输入Gpio,监听输入信号变化(开关按钮的开关) mGpioIn = manager.openGpio(GPIO_IN_NAME); mGpioIn.setDirection(Gpio.DIRECTION_IN); mGpioIn.setEdgeTriggerType(Gpio.EDGE_FALLING); mGpioIn.setActiveType(Gpio.ACTIVE_HIGH); mGpioIn.registerGpioCallback(mGpioCallback); //打开并设置输出Gpio mGpioOut = manager.openGpio(GPIO_OUT_NAME); mGpioOut.setDirection(Gpio.DIRECTION_OUT_INITIALLY_HIGH); } catch (IOException e) { e.printStackTrace(); } } private GpioCallback mGpioCallback = new GpioCallback() { @Override public boolean onGpioEdge(Gpio gpio) { try { //当按开关按钮的时候,改变输出Gpio的信号,从而控制LED灯的亮和灭 mGpioOut.setValue(!mGpioOut.getValue()); } catch (IOException e) { e.printStackTrace(); } return true; } @Override public void onGpioError(Gpio gpio, int error) { } }; @Override protected void onDestroy() { super.onDestroy(); //关闭Gpio if (mGpioIn != null) { try { mGpioIn.unregisterGpioCallback(mGpioCallback); mGpioIn.close(); mGpioIn = null; } catch (IOException e) { e.printStackTrace(); } } if (mGpioOut != null) { try { mGpioOut.close(); mGpioOut = null; } catch (IOException e) { e.printStackTrace(); } } } }3.运行结果
通过按钮的开关,来控制LED等的亮和灭。
提示1:在实验的过程中,发现使用BCM6引脚会报错如下:
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: com.google.android.things.pio.PioException: android.os.ServiceSpecificException: BCM6 driver failure
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: at com.google.android.things.pio.GpioImpl.setDirection(GpioImpl.java:64)
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: at com.chengxiang.gpiodemo.MainActivity.onCreate(MainActivity.java:39)
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: at android.app.Activity.performCreate(Activity.java:6662)
03-04 15:12:48.497 29491-29491/com.chengxiang.gpiodemo W/System.err: at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1118)
处理1:更换BCM5接口即正常,目前只能猜测是否是things系统还是预览版,存在一些bug造成。
欢迎大家关注“Android Things开发”微信公众号和加入讨论QQ群,在这里你可以获得Android Things相关的最新资讯,并且第一时间获得我的技术文章,和大家交流开发心得和遇到的问题噢!
作者:p106786860 发表于2017/3/11 11:33:27 原文链接
阅读:121 评论:0 查看评论