J'ai continué et personnalisé davantage willDisplayCell pour obtenir une meilleure simulation des styles de cellule dans l'application des paramètres.
Objectif c
- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
{
if ([cell respondsToSelector:@selector(tintColor)]) {
if (tableView == self.tableView) {
CGFloat cornerRadius = 5.f;
cell.backgroundColor = UIColor.clearColor;
CAShapeLayer *layer = [[CAShapeLayer alloc] init];
CGMutablePathRef pathRef = CGPathCreateMutable();
CGRect bounds = CGRectInset(cell.bounds, 10, 0);
BOOL addLine = NO;
if (indexPath.row == 0 && indexPath.row == [tableView numberOfRowsInSection:indexPath.section]-1) {
CGPathAddRoundedRect(pathRef, nil, bounds, cornerRadius, cornerRadius);
} else if (indexPath.row == 0) {
CGPathMoveToPoint(pathRef, nil, CGRectGetMinX(bounds), CGRectGetMaxY(bounds));
CGPathAddArcToPoint(pathRef, nil, CGRectGetMinX(bounds), CGRectGetMinY(bounds), CGRectGetMidX(bounds), CGRectGetMinY(bounds), cornerRadius);
CGPathAddArcToPoint(pathRef, nil, CGRectGetMaxX(bounds), CGRectGetMinY(bounds), CGRectGetMaxX(bounds), CGRectGetMidY(bounds), cornerRadius);
CGPathAddLineToPoint(pathRef, nil, CGRectGetMaxX(bounds), CGRectGetMaxY(bounds));
addLine = YES;
} else if (indexPath.row == [tableView numberOfRowsInSection:indexPath.section]-1) {
CGPathMoveToPoint(pathRef, nil, CGRectGetMinX(bounds), CGRectGetMinY(bounds));
CGPathAddArcToPoint(pathRef, nil, CGRectGetMinX(bounds), CGRectGetMaxY(bounds), CGRectGetMidX(bounds), CGRectGetMaxY(bounds), cornerRadius);
CGPathAddArcToPoint(pathRef, nil, CGRectGetMaxX(bounds), CGRectGetMaxY(bounds), CGRectGetMaxX(bounds), CGRectGetMidY(bounds), cornerRadius);
CGPathAddLineToPoint(pathRef, nil, CGRectGetMaxX(bounds), CGRectGetMinY(bounds));
} else {
CGPathAddRect(pathRef, nil, bounds);
addLine = YES;
}
layer.path = pathRef;
CFRelease(pathRef);
layer.fillColor = [UIColor colorWithWhite:1.f alpha:0.8f].CGColor;
if (addLine == YES) {
CALayer *lineLayer = [[CALayer alloc] init];
CGFloat lineHeight = (1.f / [UIScreen mainScreen].scale);
lineLayer.frame = CGRectMake(CGRectGetMinX(bounds)+10, bounds.size.height-lineHeight, bounds.size.width-10, lineHeight);
lineLayer.backgroundColor = tableView.separatorColor.CGColor;
[layer addSublayer:lineLayer];
}
UIView *testView = [[UIView alloc] initWithFrame:bounds];
[testView.layer insertSublayer:layer atIndex:0];
testView.backgroundColor = UIColor.clearColor;
cell.backgroundView = testView;
}
}
}
Rapide
override func tableView(tableView: UITableView, willDisplayCell cell: UITableViewCell, forRowAtIndexPath indexPath: NSIndexPath) {
if (cell.respondsToSelector(Selector("tintColor"))){
if (tableView == self.tableView) {
let cornerRadius : CGFloat = 12.0
cell.backgroundColor = UIColor.clearColor()
var layer: CAShapeLayer = CAShapeLayer()
var pathRef:CGMutablePathRef = CGPathCreateMutable()
var bounds: CGRect = CGRectInset(cell.bounds, 25, 0)
var addLine: Bool = false
if (indexPath.row == 0 && indexPath.row == tableView.numberOfRowsInSection(indexPath.section)-1) {
CGPathAddRoundedRect(pathRef, nil, bounds, cornerRadius, cornerRadius)
} else if (indexPath.row == 0) {
CGPathMoveToPoint(pathRef, nil, CGRectGetMinX(bounds), CGRectGetMaxY(bounds))
CGPathAddArcToPoint(pathRef, nil, CGRectGetMinX(bounds), CGRectGetMinY(bounds), CGRectGetMidX(bounds), CGRectGetMinY(bounds), cornerRadius)
CGPathAddArcToPoint(pathRef, nil, CGRectGetMaxX(bounds), CGRectGetMinY(bounds), CGRectGetMaxX(bounds), CGRectGetMidY(bounds), cornerRadius)
CGPathAddLineToPoint(pathRef, nil, CGRectGetMaxX(bounds), CGRectGetMaxY(bounds))
addLine = true
} else if (indexPath.row == tableView.numberOfRowsInSection(indexPath.section)-1) {
CGPathMoveToPoint(pathRef, nil, CGRectGetMinX(bounds), CGRectGetMinY(bounds))
CGPathAddArcToPoint(pathRef, nil, CGRectGetMinX(bounds), CGRectGetMaxY(bounds), CGRectGetMidX(bounds), CGRectGetMaxY(bounds), cornerRadius)
CGPathAddArcToPoint(pathRef, nil, CGRectGetMaxX(bounds), CGRectGetMaxY(bounds), CGRectGetMaxX(bounds), CGRectGetMidY(bounds), cornerRadius)
CGPathAddLineToPoint(pathRef, nil, CGRectGetMaxX(bounds), CGRectGetMinY(bounds))
} else {
CGPathAddRect(pathRef, nil, bounds)
addLine = true
}
layer.path = pathRef
layer.fillColor = UIColor(red: 255/255.0, green: 255/255.0, blue: 255/255.0, alpha: 0.8).CGColor
if (addLine == true) {
var lineLayer: CALayer = CALayer()
var lineHeight: CGFloat = (1.0 / UIScreen.mainScreen().scale)
lineLayer.frame = CGRectMake(CGRectGetMinX(bounds)+10, bounds.size.height-lineHeight, bounds.size.width-10, lineHeight)
lineLayer.backgroundColor = tableView.separatorColor.CGColor
layer.addSublayer(lineLayer)
}
var testView: UIView = UIView(frame: bounds)
testView.layer.insertSublayer(layer, atIndex: 0)
testView.backgroundColor = UIColor.clearColor()
cell.backgroundView = testView
}
}
}
Swift 3
func tableView(_ tableView: UITableView, willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath) {
let cornerRadius: CGFloat = 5
cell.backgroundColor = .clear
let layer = CAShapeLayer()
let pathRef = CGMutablePath()
let bounds = cell.bounds.insetBy(dx: 20, dy: 0)
var addLine = false
if indexPath.row == 0 && indexPath.row == tableView.numberOfRows(inSection: indexPath.section) - 1 {
pathRef.__addRoundedRect(transform: nil, rect: bounds, cornerWidth: cornerRadius, cornerHeight: cornerRadius)
} else if indexPath.row == 0 {
pathRef.move(to: .init(x: bounds.minX, y: bounds.maxY))
pathRef.addArc(tangent1End: .init(x: bounds.minX, y: bounds.minY), tangent2End: .init(x: bounds.midX, y: bounds.minY), radius: cornerRadius)
pathRef.addArc(tangent1End: .init(x: bounds.maxX, y: bounds.minY), tangent2End: .init(x: bounds.maxX, y: bounds.midY), radius: cornerRadius)
pathRef.addLine(to: .init(x: bounds.maxX, y: bounds.maxY))
addLine = true
} else if indexPath.row == tableView.numberOfRows(inSection: indexPath.section) - 1 {
pathRef.move(to: .init(x: bounds.minX, y: bounds.minY))
pathRef.addArc(tangent1End: .init(x: bounds.minX, y: bounds.maxY), tangent2End: .init(x: bounds.midX, y: bounds.maxY), radius: cornerRadius)
pathRef.addArc(tangent1End: .init(x: bounds.maxX, y: bounds.maxY), tangent2End: .init(x: bounds.maxX, y: bounds.midY), radius: cornerRadius)
pathRef.addLine(to: .init(x: bounds.maxX, y: bounds.minY))
} else {
pathRef.addRect(bounds)
addLine = true
}
layer.path = pathRef
layer.fillColor = UIColor(white: 1, alpha: 0.8).cgColor
if (addLine == true) {
let lineLayer = CALayer()
let lineHeight = 1.0 / UIScreen.main.scale
lineLayer.frame = CGRect(x: bounds.minX + 10, y: bounds.size.height - lineHeight, width: bounds.size.width - 10, height: lineHeight)
lineLayer.backgroundColor = tableView.separatorColor?.cgColor
layer.addSublayer(lineLayer)
}
let testView = UIView(frame: bounds)
testView.layer.insertSublayer(layer, at: 0)
testView.backgroundColor = .clear
cell.backgroundView = testView
}
Swift 4.2
override func tableView(_ tableView: UITableView, willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath) {
if (cell.responds(to: #selector(getter: UIView.tintColor))){
if tableView == self.tableView {
let cornerRadius: CGFloat = 12.0
cell.backgroundColor = .clear
let layer: CAShapeLayer = CAShapeLayer()
let path: CGMutablePath = CGMutablePath()
let bounds: CGRect = cell.bounds
bounds.insetBy(dx: 25.0, dy: 0.0)
var addLine: Bool = false
if indexPath.row == 0 && indexPath.row == ( tableView.numberOfRows(inSection: indexPath.section) - 1) {
path.addRoundedRect(in: bounds, cornerWidth: cornerRadius, cornerHeight: cornerRadius)
} else if indexPath.row == 0 {
path.move(to: CGPoint(x: bounds.minX, y: bounds.maxY))
path.addArc(tangent1End: CGPoint(x: bounds.minX, y: bounds.minY), tangent2End: CGPoint(x: bounds.midX, y: bounds.minY), radius: cornerRadius)
path.addArc(tangent1End: CGPoint(x: bounds.maxX, y: bounds.minY), tangent2End: CGPoint(x: bounds.maxX, y: bounds.midY), radius: cornerRadius)
path.addLine(to: CGPoint(x: bounds.maxX, y: bounds.maxY))
} else if indexPath.row == (tableView.numberOfRows(inSection: indexPath.section) - 1) {
path.move(to: CGPoint(x: bounds.minX, y: bounds.minY))
path.addArc(tangent1End: CGPoint(x: bounds.minX, y: bounds.maxY), tangent2End: CGPoint(x: bounds.midX, y: bounds.maxY), radius: cornerRadius)
path.addArc(tangent1End: CGPoint(x: bounds.maxX, y: bounds.maxY), tangent2End: CGPoint(x: bounds.maxX, y: bounds.midY), radius: cornerRadius)
path.addLine(to: CGPoint(x: bounds.maxX, y: bounds.minY))
} else {
path.addRect(bounds)
addLine = true
}
layer.path = path
layer.fillColor = UIColor.white.withAlphaComponent(0.8).cgColor
if addLine {
let lineLayer: CALayer = CALayer()
let lineHeight: CGFloat = 1.0 / UIScreen.main.scale
lineLayer.frame = CGRect(x: bounds.minX + 10.0, y: bounds.size.height - lineHeight, width: bounds.size.width, height: lineHeight)
lineLayer.backgroundColor = tableView.separatorColor?.cgColor
layer.addSublayer(lineLayer)
}
let testView: UIView = UIView(frame: bounds)
testView.layer.insertSublayer(layer, at: 0)
testView.backgroundColor = .clear
cell.backgroundView = testView
}
}
}
[UIBezierPath bezierPathWithRoundedRect:bounds byRoundingCorners:corner cornerRadii:cornerSize];
Dans iOS 13 et les versions ultérieures, ce style de tableau est enfin rendu disponible par Apple, sans avoir à le repenser, avec le nouveau style de vue de table UITableView.Style.insetGrouped .
Dans Xcode 11 et plus, cela peut être défini dans les paramètres du générateur d'interface pour la vue tableau, en sélectionnant Encart groupé pour le style:
la source
En répondant à @NarasimhaiahKolli, sur la façon dont j'ai défini la vue d'arrière-plan de la cellule pour que toute la cellule ne ressemble pas à une surbrillance. J'espère que cela t'aides.
la source
La réponse de @jvanmetre est excellente et cela fonctionne. S'appuyant sur cela et comme suggéré par @SergiySalyuk dans les commentaires. J'ai mis à jour le code pour utiliser UIBezierPath à la place, ce qui le rend plus simple à comprendre et légèrement plus rapide.
Ma version corrige également le bogue du séparateur et ajoute une vue d'arrière-plan sélectionnée qui correspond à la cellule.
N'oubliez pas de définir votre vue de table sur aucun séparateur:
tableView.separatorStyle = UITableViewCellSeparatorStyleNone;
Objectif c
la source
J'essayais d'obtenir le même aspect arrondi de l'application Paramètres sur les cellules de vue de la table. Ma réponse est également basée sur une réponse SO pour savoir comment définir cornerRadius uniquement pour le coin supérieur gauche et supérieur droit d'un UIView? .
la source
Après avoir essayé certaines des réponses ici, j'ai décidé de me lancer complètement et d'implémenter une sous-classe entière par-dessus
UITableView
etUITableViewCell
de reproduire le style de vue de tableau groupé arrondi dans iOS 7.https://github.com/TimOliver/TORoundedTableView
Cela a fini par être un processus très complexe:
layoutSubviews
dansUITableView
la Restructurer chaque cellule et vue accessoire afin qu'ils ne sont plus bord à bord.UITableViewCell
-classer afin de supprimer les vues de délimitation du séparateur supérieur et inférieur (mais en laissant celles à l'intérieur de la section intactes).UITableViewCell
vue d'arrière-plan personnalisée qui pourrait éventuellement avoir des coins arrondis en haut et en bas à utiliser pour les première et dernière cellules de chaque section. Ces éléments devaient êtreCALayer
pour éviterUITableView
le comportement implicite de changer la couleur des vues d'arrière-plan lorsqu'un utilisateur appuie sur la cellule.CALayer
instances qui ne répondent paslayoutSubviews
, j'ai ensuite dû faire quelques bricolages de Core Animation pour m'assurer que les cellules du haut et du bas sont redimensionnées à la même vitesse que les autres cellules lorsque l'utilisateur fait pivoter l'appareil.Dans l'ensemble, c'est possible de le faire, mais comme cela nécessite pas mal d'efforts et coûte un peu de performances (car il combat constamment le code d'Apple en essayant de tout remettre en place), il est préférable de déposer un radar auprès d'Apple pour leur demander exposer officiellement ce style. D'ici là, n'hésitez pas à utiliser ma bibliothèque. :)
la source
J'ai créé une méthode appelée
addRoundedCornersWithRadius:(CGFloat)radius ForCell:(UITableViewCell *)cell atIndexPath:(NSIndexPath *)indexPath
qui créera des coins arrondis en haut et en bas de chaque section.L'avantage d'utiliser la
maskView
propriété deUITableViewCell
est que lorsque vous sélectionnez la cellule, les coins arrondis sont toujours visibles.la source
Ma réponse est peut-être trop tardive mais pour la version Swift (toute), ce sera sûrement utile et très facile à utiliser.
PS: j'ai utilisé le code suivant pour Swift 3.0.
la source
code de travail pour swift ... ce que nous faisons en fait, c'est si la section n'a qu'une seule ligne, nous le faisons de tous les côtés, si la section a plusieurs lignes, nous le faisons en haut de la première ligne et en bas à la dernière ligne ... les propriétés BottomLeft, BottomRight, topLeft, TopRight doivent être de type rect corner (Suggestions de xcode lorsque vous tapez ... il y a un autre coin de contenu de propriété avec le même nom .. alors vérifiez que)
la source
J'ai peur qu'il ne semble pas y avoir de moyen facile de le faire. Vous devrez personnaliser votre UITableViewCell, quelque chose comme ça fonctionne:
Définissez le style de votre tableView sur grouped.
Définissez la couleur d'arrière-plan de TableView sur une couleur claire.
Sur votre -
(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)
clarifiez l'arrière-plan de la cellule et créez un UIView avec les coins arrondis souhaités comme arrière-plan. Quelque chose comme ça:Vous devrez peut-être peaufiner davantage, mais c'est l'idée principale.
la source
Je voulais réaliser la même chose mais avec une bordure autour de chaque section (ligne sous iOS6). Comme je n'ai pas trouvé de modification facile des solutions suggérées, j'ai proposé la mienne. C'est une modification de la réponse donnée par @Roberto Ferraz à ce sujet. J'ai créé une classe personnalisée qui hérite de UITableViewCell. J'y ai ajouté une vue de conteneur avec la taille appropriée (dans mon cas, rétrécie des deux côtés avec 15px). Que dans la classe, j'ai fait ceci:
Ensuite, dans votre source de données, procédez comme suit:
Et voila - vous avez des coins arrondis ET des bordures sur vos sections.
J'espère que cela t'aides!
PS J'ai fait quelques modifications car j'ai trouvé des bogues dans le code d'origine - principalement je n'ai pas défini toutes les valeurs dans tous les cas, ce qui provoque des effets très étonnants lorsque les cellules ont été réutilisées :)
la source
swift 4 Si vous souhaitez inclure également l'en-tête de section, essayez ci-dessous un
déclarer cornerLayerWidth comme variable globale
var cornerLayerWidth: CGFloat = 0,0
et
la source
Dans Swift 4.2:
Utiliser:
Si la cellule est la première d'un groupe, définissez
top = True
, s'il s'agit de la dernière cellulebottom = true
, si la cellule est la seule du groupe, définissez les deux surtrue
.Si vous voulez plus ou moins arrondi, changez simplement les radios de 10 à une autre valeur.
la source
Ce code définira des coins arrondis pour la vue du tableau entier au lieu d'une seule cellule.
Et effacez la couleur d'arrière-plan de chaque cellule dans cellForRow
la source
Ajoutez ceci pour supprimer la ligne supérieure de la vue de la table self.tableView.separatorStyle = UITableViewCellSeparatorStyleNone;
la source