@quenty/camera 14.20.3 → 14.20.4-canary.11a5dcf.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (42) hide show
  1. package/CHANGELOG.md +16 -0
  2. package/package.json +17 -17
  3. package/src/Client/CameraStack.lua +27 -20
  4. package/src/Client/CameraStackService.lua +53 -35
  5. package/src/Client/CameraState.lua +8 -8
  6. package/src/Client/CameraUtils.lua +1 -1
  7. package/src/Client/CameraUtils.story.lua +5 -4
  8. package/src/Client/Controls/CameraControls.lua +107 -60
  9. package/src/Client/Controls/CameraGamepadInputUtils.lua +36 -21
  10. package/src/Client/Controls/GamepadRotateModel.lua +22 -12
  11. package/src/Client/Effects/CameraEffectUtils.lua +10 -1
  12. package/src/Client/Effects/CustomCameraEffect.lua +21 -5
  13. package/src/Client/Effects/DefaultCamera.lua +50 -32
  14. package/src/Client/Effects/FadeBetween/FadeBetweenCamera.lua +7 -7
  15. package/src/Client/Effects/FadeBetween/FadeBetweenCamera2.lua +11 -11
  16. package/src/Client/Effects/FadeBetween/FadeBetweenCamera3.lua +57 -21
  17. package/src/Client/Effects/FadeBetween/FadeBetweenCamera4.lua +17 -9
  18. package/src/Client/Effects/FadingCamera.lua +21 -5
  19. package/src/Client/Effects/HeartbeatCamera.lua +22 -9
  20. package/src/Client/Effects/ImpulseCamera.lua +44 -28
  21. package/src/Client/Effects/ImpulseCamera.story.lua +6 -6
  22. package/src/Client/Effects/InverseFader.lua +22 -6
  23. package/src/Client/Effects/LagPointCamera.lua +27 -8
  24. package/src/Client/Effects/OverrideDefaultCameraToo.lua +26 -4
  25. package/src/Client/Effects/PointCamera.lua +22 -6
  26. package/src/Client/Effects/PushCamera.lua +35 -14
  27. package/src/Client/Effects/RotatedCamera.lua +23 -9
  28. package/src/Client/Effects/SmoothPositionCamera.lua +22 -10
  29. package/src/Client/Effects/SmoothRotatedCamera.lua +52 -24
  30. package/src/Client/Effects/SmoothZoomedCamera.lua +31 -12
  31. package/src/Client/Effects/SummedCamera.lua +38 -16
  32. package/src/Client/Effects/TrackCamera.lua +24 -11
  33. package/src/Client/Effects/XZPlaneLockCamera.lua +21 -8
  34. package/src/Client/Effects/ZoomedCamera.lua +24 -7
  35. package/src/Client/Input/CameraInputUtils.lua +49 -13
  36. package/src/Client/Input/CameraTouchInputUtils.lua +17 -16
  37. package/src/Client/Utility/CameraFrame.lua +2 -2
  38. package/src/Client/Utility/CameraFrame.story.lua +21 -12
  39. package/src/Client/Utility/CameraStateTweener.lua +39 -19
  40. package/src/Client/Utility/FieldOfViewUtils.lua +1 -1
  41. package/test/scripts/Client/ClientMain.client.lua +1 -1
  42. package/test/scripts/Server/ServerMain.server.lua +1 -1
