Plutôt que de créer deux UIImageViews
, il semble logique de simplement modifier le image
d'une vue. Si je le fais, existe-t-il un fondu / fondu qui se dissolve entre les deux images plutôt qu'un changement instantané?
Réponses
Trop de publicités?Il peut être beaucoup plus simple en utilisant les méthodes nouvelles basé sur des blocs, UIKit animation.
Supposons que le code suivant est dans le contrôleur de vue, et le UIImageView vous voulez fondu enchaîné est une sous-vue de self.view adressable via la propriété self.imageView. Puis, tout ce dont vous avez besoin est :
Fait.
Et pour ce faire à Swift, c’est comme si :
Edit: il y a une meilleure solution de @algues ci-dessous.
Une autre façon de le faire est en utilisant les CAAnimation transitions:
CATransition *transition = [CATransition animation];
transition.duration = 0.25;
transition.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
transition.type = kCATransitionFade;
transition.delegate = self;
[self.view.layer addAnimation:transition forKey:nil];
view1.hidden = YES;
view2.hidden = NO;
Voir le point de Vue des Transitions exemple de projet à partir d'Apple: http://developer.apple.com/library/ios/#samplecode/ViewTransitions/Introduction/Intro.html#//apple_ref/doc/uid/DTS40007411
Oui, ce que vous dites est absolument correct et c'est le moyen de le faire. J'ai écrit cette méthode et je l'utilise toujours pour fondre mon image. Je traite avec CALayer
pour cela. Vous devez importer Core Animation pour cela.
+ (void)fadeInLayer:(CALayer *)l
{
CABasicAnimation *fadeInAnimate = [CABasicAnimation animationWithKeyPath:@"opacity"];
fadeInAnimate.duration = 0.5;
fadeInAnimate.repeatCount = 1;
fadeInAnimate.autoreverses = NO;
fadeInAnimate.fromValue = [NSNumber numberWithFloat:0.0];
fadeInAnimate.toValue = [NSNumber numberWithFloat:1.0];
fadeInAnimate.removedOnCompletion = YES;
[l addAnimation:fadeInAnimate forKey:@"animateOpacity"];
return;
}
Vous pouvez faire le contraire pour Fade out une image. Après qu'il s'estompe. Vous venez de le supprimer de superview (qui est UIImageView
). [imageView removeFromSuperview]
.
Vous pouvez également forfait le fondu d'entrée en fonction dans une sous-classe, de sorte que vous pouvez ensuite l'utiliser comme une commune UIImageView, comme dans l'exemple suivant:
IMMFadeImageView *fiv=[[IMMFadeImageView alloc] initWithFrame:CGRectMake(10, 10, 50, 50)];
[self.view addSubview:fiv];
fiv.image=[UIImage imageNamed:@"initialImage.png"];
fiv.image=[UIImage imageNamed:@"fadeinImage.png"]; // fades in
Une mise en œuvre possible de la façon suivante.
Remarque: la façon dont vous avez réellement mettre en œuvre le fondu dans l' setImage:
fonction peut modifier, et pourrait être l'un de l'autre d'excellents exemples décrits dans les autres réponses à cette question - de créer une autre à la volée UIImageView
comme je le fais ici pourrait être inacceptable pour les frais généraux de votre situation spécifique.
IMMFadeImageView.h :
#import <UIKit/UIKit.h>
@interface IMMFadeImageView : UIImageView
@property (nonatomic,assign) float fadeDuration;
@end
IMMFadeImageView.m :
#import "IMMFadeImageView.h"
@implementation IMMFadeImageView
@synthesize fadeDuration;
- (id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
self.fadeDuration=1;
}
return self;
}
-(void)setImage:(UIImage *)newImage{
if(!self.image||self.fadeDuration<=0){
super.image=newImage;
} else {
UIImageView *iv=[[UIImageView alloc] initWithFrame:self.bounds];
iv.contentMode=self.contentMode;
iv.image=super.image;
iv.alpha=1;
[self addSubview:iv];
super.image=newImage;
[UIView animateWithDuration:self.fadeDuration delay:0 options:UIViewAnimationCurveEaseInOut animations:^{
iv.alpha=0;
} completion:^(BOOL finished) {
[iv removeFromSuperview];
}];
}
}
Le code ci-dessus repose sur quelques hypothèses (y compris l'ARC d'être activé dans votre projet XCode), est destiné à être utilisé comme une preuve de concept, et dans l'intérêt de la clarté et de la précision, il reste pertinent en omettant importants sans rapport avec le code. Merci de ne pas juste le copier-coller à l'aveuglette.
J'avais besoin de la transition pour répéter indéfiniment. Il a fallu beaucoup d'essais et d'erreurs pour celui-ci mais j'ai finalement obtenu le résultat final que je cherchais. Ce sont des extraits de code pour ajouter une animation d'image à un UIImageView dans un UITableViewCell.
Voici le code correspondant:
@interface SomeViewController ()
@property(nonatomic, strong) NSMutableArray *imagesArray;
@property(nonatomic, assign) NSInteger varietyImageAnimationIndex;
@property(nonatomic, assign) BOOL varietyImagesAnimated;
@end
@implementation SomeViewController
@synthesize imagesArray;
@synthesize varietyImageAnimationIndex;
@synthesize varietyImagesAnimated;
...
// NOTE: Initialize the array of images in perhaps viewDidLoad method.
-(void)animateImages
{
varietyImageAnimationIndex++;
[UIView transitionWithView:varietyImageView
duration:2.0f
options:UIViewAnimationOptionTransitionCrossDissolve
animations:^{
varietyImageView.image = [imagesArray objectAtIndex:varietyImageAnimationIndex % [imagesArray count]];
} completion:^(BOOL finished) {
[self animateImages];
}];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
...
[cell.imageView setImage:[imagesArray objectAtIndex:0]];
[self setVarietyImageView:cell.imageView];
if (! varietyImagesAnimated)
{
varietyImagesAnimated = YES;
[self animateImages];
}
...
return cell;
}