当前位置: 首页 > article >正文

APM32主控键盘全功能开发实战教程:软件部分

APM32主控键盘全功能开发实战教程:从零基础到RGB矩阵高级玩法

🔥 前言:随着机械键盘DIY风潮兴起,国产APM32芯片因其高性价比和与STM32的完美兼容性,正逐渐成为键盘开发主控的新宠。本文将手把手带你从最基础的环境搭建到高级RGB灯效开发,零基础也能轻松上手!

一、开发环境搭建与硬件准备

作为键盘开发的第一步,环境搭建至关重要。APM32是STM32F103系列的国产替代方案,完全兼容STM32的开发生态,我们只需按部就班准备好以下资源:

硬件准备清单:

  • APM32F103C8T6开发板(或带APM32主控的键盘PCB)
  • ST-Link V2烧录器(必备4根杜邦线:GND、SWCLK、SWDIO、3.3V)
  • 键盘PCB(已焊接完成,预留SWD接口和RGB灯位)
  • 旋钮编码器(可选,用于开发高级功能)

💡 小贴士:购买时可直接搜索"APM32F103C8T6开发板",价格通常在15-30元,比同规格STM32便宜30%左右。

软件工具包:

  • ST-Link驱动程序(ST官网直达链接)
  • QMK Firmware开发环境(GitHub仓库地址)
  • VIA配置工具(官网下载最新版)

硬件连接图解:

APM32的SWD接口是键盘固件烧录的关键,按照下表正确连接:

ST-Link引脚APM32 PCB引脚说明
GNDGND接地线,防止电平紊乱
SWCLKSWCLK串行时钟线,同步数据传输
SWDIOSWDIO串行数据线,传输固件数据
3.3V3.3V电源线,供电保障稳定通信

📝 注意事项:连接时务必确认引脚对应关系,错误连接可能导致芯片损坏!

二、Bootloader烧录全流程

Bootloader(引导加载程序)是实现后续固件更新的基础,出厂APM32未预装此程序,必须首先烧录。

详细烧录步骤:

1. 驱动安装与验证
# 步骤1:下载ST-Link驱动
# 官网搜索"STSW-LINK009"下载最新版本# 步骤2:安装驱动
# 双击下载的exe文件,按提示完成安装# 步骤3:验证安装
# 将ST-Link连接电脑,查看设备管理器是否识别

💡 疑难解答:若设备显示黄色感叹号,右键更新驱动并手动指定安装目录。

2. 硬件精准连接

按照前文连接图表,确保4根杜邦线连接正确。常见错误包括:

  • 针脚接触不良(建议轻轻晃动确认连接稳固)
  • GND与3.3V接反(会导致芯片无法识别)
3. Bootloader文件准备与烧录
# 步骤1:打开ST-Link Utility软件
# 可从ST官网下载"STSW-LINK004"工具包# 步骤2:连接目标设备
# 点击Target -> Connect,等待连接成功# 步骤3:加载Bootloader文件
# 点击File -> Open file,选择下载的bin文件# 步骤4:开始烧录
# 点击Target -> Program & Verify,等待完成

🔍 关键点:烧录成功后,设备管理器会显示新设备"MAPL033003"(APM32 Bootloader标识)

4. 烧录验证

断开并重新连接APM32开发板,检查设备管理器中是否出现"MAPL033003"设备。若未出现,可能原因:

  • Bootloader烧录失败(重复烧录步骤)
  • 连接不稳定(检查USB连接)
  • 驱动未正确安装(重新安装驱动)

三、VIA兼容固件开发实战

VIA是键盘DIY社区最受欢迎的配置工具,支持通过图形界面自定义键位,无需重新编译固件。下面介绍如何开发支持VIA的APM32固件。

1. 固件项目结构创建

首先,我们需要基于QMK框架创建适用于APM32的项目:

# 克隆QMK仓库(推荐使用Git for Windows)
git clone https://github.com/qmk/qmk_firmware.git
cd qmk_firmware# 创建APM32项目(基于planck键盘模板)
cp -r keyboards/planck keyboards/apm32_via
cd keyboards/apm32_via