@@ -1,3 +1,4 @@
1
+ --!strict
1
2
  --[=[
2
3
  Hack to maintain default camera control by binding before and after the camera update cycle
3
4
  This allows other cameras to build off of the "default" camera while maintaining the same Roblox control scheme.
@@ -8,31 +9,44 @@
8
9
 
9
10
  local require = require(script.Parent.loader).load(script)
10
11
 
12
+ local HttpService = game:GetService("HttpService")
11
13
  local RunService = game:GetService("RunService")
12
14
  local Workspace = game:GetService("Workspace")
13
- local HttpService = game:GetService("HttpService")
14
15
 
15
- local CameraState = require("CameraState")
16
- local SummedCamera = require("SummedCamera")
17
- local Maid = require("Maid")
18
16
  local CFrameUtils = require("CFrameUtils")
17
+ local CameraEffectUtils = require("CameraEffectUtils")
19
18
  local CameraFrame = require("CameraFrame")
19
+ local CameraState = require("CameraState")
20
+ local Maid = require("Maid")
21
+ local Observable = require("Observable")
22
+ local Rx = require("Rx")
23
+ local SummedCamera = require("SummedCamera")
20
24
  local ValueObject = require("ValueObject")
21
- local _Rx = require("Rx")
22
- local _Observable = require("Observable")
23
25
 
24
26
  local EPSILON = 0.001
25
27
 
26
28
  local DefaultCamera = {}
27
29
  DefaultCamera.ClassName = "DefaultCamera"
28
30
 
31
+ export type DefaultCamera = typeof(setmetatable(
32
+ {} :: {
33
+ CameraState: CameraState.CameraState,
34
+ _key: string,
35
+ _maid: Maid.Maid,
36
+ _isFirstPerson: ValueObject.ValueObject<boolean>,
37
+ _cameraState: CameraState.CameraState,
38
+ _lastCameraFrame: CameraFrame.CameraFrame?,
39
+ },
40
+ {} :: typeof({ __index = DefaultCamera })
41
+ )) & CameraEffectUtils.CameraEffect
42
+
29
43
  --[=[
30
44
  Constructs a new DefaultCamera
31
45
 
32
46
  @return DefaultCamera
33
47
  ]=]
34
- function DefaultCamera.new()
35
- local self = setmetatable({}, DefaultCamera)
48
+ function DefaultCamera.new(): DefaultCamera
49
+ local self: DefaultCamera = setmetatable({} :: any, DefaultCamera)
36
50
 
37
51
  self._key = HttpService:GenerateGUID(false)
38
52
  self._maid = Maid.new()
@@ -43,7 +57,7 @@ function DefaultCamera.new()
43
57
  return self
44
58
  end
45
59
 
46
- function DefaultCamera:__add(other)
60
+ function DefaultCamera.__add(self: DefaultCamera, other: CameraEffectUtils.CameraEffect)
47
61
  return SummedCamera.new(self, other)
48
62
  end
49
63
 
@@ -51,7 +65,7 @@ end
51
65
  Overrides the global field of view in the cached camera state
52
66
  @param fieldOfView number
53
67
  ]=]
54
- function DefaultCamera:SetRobloxFieldOfView(fieldOfView)
68
+ function DefaultCamera.SetRobloxFieldOfView(self: DefaultCamera, fieldOfView: number)
55
69
  self._cameraState.FieldOfView = fieldOfView
56
70
  end
57
71
 
@@ -63,7 +77,7 @@ DefaultCamera.OverrideGlobalFieldOfView = DefaultCamera.SetRobloxFieldOfView
63
77
 
64
78
  @param cameraState CameraState
65
79
  ]=]
66
- function DefaultCamera:SetRobloxCameraState(cameraState)
80
+ function DefaultCamera.SetRobloxCameraState(self: DefaultCamera, cameraState: CameraState.CameraState)
67
81
  self._cameraState = cameraState or error("No CameraState")
68
82
  end
69
83
 
@@ -75,7 +89,7 @@ DefaultCamera.OverrideCameraState = DefaultCamera.SetRobloxCameraState
75
89
 
76
90
  @param cframe CFrame
77
91
  ]=]
78
- function DefaultCamera:SetRobloxCFrame(cframe: CFrame)
92
+ function DefaultCamera.SetRobloxCFrame(self: DefaultCamera, cframe: CFrame)
79
93
  self._cameraState.CFrame = cframe
80
94
  end
81
95
 
@@ -84,7 +98,7 @@ end
84
98
 
85
99
  @return CameraState
86
100
  ]=]
87
- function DefaultCamera:GetRobloxCameraState()
101
+ function DefaultCamera.GetRobloxCameraState(self: DefaultCamera): CameraState.CameraState
88
102
  return self._cameraState
