lightInformationBlock.ts 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132
  1. import { NodeMaterialBlock } from '../../nodeMaterialBlock';
  2. import { NodeMaterialBlockConnectionPointTypes } from '../../nodeMaterialBlockConnectionPointTypes';
  3. import { NodeMaterialBuildState } from '../../nodeMaterialBuildState';
  4. import { NodeMaterialConnectionPoint } from '../../nodeMaterialBlockConnectionPoint';
  5. import { NodeMaterialBlockTargets } from '../../nodeMaterialBlockTargets';
  6. import { _TypeStore } from '../../../../Misc/typeStore';
  7. import { Nullable } from '../../../../types';
  8. import { Scene } from '../../../../scene';
  9. import { Effect } from '../../../effect';
  10. import { NodeMaterial } from '../../nodeMaterial';
  11. import { Mesh } from '../../../../Meshes/mesh';
  12. import { Light } from '../../../../Lights/light';
  13. import { PointLight } from '../../../../Lights/pointLight';
  14. /**
  15. * Block used to get data information from a light
  16. */
  17. export class LightInformationBlock extends NodeMaterialBlock {
  18. private _lightDataDefineName: string;
  19. private _lightColorDefineName: string;
  20. /**
  21. * Gets or sets the light associated with this block
  22. */
  23. public light: Nullable<Light>;
  24. /**
  25. * Creates a new LightInformationBlock
  26. * @param name defines the block name
  27. */
  28. public constructor(name: string) {
  29. super(name, NodeMaterialBlockTargets.Vertex);
  30. this.registerInput("worldPosition", NodeMaterialBlockConnectionPointTypes.Vector4, false, NodeMaterialBlockTargets.Vertex);
  31. this.registerOutput("direction", NodeMaterialBlockConnectionPointTypes.Vector3);
  32. this.registerOutput("color", NodeMaterialBlockConnectionPointTypes.Color3);
  33. }
  34. /**
  35. * Gets the current class name
  36. * @returns the class name
  37. */
  38. public getClassName() {
  39. return "LightInformationBlock";
  40. }
  41. /**
  42. * Gets the world position input component
  43. */
  44. public get worldPosition(): NodeMaterialConnectionPoint {
  45. return this._inputs[0];
  46. }
  47. /**
  48. * Gets the direction output component
  49. */
  50. public get direction(): NodeMaterialConnectionPoint {
  51. return this._outputs[0];
  52. }
  53. /**
  54. * Gets the direction output component
  55. */
  56. public get color(): NodeMaterialConnectionPoint {
  57. return this._outputs[1];
  58. }
  59. public bind(effect: Effect, nodeMaterial: NodeMaterial, mesh?: Mesh) {
  60. if (!mesh) {
  61. return;
  62. }
  63. if (!this.light || !this.light.isEnabled) {
  64. effect.setFloat3(this._lightDataDefineName, 0, 0, 0);
  65. effect.setFloat3(this._lightColorDefineName, 0, 0, 0);
  66. return;
  67. }
  68. this.light.transferToNodeMaterialEffect(effect, this._lightDataDefineName);
  69. effect.setColor3(this._lightColorDefineName, this.light.diffuse);
  70. }
  71. protected _buildBlock(state: NodeMaterialBuildState) {
  72. super._buildBlock(state);
  73. state.sharedData.bindableBlocks.push(this);
  74. let direction = this.direction;
  75. let color = this.color;
  76. if (!this.light) {
  77. state.compilationString += this._declareOutput(direction, state) + ` = vec3(0.);\r\n`;
  78. state.compilationString += this._declareOutput(color, state) + ` = vec3(0.);\r\n`;
  79. } else {
  80. this._lightDataDefineName = state._getFreeDefineName("lightData");
  81. state._emitUniformFromString(this._lightDataDefineName, "vec3");
  82. this._lightColorDefineName = state._getFreeDefineName("lightColor");
  83. state._emitUniformFromString(this._lightColorDefineName, "vec3");
  84. if (this.light instanceof PointLight) {
  85. state.compilationString += this._declareOutput(direction, state) + ` = normalize(${this._lightDataDefineName} - ${this.worldPosition.associatedVariableName}.xyz);\r\n`;
  86. } else {
  87. state.compilationString += this._declareOutput(direction, state) + ` = ${this._lightDataDefineName};\r\n`;
  88. }
  89. state.compilationString += this._declareOutput(color, state) + ` = ${this._lightColorDefineName};\r\n`;
  90. }
  91. return this;
  92. }
  93. public serialize(): any {
  94. let serializationObject = super.serialize();
  95. if (this.light) {
  96. serializationObject.lightId = this.light.id;
  97. }
  98. return serializationObject;
  99. }
  100. public _deserialize(serializationObject: any, scene: Scene, rootUrl: string) {
  101. super._deserialize(serializationObject, scene, rootUrl);
  102. if (serializationObject.lightId) {
  103. this.light = scene.getLightByID(serializationObject.lightId);
  104. }
  105. }
  106. }
  107. _TypeStore.RegisteredTypes["BABYLON.LightInformationBlock"] = LightInformationBlock;