STM32F103ZET6 驱动 OLED

这篇具有很好参考价值的文章主要介绍了STM32F103ZET6 驱动 OLED。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

STM32F103ZET6 驱动 OLED

目录
  • 前言
  • OLED模块的基本了解
  • OLED驱动程序的开发
前言

​ 大家好,这是我第一次发帖,由于,我的技术并不成熟,程序难免有编写不规范的地方,希望读者能够指正,也希望这篇帖子能够让读者对OLED模块有个大致的了解。很高兴能与大家交流。

OLED模块的基本了解

OLED模块的引脚:

oled 驱动程序,stm32,单片机,嵌入式硬件

​ 图片转载自淘宝商家

​ 我使用的OLED模块有以下几个引脚:

引脚名 功能 驱动电压 相连接MCU的端口
GND 接地 GND
VCC 电源电压 3.3v ~ 5v 3.3v
DO 时钟线 2.2v ~ 5v SCLK(PA5)
D1 数据线 2.2v ~ 5v MOSI(PA7)
RES 复位线 2.2v ~ 5v PC5
DC 数据/命令控制线 2.2v ~ 5v PC4
CS 片选线 2.2v ~ 5v PA4
  • RES 为复位线,低电平复位
  • 当GPIO向DC端口输出高电平时,MCU会通过GPIO向D1端口发送数据,使其显示在OLED屏上。当GPIO向DC端口输出低电平时,MCU会通过GPIO向D1端口发送命令,通过这些命令,可以配置OLED模块。

以上是对OLED模块引脚的简要了解,在编写驱动程序之前,我们还需要了解OLED模块的寻址方式。

OLED模块的寻址方式:

OLED有三种寻址模式:

  • 水平寻址

  • 垂直寻址

  • 页寻址

    最常用的寻址模式是页寻址模式,本驱动程序所使用的寻址方法也是页寻址。我会重点介绍页寻址和水平寻址,简要地介绍垂直寻址。

在介绍寻址模式之前,我们需要了解一些预备知识:

0.96寸的OLED显示屏有128列,64行,即128x64,64行被分为8组,每个128x8的区域被称为页,如下图:
oled 驱动程序,stm32,单片机,嵌入式硬件

可以看到COM0~COM7,也就是0 ~ 7行从属于Page0,也就是第0页,依此类推。

通过这种划分,可以把整个屏幕划为8份。

通过这样的划分,当我们往某页某一列中写入数据0x5A时,就能控制哪一列的哪个格子是亮或者灭的,如下图:

oled 驱动程序,stm32,单片机,嵌入式硬件

0x5A

1
0
1
0
0
1
0
1

(注:从顶行到底行,由地位到高位)

​ 在OLED模块中,我们会通过指令来设置OLED模块,假设,我们通过WriteCmd(uint8_t command)函数向OLED模块发送指令。你会发现,有一条就会生效的指令,有多条配合使用才会生效的指令。

void OLED_Init(void) {
	
	// 使能相关的GPIO口 配置SPI外设
	OLED_SPI_Init();	
	
	OLED_SPI_RES_HIGH;
	// 延时200ms
	Delay_us(200);
	/**************************************** 以下是官方的代码******************************/
	WriteCmd(0xAE); //display off
	WriteCmd(0x20);	//Set Memory Addressing Mode	
	WriteCmd(0x10);	//00,Horizontal Addressing Mode;01,Vertical Addressing Mode;10,Page Addressing Mode (RESET);11,Invalid
	WriteCmd(0xb0);	//Set Page Start Address for Page Addressing Mode,0-7
	WriteCmd(0xc8);	//Set COM Output Scan Direction
	WriteCmd(0x00); //---set low column address
	WriteCmd(0x10); //---set high column address
	WriteCmd(0x40); //--set start line address
	WriteCmd(0x81); //--set contrast control register
	WriteCmd(0xff); //亮度调节 0x00~0xff
	WriteCmd(0xa1); //--set segment re-map 0 to 127
	WriteCmd(0xa6); //--set normal display
	WriteCmd(0xa8); //--set multiplex ratio(1 to 64)
	WriteCmd(0x3F); //
	WriteCmd(0xa4); //0xa4,Output follows RAM content;0xa5,Output ignores RAM content
	WriteCmd(0xd3); //-set display offset
	WriteCmd(0x00); //-not offset
	WriteCmd(0xd5); //--set display clock divide ratio/oscillator frequency
	WriteCmd(0xf0); //--set divide ratio
	WriteCmd(0xd9); //--set pre-charge period
	WriteCmd(0x22); //
	WriteCmd(0xda); //--set com pins hardware configuration
	WriteCmd(0x12);
	WriteCmd(0xdb); //--set vcomh
	WriteCmd(0x20); //0x20,0.77xVcc
	WriteCmd(0x8d); //--set DC-DC enable
	WriteCmd(0x14); //
	WriteCmd(0xaf); //--turn on oled panel
}