89
103
  end
90
104
 
@@ -93,14 +107,14 @@ end
93
107
 
94
108
  @param cameraFrame CameraState | nil
95
109
  ]=]
96
- function DefaultCamera:SetLastSetCameraFrame(cameraFrame: CameraFrame.CameraFrame)
110
+ function DefaultCamera.SetLastSetCameraFrame(self: DefaultCamera, cameraFrame: CameraFrame.CameraFrame)
97
111
  self._lastCameraFrame = CameraFrame.new(cameraFrame.QFrame, cameraFrame.FieldOfView)
98
112
  end
99
113
 
100
114
  --[=[
101
115
  Gets whether the Roblox camera is in first person
102
116
  ]=]
103
- function DefaultCamera:IsFirstPerson(): boolean
117
+ function DefaultCamera.IsFirstPerson(self: DefaultCamera): boolean
104
118
  return self._isFirstPerson.Value
105
119
  end
106
120
 
@@ -109,7 +123,7 @@ end
109
123
 
110
124
  @return Observable<boolean>
111
125
  ]=]
112
- function DefaultCamera:ObserveIsFirstPerson(): _Observable.Observable<boolean>
126
+ function DefaultCamera.ObserveIsFirstPerson(self: DefaultCamera): Observable.Observable<boolean>
113
127
  return self._isFirstPerson:Observe()
114
128
  end
115
129
 
@@ -119,8 +133,8 @@ end
119
133
  @param predicate ((inFirstPerson: boolean) -> boolean)?
120
134
  @return Observable<Brio<boolean>>
121
135
  ]=]
122
- function DefaultCamera:ObserveIsFirstPersonBrio(predicate: _Rx.Predicate<boolean>?)
123
- return self._isFirstPerson:Observe(predicate)
136
+ function DefaultCamera.ObserveIsFirstPersonBrio(self: DefaultCamera, predicate: Rx.Predicate<boolean>?)
137
+ return self._isFirstPerson:ObserveBrio(predicate)
124
138
  end
125
139
 
126
140
  --[=[
@@ -130,10 +144,10 @@ end
130
144
  Be sure to call UnbindFromRenderStep when using this.
131
145
  :::
132
146
  ]=]
133
- function DefaultCamera:BindToRenderStep()
147
+ function DefaultCamera.BindToRenderStep(self: DefaultCamera): Maid.Maid
134
148
  local maid = Maid.new()
135
149
 
136
- RunService:BindToRenderStep("DefaultCamera_Preupdate" .. self._key, Enum.RenderPriority.Camera.Value-2, function()
150
+ RunService:BindToRenderStep("DefaultCamera_Preupdate" .. self._key, Enum.RenderPriority.Camera.Value - 2, function()
137
151
  local camera = Workspace.CurrentCamera
138
152
 
139
153
  if self._lastCameraFrame then
@@ -155,16 +169,20 @@ function DefaultCamera:BindToRenderStep()
155
169
  self._cameraState:Set(camera)
156
170
  end)
157
171
 
158
- RunService:BindToRenderStep("DefaultCamera_PostUpdate" .. self._key, Enum.RenderPriority.Camera.Value+2, function()
159
- local camera = Workspace.CurrentCamera
172
+ RunService:BindToRenderStep(
173
+ "DefaultCamera_PostUpdate" .. self._key,
174
+ Enum.RenderPriority.Camera.Value + 2,
175
+ function()
176
+ local camera = Workspace.CurrentCamera
160
177
 
161
- -- Based upon Roblox's camera scripts
162
- local distance = (camera.CFrame.Position - camera.Focus.Position).magnitude
163
- self._isFirstPerson.Value = distance <= 0.75
178
+ -- Based upon Roblox's camera scripts
179
+ local distance = (camera.CFrame.Position - camera.Focus.Position).magnitude
180
+ self._isFirstPerson.Value = distance <= 0.75
164
181
 
165
- -- Capture
166
- self._cameraState = CameraState.new(camera)
167
- end)
182
+ -- Capture
183
+ self._cameraState = CameraState.new(camera)
184
+ end
185
+ )
168
186
 
169
187
  maid:GiveTask(function()
170
188
  self._isFirstPerson.Value = false
@@ -182,14 +200,14 @@ end
182
200
  --[=[
183
201
  Unbinds the camera from the RunService
184
202
  ]=]
185
- function DefaultCamera:UnbindFromRenderStep()
203
+ function DefaultCamera.UnbindFromRenderStep(self: DefaultCamera)
186
204
  self._maid._binding = nil
187
205
  end
188
206
 
189
207
  --[=[
190
208
  Cleans up the binding
191
209
  ]=]
192
- function DefaultCamera:Destroy()
210
+ function DefaultCamera.Destroy(self: DefaultCamera)
193
211
  self._maid:DoCleaning()
194
212
  end
195
213
 
@@ -199,7 +217,7 @@ end
199
217
  @prop CameraState CameraState
200
218
  @within DefaultCamera
201
219
  ]=]
