Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
M
Motion
Overview
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Dmitriy Stepanets
Motion
Commits
3e422773
Unverified
Commit
3e422773
authored
Jun 08, 2017
by
Daniel Dahan
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
second round reworking the MotionController
parent
fcf3d822
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
331 additions
and
248 deletions
+331
-248
Sources/Debug Plugin/MotionDebugPlugin.swift
+1
-1
Sources/Motion.swift
+12
-12
Sources/MotionController.swift
+316
-233
Sources/MotionIndependentController.swift
+2
-2
No files found.
Sources/Debug Plugin/MotionDebugPlugin.swift
View file @
3e422773
...
@@ -91,7 +91,7 @@ extension MotionDebugPlugin:MotionDebugViewDelegate {
...
@@ -91,7 +91,7 @@ extension MotionDebugPlugin:MotionDebugViewDelegate {
public
func
onProcessSliderChanged
(
progress
:
Float
)
{
public
func
onProcessSliderChanged
(
progress
:
Float
)
{
let
seekValue
=
Motion
.
shared
.
isPresenting
?
progress
:
1.0
-
progress
let
seekValue
=
Motion
.
shared
.
isPresenting
?
progress
:
1.0
-
progress
Motion
.
shared
.
update
(
progress
:
Double
(
seekValue
))
Motion
.
shared
.
update
(
elapsedTime
:
Double
(
seekValue
))
}
}
func
onPerspectiveChanged
(
translation
:
CGPoint
,
rotation
:
CGFloat
,
scale
:
CGFloat
)
{
func
onPerspectiveChanged
(
translation
:
CGPoint
,
rotation
:
CGFloat
,
scale
:
CGFloat
)
{
...
...
Sources/Motion.swift
View file @
3e422773
...
@@ -166,12 +166,12 @@ fileprivate extension Motion {
...
@@ -166,12 +166,12 @@ fileprivate extension Motion {
prepareViewControllers
()
prepareViewControllers
()
prepareSnapshotView
()
prepareSnapshotView
()
prepare
For
Transition
()
prepareTransition
()
prepareContext
()
prepareContext
()
prepareToView
()
prepareToView
()
prepareViewHierarchy
()
prepareViewHierarchy
()
processContext
()
processContext
()
prepare
ForAnimation
()
prepare
TransitionPairs
()
processForAnimation
()
processForAnimation
()
}
}
}
}
...
@@ -188,7 +188,7 @@ internal extension Motion {
...
@@ -188,7 +188,7 @@ internal extension Motion {
fullScreenSnapshot
?
.
removeFromSuperview
()
fullScreenSnapshot
?
.
removeFromSuperview
()
}
}
override
func
complete
(
finished
:
Bool
)
{
override
func
complete
(
isFinished
finished
:
Bool
)
{
guard
isTransitioning
else
{
guard
isTransitioning
else
{
return
return
}
}
...
@@ -220,13 +220,13 @@ internal extension Motion {
...
@@ -220,13 +220,13 @@ internal extension Motion {
}
}
// move fromView & toView back from our container back to the one supplied by UIKit
// move fromView & toView back from our container back to the one supplied by UIKit
if
(
toOverFullScreen
&&
f
inished
)
||
(
fromOverFullScreen
&&
!
finished
)
{
if
(
toOverFullScreen
&&
isF
inished
)
||
(
fromOverFullScreen
&&
!
finished
)
{
transitionContainer
.
addSubview
(
f
inished
?
fromView
:
toView
)
transitionContainer
.
addSubview
(
isF
inished
?
fromView
:
toView
)
}
}
transitionContainer
.
addSubview
(
f
inished
?
toView
:
fromView
)
transitionContainer
.
addSubview
(
isF
inished
?
toView
:
fromView
)
if
isPresenting
!=
f
inished
,
!
isContainerController
{
if
isPresenting
!=
isF
inished
,
!
isContainerController
{
// only happens when present a .overFullScreen VC
// only happens when present a .overFullScreen VC
// bug: http://openradar.appspot.com/radar?id=5320103646199808
// bug: http://openradar.appspot.com/radar?id=5320103646199808
UIApplication
.
shared
.
keyWindow
!.
addSubview
(
isPresenting
?
fromView
:
toView
)
UIApplication
.
shared
.
keyWindow
!.
addSubview
(
isPresenting
?
fromView
:
toView
)
...
@@ -249,7 +249,7 @@ internal extension Motion {
...
@@ -249,7 +249,7 @@ internal extension Motion {
insertToViewFirst
=
false
insertToViewFirst
=
false
defaultAnimation
=
.
auto
defaultAnimation
=
.
auto
super
.
complete
(
finished
:
f
inished
)
super
.
complete
(
isFinished
:
isF
inished
)
if
finished
{
if
finished
{
if
let
fvc
=
fvc
,
let
tvc
=
tvc
{
if
let
fvc
=
fvc
,
let
tvc
=
tvc
{
...
@@ -342,13 +342,13 @@ fileprivate extension Motion {
...
@@ -342,13 +342,13 @@ fileprivate extension Motion {
}
}
internal
extension
Motion
{
internal
extension
Motion
{
override
func
prepare
For
Transition
()
{
override
func
prepareTransition
()
{
super
.
prepare
For
Transition
()
super
.
prepareTransition
()
insert
(
preprocessor
:
DefaultAnimationPreprocessor
(
motion
:
self
),
before
:
DurationPreprocessor
.
self
)
insert
(
preprocessor
:
DefaultAnimationPreprocessor
(
motion
:
self
),
before
:
DurationPreprocessor
.
self
)
}
}
override
func
prepare
ForAnimation
()
{
override
func
prepare
TransitionPairs
()
{
super
.
prepare
ForAnimation
()
super
.
prepare
TransitionPairs
()
context
.
hide
(
view
:
toView
)
context
.
hide
(
view
:
toView
)
}
}
}
}
...
...
Sources/MotionController.swift
View file @
3e422773
...
@@ -107,7 +107,7 @@ public class MotionController: NSObject {
...
@@ -107,7 +107,7 @@ public class MotionController: NSObject {
internal
var
isFinished
=
true
internal
var
isFinished
=
true
/// An Array of MotionPreprocessors used during a transition.
/// An Array of MotionPreprocessors used during a transition.
internal
var
processors
:
[
MotionPreprocessor
]
!
internal
var
pr
epr
ocessors
:
[
MotionPreprocessor
]
!
/// An Array of MotionAnimators used during a transition.
/// An Array of MotionAnimators used during a transition.
internal
var
animators
:
[
MotionAnimator
]
!
internal
var
animators
:
[
MotionAnimator
]
!
...
@@ -125,6 +125,25 @@ public class MotionController: NSObject {
...
@@ -125,6 +125,25 @@ public class MotionController: NSObject {
internal
override
init
()
{}
internal
override
init
()
{}
}
}
public
extension
MotionController
{
/**
Receive callbacks on each animation frame.
Observers will be cleaned when a transition completes.
- Parameter observer: A MotionTransitionObserver.
*/
func
addTransitionObserver
(
observer
:
MotionTransitionObserver
)
{
defer
{
transitionObservers
?
.
append
(
observer
)
}
guard
nil
==
transitionObservers
else
{
return
}
transitionObservers
=
[]
}
}
fileprivate
extension
MotionController
{
fileprivate
extension
MotionController
{
/// Updates the transition observers.
/// Updates the transition observers.
func
updateTransitionObservers
()
{
func
updateTransitionObservers
()
{
...
@@ -155,6 +174,10 @@ fileprivate extension MotionController {
...
@@ -155,6 +174,10 @@ fileprivate extension MotionController {
}
}
fileprivate
extension
MotionController
{
fileprivate
extension
MotionController
{
/**
Handler for the DisplayLink updates.
- Parameter _ link: CADisplayLink.
*/
@objc
@objc
func
handleDisplayLink
(
_
link
:
CADisplayLink
)
{
func
handleDisplayLink
(
_
link
:
CADisplayLink
)
{
guard
isTransitioning
else
{
guard
isTransitioning
else
{
...
@@ -180,7 +203,7 @@ fileprivate extension MotionController {
...
@@ -180,7 +203,7 @@ fileprivate extension MotionController {
}
else
{
}
else
{
var
eTime
=
cTime
/
totalDuration
var
eTime
=
cTime
/
totalDuration
if
!
isFinished
{
if
!
isFinished
{
eTime
=
1
-
eTime
eTime
=
1
-
eTime
}
}
...
@@ -191,269 +214,329 @@ fileprivate extension MotionController {
...
@@ -191,269 +214,329 @@ fileprivate extension MotionController {
}
}
public
extension
MotionController
{
public
extension
MotionController
{
// MARK: Interactive Transition
/**
Updates the elapsed time for the interactive transition.
/**
- Parameter elapsedTime t: the current progress, must be between -1...1.
Update the progress for the interactive transition.
*/
- Parameters:
public
func
update
(
elapsedTime
t
:
TimeInterval
)
{
- progress: the current progress, must be between -1...1
guard
isTransitioning
else
{
*/
return
public
func
update
(
progress
:
Double
)
{
}
guard
isTransitioning
else
{
return
}
self
.
beginTime
=
nil
beginTime
=
nil
self
.
elapsedTime
=
max
(
-
1
,
min
(
1
,
progress
))
elapsedTime
=
max
(
-
1
,
min
(
1
,
t
))
}
/**
Finish the interactive transition.
Will stop the interactive transition and animate from the
current state to the **end** state
*/
public
func
end
(
animate
:
Bool
=
true
)
{
guard
isTransitioning
else
{
return
}
if
!
animate
{
self
.
complete
(
isFinished
:
true
)
return
}
}
var
maxTime
:
TimeInterval
=
0
for
animator
in
self
.
animators
{
/**
maxTime
=
max
(
maxTime
,
animator
.
resume
(
at
:
self
.
elapsedTime
*
self
.
totalDuration
,
isReversed
:
false
))
Finish the interactive transition.
Will stop the interactive transition and animate from the
current state to the **end** state
- Parameter isAnimated: A boolean indicating if the completion is animated.
*/
public
func
end
(
isAnimated
:
Bool
=
true
)
{
guard
isTransitioning
else
{
return
}
guard
isAnimated
else
{
complete
(
isFinished
:
true
)
return
}
var
v
:
TimeInterval
=
0
for
a
in
animators
{
v
=
max
(
v
,
a
.
resume
(
at
:
elapsedTime
*
totalDuration
,
isReversed
:
false
))
}
complete
(
after
:
v
,
isFinished
:
true
)
}
}
self
.
complete
(
after
:
maxTime
,
isFinished
:
true
)
}
/**
/**
Cancel the interactive transition.
Cancel the interactive transition.
Will stop the interactive transition and animate from the
Will stop the interactive transition and animate from the
current state to the **begining** state
current state to the **begining** state
*/
- Parameter isAnimated: A boolean indicating if the completion is animated.
public
func
cancel
(
animate
:
Bool
=
true
)
{
*/
guard
isTransitioning
else
{
return
}
public
func
cancel
(
isAnimated
:
Bool
=
true
)
{
if
!
animate
{
guard
isTransitioning
else
{
self
.
complete
(
isFinished
:
false
)
return
return
}
}
var
maxTime
:
TimeInterval
=
0
guard
isAnimated
else
{
for
animator
in
self
.
animators
{
complete
(
isFinished
:
false
)
var
adjustedProgress
=
self
.
elapsedTime
return
if
adjustedProgress
<
0
{
}
adjustedProgress
=
-
adjustedProgress
}
var
v
:
TimeInterval
=
0
maxTime
=
max
(
maxTime
,
animator
.
resume
(
at
:
adjustedProgress
*
self
.
totalDuration
,
isReversed
:
true
))
for
a
in
animators
{
var
t
=
elapsedTime
if
t
<
0
{
t
=
-
t
}
v
=
max
(
v
,
a
.
resume
(
at
:
t
*
totalDuration
,
isReversed
:
true
))
}
complete
(
after
:
v
,
isFinished
:
false
)
}
}
self
.
complete
(
after
:
maxTime
,
isFinished
:
false
)
}
/**
Override modifiers during an interactive animation.
For example:
Motion.shared.apply([.position(x:50, y:50)], to:view)
/**
Override transition animations during an interactive animation.
will set the view's position to 50, 50
- Parameters:
- modifiers: the modifiers to override
- view: the view to override to
*/
public
func
apply
(
transitions
:
[
MotionTransition
],
to
view
:
UIView
)
{
guard
isTransitioning
else
{
return
}
let
targetState
=
MotionTargetState
(
transitions
:
transitions
)
if
let
otherView
=
self
.
context
.
pairedView
(
for
:
view
)
{
for
animator
in
self
.
animators
{
animator
.
apply
(
state
:
targetState
,
to
:
otherView
)
}
}
for
animator
in
self
.
animators
{
animator
.
apply
(
state
:
targetState
,
to
:
view
)
}
}
}
public
extension
MotionController
{
For example:
// MARK: Observe Progress
/**
Motion.shared.apply([.position(x:50, y:50)], to: view)
Receive callbacks on each animation frame.
Observers will be cleaned when transition completes
- Parameters:
will set the view's position to 50, 50
- observer: the observer
- Parameter transitions: An Array of MotionTransitions.
*/
- Parameter to view: A UIView.
func
observeForProgressUpdate
(
observer
:
MotionTransitionObserver
)
{
*/
if
transitionObservers
==
nil
{
public
func
apply
(
transitions
:
[
MotionTransition
],
to
view
:
UIView
)
{
transitionObservers
=
[]
guard
isTransitioning
else
{
return
}
let
s
=
MotionTargetState
(
transitions
:
transitions
)
let
v
=
context
.
pairedView
(
for
:
view
)
??
view
for
a
in
animators
{
a
.
apply
(
state
:
s
,
to
:
v
)
}
}
}
transitionObservers
!.
append
(
observer
)
}
}
}
// internal methods for transition
internal
extension
MotionController
{
internal
extension
MotionController
{
/// Load plugins, processors, animators, container, & context
/**
/// must have transitionContainer set already
Load plugins, processors, animators, container, & context
/// subclass should call context.set(fromViews:toViews) after inserting fromViews & toViews into the container
The transitionContainer must already be set.
func
prepareForTransition
()
{
Subclasses should call context.set(fromViews: toViews) after
guard
isTransitioning
else
{
fatalError
()
}
inserting fromViews & toViews into the container
plugins
=
Motion
.
enabledPlugins
.
map
({
return
$0
.
init
()
})
*/
processors
=
[
func
prepareTransition
()
{
IgnoreSubviewModifiersPreprocessor
(),
guard
isTransitioning
else
{
MatchPreprocessor
(),
fatalError
()
SourcePreprocessor
(),
}
CascadePreprocessor
(),
DurationPreprocessor
()
prepareTransitionContainer
()
]
prepareContext
()
animators
=
[
preparePreprocessors
()
MotionDefaultAnimator
<
MotionCoreAnimationViewContext
>
()
prepareAnimators
()
]
preparePlugins
()
if
#available(iOS 10, tvOS 10, *)
{
animators
.
append
(
MotionDefaultAnimator
<
MotionViewPropertyViewContext
>
())
}
}
// There is no covariant in Swift, so we need to add plugins one by one.
/// Prepares the transition from-view & to-view pairs.
for
plugin
in
plugins
{
func
prepareTransitionPairs
()
{
processors
.
append
(
plugin
)
guard
isTransitioning
else
{
animators
.
append
(
plugin
)
fatalError
()
}
transitionPairs
=
[([
UIView
],
[
UIView
])]()
for
a
in
animators
{
let
fv
=
context
.
fromViews
.
filter
{
(
view
:
UIView
)
->
Bool
in
return
a
.
canAnimate
(
view
:
view
,
isAppearing
:
false
)
}
let
tv
=
context
.
toViews
.
filter
{
(
view
:
UIView
)
->
Bool
in
return
a
.
canAnimate
(
view
:
view
,
isAppearing
:
true
)
}
transitionPairs
.
append
((
fv
,
tv
))
}
}
}
}
transitionContainer
.
isUserInteractionEnabled
=
false
internal
extension
MotionController
{
func
processContext
()
{
// a view to hold all the animating views
guard
isTransitioning
else
{
container
=
UIView
(
frame
:
transitionContainer
.
bounds
)
fatalError
()
transitionContainer
.
addSubview
(
container
)
}
context
=
MotionContext
(
container
:
container
)
for
v
in
preprocessors
{
v
.
process
(
fromViews
:
context
.
fromViews
,
toViews
:
context
.
toViews
)
for
processor
in
processors
{
}
processor
.
context
=
context
}
for
animator
in
animators
{
animator
.
context
=
context
}
}
}
/// Actually animate the views
/// subclass should call `prepareTransition` & `prepareTransitionPairs` before calling `animate`
func
animate
()
{
guard
isTransitioning
else
{
fatalError
()
}
for
(
currentFromViews
,
currentToViews
)
in
transitionPairs
{
// auto hide all animated views
for
view
in
currentFromViews
{
context
.
hide
(
view
:
view
)
}
for
view
in
currentToViews
{
context
.
hide
(
view
:
view
)
}
}
var
totalDuration
:
TimeInterval
=
0
var
animatorWantsInteractive
=
false
for
(
i
,
animator
)
in
animators
.
enumerated
()
{
let
duration
=
animator
.
animate
(
fromViews
:
transitionPairs
[
i
]
.
0
,
toViews
:
transitionPairs
[
i
]
.
1
)
if
duration
==
.
infinity
{
animatorWantsInteractive
=
true
}
else
{
totalDuration
=
max
(
totalDuration
,
duration
)
}
}
self
.
totalDuration
=
totalDuration
if
animatorWantsInteractive
{
update
(
elapsedTime
:
0
)
}
else
{
complete
(
after
:
totalDuration
,
isFinished
:
true
)
}
}
func
processContext
()
{
func
complete
(
after
:
TimeInterval
,
isFinished
:
Bool
)
{
guard
isTransitioning
else
{
fatalError
()
}
guard
isTransitioning
else
{
for
processor
in
processors
{
fatalError
()
processor
.
process
(
fromViews
:
context
.
fromViews
,
toViews
:
context
.
toViews
)
}
if
after
<=
0.001
{
complete
(
isFinished
:
isFinished
)
return
}
let
v
=
(
isFinished
?
elapsedTime
:
1
-
elapsedTime
)
*
totalDuration
self
.
isFinished
=
isFinished
self
.
currentAnimationDuration
=
after
+
v
self
.
beginTime
=
CACurrentMediaTime
()
-
v
}
}
}
func
complete
(
isFinished
:
Bool
)
{
func
prepareForAnimation
()
{
guard
isTransitioning
else
{
guard
isTransitioning
else
{
fatalError
()
}
fatalError
()
transitionPairs
=
[([
UIView
],
[
UIView
])]()
}
for
animator
in
animators
{
let
currentFromViews
=
context
.
fromViews
.
filter
{
(
view
:
UIView
)
->
Bool
in
for
animator
in
animators
{
return
animator
.
canAnimate
(
view
:
view
,
isAppearing
:
false
)
animator
.
clean
()
}
}
let
currentToViews
=
context
.
toViews
.
filter
{
(
view
:
UIView
)
->
Bool
in
return
animator
.
canAnimate
(
view
:
view
,
isAppearing
:
true
)
transitionContainer
!.
isUserInteractionEnabled
=
true
}
transitionPairs
.
append
((
currentFromViews
,
currentToViews
))
let
completion
=
completionCallback
transitionPairs
=
nil
transitionObservers
=
nil
transitionContainer
=
nil
completionCallback
=
nil
container
=
nil
preprocessors
=
nil
animators
=
nil
plugins
=
nil
context
=
nil
beginTime
=
nil
elapsedTime
=
0
totalDuration
=
0
completion
?(
isFinished
)
}
}
}
}
/// Actually animate the views
fileprivate
extension
MotionController
{
/// subclass should call `prepareForTransition` & `prepareForAnimation` before calling `animate`
/// Prepares the transition container.
func
animate
()
{
func
prepareTransitionContainer
()
{
guard
isTransitioning
else
{
fatalError
()
}
transitionContainer
.
isUserInteractionEnabled
=
false
for
(
currentFromViews
,
currentToViews
)
in
transitionPairs
{
// auto hide all animated views
// a view to hold all the animating views
for
view
in
currentFromViews
{
container
=
UIView
(
frame
:
transitionContainer
.
bounds
)
context
.
hide
(
view
:
view
)
transitionContainer
.
addSubview
(
container
)
}
for
view
in
currentToViews
{
context
.
hide
(
view
:
view
)
}
}
}
var
totalDuration
:
TimeInterval
=
0
/// Prepares the context.
var
animatorWantsInteractive
=
false
func
prepareContext
()
{
for
(
i
,
animator
)
in
animators
.
enumerated
()
{
context
=
MotionContext
(
container
:
container
)
let
duration
=
animator
.
animate
(
fromViews
:
transitionPairs
[
i
]
.
0
,
toViews
:
transitionPairs
[
i
]
.
1
)
if
duration
==
.
infinity
{
animatorWantsInteractive
=
true
}
else
{
totalDuration
=
max
(
totalDuration
,
duration
)
}
}
}
self
.
totalDuration
=
totalDuration
/// Prepares the preprocessors.
if
animatorWantsInteractive
{
func
preparePreprocessors
()
{
update
(
progress
:
0
)
preprocessors
=
[
}
else
{
IgnoreSubviewModifiersPreprocessor
(),
complete
(
after
:
totalDuration
,
isFinished
:
true
)
MatchPreprocessor
(),
SourcePreprocessor
(),
CascadePreprocessor
(),
DurationPreprocessor
()
]
for
v
in
preprocessors
{
v
.
context
=
context
}
}
}
}
/// Prepares the animators.
func
complete
(
after
:
TimeInterval
,
isFinished
:
Bool
)
{
func
prepareAnimators
()
{
guard
isTransitioning
else
{
fatalError
()
}
animators
=
[
if
after
<=
0.001
{
MotionDefaultAnimator
<
MotionCoreAnimationViewContext
>
()
complete
(
isFinished
:
isFinished
)
]
return
if
#available(iOS 10, tvOS 10, *)
{
animators
.
append
(
MotionDefaultAnimator
<
MotionViewPropertyViewContext
>
())
}
for
v
in
animators
{
v
.
context
=
context
}
}
}
let
v
=
(
isFinished
?
elapsedTime
:
1
-
elapsedTime
)
*
totalDuration
self
.
isFinished
=
isFinished
/// Prepares the plugins.
self
.
currentAnimationDuration
=
after
+
v
func
preparePlugins
()
{
self
.
beginTime
=
CACurrentMediaTime
()
-
v
plugins
=
Motion
.
enabledPlugins
.
map
({
}
return
$0
.
init
()
})
func
complete
(
isFinished
:
Bool
)
{
guard
isTransitioning
else
{
fatalError
()
}
for
plugin
in
plugins
{
for
animator
in
animators
{
preprocessors
.
append
(
plugin
)
animator
.
clean
()
animators
.
append
(
plugin
)
}
}
}
transitionContainer
!.
isUserInteractionEnabled
=
true
let
completion
=
completionCallback
transitionPairs
=
nil
transitionObservers
=
nil
transitionContainer
=
nil
completionCallback
=
nil
container
=
nil
processors
=
nil
animators
=
nil
plugins
=
nil
context
=
nil
beginTime
=
nil
elapsedTime
=
0
totalDuration
=
0
completion
?(
isFinished
)
}
}
}
// MARK: Plugin Support
internal
extension
MotionController
{
internal
extension
MotionController
{
static
func
isEnabled
(
plugin
:
MotionPlugin
.
Type
)
->
Bool
{
/**
return
enabledPlugins
.
index
(
where
:
{
return
$0
==
plugin
})
!=
nil
Checks if a given plugin is enabled.
}
- Parameter plugin: A MotionPlugin.Type.
- Returns: A boolean indicating if the plugin is enabled or not.
static
func
enable
(
plugin
:
MotionPlugin
.
Type
)
{
*/
disable
(
plugin
:
plugin
)
static
func
isEnabled
(
plugin
:
MotionPlugin
.
Type
)
->
Bool
{
enabledPlugins
.
append
(
plugin
)
return
nil
!=
enabledPlugins
.
index
(
where
:
{
return
$0
==
plugin
})
}
}
/**
Enables a given plugin.
- Parameter plugin: A MotionPlugin.Type.
*/
static
func
enable
(
plugin
:
MotionPlugin
.
Type
)
{
disable
(
plugin
:
plugin
)
enabledPlugins
.
append
(
plugin
)
}
static
func
disable
(
plugin
:
MotionPlugin
.
Type
)
{
/**
if
let
index
=
enabledPlugins
.
index
(
where
:
{
return
$0
==
plugin
})
{
Disables a given plugin.
enabledPlugins
.
remove
(
at
:
index
)
- Parameter plugin: A MotionPlugin.Type.
*/
static
func
disable
(
plugin
:
MotionPlugin
.
Type
)
{
guard
let
index
=
enabledPlugins
.
index
(
where
:
{
return
$0
==
plugin
})
else
{
return
}
enabledPlugins
.
remove
(
at
:
index
)
}
}
}
}
}
internal
extension
MotionController
{
internal
extension
MotionController
{
// should call this after `prepareForTransition` & before `processContext`
// should call this after `prepareTransitionPairs` & before `processContext`
func
insert
<
T
>
(
preprocessor
:
MotionPreprocessor
,
before
:
T
.
Type
)
{
func
insert
<
T
>
(
preprocessor
:
MotionPreprocessor
,
before
:
T
.
Type
)
{
let
processorIndex
=
processors
.
index
{
let
v
=
preprocessors
.
index
{
$0
is
T
}
??
preprocessors
.
count
$0
is
T
preprocessor
.
context
=
context
}
??
processors
.
count
preprocessors
.
insert
(
preprocessor
,
at
:
v
)
preprocessor
.
context
=
context
}
processors
.
insert
(
preprocessor
,
at
:
processorIndex
)
}
}
}
Sources/MotionIndependentController.swift
View file @
3e422773
...
@@ -37,11 +37,11 @@ public class MotionIndependentController: MotionController {
...
@@ -37,11 +37,11 @@ public class MotionIndependentController: MotionController {
transitionContainer
=
rootView
transitionContainer
=
rootView
completionCallback
=
completion
completionCallback
=
completion
prepare
For
Transition
()
prepareTransition
()
context
.
defaultCoordinateSpace
=
.
sameParent
context
.
defaultCoordinateSpace
=
.
sameParent
context
.
set
(
fromViews
:
fromViews
,
toViews
:
toViews
)
context
.
set
(
fromViews
:
fromViews
,
toViews
:
toViews
)
processContext
()
processContext
()
prepare
ForAnimation
()
prepare
TransitionPairs
()
animate
()
animate
()
}
}
}
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment