0
votes

CornerRadius et Shadow sur un UIView avec @IBInspectable Swift 4.2

Est-il possible d'avoir à la fois CornerRaduis et une ombre sur un UIView ?

J'ai configuré une classe personnalisée pour un UIView qui utilise @IBInspectable pour définir un cornerRadius et un addShadow qui peut être true ou false code>. Lorsque je règle le cornerRadius , l'ombre ne s'affiche pas, si je retire le cornerRadius , il s'affiche à nouveau. Merci d'avance!

Classe personnalisée:

import UIKit

class CustomUIView: UIView {

    override func awakeFromNib() {
        self.layer.masksToBounds = cornerRadius > 0
    }

    @IBInspectable var useDefaultRadius: Bool = true {
        didSet {
            self.layer.masksToBounds = cornerRadius > 0
        }
    }

    @IBInspectable var cornerRadius: CGFloat {
        set {
            self.layer.cornerRadius = newValue

        }
        get {
            if (useDefaultRadius) {
                    // Set default radius
                    self.layer.cornerRadius = 23
                }

            return self.layer.cornerRadius
        }
    }

    @IBInspectable var addShadow:Bool = true{

        didSet(newValue) {
            if(newValue == true){
                self.layer.masksToBounds = false
                self.layer.shadowColor = UIColor.black.cgColor
                self.layer.shadowOpacity = 0.5
                self.layer.shadowOffset = CGSize(width: 2, height: 3)
                self.layer.shadowRadius = 3

                self.layer.shadowPath = UIBezierPath(rect: bounds).cgPath
                self.layer.shouldRasterize = true
                self.layer.rasterizationScale =  UIScreen.main.scale
                print("trying to use shadow")
            }
        }

    }


}


1 commentaires

Si ma réponse vous a aidé, veuillez l'accepter. car cela m'encourage à aider plus de gens.


3 Réponses :


1
votes

SET true code> maskstobounds code> in addshadow: bool code> ou vous n'avez pas besoin de définir maskstobounds dans Addshadow: BOOL DARTSET MODE

@IBInspectable var addShadow:Bool = true{

        didSet(newValue) {
            if(newValue == true){
                //self.layer.masksToBounds = false
                self.layer.masksToBounds = true
                self.layer.shadowColor = UIColor.black.cgColor
                self.layer.shadowOpacity = 0.5
                self.layer.shadowOffset = CGSize(width: 2, height: 3)
                self.layer.shadowRadius = 3

                self.layer.shadowPath = UIBezierPath(rect: bounds).cgPath
                self.layer.shouldRasterize = true
                self.layer.rasterizationScale =  UIScreen.main.scale
                print("trying to use shadow")
            }
        }

    }


7 commentaires

@MatthewMitchell: vous avez ajouté masksToBounds true pour les radios d'angle> 0 dans awakeFromNib alors supprimez cette ligne, votre code fonctionnera également


Toujours pas de travail, dès que j'ai mis un coin, le rayon de l'ombre disparaît


@MatthewMitchell J'ai mis à jour la réponse. Pouvez-vous essayer celui-ci


si je supprime ça, cornerRaduis cesse de fonctionner complètement


@MatthewMitchell Ok alors vous devez définir de vrais masksToBounds dans addShadow et suivre le lien donné


Le problème ici semble être que l'ombre est censée s'afficher en dehors des limites du calque, mais comme vous devez définir masksToBounds = true , l'ombre sera invisible (car elle est en dehors du masque). Vous pouvez créer une vue qui utilise un CAShapeLayer ( override static var layerClass: AnyClass {return CAShapeLayer.self} }, puis définir un chemin d'angle arrondi (à la fois comme chemin et comme shadowPath. Vous devez alors également remplacer backgoundColor pour obtenir / définir le fillColor du shapeLayer.


@Lutz: avez-vous suivi mes liens donnés



5
votes

Plutôt que de créer des classes personnalisées et de changer la classe d'uiview à chaque fois, je préfère l'étendre. J'y parviens en étendant UIView comme mentionné ci-dessous:

extension UIView {

    @IBInspectable
    var cornerRadius: CGFloat {
        get {
            return layer.cornerRadius
        }
        set {
            layer.cornerRadius = newValue
        }
    }

    @IBInspectable
    var borderWidth: CGFloat {
        get {
            return layer.borderWidth
        }
        set {
            layer.borderWidth = newValue
        }
    }

    @IBInspectable
    var borderColor: UIColor? {
        get {
            let color = UIColor.init(cgColor: layer.borderColor!)
            return color
        }
        set {
            layer.borderColor = newValue?.cgColor
        }
    }

    @IBInspectable
    var shadowRadius: CGFloat {
        get {
            return layer.shadowRadius
        }
        set {

            layer.shadowRadius = shadowRadius
        }
    }
    @IBInspectable
    var shadowOffset : CGSize{

        get{
            return layer.shadowOffset
        }set{

            layer.shadowOffset = newValue
        }
    }

    @IBInspectable
    var shadowColor : UIColor{
        get{
            return UIColor.init(cgColor: layer.shadowColor!)
        }
        set {
            layer.shadowColor = newValue.cgColor
        }
    }
    @IBInspectable
    var shadowOpacity : Float {

        get{
            return layer.shadowOpacity
        }
        set {

            layer.shadowOpacity = newValue

        }
    }        
}

Et définissez les propriétés dans le storyboard comme suit:

 entrez la description de l'image ici p>

C'est tout.

J'espère que cela vous aidera.


0 commentaires

0
votes

Voici l'astuce, vous devez définir true sur masksToBounds puis définir false sur masksToBounds avant d'ajouter une ombre code. vous pouvez vérifier cette méthode pour clarifier les choses:

func addShadow(color: UIColor, bottomOrTop: Bool = false, radius: CGFloat = 2, height: CGFloat = 3) {
        // These below line makes the trick to draw shadow with corner radius
        self.layer.masksToBounds = true
        self.layer.masksToBounds = false
        self.layer.shadowOffset = CGSize(width: height, height:  bottomOrTop ? height : height * -1)
        self.layer.shadowRadius = radius
        self.layer.shadowColor = color.cgColor
        self.layer.shadowOpacity = 0.3
    }


0 commentaires