import * as moment from 'moment';
import { BaseLog as Log } from 'base-log'
const log = new Log('Filters');
export interface NumberFilterOption{
max?: number,
min?: number,
unit?: number,
dot?: number,
ceil?: boolean,
string?: boolean,
thousand?: boolean
}
export class Filters {
number = (number: any, opts?: {}):any => {
if (typeof number === 'object') {
opts = number;
return filter(true, opts);
} else {
opts = opts || {};
return filter(false, opts);
}
/**
* 过滤器
* @param unFilter 不立即执行过滤
*/
function filter(unFilter: boolean, opts: NumberFilterOption): Function | {} {
const max = (opts.max || opts.max == 0) ? Number(opts.max) : 10000000;
const min = Number(opts.min) || 0;
const unit = Number(opts.unit) || 1;
/*单位,即1单位为多少*/
const dot = opts.dot || 0;
const ceil = opts.ceil || false;
/*是否向上取整,默认为flase*/
const string = opts.string || false;
/*输出的数据格式,默认为数字类型*/
let isMin, isMax, isUnit, isNull;
// 判断最大最小,单位,为提示做准备
function judge(number: number | string) {
log.info('number',number);
isNull = number === undefined || number === null;
number = Number(number); // 转化为数字
isMin = number < min;
isMax = number > max;
isUnit = number % unit !== 0;
return number;
}
// 初始过滤
function initFilter(number: number): number {
if (min > max) {
log.info('错误:最小值不能大于最大值!');
}
number = Number(number) || min;
/*过滤非数字*/
// 整数部分
const int = ceil ? Math.ceil(number / unit) * unit : Math.floor(number / unit) * unit;
// 小数部分
const numberStr = number.toString();
const float = Number(parseFloat(numberStr).toFixed(dot)) - parseInt(numberStr);
return int + float;
}
//最小值过滤
function filterMin(number: number): number {
// toFixed返回string类型
const numberStr = parseFloat((isMin ? min : number).toString()).toFixed(dot);
return Number(numberStr);
}
//最大值过滤
function filterMax(number: number): number {
// toFixed返回string类型
const numberStr = parseFloat((isMax ? max : number).toString()).toFixed(dot);
return Number(numberStr);
}
// 实际过滤处理
function filterHandle(number: number | string) {
const originNumber = number;
number = judge(number);
number = initFilter(number);
/*过滤单位及取整方向*/
/*过滤最大最小*/
number = filterMin(filterMax(filterMin(number)));
const isChange = (originNumber + '') !== (number + '');
return {
value: string ? number.toString() : number,
max: max,
min: min,
unit: unit,
isNull: isNull,
isChange: isChange,
isMax: isMax, // 被最大值
isMin: isMin, // 被最小值
isUnit: isUnit // 被单位化
};
}
if (unFilter) {
return filterHandle;
} else {
return filterHandle(number);
}
}
}
// 转小数
toFloat = (input,dot,onlyNumber) => {
input = input || 0;
dot = dot || 2;
onlyNumber = onlyNumber || false;
var output = dot=='auto' ? input+'' : input.toFixed(dot);
return onlyNumber ? output.split('.')[1] : '.'+output.split('.')[1];
}
// 转整数
toInt = (input,type) => {
input = input || 0;
if(type=='floor'){
return Math.floor(input);
}else if(type=='ceil') {
return Math.ceil(input);
}else if(type=='progress'){ // 进度条特有(大于0小于1为1%,其他向下取整)
return (input>0 && input<=1) ? 1 : Math.floor(input);
}else{
return parseInt(input);
}
}
// 整数转千分位
toThousands = (num) => {
var num = (num || 0).toString(), result = '';
while (num.length > 3) {
result = ',' + num.slice(-3) + result;
num = num.slice(0, num.length - 3);
}
if (num) { result = num + result; }
return result;
}
// 货币格式
currency = (number,dot=2) => {
// 整数部分
const int = Math.floor(number);
const intStr = this.toThousands(int);
// 小数部分
const float = parseFloat((number - int).toString()).toFixed(dot);
const floatStr = float.split('.')[1] ? '.' + float.split('.')[1] : '';
return intStr + floatStr;
}
// 转中文大写数字
chinese = (n) => {
if (!/^(0|[1-9]\d*)(\.\d+)?$/.test(n)) throw new Error('数据非法');
var unit = "万千百拾亿千百拾万千百拾元角分", str = "";
n += "00";
var p = n.indexOf('.');
if (p >= 0) n = n.substring(0, p) + n.substr(p + 1, 2);
unit = unit.substr(unit.length - n.length);
for (var i = 0; i < n.length; i++)
str += '零壹贰叁肆伍陆柒捌玖'.charAt(n.charAt(i)) + unit.charAt(i);
return str.replace(/零(千|百|拾|角)/g, "零").replace(/(零)+/g, "零").replace(/零(万|亿|元)/g, "$1").replace(/(亿)万|壹(拾)/g, "$1$2").replace(/^元零?|零分/g, "").replace(/元$/g, "元整");
}
/**
* 单位转化
* @param input 输入值
* @param dot 小数点
* @param hide 隐藏单位名称,10000->1,100->100
* @param type 类型
* 类型0:10000->1万,100->100 (默认)
* 类型1:10000->1万,100->100元
* 类型2:10000->1万元,100->100元
* @returns {*}
*/
unitByWan = (input, dot?, hide?, type?) => {
dot = Number(dot || 0);
// const suffix = css ? "万" : '万';
const suffix = '万';
const isWan = input >= 10000;
input = input ? Number(input) : 0;
input = input >= 10000 ? input / 10000 : input;
input = parseFloat(input).toFixed(dot);
if(hide) return input; // 不显示单位直接返回
if(isWan) input += suffix;
if(type == 1){
if(!isWan) input += '元';
}else if(type ==2){
input += '元';
}
return input;
}
// 转换为万
unitToWan = (input, dot) => {
dot = Number(dot || 0);
input = input >= 10000 ? input / 10000 : input;
return dot > 0 ? parseFloat(input).toFixed(dot) : input;
}
// 过滤0
filterZero = (args) => {
var temp = [], number;
for (var i = 0; i < args.length; i++) {
number = Number(args[i]);
if (number > 0) {
temp.push(number);
}
}
return temp;
}
// 取最小值
min(){
const args = this.filterZero(arguments);
return args.length > 0 ? Math.min.apply(this, args) : 0;
}
// 取最大值
max(){
const args = this.filterZero(arguments);
return args.length > 0 ? Math.max.apply(this, args) : 0;
}
/**
* 打星号
* @param value 值
* @param prefix 前缀
* @param suffix 后缀
* @param count 星号数量
* @returns {string}
*/
addStar = (value, prefix, count, suffix) => {
if(!value) return;
const len = value.length;
value = value ? '' + value : '';
count = count || 4;
prefix = prefix || 0;
suffix = suffix || len - prefix - count;
function range(count) {
var arr = [];
for (var i = 0, n = count; i < n; i++) {
arr.push(i);
}
return arr;
}
var star = range(count).map(function () {
return '*';
}).join('');
if (prefix === 0) {
return star + value.substr(-suffix);
} else {
return value.substr(0, prefix) + star + value.substr(-suffix);
}
}
/*
* 添加空格
* value 要分割的值
* type 分割值类型,默认为银行卡类型
* */
space = (value, type = 'bankcard') =>{
var len = value.length;
// var last = value[len-1];
if(type == 'bankcard'){
var originValue = this.trim(value); // 原始去除空格的值
var originLen = originValue.length;
var originLast = originValue[originLen-1];
if(originLen != 1 && originLen % 4 == 1){
value = value.substr(0,len-1);
var res = value + ' ' + originLast;
return res;
}else{
return value;
}
}else{
return value
}
}
// 清除空格
trim = (value, pos = 'all') => {
if (!value) return value;
if(pos == 'end'){
return value.replace(/\s$/,'')
}else if(pos == 'start'){
return value.replace(/^\s/,'');
}else{
return value.replace(/\s/g, '');
}
}
/**
* 填充空格事件处理
* event 传入的事件
* type 空格类型,默认银行类型
*/
fillSpace = (value, del = false, type = 'bankcard') => {
var len = value.length;
var last = value[len-1];
if(del){ // 是否后退删除
if(last == ' '){
return this.trim(value,'end');
}else{
return value;
}
}else{
return this.space(value,type);
}
}
/**
* 过滤输入并分割为指定的格式
* @ input 要过滤的输入
* @ style 分割后的样式,可以是css,也可以是其他自定义样式(如手机号3-4-4分隔样式)
* @ sep 分隔符号
*/
splitBy = (input, style, sep) => {
var output;
input = input ? '' + input : '';
if (style == 'phone') { /*手机号分割格式化,类似 186-1601-6872*/
return splitForPhone(sep);
} else if (style == 'bankcard') { /*银行卡号分割格式化*/
return splitForBankcard(sep);
} else if (input.indexOf('天') > -1) {
return splitByDefault('天');
} else if (input.indexOf('年') > -1) {
return splitByDefault('年');
} else {
return splitByDefault(sep);
}
// 手机号分隔方法
function splitForPhone(sep) {
sep = sep || ' ';
return input.replace(/\s/g, "").replace(/(\d{3})/, "$1" + sep).replace(/(\d{4})/, "$1" + sep);
}
// 银行卡号分隔方法
function splitForBankcard(sep) {
sep = sep || ' ';
return input.replace(/\s/g, "").replace(/(\d{4})/g, "$1" + sep);
}
// 默认分隔方法
function splitByDefault(sep) {
sep = sep || ' ';
input = input.split(sep)[0];
return output = style
? input + "" + sep + ""
: input;
}
}
substr = (input,length,suffix?) => {
suffix = suffix || '...';
if(input && length){
input = input.length>length
? (length > 0 ? input.substr(0,length) + suffix : input.substr(length) + suffix)
: input;
return input;
}else{
return input;
}
}
// 默认数字格式化
format = (number,dot?) => {
number = number > 0
? this.currency(number, dot > -1 ? dot : null)
: parseFloat(number).toFixed(dot);
return number;
}
// 默认日期过滤
moment = (input,outFormat,inFormat) => {
inFormat = inFormat || "YYYYMMDDHHmmss";
outFormat = outFormat || "YYYY-MM-DD HH:mm:ss";
return input
? moment(input,inFormat).format(outFormat)
: moment().format(outFormat);
}
}