以上面官方提供的初始化代码片段为例子:

WriteCmd(0xAE); //display off 关闭显示
WriteCmd(0x81); //--set contrast control register
WriteCmd(0xff); //亮度调节 0x00~0xff
// 以上两条命令是设置对比度控制
// 通过0x81命令选择相应的寄存器,然后,设置范围0x00 ~ 0xff的亮度大小,控制OLED屏的亮度

如果想熟悉命令,请参考相应的官方手册。

下面简要介绍几条命令:

WriteCmd(0x00);  // 设置为水平寻址
WriteCmd(0x01);  // 设置为垂直寻址
WriteCmd(0x10);  // 设置为页寻址
WriteCmd(0x8D); // 设置电荷泵
WriteCmd(0x14); // 开启电荷泵
WriteCmd(0xAF); // OLED唤醒
WriteCmd(0xAE); // 关闭OLED

设置页地址:

0xby

7 6 5 4 3 2 1 0
1 0 1 1 Y3 Y2 Y1 Y0

这就是设置页地址命令的格式,[7:4]位是固定的,而[3:0]位可以通过写入0000b ~ 0111b,这个值域的二进制数来指定程序在屏幕显示时的起始地址。

设置列地址:

关于设置列地址,有两条指令0x1[x7:x4]0x0[x3:x0]

高四位的值为1的指令表示的是设置列地址的高四位,高四位的值为0的指令表示设置列地址的第四位。

然后,指令**0x1[x7:x4]的值左移四位,然后与0x0[x3:x0]**的值相加,组成一个8位二进制数,来决定选择的是0 ~127行中的第几行为初始地址

7 6 5 4 3 2 1 0
0 0 0 1 x7 x6 x5 x4
7 6 5 4 3 2 1 0
0 0 0 0 x3 x2 x1 x0

所以下面的一个函数,大家应该看得懂:

// 设置起始坐标
void SetPos(uint8_t x, uint8_t y) {
	
	// 设置页地址
	WriteCmd(0xb0 + y);
	// 取列高位
	WriteCmd((x & 0xf0)>>4 | 0x10);
	// 取列低位
	WriteCmd((x & 0x0f) | 0x01);
}

// 以上代码的意思是,将每个页地址的起始地址设置为0列

对以上的知识有个基本了解之后,下面将介绍几种寻址模式:

  • 首先是页寻址

oled 驱动程序,stm32,单片机,嵌入式硬件
​ 如上图所示,页寻址的办法是,横向对每行进行读和写,当到达每行的末尾的时候,会立即返回每行的开头。

如果到达该行的末尾时,我们不想返回该行的开头,那么我们就需要坐标的起始值。

  • 水平寻址
    oled 驱动程序,stm32,单片机,嵌入式硬件
    ​ 如上图所示,当完成对一行的遍历后,页地址值会自增1,然后,会跳到下一页进行遍历,当对0 ~7 页都遍历之后,会返回0页0列。
OLED驱动程序的开发

本次实验使用了STM32F103ZET6最小系统板,面包板,以及一个电源模块和JLINK OB仿真器,如下图:
oled 驱动程序,stm32,单片机,嵌入式硬件

SPI模块的程序如下:

#ifndef _SPI_H
#define _SPI_H

#include "stm32f10x.h"

// DO SCLK 
#define OLED_SPI_DO_Pin			GPIO_Pin_5
#define OLED_SPI_DO_Port		GPIOA
#define OLED_SPI_DO_CLK			RCC_APB2Periph_GPIOA
#define OLED_SPI_DO_CLK_FUN		RCC_APB2PeriphClockCmd

// D1 MOSI 
#define OLED_SPI_MOSI_Pin		GPIO_Pin_7
#define OLED_SPI_MOSI_Port		GPIOA
#define OLED_SPI_MOSI_CLK		RCC_APB2Periph_GPIOA
#define OLED_SPI_MOSI_CLK_FUN	RCC_APB2PeriphClockCmd

// CS NSS
#define OLED_SPI_CS_Pin			GPIO_Pin_4
#define OLED_SPI_CS_Port		GPIOA
#define OLED_SPI_CS_CLK			RCC_APB2Periph_GPIOA
#define OLED_SPI_CS_CLK_FUN		RCC_APB2PeriphClockCmd

// DC Data or Cammand 数据或者命令选择
#define OLED_SPI_DC_Pin			GPIO_Pin_4
#define OLED_SPI_DC_Port		GPIOC
#define OLED_SPI_DC_CLK			RCC_APB2Periph_GPIOC
#define OLED_SPI_DC_CLK_FUN		RCC_APB2PeriphClockCmd

// RES RESET
#define OLED_SPI_RES_Pin		GPIO_Pin_5
#define OLED_SPI_RES_Port		GPIOC
#define OLED_SPI_RES_CLK		RCC_APB2Periph_GPIOC
#define OLED_SPI_RES_CLK_FUN	RCC_APB2PeriphClockCmd

#define OLED_SPI				SPI1
#define OLED_SPI_CLK			RCC_APB2Periph_SPI1
#define OLED_SPI_CLK_FUN		RCC_APB2PeriphClockCmd
#define OLED_SPI_GPIO_CLK_FUN	RCC_APB2PeriphClockCmd

// 复位引脚的高低电平的输出
#define OLED_SPI_RES_HIGH		GPIO_SetBits(OLED_SPI_RES_Port, OLED_SPI_RES_Pin)		
#define OLED_SPI_RES_LOW		GPIO_ResetBits(OLED_SPI_RES_Port, OLED_SPI_RES_Pin)

// DC命令选择的高低电平的输出
#define OLED_SPI_DC_HIGH		GPIO_SetBits(OLED_SPI_DC_Port, OLED_SPI_DC_Pin)
#define OLED_SPI_DC_LOW			GPIO_ResetBits(OLED_SPI_DC_Port, OLED_SPI_DC_Pin)

void OLED_SPI_Init(void);
void OLED_SPI_Write(uint8_t data);

#endif


#include "spi.h"

void OLED_SPI_Init(void) {

	SPI_InitTypeDef SPI_InitStructure;
	GPIO_InitTypeDef GPIO_InitStructure;
	
	// 打开时钟
	OLED_SPI_CLK_FUN(OLED_SPI_CLK, ENABLE);
	OLED_SPI_GPIO_CLK_FUN(OLED_SPI_DO_CLK | OLED_SPI_MOSI_CLK | OLED_SPI_CS_CLK | OLED_SPI_DC_CLK
		| OLED_SPI_RES_CLK, ENABLE);
	
	// DO SCLK
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
	GPIO_InitStructure.GPIO_Pin = OLED_SPI_DO_Pin;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	
	GPIO_Init(OLED_SPI_DO_Port, &GPIO_InitStructure);
	
	// D1 MOSI
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
	GPIO_InitStructure.GPIO_Pin = OLED_SPI_MOSI_Pin;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	
	GPIO_Init(OLED_SPI_MOSI_Port, &GPIO_InitStructure);
	
	// CS NSS
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = OLED_SPI_CS_Pin;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	
	GPIO_Init(OLED_SPI_CS_Port, &GPIO_InitStructure);
	
	// DC 命令数据选择
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = OLED_SPI_DC_Pin;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	
	GPIO_Init(OLED_SPI_DC_Port, &GPIO_InitStructure);
	
	// RES RESET 低电平复位
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin = OLED_SPI_RES_Pin;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	
	GPIO_Init(OLED_SPI_RES_Port, &GPIO_InitStructure);
	
	// 初始化 SPI结构体
	SPI_InitStructure.SPI_NSS = SPI_NSS_Soft; // 软件控制
	SPI_InitStructure.SPI_Mode = SPI_Mode_Master; // 主机模式
	SPI_InitStructure.SPI_FirstBit = SPI_FirstBit_MSB; // 大端数据先行
	SPI_InitStructure.SPI_Direction = SPI_Direction_1Line_Tx; // 单线发送
	SPI_InitStructure.SPI_DataSize = SPI_DataSize_8b; // 数据长度为8
	SPI_InitStructure.SPI_CRCPolynomial = 7;
	SPI_InitStructure.SPI_CPOL = SPI_CPOL_High;
	SPI_InitStructure.SPI_CPHA = SPI_CPHA_2Edge; // 空闲时为高电平,偶数边沿
	SPI_InitStructure.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_4;
	
	// 初始化SPI
	SPI_Init(OLED_SPI, &SPI_InitStructure);
	
	// 使能SPI
	SPI_Cmd(OLED_SPI, ENABLE);
}

void OLED_SPI_Write(uint8_t data) {
	
	// 判断 SPI的 发送缓冲区是否为空?
	while(SPI_I2S_GetFlagStatus(OLED_SPI, SPI_I2S_FLAG_TXE) == RESET);
	
	SPI_I2S_SendData(OLED_SPI, data);
}


SPI模块的配置如上面的代码所示,关于SPI协议,在本贴中,不会提及,请感兴趣的读者去阅读STM32的参考手册。要提及的一点是,SPI_InitStructure.SPI_NSS需要设置成软件控制,如果有硬件控制,可能OLED无法显示数据,我个人认为,可能是如果通过硬件控制,NSS端口可能以极快的频率在高低电平之间来回切换,导致采集数据时,OLED无法被作为从设备选中,这是一家之言,如果有不正确之处,请大家指正。

OLED模块如下:

#ifndef __OLED_H
#define	__OLED_H

#include "stm32f10x.h"

#define OLED_ADDRESS	0x78 //通过调整0R电阻,屏可以0x78和0x7A两个地址 -- 默认0x78
#define OLED_CMD		0
#define OLED_DATA		1

void WriteCmd(uint8_t SPI_Command);
void WriteData(uint8_t SPI_Data);
void OLED_Init(void);
void OLED_ON(void);
void OLED_OFF(void);
void SetPos(uint8_t x, uint8_t y);
void OLED_Fill(uint8_t Fill_Data);
void OLED_Clean(void);
void OLED_ShowStr(uint8_t x, uint8_t y, char ch[], uint8_t TextSize);

#endif
#include "spi.h"
#include "oled.h"
#include "bsp_systick.h"
#include "codetab.h"

// 设置oled的显存
// 存放格式如下
// [0] 0 1 2 3 ... 127
// [1] 0 1 2 3 ... 127
// [2] 0 1 2 3 ... 127
// [3] 0 1 2 3 ... 127
// [4] 0 1 2 3 ... 127
// [5] 0 1 2 3 ... 127
// [6] 0 1 2 3 ... 127
// [7] 0 1 2 3 ... 127
uint8_t OLED_GRAM[128][8];