🔧 开发提示:如果不熟悉Git,也可以直接从GitHub下载ZIP文件解压使用。

2. 关键配置文件修改

(1) 键位映射文件(keymap.c)
// keymap.c - 定义键盘按键映射和功能
// 这里我们定义一个5行4列的小键盘布局const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {[0] = LAYOUT_ortho_5x4(KC_ESC,  KC_1,    KC_2,    KC_3,    // 第一行:ESC, 1, 2, 3KC_TAB,  KC_Q,    KC_W,    KC_E,    // 第二行:TAB, Q, W, EKC_CAPS, KC_A,    KC_S,    KC_D,    // 第三行:CAPSLOCK, A, S, DKC_LSFT, KC_Z,    KC_X,    KC_C,    // 第四行:SHIFT, Z, X, CKC_LCTL, KC_LGUI, KC_LALT, KC_SPC   // 第五行:CTRL, WIN, ALT, SPACE)
};
(2) 配置文件(config.h)
// config.h - 定义键盘硬件配置和参数// 矩阵大小定义
#define MATRIX_ROWS 5          // 5行按键
#define MATRIX_COLS 4          // 4列按键// 引脚定义(注意核对PCB设计)
#define MATRIX_COL_PINS { PIN_A6, PIN_A7, PIN_B0, PIN_B1 }  // 列引脚
#define MATRIX_ROW_PINS { PIN_A1, PIN_A2, PIN_A3, PIN_A4, PIN_A5 }  // 行引脚// RGB灯带定义
#define RGB_PIN PIN_B10        // RGB数据引脚
#define RGB_NUM 17             // LED灯数量
(3) 键盘定义文件(keyboard.h)
// keyboard.h - 定义键盘布局和结构
#ifndef KB_H
#define KB_H// 包含必要的头文件
#include "quantum.h"  // QMK核心库
#include "keymap.h"   // 键位映射// 定义键盘布局(5x4矩阵)
#define LAYOUT_ortho_5x4( \k00, k01, k02, k03, \k10, k11, k12, k13, \k20, k21, k22, k23, \k30, k31, k32, k33, \k40, k41, k42, k43  \
) { \{ k00, k01, k02, k03 }, \{ k10, k11, k12, k13 }, \{ k20, k21, k22, k23 }, \{ k30, k31, k32, k33 }, \{ k40, k41, k42, k43 }  \
}#endif // KB_H

3. 编译与烧录技巧

在项目根目录执行编译命令:

# 编译VIA兼容固件
make apm32_via:default# 编译成功后,会在.build目录生成.bin文件
# 例如:qmk_firmware/.build/apm32_via_default.bin

🚀 加速技巧:首次编译较慢,可添加-j8参数利用多核加速,如make apm32_via:default -j8

固件烧录操作:
  1. 打开QMK Toolbox工具
  2. 加载编译好的bin文件
  3. 确保APM32处于Bootloader模式(重新上电或重置键盘)
  4. 点击"Flash"按钮开始烧录

4. VIA识别文件配置

为使VIA正确识别我们的键盘,需创建专用配置文件:

// apm32_via.json - VIA识别配置文件
{"name": "APM32 VIA键盘",           // 键盘名称"shortName": "APM32_VIA",          // 短名称"manufacturer": "DIY工坊",         // 制造商"bootloader": "caterina",         // 引导加载程序类型"matrix": {                       // 矩阵配置"rows": 5,"columns": 4,"rowsPins": ["A1", "A2", "A3", "A4", "A5"],"columnsPins": ["A6", "A7", "B0", "B1"],"diodeDirection": "COL2ROW"     // 二极管方向},"rgb": {                          // RGB配置"pin": "B10","leds": 17                      // LED数量},"keyCount": 20                    // 按键总数
}

📱 VIA使用提示:在VIA软件中,点击"设置">“设计”,然后导入该JSON文件,即可自定义键位。

