固定翼无人机着陆纵向控制与串级PID仿真解析
简介面向固定翼无人机纵向控制与着陆场景的研究者、飞控开发者和相关专业学生这份zip资源包围绕PID控制策略提供了着陆路径规划、高度跟踪与动力学建模的完整实现。包内共8个文件包含4个MATLAB脚本m文件用于纵向模型分析、着陆路径解算与高度跟踪建模以及4个Simulink模型文件mdl/slx各2个用于着陆控制与高度跟踪的系统级仿真调试整体压缩包仅70KB结构紧凑。资料按不同控制环节独立组织既可直接运行查看Simulink模型结构也能结合m文件理解从动力学矩阵到控制律设计的思路。已有2070人学习下载对于正在做固定翼着陆控制课程设计、仿真验证或算法改进的读者是一份便于快速上手和二次开发的实用参考资料。1. 固定翼着陆纵向控制这份资源解决的不只是调PID做固定翼飞控的人迟早会在着陆阶段翻车一次。平飞时姿态稳定、高度保持都没问题一到下滑道就出现高度掉得快、速度稳不住、拉平时机拿不准这几个老大难。我第一次跑固定翼着陆纵向控制仿真时看着高度曲线在下滑段末尾一路冲过头又看着拉平段升降舵反复满偏才发现着陆纵向控制跟巡航段完全是两套逻辑——它要同时管住高度、下沉率、空速和俯仰角四个量而它们之间是强耦合的。这份固定翼无人机着陆纵向控制.zip核心就是把着陆阶段的纵向控制律从零梳理出来包含下滑段定下滑角控制、拉平段指数拉平策略、高度与空速的串级PID结构以及一组能在仿真里直接跑通的初始参数。适合正在做固定翼飞控算法验证、参加竞赛或课程设计的人也适合被着陆段反复折磨的入门开发者。2. 着陆纵向控制律拆解下滑率恒定与拉平段的切换逻辑2.1 为什么着陆不能用平飞的定高PID直接改参数固定翼平飞时高度控制的目标是让高度误差收敛到零控制结构通常是高度外环叠加俯仰角内环。这个结构在巡航段好用是因为飞行状态变化慢空速基本稳定在配平点附近高度环输出的俯仰角指令在几度范围内小幅修正即可。但着陆时状态变化剧烈。飞行高度不断减小空速也要从巡航速度回落到着陆速度气动力的变化让俯仰通道的响应特性也跟着变。更重要的是着陆阶段对高度误差的控制要求不是“收敛”而是“精确跟踪一条随时间变化的下滑轨迹”——高度误差甚至是特意由负变正再变零的。直接把巡航段的高度PID拿过来用在小高度误差场景下会让飞机在下滑道上方反复震荡接地点落点分散。这份资源里用的是分段控制下滑段保持恒定的航迹角下滑角拉平段用指数拉平律把下沉率按高度比例衰减。两个阶段之间的切换条件通常用无线电高度阈值触发比如高度低于某个值常见仿真是30米到15米之间的某个阈值具体取决于飞机的下滑角与接地速度设计就切入拉平模式。这个切换本身是离散的但控制律内部的误差信号是连续的所以切换瞬间要保证升降舵指令不跳变这也是很多实现里没处理好导致着陆抖动的地方。2.2 下滑段控制律高度变化率与空速保护的嵌套下滑段的经典结构是俯仰角内环加高度变化率外环。高度变化率的反馈本质上替代了高度误差的比例项——因为在下滑段真正的控制目标是让下沉率稳定在一个给定值附近高度本身反而会沿着下滑道自然减小。常见做法是# 下滑段纵向控制高度变化率外环 俯仰角内环 # dt控制周期秒h_dot当前垂直速度米/秒h_dot_ref目标下沉率米/秒 # pitch当前俯仰角弧度pitch_cmd最终俯仰角指令弧度 h_dot_error h_dot_ref - h_dot pitch_cmd_hdot kp_hdot * h_dot_error ki_hdot * h_dot_error_integral # 空速保护当空速低于着陆参考速度时压低俯仰角限制防止继续抬头减速 if airspeed airspeed_land_ref: pitch_cmd min(pitch_cmd_hdot, pitch_cmd_trim - 0.05) else: pitch_cmd pitch_cmd_hdot pitch_cmd saturate(pitch_cmd, pitch_min_land, pitch_max_land)这组代码里的外环输出是俯仰角指令内环飞控再把它转成升降舵指令。kp_hdot 和 ki_hdot 决定了下滑道跟踪的响应速度与稳态误差。注意空速保护分支当空速低于着陆参考值时强制限制俯仰角不超过配平值减一个固定余量避免飞机为了追下滑道不断抬头、把速度越拖越低。这个保护逻辑在真实着陆中非常重要——很多着陆失速事故的直接诱因就是下滑段为了压高率而收油、抬头空速掉到失速速度以下。参数方面kp_hdot 一般取 0.1 到 0.5 之间单位俯仰角弧度 / 下沉率米每秒具体大小取决于飞机的静稳定裕度。外环带宽要留够余量避免和俯仰姿态内环带宽重叠。2.3 拉平段指数拉平律与接地下沉率控制拉平段的目标是在高度从拉平阈值降到零的过程中把下沉率从下滑段的恒定值平滑过渡到接地允许值常见仿真取 0.5 到 1.5 米/秒。指数拉平律的核心是让下沉率随着高度按比例衰减——高度越高允许的下沉率越大高度越低允许的下沉率越小。# 拉平段按高度比例生成目标下沉率指数拉平律 # h当前无线电高度米h_flare_start拉平起始高度米tau拉平时间常数秒 # h_dot_flare_ref当前拉平段目标下沉率米/秒 time_const max(tau, 0.5) # 防止除零过小的tau会让指令变化过快 h_dot_flare_ref -h / time_const if h_dot_flare_ref -0.3: # 限制最大下沉率避免指令过缓导致高度悬停 h_dot_flare_ref -0.3 # 拉平段的下沉率误差与下滑段复用同一个比例控制器 h_dot_error_flare h_dot_flare_ref - h_dot pitch_cmd_flare kp_hdot * h_dot_error_flare pitch_cmd_trim这里 tau 是关键参数。tau 越大拉平越平缓但接地距离会拉长tau 越小拉平越急下沉率衰减越快。实际调试时从 tau 拉平起始高度的 1.5 到 2 倍开始试比较稳妥。0.3 的限制是为了不让指令在接地瞬间变成零——若高度在接地前一直存在且下沉率指令始终随高度减小理论上飞机永远不会接地所以要设一个最小下沉率阈值保证它能落下去。2.4 纵向通道的飞控内环为什么必须有俯仰角速率阻尼着陆纵向控制的外环是高度变化率内环是俯仰角控制再往下才是舵面。很多人在仿真里只看高度变化率环忽略了俯仰角速率阻尼的作用。着陆阶段飞机速度低、动压小舵面效率下降俯仰响应变慢这时候如果内环阻尼不足俯仰角会出现小幅震荡体现在高度曲线上就是拉平段的波浪形下沉率。这份资源里的控制器结构里内环用的是俯仰角加俯仰角速率反馈# 俯仰角内环角度比例反馈 角速率阻尼 # pitch_rate俯仰角速率弧度/秒pitch_rate_cmd_ff前馈通常为0不需要 delta_e kp_pitch * (pitch_cmd - pitch) - kd_pitch * pitch_rate注意这里用的是减号角速率项是阻尼不是误差驱动的方向是抑制当前角速率。kd_pitch 的大小决定了阻尼比取值太小时俯仰震荡太大时舵面反应慢、拉平迟钝。仿真里从 kd_pitch 0.1 开始逐步加观察俯仰角速率曲线是否出现 2 到 3 Hz 以上的抖动一旦出现就把增益降回一半。3. 从资源包到可运行工程结构与代码落地路径3.1 资源包的目录结构与核心模块打开固定翼无人机着陆纵向控制.zip典型的工程结构包含模型定义、控制器、仿真主循环、参数配置四个部分。与此对应的文件组织方式通常是文件/目录作用关键内容aircraft_model/飞机本体模型气动系数、推力模型、重力与惯性项controller/纵向控制器下滑段、拉平段、内环、状态切换params/配置参数PID增益、拉平阈值、舵面限幅、时间常数simulation/仿真主循环欧拉积分或龙格库塔积分、数据记录analysis/结果分析高度曲线、下沉率曲线、舵面指令曲线绘制核心的纵向控制模块会是一个类输入当前飞行状态高度、垂直速度、空速、俯仰角、俯仰角速率输出升降舵指令。仿真主循环按固定步长调用这个控制器的 step 方法。3.2 把控制器从滑行逻辑到仿真验证串起来一个完整的着陆纵向控制仿真主循环逻辑通常这样组织# 仿真主循环从初始高度下滑至接地记录全程状态 # 初始条件高度 h0200m空速 v035m/s下滑角 gamma-5度 # 结束条件无线电高度小于 0.05m 或接地判定 for step in range(max_steps): # 1. 状态读取从飞行动力学模型获取当前状态 h state.altitude_radar # 无线电高度米 h_dot state.climb_rate # 下沉率米/秒 airspeed state.airspeed # 空速米/秒 pitch state.pitch_angle # 俯仰角弧度 pitch_rate state.pitch_rate # 俯仰角速率弧度/秒 # 2. 阶段判断下滑段 / 拉平段切换 if h h_flare_start: phase glide else: phase flare # 3. 控制指令计算 if phase glide: pitch_cmd glide_controller.update(h_dot, airspeed, h_dot_ref) else: pitch_cmd flare_controller.update(h, h_dot, pitch_cmd_trim) # 4. 内环与舵面 delta_e pitch_inner_loop.update(pitch_cmd, pitch, pitch_rate) # 5. 执行模型一步积分4阶龙格库塔常见 state aircraft_model.step(state, thrust, delta_e, dt) # 6. 记录日志 log.append(step, h, h_dot, airspeed, pitch, delta_e) # 7. 接地判定 if h 0.05 and h_dot -0.5: touch_down True break这里有个容易忽略的细节接地判定不能只看高度还要同时判断下沉率。有些仿真里高度先降到零但下沉率还在 -3 米/秒这不是接地是要坠毁——如果只用高度阈值程序会在飞机还没完成拉平的时候就提前截断。3.3 参数配置文件的组织方式参数集中在单独的配置文件里避免在控制器代码里散落魔法数字# 着陆纵向控制参数 # 下滑段参数 glide_h_dot_ref -3.2 # 目标下沉率米/秒对应约5度下滑角 kp_hdot 0.25 # 高度变化率比例增益 ki_hdot 0.02 # 高度变化率积分增益 integral_limit 0.1 # 积分限幅防止windup # 拉平段参数 h_flare_start 15.0 # 拉平起始高度米 tau_flare 8.0 # 拉平时间常数秒 h_dot_flare_min -0.3 # 最小下沉率指令米/秒 # 内环参数 kp_pitch 2.5 # 俯仰角比例增益 kd_pitch 0.15 # 俯仰角速率阻尼增益 pitch_limits [-0.35, 0.35] # 俯仰角指令限幅弧度约正负20度 # 舵面限幅 elevator_limit 0.4 # 升降舵最大偏度弧度约23度这些参数不是一个固定组合而是需要按飞机模型特性调整的。换一架飞机气动导数变了最优增益完全不同。把它单独列在配置文件里换机型时只需要改这个文件不用动控制器代码。4. 串级PID整定路径从镇定姿态环到高度变化率环4.1 整定顺序内环优先外环后调空速耦合放最后着陆纵向控制的PID参数整定顺序能省掉大量试错时间。常规做法是先锁死外环只调内环让俯仰阶跃响应达到临界阻尼状态然后固定内环调节高度变化率环的比例增益最后再引入积分项和空速保护。先把内环整定清楚的原因很简单外环是通过内环来改变飞机姿态的。如果内环本身有超调或相位滞后外环的增益越大越容易激发内环的模态耦合产生高频震荡。这就是为什么很多人调高度环时发现高度曲线还没发散俯仰角速率先抖起来了。# 内环阶跃测试给定一个固定的俯仰角指令阶跃观察俯仰响应 # pitch_cmd_step 0.15 rad约8.6度 # 记录俯仰角上升时间、超调量、稳态误差、是否有震荡合适的内环参数特征是阶跃响应的上升时间在 0.5 到 1.2 秒之间超调不超过 10%稳态误差在 0.5 度以内。如果上升时间太慢说明 kp_pitch 偏小或 kd_pitch 偏大按比例调整。这里注意一个问题——内环的阻尼不要调到完全临界阻尼留一点轻阻尼反而有利于外环做修正因为内环相位滞后小的同时高频增益也不至于太大。4.2 外环带宽与内环带宽的倍数关系串级PID的整定有个重要的频率隔离原则内环带宽要高出外环 5 到 10 倍。着陆场景下的物理含义是高度变化率环的修正动作要能被俯仰角内环快速跟随不能出现外环指令已经变化了内环还在追赶上一拍指令的情况。落地操作时先用阶跃响应测出内环带宽再据此设计外环增益# 用小幅阶跃测内环带宽的近似方法 # 对俯仰指令加 0.05 rad约2.9度的阶跃等到俯仰角稳定后 # 测量从起始到响应达到63%的时间 t63 # 近似带宽rad/s≈ 1 / t63 # 假设测得 t63 0.6s则内环带宽约为 1.67 rad/s # 外环带宽取内环的 1/8 ≈ 0.2 rad/s # 对应 kp_hdot 大概在 0.15 到 0.3 区间具体通过阶跃响应调注意这个方法是很粗糙的估算。飞行控制里外环对象不是纯积分环节高度变化率对俯仰角的响应还包含动力学延迟但做初始值设定足够用。4.3 空速耦合着陆速度区间的增益调度问题着陆过程中空速会从巡航速度降到着陆速度动压变化导致舵面效率不同。同样的升降舵偏角低速时的力矩比高速时小得多。如果整套PID增益是按巡航速度整定的到了着陆低速段响应会明显变迟钝。这份资源里的处理方式是做一个简单的增益调度按空速线性插值修正外环增益# 空速调度将巡航段增益线性折算到着陆段 # v_cruise巡航速度v_land着陆参考速度v_now当前空速 # kp_hdot_base巡航段的标称增益 if v_now v_cruise: kp_hdot_used kp_hdot_base elif v_now v_land: kp_hdot_used kp_hdot_base * 1.4 else: ratio (v_now - v_land) / (v_cruise - v_land) kp_hdot_used kp_hdot_base * (1.0 0.4 * (1.0 - ratio))这个调度逻辑简单但实用——低速时适当放大高度变化率环增益补偿舵面效率下降。这个放大系数 1.4 不是固定的取决于飞机的动压变化范围。仿真时可以用一个空速斜坡输入来测试观察不同空速点的高度跟踪误差是否一致。4.4 参数表格参考参数作用调大后果调小后果失稳征兆kp_pitch俯仰角跟踪比例增益响应快可能超调响应慢外环修正滞后俯仰角高频抖动kd_pitch俯仰角速率阻尼阻尼变大响应变钝阻尼不足震荡发散俯仰角速率出现2Hz以上波动kp_hdot下沉率比例增益下滑道跟踪紧实跟踪松弛误差偏大高度变化率出现锯齿状波动ki_hdot下沉率积分增益稳态误差消除更快稳态误差残留积分饱合导致超调tau_flare拉平时间常数拉平平缓接地距离长拉平急促下沉率衰减快接地下沉率超标失稳征兆判断这一列是仿真调试时最先要盯的信号。看到哪个征兆先去查对应增益不要盲目乱调。5. 着陆纵向控制的避坑记录常见翻车点与排查方法5.1 拉平段高度曲线先抬头再下砸现象仿真中飞机到拉平起始高度后高度先短暂上扬然后快速下坠接地下沉率达到 -2.5 米/秒以上远超允许值。原因拉平起始高度与下滑角不匹配。飞机在切入拉平时实际下沉率远大于指数拉平律给出的目标下沉率控制器为了让高度变化率追上目标短时间内输出较大的抬头指令俯仰角迅速增加导致升力增加高度短暂上升但此时空速偏低抬头后诱导阻力增大空速进一步下降升力反而减小飞机失去支撑力后快速下沉。数学本质是拉平初始高度太低或 tau 太小导致初始下沉率误差过大控制器不得不做大修正。解决把 h_flare_start 提高 20% 到 30%或者把 tau 增大。从能量角度理解——拉平段的本质是把下滑段的动能和势能转化为水平动能同时控制下沉率起始高度决定了可用能量有多少。我一般先保持 tau 不变逐步提高 h_flare_start 观察接地下沉率是否回落。5.2 高度变化率反馈噪声被微分放大现象仿真模型里加入传感器噪声后高度变化率信号出现高频抖动升降舵指令跟着高频摆动但高度曲线本身看起来还算平滑。原因高度变化率一般从气压高度差分获得差分运算本质上是高通滤波噪声会被放大。高度环增益越高这种高频抖动越容易被传递到舵面指令。这是仿真里最常见的“看着没问题一加噪声就翻车”的问题。解决对高度变化率反馈增加低通滤波# 一阶低通滤波截止频率取 2~5 Hz # h_dot_raw原始高度变化率测量值h_dot_filtered滤波后值 # alpha 取 0.2~0.5 之间dt0.01s 时 h_dot_filtered alpha * h_dot_raw (1 - alpha) * h_dot_filtered_prev注意滤波也会带来相位延迟外环增益要适当回调。一个实用的检查方法先无噪声跑通再加噪声和滤波对比两个工况的高度跟踪误差误差增量在 20% 以内说明滤波器参数可接受。5.3 拉平切换瞬间舵面跳变现象飞行高度穿过拉平阈值时升降舵指令瞬间变化超过 0.2 弧度飞机姿态阶跃变化高度曲线出现折点。原因下滑段和拉平段的控制律结构不同——下滑段用的是恒定 h_dot_ref拉平段用的是随高度线性变化的目标在切换边界上目标值不连续。如果下滑段的 h_dot_ref 与拉平时的 h_dot_flare_ref 在该高度上不一致控制器会瞬间看到一个大误差信号。解决在阶段切换时对误差信号做平滑过渡或者保证切换边界上两个控制律的目标值一致# 在切换点之前先计算出拉平段在 h_flare_start 处的目标下沉率 # 下滑段的 h_dot_ref 应该与它在同一高度上尽量接近 h_dot_flare_at_start -h_flare_start / tau_flare # 拉平初始目标下沉率 h_dot_ref_glide h_dot_flare_at_start # 下滑段目标下沉率直接对齐这是一种简便处理真实飞机里更多用过渡逻辑——在切换高度前后的一段高度带内对两个控制律的输出做线性混合。这种做法更平滑但实现复杂度高一些。资源包里用的是简化方案用它的初始参数仿真时一般不出现这个跳变但如果自己改动了 tau 或 h_flare_start就有可能出现。5.4 积分项饱和导致拉平段俯仰角指令持续超调现象拉平段的中段俯仰角指令持续维持在限幅值附近飞机抬头过猛空速快速衰减接地时速度低于失速速度。原因下滑段如果持续存在小的下沉率误差积分项会不断累积。切换到拉平段时误差方向翻转但积分项还没来得及回落外环输出被积分项顶到限幅。解决增加积分清空逻辑# 阶段切换时清空积分项避免下滑段累积的积分影响拉平段 if phase_changed: h_dot_error_integral 0.0另一个更通用的手段是把积分限幅调小让积分项在控制总量中的占比不超过 15% 到 20%。我一般在设计阶段就会把积分项的作用限制在消除稳态误差的范围内不给它跨越阶段干扰动态响应的能力。6. 验证着陆控制器的两种方法蒙特卡洛散布与舵面饱和审计仿真是调参的工具不是最终答案。固定翼着陆纵向控制器的验证我习惯跑两组实验一组是初始状态散布下的蒙特卡洛接地点分布另一组是舵面指令的饱和审计。蒙特卡洛的核心思想是让初始高度、初始空速、初始俯仰角都加上一个合理的扰动跑上百次着陆仿真统计接地点位置、接地下沉率、接地空速的分布。固定翼着陆的好控制器接地点散布应该在一个合理的范围内且不随初始状态扰动出现极端值# 蒙特卡洛接地点散布统计 # 扰动项初始高度 ±5m、初始空速 ±2m/s、初始俯仰角 ±0.05rad # 统计量接地点距离、接地下沉率、接地空速的均值与标准差 results [] for i in range(200): h0 200 random.uniform(-5, 5) v0 35 random.uniform(-2, 2) pitch0 0.1 random.uniform(-0.05, 0.05) landing run_landing_sim(h0, v0, pitch0) results.append(landing) distances [r.distance for r in results] sink_rates [r.sink_rate for r in results] ground_speeds [r.ground_speed for r in results] # 常见的可接受范围参考 # 接地距离标准差 15m下沉率均值 1.2m/s接地空速标准差 2m/s如果接地下沉率有超过 1.5 米/秒的样本且都对应同一种初始状态扰动方向说明控制器在某个边界状态下存在系统性缺陷。比如可能都是初始空速偏大的样本那就要检查拉平起始高度是否应该随初始空速做调整。舵面饱和审计是看控制器在全程飞行中是否有升降舵偏度长时间停在限幅值附近的情况。舵面饱和意味着控制器已经失去了线性调节能力进入开环状态。在着陆这种安全敏感阶段舵面饱和时间占比超过 5% 就说明增益匹配有问题# 饱和审计统计舵面在限幅附近停留的时间占比 # 限幅定义|delta_e| 0.9 * elevator_limit saturation_count 0 for entry in log: if abs(entry.delta_e) 0.9 * elevator_limit: saturation_count 1 saturation_ratio saturation_count / len(log) if saturation_ratio 0.05: print(warning: elevator saturation ratio , saturation_ratio)如果饱和集中在某个特定阶段——比如拉平后段——说明拉平段的增益或指令限幅需要重新匹配。拉平后段是舵面需求最大的时候飞机速度低、动压小为了维持足够的俯仰力矩需要大舵偏。这时饱和不一定是坏事但要看它的持续性和对称性——持续单向饱和说明配平力矩不足双向交替饱和说明增益太高。从那以后我每次调完一套着陆参数都会强制自己跑一遍蒙特卡洛和饱和审计这两项检查而不是盯着单次仿真曲线觉得“手感对了”就完事。单次曲线会骗人统计分布不会。希望帮到你。本文还有配套的精品资源点击获取