基于CH554单片机的USB键盘蓝牙改造方案与实现
2026/7/28 8:35:06 网站建设 项目流程

1. 项目概述:当USB键盘遇上蓝牙,一次硬核的“无线化”改造

手头有一把闲置的Cherry轴机械键盘,手感扎实,但拖着一条长长的USB线缆,在如今无线桌面大行其道的时代,总觉得有些碍事。直接换蓝牙键盘?成本不低,而且老键盘的“灵魂”就没了。于是,一个硬核的想法诞生了:能不能给这把有线USB键盘,装上一个“蓝牙心脏”,让它原地变身无线键盘?这就是本次项目的核心——利用一颗国产的8位单片机CH554,制作一个USB Host(主机)设备,读取USB键盘的键值数据,再通过蓝牙模块发送出去,最终实现USB有线键盘到蓝牙键盘的无缝转换。

这个项目听起来有点极客,但实际拆解开来,你会发现它融合了嵌入式开发、USB协议、HID(人机接口设备)解析和蓝牙通信等多个有趣的技术点。它不仅仅是一个简单的转接器,更是一个深入了解现代计算机外设如何与主机通信的绝佳实践。无论你是嵌入式爱好者、硬件DIY玩家,还是单纯想拯救一把老键盘,这个项目都能让你在动手过程中获得满满的成就感。接下来,我将带你从原理到焊接,从代码到调试,完整复现这个“键盘无线化”改造的全过程。

2. 核心方案设计与芯片选型解析

2.1 为什么是CH554?低成本USB主从双角色芯片的优势

要实现USB键盘转蓝牙,核心控制器需要具备一个关键能力:作为USB Host(主机)去识别和读取USB键盘的数据。市面上常见的单片机(如STM32、ESP32)很多都只支持USB Device(设备)模式,即只能被电脑识别为一个设备,而不能主动去读取其他USB设备。专门支持USB Host功能的芯片往往价格较高或外围电路复杂。

这时,沁恒微电子的CH554系列芯片进入了视野。这是一颗基于增强型E8051内核的8位单片机,其最大的亮点就是内置了USB主机和设备控制器,支持全速USB 2.0。这意味着,用这一颗芯片,我们就能搭建一个简易的USB主机系统,去枚举和通信连接上的USB键盘。同时,它价格低廉(零售价仅几元人民币),开发资料相对齐全,对于DIY项目来说成本和技术门槛都非常友好。

除了USB Host,我们还需要蓝牙功能。CH554本身不带蓝牙,因此方案是“CH554 + 蓝牙模块”。蓝牙模块选择常见的HC-05或JDY-31等串口透传模块即可,CH554通过UART串口与蓝牙模块通信,将解析出的键盘键值数据发送给模块,再由模块以蓝牙HID(键盘)的身份广播出去,被电脑、手机等设备连接。

方案框图如下:

USB键盘 --> CH554 (作为USB Host,解析键值) --> UART串口 --> 蓝牙透传模块 --> 蓝牙无线信号 --> 电脑/平板/手机

整个系统的供电可以由一个微型锂电池配合充电管理电路解决,实现完全无线化。

2.2 系统工作流程与关键挑战预判

在动手之前,理清整个系统的工作流和可能遇到的坑至关重要:

  1. 上电与初始化:系统上电,CH554初始化自身的USB主机控制器、UART串口以及GPIO等外设。
  2. USB键盘枚举:当USB键盘插入后,CH554作为主机会发起枚举过程。这是第一个难点:CH554需要正确实现USB主机协议栈,发送标准请求(如获取设备描述符、设置地址、获取配置描述符等),最终识别出这是一个HID类设备,并为其配置正确的端点(Endpoint)。
  3. HID报告描述符解析与键值读取:枚举成功后,键盘会定期向主机发送报告(Report)。CH554需要从指定的中断输入端点(通常是IN端点)读取报告数据。报告的数据格式由键盘的HID报告描述符定义,我们需要编写代码来解析这个格式,提取出按键状态(哪个键被按下或释放)。
  4. 键值映射与协议转换:解析出的原始键值通常是USB HID Usage ID。我们需要将其映射为标准的键盘扫描码或直接转换为蓝牙HID协议中定义的Usage Page和Usage ID。
  5. 蓝牙数据传输:将转换后的键值数据,按照与蓝牙模块约定好的串口数据格式(例如,自定义一个简单的帧头+键值数据+帧尾的格式),通过UART发送给蓝牙模块。
  6. 蓝牙模块角色配置:蓝牙模块需要预先配置为“从设备(Slave)”和“HID设备(键盘)”模式。这样,它才能被终端设备发现并识别为一个蓝牙键盘。

关键挑战预判:

  • USB主机协议栈实现:这是最大的技术难点。虽然CH554提供了底层USB控制器驱动,但完整的主机枚举和HID设备通信逻辑需要自行实现或借鉴有限的开源代码。
  • HID报告解析:不同键盘的报告描述符可能略有差异,需要通用的解析方法或针对特定键盘进行适配。
  • 实时性:USB键盘的按键报告速度很快,系统需要有足够快的响应速度来处理数据并转发,避免按键延迟或丢失。
  • 低功耗设计:如果追求便携,需要考虑CH554和蓝牙模块在空闲时的休眠与唤醒机制。

3. 硬件电路设计与搭建要点

3.1 核心电路原理图详解

硬件部分是项目的基础。我们需要围绕CH554设计一个最小系统,并连接USB Host接口、蓝牙模块和电源。

1. CH554最小系统:

  • 电源:CH554工作电压为5V或3.3V。为了与蓝牙模块(通常3.3V)兼容,整个系统采用3.3V供电。可以使用AMS1117-3.3等LDO从锂电池(3.7V)降压得到。
  • 时钟:CH554内置了24MHz时钟源,对于全速USB(12Mbps)来说足够稳定,因此可以省去外部晶振,简化电路。
  • 复位:需要一个简单的RC复位电路(如10k电阻上拉,104电容到地)。
  • 调试/下载接口:CH554支持通过串口(UART0)进行ISP(在系统编程)。需要引出TXD0RXD0D+引脚(用于进入下载模式)。通常用一个4Pin的排针(VCC, TXD, RXD, GND)即可。

2. USB Host接口设计:这是区别于普通USB设备的关键。USB Host需要提供5V电源(VBUS)给下游设备(键盘)。因此,我们需要一个5V的升压电路(例如MT3608),将3.3V升压至5V,并通过一个MOS管(如SI2301)控制其通断。CH554的一个GPIO引脚控制这个MOS管,实现USB电源的管理(插入检测后上电)。 USB数据线D+D-需要串联22欧姆的匹配电阻,并连接至CH554的UD+UD-引脚。务必注意:CH554的USB引脚是3.3V电平,而标准USB信号是5V电平。虽然全速USB在3.3V下也能工作,但为了更好的兼容性,建议在D+D-线上添加电平转换芯片(如SN74LVC1T45)或使用分压电阻网络进行电平适配,这是一个容易忽略但影响稳定性的细节。

3. 蓝牙模块接口:选择一款3.3V供电的串口蓝牙模块,如JDY-31。连接非常简单:

  • VCC-> 系统3.3V
  • GND-> 系统GND
  • TXD-> CH554的RXD1(UART1接收)
  • RXD-> CH554的TXD1(UART1发送)
  • STATELED引脚可接一个LED,用于指示蓝牙连接状态。

4. 电源管理:使用一块500mAh左右的锂电池,搭配TP4056充电管理芯片。系统总功耗主要来自CH554、蓝牙模块和给USB键盘供电的5V升压电路。在键盘无操作时,可以通过软件让CH554和蓝牙模块进入休眠模式以省电。

3.2 PCB设计与焊接注意事项

对于DIY项目,可以使用洞洞板或绘制简单的双面PCB。

注意:USB数据线(D+/D-)属于高速信号线,在PCB布线时应尽量短且等长,并远离时钟和其他高频信号线,以减少干扰。如果使用洞洞板,连接线请使用屏蔽线或双绞线。

焊接与调试顺序建议:

  1. 先焊接电源部分(LDO、充电芯片),确保3.3V和5V电压输出正常、稳定。
  2. 焊接CH554最小系统及其外围的电阻电容。此时先不插芯片,用万用表测量各引脚对地电阻,避免短路。
  3. 插入CH554,通过串口尝试连接,测试能否进入ISP模式。可以先用一个简单的LED闪烁程序测试芯片是否工作正常。
  4. 焊接蓝牙模块接口和电平转换电路(如果有)。
  5. 最后焊接USB Host接口的电源控制MOS管和升压电路。

一个关键的测试点:在焊接完USB Host的5V升压电路后,先不要接键盘。测量USB-A母座的VBUS引脚,在CH554程序控制下,是否能正确输出5V并关断。

4. 核心软件实现:从USB枚举到蓝牙发送

4.1 CH554 USB主机协议栈的实现要点

CH554的官方SDK中提供了USB Host功能的库文件(CH554UFI.LIB)和示例代码,这是我们开发的基础。但示例通常只针对U盘(Mass Storage),我们需要在此基础上修改为支持HID设备。

核心任务集中在USB_Host.cUSB_Host.h中。你需要重点关注以下几个函数和流程:

  1. 主机初始化USB_Host_Init(),配置USB主机控制器的工作模式。
  2. 设备连接检测:CH554的USB主机控制器支持连接检测。你需要轮询或使用中断检测UH_INSERT事件。
  3. 端口使能与复位:检测到设备插入后,调用Host_SetPortEnable()使能下游端口,并发送复位信号Host_SendReset()
  4. 标准枚举流程:这是最复杂的部分。你需要按照USB协议,依次发送以下标准请求:
    • GET_DESCRIPTOR(DEVICE):获取设备描述符,得知设备的VID(厂商ID)、PID(产品ID)和最大包大小。
    • SET_ADDRESS:为设备分配一个唯一的地址。
    • GET_DESCRIPTOR(CONFIGURATION):获取配置描述符集合。这里包含了接口描述符、端点描述符以及HID报告描述符
  5. HID设备识别与配置:从配置描述符中,找到bInterfaceClass0x03(HID类)的接口。记录该接口下中断输入端点(bEndpointAddress方向为IN,传输类型为Interrupt)的地址和最大包大小。
  6. 设置配置与空闲:发送SET_CONFIGURATIONSET_IDLE请求,让键盘进入工作状态。

实操心得:

  • 调试利器——串口打印:在整个枚举过程中,将每一步发送的请求、接收到的描述符数据通过串口打印到电脑,是排查问题的唯一有效方法。你可以对照USB协议文档,逐字节分析数据是否正确。
  • 描述符解析:HID报告描述符是一套复杂的、自描述的数据结构。对于键盘,我们其实可以“偷懒”:大部分标准USB键盘的报告格式是固定的(通常是一个8字节的数组,第一个字节是Modifier键,第二个字节保留,后面6个字节是普通按键的Usage ID)。我们可以先硬编码解析这种常见格式,如果遇到不兼容的键盘,再考虑实现完整的报告描述符解析器。
  • 超时与错误处理:每个USB事务都必须设置合理的超时时间。枚举过程中任何一步失败,都应重置USB端口,重新开始枚举流程。

4.2 HID报告解析与键值映射逻辑

假设我们读取到的键盘报告是8字节数组Report[8]

  • Report[0]:修饰键(Modifier)。每一位对应一个键:左Ctrl、左Shift、左Alt、左GUI(Win键)、右Ctrl、右Shift、右Alt、右GUI。
  • Report[2]~Report[7]:普通按键的Usage ID。最多同时报告6个按键。例如,0x04代表a/A键,0x05代表b/B键。

我们的任务是将这个USB HID报告,转换为要发送给蓝牙模块的数据。蓝牙HID协议(在HOGP,HID Over GATT Profile中)使用的也是类似的Usage ID系统,绝大部分基础键值是相同的。因此,转换工作相对简单,主要是重新打包数据格式。

我们可以定义一个简单的串口通信协议帧:

[帧头 0xAA] [按键数量 N] [修饰键字节] [按键1] [按键2] ... [按键N] [帧尾 0x55]

例如,按下A键(左Shift +a键):USB报告可能是Report[0]=0x02(左Shift),Report[2]=0x04。那么发送给蓝牙模块的数据就是:0xAA, 0x01, 0x02, 0x04, 0x55

在CH554程序中,需要开启定时器中断,定期(例如每1ms)查询USB主机控制器的中断输入端点是否有数据。如果有,则读取报告,解析,打包,通过UART1发送出去。

4.3 蓝牙模块的配置与通信

蓝牙模块(以JDY-31为例)需要预先用AT命令进行配置,使其符合我们的需求:

  1. 角色:设置为从设备(Slave)。
  2. 工作模式:设置为透传模式。
  3. 设备类型:尽可能设置为HID键盘(有些模块支持AT+TYPEHID命令)。如果模块不支持直接设置HID,那么它就是一个串口透传通道,最终在接收端(如电脑)需要有一个配套的程序将串口数据再虚拟成HID设备,这样复杂度就转移了。因此,优先选择支持HID模式的蓝牙模块至关重要。
  4. 名称:设置为易于识别的名字,如USB2BT-Keyboard
  5. 配对码:设置一个简单的配对码,如1234

配置完成后,模块上电就会自动进入广播状态。当手机或电脑搜索并配对连接后,模块的状态引脚会变高。CH554可以检测这个引脚,从而知道蓝牙是否已连接,并可以据此控制LED指示灯。

在通信中,要处理好串口发送的流量控制。避免CH554发送速度过快,导致蓝牙模块或接收端缓冲区溢出。可以在发送每个数据帧后加入短暂延时。

5. 系统调试与问题排查实录

5.1 USB枚举失败:从电气到协议的逐层排查

这是最可能出问题的环节。如果键盘插入后没有任何反应,或者枚举过程卡住,请按以下顺序排查:

  1. 电气连接检查

    • 测量USB口的VBUS是否有5V输出?控制MOS管的GPIO电平是否正确?
    • 用示波器或逻辑分析仪查看D+/D-线上是否有数据波形?插入键盘的瞬间,应该能看到D+D-被上拉(USB全速设备上拉D+)导致的电平变化。
    • 检查D+/D-的串联电阻和电平转换电路是否正常。
  2. 软件流程排查

    • 确保打印了调试信息:这是最重要的。查看枚举流程在哪一步打印停止。
    • 获取设备描述符失败:可能是USB数据传输的PID(Packet ID)错误、CRC校验错误,或者设备没有响应。检查CH554的USB主机驱动配置,特别是速度(全速)和超时时间设置。
    • 获取配置描述符失败:可能是上一步分配的地址不对,或者设备请求的包长度超过了CH554设置的缓冲区大小。确保GET_DESCRIPTOR请求的wLength字段足够大(比如256字节)。
    • 找不到HID接口:打印出完整的配置描述符,仔细查看每个接口描述符的bInterfaceClass字段。有些复合设备(如带USB Hub的键盘)可能有多个接口。
  3. 工具辅助

    • 如果条件允许,使用USB协议分析仪(如Beagle USB)是终极解决方案,可以捕获总线上的所有原始数据包,与你的代码逻辑进行比对。

5.2 按键无响应或连击:数据解析与传输的优化

如果键盘能被识别,但按键没反应,或者按一次出现多个字符:

  1. 报告解析错误:确认你解析的字节索引是正确的。打印出每次收到的原始8字节报告数据,对照你按下的键,检查数据是否对应。特别注意,按键释放时,报告中的所有按键字节应该被清零。
  2. 键值映射错误:确认USB HID Usage ID到蓝牙HID Usage ID的映射关系。大部分基础键值一致,但一些特殊功能键(如多媒体键)可能需要单独映射。
  3. 数据传输延迟或丢失
    • 检查UART波特率是否匹配(CH554和蓝牙模块通常为9600或115200)。
    • 在UART发送函数前后加上时间戳打印,计算一下从收到USB报告到发送完串口数据的时间。如果超过10ms,可能会感觉到延迟。优化代码结构,将耗时的操作(如复杂的字符串处理)移出中断服务函数。
    • 检查蓝牙模块的连接质量。距离过远或有遮挡会导致数据包丢失,表现为偶尔按键失灵。

5.3 功耗过高与稳定性提升

项目完成后,如果希望做成一个便携设备,功耗就是下一个需要攻克的问题。

  1. 测量功耗基线:使用万用表电流档,串联在电池供电回路中,分别测量以下状态电流:

    • 待机状态(蓝牙已连接,无按键)。
    • 广播状态(蓝牙未连接)。
    • 按键频繁操作状态。
  2. 实施节能措施

    • CH554休眠:在蓝牙已连接且长时间无按键时,让CH554进入空闲(Idle)或掉电(Power Down)模式。可以通过定时器中断或外部中断(例如,将USB总线状态变化或某个GPIO连接到键盘的电路上,产生唤醒信号)来唤醒。CH554的USB主机控制器在休眠时无法工作,所以需要权衡。
    • 蓝牙模块功耗:选择支持低功耗(BLE)的模块,如基于TI CC254x或Nordic nRF51822的模块。并配置其连接间隔(Connection Interval)到一个合理的值(如50ms),间隔越长越省电。
    • 电源电路优化:5V升压电路在键盘拔出后应立即关闭。给CH554和蓝牙模块供电的LDO,应选择静态电流(Quiescent Current)小的型号。
  3. 稳定性强化

    • 增加看门狗:启用CH554的内部看门狗,防止程序跑飞。
    • 异常恢复机制:在代码中,如果检测到USB通信异常(如连续多次枚举失败),或蓝牙连接断开,应执行软复位或重新初始化的流程。
    • 电源滤波:在电池输入端、各芯片的电源引脚附近,增加足够容量的钽电容和瓷片电容(如10uF + 0.1uF),以滤除噪声,防止因电压波动导致复位或工作异常。

经过以上步骤,一个功能完整、性能稳定的USB键盘转蓝牙适配器就真正制作完成了。它不仅让老键盘重获新生,更是一个深入理解USB和蓝牙底层通信协议的绝佳学习案例。整个过程中,从硬件焊接、协议分析到代码调试,每一步的挑战与解决,都是对开发者综合能力的锻炼。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询