Skip to content
This repository has been archived by the owner on Aug 30, 2023. It is now read-only.

Commit

Permalink
Add support for copying animation traits. (#30)
Browse files Browse the repository at this point in the history
  • Loading branch information
jverkoey committed Dec 12, 2017
1 parent 4f74d24 commit f7fb095
Show file tree
Hide file tree
Showing 11 changed files with 76 additions and 6 deletions.
2 changes: 1 addition & 1 deletion src/MDMAnimationTraits.h
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@
/**
A generic representation of animation traits.
*/
@interface MDMAnimationTraits: NSObject
@interface MDMAnimationTraits: NSObject <NSCopying>

/**
Initializes the instance with the provided duration and kCAMediaTimingFunctionEaseInEaseOut timing
Expand Down
9 changes: 9 additions & 0 deletions src/MDMAnimationTraits.m
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,15 @@ - (instancetype)initWithDelay:(NSTimeInterval)delay
return self;
}

#pragma mark - NSCopying

- (id)copyWithZone:(NSZone *)zone {
return [[[self class] alloc] initWithDelay:self.delay
duration:self.duration
timingCurve:[self.timingCurve copyWithZone:zone]
repetition:[self.repetition copyWithZone:zone]];
}

@end

@implementation MDMAnimationTraits (SystemTraits)
Expand Down
2 changes: 1 addition & 1 deletion src/MDMRepetition.h
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
/**
Represents repetition that repeats a specific number of times.
*/
@interface MDMRepetition: NSObject <MDMRepetitionTraits>
@interface MDMRepetition: NSObject <NSCopying, MDMRepetitionTraits>

/**
Initializes the instance with the given number of repetitions.
Expand Down
7 changes: 7 additions & 0 deletions src/MDMRepetition.m
Original file line number Diff line number Diff line change
Expand Up @@ -39,5 +39,12 @@ - (instancetype)initWithNumberOfRepetitions:(double)numberOfRepetitions
return self;
}

#pragma mark - NSCopying

- (id)copyWithZone:(__unused NSZone *)zone {
return [[[self class] alloc] initWithNumberOfRepetitions:self.numberOfRepetitions
autoreverses:self.autoreverses];
}

@end

2 changes: 1 addition & 1 deletion src/MDMRepetitionOverTime.h
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
/**
Represents repetition that repeats until a specific duration has passed.
*/
@interface MDMRepetitionOverTime: NSObject <MDMRepetitionTraits>
@interface MDMRepetitionOverTime: NSObject <NSCopying, MDMRepetitionTraits>

/**
Initializes the instance with the given duration.
Expand Down
6 changes: 6 additions & 0 deletions src/MDMRepetitionOverTime.m
Original file line number Diff line number Diff line change
Expand Up @@ -38,5 +38,11 @@ - (instancetype)initWithDuration:(double)duration autoreverses:(BOOL)autoreverse
return self;
}

#pragma mark - NSCopying

- (id)copyWithZone:(__unused NSZone *)zone {
return [[[self class] alloc] initWithDuration:self.duration autoreverses:self.autoreverses];
}

@end

2 changes: 1 addition & 1 deletion src/MDMRepetitionTraits.h
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
/**
A generalized representation of a repetition traits.
*/
@protocol MDMRepetitionTraits <NSObject>
@protocol MDMRepetitionTraits <NSObject, NSCopying>

/**
Whether the animation should animate backwards after animating forwards.
Expand Down
2 changes: 1 addition & 1 deletion src/MDMSpringTimingCurve.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@
/**
A timing curve that represents the motion of a single-dimensional attached spring.
*/
@interface MDMSpringTimingCurve: NSObject <MDMTimingCurve>
@interface MDMSpringTimingCurve: NSObject <NSCopying, MDMTimingCurve>

/**
Initializes the timing curve with the given parameters and an initial velocity of zero.
Expand Down
14 changes: 14 additions & 0 deletions src/MDMSpringTimingCurve.m
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,20 @@ - (void)setInitialVelocity:(CGFloat)initialVelocity {
_coefficientsAreInvalid = YES;
}

#pragma mark - NSCopying

- (id)copyWithZone:(NSZone *)zone {
MDMSpringTimingCurve *copy =
[[[self class] allocWithZone:zone] initWithMass:self.mass
tension:self.tension
friction:self.friction
initialVelocity:self.initialVelocity];
copy->_coefficientsAreInvalid = _coefficientsAreInvalid;
copy->_duration = _duration;
copy->_dampingRatio = _dampingRatio;
return copy;
}

#pragma mark - Private

- (void)recalculateCoefficientsIfNeeded {
Expand Down
2 changes: 1 addition & 1 deletion src/MDMTimingCurve.h
Original file line number Diff line number Diff line change
Expand Up @@ -20,5 +20,5 @@
/**
A generalized representation of a timing curve.
*/
@protocol MDMTimingCurve <NSObject>
@protocol MDMTimingCurve <NSObject, NSCopying>
@end
34 changes: 34 additions & 0 deletions tests/unit/MDMAnimationTraitsTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -126,4 +126,38 @@ class MDMAnimationTraitsTests: XCTestCase {
XCTAssertEqual(setRepetition.autoreverses, repetition.autoreverses)
}
}

func testModifyingACopyDoesNotModifyTheOriginal() {
let spring = MDMSpringTimingCurve(mass: 0.7, tension: 0.8, friction: 0.9)
let repetition = MDMRepetition(numberOfRepetitions: 5)
let traits = MDMAnimationTraits(delay: 0.2,
duration: 0.5,
timingCurve: spring,
repetition: repetition)

let copy = traits.copy() as! MDMAnimationTraits
copy.delay = copy.delay + 1
copy.duration = copy.duration + 1
if let springCopy = copy.timingCurve as? MDMSpringTimingCurve {
springCopy.friction = springCopy.friction + 1
springCopy.tension = springCopy.tension + 1
springCopy.mass = springCopy.mass + 1
springCopy.initialVelocity = springCopy.initialVelocity + 1

XCTAssertNotEqualWithAccuracy(springCopy.friction, spring.friction, 0.001)
XCTAssertNotEqualWithAccuracy(springCopy.tension, spring.tension, 0.001)
XCTAssertNotEqualWithAccuracy(springCopy.mass, spring.mass, 0.001)
XCTAssertNotEqualWithAccuracy(springCopy.initialVelocity, spring.initialVelocity, 0.001)
}
if let repetitionCopy = copy.repetition as? MDMRepetition {
repetitionCopy.autoreverses = !repetitionCopy.autoreverses
repetitionCopy.numberOfRepetitions = repetitionCopy.numberOfRepetitions + 1

XCTAssertNotEqual(repetitionCopy.autoreverses, repetition.autoreverses)
XCTAssertNotEqual(repetitionCopy.numberOfRepetitions, repetition.numberOfRepetitions)
}

XCTAssertNotEqualWithAccuracy(copy.duration, traits.duration, 0.001)
XCTAssertNotEqualWithAccuracy(copy.delay, traits.delay, 0.001)
}
}

0 comments on commit f7fb095

Please sign in to comment.