一、环境介绍

单片机采用: STM32F103ZET6

编程软件: keil5

编程语言: C语言

编程风格:  寄存器开发.

目标芯片: XPT2046---标准SPI接口时序

二、XPT2046芯片介绍

2.1  功能

XPT2046是一颗12位的ADC芯片,可以当做普通的ADC芯片使用,但是一般都是用在电阻触摸屏上,方便定位触摸屏坐标。

图1: XPT2046内部原理图

 图2:电阻触摸屏---引出的4条线就接在XPT2046的YN\XN\YP\XP上

(XPT2046支持笔中断输出--低电平有效,这个引脚可以配置到单片机的中断脚上,或者轮询判断这个引脚状态,判断触摸屏是否已经按下)

 可以单独买一个触摸屏+一个XPT2046就可以自己做手画板、触摸按键(自己用一张纸在下面画个模型就行)、等等很多小玩意。

图3:采用的电阻触摸屏的LCD屏(上面盖的哪一层薄膜就是触摸用的)

2.2 特性

1. 工作电压范围为 2.2V~5.25V
2. 支持 1.5V~5.25V 的数字 I/O 口
3. 内建 2.5V 参考电压源
4. 电源电压测量(0V~6)
5. 内建温度测量功能
6. 触摸压力测量
7. 采用 SPI 3线控制通信接口
8. 具有自动 power-down 功能
9.  封装:QFN-16、 TSSOP-16 和 VFBGA-48与 TSC2046、 AK4182A 完全兼容
10.  XPT2046 在 125KHz 转换速率和 2.7V 电压下的功耗仅为750 µW。 XPT2046 11. 以其低功耗和高速率等特性,被广泛应用在采用电池供电的小型手持设备上,比如 PDA、手机等。
12. XPT2046 有 TSSOP-16、 QFN-16 和 VFBGA 三种封装形
式,温度范围是 - 40 ~ + 85℃ 。

2.3  工作原理

XPT2046 是一种典型的逐次逼近型模数转换器(SAR ADC),包含了采样/保持、模数转换、串口数据输出等功能。同时芯片集成有一个 2.5V的内部参考电压源、温度检测电路,工作时使用外部时钟。 XPT2046 可以单电源供电,电源电压范围为 2.7V~5.5V。参考电压值直接决定ADC的输入范围,参考电压可以使用内部参考电压,也可以从外部直接输入1V~VCC范围内的参考电压(要求外部参考电压源输出阻抗低)。 X、 Y、 Z、 VBAT、 Temp和AUX模拟信号经过片内的
控制寄存器选择后进入ADC, ADC可以配置为单端或差分模式。选择VBAT、 Temp和AUX时可以配置为单端模式;作为触摸屏应用时,可以配置为差分模式,这可有效消除由于驱动开关的寄生电阻及外部的干扰带来的测量误差,提高转换准确度。

典型的应用:

单端工作模式

SER/DFR置为高电平时, XPT2046 工作在为单端模式,单端工作模式的应用原理如下图所示。
单端模式简单,在采样过程完成后,转换过程中可以关闭驱动开关,降低功耗。但这种模式的缺点是精度直接受参考电压源的精度限制,同时由于内部驱动开关的导通电阻存在,导通电阻与触摸屏电阻的分压作用,也会带来测量误差。

(图片里的A2 A1 A0 ,还有上面说的SER/DFR就是XPT2046的配置命令,具体使用方法在后面会讲到)

差分工作模式

SER/DFR置为低电平时, XPT2046 为差分工作模式.
差分模式的优点是: +REF 和-REF 的输入分别直接接到 YP、 YN 上,可消除由于驱动开关的导通电阻引入的坐标测量误差。
缺点是:无论是采样还是转换过程中,驱动开关都需要接通,相对单端模式而言,功耗增加了。
如果不考虑功耗的话,当前就选择差分工作模式了。

(图片里的A2 A1 A0 ,还有上面说的SER/DFR就是XPT2046的配置命令,具体使用方法在后面会讲到)

2.3  XPT2046采集并转换一次数据的时序介绍

XPT2046 数据接口是串行接口,处理器和转换器之间的通信需要 8 个时钟周期,可采用 SPI、 SSI 和 Microwire 等同步串行接口。一次完整的转换需要 24 个串行同步时钟(DCLK)来完成。

