zoukankan      html  css  js  c++  java
  • 实现一个炫酷的随机标签排列效果(颜色随机,大小随机,成菱形排列的列表)

    实现一个文字颜色随机,字体大小成正态分布,整体呈菱形的排列的标签列表;

    如何实现一个如下图随机排布的标签列表(vue语法):
    dome示例: http://39.106.166.212/tag

    首先假设我们可以拿到一个标签列表的数组,这里将一步步实现如图效果:

    1、创建tag组件,编写 随机颜色方法 和 大小成正态分布的方法 实现颜色和大小随机的文字标签;

    (1)编写随机颜色方法$RandomColor

    通过随机生成一个有效范围内的rgb值即可实现;

    /*随机颜色rgb*/
    const $RandomColor = function(){
         var r=Math.floor(Math.random()*256);
         var g=Math.floor(Math.random()*256);
         var b=Math.floor(Math.random()*256);
         return "rgb("+r+','+g+','+b+")";
    }

    为了防止与背景颜色重合也可hsl模式生成,降低明度防止与背景重合;

    /*随机颜色hsl*/
    const $RandomColor2 = function() {
        return "hsl(" + 
            Math.round(Math.random() * 360) + "," + 
            Math.round(Math.random() * 100) + '%,' + 
            Math.round(Math.random() * 80) + '%)';
    }
    (2)编写实现正态分布的方法$Normal

    js中只有随机分布,通过网上查找方法可以通过Box-muller算法将两个随机分布拼接为一个正态分布:
    参考:
    https://www.cnblogs.com/zztt/p/4025207.html
    https://en.wikipedia.org/wiki/Box%E2%80%93Muller_transform,写成js为
    入参为均值和方差:

    /*利用Box-Muller方法极坐标形式    使用两个均匀分布产生一个正态分布*/
    const $Normal = function(mean,sigma){
        var u=0.0, v=0.0, w=0.0, c=0.0;
        do{
            //获得两个(-1,1)的独立随机变量
            u=Math.random()*2-1.0;
            v=Math.random()*2-1.0;
            w=u*u+v*v;
        }while(w==0.0||w>=1.0)
        c=Math.sqrt((-2*Math.log(w))/w);
        return mean+u*c*sigma;
    }

    自此一个随机颜色和大小的tag组件完成

    2、将数组随机排列为菱形(中间多两头少的列表)

    首先在created中从接口获取到如下一个数组列表,这里我们不使用最大值参数,默认为剩余的一半;

    (1)编写随机拆分一个数的方法$RandomSplit获取一组和为列表长度的数组;
    /*
     * 随机拆分一个数
     * params 总和,个数,最大值 {num}
     */


    const $RandomSplit = function(total,nums,max{
        let rest = total;
        let result = Array.apply(null, { length: nums })
            .map((n, i) => nums - i)
            .map(n => {
                const v = 1 + Math.floor(Math.random() * (max | rest / n * 2 - 1));
                rest -= v;
                return v;
            });
        result[nums - 1] += rest;
        return result;
    }

    下图是将44随机拆分为8个数的和,

    (2)编写$NormalSort方法将上面获取到的数随机排列为两端小中间大数组;

    大概思路为先排序,然后每次去两个数分别放置在两端,放置的过程汇总计算两端和,判断大小选择性放置,防止两端排布不均匀

    /*类正态排序*/
    const $NormalSort = function(arr){
        var temp = [], i = 0, l = arr.length,leftTo=0,rightTo=0,
        sortArr = arr.sort(function(a,b){return b-a}); //先将数组从大到小排列得到 [7,6,5,5,4,3,2,1]
        while(arr.length>1){
            let a = arr.pop();
            let b= arr.pop();
            if(leftTo<rightTo){
                temp[i] = b;
                temp[l-(i+1)] = a;
            }else{
                temp[i] = b;
                temp[l-(i+1)] = a;
            }
            i++;
        }
        return temp;
    }

    我们该方法将上一步的数组重新排序为:

    (3)最后将list数据按照上一步获取的数据结构从新生成一个可供v-for使用的数据结构;
    computed:{
            tags(){
                this.list =  $NormalSort($RandomSplit(this.tagList.length,8));//获取数据结构
                let temp = this.tagList.sort(function(a,b){    //重新随机排序
                    return Math.random()>.5 ? -1 : 1
                }).concat();
                return this.list.map((v,k) => {//根据list生成数据结构
                    return temp.splice(0,v);
                })
            }

        },

    html代码

    <div v-for="(item,index) in tags" :key="index"  class="tag-body-tags-li">
                           <Tag v-for="(tag,index) in item" :key="tag.id" :tname="tag.name" ></Tag>
                       </div> 
  • 相关阅读:
    oracle 静默安装
    浅析hybrid模式下地支付宝钱包和微信
    LeetCode96_Unique Binary Search Trees(求1到n这些节点能够组成多少种不同的二叉查找树) Java题解
    hdu 5411 CRB and Puzzle 矩阵高速幂
    Hadoop作业性能指标及參数调优实例 (三)Hadoop作业性能參数调优方法
    实现Android4.4系统设置分页滑动浏览功能
    oracle 数据库中数据导出到excel
    Nginx配置upstream实现负载均衡
    公司须要内部的地图服务,准备自己去开发可是成本太高,如今有没有专门为企业提供GIS地图开发的产品呀?大概价格多少?
    图片在内存中的占用的空间大小
  • 原文地址:https://www.cnblogs.com/pangys/p/10570189.html
Copyright © 2011-2022 走看看