STM32 GPIO模拟UART串口:最简延时方式

2023-05-16

STM32 GPIO模拟UART串口:最简延时方式

在一些应用场景,MCU的硬件UART资源不足时,或者可用于硬件UART配置的管脚优先配置给了其它功能使用,就可以通过GPIO模拟UART功能以获得串口支持。本文介绍基于延时方式的实现,除了TX和RX两个GPIO管脚,不需要用到其它MCU资源。延时的实现需要用到微秒延时函数,参考 STM32 HAL us delay(微秒延时)的指令延时实现方式及优化 。

这里以STM32F401CCU6芯片,STM32CUBEIDE开发平台实现模拟UART的范例。范例的UART通讯协议采用最常用的配置,即一个起始位,8个数据位,一个停止位,波特率为9600bps,码宽为104us。如果需要扩展高级功能,可以基于范例的基本实现进行修改。

字节发送过程,通过微秒延时控制按周期进行位的发送,对应的GPIO配置为push-pull输出,默认输出高电平。
字节接收过程,通过将接收管脚设置为下降沿触发中断,从而在第一个下降沿到来时识别为接收开始,然后通过微秒延时控制,在1.5个周期时接收第一个位,随后都在1个周期延时接收后续的位。在接收到停止位时进行数据处理和后续接收准备。

范例的工程设计为回环测试。RX管脚接收到一个字节后,TX管脚将这个字节发出去。

工程配置

首先建立基本工程配置,设置时钟系统:
在这里插入图片描述
在这里插入图片描述
然后选择一对GPIO作为模拟UART的TX和RX管脚。这里用PA0作为TX, PA1作为RX(下降沿中断模式)。
在这里插入图片描述
在这里插入图片描述
并使能PA1的下降沿中断响应:
在这里插入图片描述
在这里插入图片描述
保存并生成基本工程代码:
在这里插入图片描述

代码实现

接收过程和发送过程都要进行状态控制以识别和控制空闲态和工作态,接收管脚接收到第一个下降沿中断时会识别为接收开始,后续接收数据过程中也会有下降沿中断接收到,但不会做处理,而是在周期延时控制下进行数据位的接收,接收完一个字节之后,后续来的下降沿才会识别为新的数据接收开始。

完整的main.c代码如下:

/* USER CODE BEGIN Header */
/**
  ******************************************************************************
  * @file           : main.c
  * @brief          : Main program body
  ******************************************************************************
  * @attention
  *
  * Copyright (c) 2022 STMicroelectronics.
  * All rights reserved.
  *
  * This software is licensed under terms that can be found in the LICENSE file
  * in the root directory of this software component.
  * If no LICENSE file comes with this software, it is provided AS-IS.
  *
  ******************************************************************************
  */
//Written by Pegasus Yu in 2022
/* USER CODE END Header */
/* Includes ------------------------------------------------------------------*/
#include "main.h"

/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */

/* USER CODE END Includes */

/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */

/* USER CODE END PTD */

/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */
__IO float usDelayBase;
void PY_usDelayTest(void)
{
  __IO uint32_t firstms, secondms;
  __IO uint32_t counter = 0;

  firstms = HAL_GetTick()+1;
  secondms = firstms+1;

  while(uwTick!=firstms) ;

  while(uwTick!=secondms) counter++;

  usDelayBase = ((float)counter)/1000;
}

void PY_Delay_us_t(uint32_t Delay)
{
  __IO uint32_t delayReg;
  __IO uint32_t usNum = (uint32_t)(Delay*usDelayBase);

  delayReg = 0;
  while(delayReg!=usNum) delayReg++;
}

void PY_usDelayOptimize(void)
{
  __IO uint32_t firstms, secondms;
  __IO float coe = 1.0;

  firstms = HAL_GetTick();
  PY_Delay_us_t(1000000) ;
  secondms = HAL_GetTick();

  coe = ((float)1000)/(secondms-firstms);
  usDelayBase = coe*usDelayBase;
}


