STM32F103ZET6+ADF4351+HMI串口屏

目录

  • STM32F103ZET6+ADF4351+HMI串口屏
    • 功能:
    • 人机界面:
    • STM32F103ZET6程序实现:
      • 程序逻辑:
      • 核心代码:
      • **ADF4351.C**
      • **ADF4351.H**
      • **HMI.C**
      • **HMI.H**
      • **MAIN.C**
    • 硬件:
      • 原理图
      • 概述:
      • 连线
      • 实物图:

功能:

  • 显示当前输出频率

  • 100KHz步进,通过HMI屏幕触控修改

  • 1MHz步进,通过HMI屏幕触控修改

  • 实时修改输出频率,通过HMI屏幕触控修改

人机界面:

人机界面是通过陶晶驰串口屏来实现的,串口屏和单片机通过串口通信,只需设定相同的波特率,就可以实现通信。

HMI可以通过USART HMI软件来写界面,非常的简单方便。

具体界面如下:

  • 输出频率:显示当前ADF4351输出频率
  • 频率步进:如图所示,支持100KHz,1MHz的频率步进
  • 频率校准:点击输入框,唤出数字键盘后,输入目标频率,点击OK, 按下校准键,修改成功,如下图:

STM32F103ZET6程序实现:

程序逻辑:

核心代码:

ADF4351.C

