NUCLEO-F412ZG板子上的元器件并没有完全焊接,除去ST-LINK部分和电源部分后,还有用一个USB主机接口,三个LED灯和两个按钮,不过很多功能引脚都已经引到了插针。查看原理图可发现,由原理图模块的5大部分与电源部分组成,即连接端子、ST-LINK、MCU、USB、以太网和电源部分。

电源部分考虑的非常充分,5V有三路输入,一路是有外部输入6-15VDC电源经U5(LD1117S50TR)转为5VDC电源;第二路是USB端口提供的5V电源,同时还有电流限制保护U4(ST890CDR);第三路则是由外部直接输入5V电源。默认是选择的USB口电源输入,并U6(LD39050PU33R)输出3.3VDC电源。当然还有ST-LINK部分的电源以及USB主机部分的电源。而且这两部分也是上述3路5VDC供电。

以太网部分的电路并未焊接。时钟部分ST-LINK使用了8M的外部晶振(X1),而F412的主时钟输入有两路,一路是从ST-LINK的主控芯片MCO引来,一路也是外界的8M外部晶振(X3)。板子采用的是从MCO引来的时钟。此外还有一个32.768K的外部晶振(X2)。

在了解了基本电路后,开始编程之旅,使用的开发环境是IAR EWARM7.5。首先使用STM32CubeMX创建一个项目。打开STM32CubeMX出现如下的界面。

点击“New Project”新建一个项目,弹出新项目对话框:

由于使用的是NUCLEO-F412ZG开发板,所以选择Board Selector标签,并选择板子的类型为Nucleo144,选择MCU系列为STM32F4,点击“OK”按钮创建项目,出现如下界面:

在第一个项目中我们简单的利用开发板上提供的按钮B1来控制开发板上的三个指示灯LD1(绿色)、LD2(蓝色)、LD3(红色)其中:

按钮B1对应的输入引脚为:PC13

绿色指示灯LD1对应的引脚为:PB0

蓝色指示灯LD2对应的引脚为:PB7

红色指示灯LD3对应的引脚为:PB14

同时通过引脚PG2来驱动外围的继电器电路,这部分电路由自己搭建。原理图如下:

对于IO的配置可以在STM32CubeMX中完成,将PC13配置为GPIO_EXIT13;将PB0、PB7、PB14与PG2都配置为GPIO_OUTPUT。配置好GPIO引脚的类型后就可以在”Configuration“标签(如下图所示)中配置GPIO口了。

在“System“下,选择GPIO弹出”Pin Configuration“对话框。在对话框中一一配置各个GPIO引脚,在本次中我配置个引脚如下:

完成以上配置后,生成IAR EWARM项目则会在生成的源码中出现GPIO的配置,源码如下:

GPIO_InitTypeDef GPIO_InitStruct;

/* GPIO Ports Clock Enable */

__HAL_RCC_GPIOC_CLK_ENABLE();

__HAL_RCC_GPIOH_CLK_ENABLE();

__HAL_RCC_GPIOB_CLK_ENABLE();

__HAL_RCC_GPIOD_CLK_ENABLE();

__HAL_RCC_GPIOG_CLK_ENABLE();

__HAL_RCC_GPIOA_CLK_ENABLE();

/*Configure GPIO pin : B1_Pin */

GPIO_InitStruct.Pin = B1_Pin;

GPIO_InitStruct.Mode = GPIO_MODE_IT_RISING;

GPIO_InitStruct.Pull = GPIO_NOPULL;

HAL_GPIO_Init(B1_GPIO_Port, &GPIO_InitStruct);

/*Configure GPIO pins : LD1_Pin LD3_Pin LD2_Pin */

GPIO_InitStruct.Pin = LD1_Pin|LD3_Pin|LD2_Pin;

GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;

GPIO_InitStruct.Pull = GPIO_NOPULL;

GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;

HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);

/*Configure GPIO pins : STLK_RX_Pin STLK_TX_Pin */

GPIO_InitStruct.Pin = STLK_RX_Pin|STLK_TX_Pin;

GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;

GPIO_InitStruct.Pull = GPIO_NOPULL;

GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH;

GPIO_InitStruct.Alternate = GPIO_AF7_USART3;

HAL_GPIO_Init(GPIOD, &GPIO_InitStruct);

/*Configure GPIO pins : Relay_Ctrl_Pin USB_PowerSwitchOn_Pin */

GPIO_InitStruct.Pin = Relay_Ctrl_Pin|USB_PowerSwitchOn_Pin;

GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;

GPIO_InitStruct.Pull = GPIO_NOPULL;

GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;

