Skip to content

Commit

Permalink
Add method for ensuring image and animatedImage are mutually exclusiv…
Browse files Browse the repository at this point in the history
…e without needing to use TJAnimatedImageView.
  • Loading branch information
timonus committed Sep 15, 2022
1 parent ad09085 commit 4e886f4
Show file tree
Hide file tree
Showing 2 changed files with 48 additions and 8 deletions.
4 changes: 4 additions & 0 deletions UIImageView+AnimatedGIF.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,10 @@ NS_ASSUME_NONNULL_BEGIN

@interface UIImageView (AnimatedGIF)

/// Makes it so that setting @c image will implicitly unset @c animatedImage without the need for @c TJAnimatedImageView.
/// Note: Swizzles out @c -setImage: internally.
+ (void)tj_configureStillImageAnimatedImageMutualExclusivity;

/// Allows for playback of animated GIFs from data or URL inputs.
/// Prior to iOS 13 usage of this method will set a still image instead of an animated one.
@property (nonatomic, nullable) TJAnimatedImage *animatedImage;
Expand Down
52 changes: 44 additions & 8 deletions UIImageView+AnimatedGIF.m
Original file line number Diff line number Diff line change
Expand Up @@ -91,14 +91,41 @@ - (CGSize)size

static char *const kUIImageViewAnimatedGIFAnimatedImageKey = "kUIImageViewAnimatedGIFAnimatedImageKey";

#if defined(__has_attribute) && __has_attribute(objc_direct_members)
__attribute__((objc_direct_members))
#endif
@implementation UIImageView (AnimatedGIF)

static BOOL _tj_configuredStillImageAnimatedImageMutualExclusivity;

+ (void)tj_configureStillImageAnimatedImageMutualExclusivity
{
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
Class class = [self class];
SEL originalSelector = @selector(setImage:);
SEL swizzledSelector = @selector(_setImage:);
Method originalMethod = class_getInstanceMethod(class, originalSelector);
Method swizzledMethod = class_getInstanceMethod(class, swizzledSelector);
method_exchangeImplementations(originalMethod, swizzledMethod);
_tj_configuredStillImageAnimatedImageMutualExclusivity = YES;
});
}

- (void)_setImage:(UIImage *)image
{
if (_tj_configuredStillImageAnimatedImageMutualExclusivity) {
self.animatedImage = nil;
[self _setImage:image];
} else {
NSAssert(NO, @"%s is being invoked when %@ hasn't been called", __PRETTY_FUNCTION__, NSStringFromSelector(@selector(tj_configureStillImageAnimatedImageMutualExclusivity)));
}
}

- (void)_tj_setImageAnimated:(UIImage *const)image
{
[self setImage:image];
if (_tj_configuredStillImageAnimatedImageMutualExclusivity) {
[self _setImage:image];
} else {
[self setImage:image];
}
}

- (void)setAnimatedImage:(TJAnimatedImage *const)animatedImage
Expand Down Expand Up @@ -147,15 +174,24 @@ - (TJAnimatedImage *)animatedImage

@end

#if defined(__has_attribute) && __has_attribute(objc_direct_members)
__attribute__((objc_direct_members))
#endif
@implementation TJAnimatedImageView

- (void)setImage:(UIImage *)image
{
self.animatedImage = nil;
if (!_tj_configuredStillImageAnimatedImageMutualExclusivity) {
// UIImageView handles nil-ing out animatedImage if tj_configureStillImageAnimatedImageMutualExclusivity is called
self.animatedImage = nil;
}
[super setImage:image];
}

- (void)_tj_setImageAnimated:(UIImage *const)image
{
if (_tj_configuredStillImageAnimatedImageMutualExclusivity) {
[super _tj_setImageAnimated:image];
} else {
[super setImage:image];
}
}

@end

0 comments on commit 4e886f4

Please sign in to comment.