Je veux que mes UICollectionViewCells aient des coins arrondis et des ombres portées mais j'ai rencontré un problème où il semble que je ne peux avoir que l'un ou l'autre, mais pas les deux.
Pour contourner les coins, j'utilise ce code dans l'initialisation de la cellule:
CALayer *layer = [self layer];
[layer setCornerRadius:4];
[layer setRasterizationScale:[[UIScreen mainScreen] scale]];
[layer setShouldRasterize:YES];
Pour ajouter simplement une ombre portée, j'utilise ce code dans l'initialisation de la cellule:
CALayer *layer = [self layer];
[layer setMasksToBounds:NO];
[layer setRasterizationScale:[[UIScreen mainScreen] scale]];
[layer setShouldRasterize:YES];
[layer setShadowColor:[[UIColor blackColor] CGColor]];
[layer setShadowOffset:CGSizeMake(0.0f,0.5f)];
[layer setShadowRadius:8.0f];
[layer setShadowOpacity:0.2f];
[layer setShadowPath:[[UIBezierPath bezierPathWithRoundedRect:self.bounds cornerRadius:layer.cornerRadius] CGPath]];
Pour essayer d'avoir des coins arrondis et une ombre portée j'utilise ce code dans l'initialisation de la cellule:
CALayer *layer = [self layer];
[layer setMasksToBounds:NO];
[layer setCornerRadius:4];
[layer setRasterizationScale:[[UIScreen mainScreen] scale]];
[layer setShouldRasterize:YES];
[layer setShadowColor:[[UIColor blackColor] CGColor]];
[layer setShadowOffset:CGSizeMake(0.0f,0.5f)];
[layer setShadowRadius:8.0f];
[layer setShadowOpacity:0.2f];
[layer setShadowPath:[[UIBezierPath bezierPathWithRoundedRect:self.bounds cornerRadius:layer.cornerRadius] CGPath]];
mais cela se traduit par l'ombre portée uniquement.
Est-ce un bug ou est-ce que je fais quelque chose de mal?
Fonctionne très bien pour moi:
-(UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
...
cell.layer.masksToBounds = YES;
cell.layer.cornerRadius = 6;
...
return cell;
}
Si vous placez toutes vos sous-vues dans la vue de contenu UICollectionViewCell
, ce que vous êtes probablement, vous pouvez définir l'ombre sur le calque de la cellule et la bordure sur le calque contentView
pour obtenir les deux résultats.
cell.contentView.layer.cornerRadius = 2.0f;
cell.contentView.layer.borderWidth = 1.0f;
cell.contentView.layer.borderColor = [UIColor clearColor].CGColor;
cell.contentView.layer.masksToBounds = YES;
cell.layer.shadowColor = [UIColor lightGrayColor].CGColor;
cell.layer.shadowOffset = CGSizeMake(0, 2.0f);
cell.layer.shadowRadius = 2.0f;
cell.layer.shadowOpacity = 1.0f;
cell.layer.masksToBounds = NO;
cell.layer.shadowPath = [UIBezierPath bezierPathWithRoundedRect:cell.bounds cornerRadius:cell.contentView.layer.cornerRadius].CGPath;
cell.contentView.layer.cornerRadius = 2.0
cell.contentView.layer.borderWidth = 1.0
cell.contentView.layer.borderColor = UIColor.clear.cgColor
cell.contentView.layer.masksToBounds = true
cell.layer.shadowColor = UIColor.lightGray.cgColor
cell.layer.shadowOffset = CGSize(width: 0, height: 2.0)
cell.layer.shadowRadius = 2.0
cell.layer.shadowOpacity = 1.0
cell.layer.masksToBounds = false
cell.layer.shadowPath = UIBezierPath(roundedRect: cell.bounds, cornerRadius: cell.contentView.layer.cornerRadius).cgPath
Je pense avoir rencontré un problème similaire. Mon problème était que l'écrêtage dans mes sous-vues du UICollectionViewCell
ne fonctionnait pas correctement avec les ombres et les bordures arrondies. Le même code fonctionnait très bien avant quand j'avais cette vue (en tant que sous-classe UIView
standard) dans un UIScrollView
.
Donc, pour faire court, j'ai déplacé toute cette configuration de initWithCoder
vers un endroit ultérieur après l'avoir obtenue de -dequeueReusableCellWithReuseIdentifier:forIndexPath:
. Résolu le problème pour moi. On dirait que UICollectionViews
fait quelque chose que je ne m'attendrais pas aux couches de leurs cellules à un moment donné?
Il y a un moment délicat. Couper les coins et déposer l'ombre est une fonction mutuellement exclusive dans une seule couche. La suppression de l'ombre est un processus d'extension de cadre, mais les coins sont le processus de masquage aux limites.
La solution est en séparation de fonctions. Je recommande de configurer l'ombre pour le calque de cellule, mais de couper les coins pour le calque contentView de cette cellule.
Si vous utilisez une sous-classe pour créer la collection, assurez-vous simplement de procéder comme suit.
CALayer *layer = [self layer];
[layer setCornerRadius:_cornerRadius];
[layer setRasterizationScale:[[UIScreen mainScreen] scale]];
[layer setShouldRasterize:YES];
[layer setShadowColor:[[UIColor blackColor] CGColor]];
[layer setShadowOffset:CGSizeMake(0.0,4.0)];
[layer setShadowRadius:6.0f];
[layer setShadowOpacity:0.25];
[layer setShadowPath:[[UIBezierPath bezierPathWithRoundedRect:self.bounds cornerRadius:layer.cornerRadius] CGPath]];
self.contentView.layer.cornerRadius = _cornerRadius;
self.contentView.layer.borderWidth= _borderWidth;
self.contentView.layer.borderColor = _borderColor.CGColor;
self.contentView.backgroundColor = [UIColor whiteColor];
self.backgroundColor = [UIColor clearColor];
fonctionne comme un charme.