首页 文章

向我的UIView添加投影的最佳方法是什么

提问于
浏览
102

我试图为彼此叠加的视图添加一个投影,视图崩溃允许其他视图中的内容被看到,在这种情况下我想保持 view.clipsToBounds ON,这样当视图崩溃时,他们的内容被剪裁 .

这似乎让我很难为图层添加阴影,因为当我转动 clipsToBounds 时,阴影也会被剪裁 .

我一直试图操纵 view.frameview.bounds 以便为帧添加一个投影,但允许边界足够大以包含它,但是我没有运气 .

这是我用来添加阴影的代码(这仅适用于 clipsToBounds OFF,如图所示)

view.clipsToBounds = NO;
view.layer.shadowColor = [[UIColor blackColor] CGColor];
view.layer.shadowOffset = CGSizeMake(0,5);
view.layer.shadowOpacity = 0.5;

以下是应用于最轻的灰色层的阴影的屏幕截图 . 希望这能让我了解如果 clipsToBounds 为OFF,我的内容将如何重叠 .

Shadow Application.

如何为我的_3023801添加阴影并保持我的内容被剪裁?

编辑:只是想补充说我还使用了带阴影的背景图像,这确实很有效,但是我仍然想知道最好的编码解决方案 .

6 回答

  • 62

    试试这个:

    UIBezierPath *shadowPath = [UIBezierPath bezierPathWithRect:view.bounds];
    view.layer.masksToBounds = NO;
    view.layer.shadowColor = [UIColor blackColor].CGColor;
    view.layer.shadowOffset = CGSizeMake(0.0f, 5.0f);
    view.layer.shadowOpacity = 0.5f;
    view.layer.shadowPath = shadowPath.CGPath;
    

    First of all :用作 shadowPathUIBezierPath 至关重要 . 如果你没有't use it, you might not notice a difference at first, but the keen eye will observe a certain lag occurring during events like rotating the device and/or similar. It'进行重要的性能调整 .

    Regarding your issue specifically :重要的一行是 view.layer.masksToBounds = NO . 它禁用视图's layer's子图层的剪切,这些子图层比视图的边界延伸得更远 .

    对于那些想知道 masksToBounds (在图层上)和视图自己的 clipToBounds 属性之间的区别是:实际上并没有 . 切换一个会影响另一个 . 只是一个不同的抽象层次 .


    Swift 2.2:

    override func layoutSubviews()
    {
        super.layoutSubviews()
    
        let shadowPath = UIBezierPath(rect: bounds)
        layer.masksToBounds = false
        layer.shadowColor = UIColor.blackColor().CGColor
        layer.shadowOffset = CGSizeMake(0.0, 5.0)
        layer.shadowOpacity = 0.5
        layer.shadowPath = shadowPath.CGPath
    }
    

    斯威夫特3:

    override func layoutSubviews()
    {
        super.layoutSubviews()
    
        let shadowPath = UIBezierPath(rect: bounds)
        layer.masksToBounds = false
        layer.shadowColor = UIColor.black.cgColor
        layer.shadowOffset = CGSize(width: 0.0, height: 5.0)
        layer.shadowOpacity = 0.5
        layer.shadowPath = shadowPath.cgPath
    }
    
  • 13

    Wasabii在Swift 2.3中的回答:

    let shadowPath = UIBezierPath(rect: view.bounds)
        view.layer.masksToBounds = false
        view.layer.shadowColor = UIColor.blackColor().CGColor
        view.layer.shadowOffset = CGSize(width: 0, height: 0.5)
        view.layer.shadowOpacity = 0.2
        view.layer.shadowPath = shadowPath.CGPath
    

    在Swift 3/4中:

    let shadowPath = UIBezierPath(rect: view.bounds)
        view.layer.masksToBounds = false
        view.layer.shadowColor = UIColor.black.cgColor
        view.layer.shadowOffset = CGSize(width: 0, height: 0.5)
        view.layer.shadowOpacity = 0.2
        view.layer.shadowPath = shadowPath.cgPath
    

    如果您正在使用AutoLayout,请将此代码放在layoutSubviews()中 .

  • 265

    诀窍是正确定义视图层的 masksToBounds 属性:

    view.layer.masksToBounds = NO;
    

    它应该工作 .

    Source

  • 13

    您可以为UIView创建扩展,以在设计编辑器中访问这些值

    Shadow options in design editor

    extension UIView{
    
        @IBInspectable var shadowOffset: CGSize{
            get{
                return self.layer.shadowOffset
            }
            set{
                self.layer.shadowOffset = newValue
            }
        }
    
        @IBInspectable var shadowColor: UIColor{
            get{
                return UIColor(cgColor: self.layer.shadowColor!)
            }
            set{
                self.layer.shadowColor = newValue.cgColor
            }
        }
    
        @IBInspectable var shadowRadius: CGFloat{
            get{
                return self.layer.shadowRadius
            }
            set{
                self.layer.shadowRadius = newValue
            }
        }
    
        @IBInspectable var shadowOpacity: Float{
            get{
                return self.layer.shadowOpacity
            }
            set{
                self.layer.shadowOpacity = newValue
            }
        }
    }
    
  • 1

    您也可以从故事板为视图设置阴影

    enter image description here

  • 6

    在viewWillLayoutSubviews上:

    override func viewWillLayoutSubviews() {
        sampleView.layer.masksToBounds =  false
        sampleView.layer.shadowColor = UIColor.darkGrayColor().CGColor;
        sampleView.layer.shadowOffset = CGSizeMake(2.0, 2.0)
        sampleView.layer.shadowOpacity = 1.0
    }
    

    使用UIView的扩展:

    extension UIView {
    
        func addDropShadowToView(targetView:UIView? ){
            targetView!.layer.masksToBounds =  false
            targetView!.layer.shadowColor = UIColor.darkGrayColor().CGColor;
            targetView!.layer.shadowOffset = CGSizeMake(2.0, 2.0)
            targetView!.layer.shadowOpacity = 1.0
        }
    }
    

    用法:

    sampleView.addDropShadowToView(sampleView)
    

相关问题