1.硬件

1.1 电机

RM有很多不同型号的电机,不同型号的电机有它不同的用途,但是以用途分类的话主要是分成两种电机:

  1. 用来精准控制位置的电机,在RM中的主要是云台电机。

    RM官网上的云台电机只有一款:GM6020。云台电机的特点就是:运动无噪音、大力矩、高精度。尤其是大力矩高精度,这点对于云台电机很重要。还有一点与其他的电机不太一样的是,云台电机一般是电压驱动。这一点在使用的细节上也有体现

    云台电机是利用压电材料输入电压会产生变形的特性,使其能产生超声波频率的机械振动,再透过摩擦驱动的机构设计,让云台电机如同电磁马达一般,可做旋转运动或直线式移动。

  1. 用来提供动力的电机

    提供动力的电机现在在RM有两种,一种是M3508减速直流电机,一种是M2006 P36直流无刷减速电机。前者扭矩更大,一般被用作轮子的驱动;后者往往用来做播弹系统的动力来源。

我们的主控不能直接去控制电机,而需要中间加一个电调来作为中间人,收到主控的命令后通知电机进行相关的运动,并且通过can总线获取电机的温度、转子位置和转子转速等信息返送给主控。GM6020云台电机内部自带电调

1.2 主控

目前主要使用到的主控是C板和A板。因为C板自带陀螺仪,被用来控制机器人的云台部分。A板用来控制机器人底盘的运动。

2.软件

软件部分主要就是如何通过Cubemx配置,并且在clion中编写Cubemx不能配置的部分(我想说的是用来接收can通讯信息的接收过滤器)、电机的具题控制参数与逻辑。

2.1 Cubemx配置

2.1.1 芯片选型

通过查看主控板的手册,可以知道主控芯片用的是STM32F427IIH6芯片,因此在Cubemx中选择对应的芯片型号,进入配置。

2.1.2 时钟配置

2.1.2.1先开启时钟

在RCC栏中使能外部高速时钟HSE,使用的信号选择晶振信号。

2.1.2.2 配置时钟树

​ f4系列的时钟树相较于f1系列明显长的更大,更复杂,先粗浅的配置它一下,之后有对时钟特殊的要求的时候再进行仔细的配置和了解。之前的f1的外部晶振时钟是8MHZ的因此左侧标红的区域(Input frequency)选择的是8。但是这个开发板的外部晶振是12MHZ的,因此就相应的选择成12。选择HSE通道,然后将系统时钟调到最大(180Mhz),直接在HCLK处填入180,Cube就会自动帮你配置。

2.1.3 debug配置

Pinout & Configuration中的System Core配置SYS的时候将Debug选择成Serial Wire

如果没有勾选Serial Wire 程序只能下载一遍,然后需要将BOOT1、BOOT2引脚电平通过跳线帽均置为高电平并复位开发板,然后再尝试将正确的程序重新下载,下载完成后,需要将BOOT引脚都恢复为低电平。

2.1.4 can外设配置

2.1.4.1 can外设开启

在Connectivity选项栏中选中要开启的CAN外设。点击Activated开启。

2.1.4.2 引脚选择

然后去查看开发板的原理图,找到相应的外设的引脚,看看和他默认的是否相同。有的一些外设对应的引脚和Cube里默认的引脚是不一样的,这一点很重要,要确认一下。

RM开发板手册资料:RoboMaster开发板套件

如果引脚不对应那么根据原理图中的引脚,在Cubemx中找到对应的引脚选择上对应的功能

2.1.4.3 开启接收中断

电调会通过can总线发送电机信息给主控,can总线收到信息后进入接收中断,因此要开启can的接收中断。

2.1.4.4 配置波特率

由于CAN属于异步通讯,没有时钟信号线,连接在同一个总线网络中的各个节点会像串口异步通讯那样,节点间使用约定好的波特率进行通讯。

can外设的通信速率最大是1MHZ,因此我们需要调节CAN外设分频系数、BS1段长度、BS2段长度来把波特率调到1Mhz。