void PY_Delay_us(uint32_t Delay)
{
  __IO uint32_t delayReg;

  __IO uint32_t msNum = Delay/1000;
  __IO uint32_t usNum = (uint32_t)((Delay%1000)*usDelayBase);

  if(msNum>0) HAL_Delay(msNum);

  delayReg = 0;
  while(delayReg!=usNum) delayReg++;
}
/* USER CODE END PD */

/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */
#define GPIO_OUTPUT_EXEC_DELAY_us 8
#define BaudRate_us 104 //for 9600bps
#define RD HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_1);
#define TDL HAL_GPIO_WritePin(GPIOA, GPIO_PIN_0, GPIO_PIN_RESET)
#define TDH HAL_GPIO_WritePin(GPIOA, GPIO_PIN_0, GPIO_PIN_SET)
/* USER CODE END PM */

/* Private variables ---------------------------------------------------------*/

/* USER CODE BEGIN PV */
#define buff_len 256
uint8_t tx_status = 0;
uint8_t rx_status = 0;

uint8_t txd[buff_len];
uint8_t rxd[buff_len];

uint32_t txd_index=0;
uint32_t rxd_index=0;
/* USER CODE END PV */

/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
static void MX_GPIO_Init(void);
/* USER CODE BEGIN PFP */

/* USER CODE END PFP */

/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */

/* USER CODE END 0 */

/**
  * @brief  The application entry point.
  * @retval int
  */
