基于JavaScript实现年份数字拼图效果

作者:页面旅途时间:2026-10-26 08:30:22浏览:435

本文详细介绍如何利用JavaScript实现年份数字的拼图展示效果。通过定义0-9数字的网格坐标,计算并高亮对应卡片位置。在此基础上,引入异步串行绘制机制,实现了类似手写笔画的动态显示效果,为前端年会或活动页面增添视觉趣味。

背景

时光飞逝,2022年即将结束,公司的年会安排是否已就绪?(顺便关心一下,您的健康状况如何?)

日前浏览到一个功能强大的年会抽奖系统,其中年份数字的拼图特效令人印象深刻,因此决定深入探究其实现方法。首先观察具体效果,图中展示了由卡片拼成的“2022”年份数字。

背景

实现原理

从视觉效果来看,核心在于将特定卡片设为高亮颜色以拼凑出数字形状。其基本实现思路如下:

  • 首先设计数字(0-9)在横向和纵向上所占用的卡片列数与行数,例如上图示例中,横向占用3列,纵向占用5行;
  • 针对每个数字(0-9)的具体形状,提取亮色卡片位置的坐标,从而构建出每个数字的形状坐标数组;
  • 依据每个数字的形状坐标及需展示的数字序列,计算出最终的具体位置,并将对应坐标的卡片设置为高亮状态即可;

具体实现

1. 创建背景卡片

拼图展示的数字为当前年份(2022),即4位数字。根据数字横向占3列、纵向占5行的设定,且数字间间隔1列,为保持美观,数字区域上下左右边界需各留出一行或一列空白。因此,背景卡片的总行数和列数计算如下:

行数 = 5 + 1 + 1 = 7;

列数 = 3 * 4 + 3(间隔) + 1 + 1 = 17;

const rowCount = 7;
const colCount = 17;
// 创建卡片
const createCard = () => {
  const frag = document.createDocumentFragment();
  for (let i = 0; i < rowCount; i++) {
    for (let j = 0; j < colCount; j++) {
      const item = document.createElement('div');
      item.className = "item";
      frag.appendChild(item);
    }

  }
  document.querySelector('.container').appendChild(frag);
}

2. 设置数字形状坐标

这一步骤旨在根据每个数字的形状,记录路径上各点的坐标。规则是从上到下、从左到右,找出所有路径上的点。0-9的形状坐标数组如代码所示,可对照上文图片确认数字的形状坐标。

注意:若需设计其他字体的数字展示形式,可根据具体形状收集路径点坐标。

// 0-9数字的坐标形状
const NUMBER_MATRIX = [
  [
    // 0
    [0, 0],
    [1, 0],
    [2, 0],
    [0, 1],
    [2, 1],
    [0, 2],
    [2, 2],
    [0, 3],
    [2, 3],
    [0, 4],
    [1, 4],
    [2, 4]
  ],
  [
    // 1
    [1, 0],
    [0, 1],
    [1, 1],
    [1, 2],
    [1, 3],
    [0, 4],
    [1, 4],
    [2, 4]
  ],
  [
    // 2
    [0, 0],
    [1, 0],
    [2, 0],
    [2, 1],
    [0, 2],
    [1, 2],
    [2, 2],
    [0, 3],
    [0, 4],
    [1, 4],
    [2, 4]
  ],
  [
    // 3
    [0, 0],
    [1, 0],
    [2, 0],
    [2, 1],
    [0, 2],
    [1, 2],
    [2, 2],
    [2, 3],
    [0, 4],
    [1, 4],
    [2, 4]
  ],
  [
    // 4
    [0, 0],
    [2, 0],
    [0, 1],
    [2, 1],
    [0, 2],
    [1, 2],
    [2, 2],
    [2, 3],
    [2, 4]
  ],
  [
    // 5
    [0, 0],
    [1, 0],
    [2, 0],
    [0, 1],
    [0, 2],
    [1, 2],
    [2, 2],
    [2, 3],
    [0, 4],
    [1, 4],
    [2, 4]
  ],
  [
    // 6
    [0, 0],
    [1, 0],
    [2, 0],
    [0, 1],
    [0, 2],
    [1, 2],
    [2, 2],
    [0, 3],
    [2, 3],
    [0, 4],
    [1, 4],
    [2, 4]
  ],
  [
    // 7
    [0, 0],
    [1, 0],
    [2, 0],
    [2, 1],
    [2, 2],
    [2, 3],
    [2, 4]
  ],
  [
    // 8
    [0, 0],
    [1, 0],
    [2, 0],
    [0, 1],
    [2, 1],
    [0, 2],
    [1, 2],
    [2, 2],
    [0, 3],
    [2, 3],
    [0, 4],
    [1, 4],
    [2, 4]
  ],
  [
    // 9
    [0, 0],
    [1, 0],
    [2, 0],
    [0, 1],
    [2, 1],
    [0, 2],
    [1, 2],
    [2, 2],
    [2, 3],
    [0, 4],
    [1, 4],
    [2, 4]
  ]
];

3. 数字拼图

第二步中给出的数字形状坐标仅适用于单个数字展示。若需并排展示多个数字,则需对每个数字的坐标进行换算,主要遵循以下两条规则:

  • 由于数字横向排列,每增加一个数字,x坐标需增加4列(包含一列数字间隔);
  • 因数字展示区域周边上下左右均空出一行或一列,故x坐标和y坐标的起始位置均从(1,1)开始。
// 根据数字形状、当前年份等信息,筛选出需要设置为亮色的卡片位置
const getHighlight = () => {
  // 获取当前年份
  let year = new Date().getFullYear() + "";
  let step = 4,
    xoffset = 1,
    yoffset = 1,
    highlight = [];

  year.split('').forEach(n => {
    highlight = highlight.concat(
      NUMBER_MATRIX[n].map(item => {
        return `${item[0] + xoffset}-${item[1] + yoffset}`;
      })
    );
    xoffset += step;
  });

  return highlight;
}

最后highlight返回的即为点坐标字符串数组,格式类似['1-1', '2-1']。

随后即可根据返回的点坐标数组绘制拼图,具体操作是为对应坐标的卡片添加高亮样式类名。

const createHighLight = async (cards, hightLight) => {
  for (let i = 0; i < hightLight.length; i++) {
    const [col, row] = hightLight[i].split('-');
    const index = Math.floor(row) * colCount + Math.floor(col);
    cards[index].className = 'item highlight'
  }
}

最终实现效果如下图所示:

背景

延伸

上文仅实现了静态数字的拼图展示。若能让数字动起来,例如实现写字效果或倒计时变动数字效果,将使拼图更加酷炫。下文将演示如何实现写字效果。

原理十分简单,只需在绘制数字拼图卡片时,将每个坐标点的绘制改为异步串行执行即可。

const createHighLight = async (cards, hightLight) => {
  for (let i = 0; i < hightLight.length; i++) {
    await new Promise((resolve, reject) => setTimeout(resolve, 100));
    const [col, row] = hightLight[i].split('-');
    const index = Math.floor(row) * colCount + Math.floor(col);
    cards[index].className = 'item highlight'
  }
  // 绘制结束后,循环绘制
  await new Promise((resolve, reject) => setTimeout(resolve, 100));
  drawData(); 
}

具体实现效果如下所示:

背景

注意:数字的绘制效果可能与正常书写笔画顺序不一致,这是因为坐标点是按从上到下、从左到右的顺序收集的。若调整坐标点顺序以符合书写笔画顺序,即可看到正常的书写效果,读者可自行尝试。

总结

本文主要分析了数字拼图效果的实现原理,核心在于先确定每个数字的形状坐标,再依据形状坐标绘制高亮卡片。最后在静态数字拼图效果基础上,借助异步串行机制,实现了手写字效果,其他效果可在此基础上自行探索。

以上就是基于JavaScript实现年份数字拼图效果的详细内容,更多关于JavaScript年份数字拼图的资料请关注本站其它相关文章!

作者最新文章