#include "ADF4351.h"
#include "delay.h"//定义32位数据,每一个数字4位,要有8个数字
//这里的数字已经是配置好的了,直接调用就可以写入寄存器里面#define ADF4351_R0         ((u32)0X2C8018)
#define ADF4351_R1          ((u32)0X8029)
#define ADF4351_R2          ((u32)0X10E42)
#define ADF4351_R3          ((u32)0X4B3)
#define ADF4351_R4          ((u32)0XEC803C)
#define ADF4351_R5          ((u32)0X580005)#define ADF4351_R1_Base  ((u32)0X8001)
#define ADF4351_R4_Base ((u32)0X8C803C)
#define ADF4351_R4_ON     ((u32)0X8C803C)
#define ADF4351_R4_OFF  ((u32)0X8C883C)#define ADF4351_RF_OFF   ((u32)0XEC801C)#define ADF4351_PD_ON        ((u32)0X10E42)
#define ADF4351_PD_OFF  ((u32)0X10E02)void ADF_Output_GPIOInit(void)
{GPIO_InitTypeDef GPIO_InitStruct;RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);GPIO_InitStruct.GPIO_Pin = GPIO_Pin_8|GPIO_Pin_9|GPIO_Pin_10|GPIO_Pin_11;GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP; GPIO_Init(GPIOB, &GPIO_InitStruct);}void ADF_Input_GPIOInit(void)
{GPIO_InitTypeDef GPIO_InitStruct;RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);GPIO_InitStruct.GPIO_Pin = GPIO_Pin_8|GPIO_Pin_10|GPIO_Pin_11;GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP; GPIO_Init(GPIOB, &GPIO_InitStruct);GPIO_InitStruct.GPIO_Pin = GPIO_Pin_9;GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IN_FLOATING ; GPIO_Init(GPIOB, &GPIO_InitStruct);
}void delay (int length)
{while (length >0){length--;}
}void WriteToADF4351(u8 count, u8 *buf)
{u8 ValueToWrite = 0;u8 i = 0;u8 j = 0;//    ADF_Output_GPIOInit();  ADF4351_CE = 1;delay_us(1);ADF4351_CLK = 0;ADF4351_LE = 0;delay_us(1);for(i = count; i>0; i--){ValueToWrite = *(buf + i - 1);for(j = 0; j < 8; j++){if(0x80 == (ValueToWrite & 0x80)){ADF4351_OUTPUT_DATA = 1;}else{ADF4351_OUTPUT_DATA = 0;}delay_us(1);ADF4351_CLK = 1;delay_us(1);ValueToWrite <<= 1;ADF4351_CLK = 0;    }}ADF4351_OUTPUT_DATA = 0;delay_us(1);ADF4351_LE = 1;delay_us(1);ADF4351_LE = 0;
}void ReadToADF4351(u8 count, u8 *buf)
{u8 i = 0;u8 j = 0;u8 iTemp = 0;u8 RotateData = 0;ADF_Input_GPIOInit();ADF4351_CE = 1;delay_us(1);ADF4351_CLK = 0;ADF4351_LE = 0;delay_us(1);for(i = count; i > 0; i--){for(j = 0; j < 8; j++){RotateData <<= 1;delay_us(1);iTemp = ADF4351_INPUT_DATA;ADF4351_CLK = 1;if(0x01 == (iTemp & 0x01)){RotateData |= 1;}delay_us(1);ADF4351_CLK = 0;}*(buf+i-1) = RotateData;}delay_us(1);ADF4351_LE = 1;delay_us(1);ADF4351_LE = 0;
}void ADF4351Init(void)
{u8 buf[4] = {0,0,0,0};ADF_Output_GPIOInit();buf[3] = 0x00;buf[2] = 0x58;buf[1] = 0x00;             //write communication register 0x00580005 to control the progress buf[0] = 0x05;               //to write Register 5 to set digital lock detectorWriteToADF4351(4,buf);        //每次写入8位数据,共32位数据写入,因为每个寄存器有32位,每次控制一个寄存器buf[3] = 0x00;buf[2] = 0xec;                //(DB23=1)The signal is taken from the VCO directly;(DB22-20:4H)the RF divider is 16;(DB19-12:50H)R is 80buf[1] = 0x80;               //(DB11=0)VCO powerd up;buf[0] = 0x3C;                //(DB5=1)RF output is enabled;(DB4-3=3H)Output power level is 5WriteToADF4351(4,buf);     buf[3] = 0x00;buf[2] = 0x00;buf[1] = 0x04;               //(DB14-3:96H)clock divider value is 150.buf[0] = 0xB3;WriteToADF4351(4,buf);  buf[3] = 0x00;buf[2] = 0x01;              //(DB6=1)set PD polarity is positive;(DB7=1)LDP is 6nS;buf[1] = 0x0E;                //(DB8=0)enable fractional-N digital lock detect;buf[0] = 0x42;               //(DB12-9:7H)set Icp 2.50 mA;WriteToADF4351(4,buf);     //(DB23-14:1H)R counter is 1buf[3] = 0x00;buf[2] = 0x00;buf[1] = 0x80;              //(DB14-3:6H)MOD counter is 6;buf[0] = 0x29;               //(DB26-15:6H)PHASE word is 1,neither the phase resync WriteToADF4351(4,buf); //nor the spurious optimization functions are being used//(DB27=1)prescaler value is 8/9buf[3] = 0x00;buf[2] = 0x2c;buf[1] = 0x80;buf[0] = 0x18;                      //(DB14-3:0H)FRAC value is 0;WriteToADF4351(4,buf);     //(DB30-15:140H)INT value is 320;
}void WriteOneRegToADF4351(u32 Regster)
{u8 buf[4] = {0,0,0,0};buf[3] = (u8)((Regster>>24)&(0X000000FF));buf[2] = (u8)((Regster>>16)&(0X000000FF));buf[1] = (u8)((Regster>>8) &(0X000000FF));buf[0] = (u8)((Regster)&(0X000000FF));WriteToADF4351(4, buf);
}void ADF4351_Init_some(void)
{WriteOneRegToADF4351(ADF4351_R2);WriteOneRegToADF4351(ADF4351_R3);WriteOneRegToADF4351(ADF4351_R5);
}void ADF4351WriteFreq(float Fre) //写入频率
{u16 Fre_temp, N_Mul = 1, Mul_Core = 0;u16 INT_Fre, Frac_temp, Mod_temp, i;u32 W_ADF4351_R0 = 0, W_ADF4351_R1 = 0, W_ADF4351_R4 = 0;float multiple;if(Fre < 35.0) //频率限幅{Fre = 35.0;}if(Fre > 4400.0){Fre = 4400.0;}Mod_temp = 1000;Fre = ((float)((u32)(Fre * 10))) / 10;Fre_temp = Fre;for(i = 0; i < 10; i++){if(((Fre_temp * N_Mul) >= 2199.9) && ((Fre_temp * N_Mul) <= 4400.1)){break;}Mul_Core++;N_Mul = N_Mul * 2;}multiple = (Fre * N_Mul) / 25;     //带宽出已固定为参考25M,若改参考频率,则应修改R4低字节  原本25 修改频率INT_Fre = (u16)multiple;Frac_temp = ((u32)(multiple * 1000)) % 1000;while(((Frac_temp % 5) == 0) && ((Mod_temp % 5) == 0)){Frac_temp = Frac_temp / 5;Mod_temp = Mod_temp / 5;}while(((Frac_temp % 2) == 0) && ((Mod_temp % 2) == 0)){Frac_temp = Frac_temp / 2;Mod_temp = Mod_temp / 2;}Mul_Core %= 7;W_ADF4351_R0 = (INT_Fre << 15) + (Frac_temp << 3);W_ADF4351_R1 = ADF4351_R1_Base + (Mod_temp << 3);W_ADF4351_R4 = ADF4351_R4_ON + (Mul_Core << 20);WriteOneRegToADF4351(ADF4351_RF_OFF);WriteOneRegToADF4351(W_ADF4351_R1);WriteOneRegToADF4351(W_ADF4351_R0);WriteOneRegToADF4351(W_ADF4351_R4);
}

