mob-sakai / ParticleEffectForUGUI

Render particle effect in UnityUI(uGUI). Maskable, sortable, and no extra Camera/RenderTexture/Canvas.
MIT License
4.2k stars 616 forks source link
component effects particle particle-system ugui ui unity unity3d

UIParticleIcon Particle Effect For UGUI (UI Particle)



PRs Welcome

<< 📝 Description | 📌 Key Features | 🎮 Demo | ⚙ Installation | 🚀 Usage | 🛠 Development Note | 🤝 Contributing >>

📝 Description

This package uses the new APIs MeshBake/MeshTrailBake (introduced in Unity 2018.2) to render particles through CanvasRenderer.
You can render, mask, and sort your ParticleSystems for UI without the need for an additional Camera, RenderTexture, or Canvas.



📌 Key Features



🎮 Demo



⚙ Installation

This package requires Unity 2018.3 or later.

Install via OpenUPM

Install via UPM (with Package Manager UI)

Install via UPM (Manually)

Install as Embedded Package

  1. Download a source code zip file from Releases and extract it.
  2. Place it in your project's Packages directory.
    • If you want to fix bugs or add features, install it as an embedded package.
    • To update the package, you need to re-download it and replace the contents.



🚀 Usage

Component: UIParticle

UIParticle controls the ParticleSystems that are attached to its own game objects and child game objects.

NOTE: Press the Refresh button to reconstruct the rendering order based on children ParticleSystem's sorting order and z-position.



Basic Usage

  1. Select GameObject/UI/ParticleSystem to create UIParticle with a ParticleSystem. particle
  2. Adjust the ParticleSystem as you like. particle1


Usage with Your Existing ParticleSystem Prefab

  1. Select GameObject/UI/ParticleSystem (Empty) to create UIParticle. empty
  2. Drag and drop your ParticleSystem prefab onto UIParticle. particle3


Usage with Mask or RectMask2D Component

If you want to mask particles, set a stencil-supported shader (such as UI/UIAdditive) to the material for ParticleSystem. If you use some custom shaders, see the How to Make a Custom Shader to Support Mask/RectMask2D Component section.



Usage with Script

// Instantiate ParticleSystem prefab with UIParticle on runtime.
var go = GameObject.Instantiate(prefab);
var uiParticle = go.AddComponent<UIParticle>();
uiParticle.scale = 100;

// Control by ParticleSystem.
particleSystem.Play();
particleSystem.Emit(10);

// Control by UIParticle.
uiParticle.Play();
uiParticle.Stop();



Component: UIParticleAttractor

UIParticleAttractor attracts particles generated by the specified ParticleSystem.



🛠 Development Note

Compares the Baking mesh approach with the conventional approach

Performance test results

Approach FPS on Editor FPS on iPhone6 FPS on Xperia XZ
Particle System 43 57 22
UIParticleSystem 4 3 0 (unmeasurable)
Sorting By Canvas 43 44 18
UIParticle 17 12 4
UIParticle with MeshSharing 44 45 30

🔍 FAQ: Why Are My UIParticles Not Displayed Correctly?

If ParticleSystem alone displays particles correctly but UIParticle does not, please check the following points:


Shader Limitation

The use of UI shaders is recommended.

Built-in shaders are not supported

UIParticle does not support all built-in shaders except for UI/Default.
If their use is detected, an error is displayed in the inspector.
Use UI shaders instead.

(Unity 2018 or 2019) UV.zw components will be discarded

UIParticleRenderer renders the particles based on UIVertex.
Therefore, only the xy components are available for each UV in the shader. (zw components will be discarded).
So unfortunately, UIParticles will not work well with some shaders.

(Unity 2018 or 2019) Custom vertex streams

When using custom vertex streams, you can fill zw components with "unnecessary" data.
Refer to this issue for more information.


Overheads

UIParticle has some overheads, and the batching depends on uGUI.
When improving performance, keep the following in mind:

How to Make a Custom Shader to Support Mask and RectMask2D Component

Shader tips ```ShaderLab Shader "Your/Custom/Shader" { Properties { // ... // #### required for Mask #### _StencilComp ("Stencil Comparison", Float) = 8 _Stencil ("Stencil ID", Float) = 0 _StencilOp ("Stencil Operation", Float) = 0 _StencilWriteMask ("Stencil Write Mask", Float) = 255 _StencilReadMask ("Stencil Read Mask", Float) = 255 _ColorMask ("Color Mask", Float) = 15 [Toggle(UNITY_UI_ALPHACLIP)] _UseUIAlphaClip ("Use Alpha Clip", Float) = 0 } SubShader { Tags { // ... } // #### required for Mask #### Stencil { Ref [_Stencil] Comp [_StencilComp] Pass [_StencilOp] ReadMask [_StencilReadMask] WriteMask [_StencilWriteMask] } ColorMask [_ColorMask] // ... Pass { // ... // #### required for RectMask2D #### #include "UnityUI.cginc" #pragma multi_compile __ UNITY_UI_CLIP_RECT float4 _ClipRect; // #### required for Mask #### #pragma multi_compile __ UNITY_UI_ALPHACLIP struct appdata_t { // ... }; struct v2f { // ... // #### required for RectMask2D #### float4 worldPosition : TEXCOORD1; }; v2f vert(appdata_t v) { v2f OUT; // ... // #### required for RectMask2D #### OUT.worldPosition = v.vertex; return OUT; } fixed4 frag(v2f IN) : SV_Target { // ... // #### required for RectMask2D #### #ifdef UNITY_UI_CLIP_RECT color.a *= UnityGet2DClipping(IN.worldPosition.xy, _ClipRect); #endif // #### required for Mask #### #ifdef UNITY_UI_ALPHACLIP clip (color.a - 0.001); #endif return color; } ENDCG } } } ```



🤝 Contributing

Issues

Issues are incredibly valuable to this project:

Pull Requests

Pull requests offer a fantastic way to contribute your ideas to this repository.
Please refer to CONTRIBUTING.md and develop branch for guidelines.

Support

This is an open-source project developed during my spare time.
If you appreciate it, consider supporting me.
Your support allows me to dedicate more time to development. 😊




License

Author

See Also