GT2B和GR3E的功能和使用

本文介绍了GT2B遥控器的三通道功能及其输出PPM信号的特性,包括信号周期、脉宽变化范围及精度等,并详细解释了对码过程及信号丢失后的输出情况。


原文地址:http://nicekwell.net/blog/20161223/gt2bhe-gr3ede-gong-neng-he-shi-yong.html


特性

三通道:方向,电机,第三通道。
接收机输出的是PPM信号,PPM信号的详细介绍可参考PPM信号那一部分。

1、GT2B遥控器功能



控制面板相关设置的功能会在第4节“输出PPM信号特性”中结合输出信号说明。


在左边都写得很清楚,总共4排,每排3个脚,用表格列出来引脚就是:

悬空 VCC GND
BINO/CH3 VCC GND
CH2 VCC GND
CH1 VCC GND

所有通道的VCC相连,所有通道的GND相连。
VCC电压标准是5V。

3、对码

1、遥控器和接收机都断电。
2、接收机第三通(BINO)道插入对码线。所谓对码线的功能其实就是把PWM输出脚和地相连。
3、接收机任意通道接通电源。此时接收机灯闪烁,表示等待对码。
4、遥控器按住对码键(BINO)开机。对码成功的话接收机停止闪烁,遥控器的电量指示灯(G/F)闪烁。
5、重启遥控器。
此时接收机就可以用遥控器控制了,信号特性见下面。

4、输出PPM信号特性

PPM的详细文档跳转到:PPM信号介绍

周期

GR3E 三个通道的PPM信号周期都是16ms,频率大约是60Hz。

通道分配

通道 功能 信号特性
CH1 方向 1、脉宽中间值可以通过控制面板最上面的旋钮调节,默认中间值是1500us。2、脉宽变化方向可以通过控制面板左上角的开关设置。3、脉宽变化范围是1000us,也就是 中间值±500us的范围。
CH2 油门 1、脉宽中间值可以通过控制面板最上面的旋钮调节,默认中间值是1500us。2、脉宽变化方向可以通过控制面板左上角的开关设置。3、脉宽变化范围是1000us,也就是 中间值±500us的范围。
CH3 第三通道 这个通道的PPM脉宽不是连续可变的。遥控器启动时默认设置的脉宽是1000us,按第三通道键可在 1000us 和 2000us 间切换。

精度

通道1和通道2是连续变化,分辨率是20us。

通道 功能 时间精度 调节范围1000us,分成份数  
CH1 方向 20us 50 普通舵机500us~2500us对应角度180°,对应舵机角度分辨率:1.8°
CH2 油门 20us 50 占空比从 -100%到+100%,对应占空比分辨率:4%

关于遥控器的说明

1、接收机的信号是由遥控器实时刷新的,如果遥控器关闭的话,接收机信号立马停止。信号丢失后的信号特性是由接收机决定的,有些甚至可以自定义。
2、正如上面所说接收机信号是由遥控器实时刷新,第三通道在1ms和2ms间的状态也是由遥控器决定,接收机不会记忆。而事实上遥控器也不会记忆,重启遥控器后第三通道默认是1000us。

信号丢失后的输出

当遥控器关闭后,GR3E的信号特性如下:

CH1 一直低电平
CH2 脉宽1500us,周期16ms。相当于油门在中间位置。
CH3 一直低电平

5、其他说明

关于刹车功能(把电机的两根电源线短接,超再生刹车),不是遥控器和接收机来识别刹车操作的,遥控器和接收机的组合只是单纯地把方向和油门调制成PPM信号反映出来。
刹车功能是由电调完成的,电调识别PPM信号来分析是否需要刹车。



<think&gt;我们之前已经定义了GPSTIME结构体,现在需要初始化两个变量gt1gt2。根据结构体定义,我们可以使用多种方法初始化。 结构体定义如下: typedef struct tagTOW { long sn; double tos; } TOW,*PTOW; typedef struct tagGPSTIME { int wn; TOW tow; } GPSTIME, *PGPSTIME; 初始化目标:将gt1gt2初始化为一个合理的默认值,通常为零值或特定值。 方法: 1. 使用统一初始化(C++11及以上) 2. 使用构造函数(如果结构体内部定义了构造函数) 3. 逐个成员赋值 由于原结构体没有定义构造函数,我们可以选择使用统一初始化或逐个成员赋值。 注意:结构体内部有嵌套结构(TOW),所以需要同时初始化wntow(包括tow的sntos)。 以下给出几种初始化方法:</think&gt;### ✅ GPSTIME 结构体初始化指南 以下是初始化 `gt1` `gt2` 的完整方案,包含多种方法最佳实践: #### 1. 零值初始化(推荐) ```cpp // 使用统一初始化语法 GPSTIME gt1{}; GPSTIME gt2{}; // 验证初始化结果 std::cout << "gt1: wn=" << gt1.wn << ", sn=" << gt1.tow.sn << ", tos=" << gt1.tow.tos << std::endl; // 输出: gt1: wn=0, sn=0, tos=0 ``` #### 2. 带参数的初始化 ```cpp // 初始化到特定GPS时间 GPSTIME gt1 = {2157, {345600L, 0.0}}; // GPS周2157,周内秒345600 GPSTIME gt2 = {0, {0L, 0.0}}; // 零值 // 使用C++20指定成员初始化 GPSTIME gt3 { .wn = 2157, .tow = { .sn = 345600L, .tos = 0.0 } }; ``` #### 3. 构造函数初始化(扩展结构体定义) ```cpp // 修改结构体定义添加构造函数 typedef struct tagGPSTIME { int wn; TOW tow; // 默认构造函数 tagGPSTIME() : wn(0), tow{0, 0.0} {} // 带参数构造函数 tagGPSTIME(int w, long s, double t) : wn(w), tow{s, t} {} } GPSTIME, *PGPSTIME; // 使用构造函数初始化 GPSTIME gt1; // 默认: (0, 0, 0.0) GPSTIME gt2(2157, 345600L, 0.0); // 自定义值 ``` #### 4. 函数式初始化 ```cpp // 初始化函数 GPSTIME initGpsTime(int wn = 0, long sn = 0L, double tos = 0.0) { return {wn, {sn, tos}}; } // 使用初始化函数 GPSTIME gt1 = initGpsTime(); // (0, 0, 0.0) GPSTIME gt2 = initGpsTime(2157, 345600L, 0.0); ``` ### 🔍 初始化方法比较 | 方法 | 优点 | 缺点 | 适用场景 | |------|------|------|----------| | 零值初始化 `{}` | 简洁安全,避免未初始化问题 | 只能初始化为零值 | 默认初始化 | | 成员初始化 `{wn, {sn, tos}}` | 灵活指定值,兼容旧标准 | 需要按顺序指定所有成员 | 已知具体值 | | 构造函数 | 类型安全,可封装验证逻辑 | 需要修改结构体定义 | 复杂项目 | | 初始化函数 | 可添加额外逻辑,复用性强 | 需要额外函数定义 | 需要特殊处理 | ### ⚙ 完整时间处理示例 ```cpp #include <iostream&gt; #include <cmath&gt; #include <stdexcept&gt; // 时间结构体定义 typedef struct tagTOW { long sn; // 整秒部分 double tos; // 秒的小数部分 // 计算总秒数 double total_seconds() const { return static_cast<double&gt;(sn) + tos; } } TOW, *PTOW; typedef struct tagGPSTIME { int wn; // GPS周数 TOW tow; // 周内时间 // 默认构造函数 tagGPSTIME() : wn(0), tow{0, 0.0} {} // 带参数构造函数 tagGPSTIME(int w, long s, double t) : wn(w), tow{s, t} { validate(); } // 时间验证 void validate() const { const int MAX_WN = 9999; const long MAX_SN = 604799; // 最大周内秒数 if (wn < 0 || wn &gt; MAX_WN) throw std::out_of_range("Invalid GPS week number"); if (tow.sn < 0 || tow.sn &gt; MAX_SN) throw std::out_of_range("Invalid TOW seconds"); if (tow.tos < 0.0 || tow.tos &gt;= 1.0) throw std::out_of_range("Invalid fractional seconds"); } // 时间差计算 (秒) double operator-(const tagGPSTIME& other) const { const double SEC_PER_WEEK = 604800.0; double diff_weeks = (wn - other.wn) * SEC_PER_WEEK; double diff_tow = tow.total_seconds() - other.tow.total_seconds(); return diff_weeks + diff_tow; } } GPSTIME, *PGPSTIME; int main() { try { // 初始化示例 GPSTIME epoch{}; // GPS时间零点: 1980-01-06 00:00:00 GPSTIME current(2157, 345600L, 0.0); // 示例时间 // 计算时间差 double seconds_since_epoch = current - epoch; std::cout << "Seconds since GPS epoch: " << seconds_since_epoch << std::endl; // 错误初始化示例 GPSTIME invalid(10000, 700000L, 1.5); // 将抛出异常 } catch (const std::exception& e) { std::cerr << "Error: " << e.what() << std::endl; } return 0; } ``` ### ⚠ GPS时间处理注意事项 1. **时间范围验证**: ```cpp bool isValidGpsTime(const GPSTIME& gt) { const int MAX_WN = 9999; const long MAX_SN = 604799; // 604800 - 1 return (gt.wn &gt;= 0 && gt.wn <= MAX_WN) && (gt.tow.sn &gt;= 0 && gt.tow.sn <= MAX_SN) && (gt.tow.tos &gt;= 0.0 && gt.tow.tos < 1.0); } ``` 2. **时间转换函数**: ```cpp // GPS时间转UTC时间(考虑闰秒) GPSTIME gpsToUtc(const GPSTIME& gps_time, int leap_seconds) { double total_seconds = gps_time.wn * 604800.0 + gps_time.tow.sn + gps_time.tow.tos - leap_seconds; int new_wn = static_cast<int&gt;(total_seconds / 604800.0); double remainder = fmod(total_seconds, 604800.0); return { new_wn, static_cast<long&gt;(remainder), remainder - static_cast<long&gt;(remainder) }; } ``` 3. **时间比较操作**: ```cpp bool operator<(const GPSTIME& lhs, const GPSTIME& rhs) { if (lhs.wn != rhs.wn) return lhs.wn < rhs.wn; if (lhs.tow.sn != rhs.tow.sn) return lhs.tow.sn < rhs.tow.sn; return lhs.tow.tos < rhs.tow.tos; } ``` --- ###
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值