美文网首页
TweenOne数字变化 超过最大数值后,显示错误解决方案

TweenOne数字变化 超过最大数值后,显示错误解决方案

作者: 日不落000 | 来源:发表于2020-01-15 14:53 被阅读0次
需求: TweenOne显示数字组件当数据太大的时候显示数据不对,需要显示正确数据。
解决过程:

找到以下相关issue:
https://github.com/ant-design/ant-motion/issues/210
https://github.com/ant-design/ant-motion/issues/234
更新到最新版本后问题仍然存在,然后去查看了源代码看到插件内部没有使用bignumber进行处理,数据大的时候还是会有问题,因此决定使用bignumber对这个插件进行改动使其支持bignumber,进而满足业务需求。

原因:

使用的插件

import Children from 'rc-tween-one/lib/plugin/ChildrenPlugin';

没有使用bignumber进行处理。

解决方案:

修改这个插件使其满足需要,修改前的代码如下:
https://github.com/react-component/tween-one/blob/master/src/plugin/ChildrenPlugin.jsx
修改后的核心代码如下:


ChildrenPlugin.prototype = {
  setRatio(ratio) {
    const { valueStr, floatLength, formatMoney } = this.vars;
    let v ;
    // = (value - this.start.value) * ratio + this.start.value;
    v = new BigNumber(valueStr).minus(this.start.value).multipliedBy(ratio).plus(this.start.value);
    if (typeof floatLength === 'number') {
      if (floatLength) {
        v = YData.removeTail0(v.toFixed(floatLength));//删除尾部无效的0
      } else {
        v = v.toFixed(0);
      }
    }
    v = formatMoney ? this.toMoney(v, formatMoney) : v;
    this.target.innerHTML = v;
  },
};

添加了字段:valueStr将字符串传到AnimateNumber

import React from 'react';
import TweenOne from 'rc-tween-one';
// import Children from 'rc-tween-one/lib/plugin/ChildrenPlugin';
import config from 'utils/config';
import YData from 'appRoot/utils/YData';
import BigNumber from 'bignumber.js';


const ChildrenPlugin = function (target, vars) {
  this.target = target;
  this.vars = vars;
};

ChildrenPlugin.prototype = {
  name: 'Children',
  getAnimStart() {
    const { formatMoney } = this.vars;
    const opts = {
      thousand: formatMoney && formatMoney.thousand || ',',
      decimal: formatMoney && formatMoney.decimal || '.',
    };
    const rep = new RegExp(`\\${opts.thousand}`, 'g');
    this.start = this.vars.startAt || {
      value: parseFloat(this.target.innerHTML.replace(rep, '').replace(opts.decimal, '.')) || 0
    };
  },
  toMoney(v, _opts) {
    const opts = {
      thousand: _opts.thousand || ',',
      decimal: _opts.decimal || '.',
    };
    const negative = parseFloat(v) < 0 ? '-' : '';
    const numberArray = v.toString().split('.');
    const base = Math.abs(parseInt(numberArray[0], 10)).toString();
    const mod = base.length > 3 ? base.length % 3 : 0;
    const decimal = numberArray[1];
    return `${negative}${mod ? `${base.substr(0, mod)}${opts.thousand}` : ''}${
      base.substr(mod).replace(/(\d{3})(?=\d)/g, `$1${opts.thousand}`)}${
      decimal ? `${opts.decimal}${decimal}` : ''
    }`;
  },
  setRatio(ratio) {
    const { valueStr, floatLength, formatMoney } = this.vars;
    let v ;
    // = (value - this.start.value) * ratio + this.start.value;
    v = new BigNumber(valueStr).minus(this.start.value).multipliedBy(ratio).plus(this.start.value);
    const vString = v.toString();
    console.log('vString',vString)
    if (typeof floatLength === 'number') {
      if (floatLength) {
        v = YData.removeTail0(v.toFixed(floatLength));//删除尾部无效的0
      } else {
        v = v.toFixed(0);
      }
    }
    v = formatMoney ? this.toMoney(v, formatMoney) : v;
    this.target.innerHTML = v;
  },
};

const Children = ChildrenPlugin;

TweenOne.plugins.push(Children);

/**
 * 使 TweenOne 支持bignumber显示,添加了plugin Children 字段 valueStr 
 *             <AnimateNumber
                valueStr={valueStr} //valueStr = '1234567890123456789.1234567899';
                value={Number(valueStr)}
                floatLength={2}
              />
 * 
 * @param {*} props 
 */
const AnimateNumber = (props) => {
  const { value, valueStr, formatMoney = true, floatLength = config.MAX_DECIMAL_DIGITS, duration = 1000, style } = props;
  const animation = value || value === 0 ? {
    Children: {
      value: Number(valueStr),
      valueStr: `${valueStr}`,
      floatLength,
      formatMoney,
    },
    duration,
  } : null;
  return (
    <TweenOne
      animation={animation}
      style={style}
    >
      0
    </TweenOne>
  );
};

export default AnimateNumber;

参考:
https://motion.ant.design/components/tween-one#components-tween-one-demo-easingPath

相关文章

网友评论

      本文标题:TweenOne数字变化 超过最大数值后,显示错误解决方案

      本文链接:https://www.haomeiwen.com/subject/wletzctx.html