四、旋钮功能开发与虚拟键高级应用

旋钮是高级键盘的标志性功能,下面详解如何实现旋钮控制和虚拟键映射。

1. 虚拟键原理详解

虚拟键是软件层面定义的按键,没有对应的物理按键。它们可用于:

  • 层切换(比如Fn功能)
  • 媒体控制(音量、播放)
  • 特殊功能触发(如宏命令)
// 虚拟键定义示例
#define KC_VK1 MO(1)              // 虚拟键1:按住时切换到第1层
#define KC_VK2 KC_MEDIA_VOL_UP    // 虚拟键2:音量增加
#define KC_VK3 KC_MEDIA_VOL_DOWN  // 虚拟键3:音量减小

2. 旋钮固件开发

(1) 启用旋钮功能

rules.mk文件中添加:

# 启用编码器(旋钮)功能
ENCODER_ENABLE = yes  # 开启旋钮支持
(2) 配置旋钮针脚

config.h中定义旋钮引脚:

// 旋钮配置
#define ENCODER_PINS B13, B12  // A相连接B13,B相连接B12
#define ENCODER_RESOLUTION 1   // 分辨率:转动一格触发一次

⚠️ 注意事项:旋钮引脚必须支持中断功能,一般选择B组或A组高位引脚。

(3) 旋钮功能映射

keymap.c中添加旋钮处理函数:

