uni-search-bar 下拉面板必须用 v-if 控制显隐,v-show 会导致 dom 占位、错位、触摸穿透;需结合 loading 状态判断、手动防抖、键盘收起与焦点控制、scroll-view 高度自适应等细节优化体验。

uni-search-bar 的下拉联想面板必须用 v-if 控制显隐
直接用 v-show 会导致 DOM 始终存在,iOS 上容易错位、遮挡按钮,安卓真机还可能触发触摸穿透异常。更关键的是,v-show="false" 时面板仍占布局空间,滚动时会突然“跳一下”。v-if 才能真正销毁节点,配合 <transition></transition> 做淡入淡出才稳定。
实操建议:
- 判断条件别只写 suggestionList.length > 0,要加上请求状态:v-if="showSuggestions && (suggestionList.length || loading)"
- loading 状态单独渲染骨架或文字,避免空白闪动
- 过渡 class 里别用 transform: scale(),某些 Android Webview 渲染不一致,改用 opacity + height 更稳妥
防抖逻辑必须手写,@input 不是“等用户停”而是“每打一个字就触发”
uni-search-bar 的 @input 事件在每个字符输入后立刻触发,输“苹果”会连续触发三次: “苹” → “苹果” → “苹果手”。不加控制,接口请求会堆叠、UI 卡顿、后端压力陡增。
实操建议:
- 用 setTimeout + clearTimeout,延迟 300–500ms 再发请求,别依赖组件内置节流(它没有)
- 每次新输入前必须 clearTimeout(this.timer),否则定时器残留导致内存泄漏
- 在页面卸载钩子中再次清理:onUnload() { clearTimeout(this.timer) }
- 输入长度 ≤ 1 时,直接清空联想列表并 return,避免搜单字返回几百条低质词
点击联想词后,键盘收起和焦点处理在 App 端最容易出问题
点了“iPhone 15”,输入框内容变了,但键盘没关、没跳转、光标还在闪——这是 App(尤其 iOS)最常见卡点。根本不是逻辑漏了,而是 Webview 渲染时机和焦点链没对齐。
实操建议:
- 点击项后立即执行 uni.hideKeyboard(),别等 @confirm 或回车
- 同步调用 this.$refs.searchBarRef?.blur()(如果 ref 存在)
- 手动设 focus = false,防止 v-model 绑定的 input 持续聚焦干扰后续操作
- 安卓真机上 confirm-type="search" 有时不触发 @confirm,必须用点击事件兜底调搜索函数
动画本身不难,难的是高度自适应和滚动边界控制
联想面板高度不固定:2 条词和 10 条词,面板高度差一倍。如果用 max-height + overflow-y: auto,iOS 上常出现滚动条卡死、滑不动、或内容被裁掉顶部。
实操建议:
- 面板容器用 position: absolute + top: 100%,脱离文档流避免影响父级高度计算
- 内部列表用 scroll-view 包裹,设 scroll-y 和固定 max-height(如 200rpx)
- 每次更新列表后,手动调用 scroll-view 的 scrollIntoView 方法确保首项可见
- 别给 scroll-view 设 flex: 1,某些平台会忽略高度约束,导致撑满全屏
动画效果本身只是视觉糖,真正决定体验的是请求时机、DOM 生命周期、焦点控制这三处细节。多数人卡在“为什么点了没反应”,其实问题不在动画,而在键盘没收、定时器没清、或面板 DOM 还在那儿挡着。