int main(void)
{
  /* USER CODE BEGIN 1 */
  uint8_t bytebit;
  /* USER CODE END 1 */

  /* MCU Configuration--------------------------------------------------------*/

  /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
  HAL_Init();

  /* USER CODE BEGIN Init */

  /* USER CODE END Init */

  /* Configure the system clock */
  SystemClock_Config();

  /* USER CODE BEGIN SysInit */

  /* USER CODE END SysInit */

  /* Initialize all configured peripherals */
  MX_GPIO_Init();
  /* USER CODE BEGIN 2 */
  PY_usDelayTest();
  PY_usDelayOptimize();

  /* USER CODE END 2 */

  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
	  switch(rx_status)
	  {

	  case 1:{//bit 1
		     rxd[rxd_index] = 0;
             PY_Delay_us_t(1.5*BaudRate_us);
             bytebit = RD;
             (bytebit==0)?(rxd[rxd_index]>>=1):(rxd[rxd_index]=(rxd[rxd_index]>>1)|0x80);
             rx_status ++;
	         }
	  case 2:{//bit 2
             PY_Delay_us_t(BaudRate_us);
             bytebit = RD;
             (bytebit==0)?(rxd[rxd_index]>>=1):(rxd[rxd_index]=(rxd[rxd_index]>>1)|0x80);
             rx_status ++;
	         }
	  case 3:{//bit 3
             PY_Delay_us_t(BaudRate_us);
             bytebit = RD;
             (bytebit==0)?(rxd[rxd_index]>>=1):(rxd[rxd_index]=(rxd[rxd_index]>>1)|0x80);
             rx_status ++;
	         }
	  case 4:{//bit 4
             PY_Delay_us_t(BaudRate_us);
             bytebit = RD;
             (bytebit==0)?(rxd[rxd_index]>>=1):(rxd[rxd_index]=(rxd[rxd_index]>>1)|0x80);
             rx_status ++;
	         }
	  case 5:{//bit 5
             PY_Delay_us_t(BaudRate_us);
             bytebit = RD;
             (bytebit==0)?(rxd[rxd_index]>>=1):(rxd[rxd_index]=(rxd[rxd_index]>>1)|0x80);
             rx_status ++;
	         }
	  case 6:{//bit 6
             PY_Delay_us_t(BaudRate_us);
             bytebit = RD;
             (bytebit==0)?(rxd[rxd_index]>>=1):(rxd[rxd_index]=(rxd[rxd_index]>>1)|0x80);
             rx_status ++;
	         }
	  case 7:{//bit 7
             PY_Delay_us_t(BaudRate_us);
             bytebit = RD;
             (bytebit==0)?(rxd[rxd_index]>>=1):(rxd[rxd_index]=(rxd[rxd_index]>>1)|0x80);
             rx_status ++;
	         }
	  case 8:{//bit 8
             PY_Delay_us_t(BaudRate_us);
             bytebit = RD;
             (bytebit==0)?(rxd[rxd_index]>>=1):(rxd[rxd_index]=(rxd[rxd_index]>>1)|0x80);
             rx_status ++;
	         }
	  case 9:{//stop bit
             PY_Delay_us_t(BaudRate_us);
             bytebit = RD;
             if(bytebit==1)
             {
                 tx_status = 1; //Sending enable for loop-back test
                 bytebit = rxd[rxd_index];

            	 if(rxd_index==(buff_len-1)) rxd_index=0;
            	 else rxd_index++;

             }

             rx_status = 0;
		     break;
	         }

	  default:break;
	  }

	  switch(tx_status)
	  {

	  case 1:{//start bit
             TDL;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             tx_status ++;
	         }
	  case 2:{//bit 1
             if((bytebit&0x01)==0) TDL;
             else TDH;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             bytebit >>= 1;
             tx_status ++;
	         }
	  case 3:{//bit 2
             if((bytebit&0x01)==0) TDL;
             else TDH;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             bytebit >>= 1;
             tx_status ++;
	         }
	  case 4:{//bit 3
             if((bytebit&0x01)==0) TDL;
             else TDH;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             bytebit >>= 1;
             tx_status ++;
	         }
	  case 5:{//bit 4
             if((bytebit&0x01)==0) TDL;
             else TDH;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             bytebit >>= 1;
             tx_status ++;
	         }
	  case 6:{//bit 5
             if((bytebit&0x01)==0) TDL;
             else TDH;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             bytebit >>= 1;
             tx_status ++;
	         }
	  case 7:{//bit 6
             if((bytebit&0x01)==0) TDL;
             else TDH;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             bytebit >>= 1;
             tx_status ++;
	         }
	  case 8:{//bit 7
             if((bytebit&0x01)==0) TDL;
             else TDH;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             bytebit >>= 1;
             tx_status ++;
	         }
	  case 9:{//bit 8
             if((bytebit&0x01)==0) TDL;
             else TDH;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             tx_status ++;
	         }
	  case 10:{//stop bit
             TDH;
             PY_Delay_us_t(BaudRate_us-GPIO_OUTPUT_EXEC_DELAY_us);
             tx_status = 0;
	         }
	  default:break;
	  }
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
  }
  /* USER CODE END 3 */
}

/**
  * @brief System Clock Configuration
  * @retval None
  */
void SystemClock_Config(void)
{
  RCC_OscInitTypeDef RCC_OscInitStruct = {0};
  RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};

  /** Configure the main internal regulator output voltage
  */
  __HAL_RCC_PWR_CLK_ENABLE();
  __HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE2);

  /** Initializes the RCC Oscillators according to the specified parameters
  * in the RCC_OscInitTypeDef structure.
  */
  RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI;
  RCC_OscInitStruct.HSIState = RCC_HSI_ON;
  RCC_OscInitStruct.HSICalibrationValue = RCC_HSICALIBRATION_DEFAULT;
  RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI;
  RCC_OscInitStruct.PLL.PLLM = 16;
  RCC_OscInitStruct.PLL.PLLN = 336;
  RCC_OscInitStruct.PLL.PLLP = RCC_PLLP_DIV4;
  RCC_OscInitStruct.PLL.PLLQ = 4;
  if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
  {
    Error_Handler();
  }

  /** Initializes the CPU, AHB and APB buses clocks
  */
  RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
                              |RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;
  RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
  RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
  RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV2;
  RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;

  if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_2) != HAL_OK)
  {
    Error_Handler();
  }
}

/**
  * @brief GPIO Initialization Function
  * @param None
  * @retval None
  */
static void MX_GPIO_Init(void)
{
  GPIO_InitTypeDef GPIO_InitStruct = {0};

  /* GPIO Ports Clock Enable */
  __HAL_RCC_GPIOA_CLK_ENABLE();

  /*Configure GPIO pin Output Level */
  HAL_GPIO_WritePin(GPIOA, GPIO_PIN_0, GPIO_PIN_SET);

  /*Configure GPIO pin : PA0 */
  GPIO_InitStruct.Pin = GPIO_PIN_0;
  GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
  GPIO_InitStruct.Pull = GPIO_NOPULL;
  GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH;
  HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);

  /*Configure GPIO pin : PA1 */
  GPIO_InitStruct.Pin = GPIO_PIN_1;
  GPIO_InitStruct.Mode = GPIO_MODE_IT_FALLING;
  GPIO_InitStruct.Pull = GPIO_PULLUP;
  HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);

  /* EXTI interrupt init*/
  HAL_NVIC_SetPriority(EXTI1_IRQn, 0, 0);
  HAL_NVIC_EnableIRQ(EXTI1_IRQn);

}

/* USER CODE BEGIN 4 */
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{

  if(GPIO_Pin==GPIO_PIN_1)
  {
	if(rx_status==0) rx_status = 1;  //get falling edge of start bit
  }
}
/* USER CODE END 4 */

/**
  * @brief  This function is executed in case of error occurrence.
  * @retval None
  */
void Error_Handler(void)
{
  /* USER CODE BEGIN Error_Handler_Debug */
  /* User can add his own implementation to report the HAL error return state */
  __disable_irq();
  while (1)
  {
  }
  /* USER CODE END Error_Handler_Debug */
}

#ifdef  USE_FULL_ASSERT
/**
  * @brief  Reports the name of the source file and the source line number
  *         where the assert_param error has occurred.
  * @param  file: pointer to the source file name
  * @param  line: assert_param error line source number
  * @retval None
  */
void assert_failed(uint8_t *file, uint32_t line)
{
  /* USER CODE BEGIN 6 */
  /* User can add his own implementation to report the file name and line number,
     ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */
  /* USER CODE END 6 */
}
#endif /* USE_FULL_ASSERT */

注意事项

本范例采用自然指令延时实现UART收发,在接收完整个字节或发送完整个字节前不能被打断,否则时序不准会出错。所以本范例方式适用于不会同时进行收发的场景。
本范例实现环回测试,通过PC连接MCU后可以发送单个字节并接收到回送的字节。不能同时发2个字节以上,因为收到第一个字节后就开始回传,如果有第二个以上的字节接收,则如上所述会产生时序冲突。当然,通过具体的协议控制,修改程序,可以控制程序在接收到符合条件/数目的字节后才开始处理如回送,则一次接收到的串口数据不受限制。
要实现能够同时进行收发的模拟UART功能,提高鲁棒性,则需要用到TIM定时器资源。可参阅 STM32 GPIO模拟UART串口:外部时钟及TIM方式。

测试效果

通过串口工具向例程芯片发送数据,得到回送的数据:
在这里插入图片描述
再发送一次单字节
在这里插入图片描述

例程下载

STM32 GPIO模拟UART串口:最简延时方式 例程下载

–End–

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

STM32 GPIO模拟UART串口:最简延时方式 的相关文章

  • STM32超声波——HC_SR04

    文章目录 一 超声波图片 二 时序图 三 超声波流程 四 单位换算 五 取余计算 六 换算距离 七 超声波代码 一 超声波图片 测量距离 2cm 400cm 二 时序图 1 以下时序图要先提供一个至少10us的脉冲触发信号 告诉单片机我准备
  • 物联网网关

    物联网网关是 连接物联网设备和互联网的重要桥梁 它负责将物联网设备采集到的数据进行处理 存储和转发 使其能够与云端或其它设备进行通信 物联网网关的作用是实现物联网设备与云端的无缝连接和数据交互 物联网网关功能 数据采集 物联网网关可以从物联
  • STM32F103概要

    The STM32F103x4 STM32F103x6 STM32F103xC STM32F103xD and STM32F103xE are a drop in replacement for STM32F103x8 B medium d
  • HAL 锁定和解锁函数如何使用以及为什么?

    我试图理解另一位程序员编写的代码 它使用了I C http en wikipedia org wiki I C2 B2C通信以将数据写入 STM32 微控制器的 EEPROM 一般来说 我理解他的代码是如何工作的 但我不明白他为什么使用HA
  • 硬件基础-电容

    电容 本质 电容两端电压不能激变 所以可以起到稳定电压作用 充放电 电容量的大小 想使电容容量大 使用介电常数高的介质 增大极板间的面积 减小极板间的距离 品牌 国外 村田 muRata 松下 PANASONIC 三星 SAMSUNG 太诱
  • IOError:[Errno 2]没有这样的文件或目录(当它确实存在时)Python [重复]

    这个问题在这里已经有答案了 我正在通过 python 中的 uart 传输文件文件夹 下面您可以看到简单的功能 但有一个问题 因为我收到如标题所示的错误 IOError Errno 2 No such file or directory 1
  • 跟着野火学FreeRTOS:第一段(任务定义,切换以及临界段)

    在裸机系统中 系统的主体就是 C P U CPU CP U 按照预先设定的程序逻辑在 m a i n
  • mmap 比 ioremap 慢

    我正在为运行 Linux 2 6 37 的 ARM 设备进行开发 我正在尝试尽快切换 IO 引脚 我制作了一个小内核模块和一个用户空间应用程序 我尝试了两件事 使用以下命令直接从内核空间操作 GPIO 控制寄存器ioremap mmap G
  • Sphinx:如何排除自动模块中的导入?

    我有一个用 Python 编写的 Raspberry Pi 项目 它使用 RPi GPIO 模块 代码上的所有工作都是在 Windows 机器上完成的 其中 RPi GPIO 不会安装 每次我尝试运行 autodoc 时 它都会崩溃 说它无
  • gpiod - 在设备树中使用标签

    我想用libgpiod通过自定义板上的用户空间控制一些 GPIO 我有一个 i MX6UL 处理器 它有数百个引脚 我将只使用其中 8 个 作为 GPIO 我读到了关于libgpiod因为它正在取代旧的 sysfs API 我很高兴您可以为
  • Freertos低功耗管理

    空闲任务中的低功耗Tickless处理 在整个系统运行得过程中 其中大部分时间都是在执行空闲任务的 空闲任务之所以执行 因为在系统中的其他任务处于阻塞或者被挂起时才会执行 因此可以将空闲任务的执行时间转换成低功耗模式 在其他任务解除阻塞而准
  • 从没有中断引脚并且在测量准备好之前需要一些时间的传感器读取数据的最佳方法

    我正在尝试将压力传感器 MS5803 14BA 与我的板 NUCLEO STM32L073RZ 连接 根据 第 3 页 压力传感器需要几毫秒才能准备好读取测量值 对于我的项目 我对需要大约 10 毫秒来转换原始数据的最高分辨率感兴趣 不幸的
  • 通过 USB 模拟 UART

    有谁知道是否可以通过 USB 模拟 UART 简单串行发送和接收 这将如何实现 我在 Microchip 网站上找到了这个链接 但不是很容易找到 http www microchip com forums m522571 print asp
  • 跨线程操作无效:从创建它的线程以外的线程访问控制“textBox1”[重复]

    这个问题在这里已经有答案了 我想使用 UART 将温度值从微控制器发送到 C 接口并显示温度Label Content 这是我的微控制器代码 while 1 key scan get value of temp if Usart Data
  • 如何在Python脚本中获取方波的频率

    我正在使用 TSL235 http www ti com lit ds symlink tsl235 pdf http www ti com lit ds symlink tsl235 pdf 光频转换器和 Raspberry Pi 传感器
  • HAL_Delay() 陷入无限循环

    我被 HAL Delay 函数困住了 当我调用此函数 HAL Delay 时 控制陷入无限循环 在寻找问题的过程中 我发现了这个 http www openstm32 org forumthread2145 threadId2146 htt
  • 使用 STM32F0 ADC 单独读取不同的输入

    STM32F072CBU 微控制器 我有多个 ADC 输入 并且希望单独读取它们 STMcubeMX 生成样板代码 假设我希望按顺序读取所有输入 但我无法弄清楚如何纠正这个问题 这篇博文 http blog koepi info 2015
  • 如何在嵌入式Linux中检测GPIO线上的中断?

    GPIO 39 上每 10ms 产生一个中断熊猫板 OMAP4 http www ti com product OMAP4460 我已在 Linux 驱动程序代码中为此注册了一个处理程序 但由于未检测到中断 因此未调用该处理程序 我在硬件级
  • 对 FINTEK F81866A 芯片组上的 GPIO 引脚进行编程

    我有一个德承DE 1000 http www cincoze com goods info php id 10工业 PC 具有芬泰克 F81866A http www fintek com tw index php i o controll
  • 使用 BeagleBone Black 内核 >= 3.8 打开/关闭 USB 电源

    我需要 关闭 gt 睡眠几秒钟 gt 打开 beaglebone black 的 USB 电源 能够对连接到 USB 的设备 华为 E220 调制解调器 进行硬件重置 已经尝试过软重置 使用取消绑定 绑定和授权0 1 但软件重置不足以使设备