经过前人的经验总结:分别设置成3 、10、3的时候正好可以成1Mhz,但是不能直接按顺序设置,因为如果预分频系数设置成3,BS1段是不允许设置成10的,因此要先将预分频系数调大,然后调BS1和BS2段最后再将分频设置成3.

波特率计算知识点:

2.1.5 生成文件

2.1.5.1 生成成对的.c/.h文件

2.1.5.2 配置使用clion IDE 打开

之后生成代码即可

在生成好文件后选择打开文件夹(Open Folder),而不是直接打开工程(Open Project),否则它会不知道用什么打开

之后返回打开的文件夹的上一层,然后右键用clion打开文件

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-yHjmWgli-1651241400621)(https://www.houenup.com/wp-content/uploads/2022/03/image-2022030117300085-300x86.png)]

2.2 代码部分配置

2.2.1 接收过滤器配置

2.2.1.1 配置代码
CAN_FilterTypeDef can_filter_st;                     //实例化一个can接收过滤器
can_filter_st.FilterBank = 0;                      //选择过滤器0
can_filter_st.FilterActivation = ENABLE;           //开启该过滤器
can_filter_st.FilterMode = CAN_FILTERMODE_IDMASK;  //筛选器模式是ID掩码模式
can_filter_st.FilterScale = CAN_FILTERSCALE_32BIT; //筛选器位宽
can_filter_st.FilterIdHigh = 0x0000;
can_filter_st.FilterIdLow = 0x0000;
can_filter_st.FilterMaskIdHigh = 0x0000;
can_filter_st.FilterMaskIdLow = 0x0000;
can_filter_st.FilterFIFOAssignment = CAN_RX_FIFO0  //把接收到的报文放入到FIFO0中
HAL_CAN_ConfigFilter(&hcan1, &can_filter_st);       //把过滤器配置配置给can1外设
2.2.1.2 相关知识点
接收中断:

一旦往FIFO存入一个报文,硬件就会更新FMP[1:0]位,并且如果CAN_IER寄存器的FMPIE位为’1’,那么就会产生一个中断请求。
当FIFO 变 满 时( 即 第3 个 报 文 被 存 入) , CAN_RFR 寄 存 器 的FULL 位 就 被 置’1’ , 并 且 如 果CAN_IER寄存器的FFIE位为’1’,那么就会产生一个满中断请求。
在溢出的情况下, FOVR位被置’1’,并且如果CAN_IER寄存器的FOVIE位为’1’,那么就会产生一个溢出中断请求。

接收FIFO:

​ CAN外设一共有2个接收FIFO,每个FIFO中有3个邮箱,即最多可以缓存6个接收到的报文。当接收到报文时,FIFO的报文计数器会自增,而STM32内部读取FIFO数据后,报文计数器会自减,通过状态寄存器可获知报文计数器的值

STM32的 CAN 有两个 FIFO,分别是 FIFO0和 FIFO1。为了便于区分,下面 FIFO0写作FIFO_0,FIFO1写作 FIFO_1。
每组过滤器组必须关联且只能关联一个 FIFO。复位默认都关联到 FIFO_0。所谓“关联”是指假如收到的报文从某个过滤器通过了,那么该报文会被存到该过滤器相连的 FIFO。从另一方面来说,每个 FIFO 都关联了一串的过滤器组,两个 FIFO 刚好瓜分了所有的过滤器组。每当收到一个报文,CAN 就将这个报文先与 FIFO_0关联的过滤器比较,如果被匹配,就将此报文放入 FIFO_0中。如果不匹配, 再将报文与 FIFO_1关联的过滤器比较, 如果被匹配, 该报文就放入 FIFO_1中。如果还是不匹配,此报文就被丢弃。
每个 FIFO 的所有过滤器都是并联的,只要通过了其中任何一个过滤器,该报文就有效。如果一个报文既符合 FIFO_0的规定,又符合 FIFO_1的规定,显然,根据操作顺序,它只会放到 FIFO_0中。
每个 FIFO 中只有激活了的过滤器才起作用,换句话说,如果一个 FIFO 有20个过滤器,但是只激话了5个,那么比较报文时,只拿这5个过滤器作比较。一般要用到某个过滤器时,在初始化阶段就直接将它激活。需要注意的是,每个 FIFO 必须至少激活一个过滤器,它才有可能收到报文。如果一个过滤器都没有激活,那么是所有报文都报废的。一般的,如果不想用复杂的过滤功能, FIFO 可以只激活一组过滤器组,且将它设置成 32位的屏蔽位模式,两个标准值寄存器(FxR1,FxR2)都设置成0。这样所有报文均能通过。(STM32提供的例程里就是这么做的! )

验收筛选器:

​ 在CAN协议中,消息的标识符与节点地址无关,但与消息内容有关。因此,发送节点将报文广播给所有接收器时,接收节点会根据报文标识符的值来确定软件是否需要该消息,为了简化软件的工作,STM32的CAN外设接收报文前会先使用验收筛选器检查,只接收需要的报文到FIFO中,筛选器工作的时候,可以调整筛选ID的长度及过滤模式。根据过滤方法分为标识符列表模式掩码模式

筛选器模式:
  1. 标志符列表模式:

​ 它把要接收的报文的ID列成一个表,要求报文ID与列表中的某一个标识符完全相同才可以接收,可以理解为白名单

标识符列表模式下,CAN_FxR1 和 CAN_FxR2中都是要匹配的标识符,收到的帧的标识符必须与其中一个吻合才能通过过滤

  1. 掩码模式:

​ 它把可接收报文ID的某几位作为列表,这几位称为掩码,可以把它理解成关键字搜索,只要掩码(关键字相同),就符合要求,报文就会被保存到接收FIFO。

掩码模式下,那个填写掩码的寄存器与想要筛出来的ID一位一位地对应 ,那个想要筛出来的ID寄存器就填写对应位想要的数,然后掩码寄存器对应的位填写是否需要一致(如果想要该位与需要该位筛选出来的ID的数值相同,则需要在该位的掩码上写上1,不需要相同则写上0即可)

理解:标识符列表模式是为了过滤出一个标识符,而屏蔽位模式因为屏蔽了某些位所以可以过滤出一组标识符,对于不需要用筛选器组的应处以禁用状态

一般我们用的都是普通型的,所以在本文中可以说 STM32有14组过滤器组。根据配置,每1组过滤器组可以有1个,2个或4个过滤器。这些过滤器相当于关卡,每当收到一条报文时,CAN 要先将收到的报文从这些过滤器上”过”一下,能通过的报文是有效报文,收进 FIFO,不能通过的是无效报文(不是发给”我”的报文),直接丢弃。通过对两个可配置寄存器值得改变可以选择过滤器的数量。在一组过滤器中,整组的过滤器都使用同一种工作模式

1.在32位的屏蔽位模式下:
有1个过滤器。
FxR2用于指定需要关心哪些位,FxR1用于指定这些位的标准值。
2.在32位的列表模式下:
有两个过滤器。
FxR1指定过滤器0的标准值,收到报文的标识符只有跟 FxR1完全相同时,才算通过。
FxR2指定过滤器1的标准值。
3.在16位的屏蔽位模式下:
有2个过滤器。
FxR1配置过滤器0,其中,[31-16]位指定要关心的位,[15-0]位指定这些位的标准值。
FxR2配置过滤器1,其中,[31-16]位指定要关心的位,[15-0]位指定这些位的标准值。
4.在16位的列表模式下:
有4个过滤器。
FxR1的[15-0]位配置过滤器0,FxR1的[31-16]位配置过滤器1。
FxR2的[15-0]位配置过滤器2,FxR2的[31-16]位配置过滤器3。

2.2.2 开启对应can外设

HAL_CAN_Start(&hcan1);       //开启can1

2.2.3 开启接收中断

 HAL_CAN_ActivateNotification(&hcan1, CAN_IT_RX_FIFO0_MSG_PENDING);CAN_IT_RX_FIFO0_MSG_PENDING:当FIFO0中有消息的时候进入中断。

可以看出CAN_IT_RX_FIFO0_MSG_PENDING中的FIFO0和我们配置过滤器时的报文存放位置式相对应的。

can_filter_st.FilterFIFOAssignment = CAN_RX_FIFO0 //把接收到的报文放入到FIFO0中

2.2.4 在接收中断中获取并解析数据

2.2.4.1 重定义can接收中断回调函数

can中断回调函数是弱定义,我们在任意一个地方重写中断回调函数,并在其中进行对数据的操作。

can接收的中断回调函数是

void HAL_CAN_RxFifo0MsgPendingCallback(CAN_HandleTypeDef *hcan)
2.2.4.2 接收报文结构体
typedef struct
{uint32_t StdId;            //存储了报文的标准标识符 11位uint32_t ExtId;                //存储了报文的扩展标识符 29位uint32_t IDE;                  //存储了IDE扩展标志     uint32_t RTR;              //存储了RTR远程帧标志uint32_t DLC;              //存储了报文数据段的长度,0-8uint32_t Timestamp;             //时间戳   uint32_t FilterMatchIndex;  } CAN_RxHeaderTypeDef;
2.2.4.3 接收函数
HAL_StatusTypeDef HAL_CAN_GetRxMessage(CAN_HandleTypeDef *hcan, uint32_t RxFifo, CAN_RxHeaderTypeDef *pHeader, uint8_t aData[])
作用:从Rx FIFO收取一个can帧
hcan:CAN句柄指针2
Rx FIFO:从哪个FIFO中取。可填 CAN_RX_FIFO0, CAN_RX_FIFO1
*pHeader:接收报文定义结构体的指针
aData[]:接收数据域的指针

接收函数的作用就是从对应的FIFO中收取一帧can数据,然后把Can数据解剖,然后把对应的部分放在我们事先实例化好的接收结构体中,其中最主要的就是DATA部分。

因为can总线上只要有信号通过过滤器进入fifo那么就会进入接收中断,如果can总线上挂载的数据多了,我们就需要根据他们发过来的报文中的ID来分别他们是谁,并通过判断语句进行对应的操作。

2.2.4.4 解析数据

所谓数据的解析,就是从接收函数填充好的接收结构体中拿出我们需要知道的信息,然后读懂DATA中的数据的意思(包括转子位置、转速等信息)。而填充给结构体的数据是电调发过来的,这一帧数据是怎样存放的,电调自己是有一套报文格式的,我们可以通过这个格式来解析对应的信息。

在这里找到C620电调的使用说明:https://www.robomaster.com/zh-CN/products/components/general/M3508

通过查阅手册,我们了解到如何通过标识符来判断这是哪个电机发来的信息如何在DATA中解析到我们想要的数据

我们可以定义一个结构体,每当我们解析数据的时候,直接把对应的data中的数据解析出来存放到对应的实例化好的结构体中。 解析的过程也可以定义一个函数来处理。

结构体定义:
typedef struct
{uint16_t ecd;int16_t speed_rpm;int16_t given_current;uint8_t temperate;int16_t last_ecd;
} motor_measure_t;解析函数:
get_motor_measure(ptr, data)
{(ptr)->last_ecd = (ptr)->ecd;     (ptr)->ecd = (uint16_t)((data)[0] << 8 | (data)[1]);            (ptr)->speed_rpm = (uint16_t)((data)[2] << 8 | (data)[3]);      (ptr)->given_current = (uint16_t)((data)[4] << 8 | (data)[5]);  (ptr)->temperate = (data)[6];    }

2.2.5 接收数据总结与示例

2.2.5.1总结:

接收数据这里写的有点多,这里做一个总结。

首先我们要先启用相应的can总线,这是一定的。

然后在can总线上,因为只有一根总线,而并不是所有的信息我们都要接收(虽然在我们配置的时候配置的是都接受),因此需要配置接收过滤器来过滤掉我们不需要的数据。

如果数据通过了过滤器,进入到了对应的FIFO,那么它就会产生一个中断,因此我们要使能这个接收中断,这样才能在中断产生的时候进入到中断中去,进行下一步的处理。

数据因为进入fifo而呼叫了一个中断,我们进入这个中断的时候就需要用对应的函数来获取这个进入fifo中的数据,然后根据一定的格式来解析它。

在解析的时候为了条例更清晰并且便于我们的操作,我们可以规定一个数据结构体,以及信息解析的一个“方法”。然后在接收中断中我们需要实例化两个结构体。一个结构体是stm32规定的接受数据的结构体,我们获取的帧数据会被解剖填入这个结构体中,其中包括stdid这一项,我们可以通过这一项的数值来判断这帧数据是谁发来的,从而进行对应的操作。 另一个结构体就是我们自己定义的结构体,这个结构体主要是配合我们自己定义的解析数据的方法来使用,将can数据帧中的DATA段数据一项一项地解析出来0。

2.2.5.2中断回调函数示例
#define CAN_CHASSIS_ALL_ID  0x200
#define CAN_3508_M1_ID  0x201
#define CAN_3508_M2_ID 0x202
#define CAN_3508_M3_ID 0x203
#define CAN_3508_M4_ID 0x204数据结构体定义
typedef struct
{uint16_t ecd;int16_t speed_rpm;int16_t given_current;uint8_t temperate;int16_t last_ecd;
} motor_measure_t;数据解析方法定义
#define get_motor_measure(ptr, data)                                    \{                                                                   \(ptr)->last_ecd = (ptr)->ecd;                                   \(ptr)->ecd = (uint16_t)((data)[0] << 8 | (data)[1]);            \(ptr)->speed_rpm = (uint16_t)((data)[2] << 8 | (data)[3]);      \(ptr)->given_current = (uint16_t)((data)[4] << 8 | (data)[5]);  \(ptr)->temperate = (data)[6];                                   \}static motor_measure_t motor_chassis[7];  //实例化一个结构体数据,数组中的每一个结构体存放一个对应电机的相关数据,因为整台车上有7个电机因此数组大小为7void HAL_CAN_RxFifo0MsgPendingCallback(CAN_HandleTypeDef *hcan)
{CAN_RxHeaderTypeDef rx_header;uint8_t rx_data[8];HAL_CAN_GetRxMessage(hcan, CAN_RX_FIFO0, &rx_header, rx_data);switch (rx_header.StdId){case CAN_3508_M1_ID:case CAN_3508_M2_ID:case CAN_3508_M3_ID:case CAN_3508_M4_ID:{static uint8_t i = 0;//get motor idi = rx_header.StdId - CAN_3508_M1_ID;get_motor_measure(&motor_chassis[i], rx_data);break;}default:{break;}}
}

2.2.4 can发送配置

can发送有两点:

  1. 配置好报文结构体
  2. 通过函数HAL_CAN_AddTxMessage发送报文
2.2.4.1 发送数据结构体配置
CAN_TxHeaderTypeDef  chassis_tx_message;
chassis_tx_message.StdId = 0x200;              //指定标准标识符chassis_tx_message.IDE = CAN_ID_STD;          /*要传输的消息的标识符类型标准帧:CAN_ID_STD扩展帧:CAN_ID_EXT*/chassis_tx_message.RTR = CAN_RTR_DATA;           /*要传输的消息的帧类型数据帧:CAN_RTR_DATA远程帧:CAN_RTR_REMOTE */chassis_tx_message.DLC = 0x08;                  /*将要传输的帧的长度。取值范围为0 ~ 8  */
2.2.4.2 发送数据
发送数据报文结构

发送数据的结构不是自己随便的定义的,因为我们can发送的信息时让电调接收的,电调接收信息有一个数据帧的格式,我们需要根据这个帧的格式来发送我们的数据,才能控制我们想要控制的东西。

在这里找到C620电调的使用说明:M3508减速电机套装 (robomaster.com)

通过翻阅C620电调的使用说明我们可以看到我们可以通过控制标识符以及在data段中的对应位置填写数值来控制8个不同的电机的电流大小

发送函数
HAL_CAN_AddTxMessage(CAN_HandleTypeDef *hcan, CAN_TxHeaderTypeDef *pHeader, uint8_t aData[], uint32_t *pTxMailbox)1. CAN_HandleTypeDef *hcan: CAN的句柄指针,如果是can1就输入&hcan1, can2 就输入 &hcan2
2. CAN_TxHeaderTypeDef *pHeader:待发送的CAN数据帧信息的结构体指针。包含了CAN的ID,格式等重要信息。
3. uint8_t aData[] : 装载了待发送的数据的数组名称
4. uint32_t *pTxMailbox: 用于存储CAN发送所使用的邮箱号

​ 这个发送邮箱一般没用

2.2.4.3 发送数据总结与示例
2.2.4.3.1 总结

相较于接收数据,发送数据更加的直接一些。我们只需要关注,怎么发出去,把什么发出去这两个问题即可。

怎么发出去? 用函数HAL_CAN_AddTxMessage发出去。

发出去什么?发出去我们组织好的数据。

何谓组织好的数据?首先报文结构要组织好,然后报文内容要组织好。

报文的结构如何组织?stm32给我们规定了结构体 CAN_TxHeaderTypeDef,我们按照结构体的结构配置即可,其中最主要的一个内容是StdId,这一项决定了我们要把数据发给谁。

内容是什么?我们发送数据的主要内容就是给电机传达转速,也就是电流大小,而电流大小要放在DATA中的对应位置,这样电调才能够准确的解析并执行。

2.2.4.3.2示例
static CAN_TxHeaderTypeDef  chassis_tx_message;
static uint8_t              chassis_can_send_data[8];
int16_t motor1,motor2,motor3,motor4;
uint32_t send_mail_box; //发送邮箱一般没什么用 随便是个什么值motor1=4000;
motor2=4000;
motor3=4000;
motor4=4000;
chassis_can_send_data[0] = motor1 >> 8;
chassis_can_send_data[1] = motor1;
chassis_can_send_data[2] = motor2 >> 8;
chassis_can_send_data[3] = motor2;
chassis_can_send_data[4] = motor3 >> 8;
chassis_can_send_data[5] = motor3;
chassis_can_send_data[6] = motor4 >> 8;
chassis_can_send_data[7] = motor4;
/* USER CODE END 2 *
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{/* USER CODE END WHILE */HAL_CAN_AddTxMessage(&hcan1, &chassis_tx_message, chassis_can_send_data, &send_mail_box);HAL_Delay(2);/* USER CODE BEGIN 3 */}/* USER CODE END 3 */

RoboMaster电机驱动相关推荐

  1. 《Arduino开发实战指南:机器人卷》一3.3 直流电机驱动电路原理

    本节书摘来华章计算机<Arduino开发实战指南:机器人卷>一书中的第3章 ,第3.3节,黄文恺 伍冯洁 陈 虹 编著更多章节内容可以访问云栖社区"华章计算机"公众号查 ...

  2. 电机驱动板测试:是否可以输出150kHz高频信号?

    ▌01 双路电机驱动电路 1.双路电机驱动 这款电机驱动电路是由龙邱公司提供,用于 2021春季学期-创新设计与实践-高级下 用于驱动车模车模平台上的小型直流电机.模块上的型号为: MOS桥: 型号: ...

  3. autosar架构详细介绍_【技术】基于AUTOSAR的电机驱动系统分析

    来源 | 前瞻情报部 作者 | 汽车软件 进圈 | "动力总成测试群",关注本公众号后,添加文末主编微信,备注"进圈" 前言 纯电动汽车和混合动力汽车是新能源汽 ...

  4. l293d电机驱动原理_一文搞懂步进电机特性、原理及驱动器设计

    1.步进电机的概念 步进电机是将电脉冲信号,转变为角位移或线位移的开环控制电机,又称为脉冲电机.在非超载的情况下,电机的转速.停止的位置只取决于脉冲信号的频率和脉冲数,而不受负载变化的影响.当步进驱动 ...

  5. 基于机器学习的捡球机器人设计与实现(探索)第4篇——电机驱动板选择(2019-03-02)

    2019-03-02 by 崔斐然 转眼已经过去一个月了,小车进展微乎其微,最近车架材料什么的的都到了,从亚博智能店里买了车架和电机驱动,以前也不知道这个驱动板怎么用,到手了才发现用起来超级简单, 驱 ...

  6. H桥电机驱动原理与应用

    本文的内容是要告诉大家什么是H桥以及它如何是工作的. H桥电机驱动原理与应用 原著:吉姆布朗 1998年4月 整理上传:鲍勃乔丹 2002年9月 翻译:韦文潮 2007年12月 我们首先来看马达是如何 ...

  7. 电机驱动TB6612FNG全网断货,可替代方案来了,文末送模块!

    正巧,这几天准备设计一款小型mini的小车车,准备选用TB6612作为电机驱动. TB6612FNG是一款便宜且性能较好的一款电机驱动,单个IC可以用来驱动2个直流减速电机,电机电压在6~15V之间, ...

  8. ir2104s的自举电容_电赛必备,IR2104S半桥驱动MOS管电机驱动板(PCB工程文件+磁悬浮代码)...

    IR2104S半桥驱动MOS管电机驱动板设计心得: (1)驱动电路方案为经典的半桥驱动IR2104S加N沟道MOS管IR7843,MOSEFT内部有续流二极管,听说是寄生的(不知对不对),所以外加了肖 ...

  9. robomaster裁判系统服务器,2018裁判系统调试组网完全攻略

    1.jpg (52.6 KB, 下载次数: 3) 2018-4-15 21:49 上传 接下来是几个比较容易弄混淆的点: 主服务器程序将会同时监听机器上所有的 IP 地址,所以请保证机器上已经设置了 ...

  10. a4988 脉宽要求_基于STM32的微型步进电机驱动控制器设计

    基于STM32的微型步进电机驱动控制器设计 摘 要: 设计了一种微型步进电机驱动控制器,通过上位机界面修改步进电机转速.旋转角度.细分系数.该设计以STM32F103T8U6作为主控制器,以A4988 ...

最新文章

  1. RMI远程方法调用讲解教程
  2. 自制php操作mysql工具类(DB.class.php)
  3. IT界程序员几大恶习能立即让你变穷,你有吗?
  4. Python 'takes exactly 1 argument (2 given)' Python error
  5. JavaScript设计的漂亮的玫瑰花
  6. LiveVideoStackCon讲师热身分享 ( 三 ) —— Facebook的工具文化与多媒体QoE
  7. UVA11525 Permutation 逆康托展开
  8. 详解 Solidity 事件Event
  9. java随机数函数生成指定区间的,意外的惊喜
  10. the port is already in use
  11. kali虚拟机分辨率设置
  12. 如何将影像地图转换为国家2000坐标系
  13. 移动安全-Frida hook安卓So层函数实战
  14. 计算机绘图的实验报告怎么写,计算机绘图—autocad2011实验报告
  15. world标题是大写数字,题注要阿拉伯数字,交叉引用不会出错
  16. DailyTask-changeLog学习手册
  17. Day_8/08(List集合和Set集合)
  18. Sqlserver CPU使用率超高占到100% 使用跟踪查看问题sql语句
  19. 在谷歌Chrome上用VLC低延迟(300毫秒)播放播放海康大华RTSP
  20. 图文详解 HDFS 的工作机制及其原理

热门文章

  1. 《DOOM启示录》读书感
  2. 20135210——信息安全系统设计基础第一周学习总结
  3. Linux中chmod命令修改权限详解
  4. 无需重装软件,解决不满足升级要求问题,Windows10成功升级Windows11方案——以戴尔XPS15 9550 i7-6700HQ CPU为例
  5. delphi 消息列表中文说明
  6. windows如何在局域网下共享文件(传输文件、修改文件)
  7. 天锐绿盾移动终端支持 Android、IOS 移动客户端
  8. 16款私藏多年的PC端效率小软件推荐
  9. c语言ic卡读写软件,IC卡读写工具|ACR122U写卡软件下载 v3.7 免费版_最火软件站
  10. WeCode在线少儿编程|为什么我们选择代码编程