// 旋钮处理函数 - 定义旋钮转动时的行为
bool encoder_update_user(uint8_t index, bool clockwise) {if (index == 0) {  // 第一个旋钮if (clockwise) {tap_code(KC_VK2);  // 顺时针:音量增加} else {tap_code(KC_VK3);  // 逆时针:音量减小}}return true;  // 返回true表示已处理该事件
}

3. 旋钮按压功能实现

旋钮除了可以旋转,还可以按下。我们可以将旋钮按压映射为另一个功能:

// 在keymap.c的键位映射中添加旋钮按压键位
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {[0] = LAYOUT_ortho_5x4(KC_ESC,  KC_1,    KC_2,    KC_3,KC_TAB,  KC_Q,    KC_W,    KC_E,KC_CAPS, KC_A,    KC_S,    KC_D,KC_LSFT, KC_Z,    KC_X,    KC_C,KC_MUTE, KC_LGUI, KC_LALT, KC_SPC  // KC_MUTE为旋钮按压功能:静音)
};

🎯 应用场景:音量调节时按下旋钮静音,完美配合音频控制功能。

五、RGB矩阵灯效开发详解

APM32强大的性能支持丰富的RGB灯效,下面详细讲解WS2812B灯珠的矩阵控制实现。

1. RGB矩阵功能配置

(1) 修改rules.mk启用RGB
# RGB矩阵配置
RGBMATRIX_ENABLE = yes         # 启用RGB矩阵
RGBMATRIX_DRIVER = WS2812      # 使用WS2812B驱动
(2) 配置config.h参数
// RGB矩阵详细配置
#define DRIVER_LED_TOTAL 17      // 总LED数量
#define RGBMATRIX_PIN B10        // RGB数据引脚
#define RGBMATRIX_TIMEOUT 0      // 0表示不自动关闭
#define RGBMATRIX_HUE_STEP 8     // 色相调节步长
#define RGBMATRIX_SAT_STEP 8     // 饱和度调节步长
#define RGBMATRIX_VAL_STEP 8     // 亮度调节步长
#define RGBMATRIX_CENTER_X 112   // 动效中心X坐标
#define RGBMATRIX_CENTER_Y 33    // 动效中心Y坐标// 启用的灯效模式(根据需要开启)
#define ENABLE_RGB_MATRIX_SOLID_COLOR           // 纯色模式
#define ENABLE_RGB_MATRIX_BREATHING             // 呼吸灯效
#define ENABLE_RGB_MATRIX_CYCLE_ALL             // 彩虹循环
#define ENABLE_RGB_MATRIX_CYCLE_LEFT_RIGHT      // 左右循环
#define ENABLE_RGB_MATRIX_CYCLE_UP_DOWN         // 上下循环
#define ENABLE_RGB_MATRIX_RAINBOW_MOVING_CHEVRON // 彩虹箭头
#define ENABLE_RGB_MATRIX_CYCLE_PINWHEEL        // 旋转风车

2. RGB灯坐标定义

为使灯效正确显示,需精确定义每个LED的物理坐标:

// LED物理布局坐标定义
const rgb_led_t rgb_leds[DRIVER_LED_TOTAL] = {{.pos = {.x = 28, .y = 29}, .id = 0},    // ESC键下的LED{.pos = {.x = 84, .y = 29}, .id = 1},    // 1键下的LED{.pos = {.x = 140, .y = 29}, .id = 2},   // 2键下的LED{.pos = {.x = 196, .y = 29}, .id = 3},   // 3键下的LED{.pos = {.x = 28, .y = 47}, .id = 4},    // TAB键下的LED// ... 其他LED坐标省略 ...{.pos = {.x = 84, .y = 101}, .id = 16}   // 最后一个LED坐标
};

📏 坐标测量方法:以左上角为原点(0,0),向右为X轴正方向,向下为Y轴正方向,单位为像素。

3. 自定义灯效开发

除了使用预设灯效,还可以开发自定义灯效:

// 自定义呼吸灯效(在keymap.c中添加)
bool rgb_matrix_indicators_user(void) {if (host_keyboard_led_state().caps_lock) {// CAPSLOCK开启时,所有键变红色for (uint8_t i = 0; i < DRIVER_LED_TOTAL; i++) {rgb_matrix_set_color(i, 255, 0, 0);  // RGB值:纯红色}return false;}return true;
}

🎨 灯效开发提示:可以根据键盘层、按键状态、时间等条件创建复杂的灯效逻辑。

六、疑难问题解决方案大全

在开发过程中,可能遇到各种问题,以下是最常见问题的解决方案:

1. 烧录问题排查

问题描述可能原因解决方案
ST-Link连接失败杜邦线连接错误仔细核对连接,确保4根线都正确连接
驱动未正确安装重新安装ST-Link驱动程序
接口通信速率过高在ST-Link Utility中降低通信频率设置
设备不识别Bootloader未烧录成功重新烧录Bootloader
USB线质量问题更换高质量USB数据线

🔍 故障排查顺序:先检查硬件连接 → 再检查驱动安装 → 最后检查软件配置

2. 功能调试技巧

按键不响应排查:
// 在keymap.c中添加调试代码
void keyboard_post_init_user(void) {// 开启调试模式debug_enable = true;// 开启键盘矩阵调试debug_matrix = true;
}

然后通过QMK Toolbox观察输出,确认矩阵是否正确检测到按键。

旋钮失灵解决:
  1. 检查旋钮引脚定义是否正确
  2. 调整分辨率参数:#define ENCODER_RESOLUTION 2
  3. 验证旋钮A/B相是否接反
RGB灯不亮排查:
  1. 检查WS2812B的连接方向(确保DIN→DOUT方向正确)
  2. 验证数据引脚定义(B10)是否与PCB一致
  3. 检查供电是否足够(WS2812B需要足够电流)

💡 RGB故障排查:单个灯珠不亮通常是虚焊问题,整排不亮则可能是数据线断路或方向错误。

七、进阶知识与功能拓展

1. 多层键位设计

键盘层(Layer)是实现多功能键盘的关键技术,通过切换不同的层可以大幅扩展键位:

// 定义两个层的键位映射
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {// 基础层 - 标准键位[0] = LAYOUT_ortho_5x4(KC_ESC,  KC_1,    KC_2,    KC_3,KC_TAB,  KC_Q,    KC_W,    KC_E,KC_CAPS, KC_A,    KC_S,    KC_D,KC_LSFT, KC_Z,    KC_X,    KC_C,MO(1),   KC_LGUI, KC_LALT, KC_SPC  // MO(1):按住切换到第1层),// 功能层 - 媒体控制和F键[1] = LAYOUT_ortho_5x4(KC_GRV,  KC_F1,   KC_F2,   KC_F3,KC_TRNS, KC_MPRV, KC_MPLY, KC_MNXT,KC_TRNS, KC_VOLD, KC_MUTE, KC_VOLU,KC_TRNS, RGB_TOG, RGB_MOD, RGB_VAI,KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS  // KC_TRNS表示透明键,继承上层键位)
};

🔄 层切换方式:除了MO(n)临时切换外,还有TO(n)永久切换、TG(n)切换开关等多种方式。

2. OLED屏幕集成

OLED屏幕可以显示键盘状态、层信息和自定义图标,增强使用体验:

// 在rules.mk中启用OLED
OLED_DRIVER_ENABLE = yes// 在keymap.c中添加OLED显示函数
bool oled_task_user(void) {// 显示键盘状态oled_write_P(PSTR("APM32键盘\n"), false);// 显示当前层oled_write_P(PSTR("层: "), false);oled_write_ln(get_u8_str(get_highest_layer(layer_state)), false);// 显示大写锁定状态led_t led_state = host_keyboard_led_state();oled_write_P(led_state.caps_lock ? PSTR("CAPS: ON\n") : PSTR("CAPS: OFF\n"), false);return false;
}

3. 电源管理与省电技巧

长时间使用键盘时,电源管理至关重要:

// 在config.h中添加电源管理配置
#define USB_POLLING_INTERVAL_MS 1  // USB轮询间隔(毫秒)
#define RGB_DISABLE_WHEN_USB_SUSPENDED true  // USB挂起时关闭RGB
#define RGB_MATRIX_TIMEOUT 60000  // 60秒无操作后关闭灯效

🔋 省电提示:在无需炫酷灯效时,可设置简单的单色灯效,能显著降低功耗。

八、完整项目案例解析

为帮助理解整个开发流程,下面提供一个完整的5×4小键盘项目示例:

项目目录结构:

keyboards/
└── apm32_mini/├── config.h         // 硬件配置├── keyboard.h       // 键盘定义├── rules.mk         // 编译规则├── info.json        // 键盘信息└── keymaps/└── default/     // 默认键位配置├── keymap.c     // 键位定义└── config.h     // 用户配置

完整功能列表:

  • 5×4矩阵键位布局
  • 1个编码器旋钮(音量控制+静音)
  • 17个RGB灯珠(全键灯+底部氛围灯)
  • 2层键位(基础层+功能层)
  • VIA动态键位配置支持

编译命令:

# 编译默认键位的固件
make apm32_mini:default# 编译支持VIA的固件
make apm32_mini:via

总结

通过本教程,我们完整讲解了APM32主控键盘的开发全流程,从Bootloader烧录到RGB灯效实现。与传统32U4方案相比,APM32以国产芯片为基础,提供了更强性能和更低成本的优质选择。

希望本文对键盘开发爱好者有所帮助!如有问题,欢迎在评论区留言交流。


参考资料

  1. QMK官方文档
  2. VIA配置工具指南
  3. APM32数据手册
  4. 键盘矩阵原理解析

附录:完整开发流程图

准备工作
硬件连接
环境搭建
烧录Bootloader
开发VIA固件
配置旋钮功能
开发RGB矩阵
编译固件
烧录验证
完成开发

相关文章:

APM32主控键盘全功能开发实战教程:软件部分

APM32主控键盘全功能开发实战教程&#xff1a;从零基础到RGB矩阵高级玩法 &#x1f525; 前言&#xff1a;随着机械键盘DIY风潮兴起&#xff0c;国产APM32芯片因其高性价比和与STM32的完美兼容性&#xff0c;正逐渐成为键盘开发主控的新宠。本文将手把手带你从最基础的环境搭建…...

docker 部署 gin

编译与执行 ✅「静态编译语言 生成原生二进制文件 操作系统直接执行」 Go 语言之所以在工程部署场景中大受欢迎的核心优势&#xff1a;它直接编译成原生二进制可执行文件&#xff08;binary executable&#xff09;。 &#x1f527; Go 是“静态编译语言”&#xff08;编译型…...

十三: 神经网络的学习

这里所说的“学习”是指从训练数据中自动获取最优权重参数的过程。为了使神经网络能进行学习&#xff0c;将导入损失函数这一指标。而学习的目的就是以该损失函数为基准&#xff0c;找出能使它的值达到最小的权重参数。为了找出尽可能小的损失函数的值&#xff0c;我们将介绍利…...

Qt OpenGL编程常用类

Qt提供了丰富的类来支持OpenGL编程,以下是常用的Qt OpenGL相关类: 一、QOpenGLWidget 功能:用于在 Qt 应用程序中嵌入 OpenGL 渲染的窗口部件。替代了旧版的QGLWidget。提供了OpenGL上下文和渲染表面。 继承关系:QWidget → QOpenGLWidget 属性与方法: QOpenGLWidget 属…...

数据结构 --- 顺序表

顺序表是用一段物理地址连续的存储单元依次存储数据元素的线性结构&#xff0c;一般情况下采用数组存储&#xff0c;在数组上完成数据的增删查改 顺序表分为&#xff1a;静态顺序表、动态顺序表 一.静态顺序表 #define N 7 typedef int SLDataType;typedef struct Seqlist {…...

MySQL高级查询技巧:分组、聚合、子查询与分页【MySQL系列】

本文将深入探讨 MySQL 高级查询技巧&#xff0c;重点讲解 GROUP BY、HAVING、各种聚合函数、子查询以及分页查询&#xff08;LIMIT 语法&#xff09;的使用。文章内容涵盖实际应用中最常见的报表需求和分页实现技巧&#xff0c;适合有一定 SQL 基础的开发者进一步提升技能。 一…...

无人机多旋翼倾转动力测试系统-适用于(eVTOL开发、缩比模型测试、科研教育)

在倾转旋翼无人机、垂直起降&#xff08;VTOL&#xff09;及混合动力飞行器的研发中&#xff0c;动力系统在垂直-水平模式切换时的动态性能至关重要。LY-QZ-F4多旋翼倾转动力测试系统是全球首款专为倾转四旋翼设计的多自由度动力测试平台&#xff0c;融合高精度传感、动态倾转模…...

.NET8入门:14.ASP.NET Core MVC进阶——Model

上一篇文章我们了解了一下MVC在ASP.NET8中的一些基础概念&#xff0c;接下来深入了解一下ASP.NET Core MVC中Model的一些特性和用法。 Model 职责 Model 代表应用程序的核心数据和业务逻辑部分。它负责&#xff1a; 封装业务数据&#xff1a;表示应用程序中的实体&#xff0c;…...

latex figure Missing number, treated as zero. <to be read again>

\begin{figure}[h] \centering \includegraphics[width\linewidth]{pictures/architecture.pdf} \caption{Typical architecture.} \label{fig:architecture} \end{figure}&#xff0c; 我在编译latex&#xff0c;这段代码报错&#xff0c; Missing number, treated …...

java CompletableFuture创建异步任务(Completable异步+ExecutorService线程池)

文章目录 前置自定义线程池使用 CompletableFuture 创建异步任务 前置 来自 import java.util.concurrent.CompletableFuture; 自定义线程池 推荐根据业务需求配置 ExecutorService pool new ThreadPoolExecutor(10, // 核心线程数20, // 最大线程数60L, TimeUnit.SECONDS…...

LeetCode 高频 SQL 50 题(基础版)之 【聚合函数】部分

题目&#xff1a;620. 有趣的电影 题解&#xff1a; select * from cinema where description !boring and id%21 order by rating desc题目&#xff1a;1251. 平均售价 题解&#xff1a; select p.product_id product_id,round(ifnull(sum(p.price*u.units)/sum(u.units),0)…...

【AI学习】检索增强生成(Retrieval Augmented Generation,RAG)

1&#xff0c;介绍 出自论文《Retrieval-Augmented Generation for Knowledge-Intensive NLP Tasks》&#xff0c;RAG是权宜之计&#xff0c;通过RAG将问题简单化、精简化、剔除噪声&#xff0c;让LLM更容易理解、生成内容。RAG&#xff1a;检索增强技术检索生成&#xff08;重…...

低成本高效图像生成:GPUGeek和ComfyUI的强强联合

一、时代背景 在如今的数字化时代&#xff0c;图像生成技术正不断发展和演变&#xff0c;尤其是在人工智能领域。无论是游戏开发、虚拟现实&#xff0c;还是设计创意&#xff0c;图像生成已成为许多应用的核心技术之一。然而&#xff0c;随着图像质量需求的提升&#xff0c;生成…...

基于Matlab实现卫星轨道模拟仿真

在IT行业中&#xff0c;卫星轨道模拟和仿真程序是航空航天领域的重要工具&#xff0c;用于预测和分析人造卫星的运动轨迹。 我们需要理解卫星轨道的基本原理。地球引力使得卫星围绕地球运动&#xff0c;形成特定的椭圆或圆形轨道。牛顿的万有引力定律和开普勒的行星运动定律为…...

前端使用 spark-md5 实现大文件切片上传

需要计算文件MD5和、分片MD5&#xff1a; 封装公共方法代码如下&#xff1a; import SparkMD5 from "spark-md5"/*** 计算文件MD5* param file* returns*/ export function calculateFileMD5(file) {return new Promise((resolve) > {const reader new FileRea…...

《操作系统真相还原》——进入内核

ELF 按书上的操作来&#xff0c;在现代操作平台编译链接默认生成elf64 格式的文件&#xff0c; 很显然程序头位置发生变化&#xff0c;因为定义elf 结构的类型中有64位&#xff0c;所以我们需要将编译链接出32位格式的 gcc -m32 -c -o main.o main.c ld -m elf_i386 main.o …...

【QQ音乐】sign签名| data参数 | AES-GCM加密 | webpack(上)

1.目标 网址&#xff1a;https://y.qq.com/n/ryqq/toplist/26 切换榜单出现请求&#xff0c;可以看到sign和data是加密的 2.逆向分析 搜索sign: 可以看到sign P(n.data)&#xff0c;而n.data就是请求的加密data参数 data {"comm":{"cv":4747474,&qu…...

【STM32】按键控制LED 光敏传感器控制蜂鸣器

&#x1f50e;【博主简介】&#x1f50e; &#x1f3c5;CSDN博客专家 &#x1f3c5;2021年博客之星物联网与嵌入式开发TOP5 &#x1f3c5;2022年博客之星物联网与嵌入式开发TOP4 &#x1f3c5;2021年2022年C站百大博主 &#x1f3c5;华为云开发…...

M-OFDM模糊函数原理及仿真

文章目录 前言一、M序列二、M-OFDM 信号1、OFDM 信号表达式2、模糊函数表达式 三、MATLAB 仿真1、MATLAB 核心源码2、仿真结果①、m-OFDM 模糊函数②、m-OFDM 距离分辨率③、m-OFDM 速度分辨率④、m-OFDM 等高线图 四、资源自取 前言 本文进行 M-OFDM 的原理讲解及仿真&#x…...

【MySQL】MVCC与Read View

目录 一、数据库并发的三种场景 二、读写场景的MVCC &#xff08;一&#xff09;表中的三个隐藏字段 &#xff08;二&#xff09;undo 日志 &#xff08;三&#xff09;模拟MVCC &#xff08;四&#xff09;Read View &#xff08;五&#xff09;当前读和快照读 三、RC和…...

相机--双目立体相机

教程 链接1 教程汇总 立体匹配算法基础概念 视频讲解摄像机标定和双目立体原理 两个镜头。 双目相机也叫立体相机--Stereo Camera&#xff0c;属于深度相机。 作用 1&#xff0c;获取图像特征&#xff1b; 2&#xff0c;获取图像深度信息&#xff1b; 原理 原理和标定 …...

多目标粒子群优化算法(MOPSO),用于解决无人机三维路径规划问题,Matlab代码实现

多目标粒子群优化算法&#xff08;MOPSO&#xff09;&#xff0c;用于解决无人机三维路径规划问题&#xff0c;Matlab代码实现 目录 多目标粒子群优化算法&#xff08;MOPSO&#xff09;&#xff0c;用于解决无人机三维路径规划问题&#xff0c;Matlab代码实现效果一览基本介绍…...

工厂模式 vs 策略模式:设计模式中的 “创建者” 与 “决策者”

在日常工作里&#xff0c;需求变动或者新增功能是再常见不过的事情了。而面对这种情况时&#xff0c;那些耦合度较高的代码就会给我们带来不少麻烦&#xff0c;因为在这样的代码基础上添加新需求往往困难重重。为了保证系统的稳定性&#xff0c;我们在添加新需求时&#xff0c;…...

23、Swift框架微调实战(3)-Qwen2.5-VL-7B LORA微调OCR数据集

一、模型介绍 Qwen2.5-VL 是阿里通义千问团队开源的视觉语言模型,具有3B、7B和72B三种不同规模,能够识别常见物体、分析图像中的文本、图表等元素,并具备作为视觉Agent的能力。 Qwen2.5-VL 具备作为视觉Agent的能力,可以推理并动态使用工具,初步操作电脑和手机。在视频处…...

37. Sudoku Solver

题目描述 37. Sudoku Solver 回溯 class Solution {vector<vector<bool>> row_used;vector<vector<bool>> col_used;vector<vector<bool>> box_used;public:void solveSudoku(vector<vector<char>>& board) {row_used.r…...

C# Renci.SshNet 登陆 suse配置一粒

C# 调用Renci.SshNet 的SSH类库&#xff0c;登陆 suse linux系统&#xff0c;如果没有配置&#xff0c;会报错&#xff1a; Renci.SshNet.Common.SshAuthenticationException: No suitable authentication method found to complete 1、需要root登陆os,配置 /etc/ssh/sshd_con…...

RV1126-OPENCV 图像叠加

一.功能介绍 图像叠加&#xff1a;就是在一张图片上放上自己想要的图片&#xff0c;如LOGO&#xff0c;时间等。有点像之前提到的OSD原理一样。例如&#xff1a;下图一张图片&#xff0c;在左上角增加其他图片。 二.OPENCV中图像叠加常用的API 1. copyTo方法进行图像叠加 原理…...

修改 vscode 左侧导航栏的文字大小 (更新版)

1. 起因&#xff0c; 目的: 问题&#xff1a; vscode 左侧的文字太小了&#xff01;&#xff01;&#xff01;我最火的一篇文章&#xff0c;写的就是这个问题。 看来这个问题&#xff0c;是很广泛的一个痛点。我最近更新了 vscode&#xff0c; 这个问题又出现了。再来搞一下。…...

从C++编程入手设计模式2——工厂模式

从C编程入手设计模式 工厂模式 ​ 我们马上就要迎来我们的第二个创建型设计模式&#xff1a;工厂方法模式&#xff08;Factory Method Pattern&#xff09;。换而言之&#xff0c;我们希望使用一个这样的接口&#xff0c;使用其他手段而不是直接创建的方式&#xff08;说的有…...

云原生 Cloud Native Build (CNB)使用初体验

云原生 Cloud Native Build&#xff08;CNB&#xff09;使用初体验 引言 当“一切皆可云”成为趋势&#xff0c;传统开发环境正被云原生工具重塑。腾讯云CNB&#xff08;Cloud Native Build&#xff09;作为一站式开发平台&#xff0c;试图解决多环境协作难题。 本文将分享c…...