202
- function DefaultCamera:__index(index)
220
+ function DefaultCamera.__index(self: DefaultCamera, index)
203
221
  if index == "CameraState" then
204
222
  return rawget(self, "_cameraState")
205
223
  elseif index == "_maid" or index == "_lastCameraFrame" or index == "_key" then
@@ -209,4 +227,4 @@ function DefaultCamera:__index(index)
209
227
  end
210
228
  end
211
229
 
212
- return DefaultCamera
230
+ return DefaultCamera
@@ -5,11 +5,11 @@
5
5
 
6
6
  local require = require(script.Parent.loader).load(script)
7
7
 
8
- local Spring = require("Spring")
9
- local SummedCamera = require("SummedCamera")
10
- local SpringUtils = require("SpringUtils")
11
8
  local CameraState = require("CameraState")
12
9
  local CubicSplineUtils = require("CubicSplineUtils")
10
+ local Spring = require("Spring")
11
+ local SpringUtils = require("SpringUtils")
12
+ local SummedCamera = require("SummedCamera")
13
13
 
14
14
  local FadeBetweenCamera = {}
15
15
  FadeBetweenCamera.ClassName = "FadeBetweenCamera"
@@ -21,9 +21,9 @@ FadeBetweenCamera.ClassName = "FadeBetweenCamera"
21
21
  ]=]
22
22
  function FadeBetweenCamera.new(cameraA, cameraB)
23
23
  local self = setmetatable({
24
- _spring = Spring.new(0);
25
- CameraA = cameraA or error("No cameraA");
26
- CameraB = cameraB or error("No cameraB");
24
+ _spring = Spring.new(0),
25
+ CameraA = cameraA or error("No cameraA"),
26
+ CameraB = cameraB or error("No cameraB"),
27
27
  }, FadeBetweenCamera)
28
28
 
29
29
  self.Damper = 1
@@ -127,4 +127,4 @@ function FadeBetweenCamera:__index(index)
127
127
  end
128
128
  end
129
129
 
130
- return FadeBetweenCamera
130
+ return FadeBetweenCamera
@@ -4,8 +4,8 @@
4
4
 
5
5
  local require = require(script.Parent.loader).load(script)
6
6
 
7
- local CubicSplineUtils = require("CubicSplineUtils")
8
7
  local CameraState = require("CameraState")
8
+ local CubicSplineUtils = require("CubicSplineUtils")
9
9
 
10
10
  local FadeBetweenCamera2 = {}
11
11
  FadeBetweenCamera2.ClassName = "FadeBetweenCamera2"
@@ -18,13 +18,13 @@ FadeBetweenCamera2.__index = FadeBetweenCamera2
18
18
  ]=]
19
19
  function FadeBetweenCamera2.new(cameraA, cameraB)
20
20
  local self = setmetatable({
21
- CameraA = cameraA or error("No cameraA");
22
- CameraB = cameraB or error("No cameraB");
23
- _state0 = cameraA.CameraState;
24
- _time0 = os.clock();
25
- _target = 0;
26
- _position0 = 0;
27
- _speed = 15;
21
+ CameraA = cameraA or error("No cameraA"),
22
+ CameraB = cameraB or error("No cameraB"),
23
+ _state0 = cameraA.CameraState,
24
+ _time0 = os.clock(),
25
+ _target = 0,
26
+ _position0 = 0,
27
+ _speed = 15,
28
28
  }, FadeBetweenCamera2)
29
29
 
30
30
  return self
@@ -138,9 +138,9 @@ function FadeBetweenCamera2:_computeDoneProportion(now)
138
138
  return 1
139
139
  end
140
140
 
141
- local SPEED_CONSTANT = 0.5/15 -- 0.5 seconds is 15 speed in the other system
141
+ local SPEED_CONSTANT = 0.5 / 15 -- 0.5 seconds is 15 speed in the other system
142
142
 
143
- return math.clamp(self._speed*(now - self._time0)*SPEED_CONSTANT/dist_to_travel, 0, 1)
143
+ return math.clamp(self._speed * (now - self._time0) * SPEED_CONSTANT / dist_to_travel, 0, 1)
144
144
  end
145
145
 
146
- return FadeBetweenCamera2
146
+ return FadeBetweenCamera2
@@ -1,3 +1,4 @@
1
+ --!strict
1
2
  --[=[
2
3
  Add another layer of effects that can be faded in/out
3
4
  @class FadeBetweenCamera3
@@ -5,29 +6,51 @@
5
6
 
6
7
  local require = require(script.Parent.loader).load(script)
7
8
 
8
- local Spring = require("Spring")
9
- local SummedCamera = require("SummedCamera")
10
- local SpringUtils = require("SpringUtils")
11
- local QFrame = require("QFrame")
12
- local FieldOfViewUtils = require("FieldOfViewUtils")
13
- local CameraState = require("CameraState")
9
+ local CameraEffectUtils = require("CameraEffectUtils")
14
10
  local CameraFrame = require("CameraFrame")
11
+ local CameraState = require("CameraState")
15
12
  local CubicSplineUtils = require("CubicSplineUtils")
13
+ local FieldOfViewUtils = require("FieldOfViewUtils")
14
+ local QFrame = require("QFrame")
15
+ local Spring = require("Spring")
16
+ local SpringUtils = require("SpringUtils")
17
+ local SummedCamera = require("SummedCamera")
16
18
 
17
19
  local FadeBetweenCamera3 = {}
18
20
  FadeBetweenCamera3.ClassName = "FadeBetweenCamera3"
19
21
 
22
+ export type FadeBetweenCamera3 = typeof(setmetatable(
23
+ {} :: {
24
+ _spring: Spring.Spring<number>,
25
+ CameraA: CameraEffectUtils.CameraLike,
26
+ CameraB: CameraEffectUtils.CameraLike,
27
+ HasReachedTarget: boolean,
28
+ Damper: number,
29
+ Value: number,
30
+ Speed: number,
31
+ Velocity: number,
32
+ Target: number,
33
+ },
34
+ {} :: typeof({ __index = FadeBetweenCamera3 })
35
+ )) & CameraEffectUtils.CameraEffect
36
+
20
37
  --[=[
21
38
  @param cameraA CameraLike
22
39
  @param cameraB CameraLike
23
40
  @return FadeBetweenCamera3
24
41
  ]=]
25
- function FadeBetweenCamera3.new(cameraA, cameraB)
26
- local self = setmetatable({
27
- _spring = Spring.new(0);
28
- CameraA = cameraA or error("No cameraA");
29
- CameraB = cameraB or error("No cameraB");
30
- }, FadeBetweenCamera3)
42
+ function FadeBetweenCamera3.new(
43
+ cameraA: CameraEffectUtils.CameraLike,
44
+ cameraB: CameraEffectUtils.CameraLike
45
+ ): FadeBetweenCamera3
46
+ local self: FadeBetweenCamera3 = setmetatable(
47
+ {
48
+ _spring = Spring.new(0),
49
+ CameraA = cameraA or error("No cameraA"),
50
+ CameraB = cameraB or error("No cameraB"),
51
+ } :: any,
52
+ FadeBetweenCamera3
53
+ )
31
54
 
32
55
  self.Damper = 1
33
56
  self.Speed = 15
@@ -79,23 +102,36 @@ function FadeBetweenCamera3:__index(index)
79
102
 
80
103
  local dist = (frameA.Position - frameB.Position).magnitude
81
104
 
82
- local node0 = CubicSplineUtils.newSplineNode(0, frameA.Position,
83
- stateA.CameraFrameDerivative.Position + frameA.CFrame.lookVector*dist*0.3)
84
- local node1 = CubicSplineUtils.newSplineNode(1, frameB.Position,
85
- stateB.CameraFrameDerivative.Position + frameB.CFrame.lookVector*dist*0.3)
105
+ local node0 = CubicSplineUtils.newSplineNode(
106
+ 0,
107
+ frameA.Position,
108
+ stateA.CameraFrameDerivative.Position + frameA.CFrame.lookVector * dist * 0.3
109
+ )
110
+ local node1 = CubicSplineUtils.newSplineNode(
111
+ 1,
112
+ frameB.Position,
113
+ stateB.CameraFrameDerivative.Position + frameB.CFrame.lookVector * dist * 0.3
114
+ )
86
115
 
87
116
  -- We do the position this way because 0^-1 is undefined
88
117
  --stateA.Position + (stateB.Position - stateA.Position)*t
89
118
  local newNode = CubicSplineUtils.tweenSplineNodes(node0, node1, t)
90
- local delta = (frameB*(frameA^-1))
119
+ local delta = (frameB * (frameA ^ -1))
91
120
 
92
121
  local deltaQFrame = delta.QFrame
93
122
  if deltaQFrame.W < 0 then
94
123
  delta.QFrame = QFrame.new(
95
- deltaQFrame.x, deltaQFrame.y, deltaQFrame.z, -deltaQFrame.W, -deltaQFrame.X, -deltaQFrame.Y, -deltaQFrame.Z)
124
+ deltaQFrame.x,
125
+ deltaQFrame.y,
126
+ deltaQFrame.z,
127
+ -deltaQFrame.W,
128
+ -deltaQFrame.X,
129
+ -deltaQFrame.Y,
130
+ -deltaQFrame.Z
131
+ )
96
132
  end
97
133
 
98
- local newState = delta^t*frameA
134
+ local newState = delta ^ t * frameA
99
135
  newState.FieldOfView = FieldOfViewUtils.lerpInHeightSpace(frameA.FieldOfView, frameB.FieldOfView, t)
100
136
  newState.Position = newNode.p
101
137
 
@@ -121,7 +157,7 @@ function FadeBetweenCamera3:__index(index)
121
157
  if animating then
122
158
  return self._spring.Velocity
123
159
  else
124
- return Vector3.zero
160
+ return 0
125
161
  end
126
162
  elseif index == "HasReachedTarget" then
127
163
  local animating = SpringUtils.animating(self._spring)
@@ -135,4 +171,4 @@ function FadeBetweenCamera3:__index(index)
135
171
  end
136
172
  end
137
173
 
138
- return FadeBetweenCamera3
174
+ return FadeBetweenCamera3
@@ -4,8 +4,8 @@
4
4
 
5
5
  local require = require(script.Parent.loader).load(script)
6
6
 
7
- local CubicSplineUtils = require("CubicSplineUtils")
8
7
  local CameraState = require("CameraState")
8
+ local CubicSplineUtils = require("CubicSplineUtils")
9
9
  local Spring = require("Spring")
10
10
  local SpringUtils = require("SpringUtils")
11
11
 
@@ -20,11 +20,11 @@ FadeBetweenCamera4.__index = FadeBetweenCamera4
20
20
  ]=]
21
21
  function FadeBetweenCamera4.new(cameraA, cameraB)
22
22
  local self = setmetatable({
23
- CameraA = cameraA or error("No cameraA");
24
- CameraB = cameraB or error("No cameraB");
25
- _spring = Spring.new();
26
- _position0 = 0;
27
- _state0 = cameraA.CameraState;
23
+ CameraA = cameraA or error("No cameraA"),
24
+ CameraB = cameraB or error("No cameraB"),
25
+ _spring = Spring.new(),
26
+ _position0 = 0,
27
+ _state0 = cameraA.CameraState,
28
28
  }, FadeBetweenCamera4)
29
29
 
30
30
  self._spring.s = 15
@@ -122,11 +122,19 @@ function FadeBetweenCamera4:_computeCameraState(position)
122
122
  local a = self:_computeTargetState(0)
123
123
 
124
124
  node0 = CubicSplineUtils.newSplineNode(0, a.CameraFrame, a.CameraFrameDerivative)
125
- node1 = CubicSplineUtils.newSplineNode(self._position0, self._state0.CameraFrame, self._state0.CameraFrameDerivative)
125
+ node1 = CubicSplineUtils.newSplineNode(
126
+ self._position0,
127
+ self._state0.CameraFrame,
128
+ self._state0.CameraFrameDerivative
129
+ )
126
130
  else
127
131
  local b = self:_computeTargetState(1)
128
132
 
129
- node0 = CubicSplineUtils.newSplineNode(self._position0, self._state0.CameraFrame, self._state0.CameraFrameDerivative)
133
+ node0 = CubicSplineUtils.newSplineNode(
134
+ self._position0,
135
+ self._state0.CameraFrame,
136
+ self._state0.CameraFrameDerivative
137
+ )
130
138
  node1 = CubicSplineUtils.newSplineNode(1, b.CameraFrame, b.CameraFrameDerivative)
131
139
  end
132
140
 
@@ -136,4 +144,4 @@ function FadeBetweenCamera4:_computeCameraState(position)
136
144
  return newState, position
137
145
  end
138
146
 
