uniapp自定义验证码输入框并隐藏光标

目录
  • 一. 前言
  • 二. 实现思路
  • 三. 代码实现
  • 四. 过程中遇到的问题

一. 前言

先看下使用场景效果图:

  1. 点击输入框唤起键盘,蓝框就相当于input的光标,验证码输入错误或者不符合格式要求会将字体以及边框改成红色提示,持续1s,然后清空数据,恢复原边框样式;
  2. 5位验证码输入完毕,点击页面其他位置,隐藏键盘;这时如果发现验证码有误,再次点击输入框又唤起键盘,也能正常删除数字(这里其实做的时候遇到了bug,再次聚焦不能删除错误数字,下文会讲到)。

二. 实现思路

具体实现思路:

  • 将input标签相对于父元素做绝对定位,与父元素左边距设置为负的本身宽度即可(position: absolute; top: 0; left:-100%; width: 100%; height: 100%;)。
  • 动态去设置input的focus属性。
  • input同级使用for循环去创建5个正方形的view标签。
  • 给input同级创建的view标签绑定点击事件,在点击事件方法实现中去设置input的focus属性为true,即可弹出键盘。
  • 在键盘输入的时候,即可触发input属性的一系列方法,利用v-model双向绑定,将input输入的值赋值给循环的view方框即可。
  • 这样input也就不在屏幕中,但是又可以触发input的事件。

总的来说就是,使用for循环去创建5个正方形的view标签,然后创建一个input标签,type=tel,最大输入长度为5(根据需求来设置),再将input伪隐藏掉,获取的值分别放到5个view中展示。

验证码失败后利用v-model双向绑定,清空输入的值,增加错误提示文字和边框样式。

三. 代码实现

父组件

<uni-popup ref="codeInputPopup" background-color="#fff" :mask-click ="false" type="center">
     <CodeInput
	  :codeLength="5"
	  :disabled="codeBtnDisabled"
	  @codeInputClose="codeInputClose"
	  @submitGoodCode="submitGoodCode"
	 />
