function AccelTween.__index(F,N)if AccelTween[N]then return AccelTween[N]elseif N=="\112"then local N,O=F:_getstate(os.clock())return N elseif N=="\118"then local N,O=F:_getstate(os.clock())return O elseif N=="\097"then return F._accel elseif N=="\116"then return F._y1 elseif N=="\114\116\105\109\101"then local N=os.clock()return N<F._t1 and F._t1-N or 0 else error(("\066\097\100 \105\110\100\101\120 \037\113"):format(tostring(N)))end end function AccelTween.__newindex(O,N,F)if N=="\112"then O:_setstate(F,nil,nil,nil)elseif N=="\118"then O:_setstate(nil,F,nil,nil)elseif N=="\097"then O:_setstate(nil,nil,F,nil)elseif N=="\116"then O:_setstate(nil,nil,nil,F)elseif N=="\112\116"then O:_setstate(F,0,nil,F)else error(("\066\097\100 \105\110\100\101\120 \037\113"):format(tostring(N)))end end function AccelTween._getstate(F,N)if N<(F._t0+F._t1)/2 then local O=N-F._t0 return F._y0+((O*O)/2)*F._a0,O*F._a0 elseif N<F._t1 then local O=N-F._t1 return F._y1+((O*O)/2)*F._a1,O*F._a1 else return F._y1,0 end end function AccelTween._setstate(W,N,F,O,l)local I=os.clock()local V,U=W:_getstate(I)V=N or V U=F or U W._accel=O or W._accel local R=l or W._y1 if W._accel*W._accel<1e-08 then W._t0,W._y0,W._a0=0,V,0 W._t1,W._y1,W._a1=math.huge,R,0 else local N=R<V local F=U<0 local O=V-(U*U)/(2*W._accel)<R local l=V+(U*U)/(2*W._accel)<R if N and(F and O)or not N and(F or not F and l)then W._a0=W._accel W._t1=I+(((2*U)*U+(4*W._accel)*(R-V))^.5-U)/W._accel else W._a0=-W._accel W._t1=I+(((2*U)*U-(4*W._accel)*(R-V))^.5+U)/W._accel end W._t0=I-U/W._a0 W._y0=V-(U*U)/(2*W._a0)W._y1=R W._a1=-W._a0 end end return AccelTween
--[=[
	Sets the current and target position, and sets the velocity to 0.
	@prop pt number
	@within AccelTween
]=]

function AccelTween:__index(index)
	if AccelTween[index] then
		return AccelTween[index]
	elseif index == "p" then
		local pos, _ = self:_getstate(os.clock())
		return pos
	elseif index == "v" then
		local _, vel = self:_getstate(os.clock())
		return vel
	elseif index == "a" then
		return self._accel
	elseif index == "t" then
		return self._y1
	elseif index == "rtime" then
		local time = os.clock()
		return time < self._t1 and self._t1 - time or 0
	else
		error(("Bad index %q"):format(tostring(index)))
	end
end

function AccelTween:__newindex(index, value)
	if index == "p" then
		self:_setstate(value, nil, nil, nil)
	elseif index == "v" then
		self:_setstate(nil, value, nil, nil)
	elseif index == "a" then
		self:_setstate(nil, nil, value, nil)
	elseif index == "t" then
		self:_setstate(nil, nil, nil, value)
	elseif index == "pt" then
		self:_setstate(value, 0, nil, value)
	else
		error(("Bad index %q"):format(tostring(index)))
	end
end

function AccelTween:_getstate(time)
	if time < (self._t0 + self._t1) / 2 then
		local t = time - self._t0
		return self._y0 + t * t / 2 * self._a0, t * self._a0
	elseif time < self._t1 then
		local t = time - self._t1
		return self._y1 + t * t / 2 * self._a1, t * self._a1
	else
		return self._y1, 0
	end
end

function AccelTween:_setstate(newpos, newvel, newaccel, newtarg)
	local time = os.clock()
	local pos, vel = self:_getstate(time)
	pos = newpos or pos
	vel = newvel or vel
	self._accel = newaccel or self._accel
	local targ = newtarg or self._y1

	if self._accel * self._accel < 1e-8 then
		self._t0, self._y0, self._a0 = 0, pos, 0
		self._t1, self._y1, self._a1 = math.huge, targ, 0
	else
		local conda = targ < pos
		local condb = vel < 0
		local condc = pos - vel * vel / (2 * self._accel) < targ
		local condd = pos + vel * vel / (2 * self._accel) < targ
		if conda and condb and condc or not conda and (condb or not condb and condd) then
			self._a0 = self._accel
			self._t1 = time + ((2 * vel * vel + 4 * self._accel * (targ - pos)) ^ 0.5 - vel) / self._accel
		else
			self._a0 = -self._accel
			self._t1 = time + ((2 * vel * vel - 4 * self._accel * (targ - pos)) ^ 0.5 + vel) / self._accel
		end
		self._t0 = time - vel / self._a0
		self._y0 = pos - vel * vel / (2 * self._a0)
		self._y1 = targ
		self._a1 = -self._a0
	end
end

return AccelTween