随机推荐

  • c++ stream iword、pword和register_callback函数

    pword xff0c stream 的 register callback函数 include lt iostream gt include lt sstream gt using namespace std const int name
  • AWS CLI version 2 在 Windows 下的安装

    首先你需要到下面的链接地址中下载需要的应用 xff1a https awscli amazonaws com AWSCLIV2 msi 双击运行 双击运行下载的可以运行的文件 下一步继续 下一步继续安装进程 许可协议 你需要同意许可协议后继
  • MATLAB安装时为英文如何切换中文

    MATLAB安装时为英文如何切换中文 MATLAB安装问题 问题描述 2018b及以上版本的MATLAB安装时 xff0c 其中英文模式会根据电脑所在区域环境进行配置 若电脑所在区域环境不在中国 xff0c 则MATLAB初始化安装会被定义
  • VINS-Fusion-RGBD在双轮差数轮小车上配置并进行稠密建图

    VINS Fusion RGBD在小车上进行稠密建图 1 轮式里程计代替视觉里程计2 其他获得更为鲁棒性建图效果的做法3 点云地图及栅格地图的获得4 多个参数可配置 VINS Mono由于存在运动初始化过程 xff0c 对于地面小车来说运动
  • ST LINK V2.1接线图

    方便查询 xff0c 图片来源已经忘记了 xff0c 如有冒犯请通知我 特此记录以防忘记 anlog 2020年8月29日
  • ROS笔记之Gazebo机器人仿真(二)——Soildworks搭建机器人模型

    1 引言 机器人的模型是通过URDF文件进行描述 xff0c 具体说明可以参考URDF 但对于一些复杂的机器人 xff0c 通过直接编写URDF文件就比较繁琐 xff0c 这里我们介绍一种通过专业的三维建图软件Soildworks构建模型然
  • ROS笔记之Gazebo机器人仿真(四)——Rviz及Gazebo下机器人模型显示

    1 引言 上一章中我们成功导出了URDF文件 xff0c 这章中我们将学习如何在Rviz和Gazebo下显示我们创建的三维模型 2 预备 首先 xff0c 我们需要对导出的URDF文件进行下修改 xff08 1 xff09 package
  • 制作树莓派镜像img,并在其他新板上使用,实现批量克隆树莓派板

    1 将现有的系统制作成镜像img 2 配置网络 1 将现有的系统制作成镜像img 1 1 先将新买的sd卡用SDFormatter工具格式化 xff0c 以作备用 1 2 将带有系统的sd卡用Win32DiskImager exe工具Rea
  • Qt开发-Qt对象间的关系

    一 Qt对象间的关系 1 Qt对象间可以存在父子关系 xff08 1 xff09 每个对象都保存有它所有子对象的指针 xff08 2 xff09 每一个对象都有一个指向其父对象的指针 2 当指定Qt对象的父对象时 xff08 1 xff09
  • VScode+esp-idf:例程(esp32-web-camera)保存视频到sd卡(附源码)

    文章目录 1 移植到 esp32 web camera 2 jpeg2avi使用方法2 1 何处调用jpeg2avi start2 2 何处调用jpeg2avi add frame2 3何处调用jpeg2avi end 3 编译运行工程4
  • 单片机能代替PLC吗?过来人告诉你

    随着科技的进步和市场的需要 xff0c 近年来出现了 非常多 类似Arduino 这样的开源电子原型平台 xff0c 它们大部分实现了对单片机的二次封装 xff0c 所有外设 模块接口都是现成的 xff0c 对于 使用者 的要求 只需懂C语
  • STM32学到什么程度可以就业

    很多在门外观望的朋友总会有这些担心 STM32难不难学 xff1f 学到什么程度可以去工作 xff1f 前景怎么样 xff1f 对应的工资高不高 xff1f 对于小编来说最难的事你已经在做了 xff0c 就是还在门口观望 xff0c 望来望
  • 那么辛苦的熬单片机,不拿它DIY点小玩意怎么对得起自己。

    大家好 xff0c 我是华维蔵鹰 xff0c 不管你处于什么身份 做任何一件事情你都会需要一个动力的源泉 在大学中很多人弹吉他并不是爱好它 xff0c 只是为了多点机会去接触些妹子 xff0c 就像我们以前刚入门单片机的时候 xff0c 都
  • 众人寻AI千百度

    引 xff1a 说起AI xff0c 或许很多普通人仍然不清楚这是什么 然而说起人工智能 xff0c 机器人 xff0c 想必大家不是如雷贯耳也是耳濡目染 xff0c 略知一二 从小我们便不断的从电影 xff0c 电视剧中接触AI xff0
  • PID知识总结

    PID算法算是控制系统中一个比较常见的控制算法了 xff0c 特别是在闭环控制系统中 xff0c PID的使用尤为常见 xff0c 鄙人由于电赛延期在家闲来无事 xff0c 决定把自己在电赛备赛期间所学的PID知识总结一下 xff0c 希望
  • Java中this关键字的几种用法

    1 当成员变量和局部变量重名时 xff0c 在方法中使用this 时 xff0c 表示的是该方法所在类中的成员变量 xff08 this 是当前对象自己 xff09 如 xff1a public class Hello String s 6
  • WIN10 ping不通 VMWare CentOS7

    如题 Win10 ping不通VMWare下的Centos7 因为使用的是NAT模式 xff0c 所以检查虚拟网络编辑器下面的配置 VMWare下编辑 gt 虚拟网络编辑器 查看VMnet8的IP 设置虚拟机的IP地址和VMnet同一段 启
  • 计算机视觉数据集大全 - Part2

    转载自http homepages inf ed ac uk rbf CVonline Imagedbase htm Index by Topic Action Databases Agriculture Attribute recogni
  • Server unexpectedly closed network connection的解决

    1 apt get remove openssh server 2 sudo apt install openssh server 3 sudo service ssh start 4 ps aux grep ssh 5 sudo apt
  • STM32 GPIO模拟UART串口:最简延时方式

    STM32 GPIO模拟UART串口 xff1a 最简延时方式 在一些应用场景 xff0c MCU的硬件UART资源不足时 xff0c 或者可用于硬件UART配置的管脚优先配置给了其它功能使用 xff0c 就可以通过GPIO模拟UART功能