</uni-popup>
<script>
export default {
  data() {
    return {
     	intviation_code:'', //邀请码
		codeBtnDisabled: false //防止接口请求还未返回数据,用户多次点击
    }
  },
  methods: {
    // 提交邀请码
	async submitGoodCode(intviation_code){
		this.codeBtnDisabled = true
		this.intviation_code = intviation_code

		const response =  await this.$api.post('/ebapi/pink_api/secret_intviation_check', {
		  code: intviation_code
		})
		if(response.code === 200){
			this.codeBtnDisabled = false
			this.$refs.codeInputPopup.close()
		}else{
			this.codeBtnDisabled = false
			this.$refs.codeInputPopup.close()
			this.$api.msg(response.msg)
		 }
		},
	codeInputClose(){
	  this.$refs.codeInputPopup.close()
	  this.codeBtnDisabled = false
	}
}
</script>

子组件

<template>
  <view>
    <view class="code-popup-top">
      <view class="code-title">请输入商品邀请码</view>
      <view class="close-icon" @click="codeInputClose">
        <uni-icons type="closeempty" size="30" color="#999999" />
      </view>
    </view>
    <!-- 错误提示 -->
    <view class="code_errow" v-if="codeColor == '#ff0000'&& !isNum">邀请码必须{{ codeLength }}位数</view>
    <view class="code_errow" v-if="codeColor == '#ff0000'&& isNum ">邀请码必须是数字</view>
    <view class="code_input_con">
      <view
        v-for="(item, index) in codeLength"
        :key="index"
        class="code_input_item"
        :style="(index == intviation_code.length? 'border: 5rpx solid #1195db; width: 88rpx; height: 88rpx; line-height: 80rpx;':'color: ' + codeColor + ';' +'border: 2rpx solid' + codeColor)"
        @click="focus = true"
      >{{ intviation_code[index] && intviation_code[index] || '' }}</view>
      <input
        class="cinput"
        type="tel"
        v-model="intviation_code"
        :maxlength="codeLength"
        :focus="focus"
        :cursor="intviation_code.length"
        @focus="focus = true "
        @blur="focus = false"
      />
    </view>
    <button
      :class="['submit_code_btn', disabled ? 'btn_disabled' : '']"
      :disabled="disabled"
      @click="submitGoodCode"
    >确定</button>
  </view>
</template>

<script>
export default {
  data() {
    return {
      codeColor: '#313131', //自定义错误码颜色
      intviation_code: '', //用户输入的验证码
      focus: false, // 动态获取焦点的值
      isNum: false,
    }
  },
  props: {
    codeLength: {
      type: Number,
      default: 5,
    },
    disabled: {
      type: Boolean,
      default: false,
    },
  },
  methods: {
    codeInputClose() {
      this.intviation_code = ''
      this.$emit('codeInputClose')
    },
    submitGoodCode() {
      if (this.intviation_code.length === this.codeLength) {
        if (Number(this.intviation_code)) {
          this.$emit('submitGoodCode', this.intviation_code)
        } else {
          this.isNum = true
          this.publicErrorSetting()
        }
      } else {
        this.publicErrorSetting()
      }
    },
    // 输入不符合规范,更改样式并清空
    publicErrorSetting() {
      this.codeColor = '#ff0000'
      setTimeout(() => {
        this.intviation_code = ''
        this.codeColor = '#313131'
        this.isNum = false
      }, 1000)
    },
  },
}
</script>

<style lang="scss" scoped>
.code-popup-top {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 50upx;
  .code-title {
    font-size: 34upx;
    color: #333;
    font-weight: bold;
    position: relative;
    &::before {
      content: '';
      position: absolute;
      bottom: 0;
      width: 40upx;
      height: 19upx;
      background: linear-gradient(
        to right,
        rgba(57, 181, 74, 1),
        rgba(57, 181, 74, 0.1)
      );
    }
  }
  .close-icon {
    background: #f2f4f7;
    border-radius: 50%;
    display: flex;
    align-items: center;
    justify-content: center;
  }
}
.code_errow {
  font-size: 30upx;
  color: #ff5500;
  margin-bottom: 20upx;
}
.submit_code_btn {
  width: 100%;
  height: 83upx;
  line-height: 83upx;
  border-radius: 7upx;
  background: #39b54a;
  color: #fff;
  font-size: 31upx;
  text-align: center;
  margin-top: 45upx;
}
.btn_disabled {
  color: rgba(255, 255, 255, 0.5) !important;
  background-color: rgba(57, 181, 74, 0.4) !important;
}
.code_input_con {
  display: flex;
  justify-content: space-around;
  position: relative;
  .code_input_item {
    margin-left: 10upx;
    text-align: center;
    line-height: 88upx;
    border-radius: 14upx;
    width: 88upx;
    height: 88upx;
    font-size: 60upx;
    font-weight: bold;
    color: #333;
    &:last-child {
      margin-right: 0;
    }
  }
  /*input隐藏掉*/
  .cinput {
    position: absolute;
    top: 0;
    left: -100%;
    width: 100%;
    height: 100%;
  }
}
</style>

四. 过程中遇到的问题

1)input 的type=‘number’, ios手机正常,光标在内容最后,但Android手机光标有时候在内容最前面,导致聚焦内容删不掉。

修改input 的type = 'tel':cursor="intviation_code.length", 这样cursor属性才生效,并指定focus时光标的位置在内容最后;
type=‘tel’,也会有个小问题,可以输入一些字符,但是我们的需求只能是数字,所以代码中要做限制。就能解决这个问题了。

这个cursor无效的问题,在h5模式应该是type的原因,我试了在type是number或digit时cursor就无效,text、tel、idcard就有效

2)还有另外一种方法

  • 设置input的type=“number”,就不需要设置光标位置了;然后隐藏input文字和光标,相当于间接隐藏了input框;
  • 用到了css样式设置,color: transparent; caret-color: transparent;
  • 最主要的还是相对于父元素做绝对定位,与父元素左边距设置为负的本身宽度的一半即可(position: absolute; top: 0; left:-100%; width: 200%; height: 100%;)with: 200%为了增大点击区域,解决Android机型再次唤起键盘不能聚焦,删不掉错误数字的问题。

如何利用css隐藏input的光标示例代码

自我测试CSS : caret-color

<template>
  <view>
      <input
        class="cinput"
        type="number"
        v-model="intviation_code"
        :maxlength="codeLength"
        :focus="focus"
        @focus="focus = true "
        @blur="focus = false"
      />
    </view>
  </view>
</template>