HAL_GPIO_Init(GPIOG, &GPIO_InitStruct);

/*Configure GPIO pin : USB_OverCurrent_Pin */

GPIO_InitStruct.Pin = USB_OverCurrent_Pin;

GPIO_InitStruct.Mode = GPIO_MODE_INPUT;

GPIO_InitStruct.Pull = GPIO_NOPULL;

HAL_GPIO_Init(USB_OverCurrent_GPIO_Port, &GPIO_InitStruct);

/*Configure GPIO pins : USB_SOF_Pin USB_ID_Pin USB_DM_Pin USB_DP_Pin */

GPIO_InitStruct.Pin = USB_SOF_Pin|USB_ID_Pin|USB_DM_Pin|USB_DP_Pin;

GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;

GPIO_InitStruct.Pull = GPIO_NOPULL;

GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH;

GPIO_InitStruct.Alternate = GPIO_AF10_OTG_FS;

HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);

/*Configure GPIO pin Output Level */

HAL_GPIO_WritePin(GPIOB, LD1_Pin|LD3_Pin|LD2_Pin, GPIO_PIN_RESET);

/*Configure GPIO pin Output Level */

HAL_GPIO_WritePin(GPIOG, Relay_Ctrl_Pin|USB_PowerSwitchOn_Pin, GPIO_PIN_RESET);

在硬件配置方面,STM32CubeMX能够完成全部的基础工作,我们只需要完成自己的控制逻辑,非常方便。如果设计的好,我们自己学的程序的通用性可以大大提高,极大降低与底层硬件的耦合强度。不过在使用中发现STM32CubeMX似乎与中文操作系统配合得不太好,总是出现全角字符的困扰,估计ST不久会解决。

我的测试逻辑比较简单,一开始三个指示灯全部亮,继电器不导通。按钮B1按一下,LD1灭,再按一下LD2灭,再按一下LD3灭同时继电器吸合,再按一下三个灯全亮同时继电器断开,如此循环。

这部分的源码实现也比较简单,首先定义了一个表示状态的枚举类型,然后根据不通的状态定义逻辑操作。

typedef enum

{

STATE0 = 0,

STATE1,

STATE2,

STATE3,

STATENUM

}STATE;

/*逻辑控制的实现*/

void LogicCtrol(void)

{

GPIO_PinState b1State=HAL_GPIO_ReadPin(B1_GPIO_Port,B1_Pin);

if(b1State==GPIO_PIN_SET)

{

status++;

}

if(status>=STATENUM)

{

status=STATE0;

}

switch(status)

{

case STATE0:

{

HAL_GPIO_WritePin(GPIOB, LD1_Pin|LD3_Pin|LD2_Pin, GPIO_PIN_SET);

HAL_GPIO_WritePin(GPIOG, Relay_Ctrl_Pin, GPIO_PIN_RESET);

break;

}

case STATE1:

{

HAL_GPIO_WritePin(GPIOB, LD1_Pin, GPIO_PIN_RESET);

HAL_GPIO_WritePin(GPIOB, LD3_Pin|LD2_Pin, GPIO_PIN_SET);

HAL_GPIO_WritePin(GPIOG, Relay_Ctrl_Pin, GPIO_PIN_RESET);

break;

}

case STATE2:

{

HAL_GPIO_WritePin(GPIOB, LD1_Pin|LD2_Pin, GPIO_PIN_RESET);

HAL_GPIO_WritePin(GPIOB, LD3_Pin, GPIO_PIN_SET);

HAL_GPIO_WritePin(GPIOG, Relay_Ctrl_Pin, GPIO_PIN_RESET);

break;

}

case STATE3:

{

HAL_GPIO_WritePin(GPIOB, LD1_Pin|LD2_Pin|LD3_Pin, GPIO_PIN_RESET);

HAL_GPIO_WritePin(GPIOG, Relay_Ctrl_Pin, GPIO_PIN_SET);

break;

}

default:

{

break;

}

}

}

下载到NUCLEO-F412ZG开发板测试,结果与预期一致。