// 初始化 OLED模块0
void OLED_Init(void) {
	
	// 使能相关的GPIO口 配置SPI外设
	OLED_SPI_Init();	
	
	OLED_SPI_RES_HIGH;
	// 延时200ms
	Delay_us(200);
	
	WriteCmd(0xAE); //display off
	WriteCmd(0x20);	//Set Memory Addressing Mode	
	WriteCmd(0x10);	//00,Horizontal Addressing Mode;01,Vertical Addressing Mode;10,Page Addressing Mode (RESET);11,Invalid
	WriteCmd(0xb0);	//Set Page Start Address for Page Addressing Mode,0-7
	WriteCmd(0xc8);	//Set COM Output Scan Direction
	WriteCmd(0x00); //---set low column address
	WriteCmd(0x10); //---set high column address
	WriteCmd(0x40); //--set start line address
	WriteCmd(0x81); //--set contrast control register
	WriteCmd(0xff); //亮度调节 0x00~0xff
	WriteCmd(0xa1); //--set segment re-map 0 to 127
	WriteCmd(0xa6); //--set normal display
	WriteCmd(0xa8); //--set multiplex ratio(1 to 64)
	WriteCmd(0x3F); //
	WriteCmd(0xa4); //0xa4,Output follows RAM content;0xa5,Output ignores RAM content
	WriteCmd(0xd3); //-set display offset
	WriteCmd(0x00); //-not offset
	WriteCmd(0xd5); //--set display clock divide ratio/oscillator frequency
	WriteCmd(0xf0); //--set divide ratio
	WriteCmd(0xd9); //--set pre-charge period
	WriteCmd(0x22); //
	WriteCmd(0xda); //--set com pins hardware configuration
	WriteCmd(0x12);
	WriteCmd(0xdb); //--set vcomh
	WriteCmd(0x20); //0x20,0.77xVcc
	WriteCmd(0x8d); //--set DC-DC enable
	WriteCmd(0x14); //
	WriteCmd(0xaf); //--turn on oled panel
}

void WriteCmd(uint8_t SPI_Command) {
	
	OLED_SPI_DC_LOW;
	
	OLED_SPI_Write(SPI_Command);
}

void WriteData(uint8_t SPI_Data) {
	
	OLED_SPI_DC_HIGH;
	
	OLED_SPI_Write(SPI_Data);
}

// 打开OLED
void OLED_ON(void) {
	
	WriteCmd(0x8D); // 设置电荷泵
	WriteCmd(0x14); // 开启电荷泵
	WriteCmd(0xAF); // OLED唤醒
}

// 关闭OLED
void OLED_OFF(void) {

	WriteCmd(0x8D); // 设置电荷泵
	WriteCmd(0x10); // 关闭电荷泵
	WriteCmd(0xAE); // 关闭OLED
}

// 设置起始坐标
void SetPos(uint8_t x, uint8_t y) {
	
	// 设置页地址
	WriteCmd(0xb0 + y);
	// 取列高位
	WriteCmd((x & 0xf0)>>4 | 0x10);
	// 取列低位
	WriteCmd((x & 0x0f) | 0x01);
}

// 全屏填充
void OLED_Fill(uint8_t Fill_Data) {
	
	uint8_t m, n;
	// 设置起始地址
	for (m = 0; m < 8; m++) {
		WriteCmd(0xb0 + m);
		WriteCmd(0x00);
		WriteCmd(0x10);
	}
	
	// 填充数据
	for (n = 0; n < 128; n++) {
		WriteData(Fill_Data);
	}
}

// 清屏
void OLED_Clean(void) {
	
	OLED_Fill(0x00);
}

// 显示字符串
void OLED_ShowStr(uint8_t x, uint8_t y, char ch[], uint8_t TextSize) {
	
	uint8_t c = 0, i =0, j = 0;	
	switch(TextSize) {
		
		// 模式1:6x8点阵
		// 6列 1组
		case 1: {
			while(ch[j] != '\0') {
				
				c = ch[j] - 32;
				if (x > 126) {
					x = 0;
					y++;
				}
				SetPos(x, y);
				for (i = 0; i < 6; i++) {
					WriteData(F6x8[c][i]);
				}
				x += 6;
				j++;
			}
		}break;
		
		// 模式2: 8x16点阵 两页
		case 2: {
			
			while(ch[j] != '\0') {
				
				c = ch[j] - 32; // 字符偏移量,字库上的字体序号和ASCII码表上相差32
				if (x > 120) {
					x = 0;
					y++;
				}
				SetPos(x, y);
				for (i = 0; i < 8; i++) {
					WriteData(F8X16[c*16+i]);
				}
				SetPos(x,y+1);
				for(i=0;i<8;i++) {
					WriteData(F8X16[c*16+i+8]);
				}
				x += 8;
				j++;
			}
		}break;
	}
}

