Uniapp之键盘弹窗

适用范围

  1. 评论输入框
  2. 自定义键盘顶部工具栏
  3. 其他吸附于键盘顶部的弹框

意义

对于输入框来说,一般都包含自动抬高输入框,但是对于一些自定义窗口来说(比如输入框下添加工具栏、键盘顶部添加工具栏等),就需要自己处理弹框位置了,那么这个时候键盘弹窗就解决了复杂的处理。

示例

下面示例用于展示 keyboard-popup 使用示例,当 textarea 聚焦时,textarea 就会自动抬高到键盘上方。

html 复制代码
<template>
  <!-- 评论输入框 -->
  <!-- 注意这里需要添加adjustPosition=false属性来关闭自动上推页面 -->
  <keyboard-popup ref="replyPopup">
    	<textarea
        ref="textarea"
        v-model="content"
        placeholder="请输入内容"
        focus
        auto-focus
        maxlength="500"
        :style="{height: '160rpx'}"
        :adjustPosition="false"
        :showConfirmBar="false">
        </textarea>
  </keyboard-popup>
</template>
<script>
export default {
  data() {
    return {
      content: ''
    }
  },
  methods: {
    openPopup() {
      // 打开弹窗
      this.$refs.replyPopup.open()
    },
    openPopup() {
      // 关闭弹窗
      this.$refs.replyPopup.colse()
    }
  },
  mounted() {
    // 监听键盘高度变化,用于抬高评论框
    this.$refs.replyPopup.handleKeyboardHeightChange()
  },
  onUnload() {
    // 取消键盘高度变化监听
    this.$refs.replyPopup.offKeyboardHeightChange()
  },
}
</script>

源码

以下是 KeyboardPopup 组件的源码,可根据自己的需求加以改进。

html 复制代码
<script>
export default {
  name: 'KeyboardPopup',
  props: {
    // 是否显示底部安全距离
    showSafeBottom: {
      type: Boolean,
      default: true
    }
  },
  data() {
    return {
      showVal: false,
      keyboardHeight: 0,
      isOpen: false,
      safeAreaInsetBottom: 0
    }
  },
  methods: {
    open() {
      this.showVal = true
      this.$nextTick(() => {
        this.isOpen = true
      })
    },
    close() {
      this.isOpen = false
      this.showVal = false
    },
    onClose() {
      this.isOpen = false
      this.showVal = false
      this.$emit('close')
    },
    /**
     * 设置键盘高度,用于设置内容抬高的位置
     * @param height 高度
     */
    setKeyboardHeight(height) {
      this.keyboardHeight = height
    },
    handleKeyboardHeightChange() {
      uni.onKeyboardHeightChange(res => {
        this.keyboardHeight = res.height
      })
    },
    offKeyboardHeightChange() {
      uni.offKeyboardHeightChange()
    }
  },
  mounted() {
    // 获取底部安全距离
    if (this.showSafeBottom) {
      this.safeAreaInsetBottom = uni.getSystemInfoSync().safeAreaInsets.bottom
    }
  }
}
</script>

<template>
  <u-popup :show="showVal" @close="onClose" bgColor="transparent" :safeAreaInsetBottom="false" closeOnClickOverlay>
    <view class="content-container" :style="{bottom: keyboardHeight + 'px'}">
      <slot :isOpen="isOpen"></slot>
    </view>
    <!--  底部安全距离  -->
    <view class="safeBottom" v-if="!isOpen" :style="{height: safeAreaInsetBottom + 'px'}"></view>
  </u-popup>
</template>

<style scoped lang="scss">
.content-container {
  position: relative;
}

.safeBottom {
  width: 100%;
  background-color: #fff;
}
</style>
相关推荐
小兵张健8 小时前
价值1000的 AI 工作流:Codex 通用前端协作模式
前端·aigc·ai编程
sunny_8 小时前
面试踩大坑!同一段 Node.js 代码,CJS 和 ESM 的执行顺序居然是反的?!99% 的人都答错了
前端·面试·node.js
拉不动的猪8 小时前
移动端调试工具VConsole初始化时的加载阻塞问题
前端·javascript·微信小程序
ayqy贾杰10 小时前
Agent First Engineering
前端·vue.js·面试
IT_陈寒10 小时前
SpringBoot实战:5个让你的API性能翻倍的隐藏技巧
前端·人工智能·后端
iceiceiceice10 小时前
iOS PDF阅读器段评实现:如何从 PDFSelection 精准还原一个自然段
前端·人工智能·ios
大金乄11 小时前
封装一个vue2的elementUI 表格组件(包含表格编辑以及多级表头)
前端·javascript
葡萄城技术团队11 小时前
【性能优化篇】面对万行数据也不卡顿?揭秘协同服务器的“片段机制 (Fragments)”
前端
程序员阿峰12 小时前
2026前端必备:TensorFlow.js,浏览器里的AI引擎,不写Python也能玩转智能
前端
Jans12 小时前
Shipfe — Rust 写的前端静态部署工具:一条命令上线 + 零停机 + 可回滚 + 自动清理
前端