particle_candle_dirty_wick.lsl 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187
  1. // :SHOW:1
  2. // :CATEGORY:Light
  3. // :NAME:Rene Free Lighting System
  4. // :AUTHOR:Rene10957 Resident
  5. // :KEYWORDS: light,lamp,lighting light
  6. // :CREATED:2015-06-11 14:41:59
  7. // :EDITED:2016-03-30 20:29:28
  8. // :ID:1079
  9. // :NUM:1792
  10. // :REV:1.4
  11. // :WORLD:Opensim
  12. // :DESCRIPTION:
  13. // Particle Plugin "Candle flame dirty wick"
  14. // :CODE:
  15. // :LICENSE: CC0 (Public Domain)
  16. // Rene's Free Lighting System - Particle Plugin "Candle flame dirty wick"
  17. //
  18. // Author: Rene10957 Resident
  19. // Date: 21-03-2014
  20. ////////////////////////////////////////////////////////////////////////////////
  21. // HOW TO USE: drop this script into the same prim where the LIGHT is located //
  22. ////////////////////////////////////////////////////////////////////////////////
  23. string title = "Particle Plugin"; // title
  24. string name = "Candle flame dirty wick"; // name
  25. string version = "1.4"; // version
  26. integer silent = TRUE; // silent startup
  27. // Constants
  28. // Note: the official upper limit for particles is 4.0 meters but for more delicate particle effects
  29. // it can be useful to set maxScale to a lower value, in order to achieve more fine-grained control.
  30. integer particleChannel = -75901; // particle channel
  31. integer feedbackChannel = -57910; // feedback channel
  32. float minScale = 0.03125; // min. startScale or endScale
  33. float maxScale = 0.4; // max. startScale or endScale
  34. // Particle parameters
  35. // Note: startScale and endScale are not actual sizes, but more like aspect ratios.
  36. // The real size is determined by particleSize in the notecard, a percentage of maxScale.
  37. float age = 1.0; // particle lifetime
  38. float rate = 0.01; // particle burst rate
  39. integer count = 1; // particle count
  40. vector startScale = <0.05, 0.1, 0.0>; // particle start size
  41. vector endScale = <0.0, 0.0, 0.0>; // particle end size
  42. float minSpeed = 0.02; // particle min. burst speed
  43. float maxSpeed = 0.25; // particle max. burst speed
  44. float burstRadius = 0.0; // particle burst radius
  45. vector partAccel = <0.0, 0.0, 0.0>; // particle accelleration
  46. // Variables
  47. float particleSize; // particle size (percentage)
  48. float defParticleSize; // default particle size (percentage)
  49. float minParticleSize; // minimum particle size (percentage)
  50. // Functions
  51. startParticles(vector color, vector start, vector end, float min, float max, float radius, vector push, string txtr)
  52. {
  53. llParticleSystem([
  54. PSYS_SRC_PATTERN, PSYS_SRC_PATTERN_ANGLE_CONE,
  55. PSYS_PART_START_COLOR, color,
  56. PSYS_PART_END_COLOR, <1.0, 0.25, 0.0>,
  57. PSYS_PART_START_ALPHA, 0.5,
  58. PSYS_PART_END_ALPHA, 0.0,
  59. PSYS_PART_START_SCALE, start,
  60. PSYS_PART_END_SCALE, end,
  61. PSYS_PART_MAX_AGE, age,
  62. PSYS_SRC_BURST_RATE, rate,
  63. PSYS_SRC_BURST_PART_COUNT, count,
  64. PSYS_SRC_BURST_SPEED_MIN, min,
  65. PSYS_SRC_BURST_SPEED_MAX, max,
  66. PSYS_SRC_BURST_RADIUS, radius,
  67. PSYS_SRC_ACCEL, push,
  68. PSYS_SRC_OMEGA, <0.02, 0.02, 2.0>,
  69. PSYS_SRC_TEXTURE, txtr,
  70. PSYS_PART_FLAGS,
  71. 0 |
  72. PSYS_PART_EMISSIVE_MASK |
  73. PSYS_PART_FOLLOW_SRC_MASK |
  74. PSYS_PART_FOLLOW_VELOCITY_MASK |
  75. PSYS_PART_INTERP_COLOR_MASK |
  76. PSYS_PART_INTERP_SCALE_MASK ]);
  77. }
  78. /////////////////////////////////////////////////////////////////
  79. // From this point onwards, every particle script is identical //
  80. /////////////////////////////////////////////////////////////////
  81. // Particle size = largest dimension across both scale vectors
  82. float getParticleSize (vector start, vector end)
  83. {
  84. float max = 0.0;
  85. if (start.x > max) max = start.x;
  86. if (start.y > max) max = start.y;
  87. if (end.x > max) max = end.x;
  88. if (end.y > max) max = end.y;
  89. return max / (maxScale / 100.0);
  90. }
  91. // Particle size is too small if both start.x and end.x < minScale (0.03125), or...
  92. // both start.y and end.y < minScale (0.03125)
  93. float getMinSize (vector start, vector end, float size)
  94. {
  95. float maxX = 0.0;
  96. float maxY = 0.0;
  97. float minXY = 0.0;
  98. if (start.x < minScale && end.x < minScale) {
  99. if (start.x > end.x) maxX = start.x;
  100. else maxX = end.x;
  101. }
  102. if (start.y < minScale && end.y < minScale) {
  103. if (start.y > end.y) maxY = start.y;
  104. else maxY = end.y;
  105. }
  106. if (maxX == 0.0 && maxY == 0.0) return size;
  107. if (maxX == 0.0) minXY = maxY;
  108. else if (maxY == 0.0) minXY = maxX;
  109. else if (maxX < maxY) minXY = maxX;
  110. else minXY = maxY;
  111. return (float)llCeil((minScale / minXY) * size);
  112. }
  113. unpackMessage(string msg)
  114. {
  115. list msgList = llCSV2List(msg);
  116. integer on = (integer)llList2String(msgList, 0); // particles on/off
  117. vector color = (vector)llList2String(msgList, 1); // particle color
  118. float size = (float)llList2String(msgList, 2); // particle size (%) from notecard
  119. float inc = (float)llList2String(msgList, 3); // particle increase/decrease (%) from menu
  120. string texture = llList2String(msgList, 4); // particle texture from notecard
  121. if (inc == 999) particleSize = size; // reset particle size
  122. else particleSize += inc; // increase/decrease particle size
  123. if (particleSize < 1) particleSize = 1; // correct if size < 1%
  124. else if (particleSize > 100) particleSize = 100; // correct if size > 100%
  125. if (particleSize < minParticleSize) particleSize = minParticleSize; // correct undersized particles
  126. if (on) {
  127. vector start = startScale / defParticleSize * particleSize; // start scale
  128. vector end = endScale / defParticleSize * particleSize; // end scale
  129. float min = minSpeed / defParticleSize * particleSize; // equally resize min. burst speed
  130. float max = maxSpeed / defParticleSize * particleSize; // equally resize max. burst speed
  131. float radius = burstRadius / defParticleSize * particleSize; // equally resize burst radius
  132. vector push = partAccel / defParticleSize * particleSize; // equally resize accelleration
  133. startParticles(color, start, end, min, max, radius, push, texture);
  134. }
  135. else {
  136. llParticleSystem([]);
  137. }
  138. }
  139. default
  140. {
  141. state_entry()
  142. {
  143. defParticleSize = getParticleSize(startScale, endScale); // default particle size (percentage)
  144. vector start = startScale / defParticleSize; // start scale = 1%
  145. vector end = endScale / defParticleSize; // end scale = 1%
  146. minParticleSize = getMinSize(start, end, 1.0); // minimum particle size (percentage)
  147. if (!silent) llWhisper(0, title + " \"" + name + "\" " + version + " ready");
  148. llMessageLinked(LINK_THIS, feedbackChannel, "READY", ""); // request particle info from light script
  149. }
  150. on_rez(integer start_param)
  151. {
  152. llResetScript();
  153. }
  154. link_message(integer sender_number, integer number, string msg, key id)
  155. {
  156. if (number == particleChannel) unpackMessage(msg);
  157. }
  158. }