babylon.customProceduralTexture.ts 6.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167
  1. module BABYLON {
  2. /**
  3. * Procedural texturing is a way to programmatically create a texture. There are 2 types of procedural textures: code-only, and code that references some classic 2D images, sometimes called 'refMaps' or 'sampler' images.
  4. * Custom Procedural textures are the easiest way to create your own procedural in your application.
  5. * @see http://doc.babylonjs.com/how_to/how_to_use_procedural_textures#creating-custom-procedural-textures
  6. */
  7. export class CustomProceduralTexture extends ProceduralTexture {
  8. private _animate: boolean = true;
  9. private _time: number = 0;
  10. private _config: any;
  11. private _texturePath: string;
  12. /**
  13. * Instantiates a new Custom Procedural Texture.
  14. * Procedural texturing is a way to programmatically create a texture. There are 2 types of procedural textures: code-only, and code that references some classic 2D images, sometimes called 'refMaps' or 'sampler' images.
  15. * Custom Procedural textures are the easiest way to create your own procedural in your application.
  16. * @see http://doc.babylonjs.com/how_to/how_to_use_procedural_textures#creating-custom-procedural-textures
  17. * @param name Define the name of the texture
  18. * @param texturePath Define the folder path containing all the cutom texture related files (config, shaders...)
  19. * @param size Define the size of the texture to create
  20. * @param scene Define the scene the texture belongs to
  21. * @param fallbackTexture Define a fallback texture in case there were issues to create the custom texture
  22. * @param generateMipMaps Define if the texture should creates mip maps or not
  23. */
  24. constructor(name: string, texturePath: string, size: number, scene: Scene, fallbackTexture?: Texture, generateMipMaps?: boolean) {
  25. super(name, size, null, scene, fallbackTexture, generateMipMaps);
  26. this._texturePath = texturePath;
  27. //Try to load json
  28. this._loadJson(texturePath);
  29. this.refreshRate = 1;
  30. }
  31. private _loadJson(jsonUrl: string): void {
  32. let noConfigFile = () => {
  33. Tools.Log("No config file found in " + jsonUrl + " trying to use ShadersStore or DOM element");
  34. try {
  35. this.setFragment(this._texturePath);
  36. }
  37. catch (ex) {
  38. Tools.Error("No json or ShaderStore or DOM element found for CustomProceduralTexture");
  39. }
  40. }
  41. var configFileUrl = jsonUrl + "/config.json";
  42. var xhr: XMLHttpRequest = new XMLHttpRequest();
  43. xhr.open("GET", configFileUrl, true);
  44. xhr.addEventListener("load", () => {
  45. if (xhr.status === 200 || Tools.ValidateXHRData(xhr, 1)) {
  46. try {
  47. this._config = JSON.parse(xhr.response);
  48. this.updateShaderUniforms();
  49. this.updateTextures();
  50. this.setFragment(this._texturePath + "/custom");
  51. this._animate = this._config.animate;
  52. this.refreshRate = this._config.refreshrate;
  53. }
  54. catch (ex) {
  55. noConfigFile();
  56. }
  57. }
  58. else {
  59. noConfigFile();
  60. }
  61. }, false);
  62. xhr.addEventListener("error", () => {
  63. noConfigFile();
  64. }, false);
  65. try {
  66. xhr.send();
  67. }
  68. catch (ex) {
  69. Tools.Error("CustomProceduralTexture: Error on XHR send request.");
  70. }
  71. }
  72. /**
  73. * Is the texture ready to be used ? (rendered at least once)
  74. * @returns true if ready, otherwise, false.
  75. */
  76. public isReady(): boolean {
  77. if (!super.isReady()) {
  78. return false;
  79. }
  80. for (var name in this._textures) {
  81. var texture = this._textures[name];
  82. if (!texture.isReady()) {
  83. return false;
  84. }
  85. }
  86. return true;
  87. }
  88. /**
  89. * Render the texture to its associated render target.
  90. * @param useCameraPostProcess Define if camera post process should be applied to the texture
  91. */
  92. public render(useCameraPostProcess?: boolean): void {
  93. let scene = this.getScene();
  94. if (this._animate && scene) {
  95. this._time += scene.getAnimationRatio() * 0.03;
  96. this.updateShaderUniforms();
  97. }
  98. super.render(useCameraPostProcess);
  99. }
  100. /**
  101. * Update the list of dependant textures samplers in the shader.
  102. */
  103. public updateTextures(): void {
  104. for (var i = 0; i < this._config.sampler2Ds.length; i++) {
  105. this.setTexture(this._config.sampler2Ds[i].sample2Dname, new Texture(this._texturePath + "/" + this._config.sampler2Ds[i].textureRelativeUrl, this.getScene()));
  106. }
  107. }
  108. /**
  109. * Update the uniform values of the procedural texture in the shader.
  110. */
  111. public updateShaderUniforms(): void {
  112. if (this._config) {
  113. for (var j = 0; j < this._config.uniforms.length; j++) {
  114. var uniform = this._config.uniforms[j];
  115. switch (uniform.type) {
  116. case "float":
  117. this.setFloat(uniform.name, uniform.value);
  118. break;
  119. case "color3":
  120. this.setColor3(uniform.name, new Color3(uniform.r, uniform.g, uniform.b));
  121. break;
  122. case "color4":
  123. this.setColor4(uniform.name, new Color4(uniform.r, uniform.g, uniform.b, uniform.a));
  124. break;
  125. case "vector2":
  126. this.setVector2(uniform.name, new Vector2(uniform.x, uniform.y));
  127. break;
  128. case "vector3":
  129. this.setVector3(uniform.name, new Vector3(uniform.x, uniform.y, uniform.z));
  130. break;
  131. }
  132. }
  133. }
  134. this.setFloat("time", this._time);
  135. }
  136. /**
  137. * Define if the texture animates or not.
  138. */
  139. public get animate(): boolean {
  140. return this._animate;
  141. }
  142. public set animate(value: boolean) {
  143. this._animate = value;
  144. }
  145. }
  146. }