<script>
export default {
  data() {
    return {
      intviation_code: '', //商品邀请码
      focus: false,
    }
  },
  methods: {}
</script>

<style lang="scss" scoped>
.cinput {
    position: absolute;
    top: 0;
    left: -100%;
    width: 200%;
    height: 100%;
    color: transparent;  //输入文字颜色透明
    caret-color: transparent !important; //改变插入光标颜色为透明
  }
  }
  // 考虑兼容性
  // 浏览器支持caret-color属性,优先使用caret-color(Chrome/Firefox/Opera);其次使用::first-line方法(Safari);最后忽略(如IE)。
  @supports (-webkit-mask: none) and (not (caret-color: transparent)) {
    .cinput {
      color: transparent !important;
    }
    .cinput::first-line {
      color: transparent !important;
    }
  }
</style>

还可参考:
6位验证码输入框、隐藏光标、letter-spacing失效、自定义光标,光标动画
uniapp 手机验证码输入框(随机数、倒计时、隐藏手机号码中间四位)可以直接使用

到此这篇关于uniapp自定义验证码输入框,隐藏光标的文章就介绍到这了,更多相关uniapp验证码输入框内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • uniapp改变底部安全区顶部手机信号时间电池栏颜色样式

    目录 底部安全区域 原始状态 修改代码配置safearea 底部区域颜色配置 顶部电池栏的配置 配置顶部导航栏颜色 方案一:仅适用于原生导航配置,非自定义导航 方案一:通用,也适用于自定义导航 注意事项 uniapp中 onReady, onLoad, onShow区别 举个栗子 底部安全区域 uniapp 的默认安全区域的颜色是白色,如果我们做了沉浸式页面,背景色也是白色的话,就会看不到电池栏,等的颜色,如何修改呢? 原始状态 下图是底部安全区原始状态,感觉和整个页面格格不入 修改代码配置sa

  • uniapp动态修改元素节点样式详解

    目录 一,通过style属性绑定来修改 html: 对应的js: 实现的效果: 二,利用ref来获取dom元素节点 代码: 实现的效果: 总结 一,通过style属性绑定来修改 第一步:肯定是需要获取元素节点 在uniApp项目中没有windouw对象,所以通过document不能直接获取dom节点,vue的refs只对自定义组件有效,对uniapp中的标签不生效. 查看uniapp官网有一个uni.createSelectorQuery() API:可以通过这个属性获取标签的样式,在通过动态绑

  • uniapp 手机验证码输入框实现代码(随机数、倒计时、隐藏手机号码中间四位)可以直接使用

    如键盘被隐藏,可直接点击蓝框弹出键盘,蓝框就相当于input的光标,验证码输入错误之后会将字体以及边框改为红色,持续1.5s(可自行修改时间),然后清空数据. <template> <view class="code"> <view class="code-tip-one">请输入验证码 <view class="code-tip">已向<text>+86 {{phone.substri

  • uniapp自定义验证码输入框并隐藏光标

    目录 一. 前言 二. 实现思路 三. 代码实现 四. 过程中遇到的问题 一. 前言 先看下使用场景效果图: 点击输入框唤起键盘,蓝框就相当于input的光标,验证码输入错误或者不符合格式要求会将字体以及边框改成红色提示,持续1s,然后清空数据,恢复原边框样式: 5位验证码输入完毕,点击页面其他位置,隐藏键盘:这时如果发现验证码有误,再次点击输入框又唤起键盘,也能正常删除数字(这里其实做的时候遇到了bug,再次聚焦不能删除错误数字,下文会讲到). 二. 实现思路 具体实现思路: 将input标签

  • Android 自定义验证码输入框的实例代码(支持粘贴连续性)

    需求 1.能自定义输入框个数和样式 2.支持长按粘贴或剪切板内容自动填充(粘贴连续性) 其中第2点是最为重要的,正是其他人没有这点,逼得自己弄一个 示例 别人的示例: 粘贴居然不支持连续性,只能粘贴第一个字符,所以用的有点难受 自己的示例: 原理 大致是Edittext + n* TextView,然后设置edittext字体跟背景颜色都为透明,隐藏光标 Edittext:监听edittext每次输入一个字符就赋值到对应的TextView上,然后在清空自己 下划线:在TextView下面添加Vi

  • Android实现自定义验证码输入框效果(实例代码)

    这里提一下,这个当时也是在网上看到一个博主写的代码改了下用在我么项目中的验证码输入框.博主的地址不记得了这里只能顺带标注一下... 效果图如下: 就是这个酱紫 直入主题,代码如下: xml布局: <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" androi

  • Qt实现自定义验证码输入框控件的方法

    前言 本文实现了自定义的验证码输入框控件.控件包括图标.输入框.获取验证码按钮.验证码获取倒计时标签.支持鼠标点击获取验证码按钮后开始显示倒计时功能,倒计时为0时,才可以在此点击获取验证码按钮.效果如图: 主要的编程思想还是实现自定义控件的封装性和共用性. UI布局: 控件1:QWidget,实现整个控件的封装,这个控件使用水平布局,实现控件的水平摆放,同时,当其中一个控件隐藏时,位置会重新更新,实现在控件的后面只显示获取验证码和倒计时两个控件中的一个. 控件2:QLabel,实现展示盾牌图标.

  • Android自定义验证码输入框的方法实例

    目录 实践过程 总结 实践过程 前面我们学完了EditText和TextView两个组件,但是,光学不练没意思. 所以今天我们趁热打铁,利用两个组件实现个自定义验证码输入框. 思路前瞻: 隐形EditText接收输入,显性TextView展示内容 时刻监听EditText回调更改内容 自定义RelativeLayout 布局代码: <?xml version="1.0" encoding="utf-8"?><!--自定义验证码View-->

  • Android View教程之自定义验证码输入框效果

    前言 首先,我们来看看实现的是怎么样的效果: 如果我们拿到这样的UI,想到的布局应该是用4个EditText包在横向的LinearLayout里面,但今天要讲的View,所以我们决定用一个自定义的EditText 画出来. 学到什么? 基本理解画布概念 画布的状态.平移 布局测量 画图片 功能需求 高亮当前输入框 输入满4个数字自动调用方法 思路 完全重画一个EditText,就包含了测量布局和重新绘制这两个关键步骤.好了,到这里理一下整体的思路: 根据验证码个数以及边框大小来计算输入框显示的宽

  • Android自定义控件实现通用验证码输入框(二)

    本文实例为大家分享了Android实现通用验证码输入框第2篇具体实现代码,供大家参考,具体内容如下 效果图 话不多说,我们还是先上效果图,可以先先看看是不是自己想要的 闲聊 这种验证码输入框使用组合控件就比较烦人了,所以这边直接使用自定View步奏实现 源码 自定义输入框属性(attrs.xml) <?xml version="1.0" encoding="utf-8"?> <resources> <declare-styleable

  • Android自定义控件实现通用验证码输入框

    本文为大家分享了Android实现通用验证码输入框的具体代码,供大家参考,具体内容如下 效果图 话不多说先上效果图,可以先先看看是不是自己想要的 闲聊 闲来无事优化项目时,发现原来的验证码输入框,可扩展性不高,就拿来优化了一下,说说我开始的的思路吧,最开始是想用自定义View实现的,但是发现各种画矩,太烦人了,最后采用的组合控件的形式,Android有现成的控件,用来组合组合就能用,为什么不用呢. 源码 xml ITEM 布局文件(view_auth_code_input_item.xml) <

  • Android自定义View验证码输入框

    本文实例为大家分享了Android自定义View验证码输入框的具体代码,供大家参考,具体内容如下 验证码输入框 1.先看下样式 2.直接上代码 public class MyVcode extends AppCompatEditText { private int mFigures = 0;// 验证码个数 private int mCodeMargin = 0;// 验证码之间的间距 private int mSelectColor = 0;// 选中框的颜色 private int mNor

  • Android实现常见的验证码输入框实例代码

    前言 验证码输入框是很多APP必不可少的组件,之前在重构注册登录页面的时候,重新设计了UI,所以不能再简单的用EditText来做了,所以这篇文章将分享一下如何实现一个常见的验证码输入框.下面话不多说了,来一起看看详细的介绍吧. 正文 先搂一眼效果吧 不要把注意力都放在头顶的那一抹绿上,重点在输入框,可能大多数APP里都是采用6个方框的UI效果,我这里是按照我们设计的要求,用6根横线来划出6个数字的位置.一开始我想的是直接用6个TextView,然后传递焦点的做法,但是发现实现起来有一定的难度.

随机推荐