Advertisement
Guest User

Untitled

a guest
Nov 22nd, 2014
199
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.67 KB | None | 0 0
  1. -- Resolution of simulation
  2. local NUM_POINTS = ScrW()/2
  3. -- Width of simulation
  4. local WIDTH = ScrW()
  5. -- Spring constant for forces applied by adjacent points
  6. local SPRING_CONSTANT = 0.04
  7. -- Sprint constant for force applied to baseline
  8. local SPRING_CONSTANT_BASELINE = 0.001
  9. -- Vertical draw offset of simulation
  10. local Y_OFFSET = ScrH()-256
  11. -- Damping to apply to speed changes
  12. local DAMPING = 0.959
  13. -- Number of iterations of point-influences-point to do on wave per step
  14. -- (this makes the waves animate faster)
  15. local ITERATIONS = 3
  16.  
  17. -- Make points to go on the wave
  18. function makeWavePoints(numPoints)
  19. local t = {}
  20. for n = 1,numPoints do
  21. -- This represents a point on the wave
  22. local newPoint = {
  23. x = n / numPoints * WIDTH,
  24. y = Y_OFFSET,
  25. spd = {y=0}, -- speed with vertical component zero
  26. mass = 1
  27. }
  28. t[n] = newPoint
  29. end
  30. return t
  31. end
  32.  
  33. local wavePoints = makeWavePoints(NUM_POINTS)
  34.  
  35. -- A phase difference to apply to each sine
  36. local offset = 0
  37.  
  38. local NUM_BACKGROUND_WAVES = 3
  39. local BACKGROUND_WAVE_MAX_HEIGHT = 16
  40. local BACKGROUND_WAVE_COMPRESSION = 1/10
  41. -- Amounts by which a particular sine is offset
  42. local sineOffsets = {}
  43. -- Amounts by which a particular sine is amplified
  44. local sineAmplitudes = {}
  45. -- Amounts by which a particular sine is stretched
  46. local sineStretches = {}
  47. -- Amounts by which a particular sine's offset is multiplied
  48. local offsetStretches = {}
  49. -- Set each sine's values to a reasonable random value
  50. for i=1,NUM_BACKGROUND_WAVES do
  51. table.insert(sineOffsets, -1 + 2*math.random())
  52. table.insert(sineAmplitudes, math.random()*BACKGROUND_WAVE_MAX_HEIGHT)
  53. table.insert(sineStretches, math.random()*BACKGROUND_WAVE_COMPRESSION)
  54. table.insert(offsetStretches, math.random()*BACKGROUND_WAVE_COMPRESSION)
  55. end
  56. -- This function sums together the sines generated above,
  57. -- given an input value x
  58. function overlapSines(x)
  59. local result = 0
  60. for i=1,NUM_BACKGROUND_WAVES do
  61. result = result
  62. + sineOffsets[i]
  63. + sineAmplitudes[i] * math.sin(
  64. x * sineStretches[i] + offset * offsetStretches[i])
  65. end
  66. return result
  67. end
  68.  
  69.  
  70.  
  71. -- Update the positions of each wave point
  72. function updateWavePoints(points)
  73. for i=1,ITERATIONS do
  74. for n,p in ipairs(points) do
  75. -- force to apply to this point
  76. local force = 0
  77.  
  78. -- forces caused by the point immediately to the left or the right
  79. local forceFromLeft, forceFromRight
  80.  
  81. if n == 1 then -- wrap to left-to-right
  82. local dy = points[# points].y - p.y
  83. forceFromLeft = SPRING_CONSTANT * dy
  84. else -- normally
  85. local dy = points[n-1].y - p.y
  86. forceFromLeft = SPRING_CONSTANT * dy
  87. end
  88. if n == # points then -- wrap to right-to-left
  89. local dy = points[1].y - p.y
  90. forceFromRight = SPRING_CONSTANT * dy
  91. else -- normally
  92. local dy = points[n+1].y - p.y
  93. forceFromRight = SPRING_CONSTANT * dy
  94. end
  95.  
  96. -- Also apply force toward the baseline
  97. local dy = Y_OFFSET - p.y
  98. forceToBaseline = SPRING_CONSTANT_BASELINE * dy
  99.  
  100. -- Sum up forces
  101. force = force + forceFromLeft
  102. force = force + forceFromRight
  103. force = force + forceToBaseline
  104.  
  105. -- Calculate acceleration
  106. local acceleration = force / p.mass
  107.  
  108. -- Apply acceleration (with damping)
  109. p.spd.y = DAMPING * p.spd.y + acceleration
  110.  
  111. -- Apply speed
  112. p.y = p.y + p.spd.y
  113. end
  114. end
  115. end
  116.  
  117. -- Callback when updating
  118.  
  119.  
  120.  
  121. hook.Add("HUDPaint","waves",function()
  122.  
  123. offset = offset + 1
  124.  
  125. -- On click: Pick nearest point to mouse position
  126. if input.IsMouseDown(MOUSE_LEFT) and input.IsKeyDown(KEY_C) then
  127. local mouseX, mouseY = gui.MouseX( ),gui.MouseY( )/10
  128. local closestPoint = nil
  129. local closestDistance = nil
  130. for _,p in ipairs(wavePoints) do
  131. local distance = math.abs(mouseX-p.x)
  132. if closestDistance == nil then
  133. closestPoint = p
  134. closestDistance = distance
  135. else
  136. if distance <= closestDistance then
  137. closestPoint = p
  138. closestDistance = distance
  139. end
  140. end
  141. end
  142.  
  143.  
  144. closestPoint.y = gui.MouseY( )
  145.  
  146. end
  147.  
  148. -- Update positions of points
  149. updateWavePoints(wavePoints)
  150. for n,p in ipairs(wavePoints) do
  151. -- Draw lines between circles
  152.  
  153. if n == 1 then
  154. else
  155. local leftPoint = wavePoints[n-1]
  156. surface.SetDrawColor(85,85,255,155)
  157. surface.DrawRect(leftPoint.x, leftPoint.y + overlapSines(leftPoint.x), 2, 1024+overlapSines(p.x))
  158. end
  159. end
  160. end)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement