Подтвердить что ты не робот

Добавление округленного угла и тени для UICollectionViewCell

Итак, я уже просматривал различные сообщения о добавлении второго представления для добавления тени, но я все равно не могу заставить его работать, если я хочу добавить его в UICollectionViewCell. Я подклассифицировал UICollectionViewCell, и вот мой код, где я добавляю различные элементы пользовательского интерфейса в представление содержимого ячейки и добавляю тень к слою:

[self.contentView setBackgroundColor:[UIColor whiteColor]];

self.layer.masksToBounds = NO;
self.layer.shadowOffset = CGSizeMake(0, 1);
self.layer.shadowRadius = 1.0;
self.layer.shadowColor = [UIColor blackColor].CGColor;
self.layer.shadowOpacity = 0.5;
[self.layer setShadowPath:[[UIBezierPath bezierPathWithRect:self.bounds] CGPath]];

Я хотел бы знать, как добавить округленный угол и тень к UICollectionViewCell.

4b9b3361

Ответ 1

Ни одно из этих решений не помогло мне. Если вы поместите все свои подпредставления в представление контента UICollectionViewCell, которым вы, вероятно, являетесь, вы можете установить тень на слое ячеек и границу на слое contentView для достижения обоих результатов.

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 blackColor].CGColor;
cell.layer.shadowOffset = CGSizeMake(0, 2.0f);
cell.layer.shadowRadius = 2.0f;
cell.layer.shadowOpacity = 0.5f;
cell.layer.masksToBounds = NO;
cell.layer.shadowPath = [UIBezierPath bezierPathWithRoundedRect:cell.bounds cornerRadius:cell.contentView.layer.cornerRadius].CGPath;

Swift 3.0

self.contentView.layer.cornerRadius = 2.0
self.contentView.layer.borderWidth = 1.0
self.contentView.layer.borderColor = UIColor.clear.cgColor
self.contentView.layer.masksToBounds = true

self.layer.shadowColor = UIColor.black.cgColor
self.layer.shadowOffset = CGSize(width: 0, height: 2.0)
self.layer.shadowRadius = 2.0
self.layer.shadowOpacity = 0.5
self.layer.masksToBounds = false
self.layer.shadowPath = UIBezierPath(roundedRect: self.bounds, cornerRadius: self.contentView.layer.cornerRadius).cgPath

Ответ 2

Версия Swift 3:

cell.contentView.layer.cornerRadius = 10
cell.contentView.layer.borderWidth = 1.0

cell.contentView.layer.borderColor = UIColor.clear.cgColor
cell.contentView.layer.masksToBounds = true

cell.layer.shadowColor = UIColor.gray.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

Ответ 3

В случае, если это помогает: Вот быстрое закругление углов:

cell.layer.cornerRadius = 10
cell.layer.masksToBounds = true

с ячейкой, являющейся переменной, управляющей ячейкой: часто вы будете использовать это в override func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) → UICollectionViewCell

Наслаждайтесь!

Ответ 4

Задайте атрибуты layer для ячейки, а не contentView.

CALayer * layer = [cell layer];
[layer setShadowOffset:CGSizeMake(0, 2)];
[layer setShadowRadius:1.0];
[layer setShadowColor:[UIColor redColor].CGColor] ;
[layer setShadowOpacity:0.5]; 
[layer setShadowPath:[[UIBezierPath bezierPathWithRect:cell.bounds] CGPath]];

Ответ 5

Вот решение Swift 4, обновленное, чтобы закруглить все углы, а не только верхние углы:

contentView.layer.cornerRadius = 6.0
contentView.layer.borderWidth = 1.0
contentView.layer.borderColor = UIColor.clear.cgColor
contentView.layer.masksToBounds = true

layer.shadowColor = UIColor.lightGray.cgColor
layer.shadowOffset = CGSize(width: 0, height: 2.0)
layer.shadowRadius = 6.0
layer.shadowOpacity = 1.0
layer.masksToBounds = false
layer.shadowPath = UIBezierPath(roundedRect: bounds, cornerRadius: contentView.layer.cornerRadius).cgPath
layer.backgroundColor = UIColor.clear.cgColor

Ответ 6

Вам просто нужно (a) установить cornerRadius и (b) установить shadowPath как закругленный прямоугольник с тем же радиусом, что и cornerRadius:

self.layer.cornerRadius = 10;
self.layer.shadowPath = [[UIBezierPath bezierPathWithRoundedRect:self.bounds cornerRadius:self.layer.cornerRadius] CGPath];

Ответ 7

Я должен был сделать небольшие изменения для Swift:

cell.contentView.layer.cornerRadius = 2.0;
cell.contentView.layer.borderWidth = 1.0;
cell.contentView.layer.borderColor = UIColor.clearColor().CGColor;
cell.contentView.layer.masksToBounds = true;

cell.layer.shadowColor = UIColor.grayColor().CGColor;
cell.layer.shadowOffset = CGSizeMake(0, 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;

Ответ 8

SWIFT 4.2

Нужно добавить это в вашей пользовательской ячейке или cellForItemAt: если вы используете cellForItemAt: подход замените себя → ячейка

        self.layer.cornerRadius = 10
        self.layer.borderWidth = 1.0
        self.layer.borderColor = UIColor.lightGray.cgColor

        self.layer.backgroundColor = UIColor.white.cgColor
        self.layer.shadowColor = UIColor.gray.cgColor
        self.layer.shadowOffset = CGSize(width: 2.0, height: 4.0)
        self.layer.shadowRadius = 2.0
        self.layer.shadowOpacity = 1.0
        self.layer.masksToBounds = false

Это даст вам ячейку с закругленной границей и падающей тенью.

Ответ 9

Этот работал для меня

cell.contentView.layer.cornerRadius = 5.0
cell.contentView.layer.borderColor = UIColor.gray.withAlphaComponent(0.5).cgColor
cell.contentView.layer.borderWidth = 0.5

let border = CALayer()
let width = CGFloat(2.0)
border.borderColor = UIColor.darkGray.cgColor
border.frame = CGRect(x: 0, y: cell.contentView.frame.size.height - width, width:  cell.contentView.frame.size.width, height: cell.contentView.frame.size.height)

border.borderWidth = width
cell.contentView.layer.addSublayer(border)
cell.contentView.layer.masksToBounds = true
cell.contentView.clipsToBounds = true

Ответ 10

Ответ Майка Сабатини работает нормально, если вы настраиваете свойства ячейки непосредственно в collectionView cellForItemAt, но если вы попытаетесь установить их в awakeFromNib() пользовательского подкласса UICollectionViewCell, у вас будет неправильный bezierPath, установленный на устройствах, которые не работают. не соответствует ширине и высоте, ранее установленным в раскадровке (IB).

Решением для меня было создать функцию внутри подкласса UICollectionViewCell и вызвать ее из cellForItemAt следующим образом:

func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
    if let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "cellID", for: indexPath) as? CustomCollectionViewCell{
        cell.configure())
        return cell
    }
    else {
        return UICollectionViewCell()
    }
}

И на CustomCollectionViewCell.swift:

class CustomCollectionViewCell: UICollectionViewCell{
    func configure() {
    contentView.layer.cornerRadius = 20
    contentView.layer.borderWidth = 1.0
    contentView.layer.borderColor = UIColor.clear.cgColor
    contentView.layer.masksToBounds = true
    layer.shadowColor = UIColor.black.cgColor
    layer.shadowOffset = CGSize(width: 0, height: 2.0)
    layer.shadowRadius = 2.0
    layer.shadowOpacity = 0.5
    layer.masksToBounds = false
    layer.shadowPath = UIBezierPath(roundedRect: bounds, cornerRadius: contentView.layer.cornerRadius).cgPath}
 }

Ответ 11

Вы можете установить цвет тени, радиус и смещение в методе UICollectionViewDataSource при создании UICollectionViewCell

cell.layer.shadowColor = UIColor.gray.cgColor
cell.layer.shadowOffset = CGSize(width: 0, height: 2.0)
cell.layer.shadowRadius = 1.0
cell.layer.shadowOpacity = 0.5
cell.layer.masksToBounds = false

Ответ 12

Если вы загружаете ячейку из xib, тогда awakeFromNib - это место, куда нужно поместить код.

class MyCollectionViewCell: UICollectionViewCell {
    override func awakeFromNib() {
        layer.cornerRadius = 7
        layer.masksToBounds = true
    }
}

Ответ 13

Вот мой ответ, близкий к остальным, но я добавляю угловой радиус к слою, иначе углы не будут заполняться правильно. Кроме того, это делает небольшое небольшое расширение для UICollectionViewCell.

extension UICollectionViewCell {
func shadowDecorate() {
    let radius: CGFloat = 10
    contentView.layer.cornerRadius = radius
    contentView.layer.borderWidth = 1
    contentView.layer.borderColor = UIColor.clear.cgColor
    contentView.layer.masksToBounds = true

    layer.shadowColor = UIColor.black.cgColor
    layer.shadowOffset = CGSize(width: 0, height: 1.0)
    layer.shadowRadius = 2.0
    layer.shadowOpacity = 0.5
    layer.masksToBounds = false
    layer.shadowPath = UIBezierPath(roundedRect: bounds, cornerRadius: radius).cgPath
    layer.cornerRadius = radius
}

}

Вы можете вызвать его в collectionView(_:cellForItemAt:) источника данных, как только удалите свою ячейку из очереди.

Ответ 14

Вот мое решение. Это похоже на другие ответы, с одним ключевым отличием. Это не создает путь, который зависит от границ представления. Каждый раз, когда вы создаете путь на основе границ и предоставляете его слою, вы можете столкнуться с проблемами при его изменении, и вам необходимо настроить методы для обновления пути.

Более простое решение - избегать использования всего, что зависит от границ.

let radius: CGFloat = 10

self.contentView.layer.cornerRadius = radius
// Always mask the inside view
self.contentView.layer.masksToBounds = true

self.layer.shadowColor = UIColor.black.cgColor
self.layer.shadowOffset = CGSize(width: 0, height: 1.0)
self.layer.shadowRadius = 3.0
self.layer.shadowOpacity = 0.5
// Never mask the shadow as it falls outside the view
self.layer.masksToBounds = false

// Matching the contentView radius here will keep the shadow
// in sync with the contentView rounded shape
self.layer.cornerRadius = radius

Теперь, когда когда-либо изменится размер ячеек, API представления сделает всю работу внутренне.