浏览代码

First step

David Catuhe 7 年之前
父节点
当前提交
4cd3da2899

+ 2 - 1
Tools/Gulp/config.json

@@ -1237,7 +1237,8 @@
         },
         "particleHelper": {
             "files": [
-                "../../src/Helpers/babylon.particleHelper.js"
+                "../../src/Particles/babylon.particleSystemSet.js",
+                "../../src/Particles/babylon.particleHelper.js"
             ],
             "dependUpon": [
                 "particles"

+ 0 - 25
assets/particles/systems/fire.json

@@ -1,25 +0,0 @@
-{
-  "type": "fire",
-  "emitterType": "box",
-  "capacity": 2000,
-  "textureFile": "flare.png",
-  "minEmitBox": { "x": -0.5, "y": 1, "z": -0.5 },
-  "maxEmitBox": { "x": 0.5, "y": 1, "z": 0.5 },
-  "color1": { "r": 1, "g": 0.5, "b": 0, "a": 1.0 },
-  "color2": { "r": 1, "g": 0.5, "b": 0, "a": 1.0 },
-  "colorDead": { "r": 0, "g": 0, "b": 0, "a": 0.0 },
-  "minSize": 0.3,
-  "maxSize": 1,
-  "minLifeTime": 0.2,
-  "maxLifeTime": 0.4,
-  "emitRate": 600,
-  "blendMode": 0,
-  "gravity": { "x": 0, "y": 0, "z": 0 },
-  "direction1": { "x": 0, "y": 4, "z": 0 },
-  "direction2": { "x": 0, "y": 4, "z": 0 },
-  "minAngularSpeed": 0,
-  "maxAngularSpeed": 3.141592653589793,
-  "minEmitPower": 1,
-  "maxEmitPower": 3,
-  "updateSpeed": 0.007
-}

+ 0 - 25
assets/particles/systems/smoke.json

@@ -1,25 +0,0 @@
-{
-  "type": "smoke",
-  "emitterType": "box",
-  "capacity": 1000,
-  "textureFile": "flare.png",
-  "minEmitBox": { "x": -0.5, "y": 1, "z": -0.5 },
-  "maxEmitBox": { "x": 0.5, "y": 1, "z": 0.5 },
-  "color1": { "r": 0.1, "g": 0.1, "b": 0.1, "a": 1.0 },
-  "color2": { "r": 0.1, "g": 0.1, "b": 0.1, "a": 1.0 },
-  "colorDead": { "r": 0, "g": 0, "b": 0, "a": 0.0 },
-  "minSize": 0.3,
-  "maxSize": 1,
-  "minLifeTime": 0.3,
-  "maxLifeTime": 1.5,
-  "emitRate": 350,
-  "blendMode": 0,
-  "gravity": { "x": 0, "y": 0, "z": 0 },
-  "direction1": { "x": -1.5, "y": 8, "z": -1.5 },
-  "direction2": { "x": 1.5, "y": 8, "z": 1.5 },
-  "minAngularSpeed": 0,
-  "maxAngularSpeed": 3.141592653589793,
-  "minEmitPower": 0.5,
-  "maxEmitPower": 1.5,
-  "updateSpeed": 0.005
-}

+ 324 - 0
assets/particles/systems/sun.json

@@ -0,0 +1,324 @@
+{
+  "systems": [
+    {
+      "name": "surfaceParticles",
+      "id": "surfaceParticles",
+      "capacity": 1600,
+      "renderingGroupId": 3,
+      "isBillboardBased": false,
+      "particleEmitterType": {
+        "type": "SphereParticleEmitter",
+        "radius": 1,
+        "directionRandomizer": 0
+      },
+      "textureName": "sun/T_SunSurface.png",
+      "animations": [],
+      "minAngularSpeed": -0.4,
+      "maxAngularSpeed": 0.4,
+      "minSize": 0.4,
+      "maxSize": 0.7,
+      "minScaleX": 1,
+      "maxScaleX": 1,
+      "minScaleY": 1,
+      "maxScaleY": 1,
+      "minEmitPower": 0,
+      "maxEmitPower": 0,
+      "minLifeTime": 8,
+      "maxLifeTime": 8,
+      "emitRate": 200,
+      "gravity": [
+        0,
+        0,
+        0
+      ],
+      "color1": [
+        1,
+        1,
+        1,
+        1
+      ],
+      "color2": [
+        1,
+        1,
+        1,
+        1
+      ],
+      "colorDead": [
+        0,
+        0,
+        0,
+        1
+      ],
+      "updateSpeed": 0.005,
+      "targetStopDuration": 0,
+      "blendMode": 2,
+      "preWarmCycles": 100,
+      "preWarmStepOffset": 10,
+      "minInitialRotation": -6.283185307179586,
+      "maxInitialRotation": 6.283185307179586,
+      "colorGradients": [
+        {
+          "gradient": 0,
+          "color1": [
+            0.8509,
+            0.4784,
+            0.1019,
+            0
+          ]
+        },
+        {
+          "gradient": 0.4,
+          "color1": [
+            0.6259,
+            0.3056,
+            0.0619,
+            0.5
+          ]
+        },
+        {
+          "gradient": 0.5,
+          "color1": [
+            0.6039,
+            0.2887,
+            0.0579,
+            0.5
+          ]
+        },
+        {
+          "gradient": 1,
+          "color1": [
+            0.3207,
+            0.0713,
+            0.0075,
+            0
+          ]
+        }
+      ],
+      "textureMask": [
+        1,
+        1,
+        1,
+        1
+      ],
+      "customShader": null,
+      "preventAutoStart": false,
+      "startSpriteCellID": 0,
+      "endSpriteCellID": 0,
+      "spriteCellLoop": true,
+      "spriteCellChangeSpeed": 0,
+      "spriteCellWidth": 0,
+      "spriteCellHeight": 0,
+      "isAnimationSheetEnabled": false
+    },
+    {
+      "name": "flareParticles",
+      "id": "flareParticles",
+      "capacity": 20,
+      "renderingGroupId": 2,
+      "particleEmitterType": {
+        "type": "SphereParticleEmitter",
+        "radius": 1,
+        "directionRandomizer": 0
+      },
+      "textureName": "sun/T_SunFlare.png",
+      "animations": [],
+      "minAngularSpeed": 0,
+      "maxAngularSpeed": 0,
+      "minSize": 1,
+      "maxSize": 1,
+      "minScaleX": 0.5,
+      "maxScaleX": 1,
+      "minScaleY": 0.5,
+      "maxScaleY": 1,
+      "minEmitPower": 0.001,
+      "maxEmitPower": 0.01,
+      "minLifeTime": 10,
+      "maxLifeTime": 10,
+      "emitRate": 1,
+      "gravity": [
+        0,
+        0,
+        0
+      ],
+      "color1": [
+        1,
+        1,
+        1,
+        1
+      ],
+      "color2": [
+        1,
+        1,
+        1,
+        1
+      ],
+      "colorDead": [
+        0,
+        0,
+        0,
+        1
+      ],
+      "updateSpeed": 0.01,
+      "targetStopDuration": 0,
+      "blendMode": 2,
+      "preWarmCycles": 100,
+      "preWarmStepOffset": 10,
+      "minInitialRotation": -6.283185307179586,
+      "maxInitialRotation": 6.283185307179586,
+      "colorGradients": [
+        {
+          "gradient": 0,
+          "color1": [
+            1,
+            0.9612,
+            0.5141,
+            0
+          ]
+        },
+        {
+          "gradient": 0.25,
+          "color1": [
+            0.9058,
+            0.7152,
+            0.3825,
+            1
+          ]
+        },
+        {
+          "gradient": 1,
+          "color1": [
+            0.632,
+            0,
+            0,
+            0
+          ]
+        }
+      ],
+      "sizeGradients": [
+        {
+          "gradient": 0,
+          "factor": 0
+        },
+        {
+          "gradient": 1,
+          "factor": 1
+        }
+      ],
+      "textureMask": [
+        1,
+        1,
+        1,
+        1
+      ],
+      "customShader": null,
+      "preventAutoStart": false,
+      "startSpriteCellID": 0,
+      "endSpriteCellID": 0,
+      "spriteCellLoop": true,
+      "spriteCellChangeSpeed": 0,
+      "spriteCellWidth": 0,
+      "spriteCellHeight": 0,
+      "isAnimationSheetEnabled": false
+    },
+    {
+      "name": "glareParticles",
+      "id": "glareParticles",
+      "renderingGroupId": 1,
+      "capacity": 600,
+      "particleEmitterType": {
+        "type": "SphereParticleEmitter",
+        "radius": 1,
+        "directionRandomizer": 0
+      },
+      "textureName": "sun/T_Star.png",
+      "animations": [],
+      "minAngularSpeed": 0,
+      "maxAngularSpeed": 0,
+      "minSize": 1,
+      "maxSize": 1,
+      "minScaleX": 0.5,
+      "maxScaleX": 1.2,
+      "minScaleY": 0.75,
+      "maxScaleY": 3,
+      "minEmitPower": 0,
+      "maxEmitPower": 0,
+      "minLifeTime": 2,
+      "maxLifeTime": 2,
+      "emitRate": 300,
+      "gravity": [
+        0,
+        0,
+        0
+      ],
+      "color1": [
+        1,
+        1,
+        1,
+        1
+      ],
+      "color2": [
+        1,
+        1,
+        1,
+        1
+      ],
+      "colorDead": [
+        0,
+        0,
+        0,
+        1
+      ],
+      "updateSpeed": 0.01,
+      "targetStopDuration": 0,
+      "blendMode": 2,
+      "preWarmCycles": 100,
+      "preWarmStepOffset": 10,
+      "minInitialRotation": -6.283185307179586,
+      "maxInitialRotation": 6.283185307179586,
+      "colorGradients": [
+        {
+          "gradient": 0,
+          "color1": [
+            0.8509,
+            0.4784,
+            0.1019,
+            0
+          ]
+        },
+        {
+          "gradient": 0.5,
+          "color1": [
+            0.6039,
+            0.2887,
+            0.0579,
+            0.12
+          ]
+        },
+        {
+          "gradient": 1,
+          "color1": [
+            0.3207,
+            0.0713,
+            0.0075,
+            0
+          ]
+        }
+      ],
+      "textureMask": [
+        1,
+        1,
+        1,
+        1
+      ],
+      "customShader": null,
+      "preventAutoStart": false,
+      "startSpriteCellID": 0,
+      "endSpriteCellID": 0,
+      "spriteCellLoop": true,
+      "spriteCellChangeSpeed": 0,
+      "spriteCellWidth": 0,
+      "spriteCellHeight": 0,
+      "isAnimationSheetEnabled": false
+    }
+  ]
+}

二进制
assets/particles/textures/flare.png


二进制
assets/particles/textures/sun/T_Star.png


二进制
assets/particles/textures/sun/T_SunFlare.png


二进制
assets/particles/textures/sun/T_SunSurface.png


+ 0 - 349
src/Helpers/babylon.particleHelper.ts

@@ -1,349 +0,0 @@
-module BABYLON {
-    /**
-     * Represents all the data needed to create a ParticleSystem.
-     */
-    export interface IParticleSystemData {
-        /**
-         * ParticleSystem type
-         */
-        type: string;
-        /**
-         * Shape of the emitter
-         */
-        emitterType: string
-        /**
-         * Maximum number of particles in the system
-         */
-        capacity: number;
-        /**
-         * Link for the texture file
-         */
-        textureFile: string;
-        /**
-         * minEmitBox Vector3
-         */
-        minEmitBox?: { x: number, y: number, z: number };
-        /**
-         * maxEmitBox Vector3
-         */
-        maxEmitBox?: { x: number, y: number, z: number };
-        /**
-         * color1 Color4
-         */
-        color1: { r: number, g: number, b: number, a: number };
-        /**
-         * color2 Color4
-         */
-        color2: { r: number, g: number, b: number, a: number };
-        /**
-         * colorDead Color4
-         */
-        colorDead: { r: number, g: number, b: number, a: number };
-        /**
-         * Minimum size of each particle
-         */
-        minSize: number;
-        /**
-         * Maximum size of each particle
-         */
-        maxSize: number;
-        /**
-         * Minimum scale of each particle on X axis
-         */
-        minScaleX: number;
-        /**
-         * Maximum scale of each particle on X axis
-         */
-        maxScaleX: number;       
-        /**
-         * Minimum scale of each particle on Y axis
-         */
-        minScaleY: number;
-        /**
-         * Maximum scale of each particle on Y axis
-         */
-        maxScaleY: number;           
-        /**
-         * Minimum lifetime for each particle
-         */
-        minLifeTime: number;
-        /**
-         * Maximum lifetime for each particle
-         */
-        maxLifeTime: number;
-        /**
-         * Emit rate
-         */
-        emitRate: number;
-        /**
-         * Blend Mode
-         */
-        blendMode: number;
-        /**
-         * gravity Vector3
-         */
-        gravity: { x: number, y: number, z: number };
-        /**
-         * direction1 Vector3
-         */
-        direction1?: { x: number, y: number, z: number };
-        /**
-         * direction2 Vector3
-         */
-        direction2?: { x: number, y: number, z: number };
-        /**
-         * Minimum Angular Speed
-         */
-        minAngularSpeed: number;
-        /**
-         * Maximum Angular Speed
-         */
-        maxAngularSpeed: number;
-        /**
-         * Minimum Emit Power
-         */
-        minEmitPower: number;
-        /**
-         * Maximum Emit Power
-         */
-        maxEmitPower: number;
-        /**
-         * Update Speed
-         */
-        updateSpeed: number;
-        /**
-         * Radius
-         */
-        radius?: number;
-        /**
-         * Angle
-         */
-        angle?: number;
-    }
-    /**
-     * This class is made for on one-liner static method to help creating particle systems.
-     */
-    export class ParticleHelper {
-        /**
-         * Base Assets URL.
-         */
-        private static _baseAssetsUrl = "https://assets.babylonjs.com/particles";
-
-        /**
-         * This is the main static method (one-liner) of this helper to create different particle systems.
-         * @param type This string represents the type to the particle system to create
-         * @param emitter The object where the particle system will start to emit from.
-         * @param scene The scene where the particle system should live.
-         * @param gpu If the system will use gpu.
-         * @returns the ParticleSystem created.
-         */
-        public static CreateAsync(type: string, emitter: AbstractMesh,
-                                   scene: Nullable<Scene> = Engine.LastCreatedScene, gpu: boolean = false): Promise<ParticleSystem> {
-            
-            return new Promise((resolve, reject) => {
-                if (!scene) {
-                    scene = Engine.LastCreatedScene;;
-                }
-
-                if (gpu && !GPUParticleSystem.IsSupported) {
-                    return reject("Particle system with GPU is not supported.");
-                }
-
-                Tools.LoadFile(`${ParticleHelper._baseAssetsUrl}/systems/${type}.json`, (data, response) => {
-                    const newData = JSON.parse(data.toString()) as IParticleSystemData;
-                    return resolve(ParticleHelper.CreateSystem(newData, scene!, emitter));
-                }, undefined, undefined, undefined, (req, exception) => {
-                    return reject(`An error occured while the creation of your particle system. Check if your type '${type}' exists.`);
-                });
-
-            });
-        }
-
-        /**
-         * Static function used to create a new particle system from a IParticleSystemData
-         * @param data defines the source data
-         * @param scene defines the hosting scene
-         * @param emitter defines the particle emitter
-         * @returns a new ParticleSystem based on referenced data
-         */
-        public static CreateSystem(data: IParticleSystemData, scene: Scene, emitter: AbstractMesh): ParticleSystem {
-            // Create a particle system
-            const system = new ParticleSystem(data.type, data.capacity, scene);
-
-            // Where the particles come from
-            system.emitter = emitter; // the starting object, the emitter            
-
-            ParticleHelper.UpdateSystem(system, data, scene);
-
-            return system;
-        }
-
-        /**
-         * Static function used to update a particle system from a IParticleSystemData
-         * @param system defines the particle system to update
-         * @param data defines the source data
-         * @param scene defines the hosting scene
-         */
-        public static UpdateSystem(system: ParticleSystem, data: IParticleSystemData, scene: Scene): void {
-            // Texture of each particle
-            if (data.textureFile) {
-                system.particleTexture = new Texture(`${ParticleHelper._baseAssetsUrl}/textures/${data.textureFile}`, scene);
-            }
-
-            // Colors of all particles
-            system.color1 = new Color4(data.color1.r, data.color1.g, data.color1.b, data.color1.a);
-            system.color2 = new Color4(data.color2.r, data.color2.g, data.color2.b, data.color2.a);
-            system.colorDead = new Color4(data.colorDead.r, data.colorDead.g, data.colorDead.b, data.colorDead.a);
-
-            // Size of each particle (random between...
-            system.minSize = data.minSize;
-            system.maxSize = data.maxSize;
-
-            system.minScaleX = data.minScaleX;
-            system.maxScaleX = data.maxScaleX;    
-            
-            system.minScaleY = data.minScaleY;
-            system.maxScaleY = data.maxScaleY;              
-
-            // Life time of each particle (random between...
-            system.minLifeTime = data.minLifeTime;
-            system.maxLifeTime = data.maxLifeTime;
-
-            // Emission rate
-            system.emitRate = data.emitRate;
-
-            // Blend mode : BLENDMODE_ONEONE, or BLENDMODE_STANDARD
-            system.blendMode = data.blendMode;
-
-            // Set the gravity of all particles
-            system.gravity = new Vector3(data.gravity.x, data.gravity.y, data.gravity.z);
-
-            // Angular speed, in radians
-            system.minAngularSpeed = data.minAngularSpeed;
-            system.maxAngularSpeed = data.maxAngularSpeed;
-
-            // Speed
-            system.minEmitPower = data.minEmitPower;
-            system.maxEmitPower = data.maxEmitPower;
-            system.updateSpeed = data.updateSpeed;
-
-            switch (data.emitterType) {
-                case "box":
-
-                    if (!data.direction1 || !data.direction2) {
-                        throw new Error("Directions are missing in this particle system.");
-                    }
-
-                    if (!data.minEmitBox || !data.maxEmitBox) {
-                        throw new Error("EmitBox is missing in this particle system.");
-                    }
-
-                    system.createBoxEmitter(
-                        new Vector3(data.direction1.x, data.direction1.y, data.direction1.z),
-                        new Vector3(data.direction2.x, data.direction2.y, data.direction2.z),
-                        new Vector3(data.minEmitBox.x, data.minEmitBox.y, data.minEmitBox.z),
-                        new Vector3(data.maxEmitBox.x, data.maxEmitBox.y, data.maxEmitBox.z)
-                    );
-                    break;
-                case "sphere":
-                    system.createSphereEmitter(data.radius);
-                    break;
-                case "directed_sphere":
-                    
-                    if (!data.direction1 || !data.direction2) {
-                        throw new Error("Directions are missing in this particle system.");
-                    }
-                    
-                    system.createDirectedSphereEmitter(
-                        data.radius,
-                        new Vector3(data.direction1.x, data.direction1.y, data.direction1.z),
-                        new Vector3(data.direction2.x, data.direction2.y, data.direction2.z)
-                    );
-                    break;
-                case "cone":
-                    system.createConeEmitter(data.radius, data.angle);
-                    break;
-                default:
-                    break;
-            }
-        }
-
-        /**
-         * Static function used to export a particle system to a IParticleSystemData variable.
-         * Please note that texture file name is not exported and must be added manually
-         * @param system defines the particle system to export
-         */
-        public static ExportSystem(system: ParticleSystem): IParticleSystemData {
-            var outData: any = {};
-
-            // Colors of all particles
-            outData.color1 = { r: system.color1.r, g: system.color1.g, b: system.color1.b, a: system.color1.a };
-            outData.color2 = { r: system.color2.r, g: system.color2.g, b: system.color2.b, a: system.color2.a };
-            outData.colorDead = { r: system.colorDead.r, g: system.colorDead.g, b: system.colorDead.b, a: system.colorDead.a };
-
-            // Size of each particle (random between...
-            outData.minSize = system.minSize;
-            outData.maxSize = system.maxSize;
-
-            outData.minScaleX = system.minScaleX;
-            outData.maxScaleX = system.maxScaleX;     
-            
-            outData.minScaleY = system.minScaleY;
-            outData.maxScaleY = system.maxScaleY;             
-
-            // Life time of each particle (random between...
-            outData.minLifeTime = system.minLifeTime;
-            outData.maxLifeTime = system.maxLifeTime;
-
-            // Emission rate
-            outData.emitRate = system.emitRate;
-
-            // Blend mode : BLENDMODE_ONEONE, or BLENDMODE_STANDARD
-            outData.blendMode = system.blendMode;
-
-            // Set the gravity of all particles
-            outData.gravity = {x: system.gravity.x, y: system.gravity.y, z: system.gravity.z};
-
-            // Angular speed, in radians
-            outData.minAngularSpeed = system.minAngularSpeed;
-            outData.maxAngularSpeed = system.maxAngularSpeed;
-
-            // Speed
-            outData.minEmitPower = system.minEmitPower;
-            outData.maxEmitPower = system.maxEmitPower;
-            outData.updateSpeed = system.updateSpeed;
-
-            
-            switch (system.particleEmitterType.getClassName()) {
-                case "BoxEmitter":
-                    outData.emitterType = "box";
-                    outData.direction1 = {x: system.direction1.x, y: system.direction1.y, z: system.direction1.z };
-                    outData.direction2 = {x: system.direction2.x, y: system.direction2.y, z: system.direction2.z };
-                    outData.minEmitBox = {x: system.minEmitBox.x, y: system.minEmitBox.y, z: system.minEmitBox.z };
-                    outData.maxEmitBox = {x: system.maxEmitBox.x, y: system.maxEmitBox.y, z: system.maxEmitBox.z };
-                    break;
-                case "SphereParticleEmitter":
-                    outData.emitterType = "sphere";
-                    outData.radius = (system.particleEmitterType as SphereParticleEmitter).radius;
-                    break;
-                case "SphereDirectedParticleEmitter":
-                    outData.emitterType = "directed_sphere";
-                    var sphereDirectedParticleEmitter = system.particleEmitterType as SphereDirectedParticleEmitter;
-                    outData.radius = sphereDirectedParticleEmitter.radius;
-                    outData.direction1 = {x: sphereDirectedParticleEmitter.direction1.x, y: sphereDirectedParticleEmitter.direction1.y, z: sphereDirectedParticleEmitter.direction1.z };
-                    outData.direction2 = {x: sphereDirectedParticleEmitter.direction2.x, y: sphereDirectedParticleEmitter.direction2.y, z: sphereDirectedParticleEmitter.direction2.z };                
-                    break;
-                case "ConeEmitter":
-                    outData.emitterType = "cone";
-                    outData.radius = (system.particleEmitterType as ConeParticleEmitter).radius;
-                    outData.angle = (system.particleEmitterType as ConeParticleEmitter).angle;
-                    break;
-                default:
-                    break;
-            }
-
-            return outData;
-        }
-    }
-
-}

+ 1 - 1
src/Particles/EmitterTypes/babylon.coneParticleEmitter.ts

@@ -133,7 +133,7 @@ module BABYLON {
         }     
         
         /**
-         * Returns the string "BoxEmitter"
+         * Returns the string "ConeEmitter"
          * @returns a string containing the class name
          */
         public getClassName(): string {

+ 5 - 1
src/Particles/babylon.IParticleSystem.ts

@@ -22,6 +22,10 @@ module BABYLON {
          */
         emitter: Nullable<AbstractMesh | Vector3>;
         /**
+         * Gets or sets a boolean indicating if the particles must be rendered as billboard or aligned with the direction
+         */
+        isBillboardBased: boolean;        
+        /**
          * The rendering group used by the Particle system to chose when to render.
          */
         renderingGroupId: number;
@@ -46,7 +50,7 @@ module BABYLON {
         particleTexture: Nullable<Texture>;   
         
         /**
-         * Blend mode use to render the particle, it can be either ParticleSystem.BLENDMODE_ONEONE or ParticleSystem.BLENDMODE_STANDARD.
+         * Blend mode use to render the particle, it can be either ParticleSystem.BLENDMODE_ONEONE, ParticleSystem.BLENDMODE_STANDARD or ParticleSystem.BLENDMODE_ADD.
          */
         blendMode: number;   
         

+ 55 - 0
src/Particles/babylon.particleHelper.ts

@@ -0,0 +1,55 @@
+module BABYLON {
+    /**
+     * This class is made for on one-liner static method to help creating particle system set.
+     */
+    export class ParticleHelper {
+        /**
+         * Gets or sets base Assets URL
+         */
+        public static BaseAssetsUrl = "https://assets.babylonjs.com/particles";
+
+        /**
+         * This is the main static method (one-liner) of this helper to create different particle systems
+         * @param type This string represents the type to the particle system to create
+         * @param scene The scene where the particle system should live
+         * @param gpu If the system will use gpu
+         * @returns the ParticleSystemSet created
+         */
+        public static CreateAsync(type: string, scene: Nullable<Scene> = Engine.LastCreatedScene, gpu: boolean = false): Promise<ParticleSystemSet> {
+            
+            return new Promise((resolve, reject) => {
+                if (!scene) {
+                    scene = Engine.LastCreatedScene;;
+                }
+
+                if (gpu && !GPUParticleSystem.IsSupported) {
+                    return reject("Particle system with GPU is not supported.");
+                }
+
+                Tools.LoadFile(`${ParticleHelper.BaseAssetsUrl}/systems/${type}.json`, (data, response) => {
+                    const newData = JSON.parse(data.toString());
+                    return resolve(ParticleSystemSet.Parse(newData, scene!, gpu));
+                }, undefined, undefined, undefined, (req, exception) => {
+                    return reject(`An error occured while the creation of your particle system. Check if your type '${type}' exists.`);
+                });
+
+            });
+        }
+
+        /**
+         * Static function used to export a particle system to a IParticleSystemData variable.
+         * Please note that texture file name is not exported and must be added manually
+         * @param system defines the particle system to export
+         */
+        public static ExportSet(systems: ParticleSystem[]): ParticleSystemSet {
+            var set = new ParticleSystemSet();
+
+            for (var system of systems) {
+                set.systems.push(system);
+            }
+
+            return set;
+        }
+    }
+
+}

+ 16 - 2
src/Particles/babylon.particleSystem.ts

@@ -1416,6 +1416,8 @@
             Animation.AppendSerializedAnimations(particleSystem, serializationObject);
 
             // Particle system
+            serializationObject.renderingGroupId = particleSystem.renderingGroupId;
+            serializationObject.isBillboardBased = particleSystem.isBillboardBased;
             serializationObject.minAngularSpeed = particleSystem.minAngularSpeed;
             serializationObject.maxAngularSpeed = particleSystem.maxAngularSpeed;
             serializationObject.minSize = particleSystem.minSize;
@@ -1480,12 +1482,24 @@
             }
 
             // Emitter
-            if (parsedParticleSystem.emitterId) {
+            if (parsedParticleSystem.emitterId === undefined) {
+                particleSystem.emitter = Vector3.Zero();
+            }
+             else if (parsedParticleSystem.emitterId) {
                 particleSystem.emitter = scene.getLastMeshByID(parsedParticleSystem.emitterId);
             } else {
                 particleSystem.emitter = Vector3.FromArray(parsedParticleSystem.emitter);
             }
 
+            // Misc.
+            if (parsedParticleSystem.renderingGroupId !== undefined) {
+                particleSystem.renderingGroupId = parsedParticleSystem.renderingGroupId;
+            }
+
+            if (parsedParticleSystem.isBillboardBased !== undefined) {
+                particleSystem.isBillboardBased = parsedParticleSystem.isBillboardBased;
+            }
+
             // Animations
             if (parsedParticleSystem.animations) {
                 for (var animationIndex = 0; animationIndex < parsedParticleSystem.animations.length; animationIndex++) {
@@ -1551,7 +1565,7 @@
             let emitterType: IParticleEmitterType;
             if (parsedParticleSystem.particleEmitterType) {
                 switch (parsedParticleSystem.particleEmitterType.type) {
-                    case "SphereEmitter":
+                    case "SphereParticleEmitter":
                         emitterType = new SphereParticleEmitter();
                         break;
                     case "SphereDirectedParticleEmitter":

+ 56 - 0
src/Particles/babylon.particleSystemSet.ts

@@ -0,0 +1,56 @@
+module BABYLON {
+
+    /**
+     * Represents a set of particle systems working together to create a specific effect
+     */
+    export class ParticleSystemSet {
+        /**
+         * Gets or sets the particle system list
+         */
+        public systems = new Array<IParticleSystem>();
+
+        /**
+         * Starts all particle systems of the set
+         * @param emitter defines the mesh to use as emitter for the particle systems
+         */
+        public start(emitter: AbstractMesh): void {
+            for (var system of this.systems) {
+                system.emitter = emitter;
+                system.start();
+            }
+        }
+
+        /**
+         * Serialize the set into a JSON compatible object
+         * @returns a JSON compatible representation of the set
+         */
+        public serialize(): any {
+            var result:any = {};
+
+            result.systems = [];
+            for (var system of this.systems) {
+                result.systems.push(system.serialize());
+            }
+
+            return result;
+        }
+
+        /** 
+         * Parse a new ParticleSystemSet from a serialized source
+         * @param data defines a JSON compatible representation of the set
+         * @param scene defines the hosting scene
+         * @param gpu defines if we want GPU particles or CPU particles
+         * @returns a new ParticleSystemSet
+         */
+        public static Parse(data: any, scene: Scene, gpu = false): ParticleSystemSet {
+            var result = new ParticleSystemSet();
+            var rootUrl = ParticleHelper.BaseAssetsUrl + "/textures/";
+
+            for (var system of data.systems) {
+                result.systems.push(gpu ? GPUParticleSystem.Parse(system, scene, rootUrl) : ParticleSystem.Parse(system, scene, rootUrl));
+            }
+
+            return result;
+        }
+    }
+}