Car la question que j'avais posée a été vu à plusieurs reprises, je vais donner une réponse détaillée. N'hésitez pas à modifier si vous voulez ajouter plus de contenu approprié.
D'abord un récapitulatif sur la question: le cadre, de limites et d'un centre et de leurs relations.
Cadre en vue de l' frame
(CGRect
) est la position de son rectangle en superview
's système de coordonnées. Par défaut, il commence en haut à gauche.
Les limites de vue de l' bounds
(CGRect
) exprime un point de vue rectangle dans son propre système de coordonnées.
Centre Une center
est CGPoint
exprimée en superview
's système de coordonnées, et elle détermine la position exacte du centre de la vue.
Prises de UIView + position de ces sont les liens (ils ne fonctionnent pas dans le code, car ils sont des équations) parmi les propriétés précédentes:
REMARQUE: Ces relations ne s'appliquent pas si les vues sont en rotation. Pour de plus amples informations, je vous suggère de prendre un coup d'oeil à l'image ci-dessous prise à partir Du Tiroir de la Cuisine basée sur Stanford CS193p cours. Crédits va à @Rhubarbe.
À l'aide de l' frame
permet de repositionner et/ou redimensionner une vue à l'intérieur de ses superview
. Généralement peut être utilisé à partir d'un superview
, par exemple, lorsque vous créez un spécifique de la sous-vue. Par exemple:
// view1 will be positioned at x = 30, y = 20 starting the top left corner of [self view]
// [self view] could be the view managed by a UIViewController
UIView* view1 = [[UIView alloc] initWithFrame:CGRectMake(30.0f, 20.0f, 400.0f, 400.0f)];
view1.backgroundColor = [UIColor redColor];
[[self view] addSubview:view1];
Lorsque vous avez besoin des coordonnées de dessin à l'intérieur d'un view
vous concernent habituellement bounds
. Un exemple typique pourrait être à dessiner dans un view
d'une sous-vue comme un encart de la première. Le dessin de la sous-vue nécessite de connaître le bounds
de la superview. Par exemple:
UIView* view1 = [[UIView alloc] initWithFrame:CGRectMake(50.0f, 50.0f, 400.0f, 400.0f)];
view1.backgroundColor = [UIColor redColor];
UIView* view2 = [[UIView alloc] initWithFrame:CGRectInset(view1.bounds, 20.0f, 20.0f)];
view2.backgroundColor = [UIColor yellowColor];
[view1 addSubview:view2];
Des comportements différents de se produire lorsque vous modifiez l' bounds
d'un point de vue.
Par exemple, si vous modifiez l' bounds
size
, frame
change (et vice versa). Le changement qui se passe autour de l' center
de la vue. Utilisez le code ci-dessous et voir ce qui se passe:
NSLog(@"Old Frame %@", NSStringFromCGRect(view2.frame));
NSLog(@"Old Center %@", NSStringFromCGPoint(view2.center));
CGRect frame = view2.bounds;
frame.size.height += 20.0f;
frame.size.width += 20.0f;
view2.bounds = frame;
NSLog(@"New Frame %@", NSStringFromCGRect(view2.frame));
NSLog(@"New Center %@", NSStringFromCGPoint(view2.center));
En outre, si vous modifiez bounds
origin
vous modifiez l' origin
de son système de coordonnées internes. Par défaut, l' origin
est (0.0, 0.0)
(coin supérieur gauche). Par exemple, si vous modifiez l' origin
pour view1
vous pouvez le voir (commentaire le code précédent si vous voulez) qui maintenant le coin en haut à gauche pour view2
touche l' view1
. La motivation est assez simple. Vous vous dites view1
que son coin supérieur gauche est maintenant à la position (20.0, 20.0)
mais depuis view2
s' frame
origin
commence à partir de (20.0, 20.0)
, ils coïncident.
CGRect frame = view1.bounds;
frame.origin.x += 20.0f;
frame.origin.y += 20.0f;
view1.bounds = frame;
L' origin
représente l' view
'à la position à l'intérieur de ses superview
mais décrit la position de l' bounds
center.
Enfin, bounds
et origin
ne sont pas des concepts connexes. Les deux permettent de dériver de l' frame
d'un point de vue (Voir équations précédentes).
Vue1 de l'étude de cas
Voici ce qui se passe lors de l'utilisation de l'extrait suivant.
UIView* view1 = [[UIView alloc] initWithFrame:CGRectMake(30.0f, 20.0f, 400.0f, 400.0f)];
view1.backgroundColor = [UIColor redColor];
[[self view] addSubview:view1];
NSLog(@"view1's frame is: %@", NSStringFromCGRect([view1 frame]));
NSLog(@"view1's bounds is: %@", NSStringFromCGRect([view1 bounds]));
NSLog(@"view1's center is: %@", NSStringFromCGPoint([view1 center]));
Le parent de l'image.
Ceci à la place qu'advient-il si je change d' [self view]
limites comme suit.
// previous code here...
CGRect rect = [[self view] bounds];
rect.origin.x += 30.0f;
rect.origin.y += 20.0f;
[[self view] setBounds:rect];
Le parent de l'image.
Ici, vous dites à l' [self view]
que son coin supérieur gauche est maintenant à la position (30.0, 20.0), mais depuis view1
'image d'origine commence à partir (30.0, 20.0), ils coïncident.
Références supplémentaires (pour la mise à jour avec d'autres références si vous le souhaitez)
À propos de clipsToBounds
(source Apple doc)
La définition de cette valeur YES causes sous-vues à être clipsé sur les limites
du récepteur. Si NON, les sous-vues dont les images s'étendre au-delà de la
visible limites du récepteur sont pas coupés. La valeur par défaut est
PAS de.
En d'autres termes, si une vue de l' frame
est (0, 0, 100, 100)
et de ses sous-vue est - (90, 90, 30, 30)
, vous ne voyez qu'une partie de la sous-vue. Le dernier de ne pas dépasser les limites de la vue parent.
masksToBounds
est équivalent à clipsToBounds
. Au lieu d'un UIView
, cette propriété est appliquée à un CALayer
. Sous le capot, clipsToBounds
des appels masksToBounds
. Pour plus de références de prendre un coup d'oeil à Comment la relation entre UIView de clipsToBounds et CALayer de masksToBounds?.