微信小程序实现一个手势图案锁组件

简介: 微信小程序实现一个手势图案锁组件

说在前面

🎈现在大部分的人都喜欢使用手势图案锁来作为手机的锁屏,之前我也写过一篇使用vue封装的手势图案锁组件,想了解的可以戳这里->《vue封装一个图案手势锁组件》。那么怎么在微信小程序中实现这种手势锁屏的效果的呢?接下来让我们一起来实现一个微信小程序中可以使用的手势锁屏组件吧!

组件设计

我们主要从页面展示效果和交互效果来进行具体分析:

1、页面效果

1.1 九宫格圆点排列

使用flex布局和flex-wrap效果,使9个圆点可以均匀排列。

  • wxml
<view
    id="{{JAppsLockId + 'lock'}}"
    class="j-apps-lock"
>
    <view class="j-apps-lock-cells">
        <view
            class="j-apps-lock-cell"
            wx:for="{{size * size}}"
            wx:key="index"
            data-id="{{index}}"
            style="border:{{showBorder[index] ? '1px solid gray' : '1px solid transparent'}}"
        >
            <view
                id="{{'point-' + index}}"
                class="j-apps-lock-point"
                data-id="{{index}}"
            ></view>
        </view>
    </view>
</view>
  • wxss
.j-apps-lock {
  position: relative;
  margin: auto;
}
.j-apps-lock-cells {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-around;
}
.j-apps-lock-cell {
  display: flex;
  border-radius: 50%;
  justify-content: center;
  width: 26vw;
  height: 26vw;
  margin-top: 2vw;
}
.j-apps-lock-point {
  width: 40%;
  height: 40%;
  justify-content: center;
  background-color: rgb(187, 183, 183);
  display: flex;
  margin: auto;
  border-radius: 50%;
  position: relative;
}
1.2 划动选中圈圈效果

只需要动态判断当前圈圈是否被选中,动态修改style属性即可: border:{{showBorder[index] ? '1px solid gray' : '1px solid transparent'}}

<view
    class="j-apps-lock-cell"
    wx:for="{{size * size}}"
    wx:key="index"
    data-id="{{index}}"
    style="border:{{showBorder[index] ? '1px solid gray' : '1px solid transparent'}}"
>
...
</view>

2、交互效果

2.1 监听触屏划过圆点

我们可以对整个组件界面进行一个触屏监听,判断坐标是否经过某一个圆点的坐标,如果是,可以将当前圆点标记为选中状态。

  • wxml
<view
    id="j-apps-lock-body"
    class="j-apps-lock-body"
    bindtouchstart="mousedown"
    bindtouchmove="mouseover"
    bindtouchend="mouseup"
>
...
</view>
  • js
mousedown(e){
  this.clearPoint();
  if(this.data.points.length == 0) this.getPoints();
},
mouseover(e){
  let points = this.data.points;
  let x = e.touches[0].pageX;
  let y = e.touches[0].pageY;
  let id = '';
  let showBorder = this.data.showBorder;
  for(let i = 0; i < points.length; i++){
    const p = points[i];
    if(x >= p.left && x <= p.right && y <= p.bottom && y >= p.top){
      id = p.dataset.id;
      showBorder[i] = true;
      break;
    }
  }
  let chooseList = this.data.chooseList;
  if(isNaN(parseInt(id)) || chooseList.includes(id)) return;
  chooseList.push(id);
  this.setData({
    chooseList:chooseList,
    showBorder:showBorder
  })
},
2.2 动作结束返回动作轨迹

在手指离开手机屏幕,及触屏事件结束触发mouseup事件的时候,将选中的圈圈坐标顺序传递给父组件,这里我对圈圈的坐标定义如下,大家也可以根据实际情况自己定义:

mouseup(){
  this.triggerEvent("getPassword", {chooseList:this.data.chooseList});
},

所以上图的图案滑动轨迹返回的点集数组应该为:

[1,2,3,6,9,8,7,4,5]

核心代码详解

1、微信小程序获取dom实例对象

在进行点坐标判断的时候,我们需要获取到每一个点的坐标范围,但是在微信小程序中我们不能直接同document.getElementbyId去获取到我们需要的实例对象,那么我们该怎么获取到需要的对象,并得到其相应的坐标范围呢?

1.1 wx.createSelectorQuery()

我们需要先了解一下wx.createSelectorQuery()这个api

  • 功能

返回一个 SelectorQuery 对象实例。在自定义组件或包含自定义组件的页面中,应使用 this.createSelectorQuery() 来代替。

通过查阅官方文档,我们发现可以通过wx.createSelectorQuery()来获取到页面上的实例对象,这里我们是在小程序组件中使用,所以我们应该使用this.createSelectorQuery()来获取。

getPoints(){
  const query = this.createSelectorQuery();
  let id = '.j-apps-lock-point'
  query.selectAll(id).boundingClientRect((res)=>{
    this.setData({
      points:res
    })
  }).exec()
},

2、判断是否是否划过点位

前面我们获取的点位的dom实例在这里就可以派上用场了,微信小程序返回的实例对象中会包含这几个属性:

  • left:实例对象最左端坐标
  • right:实例对象最右端坐标
  • top:实例对象最顶端坐标
  • bottom:实例对象最底端坐标
    这里我们有两个方法来判断:
2.1 正方形区域判断

我们可以直接根据实例对象的四个端点坐标来进行一个正方形的大致位置匹配,这样得出来的结果会有少许误差,但也不会有很大的影响:x >= p.left && x <= p.right && y <= p.bottom && y >= p.top

mouseover(e){
  //前面获取的圈圈实例对象集合
  let points = this.data.points;
  //当前触屏坐标
  let x = e.touches[0].pageX;
  let y = e.touches[0].pageY;
  let id = '';
  let showBorder = this.data.showBorder;
  //判断是否划过某一个圈圈
  for(let i = 0; i < points.length; i++){
    const p = points[i];
    if(x >= p.left && x <= p.right && y <= p.bottom && y >= p.top){
      id = p.dataset.id;
      showBorder[i] = true;
      break;
    }
  }
  //记录圈圈选中状态
  let chooseList = this.data.chooseList;
  if(isNaN(parseInt(id)) || chooseList.includes(id)) return;
  chooseList.push(id);
  this.setData({
    chooseList:chooseList,
    showBorder:showBorder
  })
},
2.2 圆形区域判断

我们也可以根据点实例对象的端点得出其圆的方程,我们只需要将坐标代入方程判断是否位于圆内即可:

(x1-x)^2 + (y1-y)^2 <= r^2

所以我们需要计算出圈圈的圆心坐标和半径即可:

const r = (p.right - p.left) / 2;
const x1 = (p.left + p.right) / 2;
const y1 = (p.top + p.bottom) / 2;
mouseover(e){
  let points = this.data.points;
  let x = e.touches[0].pageX;
  let y = e.touches[0].pageY;
  let id = '';
  let showBorder = this.data.showBorder;
  for(let i = 0; i < points.length; i++){
    const p = points[i];
    const r = (p.right - p.left) / 2;
    const x1 = (p.left + p.right) / 2;
    const y1 = (p.top + p.bottom) / 2;
    if(Math.pow(x1 - x,2) + Math.pow(y1 - y,2) <= Math.pow(r,2)){
      id = p.dataset.id;
      showBorder[i] = true;
      break;
    }
  }
  let chooseList = this.data.chooseList;
  if(isNaN(parseInt(id)) || chooseList.includes(id)) return;
  chooseList.push(id);
  this.setData({
    chooseList:chooseList,
    showBorder:showBorder
  })
},

源码地址

该组件是我在自己的一个开源项目中使用到的,源码可以到该项目查看具体代码,地址如下:

微信小程序手势图案锁组件源码

具体位置如下

往期精彩

vue封装一个图案手势锁组件

vue封装一个弹幕组件

为了学(mo)习(yu),我竟开发了这样一个插件

程序员的浪漫之——情侣日常小程序

JavaScript双向链表实现LRU缓存算法

JavaScript双向链表实现LFU缓存算法

JavaScript实现前缀树

vue简单实现词云图组件

vue + echarts实现中国地图省份下钻联动

使用学过的算法做个游戏很酷的好吗

说在后面

🎉这里是JYeontu,喜欢算法,GDCPC打过卡;热爱羽毛球,大运会打过酱油。毕业一年,两年前端开发经验,目前担任H5前端开发,算法业余爱好者,有空会刷刷算法题,平时喜欢打打羽毛球🏸 ,也喜欢写些东西,既为自己记录📋,也希望可以对大家有那么一丢丢的帮助,写的不好望多多谅解🙇,写错的地方望指出,定会认真改进😊,在此谢谢大家的支持,我们下文再见🙌。

目录
相关文章
|
2月前
|
小程序 数据可视化 JavaScript
微信小程序:轻松实现时间轴组件
本文介绍了如何在微信小程序中实现一个可视化时间轴组件。该组件适用于展示用户资金流动、投资结算等时间节点,帮助用户直观了解资金去向。时间轴支持自定义节点形状、显示序号、倒序排列等功能,并通过插槽灵活定义动态内容。文中详细介绍了组件的设计与使用方法,以及如何结合动态 slot 实现自定义操作。该组件为展示用户资金信息提供了美观、易用的解决方案。
68 1
微信小程序:轻松实现时间轴组件
|
2月前
|
小程序
微信小程序动态tabBar实现:基于自定义组件,灵活支持不同用户角色与超过5个tab自由组合(更新版)
微信小程序动态tabBar实现:基于自定义组件,灵活支持不同用户角色与超过5个tab自由组合(更新版)
549 1
|
2月前
|
小程序 搜索推荐 API
微信小程序:自定义关注公众号组件样式
尽管关注公众号组件的样式固定且不可修改,但产品经理的需求却需要个性化的定制。在这种情况下,我们需要寻找解决方案,以满足这些特殊需求,尽管这可能有点棘手。
72 0
微信小程序:自定义关注公众号组件样式
|
2月前
|
小程序 前端开发 JavaScript
微信小程序图表制作利器:ECharts组件的使用与技巧
微信小程序图表制作利器:ECharts组件的使用与技巧
70 1
|
2月前
|
缓存 小程序 索引
uni-app开发微信小程序时vant组件van-tabs的使用陷阱及解决方案
uni-app开发微信小程序时vant组件van-tabs的使用陷阱及解决方案
224 1
|
2月前
|
小程序 JavaScript
微信小程序之input组件及其获取用户输入信息
微信小程序之input组件及其获取用户输入信息
66 1
|
3月前
|
小程序 容器
微信小程序常用组件的简单使用 view,scroll-view,swiper,swiper-item,text,rich-text,button,image
本文介绍了微信小程序中常用组件的使用方法,包括view、scroll-view、swiper与swiper-item、text与rich-text、button以及image组件。详细解释了各组件的功能、属性以及如何在小程序页面中进行使用。
微信小程序常用组件的简单使用 view,scroll-view,swiper,swiper-item,text,rich-text,button,image
|
2月前
|
小程序 前端开发 JavaScript
小程序入门之认识view和text组件
小程序入门之认识view和text组件
85 0
|
2月前
|
JSON 小程序 JavaScript
uni-app开发微信小程序的报错[渲染层错误]排查及解决
uni-app开发微信小程序的报错[渲染层错误]排查及解决
630 7
|
2月前
|
小程序 JavaScript 前端开发
uni-app开发微信小程序:四大解决方案,轻松应对主包与vendor.js过大打包难题
uni-app开发微信小程序:四大解决方案,轻松应对主包与vendor.js过大打包难题
722 1