139
- return FadeBetweenCamera4
147
+ return FadeBetweenCamera4
@@ -1,3 +1,4 @@
1
+ --!strict
1
2
  --[=[
2
3
  Add another layer of effects that can be faded in/out
3
4
  @class FadingCamera
@@ -5,17 +6,32 @@
5
6
 
6
7
  local require = require(script.Parent.loader).load(script)
7
8
 
9
+ local CameraEffectUtils = require("CameraEffectUtils")
10
+ local CameraState = require("CameraState")
8
11
  local Spring = require("Spring")
9
12
  local SummedCamera = require("SummedCamera")
10
13
 
11
14
  local FadingCamera = {}
12
15
  FadingCamera.ClassName = "FadingCamera"
13
16
 
17
+ export type FadingCamera = typeof(setmetatable(
18
+ {} :: {
19
+ CameraState: CameraState.CameraState,
20
+ Spring: Spring.Spring<number>,
21
+ Camera: CameraEffectUtils.CameraLike,
22
+ Damper: number,
23
+ Speed: number,
24
+ Target: number,
25
+ Value: number,
26
+ },
27
+ {} :: typeof({ __index = FadingCamera })
28
+ )) & CameraEffectUtils.CameraEffect
29
+
14
30
  --[=[
15
31
  @param camera CameraEffect
16
32
  ]=]
17
- function FadingCamera.new(camera)
18
- local self = setmetatable({}, FadingCamera)
33
+ function FadingCamera.new(camera: CameraEffectUtils.CameraLike): FadingCamera
34
+ local self: FadingCamera = setmetatable({} :: any, FadingCamera)
19
35
 
20
36
  self.Spring = Spring.new(0)
21
37
 
@@ -33,7 +49,7 @@ end
33
49
  function FadingCamera:__newindex(index, value)
34
50
  if index == "Damper" then
35
51
  self.Spring.Damper = value
36
- elseif index == "value" then
52
+ elseif index == "Value" then
37
53
  self.Spring.Value = value
38
54
  elseif index == "Speed" then
39
55
  self.Spring.Speed = value
@@ -57,7 +73,7 @@ function FadingCamera:__index(index)
57
73
  return (self.Camera.CameraState or self.Camera) * self.Spring.Value
58
74
  elseif index == "Damper" then
59
75
  return self.Spring.Damper
60
- elseif index == "value" then
76
+ elseif index == "Value" then
61
77
  return self.Spring.Value
62
78
  elseif index == "Speed" then
63
79
  return self.Spring.Speed
@@ -72,4 +88,4 @@ function FadingCamera:__index(index)
72
88
  end
73
89
  end
74
90
 
75
- return FadingCamera
91
+ return FadingCamera
@@ -1,3 +1,4 @@
1
+ --!strict
1
2
  --[=[
2
3
  Update on heartbeat, must GC this camera state, unlike others. This
3
4
  allows for camera effects to run on heartbeat and cache information once instead
@@ -10,17 +11,29 @@ local require = require(script.Parent.loader).load(script)
10
11
 
11
12
  local RunService = game:GetService("RunService")
12
13
 
13
- local SummedCamera = require("SummedCamera")
14
+ local CameraEffectUtils = require("CameraEffectUtils")
15
+ local CameraState = require("CameraState")
14
16
  local Maid = require("Maid")
17
+ local SummedCamera = require("SummedCamera")
15
18
 
16
19
  local HeartbeatCamera = {}
17
20
  HeartbeatCamera.ClassName = "HeartbeatCamera"
18
21
  HeartbeatCamera.ProfileName = "HeartbeatCamera"
19
22
 
20
- function HeartbeatCamera.new(camera)
21
- local self = setmetatable({}, HeartbeatCamera)
23
+ export type HeartbeatCamera = typeof(setmetatable(
24
+ {} :: {
25
+ CameraState: CameraState.CameraState,
26
+ _maid: Maid.Maid,
27
+ _camera: CameraEffectUtils.CameraEffect,
28
+ _currentStateCache: CameraState.CameraState,
29
+ },
30
+ {} :: typeof({ __index = HeartbeatCamera })
31
+ )) & CameraEffectUtils.CameraEffect
32
+
33
+ function HeartbeatCamera.new(camera: CameraEffectUtils.CameraEffect): HeartbeatCamera
34
+ local self: HeartbeatCamera = setmetatable({} :: any, HeartbeatCamera)
22
35
 
23
- self._camera = camera or error("No camera")
36
+ self._camera = assert(camera, "No camera")
24
37
  self._maid = Maid.new()
25
38
 
26
39
  self._currentStateCache = self._camera.CameraState or error("Camera state returned null")
@@ -33,11 +46,11 @@ function HeartbeatCamera.new(camera)
33
46
  return self
34
47
  end
35
48
 
36
- function HeartbeatCamera:__add(other)
49
+ function HeartbeatCamera.__add(self: HeartbeatCamera, other: CameraEffectUtils.CameraEffect): SummedCamera.SummedCamera
37
50
  return SummedCamera.new(self, other)
38
51
  end
39
52
 
40
- function HeartbeatCamera:ForceUpdateCache()
53
+ function HeartbeatCamera.ForceUpdateCache(self: HeartbeatCamera): ()
41
54
  self._currentStateCache = self._camera.CameraState
42
55
  end
43
56
 
@@ -47,7 +60,7 @@ end
47
60
  @prop CameraState CameraState
48
61
  @within HeartbeatCamera
49
62
  ]=]
50
- function HeartbeatCamera:__index(index)
63
+ function HeartbeatCamera.__index(self: HeartbeatCamera, index)
51
64
  if index == "CameraState" then
52
65
  return self._currentStateCache
53
66
  else
@@ -55,8 +68,8 @@ function HeartbeatCamera:__index(index)
55
68
  end
56
69
  end
57
70
 
58
- function HeartbeatCamera:Destroy()
71
+ function HeartbeatCamera.Destroy(self: HeartbeatCamera)
59
72
  self._maid:DoCleaning()
60
73
  end
61
74
 
62
- return HeartbeatCamera
75
+ return HeartbeatCamera