STM32F412应用开发笔记之二:基本GPIO控制的更多相关文章

  1. stm32开发笔记(二):stm32系列使用V3.5固件库的帮助文件以及GPIO基本功能(一)

    前言   stm32系列是最常用的单片机之一,不同的版本对应除了引脚.外设.频率.容量等'不同之外,其开发的方法是一样的.  本章讲解使用库函数使用GPIO引脚功能.   补充   本文章为多年前学习 ...

  2. libzip开发笔记(二):libzip库介绍、ubuntu平台编译和工程模板

    前言   Qt使用一些压缩解压功能,选择libzip库,libzip库比较原始,也是很多其他库的基础支撑库,编译过了windows版本,有需求编译一个ubuntu版本的,交叉编译需求的同样可参照本文章 ...

  3. Java开发笔记(二十三)数组工具Arrays

    数组作为一种组合形式的数据类型,必然要求提供一些处理数组的简便办法,包括数组比较.数组复制.数组排序等等.为此Java专门设计了Arrays工具,该工具包含了几个常用方法,方便程序员对数组进行加工操作 ...

  4. Java开发笔记(二十四)方法的组成形式

    经过前面的学习,我们发现演示的Java代码越来越复杂,而且每个例子的代码都堆在入口方法main内部,这会导致如下问题:1.一个方法内部堆砌了太多的代码行,看着费神,维护起来也吃力:2.部分代码描述的是 ...

  5. Java开发笔记(二十五)方法的输入参数

    前面通过main方法介绍了方法的定义形式,对于方法的输入参数来说,还有几个值得注意的地方,接下来分别对输入参数的几种用法进行阐述.一个方法可以有输入参数,也可以没有输入参数,倘若无需输入参数,则方法定 ...

  6. Java开发笔记(二十六)方法的输出参数

    前面介绍了方法的输入参数,与输入参数相对应的则为输出参数,输出参数也被称作方法的返回值,意思是经过方法的处理最终得到的运算数值.这个返回值可能是整型数,也可能是双精度数,也可能是数组等其它类型,甚至允 ...

  7. Java开发笔记(二十七)数值包装类型

    方法的出现缘起优化代码结构,但它的意义并不局限于此,正因为有了方法定义,编程语言才更像一门能解决实际问题的工具,而不仅仅是只能用于加减乘除的计算器.在数学的发展过程中,为了表示四则运算,人们创造了加减 ...

  8. Java开发笔记(二十八)布尔包装类型

    前面介绍了数值包装类型,因为不管是整数还是小数,它们的运算操作都是类似的,所以只要学会了Integer的用法,其它数值包装类型即可一并掌握.但是对于布尔类型boolean来说,该类型定义的是“true ...

  9. Java开发笔记(二十九)大整数BigInteger

    早期的编程语言为了节约计算机的内存,给数字变量定义了各种存储规格的数值类型,比如字节型byte只占用一个字节大小,短整型short占用两个字节大小,整型int占用四个字节大小,长整型long占用八个字 ...

随机推荐

  1. Linux下如何查找.sh后缀的文件

    find / -name *.sh或locate *.shfind 与locate的区别:locate 配合数据库查看文件位置 find 实际搜寻硬盘查询文件名称

  2. 使用charles V3.11.2 实现SSL抓包

    首先,确认开启了SSL选项: 然后到Help->SSL Proxying里查看帮助; 根据提示,将android手机连接到局域网的wifi上,然后将wifi连接的代理设置为192.168.21. ...

  3. log4j的配置

    转载:http://it.oyksoft.com/log4j/ 收藏:http://www.cnblogs.com/ITEagle/archive/2010/04/23/1718365.html 一. ...

  4. History lives on in this distinguished Polish city II 2017/1/5

    原文 Some fresh air After your time underground,you can return to ground level or maybe even a little ...

  5. oracle用户创建

    Microsoft Windows [版本 6.1.7601]版权所有 (c) 2009 Microsoft Corporation.保留所有权利. G:\Users\Admin>sqlplus ...

  6. PHP优化小建议

    PHP优化小建议 1 .. foreach 效率更高,尽量用 foreach 代替 while 和 for 循环 2 ..循环内部不要声明变量,尤其是对象这样的变量 3 ..在多重嵌套循环中,如有可能 ...

  7. DateUtils 学习记录1

    开发过程中很多时候都需要处理各种各样的日期..有些项目可能还会有自己的DateUtil.... 其实apache commons lang3有一个很好用的日期处理工具类,叫DateUtils... 基 ...

  8. jQuery的选择器中的通配符[id^='code'] 等示例及说明

    1.选择器 (1)通配符: $("input[id^='code']");//id属性以code开始的所有input标签 $("input[id$='code']&quo ...

  9. 拖动对象ondrag

    说明: 在进行拖放操作时,dataTransfer 对象用来保存被拖动的数据.它可以保存一项或多项数据.一种或者多种数据类型.dataTransfer对象有两个主要的方法:getData()方法和se ...

  10. VBA学习思路

    打算花两三天学习VBA的基础,学习资料为<别怕,VBA其实很简单>,为了快速学习,先了解大致框架,后续再深入学习各种属性.方法和技巧. 1.VBA编程环境基本操作,手工操作,熟悉即可 2. ...