You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

iOS开发:如何实现除指定Stack View外全屏模糊(键盘适配场景)

问题

我想实现除指定Stack View外,整个屏幕都模糊的效果。当前App在键盘弹出时,Stack View里的文本输入框会上移,我还想给这个Stack View加个模糊背景。

我试了这段代码:

let blurEffect = UIBlurEffect(style: .prominent)
blurEffectView = UIVisualEffectView(effect: blurEffect)
blurEffectView.frame = view.bounds 
view.addSubview(blurEffectView)

但运行后连文本输入框也被模糊了。相关场景截图:

  • App启动状态:App启动状态
  • 点击文本输入框后:点击文本输入框后的状态
  • 层级结构:视图层级结构
解决方案

要实现「除Stack View外全屏模糊+给Stack View加模糊背景」的效果,需从视图层级和模糊视图的添加方式两方面调整:

1. 实现全屏模糊(排除Stack View)

你当前的问题是把模糊视图直接加到最外层view上,覆盖了所有子视图(包括Stack View)。正确做法是将模糊视图放在Stack View的下方:

// 创建模糊视图
let blurEffect = UIBlurEffect(style: .prominent)
let blurEffectView = UIVisualEffectView(effect: blurEffect)
blurEffectView.frame = view.bounds
// 适配屏幕旋转或尺寸变化
blurEffectView.autoresizingMask = [.flexibleWidth, .flexibleHeight]

// 添加到view的最底层,让Stack View在它上方显示
view.insertSubview(blurEffectView, at: 0)

如果还有其他需要显示在模糊层上的元素,只需确保它们的视图层级高于模糊视图即可。

2. 给Stack View添加模糊背景

要给Stack View单独加模糊背景,需将模糊视图作为Stack View的子视图并放在最底层,同时设置Stack View背景透明:

// 创建Stack View的模糊背景,可选更柔和的模糊样式
let stackBlurEffect = UIBlurEffect(style: .systemUltraThinMaterial)
let stackBlurView = UIVisualEffectView(effect: stackBlurEffect)
stackBlurView.frame = stackView.bounds
stackBlurView.autoresizingMask = [.flexibleWidth, .flexibleHeight]

// 把模糊背景加到Stack View的最底层
stackView.insertSubview(stackBlurView, at: 0)
// 确保Stack View本身背景透明,让模糊背景显示出来
stackView.backgroundColor = .clear

3. 适配键盘弹出时的布局

键盘弹出时Stack View会上移,需监听键盘通知来更新模糊视图的frame:

// 在viewDidLoad中添加键盘通知监听
override func viewDidLoad() {
    super.viewDidLoad()
    NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillChangeFrame(_:)), name: UIResponder.keyboardWillChangeFrameNotification, object: nil)
}

// 处理键盘尺寸变化的方法
@objc func keyboardWillChangeFrame(_ notification: Notification) {
    guard let userInfo = notification.userInfo,
          let keyboardFrame = userInfo[UIResponder.keyboardFrameEndUserInfoKey] as? CGRect else { return }
    
    let isKeyboardShowing = keyboardFrame.origin.y < view.bounds.height
    // 调整全屏模糊视图的frame
    if isKeyboardShowing {
        blurEffectView.frame = view.bounds.inset(by: UIEdgeInsets(top: 0, left: 0, bottom: keyboardFrame.height, right: 0))
    } else {
        blurEffectView.frame = view.bounds
    }
    
    // 确保Stack View的模糊背景始终贴合Stack View
    stackBlurView.frame = stackView.bounds
}

内容的提问来源于stack exchange,提问作者Emir

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 22:40:59