Advertisement
Guest User

SPINNERS2

a guest
Feb 11th, 2016
79
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. -- Usage:
  2. -- spinner = CreateSpinner(parent)
  3. -- spinner:SetTexture('texturePath')
  4. -- spinner:SetBlendMode('blendMode')
  5. -- spinner:SetVertexColor(r, g, b)
  6. -- spinner:SetClockwise(boolean) -- true to fill clockwise, false to fill counterclockwise
  7. -- spinner:SetReverse(boolean) -- true to empty the bar instead of filling it
  8. -- spinner:SetValue(percent) -- value between 0 and 1 to fill the bar to
  9.  
  10. -- Some math stuff
  11. local cos, sin, pi2, halfpi = math.cos, math.sin, math.rad(360), math.rad(90)
  12. local function Transform(tx, x, y, angle, aspect) -- Translates texture to x, y and rotates about its center
  13.     local c, s = cos(angle), sin(angle)
  14.     local y, oy = y / aspect, 0.5 / aspect
  15.     local ULx, ULy = 0.5 + (x - 0.5) * c - (y - oy) * s, (oy + (y - oy) * c + (x - 0.5) * s) * aspect
  16.     local LLx, LLy = 0.5 + (x - 0.5) * c - (y + oy) * s, (oy + (y + oy) * c + (x - 0.5) * s) * aspect
  17.     local URx, URy = 0.5 + (x + 0.5) * c - (y - oy) * s, (oy + (y - oy) * c + (x + 0.5) * s) * aspect
  18.     local LRx, LRy = 0.5 + (x + 0.5) * c - (y + oy) * s, (oy + (y + oy) * c + (x + 0.5) * s) * aspect
  19.     tx:SetTexCoord(ULx, ULy, LLx, LLy, URx, URy, LRx, LRy)
  20. end
  21.  
  22. -- Permanently pause our rotation animation after it starts playing
  23. local function OnPlayUpdate(self)
  24.     self:SetScript('OnUpdate', nil)
  25.     self:Pause()
  26. end
  27.  
  28. local function OnPlay(self)
  29.     self:SetScript('OnUpdate', OnPlayUpdate)
  30. end
  31.  
  32. local function SetValue(self, value)
  33.     -- Correct invalid ranges, preferably just don't feed it invalid numbers
  34.     if value > 1 then value = 1
  35.     elseif value < 0 then value = 0 end
  36.    
  37.     -- Reverse our normal behavior
  38.     if self._reverse then
  39.         value = 1 - value
  40.     end
  41.    
  42.     -- Determine which quadrant we're in
  43.     local q, quadrant = self._clockwise and (1 - value) or value -- 4 - floor(value / 0.25)
  44.     if q >= 0.75 then
  45.         quadrant = 1
  46.     elseif q >= 0.5 then
  47.         quadrant = 2
  48.     elseif q >= 0.25 then
  49.         quadrant = 3
  50.     else
  51.         quadrant = 4
  52.     end
  53.    
  54.     if self._quadrant ~= quadrant then
  55.         self._quadrant = quadrant
  56.         -- Show/hide necessary textures if we need to
  57.         if self._clockwise then
  58.             for i = 1, 4 do
  59.                 self._textures[i]:SetShown(i < quadrant)
  60.             end
  61.         else
  62.             for i = 1, 4 do
  63.                 self._textures[i]:SetShown(i > quadrant)
  64.             end
  65.         end
  66.         -- Move scrollframe/wedge to the proper quadrant
  67.         self._scrollframe:SetAllPoints(self._textures[quadrant])   
  68.     end
  69.  
  70.     -- Rotate the things
  71.     local rads = value * pi2
  72.     if not self._clockwise then rads = -rads + halfpi end
  73.     Transform(self._wedge, -0.5, -0.5, rads, self._aspect)
  74.     self._rotation:SetRadians(-rads)
  75. end
  76.  
  77. local function SetClockwise(self, clockwise)
  78.     self._clockwise = clockwise
  79. end
  80.  
  81. local function SetReverse(self, reverse)
  82.     self._reverse = reverse
  83. end
  84.  
  85. local function OnSizeChanged(self, width, height)
  86.     self._wedge:SetSize(width, height) -- it's important to keep this texture sized correctly
  87.     self._aspect = width / height -- required to calculate the texture coordinates
  88. end
  89.  
  90. -- Creates a function that calls a method on all textures at once
  91. local function CreateTextureFunction(func, self, ...)
  92.     return function(self, ...)
  93.         for i = 1, 4 do
  94.             local tx = self._textures[i]
  95.             tx[func](tx, ...)
  96.         end
  97.         self._wedge[func](self._wedge, ...)
  98.     end
  99. end
  100.  
  101. -- Pass calls to these functions on our frame to its textures
  102. local TextureFunctions = {
  103.     SetTexture = CreateTextureFunction('SetTexture'),
  104.     SetBlendMode = CreateTextureFunction('SetBlendMode'),
  105.     SetVertexColor = CreateTextureFunction('SetVertexColor'),
  106. }
  107.  
  108. local function CreateSpinner(parent)
  109.     local spinner = CreateFrame('Frame', nil, parent)
  110.    
  111.     -- ScrollFrame clips the actively animating portion of the spinner
  112.     local scrollframe = CreateFrame('ScrollFrame', nil, spinner)
  113.     scrollframe:SetPoint('BOTTOMLEFT', spinner, 'CENTER')
  114.     scrollframe:SetPoint('TOPRIGHT')
  115.     spinner._scrollframe = scrollframe
  116.    
  117.     local scrollchild = CreateFrame('frame', nil, scrollframe)
  118.     scrollframe:SetScrollChild(scrollchild)
  119.     scrollchild:SetAllPoints(scrollframe)
  120.    
  121.     -- Wedge thing
  122.     local wedge = scrollchild:CreateTexture()
  123.     wedge:SetPoint('BOTTOMRIGHT', spinner, 'CENTER')
  124.     spinner._wedge = wedge
  125.    
  126.     -- Top Right
  127.     local trTexture = spinner:CreateTexture()
  128.     trTexture:SetPoint('BOTTOMLEFT', spinner, 'CENTER')
  129.     trTexture:SetPoint('TOPRIGHT')
  130.     trTexture:SetTexCoord(0.5, 1, 0, 0.5)
  131.    
  132.     -- Bottom Right
  133.     local brTexture = spinner:CreateTexture()
  134.     brTexture:SetPoint('TOPLEFT', spinner, 'CENTER')
  135.     brTexture:SetPoint('BOTTOMRIGHT')
  136.     brTexture:SetTexCoord(0.5, 1, 0.5, 1)
  137.    
  138.     -- Bottom Left
  139.     local blTexture = spinner:CreateTexture()
  140.     blTexture:SetPoint('TOPRIGHT', spinner, 'CENTER')
  141.     blTexture:SetPoint('BOTTOMLEFT')
  142.     blTexture:SetTexCoord(0, 0.5, 0.5, 1)
  143.    
  144.     -- Top Left
  145.     local tlTexture = spinner:CreateTexture()
  146.     tlTexture:SetPoint('BOTTOMRIGHT', spinner, 'CENTER')
  147.     tlTexture:SetPoint('TOPLEFT')
  148.     tlTexture:SetTexCoord(0, 0.5, 0, 0.5)
  149.    
  150.     -- /4|1\ -- Clockwise texture arrangement
  151.     -- \3|2/ --
  152.  
  153.     spinner._textures = {trTexture, brTexture, blTexture, tlTexture}
  154.     spinner._quadrant = nil -- Current active quadrant
  155.     spinner._clockwise = true -- fill clockwise
  156.     spinner._reverse = false -- Treat the provided value as its inverse, eg. 75% will display as 25%
  157.     spinner._aspect = 1 -- aspect ratio, width / height of spinner frame
  158.     spinner:HookScript('OnSizeChanged', OnSizeChanged)
  159.    
  160.     for method, func in pairs(TextureFunctions) do
  161.         spinner[method] = func
  162.     end
  163.    
  164.     spinner.SetClockwise = SetClockwise
  165.     spinner.SetReverse = SetReverse
  166.     spinner.SetValue = SetValue
  167.    
  168.     local group = wedge:CreateAnimationGroup()
  169.     local rotation = group:CreateAnimation('Rotation')
  170.     spinner._rotation = rotation
  171.     rotation:SetDuration(0)
  172.     rotation:SetEndDelay(1)
  173.     rotation:SetOrigin('BOTTOMRIGHT', 0, 0)
  174.     group:SetScript('OnPlay', OnPlay)
  175.     group:Play()
  176.    
  177.     return spinner
  178. end
  179.  
  180. ----------
  181. -- Demo
  182. ----------
  183.  
  184. local spinner1 = CreateSpinner(UIParent)
  185. spinner1:SetPoint('BOTTOMRIGHT', UIParent, 'CENTER', -2, 2)
  186. spinner1:SetSize(64, 64)
  187. spinner1:SetTexture('interface/icons/inv_mushroom_11')
  188.  
  189. spinner1:SetClockwise(false)
  190. spinner1:SetReverse(false)
  191.  
  192. local spinner2 = CreateSpinner(UIParent)
  193. spinner2:SetPoint('BOTTOMLEFT', UIParent, 'CENTER', 2, 2)
  194. spinner2:SetSize(64, 64)
  195. spinner2:SetTexture('interface/icons/inv_mushroom_11')
  196.  
  197. spinner2:SetClockwise(true)
  198. spinner2:SetReverse(false)
  199.  
  200. local spinner3 = CreateSpinner(UIParent)
  201. spinner3:SetPoint('TOPRIGHT', UIParent, 'CENTER', -2, -2)
  202. spinner3:SetSize(64, 64)
  203. spinner3:SetTexture('interface/icons/inv_mushroom_11')
  204.  
  205. spinner3:SetClockwise(true)
  206. spinner3:SetReverse(true)
  207.  
  208. local spinner4 = CreateSpinner(UIParent)
  209. spinner4:SetPoint('TOPLEFT', UIParent, 'CENTER', 2, -2)
  210. spinner4:SetSize(64, 64)
  211. spinner4:SetTexture('interface/icons/inv_mushroom_11')
  212.  
  213. spinner4:SetClockwise(false)
  214. spinner4:SetReverse(true)
  215.  
  216. local f = CreateFrame('frame')
  217. local timespent = 0
  218. f:SetScript('OnUpdate', function(self, elapsed)
  219.     timespent = timespent + elapsed
  220.     if timespent >= 3 then
  221.         timespent = 0
  222.     end
  223.    
  224.     local value = timespent / 3
  225.     spinner1:SetValue(value)
  226.     spinner2:SetValue(value)
  227.     spinner3:SetValue(value)
  228.     spinner4:SetValue(value)
  229. end)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement