diff --git a/app/code_generate_interface.py b/app/code_generate_interface.py index 3bbd50d..089bcb6 100644 --- a/app/code_generate_interface.py +++ b/app/code_generate_interface.py @@ -154,27 +154,42 @@ class CodeGenerateInterface(QWidget): ) + + def generate_code(self): - """生成代码逻辑 - 修复导入问题""" + """生成代码逻辑 - 修复导入问题并添加配置重载""" try: - # 收集所有已加载的页面对象 - pages = [] + # 收集所有已加载的页面对象,并按类型分类 + bsp_pages = [] + component_pages = [] + device_pages = [] + for i in range(self.stack.count()): widget = self.stack.widget(i) - pages.append(widget) + # 根据页面类型分类 + if hasattr(widget, '_generate_bsp_code_internal'): + bsp_pages.append(widget) + elif hasattr(widget, '_generate_component_code_internal'): + component_pages.append(widget) + elif hasattr(widget, '_generate_device_code_internal'): + device_pages.append(widget) # 确保导入成功 from app.code_page.bsp_interface import bsp from app.code_page.component_interface import component + from app.code_page.device_interface import device # 生成 BSP 代码 - bsp_result = bsp.generate_bsp(self.project_path, pages) + bsp_result = bsp.generate_bsp(self.project_path, bsp_pages) # 生成 Component 代码 - component_result = component.generate_component(self.project_path, pages) + component_result = component.generate_component(self.project_path, component_pages) + + # 生成 Device 代码 + device_result = device.generate_device(self.project_path, device_pages) # 合并结果信息 - combined_result = f"BSP代码生成:\n{bsp_result}\n\nComponent代码生成:\n{component_result}" + combined_result = f"BSP代码生成:\n{bsp_result}\n\nComponent代码生成:\n{component_result}\n\nDevice代码生成:\n{device_result}" # 用 InfoBar 在主界面弹出 InfoBar.success( @@ -199,6 +214,9 @@ class CodeGenerateInterface(QWidget): duration=3000 ) + + + def _get_freertos_status(self): """获取FreeRTOS状态""" ioc_files = [f for f in os.listdir(self.project_path) if f.endswith('.ioc')] @@ -261,6 +279,11 @@ class CodeGenerateInterface(QWidget): comp_name = class_name[len('component_'):] # 移除 .replace("_", " ") page = get_component_page(comp_name, self.project_path, self.component_manager) self.component_manager.register_component(page.component_name, page) + elif class_name.startswith('device_'): + # Device页面 + from app.code_page.device_interface import get_device_page + device_name = class_name[len('device_'):] # 移除 device_ 前缀 + page = get_device_page(device_name, self.project_path) else: print(f"未知的页面类型: {class_name}") return None @@ -270,5 +293,4 @@ class CodeGenerateInterface(QWidget): return page except Exception as e: print(f"创建页面 {class_name} 失败: {e}") - return None - + return None \ No newline at end of file diff --git a/app/code_page/device_interface.py b/app/code_page/device_interface.py index e69de29..759861f 100644 --- a/app/code_page/device_interface.py +++ b/app/code_page/device_interface.py @@ -0,0 +1,394 @@ +from PyQt5.QtWidgets import QWidget, QVBoxLayout, QHBoxLayout +from qfluentwidgets import BodyLabel, CheckBox, ComboBox, SubtitleLabel +from PyQt5.QtCore import Qt +from app.tools.code_generator import CodeGenerator +import os +import shutil +import yaml +import re + +def load_device_config(config_path): + """加载设备配置""" + if os.path.exists(config_path): + with open(config_path, 'r', encoding='utf-8') as f: + return yaml.safe_load(f) + return {} + +def get_available_bsp_devices(project_path, bsp_type): + """获取可用的BSP设备""" + bsp_config_path = os.path.join(project_path, "User/bsp/bsp_config.yaml") + if not os.path.exists(bsp_config_path): + return [] + + try: + with open(bsp_config_path, 'r', encoding='utf-8') as f: + bsp_config = yaml.safe_load(f) + + if bsp_type in bsp_config and bsp_config[bsp_type].get('enabled', False): + devices = bsp_config[bsp_type].get('devices', []) + return [f"BSP_{bsp_type.upper()}_{device['name']}" for device in devices] + except Exception as e: + print(f"读取BSP配置失败: {e}") + + return [] + +def generate_device_header(project_path, enabled_devices): + """生成device.h文件""" + device_dir = os.path.join(os.path.dirname(__file__), "../../assets/User_code/device") + template_path = os.path.join(device_dir, "device.h") + + # 读取模板文件 + with open(template_path, 'r', encoding='utf-8') as f: + content = f.read() + + # 收集所有需要的信号定义 + signals = [] + current_bit = 0 + + # 加载设备配置来获取信号信息 + config_path = os.path.join(device_dir, "config.yaml") + device_configs = load_device_config(config_path) + + for device_name in enabled_devices: + device_key = device_name.lower() + if device_key in device_configs.get('devices', {}): + device_config = device_configs['devices'][device_key] + thread_signals = device_config.get('thread_signals', []) + + for signal in thread_signals: + signal_name = signal['name'] + signals.append(f"#define {signal_name} (1u << {current_bit})") + current_bit += 1 + + # 生成信号定义文本 + signals_text = '\n'.join(signals) if signals else '/* No signals defined */' + + # 替换AUTO GENERATED SIGNALS部分 + pattern = r'/\* AUTO GENERATED SIGNALS BEGIN \*/(.*?)/\* AUTO GENERATED SIGNALS END \*/' + replacement = f'/* AUTO GENERATED SIGNALS BEGIN */\n{signals_text}\n/* AUTO GENERATED SIGNALS END */' + content = re.sub(pattern, replacement, content, flags=re.DOTALL) + + # 保存文件 + dst_path = os.path.join(project_path, "User/device/device.h") + os.makedirs(os.path.dirname(dst_path), exist_ok=True) + with open(dst_path, 'w', encoding='utf-8') as f: + f.write(content) + + + + +class DeviceSimple(QWidget): + """简单设备界面""" + + def __init__(self, project_path, device_name, device_config): + super().__init__() + self.project_path = project_path + self.device_name = device_name + self.device_config = device_config + + # 添加必要的属性,确保兼容性 + self.component_name = device_name # 添加这个属性以兼容现有代码 + + self._init_ui() + self._load_config() + + def _init_ui(self): + layout = QVBoxLayout(self) + + # 顶部横向布局:左侧复选框,居中标题 + top_layout = QHBoxLayout() + top_layout.setAlignment(Qt.AlignVCenter) + + self.generate_checkbox = CheckBox(f"启用 {self.device_name}") + self.generate_checkbox.stateChanged.connect(self._on_checkbox_changed) + top_layout.addWidget(self.generate_checkbox, alignment=Qt.AlignLeft) + + # 弹性空间 + top_layout.addStretch() + + title = SubtitleLabel(f"{self.device_name} 配置 ") + title.setAlignment(Qt.AlignHCenter) + top_layout.addWidget(title, alignment=Qt.AlignHCenter) + + # 再加一个弹性空间,保证标题居中 + top_layout.addStretch() + + layout.addLayout(top_layout) + + # 功能说明 + desc = self.device_config.get('description', '') + if desc: + desc_label = BodyLabel(f"功能说明:{desc}") + desc_label.setWordWrap(True) + layout.addWidget(desc_label) + + # 依赖信息 + self._add_dependency_info(layout) + + # BSP配置区域 + self.content_widget = QWidget() + content_layout = QVBoxLayout(self.content_widget) + + self._add_bsp_config(content_layout) + + layout.addWidget(self.content_widget) + self.content_widget.setEnabled(False) + + layout.addStretch() + + def _add_dependency_info(self, layout): + """添加依赖信息显示""" + bsp_deps = self.device_config.get('dependencies', {}).get('bsp', []) + comp_deps = self.device_config.get('dependencies', {}).get('component', []) + + if bsp_deps or comp_deps: + deps_text = "依赖: " + if bsp_deps: + deps_text += f"BSP({', '.join(bsp_deps)})" + if comp_deps: + if bsp_deps: + deps_text += ", " + deps_text += f"Component({', '.join(comp_deps)})" + + deps_label = BodyLabel(deps_text) + deps_label.setWordWrap(True) + deps_label.setStyleSheet("color: #888888;") + layout.addWidget(deps_label) + + def _add_bsp_config(self, layout): + """添加BSP配置区域""" + bsp_requirements = self.device_config.get('bsp_requirements', []) + self.bsp_combos = {} + + if bsp_requirements: + layout.addWidget(BodyLabel("BSP设备配置:")) + + for req in bsp_requirements: + bsp_type = req['type'] + var_name = req['var_name'] + description = req.get('description', '') + + # 创建选择组合框 + req_layout = QHBoxLayout() + + label = BodyLabel(f"{bsp_type.upper()}:") + label.setMinimumWidth(80) + req_layout.addWidget(label) + + combo = ComboBox() + self._update_bsp_combo(combo, bsp_type) + + req_layout.addWidget(combo) + + if description: + desc_label = BodyLabel(f"({description})") + desc_label.setStyleSheet("color: #666666; font-size: 12px;") + req_layout.addWidget(desc_label) + + req_layout.addStretch() + layout.addLayout(req_layout) + + self.bsp_combos[var_name] = combo + + def _update_bsp_combo(self, combo, bsp_type): + """更新BSP组合框选项""" + combo.clear() + available_devices = get_available_bsp_devices(self.project_path, bsp_type) + if available_devices: + combo.addItems(available_devices) + else: + combo.addItem(f"未找到可用的{bsp_type.upper()}设备") + combo.setEnabled(False) + + def refresh_bsp_combos(self): + """刷新所有BSP组合框""" + bsp_requirements = self.device_config.get('bsp_requirements', []) + for req in bsp_requirements: + bsp_type = req['type'] + var_name = req['var_name'] + if var_name in self.bsp_combos: + current_text = self.bsp_combos[var_name].currentText() + self._update_bsp_combo(self.bsp_combos[var_name], bsp_type) + # 尝试恢复之前的选择 + index = self.bsp_combos[var_name].findText(current_text) + if index >= 0: + self.bsp_combos[var_name].setCurrentIndex(index) + + def _on_checkbox_changed(self, state): + """处理复选框状态变化""" + self.content_widget.setEnabled(state == 2) + + def is_need_generate(self): + """检查是否需要生成代码""" + return self.generate_checkbox.isChecked() + + def get_bsp_config(self): + """获取BSP配置""" + config = {} + for var_name, combo in self.bsp_combos.items(): + if combo.isEnabled(): + config[var_name] = combo.currentText() + return config + + def _generate_device_code_internal(self): + """生成设备代码""" + if not self.is_need_generate(): + return False + + # 获取BSP配置 + bsp_config = self.get_bsp_config() + + # 复制并修改文件 + template_dir = self._get_device_template_dir() + files = self.device_config.get('files', {}) + + for file_type, filename in files.items(): + src_path = os.path.join(template_dir, filename) + dst_path = os.path.join(self.project_path, f"User/device/{filename}") + + if os.path.exists(src_path): + if file_type == 'header': + # 头文件直接复制,不做修改 + os.makedirs(os.path.dirname(dst_path), exist_ok=True) + shutil.copy2(src_path, dst_path) + + elif file_type == 'source': + # 源文件需要替换BSP设备名称 + with open(src_path, 'r', encoding='utf-8') as f: + content = f.read() + + # 替换BSP设备名称 + for var_name, device_name in bsp_config.items(): + content = content.replace(var_name, device_name) + + # 保存文件 + os.makedirs(os.path.dirname(dst_path), exist_ok=True) + with open(dst_path, 'w', encoding='utf-8') as f: + f.write(content) + + self._save_config() + return True + + def _get_device_template_dir(self): + """获取设备模板目录""" + current_dir = os.path.dirname(os.path.abspath(__file__)) + # 向上找到 MRobot 根目录 + while os.path.basename(current_dir) != 'MRobot' and current_dir != '/': + current_dir = os.path.dirname(current_dir) + + if os.path.basename(current_dir) == 'MRobot': + return os.path.join(current_dir, "assets/User_code/device") + else: + # 如果找不到,使用相对路径作为备选 + return os.path.join(os.path.dirname(os.path.dirname(os.path.dirname(__file__))), "assets/User_code/device") + + def _save_config(self): + """保存配置""" + config_path = os.path.join(self.project_path, "User/device/device_config.yaml") + config_data = CodeGenerator.load_config(config_path) + config_data[self.device_name.lower()] = { + 'enabled': self.is_need_generate(), + 'bsp_config': self.get_bsp_config() + } + CodeGenerator.save_config(config_data, config_path) + + def _load_config(self): + """加载配置""" + config_path = os.path.join(self.project_path, "User/device/device_config.yaml") + config_data = CodeGenerator.load_config(config_path) + conf = config_data.get(self.device_name.lower(), {}) + + if conf.get('enabled', False): + self.generate_checkbox.setChecked(True) + + # 恢复BSP配置 + bsp_config = conf.get('bsp_config', {}) + for var_name, device_name in bsp_config.items(): + if var_name in self.bsp_combos: + combo = self.bsp_combos[var_name] + index = combo.findText(device_name) + if index >= 0: + combo.setCurrentIndex(index) + +def get_device_page(device_name, project_path): + """根据设备名返回对应的页面类""" + # 加载设备配置 + device_dir = os.path.join(os.path.dirname(__file__), "../../assets/User_code/device") + config_path = os.path.join(device_dir, "config.yaml") + device_configs = load_device_config(config_path) + + devices = device_configs.get('devices', {}) + device_key = device_name.lower() + + if device_key in devices: + device_config = devices[device_key] + page = DeviceSimple(project_path, device_name, device_config) + else: + # 如果配置中没有找到,返回一个基本的设备页面 + basic_config = { + 'name': device_name, + 'description': f'{device_name}设备', + 'files': {'header': f'{device_name.lower()}.h', 'source': f'{device_name.lower()}.c'}, + 'bsp_requirements': [], + 'dependencies': {'bsp': [], 'component': []} + } + page = DeviceSimple(project_path, device_name, basic_config) + + # 确保页面有必要的属性 + page.device_name = device_name + + return page + +class device(QWidget): + """设备管理器""" + + def __init__(self, project_path): + super().__init__() + self.project_path = project_path + + @staticmethod + def generate_device(project_path, pages): + """生成所有设备代码""" + success_count = 0 + fail_count = 0 + fail_list = [] + enabled_devices = [] + + # 生成设备代码 + for page in pages: + if hasattr(page, "device_name") and hasattr(page, "is_need_generate"): + if page.is_need_generate(): + enabled_devices.append(page.device_name) + try: + result = page._generate_device_code_internal() + if result: + success_count += 1 + else: + fail_count += 1 + fail_list.append(page.device_name) + except Exception as e: + fail_count += 1 + fail_list.append(f"{page.device_name} (异常: {e})") + + # 生成device.h文件 + try: + generate_device_header(project_path, enabled_devices) + success_count += 1 + except Exception as e: + fail_count += 1 + fail_list.append(f"device.h (异常: {e})") + + # 刷新所有页面的BSP组合框选项 + for page in pages: + if hasattr(page, 'refresh_bsp_combos'): + try: + page.refresh_bsp_combos() + except Exception as e: + print(f"刷新页面 {getattr(page, 'device_name', 'Unknown')} 的BSP选项失败: {e}") + + total_items = success_count + fail_count + msg = f"设备代码生成完成:总共尝试生成 {total_items} 项,成功 {success_count} 项,失败 {fail_count} 项。" + if fail_list: + msg += "\n失败项:\n" + "\n".join(fail_list) + + return msg \ No newline at end of file diff --git a/assets/User_code/component/ui.c b/assets/User_code/component/ui.c index 4544784..c3126bd 100644 --- a/assets/User_code/component/ui.c +++ b/assets/User_code/component/ui.c @@ -1,7 +1,7 @@ /* UI相关命令 */ -#include "component\ui.h" +#include "component/ui.h" #include diff --git a/assets/User_code/component/ui.h b/assets/User_code/component/ui.h index 3cfb3bb..e569985 100644 --- a/assets/User_code/component/ui.h +++ b/assets/User_code/component/ui.h @@ -11,7 +11,7 @@ extern "C" { #include #include -#include "component\user_math.h" +#include "component/user_math.h" #define UI_DEL_OPERATION_NOTHING (0) #define UI_DEL_OPERATION_DEL (1) @@ -45,12 +45,12 @@ typedef enum { WHITE } UI_Color_t; -typedef __Packed struct { +typedef struct __packed { uint8_t op; uint8_t num_layer; } UI_InterStudent_UIDel_t; -typedef __Packed struct { +typedef struct __packed { uint8_t name[3]; uint8_t type_op : 3; uint8_t type_ele : 3; @@ -66,28 +66,28 @@ typedef __Packed struct { uint16_t y_end : 11; } UI_Ele_t; -typedef __Packed struct { +typedef struct __packed { UI_Ele_t grapic; } UI_Drawgrapic_1_t; -typedef __Packed struct { +typedef struct __packed { UI_Ele_t grapic[2]; } UI_Drawgrapic_2_t; -typedef __Packed struct { +typedef struct __packed { UI_Ele_t grapic[5]; } UI_Drawgrapic_5_t; -typedef __Packed struct { +typedef struct __packed { UI_Ele_t grapic[7]; } UI_Drawgrapic_7_t; -typedef __Packed struct { +typedef struct __packed { UI_Ele_t grapic; uint8_t character[30]; } UI_Drawcharacter_t; -typedef __Packed struct { +typedef struct __packed { uint8_t del_operation; uint8_t layer; } UI_Del_t; diff --git a/assets/User_code/component/user_math.h b/assets/User_code/component/user_math.h index 13e1ae5..fea820f 100644 --- a/assets/User_code/component/user_math.h +++ b/assets/User_code/component/user_math.h @@ -25,6 +25,10 @@ extern "C" { #define M_2PI 6.28318530717958647692f #endif +#ifndef __packed + #define __packed __attribute__((__packed__)) +#endif /* __packed */ + #define max(a, b) \ ({ \ __typeof__(a) _a = (a); \ diff --git a/assets/User_code/device/.DS_Store b/assets/User_code/device/.DS_Store index 1fc8ef0..640682c 100644 Binary files a/assets/User_code/device/.DS_Store and b/assets/User_code/device/.DS_Store differ diff --git a/assets/User_code/device/config.yaml b/assets/User_code/device/config.yaml new file mode 100644 index 0000000..cf27c0e --- /dev/null +++ b/assets/User_code/device/config.yaml @@ -0,0 +1,16 @@ +devices: + dr16: + name: "DR16" + description: "大疆遥控器接收机" + dependencies: + bsp: ["uart"] + component: ["user_math"] + bsp_requirements: + - type: "uart" + var_name: "BSP_UART_DR16" # 需要替换的变量名 + description: "用于接收遥控器数据" + thread_signals: + - name: "SIGNAL_DR16_RAW_REDY" + files: + header: "dr16.h" + source: "dr16.c" \ No newline at end of file diff --git a/assets/User_code/device/dependencies.csv b/assets/User_code/device/dependencies.csv deleted file mode 100644 index 3f4d215..0000000 --- a/assets/User_code/device/dependencies.csv +++ /dev/null @@ -1,5 +0,0 @@ -oled_i2c,bsp/i2c -bmp280_i2c,bsp/i2c -pc_uart,bsp/uart -key_gpio,bsp/gpio_exti -servo,bsp/servo_pwm \ No newline at end of file diff --git a/assets/User_code/device/describe.csv b/assets/User_code/device/describe.csv deleted file mode 100644 index 68b476a..0000000 --- a/assets/User_code/device/describe.csv +++ /dev/null @@ -1 +0,0 @@ -servo,测试消息测试消息测试消息测试消息测试消息测试消息测试消息测试消息测试消息测试消息测试消息测试消息测试消息测试消息测试消息 \ No newline at end of file diff --git a/assets/User_code/device/device.h b/assets/User_code/device/device.h index 308aabc..9ac8953 100644 --- a/assets/User_code/device/device.h +++ b/assets/User_code/device/device.h @@ -10,6 +10,19 @@ extern "C" { #define DEVICE_ERR_INITED (-3) #define DEVICE_ERR_NO_DEV (-4) +/* AUTO GENERATED SIGNALS BEGIN */ + +/* AUTO GENERATED SIGNALS END */ + +/* USER SIGNALS BEGIN */ + +/* USER SIGNALS END */ +/*设备层通用Header*/ +typedef struct { + bool online; + uint64_t last_online_time; +} DEVICE_Header_t; + #ifdef __cplusplus } #endif diff --git a/assets/User_code/device/dr16.c b/assets/User_code/device/dr16.c new file mode 100644 index 0000000..d9c0590 --- /dev/null +++ b/assets/User_code/device/dr16.c @@ -0,0 +1,85 @@ +/* + DR16接收机 +*/ + +/* Includes ----------------------------------------------------------------- */ +#include "dr16.h" + +#include + +#include "bsp/uart.h" + +/* Private define ----------------------------------------------------------- */ +#define DR16_CH_VALUE_MIN (364u) +#define DR16_CH_VALUE_MID (1024u) +#define DR16_CH_VALUE_MAX (1684u) + +/* Private macro ------------------------------------------------------------ */ +/* Private typedef ---------------------------------------------------------- */ +/* Private variables -------------------------------------------------------- */ + +static osThreadId_t thread_alert; +static bool inited = false; + +/* Private function -------------------------------------------------------- */ +static void DR16_RxCpltCallback(void) { + osThreadFlagsSet(thread_alert, SIGNAL_DR16_RAW_REDY); +} + +static bool DR16_DataCorrupted(const DR16_t *dr16) { + if (dr16 == NULL) return DEVICE_ERR_NULL; + + if ((dr16->data.ch_r_x < DR16_CH_VALUE_MIN) || + (dr16->data.ch_r_x > DR16_CH_VALUE_MAX)) + return true; + + if ((dr16->data.ch_r_y < DR16_CH_VALUE_MIN) || + (dr16->data.ch_r_y > DR16_CH_VALUE_MAX)) + return true; + + if ((dr16->data.ch_l_x < DR16_CH_VALUE_MIN) || + (dr16->data.ch_l_x > DR16_CH_VALUE_MAX)) + return true; + + if ((dr16->data.ch_l_y < DR16_CH_VALUE_MIN) || + (dr16->data.ch_l_y > DR16_CH_VALUE_MAX)) + return true; + + if (dr16->data.sw_l == 0) return true; + + if (dr16->data.sw_r == 0) return true; + + return false; +} + +/* Exported functions ------------------------------------------------------- */ +int8_t DR16_Init(DR16_t *dr16) { + if (dr16 == NULL) return DEVICE_ERR_NULL; + if (inited) return DEVICE_ERR_INITED; + if ((thread_alert = osThreadGetId()) == NULL) return DEVICE_ERR_NULL; + + BSP_UART_RegisterCallback(BSP_UART_DR16, BSP_UART_RX_CPLT_CB, + DR16_RxCpltCallback); + + inited = true; + return DEVICE_OK; +} + +int8_t DR16_Restart(void) { + __HAL_UART_DISABLE(BSP_UART_GetHandle(BSP_UART_DR16)); + __HAL_UART_ENABLE(BSP_UART_GetHandle(BSP_UART_DR16)); + return DEVICE_OK; +} + +int8_t DR16_StartDmaRecv(DR16_t *dr16) { + if (HAL_UART_Receive_DMA(BSP_UART_GetHandle(BSP_UART_DR16), + (uint8_t *)&(dr16->data), + sizeof(dr16->data)) == HAL_OK) + return DEVICE_OK; + return DEVICE_ERR; +} + +bool DR16_WaitDmaCplt(uint32_t timeout) { + return (osThreadFlagsWait(SIGNAL_DR16_RAW_REDY, osFlagsWaitAll, timeout) == + SIGNAL_DR16_RAW_REDY); +} diff --git a/assets/User_code/device/dr16.h b/assets/User_code/device/dr16.h new file mode 100644 index 0000000..41a7a65 --- /dev/null +++ b/assets/User_code/device/dr16.h @@ -0,0 +1,45 @@ +#pragma once + +#ifdef __cplusplus +extern "C" { +#endif + +/* Includes ----------------------------------------------------------------- */ +#include + +#include "component/user_math.h" +#include "device/device.h" + +/* Exported constants ------------------------------------------------------- */ +/* Exported macro ----------------------------------------------------------- */ +/* Exported types ----------------------------------------------------------- */ +typedef struct __packed { + uint16_t ch_r_x : 11; + uint16_t ch_r_y : 11; + uint16_t ch_l_x : 11; + uint16_t ch_l_y : 11; + uint8_t sw_r : 2; + uint8_t sw_l : 2; + int16_t x; + int16_t y; + int16_t z; + uint8_t press_l; + uint8_t press_r; + uint16_t key; + uint16_t res; +} DR16_Data_t; + +typedef struct { + DR16_Data_t data; +} DR16_t; + +/* Exported functions prototypes -------------------------------------------- */ +int8_t DR16_Init(DR16_t *dr16); +int8_t DR16_Restart(void); + +int8_t DR16_StartDmaRecv(DR16_t *dr16); +bool DR16_WaitDmaCplt(uint32_t timeout); + +#ifdef __cplusplus +} +#endif diff --git a/assets/User_code/device/oled.c b/assets/User_code/device/oled.c deleted file mode 100644 index 3e9688f..0000000 --- a/assets/User_code/device/oled.c +++ /dev/null @@ -1,381 +0,0 @@ -/* - OLED显示模块。 - - 使用SPI通信时,需要#define OLED_USE_SPI - 使用I2C通信时,需要#define OLED_USE_I2C - -*/ - -/* Includes ----------------------------------------------------------------- */ -/* Include 自身的头文件。*/ -#include "oled.h" - -/* Include 标准库。*/ -#include -#include -#include - -/* Include HAL相关的头文件。*/ -#include "bsp_delay.h" -#include "bsp_spi.h" -#include - -#ifdef OLED_USE_SPI -#include "spi.h" -# - -#elif defined OLED_USE_I2C -#include "i2c.h" - -#endif - - -/* Include Component相关的头文件 */ -/* Private define ----------------------------------------------------------- */ -/* Private macro ------------------------------------------------------------ */ -#ifdef OLED_USE_SPI - -#define OLED_CMD_Set() HAL_GPIO_WritePin(OLED_DC_GPIO_Port, OLED_DC_Pin, GPIO_PIN_SET) -#define OLED_CMD_Clr() HAL_GPIO_WritePin(OLED_DC_GPIO_Port, OLED_DC_Pin, GPIO_PIN_RESET) - -#define OLED_RST_Set() HAL_GPIO_WritePin(OLED_RST_GPIO_Port, OLED_RST_Pin, GPIO_PIN_SET) -#define OLED_RST_Clr() HAL_GPIO_WritePin(OLED_RST_GPIO_Port, OLED_RST_Pin, GPIO_PIN_RESET) - -#elif defined OLED_USE_I2C -#define OLED_I2C_HANDLE hi2c1 - -#endif - -/* Private typedef ---------------------------------------------------------- */ -typedef enum { - OLED_WriteCMD = 0, - OLED_WriteData = 1, -}OLED_Write_t; - - -/* Private variables -------------------------------------------------------- */ -static const uint8_t oled_font[95][8] = { - {0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,}, /* " ", 0 */ - {0x00,0x00,0x00,0xcf,0xcf,0x00,0x00,0x00,}, /* "!", 1 */ - {0x00,0x0c,0x06,0x00,0x0c,0x06,0x00,0x00,}, /* """, 2 */ - {0x24,0xe4,0x3c,0x27,0xe4,0x3c,0x27,0x24,}, /* "#", 3 */ - {0x00,0x20,0x46,0xf9,0x9f,0x62,0x04,0x00,}, /* "$", 4 */ - {0x06,0x09,0xc6,0x30,0x0c,0x63,0x90,0x60,}, /* "%", 5 */ - {0x00,0x00,0x6e,0x91,0xa9,0x46,0xa0,0x00,}, /* "&", 6 */ - {0x00,0x00,0x00,0x1c,0x0e,0x00,0x00,0x00,}, /* "'", 7 */ - {0x00,0x00,0x3c,0x42,0x81,0x00,0x00,0x00,}, /* "(", 8 */ - {0x00,0x00,0x00,0x81,0x42,0x3c,0x00,0x00,}, /* ")", 9 */ - {0x00,0x10,0x54,0x38,0x38,0x54,0x10,0x00,}, /* "*", 10 */ - {0x00,0x10,0x10,0xfc,0x10,0x10,0x00,0x00,}, /* "+", 11 */ - {0x00,0x00,0x00,0xc0,0x60,0x00,0x00,0x00,}, /* ",", 12 */ - {0x00,0x00,0x10,0x10,0x10,0x10,0x00,0x00,}, /* "-", 13 */ - {0x00,0x00,0x00,0x00,0xc0,0xc0,0x00,0x00,}, /* ".", 14 */ - {0x00,0x00,0x00,0xc0,0x38,0x07,0x00,0x00,}, /* "/", 15 */ - {0x00,0x00,0x7c,0x92,0x8a,0x7c,0x00,0x00,}, /* "0", 16 */ - {0x00,0x00,0x00,0x84,0xfe,0x80,0x00,0x00,}, /* "1", 17 */ - {0x00,0x00,0x8c,0xc2,0xa2,0x9c,0x00,0x00,}, /* "2", 18 */ - {0x00,0x00,0x44,0x92,0x92,0x6c,0x00,0x00,}, /* "3", 19 */ - {0x00,0x20,0x38,0x24,0xfe,0x20,0x00,0x00,}, /* "4", 20 */ - {0x00,0x00,0x5e,0x92,0x92,0x62,0x00,0x00,}, /* "5", 21 */ - {0x00,0x00,0x78,0x94,0x92,0x62,0x00,0x00,}, /* "6", 22 */ - {0x00,0x00,0x82,0x62,0x1a,0x06,0x00,0x00,}, /* "7", 23 */ - {0x00,0x00,0x6c,0x92,0x92,0x6c,0x00,0x00,}, /* "8", 24 */ - {0x00,0x00,0x8c,0x52,0x32,0x1c,0x00,0x00,}, /* "9", 25 */ - {0x00,0x00,0x00,0x6c,0x6c,0x00,0x00,0x00,}, /* ":", 26 */ - {0x00,0x00,0x80,0xec,0x6c,0x00,0x00,0x00,}, /* ";", 27 */ - {0x00,0x00,0x10,0x28,0x44,0x00,0x00,0x00,}, /* "<", 28 */ - {0x00,0x00,0x24,0x24,0x24,0x24,0x00,0x00,}, /* "=", 29 */ - {0x00,0x00,0x00,0x44,0x28,0x10,0x00,0x00,}, /* ">", 30 */ - {0x00,0x00,0x0c,0xa2,0x92,0x1c,0x00,0x00,}, /* "?", 31 */ - {0x00,0x3c,0x42,0x99,0xa5,0xa2,0x3c,0x00,}, /* "@", 32 */ - {0x00,0xe0,0x1c,0x12,0x12,0x1c,0xe0,0x00,}, /* "A", 33 */ - {0x00,0xfe,0x92,0x92,0x9c,0x90,0x60,0x00,}, /* "B", 34 */ - {0x00,0x38,0x44,0x82,0x82,0x82,0x44,0x00,}, /* "C", 35 */ - {0x00,0xfe,0x82,0x82,0x82,0x82,0x7c,0x00,}, /* "D", 36 */ - {0x00,0xfe,0x92,0x92,0x92,0x92,0x92,0x00,}, /* "E", 37 */ - {0x00,0xfe,0x12,0x12,0x12,0x12,0x02,0x00,}, /* "F", 38 */ - {0x00,0x7c,0x82,0x92,0x92,0x72,0x00,0x00,}, /* "G", 39 */ - {0x00,0xfe,0x10,0x10,0x10,0x10,0xfe,0x00,}, /* "H", 40 */ - {0x00,0x82,0x82,0xfe,0x82,0x82,0x00,0x00,}, /* "I", 41 */ - {0x00,0x82,0x82,0x7e,0x02,0x02,0x00,0x00,}, /* "J", 42 */ - {0x00,0xfe,0x10,0x28,0x44,0x82,0x00,0x00,}, /* "K", 43 */ - {0x00,0xfe,0x80,0x80,0x80,0x80,0x00,0x00,}, /* "L", 44 */ - {0xfc,0x02,0x04,0xf8,0x04,0x02,0xfc,0x00,}, /* "M", 45 */ - {0x00,0xfe,0x04,0x18,0x30,0x40,0xfe,0x00,}, /* "N", 46 */ - {0x00,0x7c,0x82,0x82,0x82,0x82,0x7c,0x00,}, /* "O", 47 */ - {0x00,0x00,0xfe,0x12,0x12,0x0c,0x00,0x00,}, /* "P", 48 */ - {0x00,0x00,0x3c,0x42,0xc2,0xbc,0x00,0x00,}, /* "Q", 49 */ - {0x00,0x00,0xfe,0x32,0x52,0x8c,0x00,0x00,}, /* "R", 50 */ - {0x00,0x00,0x4c,0x92,0x92,0x64,0x00,0x00,}, /* "S", 51 */ - {0x00,0x02,0x02,0xfe,0x02,0x02,0x00,0x00,}, /* "T", 52 */ - {0x00,0x7e,0x80,0x80,0x80,0x80,0x7e,0x00,}, /* "U", 53 */ - {0x00,0x0c,0x30,0xc0,0x30,0x0c,0x00,0x00,}, /* "V", 54 */ - {0x7c,0x80,0x80,0x78,0x80,0x80,0x7c,0x00,}, /* "W", 55 */ - {0x00,0x84,0x48,0x30,0x30,0x48,0x84,0x00,}, /* "X", 56 */ - {0x00,0x06,0x08,0xf0,0x08,0x06,0x00,0x00,}, /* "Y", 57 */ - {0x00,0x00,0xc2,0xa2,0x92,0x8e,0x00,0x00,}, /* "Z", 58 */ - {0x00,0x00,0xfe,0x82,0x82,0x82,0x00,0x00,}, /* "[", 59 */ - {0x00,0x00,0x06,0x18,0x60,0x80,0x00,0x00,}, /* "\", 60 */ - {0x00,0x00,0x82,0x82,0x82,0xfe,0x00,0x00,}, /* "]", 61 */ - {0x00,0x30,0x0c,0x02,0x0c,0x30,0x00,0x00,}, /* "^", 62 */ - {0x00,0x80,0x80,0x80,0x80,0x80,0x80,0x00,}, /* "_", 63 */ - {0x00,0x00,0x04,0x0c,0x18,0x00,0x00,0x00,}, /* "`", 64 */ - {0x00,0x00,0x60,0x90,0x90,0xe0,0x00,0x00,}, /* "a", 65 */ - {0x00,0x00,0xf8,0xa0,0xe0,0x00,0x00,0x00,}, /* "b", 66 */ - {0x00,0x00,0x60,0x90,0x90,0x00,0x00,0x00,}, /* "c", 67 */ - {0x00,0x00,0xe0,0xa0,0xf8,0x00,0x00,0x00,}, /* "d", 68 */ - {0x00,0x00,0x70,0xa8,0xa8,0x90,0x00,0x00,}, /* "e", 69 */ - {0x00,0x00,0x10,0xf8,0x14,0x00,0x00,0x00,}, /* "f", 70 */ - {0x00,0x00,0xd8,0xa4,0x7c,0x00,0x00,0x00,}, /* "g", 71 */ - {0x00,0x00,0xf8,0x20,0xe0,0x00,0x00,0x00,}, /* "h", 72 */ - {0x00,0x00,0x00,0xe8,0x00,0x00,0x00,0x00,}, /* "i", 73 */ - {0x00,0x00,0x40,0x90,0x74,0x00,0x00,0x00,}, /* "j", 74 */ - {0x00,0x00,0xf8,0x60,0x90,0x00,0x00,0x00,}, /* "k", 75 */ - {0x00,0x00,0x78,0x80,0x80,0x00,0x00,0x00,}, /* "l", 76 */ - {0x00,0xe0,0x10,0xe0,0x10,0xe0,0x00,0x00,}, /* "m", 77 */ - {0x00,0x00,0xf0,0x10,0x10,0xe0,0x00,0x00,}, /* "n", 78 */ - {0x00,0x00,0x60,0x90,0x90,0x60,0x00,0x00,}, /* "o", 79 */ - {0x00,0x00,0xf0,0x48,0x48,0x30,0x00,0x00,}, /* "p", 80 */ - {0x00,0x00,0x30,0x48,0x48,0xf0,0x00,0x00,}, /* "q", 81 */ - {0x00,0x00,0x00,0xf0,0x20,0x10,0x00,0x00,}, /* "r", 82 */ - {0x00,0x00,0x90,0xa8,0xa8,0x48,0x00,0x00,}, /* "s", 83 */ - {0x00,0x10,0x10,0xf8,0x90,0x90,0x00,0x00,}, /* "t", 84 */ - {0x00,0x00,0x78,0x80,0x80,0xf8,0x00,0x00,}, /* "u", 85 */ - {0x00,0x18,0x60,0x80,0x60,0x18,0x00,0x00,}, /* "v", 86 */ - {0x00,0x38,0xc0,0x38,0xc0,0x38,0x00,0x00,}, /* "w", 87 */ - {0x00,0x88,0x50,0x20,0x50,0x88,0x00,0x00,}, /* "x", 88 */ - {0x00,0x8c,0x50,0x20,0x10,0x0c,0x00,0x00,}, /* "y", 89 */ - {0x00,0x88,0xc8,0xa8,0x98,0x88,0x00,0x00,}, /* "z", 90 */ - {0x00,0x00,0x10,0x7c,0x82,0x00,0x00,0x00,}, /* "{", 91 */ - {0x00,0x00,0x00,0xfe,0x00,0x00,0x00,0x00,}, /* "|", 92 */ - {0x00,0x00,0x00,0x82,0x7c,0x10,0x00,0x00,}, /* "}", 93 */ - {0x00,0x08,0x04,0x04,0x08,0x10,0x10,0x08,}, /* "~", 94 */ -}; - -static const uint8_t gram_logo[8][128] = { - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x02,0x06,0x0E,0X1E,0X3E,0X7E,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFE,0XFC,0XFC,0XF8,0XF8,0XF0,0XE0,0XC0,0X80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x03,0x07,0x0F,0X1F,0X3F,0X7F,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XF7,0XE7,0XC7,0X87,0x07,0x07,0x07,0x07,0x07,0x07,0x07,0x07,0x07,0x07,0x07,0x07,0x0F,0X1F,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFE,0XF0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0XC0,0XFC,0XFC,0XFC,0XFC,0XFC,0XFD,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFE,0XFC,0XFC,0XFC,0XFC,0XFC,0XFC,0XFC,0XFC,0XFC,0XFC,0XFE,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0X7F,0X3F,0x0F,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0X80,0XF0,0XFE,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0X1F,0x0F,0x0F,0x0F,0x0F,0x0F,0x0F,0x0F,0X1F,0X3F,0X7F,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XEF,0XCF,0X87,0x07,0x03,0x03,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0XE0,0XFC,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0X3F,0x07,0x00,0x00,0x00,0x00,0x00,0x00,0X40,0X40,0X40,0XC0,0XC0,0XC0,0XC0,0XC1,0XC3,0XC7,0XCF,0XDF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFF,0XFE,0XFC,0XF8,0XF0,0XE0,0XC0,0X80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x0C,0x0F,0x0F,0x0F,0x0F,0x0F,0x0F,0x0F,0x0F,0x0F,0x0F,0x0F,0x0F,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x01,0x03,0x03,0x07,0x07,0x0F,0x0F,0X1F,0X1F,0X3F,0X3F,0X7F,0X7F,0XFF,0XF3,0XE3,0XC3,0X83,0x03,0x03,0x03,0x03,0x03,0x02,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x01,0x03,0x03,0x06,0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x60,0x78,0x7B,0x1B,0x1B,0x1B,0x7B,0x7F,0x6F,0x4E,0x00,0x3E,0x7F,0x63,0x63,0x63,0x7F,0x3E,0x00,0x78,0x7B,0x6B,0x6B,0x6B,0x6B,0x7B,0x7F,0x36,0x00,0x3E,0x7F,0x63,0x63,0x63,0x7F,0x3E,0x40,0x60,0x78,0x3D,0x07,0x1F,0x7C,0x70,0x1D,0x07,0x7F,0x78,0x40,0x00,0x60,0x70,0x38,0x5D,0x6F,0x67,0x6F,0x7C,0x70,0x40,0x00,0x40,0x66,0x6F,0x6B,0x6B,0x6B,0x6B,0x7B,0x31,0x02,0x03,0x03,0x7F,0x7F,0x03,0x03,0x61,0x68,0x6B,0x6B,0x6B,0x6B,0x6B,0x0B,0x03,0x60,0x78,0x7B,0x1B,0x1B,0x1B,0x7B,0x7B,0x6F,0x4E,0x00,0x46,0x6F,0x6F,0x6B,0x6B,0x6B,0x7B,0x31,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, -}; - -static OLED_t *goled; -static bool inited = false; - -/* Private function ---------------------------------------------- */ -static void OLED_WriteByte(uint8_t data, OLED_Write_t type) { - -#ifdef OLED_USE_SPI - switch(type) { - case OLED_WriteCMD: - OLED_CMD_Clr(); - break; - - case OLED_WriteData: - OLED_CMD_Set(); - break; - } - BSP_SPI_Transmit(BSP_SPI_OLED, &data, 1); - -#elif defined OLED_USE_I2C - uint8_t cmd_data[2]; - - switch(type) { - case OLED_WriteCMD: - cmd_data[0] = 0x00; - break; - - case OLED_WriteData: - cmd_data[0] = 0x40; - break; - } - cmd_data[1] = data; - HAL_I2C_Master_Transmit_DMA(OLED_I2C, OLED_I2C_ADDRESS, cmd_data, 2); -#endif - - BSP_Delay(1); -} - -static void OLED_WriteSequenceData(uint8_t *data, uint16_t len) { -#ifdef OLED_USE_SPI - OLED_CMD_Set(); - HAL_SPI_Transmit_DMA(&hspi1, data, len); - -#elif defined OLED_USE_I2C - /* TODO */ - uint8_t cmd_data[2]; - cmd_data[0] = 0x40; - cmd_data[1] = data; - HAL_I2C_Master_Transmit_DMA(OLED_I2C, OLED_I2C_ADDRESS, cmd_data, 2); -#endif -} - -/* Exported functions ------------------------------------------------------- */ -int8_t OLED_Init(OLED_t *oled) { - if (oled == NULL) - return -1; - - if (inited) - return -1; - - oled->cursor.column = 0; - oled->cursor.page = 0; - oled->modified = true; - - goled = oled; - - OLED_RST_Clr(); - BSP_Delay(1); - OLED_RST_Set(); - BSP_Delay(5); - - OLED_WriteByte(0xae, OLED_WriteCMD); /* Dot martix display off. */ - OLED_WriteByte(0x00, OLED_WriteCMD); /* Set lower column address:(00H~0FH). */ - OLED_WriteByte(0x10, OLED_WriteCMD); /* Set higher column address:(10H~1FH). */ - OLED_WriteByte(0x20, OLED_WriteCMD); /* Set Memory Addressing Mode */ - OLED_WriteByte(0x10, OLED_WriteCMD); /* 00,Horizontal Addressing Mode;01,Vertical Addressing Mode;10,Page Addressing Mode (RESET);11,Invalid */ - OLED_WriteByte(0x32, OLED_WriteCMD); /* Set pump voltage 8v. */ - OLED_WriteByte(0x40, OLED_WriteCMD); /* Set display start line:(40H~7FH). */ - OLED_WriteByte(0x81, OLED_WriteCMD); /* Contarst control. */ - OLED_WriteByte(0x6f, OLED_WriteCMD); /* Contarst: 0x00~0xff. */ - OLED_WriteByte(0xa1, OLED_WriteCMD); /* Set segment re-map. 0xa0 or 0xa1. */ - OLED_WriteByte(0xa4, OLED_WriteCMD); /* Entire display off. */ - OLED_WriteByte(0xa6, OLED_WriteCMD); /* Set normal display. */ - OLED_WriteByte(0xa8, OLED_WriteCMD); /* Set multiplex ratio. */ - OLED_WriteByte(0x3f, OLED_WriteCMD); - OLED_WriteByte(0xad, OLED_WriteCMD); /* Set DC/DC booster. */ - OLED_WriteByte(0x8b, OLED_WriteCMD); - OLED_WriteByte(0xb0, OLED_WriteCMD); /* Set page address. */ - OLED_WriteByte(0xc8, OLED_WriteCMD); /* Com scan COM0->COM63. */ - OLED_WriteByte(0xd3, OLED_WriteCMD); /* Set display offset. */ - OLED_WriteByte(0x00, OLED_WriteCMD); - OLED_WriteByte(0xd5, OLED_WriteCMD); /* Set frame frequency. */ - OLED_WriteByte(0xf0, OLED_WriteCMD); - OLED_WriteByte(0xd9, OLED_WriteCMD); /* Set pre_charge period. */ - OLED_WriteByte(0x22, OLED_WriteCMD); - OLED_WriteByte(0xda, OLED_WriteCMD); /* Com pin configuration. */ - OLED_WriteByte(0x12, OLED_WriteCMD); - OLED_WriteByte(0xdb, OLED_WriteCMD); /* Set vcom deselect level. */ - OLED_WriteByte(0x20, OLED_WriteCMD); - OLED_WriteByte(0x8d, OLED_WriteCMD); /* Set DC-DC enable */ - OLED_WriteByte(0x14, OLED_WriteCMD); - OLED_WriteByte(0xaf, OLED_WriteCMD); /* Display on. */ - - memcmp(oled->gram, gram_logo, sizeof(oled->gram)); - - OLED_SetAllRam(oled, OLED_PEN_WRITE); /* Clear memory. */ - - OLED_Refresh(oled); /* Display initial picture. */ - return 0; -} - -OLED_t *OLED_GetDevice(void) { - if (inited) { - return goled; - } - return NULL; -} - -int8_t OLED_PrintRam(OLED_t *oled, const char* str) { - if (str == NULL) - return -1; - - oled->modified = true; - - for (uint16_t i = 0; str[i] != '\0'; i++) { - uint8_t c = str[i]; - if (c < 32) { - switch (c) { - case '\n': - oled->cursor.page ++; - oled->cursor.column = 0; - break; - - case '\t': - oled->cursor.column += 16; - break; - } - } else if (c < 126) { - if (oled->cursor.column == 128) { - oled->cursor.page ++; - oled->cursor.column = 0; - } - if (oled->cursor.page == 8) { - OLED_SetAllRam(oled, OLED_PEN_CLEAR); - oled->cursor.page = 0; - } - memcpy(&oled->gram[oled->cursor.page][oled->cursor.column], oled_font[c- 32], sizeof(oled_font[0])); - oled->cursor.column += 8; - } - } - return 0; -} - -uint8_t OLED_RewindRam(OLED_t *oled) { - oled->modified = true; - - OLED_SetAllRam(oled, OLED_PEN_CLEAR); - - oled->cursor.page = 0; - oled->cursor.column = 0; - return 0; -} - -uint8_t OLED_SetAllRam(OLED_t *oled, OLED_Pen_t pen) { - switch(pen) { - case OLED_PEN_WRITE: - memset(oled->gram, -1, sizeof(oled->gram)); - break; - - case OLED_PEN_CLEAR: - memset(oled->gram, 0, sizeof(oled->gram)); - break; - - case OLED_PEN_INVERSION: - for (uint8_t i = 0; i < 8; i++) { - for (uint8_t n = 0; n < 128; n++) { - oled->gram[i][n] = ~oled->gram[i][n]; - } - } - break; - } - return 0; -} - -uint8_t OLED_DisplayOn(OLED_t *oled) { - OLED_WriteByte(0x8d, OLED_WriteCMD); - OLED_WriteByte(0x14, OLED_WriteCMD); - OLED_WriteByte(0xaf, OLED_WriteCMD); - return 0; -} - -uint8_t OLED_DisplayOff(OLED_t *oled) { - OLED_WriteByte(0x8d, OLED_WriteCMD); - OLED_WriteByte(0x10, OLED_WriteCMD); - OLED_WriteByte(0xae, OLED_WriteCMD); - return 0; -} - - -void OLED_SetCursor(uint8_t x, uint8_t y) -{ - OLED_WriteByte((0xb0 + y), OLED_WriteCMD); /*set page address y */ - OLED_WriteByte(((x&0xf0)>>4)|0x10, OLED_WriteCMD); /*set column high address */ - OLED_WriteByte((x&0x0f), OLED_WriteCMD); /*set column low address */ -} - -uint8_t OLED_Refresh(OLED_t *oled) { - for (uint8_t i = 0; i < 8; i++) { - OLED_SetCursor(0, i); - for (uint8_t n = 0; n < 8; n++) { - OLED_WriteByte(oled->gram[i][n], OLED_WriteData); - } - } - oled->modified = false; - - return 0; -} diff --git a/assets/User_code/device/oled.h b/assets/User_code/device/oled.h deleted file mode 100644 index e296bc6..0000000 --- a/assets/User_code/device/oled.h +++ /dev/null @@ -1,45 +0,0 @@ -#pragma once - -#ifdef __cplusplus -extern "C" { -#endif - -/* Includes ----------------------------------------------------------------- */ -#include -#include - -/* Exported constants ------------------------------------------------------- */ -/* Exported macro ----------------------------------------------------------- */ -/* Exported types ----------------------------------------------------------- */ -typedef enum { - OLED_PEN_CLEAR = 0, - OLED_PEN_WRITE = 1, - OLED_PEN_INVERSION = 2, -} OLED_Pen_t; - -typedef struct { - uint8_t column; - s uint8_t page; -} OLED_Cursor_t; - -typedef struct { - OLED_Cursor_t cursor; - uint8_t gram[8][128]; - bool modified; -} OLED_t; - -/* Exported functions prototypes -------------------------------------------- */ -uint8_t OLED_Init(OLED_t *oled); -OLED_t *OLED_GetDevice(void); - -uint8_t OLED_PrintRam(OLED_t *oled, const char *str); -uint8_t OLED_RewindRam(OLED_t *oled); -uint8_t OLED_SetAllRam(OLED_t *oled, OLED_Pen_t pen); - -uint8_t OLED_DisplayOn(OLED_t *oled); -uint8_t OLED_DisplayOff(OLED_t *oled); -uint8_t OLED_Refresh(OLED_t *oled); - -#ifdef __cplusplus -} -#endif diff --git a/bsp_config.yaml b/bsp_config.yaml new file mode 100644 index 0000000..337fa09 --- /dev/null +++ b/bsp_config.yaml @@ -0,0 +1,126 @@ +can: + devices: + - instance: CAN1 + name: CAN1 + - instance: CAN2 + name: CAN2 + enabled: true +dwt: + enabled: true +gpio: + configs: + - custom_name: USER_KEY + has_exti: true + ioc_label: USER_KEY + pin: PA0-WKUP + - custom_name: ACCL_CS + has_exti: false + ioc_label: ACCL_CS + pin: PA4 + - custom_name: GYRO_CS + has_exti: false + ioc_label: GYRO_CS + pin: PB0 + - custom_name: SPI2_CS + has_exti: false + ioc_label: SPI2_CS + pin: PB12 + - custom_name: HW0 + has_exti: false + ioc_label: HW0 + pin: PC0 + - custom_name: HW1 + has_exti: false + ioc_label: HW1 + pin: PC1 + - custom_name: HH + has_exti: false + ioc_label: hh + pin: PC2 + - custom_name: ACCL_INT + has_exti: true + ioc_label: ACCL_INT + pin: PC4 + - custom_name: GYRO_INT + has_exti: true + ioc_label: GYRO_INT + pin: PC5 + - custom_name: CMPS_INT + has_exti: true + ioc_label: CMPS_INT + pin: PG3 + - custom_name: CMPS_RST + has_exti: false + ioc_label: CMPS_RST + pin: PG6 + enabled: true +i2c: + devices: + - instance: I2C1 + name: OLED + enabled: true +mm: + enabled: true +pwm: + configs: + - channel: TIM_CHANNEL_1 + custom_name: TIM8_CH1 + label: TIM8_CH1 + timer: TIM8 + - channel: TIM_CHANNEL_3 + custom_name: LASER + label: LASER + timer: TIM3 + - channel: TIM_CHANNEL_3 + custom_name: BUZZER + label: BUZZER + timer: TIM4 + - channel: TIM_CHANNEL_2 + custom_name: TIM1_CH2 + label: TIM1_CH2 + timer: TIM1 + - channel: TIM_CHANNEL_3 + custom_name: TIM1_CH3 + label: TIM1_CH3 + timer: TIM1 + - channel: TIM_CHANNEL_4 + custom_name: TIM1_CH4 + label: TIM1_CH4 + timer: TIM1 + - channel: TIM_CHANNEL_1 + custom_name: TIM1_CH1 + label: TIM1_CH1 + timer: TIM1 + - channel: TIM_CHANNEL_1 + custom_name: IMU_HEAT_PWM + label: IMU_HEAT_PWM + timer: TIM10 + - channel: TIM_CHANNEL_1 + custom_name: LED_B + label: LED_B + timer: TIM5 + - channel: TIM_CHANNEL_2 + custom_name: LED_G + label: LED_G + timer: TIM5 + - channel: TIM_CHANNEL_3 + custom_name: LED_R + label: LED_R + timer: TIM5 + - channel: TIM_CHANNEL_2 + custom_name: TIM8_CH2 + label: TIM8_CH2 + timer: TIM8 + enabled: true +spi: + devices: + - instance: SPI1 + name: BMI088 + enabled: true +time: + enabled: true +uart: + devices: + - instance: USART3 + name: DR16 + enabled: true