1
完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
扫一扫,分享给好友
最近调试了ADS1118芯片,单片机用的是STM32ZET6,用IO口模拟SPI通信,连接两片1118AD采集芯片,讲采集到的八通道数据在串口显示界面打印出来。 下面是.c代码
#include "ADS1118.h" #include "sys.h" #include "usart.h" #include "led.h" #include "delay.h" /* 32-Bit模式下CS引脚可以一直保持为低,节省一个IO口。 32-Bit模式可以细分为两种,一种是把设置寄存器(16bit)写入两次,一种是写入一次后第二次(后16bit)写0。 16-Bit模式要求在每两次通信之间CS(片选)引脚要拉高一次。 每次通信可写入16bit的配置寄存器值和读取到16bit的转换寄存器值。 */ #define INPUT PAin(4) // 数据输入 , 连接芯片的OUT #define OUTPUT PAout(5) // 数据输出 , 连接芯片的DIN #define CS PAout(6) // 片选信号 #define SCK PAout(7) // 时钟信号 #define CS1 PAout(1) // 片选1信号 u16 Conversion ; // 存储从芯片读取的数据 float Voltage ; // 存储需要显示的测量电压值 float BaseV ; // 采集电压的压基 u8 firstflag ; // 第一次进入标志 u8 collect ; // 每次采集的数据位置 float DP[8] ; // 显示处理后的八通道数据 ConfigDef Config ; void ADS1118GPIOInit(void) { GPIO_InitTypeDef GPIO_InitStructure; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP ; // PA6作为片选输出信号,设置为推挽输出 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 ; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz ; GPIO_Init(GPIOA , &GPIO_InitStructure) ; GPIO_SetBits(GPIOA,GPIO_Pin_6); // 片选初始化为高 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP ; // PA5作为数据输出信号,初始设置为推挽输出 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5 ; GPIO_Init(GPIOA , &GPIO_InitStructure) ; GPIO_ResetBits(GPIOA,GPIO_Pin_5); // 数据输出口初始化为低 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP ; // PA7作为时钟信号,设置为推挽输出 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7 ; GPIO_Init(GPIOA , &GPIO_InitStructure) ; GPIO_ResetBits(GPIOA,GPIO_Pin_7); // 时钟初始化为低 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP ; // PA1作为片选1输出信号,设置为推挽输出 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1 ; GPIO_Init(GPIOA , &GPIO_InitStructure) ; GPIO_SetBits(GPIOA,GPIO_Pin_1); // 片选初始化为高 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPD ; // PA4作为数据输入信号,设置为下拉输入 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4 ; GPIO_Init(GPIOA , &GPIO_InitStructure) ; } // 当新数据准备好检索时,此引脚变为低电平 // 在连续转换模式下,如果未从器件中检索到任何数据,则DOUT / DRDY在下一个数据就绪信号(DOUT / DRDY为低电平)之前的8 μs再次变为高电平 /********************************************************** 函数名称:RWByte 函数功能:SPI发送接收数据 函数参数:需要配置的寄存器数据 函数返回:采集到的16位数据 函数隶属:Display 创建日期:2020/04/17 14:23 作 者:Jerry 注 解: **********************************************************/ u16 RWByte(u16 DATA) { u8 t ; u16 returndata ; delay_ms(1); for(t=0;t<16;t++) { if(DATA&0x8000) // 每次向从机写八位数据,芯片在时钟下降沿锁存DIN数据 { OUTPUT = 1 ; } else { OUTPUT = 0 ; } DATA<<=1; SCK = 1 ; delay_ms(1); returndata<<=1; if(INPUT == 1) // 每次读取从机中的八位数据,芯片在时钟上升沿将数据移出 { returndata|=0x0001 ; } SCK = 0 ; delay_ms(1); } SCK = 0 ; delay_ms(1); OUTPUT = 0 ; return returndata ; } /********************************************************** 函数名称:ADS1118Init 函数功能:初始化时配置一些不常改变的寄存器值 函数参数:单次转换,工作模式,传输速率,上拉使能,更新数据 函数返回:无 函数隶属:main 创建日期:2020/04/17 14:23 作 者:Jerry 注 解: **********************************************************/ void ADS1118Init(u8 ss,u8 mode ,u8 dr,u8 pue,u8 nop) { Config.ConfigDef_T.SS = ss ; // 设置为无效果 Config.ConfigDef_T.MODE = mode ; // 设置为连续转换模式 Config.ConfigDef_T.DR = dr ; // 设置转换速率为128 SPS Config.ConfigDef_T.PULL_UP_EN = pue ; // 设置DOUT上拉使能 Config.ConfigDef_T.NOP = nop ; // 设置有效数据,更新配置寄存器 Config.ConfigDef_T.CNV_RDY_FL = 0x01 ; // 保留位,始终写1 Conversion = 0 ; Voltage = 0 ; BaseV = 0 ; firstflag = 0 ; } /********************************************************** 函数名称:Getdata 函数功能:配置寄存器值并连续采集五次数据求平均值 函数参数:通道选择,工作模式,传输速率,上拉使能,更新数据 函数返回:无 函数隶属:main 创建日期:2020/04/17 14:23 作 者:Jerry 注 解: **********************************************************/ void Getdata(u8 mux,u8 pga,u8 tsmode,u8 choose) { float FV[10] ; // 存储连续的五次转换数据 u8 t ; float displaydata ; Config.ConfigDef_T.MUX = mux ; // 设置为AIN0和GND Config.ConfigDef_T.PGA = pga ; // 设置FSR=±4.096V Config.ConfigDef_T.TS_MODE = tsmode ; // 设置温度传感器模式为ADC模式 switch (pga) { case 0 : BaseV = 187.5 ; // 压基单位为uV break ; case 1 : BaseV = 125 ; break ; case 2 : BaseV = 62.5 ; break ; case 3 : BaseV = 31.25 ; break ; case 4 : BaseV = 15.625 ; break ; case 5 : BaseV = 7.8125 ; break ; } for(t=0;t<5;t++) { switch(choose) { case CS_0 : CS = 0 ; CS1 = 1 ; break; case CS_1 : CS = 1 ; CS1 = 0 ; break; } delay_ms(1); if((INPUT == 0)||(firstflag == 0)) // CS需要周期性拉低来检测是否有新的数据产生(检测INPUT引脚是否有低电平) { Conversion = RWByte(Config.Bytes); Voltage = (BaseV*Conversion)/1000000 ; // 转换单位:uV→V Conversion = 0 ; // 数据显示之后清零 firstflag = 1 ; } CS = 1 ; CS1 = 1 ; FV[t] = Voltage ; delay_ms(15); // 延迟时间不能低于15ms } displaydata = (FV[1]+FV[2]+FV[3]+FV[4] )/4; if(choose == CS_0) { switch(mux) { case ADS1118_MUX_0G: DP[0] = displaydata ; break ; case ADS1118_MUX_1G: DP[1] = displaydata ; break ; case ADS1118_MUX_2G: DP[2] = displaydata ; break ; case ADS1118_MUX_3G: DP[3] = displaydata ; break ; } } else if(choose == CS_1) { switch(mux) { case ADS1118_MUX_0G: DP[4] = displaydata ; break ; case ADS1118_MUX_1G: DP[5] = displaydata ; break ; case ADS1118_MUX_2G: DP[6] = displaydata ; break ; case ADS1118_MUX_3G: DP[7] = displaydata ; break ; } } } void dayin(void) { u8 x ; printf("采集到的数据为 = "); for(x=0;x<8;x++) { printf("%3.3f ",DP[x]); } printf("rn"); } #ifndef __ADS1118_H #define __ADS1118_H #include "sys.h" /**单次转换启动**/ #define ADS1118_SS_NONE 0 // 无效 #define ADS1118_SS_ONCE 1 // 启动单次转换 /**输入多路复用器配置**/ #define ADS1118_MUX_01 0 // 000 = AINP 为 AIN0 且 AINN 为 AIN1(默认) #define ADS1118_MUX_03 1 // 000 = AINP 为 AIN0 且 AINN 为 AIN3 #define ADS1118_MUX_13 2 // 000 = AINP 为 AIN1 且 AINN 为 AIN3 #define ADS1118_MUX_23 3 // 000 = AINP 为 AIN2 且 AINN 为 AIN3 #define ADS1118_MUX_0G 4 // 000 = AINP 为 AIN0 且 AINN 为 GND #define ADS1118_MUX_1G 5 // 000 = AINP 为 AIN1 且 AINN 为 GND #define ADS1118_MUX_2G 6 // 000 = AINP 为 AIN2 且 AINN 为 GND #define ADS1118_MUX_3G 7 // 000 = AINP 为 AIN3 且 AINN 为 GND /**可编程增益放大器配置**/ #define ADS1118_PGA_61 0 // 000 = FSR 为 ±6.144V #define ADS1118_PGA_40 1 // 001 = FSR 为 ±4.096V #define ADS1118_PGA_20 2 // 010 = FSR 为 ±2.048V(默认) #define ADS1118_PGA_10 3 // 011 = FSR 为 ±1.024V #define ADS1118_PGA_05 4 // 100 = FSR 为 ±0.512V #define ADS1118_PGA_02 5 // 101 = FSR 为 ±0.256V /**器件工作模式配置**/ #define ADS1118_MODE_LX 0 // 连续转换模式 #define ADS1118_MODE_DC 1 // 断电并采用单次转换模式(默认) /**数据传输速率**/ #define ADS1118_DR_8 0 // 000 = 8SPS #define ADS1118_DR_16 1 // 001 = 16SPS #define ADS1118_DR_32 2 // 010 = 32SPS #define ADS1118_DR_64 3 // 011 = 64SPS #define ADS1118_DR_128 4 // 100 = 128SPS(默认) #define ADS1118_DR_250 5 // 101 = 250SPS #define ADS1118_DR_475 6 // 110 = 475SPS #define ADS1118_DR_860 7 // 111 = 860SPS /**温度传感器模式**/ #define ADS1118_TS_MODE_ADC 0 // 0 = ADC 模式(默认) #define ADS1118_TS_MODE_T 1 // 1 = 温度传感器模式 /**上拉使能**/ #define ADS1118_PULL_UP_EN_N 0 // 禁用 DOUT/DRDY 引脚的上拉电阻 #define ADS1118_PULL_UP_EN_E 1 // 使能 DOUT/DRDY 引脚的上拉电阻(默认) /**控制数据是否写入配置寄存器**/ #define ADS1118_NOP_N 0 // 00 = 无效数据, 不更新配置寄存器内容 #define ADS1118_NOP_W 1 // 01 = 有效数据, 更新配置寄存器(默认) /**保留**/ #define ADS1118_CNV_RDY_FL 1 // 始终写入 1h /***************************定义ADS1118中的四个16位寄存器********************************/ typedef union { struct { u16 CNV_RDY_FL : 1 ; // [0] 转换完成标志 u16 NOP : 2 ; // [1:2] 无操作 u16 PULL_UP_EN : 1 ; // [3] 上拉使能 u16 TS_MODE : 1 ; // [4] 温度传感器模式 u16 DR : 3 ; // [7:5] 数据传输速率 u16 MODE : 1 ; // [8] 设备运行模式 u16 PGA : 3 ; // [11:9] 可编程增益放大器配置 u16 MUX : 3 ; // [14:12] 输入多路复用器配置 u16 SS : 1 ; // [15] 操作状态或单次转换开始 } ConfigDef_T ; u16 Bytes ; } ConfigDef ; typedef enum { CS_0 = 0 , CS_1 } chipselect; /***************************声明ADS1118中的四个16位寄存器********************************/ extern ConfigDef Config ; void ADS1118GPIOInit(void); void ADS1118Init(u8 ss,u8 mode ,u8 dr,u8 pue,u8 nop) ; void Getdata(u8 mux,u8 pga,u8 tsmode,u8 choose) ; void dayin(void); #endif #include "sys.h" #include "delay.h" #include "usart.h" #include "led.h" #include "ADS1118.h" int main(void) { delay_init(); //延时函数初始化 LED_Init(); //初始化与LED连接的硬件接口 NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); uart_init(115200); ADS1118GPIOInit(); ADS1118Init(ADS1118_SS_NONE,ADS1118_MODE_LX,ADS1118_DR_128,ADS1118_PULL_UP_EN_E,ADS1118_NOP_W); while(1) { Getdata(ADS1118_MUX_0G,ADS1118_PGA_40,ADS1118_TS_MODE_ADC,CS_0); Getdata(ADS1118_MUX_1G,ADS1118_PGA_40,ADS1118_TS_MODE_ADC,CS_0); Getdata(ADS1118_MUX_2G,ADS1118_PGA_40,ADS1118_TS_MODE_ADC,CS_0); Getdata(ADS1118_MUX_3G,ADS1118_PGA_40,ADS1118_TS_MODE_ADC,CS_0); Getdata(ADS1118_MUX_0G,ADS1118_PGA_40,ADS1118_TS_MODE_ADC,CS_1); Getdata(ADS1118_MUX_1G,ADS1118_PGA_40,ADS1118_TS_MODE_ADC,CS_1); Getdata(ADS1118_MUX_2G,ADS1118_PGA_40,ADS1118_TS_MODE_ADC,CS_1); Getdata(ADS1118_MUX_3G,ADS1118_PGA_40,ADS1118_TS_MODE_ADC,CS_1); // LED1 = !LED1 ; dayin(); } } 只给了第一芯片的2引脚和第二芯片的3引脚外接了电位器,其余引脚都为悬空状态。。。。。。。。。。。。。。。。。。。。。。。。 说明: 1,芯片OUT引脚到单片机的输入引脚接的是1K电阻,其余三个引脚都是按照参考手册给的50Ω限流电阻 2,ADS1118.c里面采集数据里有个延时15ms,改小的话会出现错码,不晓得啥原因 3,写与读同时进行的情况下,读到的是上一次配置的数据,所以我在程序里遍历了五遍,摘除第一次的数据后,取后四次的数据求平均值输出显示。。。。。。。。。。。。。。。。。。。。。。。。 第一次发博,格式什么的不管了,希望有用。。。。。。。反正读别人的程序跟吃X一样。。。。 |
|
|
|
只有小组成员才能发言,加入小组>>
调试STM32H750的FMC总线读写PSRAM遇到的问题求解?
1785 浏览 1 评论
X-NUCLEO-IHM08M1板文档中输出电流为15Arms,15Arms是怎么得出来的呢?
1621 浏览 1 评论
1088 浏览 2 评论
STM32F030F4 HSI时钟温度测试过不去是怎么回事?
729 浏览 2 评论
ST25R3916能否对ISO15693的标签芯片进行分区域写密码?
1680 浏览 2 评论
1938浏览 9评论
STM32仿真器是选择ST-LINK还是选择J-LINK?各有什么优势啊?
734浏览 4评论
STM32F0_TIM2输出pwm2后OLED变暗或者系统重启是怎么回事?
570浏览 3评论
596浏览 3评论
stm32cubemx生成mdk-arm v4项目文件无法打开是什么原因导致的?
559浏览 3评论
小黑屋| 手机版| Archiver| 德赢Vwin官网 ( 湘ICP备2023018690号 )
GMT+8, 2024-12-25 01:28 , Processed in 0.692737 second(s), Total 48, Slave 42 queries .
Powered by 德赢Vwin官网 网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
德赢Vwin官网 观察
版权所有 © 湖南华秋数字科技有限公司
德赢Vwin官网 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号