公司动态

UE5 Niagara粒子系统实战:从零打造动态烟雾特效

📅 2026/7/25 11:03:03
UE5 Niagara粒子系统实战:从零打造动态烟雾特效
1. 项目概述从零到一打造动态烟雾的艺术最近在几个项目里都需要用到那种既轻盈又富有细节的动态烟雾效果比如场景氛围的烘托或者角色技能的特效表现。市面上虽然有很多现成的资产包但要么风格不匹配要么性能开销太大最关键的是你很难完全控制它飘动的“感觉”。于是我决定自己动手用UE5的Niagara系统从头构建一个会飘的烟雾特效。这不仅仅是为了得到一个可用的特效更是一个深入理解Niagara粒子系统与材质系统如何协同工作的绝佳机会。整个过程下来我发现只要理清了几个核心逻辑即使是从未接触过Niagara的新手也能跟着步骤做出令人满意的效果。这篇教程我会把我从零开始“手搓”这个烟雾特效的完整思路、每一个关键步骤以及那些容易踩坑的材质节点细节毫无保留地分享出来。这个教程的目标是制作一个基础但完整的动态烟雾特效。它看起来像一团缓缓上升、自然扩散的轻烟内部有柔和的光影变化和动态的纹理流动。我们将完全在UE5的Niagara编辑器中搭建粒子逻辑并亲手编写一个专用的烟雾材质。无论你是刚接触UE特效的初学者还是想深化Niagara理解的中级开发者这篇保姆级的拆解都能让你获得可以直接复用到自己项目中的知识。我们会避开那些华而不实的复杂参数堆砌专注于构建一个清晰、高效且易于调整的烟雾系统核心。2. 核心思路与Niagara系统设计2.1 效果拆解与方案选型在动手之前我们必须先想清楚“一团会飘的烟雾”到底由哪些视觉元素构成。如果只是放一张烟雾贴图那它只是一张静止的图片。我们要的是“活”的烟雾。经过分析它至少包含以下几个动态维度形态运动整体上烟雾需要有一个缓慢的上升趋势同时向四周扩散。这决定了粒子的初始速度和生命周期内的受力如浮力、湍流。形态变化烟雾的边缘不能是僵硬的需要随着时间柔和地消散、变形。这通常通过控制粒子的大小Scale和透明度Alpha随时间变化来实现。内部细节烟雾不是均匀的一片内部需要有类似涡流、丝缕状的纹理细节在缓慢流动。这完全依赖于材质Material的表现力。光影交互烟雾是半透明的需要对场景光源有反应产生体积感和明暗变化。基于以上分析我们的技术方案就清晰了运动逻辑Niagara负责使用Niagara粒子系统来模拟烟雾的宏观运动行为。每个粒子代表一小团烟雾元素。我们通过模块控制它们的出生、死亡、初始位置、速度、大小和透明度。视觉细节材质负责为这些粒子赋予一个专用的材质。这个材质将使用纹理采样、噪声扰动和顶点偏移等技术来模拟烟雾内部的复杂纹理和动态变化。协同工作Niagara输出粒子的位置、生命周期等数据给材质材质利用这些数据驱动纹理动画和顶点变化最终在屏幕上渲染出动态烟雾。为什么不直接用现成的体积雾或粒子模板因为自定义的方案可控性极强。你可以精确调整飘动速度、扩散形状、消散快慢甚至让烟雾对游戏中的风场做出反应这是模板难以做到的。2.2 Niagara发射器基础搭建打开UE5创建一个新的Niagara系统Niagara System。我们首先需要一个发射器Emitter。创建发射器模板在创建Niagara系统时选择“Empty空白”模板。然后在其内部添加一个新的发射器选择“Sprite Renderer精灵渲染器”作为基础。精灵渲染器适合表现这种面片状的、带有透明通道的特效。重命名与组织将发射器命名为SMK_Emitter将系统命名为NS_Smoke。良好的命名习惯是管理复杂特效资产的第一步。发射器初始化设置Spawn Rate生成速率我们不希望烟雾是连续不断的浓烟而是偶尔飘起的一团。因此在“Emitter Update发射器更新”组中将默认的“Constant Spawn Rate恒定生成速率”模块删除。改为在“Emitter Spawn发射器生成”组中添加一个Burst爆发模块。设置Burst Count爆发数量为30-50代表一团烟雾由30-50个粒子组成Burst Time为0在系统开始时一次性爆发。粒子生命周期在“Particle Spawn粒子生成”组中找到Initialize Particle初始化粒子模块。将Lifetime生命周期设置为一个范围值例如(4.0, 6.0)。这意味着每个粒子的存活时间在4到6秒之间随机这样烟雾的消散会更自然避免所有粒子同时消失的机械感。注意在特效制作中“随机性”是打破机械感、营造自然效果的关键武器。生命周期、初始速度、大小等参数尽量使用Random Range随机范围而不是固定值。3. 粒子运动逻辑的精细调控粒子出生后我们需要赋予它们“生命”让它们按照烟雾的物理特性去运动。3.1 赋予初始动力与随机性在“Particle Spawn”组中我们需要添加并配置几个核心模块初始位置Add Location添加一个Add Location模块。我们不想所有粒子从一个点爆发那样会像一个球。设置Location为一个球体范围例如Sphere Location半径设为(10, 20)。这样粒子会从一个球形空间内出生形成初始的团状。初始速度Add Velocity这是控制烟雾“飘”起来的关键。添加Add Velocity模块。主要上升力在Velocity的Z轴向上设置一个基础值比如150.0。这是模拟热空气上升的浮力。水平扩散在X和Y轴设置一个较小的随机范围例如(-30.0, 30.0)。这模拟了烟雾向四周自然扩散的初速度。随机性勾选Apply Reframe下的Randomize给速度增加一个全方位的随机扰动让粒子的运动方向更散乱自然。初始大小Scale Sprite Size添加Scale Sprite Size模块。设置一个初始大小范围比如(8.0, 15.0)。较大的粒子在中心较小的在边缘可以初步塑造体积感。3.2 模拟持续受力与消散粒子出生后的持续运动在“Particle Update粒子更新”组中控制。持续受力Add Velocity在更新组中也添加一个Add Velocity模块。但这里的配置与生成时不同。我们设置一个非常小的、持续的Z轴正向速度如5.0模拟持续的浮力。同时在X、Y轴可以添加基于噪声的力。关键操作点击Velocity参数右边的下拉箭头选择Create New Niagara Parameter命名为TurbulenceForce湍流力。然后将这个参数的输入源设置为Dynamic Noise动态噪声。动态噪声会随时间变化从而给粒子施加一个不规则、缓慢变化的侧向力完美模拟空气湍流导致的烟雾蜿蜒效果。将噪声的Amplitude振幅设为20.0左右Frequency频率设为0.3频率越低变化越缓慢平滑。阻力Drag添加Drag阻力模块。阻力会随着时间逐渐降低粒子的速度让烟雾在上升扩散后慢慢趋于静止、消散。设置Drag Coefficient阻力系数为0.5左右。这个值需要根据你想要的效果微调值越大减速越快。大小与透明度随时间变化这是实现烟雾“消散”视觉的关键。大小变化添加Scale Sprite Size模块在更新组。将其模式改为Scale缩放并链接到一个Curve曲线。创建一个新的Vector2D类型曲线横轴是Normalized Age归一化年龄0到1纵轴是缩放值。曲线形状应该是从1.0开始在生命中期缓慢增长到1.2模拟膨胀在生命末期快速下降到0。这模拟了烟雾先略微膨胀后彻底消散的过程。透明度变化Alpha精灵渲染器的透明度通常在材质中控制但我们可以通过粒子颜色Color的Alpha通道来影响它。在“Particle Spawn”组添加Initialize Particle Color模块将初始Color的AlphaA值设为0.7。在“Particle Update”组添加Color模块将其模式设为Alpha Only仅Alpha并链接到一个曲线。曲线从0.7开始在生命中期保持平稳在最后1/4生命周期快速衰减到0。这样烟雾会先保持实体感再柔和地淡出。至此Niagara部分的运动逻辑骨架已经搭建完成。你可以点击“预览”窗口播放应该能看到一堆面片以团状形式出生然后缓慢上升、扩散、最终消失。虽然现在还很难看因为没有材质但运动行为已经初具雏形。4. 烟雾材质节点的深度解析这是让一团“白色面片”变成“烟雾”的魔法步骤。我们在材质编辑器中创建一个新的材质命名为M_Smoke。4.1 基础纹理与颜色混合烟雾的质感源于纹理的叠加与混合。纹理采样我们需要至少两张纹理。基础噪声纹理使用一张T_Ground_Grass_D这样的灰度噪声贴图或者更好的一张专门用于体积效果的T_Perlin_Noise_M。将其采样后连接到Base Color基础色的输入端。这提供了烟雾最基本的灰度信息和细节。细节噪声纹理再采样一张不同缩放Tiling和偏移Offset的噪声图或者另一张不同模式的噪声图如Voronoi噪声。这张图用于与基础噪声进行混合增加细节的复杂度和随机性避免纹理重复感。纹理动画静态的噪声不是烟雾。我们需要让纹理“流动”起来。创建两个Time时间节点分别乘以不同的速度常数如0.1和0.05得到两个不同的时间流。将这两个时间流分别与两个Texture Coordinate纹理坐标节点的UV输出相加然后再分别连接到两张噪声纹理的UVs输入口。这样两张纹理就会以不同的速度缓慢滑动模拟烟雾内部涡流的运动。技巧对其中一张纹理的UV在连接时间之前先通过一个Rotator旋转节点进行小幅旋转可以让流动方向更复杂。混合与遮罩将两张流动的噪声纹理通过LinearInterpolate线性插值Lerp节点混合。用第三张噪声纹理或第一张噪声的某个通道的采样值作为Alpha遮罩。这样混合效果在烟雾表面是不均匀的有些区域显示更多基础纹理有些区域显示更多细节纹理形成了丰富的内部变化。4.2 透明度Opacity与边缘柔化烟雾材质必须是Translucent半透明混合模式并在材质域中选择Surface表面。从纹理到透明度将混合后的主噪声纹理一个灰度值连接到Opacity不透明度引脚。白色值1代表完全不透明黑色值0代表完全透明。但直接连接会得到一块块生硬的云团。实现边缘柔化这是关键步骤。我们需要让烟雾从中心向边缘逐渐透明。方法一距离场柔边。在粒子渲染器中每个粒子是一个面片四边形。我们可以利用像素到面片中心的距离。使用PixelDepth像素深度和一些计算可以模拟但更简单的方法是使用粒子的Radius半径信息如果Niagara传递了的话。不过对于精灵粒子一个更通用的技巧是使用纹理本身的渐变。方法二纹理渐变柔边推荐。准备一张Radial Gradient径向渐变纹理中心白边缘黑。将其采样后与主噪声纹理通过Multiply乘法节点相乘再输出到Opacity。这样即使主噪声纹理在边缘是白色的乘以渐变纹理的黑色后边缘也会变透明。调整渐变纹理的Tiling可以控制柔边范围。方法三顶点颜色Alpha。我们在Niagara中已经设置了粒子颜色Alpha随生命周期变化。在材质中添加Particle Color粒子颜色节点将其Alpha通道输出与纹理计算后的透明度再进行一次Multiply。这样每个粒子整体的淡入淡出就由Niagara控制而粒子内部的纹理细节和边缘柔化由材质控制。这是Niagara与材质协同工作的经典范例。最终透明度计算一个典型的连接链是(NoiseTexture * RadialGradient) * ParticleColor.Alpha-Opacity。你可以通过Power幂节点来调整透明度曲线的对比度让烟雾中心更实边缘更虚。4.3 动态顶点偏移Vertex Offset增加体积感这是让烟雾从“纸片”变“棉花糖”的高级技巧。通过轻微移动网格的顶点可以模拟烟雾表面的凹凸起伏。启用顶点偏移在材质的细节面板中勾选Allow Vertex Offset允许顶点偏移。计算偏移方向我们希望顶点沿着面片的法线方向向外或向内偏移。添加Vertex Normal顶点法线节点。计算偏移强度使用另一张动态的、低频的噪声纹理。用Time驱动其UV采样后得到(0,1)的值。通过Subtract减法减去0.5将其映射到(-0.5, 0.5)的范围。应用偏移将处理后的噪声值标量与顶点法线向量通过Multiply节点相乘再乘以一个很小的强度系数如0.5到2.0。将这个结果连接到材质的World Position Offset世界位置偏移引脚。效果这样烟雾的表面就会产生非常缓慢的、起伏的蠕动感极大地增强了体积感和动态细节。注意强度一定要小否则会破坏烟雾的整体形状。4.4 光照与后期材质模型对于半透明烟雾默认光照模型可能不适用。光照模型选择在材质根节点将Shading Model着色模型改为Unlit无光照。因为复杂的半透明体积光照计算开销大且对于风格化的烟雾我们更依赖纹理和颜色本身来表现明暗。如果你需要简单的受光可以选择Default Lit默认光照但可能需要调整Opacity和Translucency Lighting半透光照相关设置。自发光Emissive Color可以将主噪声纹理连接一点点到Emissive Color自发光颜色上比如乘以0.1并给一个淡蓝或淡灰色。这能让烟雾在暗处也微微“亮”起来显得更通透不依赖于场景光源效果更稳定。后期处理影响确保材质的Disable Depth Test禁用深度测试未被勾选。通常保持默认让烟雾和场景物体有正确的前后遮挡关系。但如果希望烟雾总是显示在其他物体前面如某些UI特效可以启用它。材质完成后回到Niagara系统在粒子渲染器模块中将Material材质指定为我们刚创建的M_Smoke。现在播放你应该能看到一团具有丰富内部纹理、边缘柔和、缓缓飘动并最终消散的动态烟雾了。5. 性能优化与参数调节心得一个特效不仅要好看还得高效。特别是在移动平台或大量使用时。5.1 性能优化关键点粒子数量与生成率这是最大的性能影响因素。我们的“Burst”方式比“Constant”更省性能因为粒子只在开始时生成一次。务必通过调试找到视觉效果可接受的最低粒子数量。有时20个精心调整的粒子比50个杂乱无章的粒子效果更好。材质复杂度纹理采样次数我们的材质用了3-4次纹理采样。可以考虑将噪声和渐变纹理合并到一张纹理的RGB通道中在材质中通过通道分离来读取减少采样次数。指令数打开材质的Stats统计面板查看指令数。对于移动端尽量控制在100条指令以内。减少复杂的数学运算特别是Power、Sine等。禁用阴影在Niagara渲染器模块和材质中确保烟雾不投射也不接收阴影这能节省大量计算。LOD细节层次为Niagara系统设置LOD。在远距离可以自动减少粒子数量、降低生成率、甚至切换到更简单的材质。剔除Culling确保启用视锥体剔除Frustum Culling。对于屏幕空间很小的烟雾它不会被渲染。5.2 艺术化参数调节技巧所有参数都没有“标准值”需要根据项目风格调节。运动风格慵懒的烟增加Drag系数降低初始Velocity的Z值降低TurbulenceForce的Amplitude和Frequency。急促的蒸汽提高初始Velocity增大湍流力的Frequency缩短粒子Lifetime。视觉风格厚重的工业浓烟在材质中减少边缘渐变范围提高透明度对比度用Power节点使用对比度更强的噪声纹理。缥缈的仙境雾气增大边缘柔化范围降低透明度整体值使用低频、柔和的噪声并增加一点蓝色/青色色调到自发光。与环境互动这是一个进阶方向。你可以将Niagara系统与场景中的Wind Directional Source风向源关联让烟雾随风向飘动。或者通过Collision碰撞模块让烟雾在遇到障碍物时绕行。6. 常见问题与排查实录在实际操作中你几乎一定会遇到下面这些问题。6.1 问题速查表问题现象可能原因排查与解决步骤粒子完全不显示或显示为纯色方块1. 材质未正确赋值。2. 材质混合模式错误。3. 粒子相机距离过近/过远被裁剪。1. 检查Niagara渲染器模块中的Material引用。2. 确认材质Blend Mode为TranslucentShading Model非Surface。3. 检查粒子渲染器的Near/Far Culling设置。烟雾边缘有锯齿或硬边1. 透明度边缘过渡太生硬。2. 纹理分辨率过低。3. 缺少抗锯齿。1. 检查材质中用于边缘柔化的渐变纹理或计算确保过渡平滑。2. 确保使用的纹理分辨率足够至少512x512。3. 在项目设置中确保后处理抗锯齿如TAA已开启。烟雾看起来像一堆重叠的卡片很“平”1. 缺少顶点偏移Vertex Offset。2. 粒子大小过于均匀。3. 纹理缺乏深度感。1. 在材质中启用并调整World Position Offset。2. 在Niagara中为粒子初始大小和缩放曲线增加更多随机性。3. 在材质中使用多张噪声图混合并尝试连接到Normal或Roughness引脚增加表面细节感需改用光照模型。运动轨迹非常规则像机器喷出的1. 随机性参数不足。2. 湍流力噪声力未启用或强度太低。3. 所有粒子生命周期相同。1. 检查所有Velocity、Location、Size的初始化确保使用了Random Range。2. 确认Add Velocity (Update)模块中的力使用了Dynamic Noise并适当提高Amplitude。3. 将粒子Lifetime设置为一个范围值。性能开销大帧率下降明显1. 粒子数量过多。2. 材质过于复杂。3. 每帧更新计算量大。1. 逐步减少Burst Count直到找到画质与性能的平衡点。2. 打开材质Stats面板优化指令数合并纹理采样。3. 检查Niagara中是否有每帧进行复杂计算的模块如复杂的向量运算考虑移至Spawn阶段或简化。透明度排序错误烟雾片层穿插混乱半透明物体的渲染顺序问题。1. 尝试在材质中调整Translucency Sort Priority。2. 避免单个烟雾系统过大可拆分为多个不同深度的发射器。3. 这是一个引擎层面的经典难题对于复杂重叠的半透明可能需要特定的美术制作规范来规避。6.2 独家避坑技巧先黑白后彩色在调试材质时先将Base Color和Emissive都断开只连接Opacity。用一个黑白分明的视图来调试透明度通道是否正确这是解决“显示问题”最快的方法。善用Niagara的“预览”视图在Niagara编辑器里你可以选择单独预览某个模块的效果。例如隐藏颜色模块只看运动轨迹能帮你快速定位运动逻辑的问题。参数暴露成变量将材质中需要频繁调整的参数如噪声流动速度、边缘柔化强度、主色调以及Niagara中的关键参数如爆发数量、上升速度、湍流强度都提升为Parameter参数并创建对应的Material Instance材质实例和Niagara System User Parameters系统用户参数。这样美术或策划可以在实例上直接调整无需重新编译材质或系统迭代效率倍增。参考现实但不必拘泥观察真实的烟雾视频注意其整体运动节奏和形态变化。但在实现时不必追求物理绝对精确。游戏特效是“视觉的艺术”有时夸张的湍流、更慢的消散速度反而能带来更好的视觉传达和艺术美感。你的目标是做出“看起来对”的烟雾而不是“物理上对”的烟雾。