对于OLED模块中的相关函数,重点介绍一下OLED_ShowStr(uint8_t x, uint8_t y, char ch[], uint8_t TextSize),这是官方提供的函数。

对于OLED_ShowStr函数,它的参数x, y代表在屏幕中进行写操作时的起始坐标值,如果我们选择的是6x8模式,也就是6列,8行来表示一个字符,那么0 ~ 127中,最大能整除6的数字是126,即x的最大值是125(包括0),当x大于126时,便会开启下一页的写操作,如下:

if (x > 126) {
	x = 0;
	y++;
}

那么问题来了,如何理解下面的表达式:

c = ch[j] - 32;

比如要想显示A字母,A字母的ASCII码值是65,那么65 - 32 = 33,33就对应着字库(注:字库文件在codetab.h文件中定义,因为篇幅原因,我就不贴出来了,大家可以通过淘宝厂家提供的百度网盘链接找到)中A字母的编号33,那么我们可以通过找到A的编号,从而找到它的编码,从而在屏幕中打印出来。

以此类推,F8X16是一个数组,每个元素是一个8位的char类型,字库中将其分行,每行有16个字符,A在33行,所以,33*16能取到A的第一个编码值,然后按顺序,从1 ~ 16,一列列地将A字母从屏幕上打印出来。

#include "stm32f10x.h"
#include "led.h"
#include "bsp_systick.h"
#include "spi.h"
#include "oled.h"


int main() {
	
	SysTick_init();
	
	LED_Init();
	
	OLED_Init();
	
	OLED_Clean();
	
	OLED_ShowStr(0, 1, "hello world", 1);
	OLED_ShowStr(0, 2, "hello world", 2);
	
	while(1) {
	
	}
}
c = ch[j] - 32;

比如要想显示A字母,A字母的ASCII码值是65,那么65 - 32 = 33,33就对应着字库(注:字库文件在codetab.h文件中定义,因为篇幅原因,我就不贴出来了,大家可以通过淘宝厂家提供的百度网盘链接找到)中A字母的编号33,那么我们可以通过找到A的编号,从而找到它的编码,从而在屏幕中打印出来。

以此类推,F8X16是一个数组,每个元素是一个8位的char类型,字库中将其分行,每行有16个字符,A在33行,所以,33*16能取到A的第一个编码值,然后按顺序,从1 ~ 16,一列列地将A字母在屏幕上打印出来。文章来源地址https://www.toymoban.com/news/detail-627896.html

#include "stm32f10x.h"
#include "led.h"
#include "bsp_systick.h"
#include "spi.h"
#include "oled.h"


int main() {
	
	SysTick_init();
	
	LED_Init();
	
	OLED_Init();
	
	OLED_Clean();
	
	OLED_ShowStr(0, 1, "hello world", 1);
	OLED_ShowStr(0, 2, "hello world", 2);
	
	while(1) {
	
	}
}