前 8 个时钟用来通过DIN引脚输入控制字节。当转换器获取有关下一次转换的足够信息后,接着根据获得的信息设置输入多路选择器和参考源输入,并进入采样模式,如果需要,将启动触摸面板驱动器。 3 个多时钟周期后,控制字节设置完成,转换器进入转换状态。这时,输入采样-保持器进入保持状态,触摸面板驱动器停止工作(单端工作模式)。

接着的12 个时钟周期将完成真正的模数转换。如果是度量比率转换方式(SER/DFR ——=0),驱动器在转换过程中将一直工作,第13 个时钟将输出转换结果的最后一位。剩下的 3 个多时钟周期将用来完成被转换器忽略的最后字节(DOUT置低)。

时序图如下:

时序图里的控制命令字节:

位 7(MSB) 位 6 位 5 位 4 位 3 位 2 位 1 位 0(LSB)
S A2 A1 A0 MODE SER/DFR  PD1 PD0

控制字节每个位的含义如下:

名称 功能描述
7 S 开始位。为 1 表示一个新的控制字节到来,为 0 则忽略 PIN 引脚上数据
6-4 A2-A0 通道选择位。这个在上面已经介绍过了
3 MODE 12 位/8 位转换分辨率选择位。为 1 选择 8 位为转换分辨率,为 0 选择 12 位分辨率
2 SER/DFR 单端输入方式/ 差分输入方式选择位。为 1 是单端输入方式,为 0 是差分输入方式
1-0 PD1-PD0 低功率模式选择位。若为11,器件总处于供电状态;若为00,器件在变换之间处于低
功率模式

注意: 差分模式仅用于 X 坐标、 Y 坐标和触摸压力的测量,其它测量要求采用单端模式。

根据上面表格的介绍,可以得到在差分模式下,选择12位分辨率,测量X和Y坐标的两个命令:0xD0 和 0x90

XPT2046还有其他模式,可以测量温度,笔中断的开关(默认是开着的),16时钟周期转换,15时钟周期转换,这些就不再介绍。 根据前面的介绍用在触摸屏上测量XY坐标的功能已经满足了。

2.4 SPI时序介绍

这里的XPT2046支持标准3线SPI接口,关于SPI时序的介绍,在前面文章里有介绍过。

参考这里: https://blog.csdn.net/xiaolong1126626497/article/details/117648539

2.5 物理坐标与屏幕坐标的转换

正常在LCD屏上使用触摸屏,肯定是需要将采集的原始X、Y值转为LCD屏的屏幕坐标才好使用。

转换的方法有很多,这里采用最简单的角系数计算方法转换。

比如,我使用的LCD屏是3.5寸的,分辨率是320*480。

1. 得到触摸屏左上角和右下角的坐标XY极限值
  x=3831,y=3934
  x=155,y=168

2. 转换坐标值
  x坐标:3831~155 -->  3676~0
  y坐标:3934~168 -->  3766~0

3. 计算斜率
  x坐标的斜率: 3676/320=11.4875
  y坐标的斜率: 3766/480=7.84583

 4. 得到实际的像素坐标
  x坐标:  320-(实时采集的当前X模拟量-155)/11.4875
  y坐标:  480-(实时采集的当前Y模拟量-168)/7.84583

这里相减的原因: 因为我测试用的触摸屏采集出来的X、Y值大小和LCD屏的屏幕坐标值大小是反过来的。

三、示例代码

采用SPI模拟时序驱动,其他平台都可以移植。

3.1 xpt2046.c

#include "xpt2046_touch.h"
struct XPT2046_TOUCH xpt2046_touch;/*
函数功能:  初始化
硬件连接:
T_MOSI--PF9
T_MISO--PB2
T_SCK---PB1
T_PEN---PF10
T_CS----PF11
*/
void XPT2046_TouchInit(void)
{/*1. 时钟初始化*/RCC->APB2ENR|=1<<3; //PBRCC->APB2ENR|=1<<7; //PF/*2. 初始化GPIO口*/GPIOB->CRL&=0xFFFFF00F;GPIOB->CRL|=0x00000830;GPIOF->CRH&=0xFFFF000F;GPIOF->CRH|=0x00003830;/*3. 上拉*/GPIOB->ODR|=0x3<<1;GPIOF->ODR|=0x7<<9;
}/*
函数功能:  SPI底层写一个字节
*/
void XPT2046_SPI_WriteOneByte(u8 cmd)
{u8 i;for(i=0;i<8;i++){XPT2046_SCK=0; //低电平写if(cmd&0x80)XPT2046_MOSI=1;else XPT2046_MOSI=0;cmd<<=1;XPT2046_SCK=1; //高电平读,保证数据线稳定}
}/*
函数功能:  读2个字节
说明: 读取16位数据,最低4位数据无效,有效数据是高12位*/
u16 XPT2046_ReadData(u8 cmd)
{u16 data;u8 i;XPT2046_CS=0;  //选中XPT2046XPT2046_MOSI=0;XPT2046_SCK=0;XPT2046_SPI_WriteOneByte(cmd);DelayUs(8); //0.008ms ,等待XPT2046转换完成。//消除忙信号XPT2046_SCK=0;DelayUs(1);XPT2046_SCK=1;//连续读取16位的数据for(i=0;i<16;i++){XPT2046_SCK=0; //通知XPT2046,主机需要数据XPT2046_SCK=1; data<<=1;if(XPT2046_MISO)data|=0x01;}data>>=4; //丢弃最低4位XPT2046_CS=1; //取消选中return data;
}/*
XPT2046的命令:10010000  :测试Y的坐标 0x90
11010000  :测试X的坐标 0xD0返回值:  0表示没有读取到坐标,1表示读取到当前坐标//1. 得到左上角和右下角的坐标XY极限值x=3831,y=3934x=155,y=168//2. 转换坐标值x坐标:3831~155 -->  3676~0y坐标:3934~168 -->  3766~0//3. 计算斜率x坐标的斜率: 3676/320=11.4875y坐标的斜率: 3766/480=7.84583//4. 得到实际的像素坐标x坐标:  320-(模拟量-155)/11.4875y坐标:  480-(模拟量-168)/7.84583
*/
u8 XPT2046_ReadXY(void)
{if(XPT2046_PEN==0) //判断触摸屏是否按下{/*1. 得到物理坐标*/xpt2046_touch.x0=XPT2046_ReadData(0xD0);xpt2046_touch.y0=XPT2046_ReadData(0x90);/*2. 得到像素坐标*/xpt2046_touch.x=320-(xpt2046_touch.x0-155)/11.4875;xpt2046_touch.y=480-(xpt2046_touch.y0-168)/7.84583;return 1;}return 0;
}

3.2 xpt2046.h

#ifndef XPT2046_TOUCH_H
#define XPT2046_TOUCH_H
#include "stm32f10x.h"
#include "sys.h"
#include "delay.h"//触摸屏引脚定义
#define XPT2046_MOSI PFout(9)
#define XPT2046_MISO PBin(2)
#define XPT2046_SCK PBout(1)
#define XPT2046_CS  PFout(11)
#define XPT2046_PEN PFin(10)//函数声明
void XPT2046_TouchInit(void);
void XPT2046_SPI_WriteOneByte(u8 cmd);
u8 XPT2046_ReadXY(void);//存放触摸屏信息的结构体
struct XPT2046_TOUCH
{u16 x0; //物理坐标xu16 y0; //物理坐标yu16 x;  //像素坐标xu16 y;  //像素坐标y
};
extern struct XPT2046_TOUCH xpt2046_touch;
#endif

STM32入门开发:编写XPT2046电阻触摸屏驱动(模拟SPI)相关推荐

  1. STM32F1与STM32CubeIDE编程实例-XPT2046电阻触摸屏驱动

    XPT2046电阻触摸屏驱动 1.XPT2046介绍 XPT2046 是一款 4 线电阻式触摸屏控制器,包含一个 12 位 125 kHz 采样 SAR 型 A/D 转换器.XPT2046支持1.5V ...

  2. STM32入门开发: 编写DS18B20温度传感器驱动(读取环境温度、支持级联)

    一.环境介绍 编程软件: keil5 操作系统: win10 MCU型号: STM32F103C8T6 STM32编程方式: 寄存器开发 (方便程序移植到其他单片机) 温度传感器: DS1820 DS ...

  3. openharmony移植之编写电阻触摸屏驱动

    之前有写过一篇关于Gt911触摸的文章,今天写一篇关于如何在openharmony上调试电阻屏触摸驱动, 首先需要修改如下两个文件,将我们的驱动文件加入驱动编译框架中, diff --git a/dr ...

  4. STM32入门开发: 制作红外线遥控器(智能居家-万能遥控器)

    一.环境介绍 MCU: STM32F103ZET6 编程软件环境: keil5 红外线传输协议:  NEC协议---38KHZ载波:.NEC协议是红外遥控协议中常见的一种. 编码发送思路:  延时函数 ...

  5. F1C100S电阻触摸屏驱动

    https://whycan.cn/t_2143.html 移植触摸屏驱动. 移植后遇到的问题,触摸中断一直在触发.[原因:由于rtp引脚复用没有设置] //读0x01C20800寄存器,可以看到没有 ...

  6. Linux驱动开发-编写PCF8591(ADC)芯片驱动

    1. PCF8591介绍 PCF8591是一个IIC总线接口的ADC/DAC转换芯片,功能比较强大,这篇文章就介绍在Linux系统里如何编写一个PCF8591的驱动,完成ADC数据采集,DAC数据输出 ...

  7. Linux驱动开发学习笔记-电容触摸屏驱动

    <电容触摸屏驱动框架> 电容触摸屏驱动其实是以下几种 linux 驱动框架的组合: ① IIC 设备驱动,因为电容触摸 IC 基本都是 IIC 接口的,因此大框架就是 IIC 设备驱动. ...

  8. STM32入门开发工具整理总结

    本文介绍一下STM32开发都有什么工具,资料需要到什么地方下载. 一.STM32资料 ST对于其新的32bit MCU平台的重视程度可从其提供的应用笔记的数量和相应的参考代码上可见一斑. STM32的 ...

  9. Linux驱动开发-编写VS1053芯片音频驱动

    1. 前言 VS1053是一款硬件编解码的音频芯片,提供SPI接口和IIS接口两种通信协议,这篇文章是介绍在Linux下如果模拟SPI时序来操作VS1053完成录音.播放音频歌曲功能.但是没有注册标准 ...

  10. stm32基于FreeRtos下的电阻触摸屏简易计算器

    先上代码: void Draw_Keyboard_Layout(void) {LCD_ShowString(5,25,200,16,16,"Power by Vincent-NJW" ...

最新文章

  1. ​相似算法比较:递归、分治、动态规划、贪心、回溯、分支限界​
  2. 如何在Keras中训练大型数据集
  3. ElasticSearch 索引详解
  4. ASP.NET MVC 的一个配置节点
  5. 4MLinux 24.0 发布
  6. python分位数回归模型_如何理解分位数回归风险价值 (VaR) 模型?
  7. “控本焦虑”的工程企业 用钉钉宜搭找到了低成本数字化的“捷径”
  8. 变相裁员??全员营销!程序员被要求卖房~
  9. python 高性能http服务器_Python高性能HTTP客户端
  10. 八月实施:电动自行车3c认证,电动自行车CCC认证费用周期,办理电动自行车ccc认证机构
  11. mysql数据库实训总结_数据库实训报告
  12. 【2020GAN】对抗生成网络论文收录(1月-6月)
  13. 政府采购和招标投标常见问题:评标的依据是什么?
  14. loop与for loop分别实现乘法口诀表
  15. 数据库批量插入和存在的问题
  16. 用户态网络协议栈-OFP-网络框架分享
  17. MavenLombok
  18. HTML5+CSS3-边框背景图、多背景图、CSS选择器、网络字体、边框背景图片、过渡、放大、旋转
  19. 猿人学试题(非常简单js混淆、雪碧图、样式干扰 css加密、js混淆源码乱码、js混淆动态cookie、访问逻辑)
  20. MISAG与MIMAG:基因组质量评估标准

热门文章

  1. 学海无涯!马士兵的Java教程
  2. kms服务器修改,kms服务器ip地址修改
  3. 检测MOS管五种方法
  4. 8.cisco思科模拟器无线路由器设备实训练习
  5. 思科模拟器交换机路由器常用命令
  6. 素数表(Prime number table)
  7. ppt 制作海报 导出高分辨率图片
  8. java计算机毕业设计风情旅游网站源码+mysql数据库+系统+lw文档+部署
  9. Android下载文件,如何获取实际的文件名
  10. w10计算机管理权限,设置win10管理权限_win10系统如何获取管理员权限