ADF4351.H

#ifndef _ADF4351_H_
#define _ADF4351_H_#include "sys.h"#define ADF4351_CLK PBout(8)
#define ADF4351_OUTPUT_DATA PBout(9)
#define ADF4351_LE PBout(10)
#define ADF4351_CE PBout(11)#define ADF4351_INPUT_DATA PBin(9)void ADF4351Init(void);
void ReadToADF4351(u8 count, u8 *buf);
void WriteToADF4351(u8 count, u8 *buf);
void WriteOneRegToADF4351(u32 Regster);
void ADF4351_Init_some(void);
void ADF4351WriteFreq(float Fre);       //  (xxx.x) M Hz#endif

HMI.C

#include "HMI.h"uint16_t  trans = 0;
float fre_mhz = 300;   //adf4351输出300MHz
char buf[64];/*****串口屏通信函数*****/void HMI_choose(unsigned char ch)
{char  temp[4];int i = 0;switch (ch){case 0x01:LED0 = 0;fre_mhz += 0.1; ADF4351WriteFreq(fre_mhz);sprintf(buf,"x0.val=%.0f",fre_mhz*10);HMISends(buf);HMISendb(0xff);break;case 0x02:LED1 = 0;fre_mhz -= 0.1;ADF4351WriteFreq(fre_mhz);sprintf(buf,"x0.val=%.0f",fre_mhz*10);HMISends(buf);HMISendb(0xff);          break;case 0x03:LED0 = 1;fre_mhz += 1;ADF4351WriteFreq(fre_mhz);sprintf(buf,"x0.val=%.0f",fre_mhz*10);HMISends(buf);HMISendb(0xff);break;case 0x04:LED1 = 1;fre_mhz -= 1;ADF4351WriteFreq(fre_mhz);sprintf(buf,"x0.val=%.0f",fre_mhz*10);HMISends(buf);HMISendb(0xff);break;case 0x05:temp[0] = USART_RX_BUF[1];temp[1] = USART_RX_BUF[2];temp[2] = USART_RX_BUF[3];temp[3] = USART_RX_BUF[5]; //USART_RX_BUF[4]是小数点0x2e,我们跳过fre_mhz = 0;            //清零之前设定的频率,防止数据叠加for ( i = 0; i < 4; i++){fre_mhz = fre_mhz *10 + temp[i] - '0';  // 通过减去'0'可以将字符转换为int类型的数值}                   fre_mhz = fre_mhz * 0.1;ADF4351WriteFreq(fre_mhz);sprintf(buf,"x0.val=%.0f",fre_mhz*10);HMISends(buf);HMISendb(0xff);break;default :break;}
}void HMIReceive(void)
{if(USART_RX_STA & 0x8000){trans = USART_RX_BUF[0];HMI_choose(trans);USART_RX_STA = 0;}
}void HMISends(char *buf1)        //字符串发送函数
{u8 i = 0;while(1){        if(buf1[i] != 0){USART_SendData(USART1, buf1[i]); //发送一个字节while(USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET) {}; //等待发送结束i++;}elsereturn ;}
}void HMISendb(u8 k)                 //字节发送函数
{u8 i;for(i = 0; i < 3; i++){if(k != 0){USART_SendData(USART1, k); //发送一个字节while(USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET) {}; //等待发送结束}elsereturn ;}
}

HMI.H

#ifndef __HMI_H
#define __HMI_H
#include "stm32f10x.h"
#include "usart.h"
#include "LED.h"
#include "adf4351.h"extern uint16_t  trans;
extern char buf[64];;
extern float fre_mhz;
void HMISends(char *buf1);
void HMISendb(u8 k);
void HMI_choose(unsigned char ch);
void HMIReceive(void);#endif

MAIN.C

#include "delay.h"
#include "sys.h"
#include "string.h"
#include "usart.h"
#include "ADF4351.h"
#include "HMI.h"
#include "LED.h"
#include "stm32f10x.h"void ADF4351Init(void);
void ReadToADF4351(u8 count, u8 *buf);
void WriteToADF4351(u8 count, u8 *buf);
void WriteOneRegToADF4351(u32 Regster);
void ADF4351WriteFreq(float Fre);           int main(void)
{SystemInit();        //初始化RCC 设置系统主频为72MHZdelay_init(72);       //延时初始化uart_init(115200);ADF4351Init();                //ADF4351初始化函数ADF4351WriteFreq(fre_mhz);//ADF4351芯片写入频率LED_Init();while(1){HMIReceive();}
}

硬件:

原理图

概述:

  • ADF4351结合外部环路滤波器和外部参考频率使用时,可实现小数N分频或整数N分频锁相环(PLL)频率合成器。

  • ADF4351具有一个集成电压控制振荡器(VCO), 其基波输 出频率范围为2200MHz至4400 MHz。

  • 此外,利用1/2/4/8/ 16/32/64分频电路,用户可以产生低至35 MHz的RF输出频 率。

  • 对于要求隔离的应用,RF输出级可以实现静音。静音 功能既可以通过引脚控制,也可以通过软件控制。

  • 同时提供辅助RF输出,且不用时可以关断。 所有片内寄存器均通过简单的三线式接口进行控制。

  • 该器件采用3.0 V至3.6 V电源供电,不用时可以关断。

连线

ADF4351 STM32F103ZET6
CLK PB8
DATA PB9
LE PB10
CE PB11

实物图:

[外链图片转存中…(img-6PzCE3yv-1628251825760)]

工程源码已经上传,点击我下载工程源码

STM32F103ZET6+ADF4351+HMI串口屏相关推荐

  1. 连接串口_气压计PTB330连接HMI串口屏

    本篇约1700字10图 分享人:张彦飞 (菏泽) ---全文概述 这是一篇"小创造"的开发经验分享. 在用振筒气压仪故障,购买新气压显示仪器的申请迟迟未通过,聪明的机务员巧用备件, ...

  2. STM32物联网项目-HMI串口屏

    HMI串口屏实验 串口屏 屏幕使用的是淘晶池的串口屏,显示内容可以通过官方上位机来编辑,屏幕学习平台:http://wiki.tjc1688.com/doku.php?id=start 通信原理:屏幕 ...

  3. STM32驱动串口屏,STM32F103C8T6串口发送指令控制HMI串口屏

    STM32驱动串口屏,STM32F103C8T6串口发送指令控制HMI串口屏 串口屏 基础指令集 硬件和接线 接线 实验前准备 STM32程序 串口程序 主函数 实验现象 总结 串口屏 串口屏是一个集 ...

  4. 51单片机驱动HMI串口屏,串口屏的下载方式

    51单片机驱动HMI串口屏,串口屏的下载方式 串口屏 串口屏的程序下载 51程序 总结 串口屏 串口屏是一个集成了单片机的屏幕模块,采用的是TTL串口协议,可以直接通过对应指令控制屏幕, 本文采用的串 ...

  5. 基于HMI串口屏的协议(STM32)

    基于HMI串口屏的协议(STM32) 提示: 硬件:STM32H750VBT6.USART_HMI(3.5寸基本型)(TJC4832T035_011X) 官方资料网站:HMI 文章目录 基于HMI串口 ...

  6. 淘晶驰 usart hmi( 串口屏)介绍

    usart hmi(串口屏)介绍 https://blog.csdn.net/IRQHandler/article/details/84570463 什么是 HMI  HMI是Human Machin ...

  7. (跨平台UI)单片机用MTF HMI串口屏 UART通信易用兼容

    MTF Sagittarius 跨平台串口显示软件 MVVM 组态 MTF Sagittarius Serial Display v1.0 可直接用于产品, 或单片机版的串口屏调试 windows, ...

  8. usart hmi(串口屏)介绍

    什么是 HMI  HMI是Human Machine  Interface 的缩写, "人机接口" ,也叫人机界面. 什么是usart hmi usart hmi 就是设备封装好 ...

  9. USART HMI智能串口屏与单片机双向通讯

    目录 ·HMI串口屏介绍 ·HMI串口屏开发实操 ·准备 ·界面认识 ·写命令 ·下载 ·HMI串口屏与单片机(stm32)双向通信 [ 功能实现: STM32控制串口屏对应的数值.文本完成相应变化 ...

  10. 基于STC15W4K48S4芯片的温度检测控制系统(支持手机蓝牙和串口屏的异步串口通信)

    目标功能 实现温度的实时检测,并通过两个异步串口将数据发送至串口屏HMI和与蓝牙模块相连接的手机上.支持手机APP和串口屏进行实时的相关数据更改.单片机根据数据要求,当实时温度不在合理范围时,做出应激 ...

最新文章

  1. Tomcat 爆出高危漏洞!
  2. linux磁盘分配方案,张明贵-Linux磁盘分区方案
  3. android碎片按钮,Android 碎片(Fragment)
  4. STM32 基础系列教程 14 - IIC
  5. 经典MySQL语句大全和常用SQL语句命令的作用。
  6. 408最后计算机网络题库,2021考研计算机统考408专业基础综合题库
  7. discuz程序的阅读(1)
  8. 云图说|DRS数据对比——带您随时观测数据一致性
  9. spring 全局变量_Spring 十个错误的使用姿势!
  10. 在windows server 2003服务器上提供NTP时间同步服务
  11. EXCEL图表技巧:选择合适图表最全指南,建议收藏
  12. c盘清理代码_WIN10 C盘空间不够怎么办?几个小方法助你清理硬盘空间
  13. 编译原理(第3版) 清华大学出版社 黄贤英等人著作 部分课后习题答案
  14. JavaWeb教程———Ajax
  15. 阿里与百度的网盘中场大战
  16. 域无法在加入计算机,计算机无法加入域的终级解决方法
  17. Python等待所有线程任务完成
  18. 1. 代码效率优化方法论
  19. Java攻略之API
  20. 计算机桌面颜色异常怎样修复,电脑显示器变色怎么办?显示器颜色异常的原因及解决方法...

热门文章

  1. 宝塔Inode信息使用率100%满了怎么清理?
  2. VB.NET数据库编程基础教程
  3. IBM X System ServerGuide 8.41 服务器 系统安装 引导盘图文教程
  4. 发家致富:爬取双色球信息并统计
  5. Matlab快速傅里叶变换
  6. HCIA物联网初级考试-第二章物联网常用的通信技术
  7. Flash Builder 的概要分析
  8. Hive教程-详细全部
  9. 用mysql做宠物商店项目_使用Java实现数据库编程 项目(宠物商店)
  10. 通达信自编的选股公式如何使用?