到了这里,关于STM32F103ZET6 驱动 OLED的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • AD7606与STM32F103ZET6的串行通信

      本文是AD7606与STM32的串行通信的学习心得,可帮助你快速入门AD7606。   图一   图二   图三   图四   根据图一,一些引脚在置高或置低时的上升或下降沿会受时间影响,因此在编写代码时,一些对引脚的操作需要放在一起,且延时函数不能随意使用。   图

    2024年02月08日
    浏览(35)
  • 用正点原子STM32F103ZET6精英板控制舵机转动实验保姆教程

    正点原子精英板一块 Jlink4线SWD下载线一根 精英板usb供电/下载线一根(负责给开发板供电) SG90舵机一个(三线:其中红线接5V电压,棕线接GED,橙黄色为信号线接开发板PB5引脚,舵机所给为3pin杜邦线母头,可用单根杜邦线(一头子一头母)将舵机线飞开接到精英板上)。 以

    2023年04月15日
    浏览(25)
  • STM32F103ZET6 封装 LQFP-144 ST意法 单片机芯片

    STM32F103ZET6 是意法半导体(STMicroelectronics)生产的一款基于 ARM Cortex-M3 内核的 32 位微控制器。它具有高性能、低功耗的特点,广泛应用于各种嵌入式系统和工业应用中。STM32F103ZET6 的主要特点如下: 内核:ARM Cortex-M3,工作频率最高可达 72MHz。 存储器:64KB SRAM,512KB FLASH。 外

    2024年04月22日
    浏览(34)
  • STM32F103ZET6【标准库函数开发】------04五个串口的详细配置

    正点原子战舰开发板 STM32F103ZET6有5个串口,查看引脚图可以找到对应的IO口分别如下 串口 USART1 USART2 USART3 UART4 UART5 输入/输出方式 USARTx_TX PA9 PA2 PB10 PC10 PC12 复用推挽输出 USARTx_RX PA10 PA3 PB11 PC11 PD2 浮空输入 USART1挂在APB2下 USART2,USART3,USART4,USART5挂在APB1下 串口调试助手设置波特率

    2024年02月03日
    浏览(80)
  • STM32---stm32f103c8t6与stm32f103zet6之间的代码移植转换

    目录 一、将c8t6转换为zet6 1、修改启动文件 2、修改芯片 3、将MD修改为HD  4、下载器的修改 5、修改完成,编译成功  二、将zet6转换为c8t6 最终结果如下:   将STM32F103C8改为STM32F103ZE   基本相同,反向即可。    

    2024年02月06日
    浏览(17)
  • MDK Keil5 创建Stm32工程-理论篇(这里以Stm32F103Zet6为例)

    整个工程可以粗略的划分为几个文件夹: BSP 底层驱动比如GPIOTimer等驱动文件 CMSIS 内核相关的文件 Firmware 生成的固件下载文件 Mycode 用户编写的相关文件,主要编写的文件都在这个文件夹里 Project 工程文件 startup 芯片启动文件 STM32F10x_FWLib 标准库文件 USER 主函数等文件 readm

    2023年04月24日
    浏览(47)
  • 【LVGL】STM32F103ZET6——LVGL_GUI_GUIDER移植过程成功

    STM32F103ZET6——LVGL_GUI_GUIDER移植过程 STM32F103ZET6——LVGL_GUI_GUIDER移植过程 使用工具: 1.LVGL库8.02 2.GUI_GUIDER 3.keil5 设计出来的总体是这样 提示:以下是本篇文章正文内容,下面案例可供参考 这部分有很多大佬已经写的很成熟了,我就不赘述了 安装包在这里硬件资源 右上角可将

    2024年02月12日
    浏览(19)
  • 正点原子stmf103zet6代码移植为stm32f103c8t6(库函数版)

    目录 1、打开正点原子的工程模板template, 点击魔术棒  2、 修改芯片型号 为stm32f103c8

    2024年02月01日
    浏览(25)
  • STM32F103ZET6 GPIO工作模式介绍+使用寄存器点亮第一个LED灯

    目录  GPIO的工作模式介绍 1.输入模式(模拟、上拉、下拉、浮空) 2.输出模式(推挽/开漏) 3.复用功能(推挽/开漏) 4.模拟输入输出(上下拉无影响) 如何使用寄存器点亮第一个LED灯         在输入模式时,施密特触发器打开,输出被禁止。可通过输入数据寄存器 GPIOx_

    2024年02月06日
    浏览(20)
  • 基于STM32F103ZET6的(单/三)路HC-SR04超声波测距+TFTLCD实时显示+距离报警

    一、成果图 说明:本程序的源码地址: https://github.com/Lfy-YF/Campus-Project            CSDN下载连接:https://download.csdn.net/download/weixin_58849239/87829470 源码包含四个版本,涉及单路测距、三路测距、增加外部中断(用来版本记录的~) 运行效果: 本程序实现脱机测距,共左中右

    2024年02月11日
    浏览(15)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包