Home icon carousel
Function requirements: automatically generate page content according to the number of icons, complete the rotation chart of icon buttons; with the browser window zooming, make the page content automatically zooming;
Extension: the number of icons per page and line can be displayed by user;
Take a look at the effect:
html structure: list of simulation data.
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>index</title> </head> <body> <script type="module"> var list=[ {icon:"angular.jpg",text:"angular",src:"https://angular.cn/"}, {icon:"axure.jpeg",text:"axure",src:"https://www.axure.com.cn/"}, {icon:"baidu.jpeg",text:"baidu",src:"https://www.baidu.com"}, {icon:"bootstrap.jpg",text:"bootstrap",src:"https://www.bootcss.com"}, {icon:"csdn.jpeg",text:"csdn",src:"https://www.csdn.net"}, {icon:"css3.jpg",text:"css3",src:"https://www.runoob.com/css3/css3-tutorial.html"}, {icon:"es6.jpeg",text:"es6",src:"https://blog.csdn.net/Charissa2017/article/details/103926266"}, {icon:"github.jpeg",text:"github",src:"https://github.com"}, {icon:"google.jpeg",text:"google",src:"https://www.google.cn"}, {icon:"grunt.jpeg",text:"grunt",src:"https://www.gruntjs.net"}, {icon:"gulp.jpeg",text:"gulp",src:"https://www.gulpjs.com.cn"}, {icon:"hbuilder.jpeg",text:"hbuilder",src:"https://www.dcloud.io"}, {icon:"html5.jpeg",text:"html5",src:"https://www.w3school.com.cn/html5/index.asp"}, {icon:"javascript.jpg",text:"javascript",src:"https://www.w3school.com.cn/js/index.asp"}, {icon:"jquery.jpeg",text:"jquery",src:"https://jquery.cuishifeng.cn"}, {icon:"less.jpg",text:"less",src:"http://lesscss.cn/"}, {icon:"node.jpeg",text:"node",src:"http://nodejs.cn/"}, {icon:"npm.jpg",text:"npm",src:"https://npmjs.org"}, {icon:"ps.jpeg",text:"ps",src:"localhost"}, {icon:"react.jpeg",text:"react",src:"https://react.docschina.org"}, {icon:"sass.jpg",text:"sass",src:"https://www.sass.hk"}, {icon:"sublime.jpeg",text:"sublime",src:"https://www.sublimetext.com"}, {icon:"svn.jpeg",text:"svn",src:"https://tortoisesvn.net"}, {icon:"typescript.jpeg",text:"typescript",src:"www.tslang.cn"}, {icon:"vscode.jpg",text:"vscode",src:"https://code.visualstudio.com"}, {icon:"vue.jpeg",text:"vue",src:"https://cn.vuejs.org"}, {icon:"webpack.jpg",text:"webpack",src:"https://www.webpackjs.com"}, {icon:"xcode.jpg",text:"xcode",src:"https://developer.apple.com/xcode/"}, {icon:"xmind.jpeg",text:"xmind",src:"https://www.xmind.cn/"}, {icon:"webstorm.jpg",text:"webstorm",src:"https://www.jetbrains.com/webstorm/"}, ] import Rem from './js/Rem.js'; import Main from './js/Main.js'; init(); function init(){ Rem.init(); //_list is the data, and "path" is the picture path, which can not be transferred, //_num is the number of icons displayed on each page. If it is not transmitted, it defaults to 18. If it is not transmitted, it defaults to 6 let main=new Main({_list:list,_path:"./img/",_num:18,_lineNum:6}); //Set page background picture main.setBgImage("url(./img/bg.jpeg)"); main.appendTo("body"); } </script> </body> </html>
Main.js file: generate the page icon according to the data content to achieve the effect of carousel chart.
import Utils from "./Utils.js"; import Rem from "./Rem.js"; export default class Main{ static styleCss=false; static num;//Number of icon s displayed per page static lineNum;//Number of icon s per line index=0;//Index representing Icon page=0;//There are several pages in total, the default is 0 position=0;//Subscript for small dot prep; constructor({_list,_path,_num=18,_lineNum=6}){ //If there is an incoming path, mosaic the picture path if(_path) _list.map(item=>item.icon=_path+item.icon); //Set the number of icon s displayed per page and per line Main.num=_num; Main.lineNum=_lineNum; this.elem=this.createElem(_list); //Monitor browser zoom, change the marginop of menuList window.addEventListener("resize", Main.setMenuListStyle); } createElem(_list){ if(this.elem) return this.elem; //The outermost div container let div=Utils.createE("div"); div.className="container"; div.id="container"; //menuContainer is the container to be moved ul is the dot below div.innerHTML=`<div class="menuContainer" id="menuContainer">${this.createMenu(_list)}</div> <ul class="iconList" id="iconList">${this.createLi()}</ul>`; //Writing style Main.styles(_list); //Get DOM element Utils.getIdElem(div,this); //Click event monitored by the small dot below this.iconList.addEventListener("click",e=>this.iconClickHandler(e)); //Default first dot display this.iconChange(this.iconList.firstChild); return div; } appendTo(parent){ Utils.appendTo(this.elem,parent); } createMenu(_list){ //Figure out how many pages there are this.page=Math.ceil(_list.length/Main.num); let str=""; for(let i=0;i<this.page;i++){ //menuCon is the parent container of each page str+=`<div class="menuCon"><div class="menuList clearfix">`; //If j is less than the number to display per page, and the index is less than the length of the array - 1, each icon element is created for(let j=0;j<Main.num&&this.index<_list.length-1;j++){ str+=`<dl class="menuDl"><a href="${_list[this.index].src}" target="_blank"> <dt><img class="menuIcon" src="${_list[this.index].icon}"></dt> <dd>${_list[this.index].text}</dd> </a></dl>` this.index++; } str+=`</div></div>`; if(this.index===_list.length-1) return str; } } createLi(){ //Create small dots below let str=""; for(let i=0;i<this.page;i++){ str+=`<li></li>` } return str; } iconClickHandler(e){ this.menuContainerMove(e); this.iconChange(e.target); } menuContainerMove(e){ let clientW=document.documentElement.clientWidth; //menuContainer Mobile if(e.target.nodeName!=="LI") return; let index=Array.from(e.currentTarget.children).indexOf(e.target); this.position=index; this.menuContainer.style.left=-Rem.getRem(clientW*this.position)+"rem"; } iconChange(_target){ //Small circle switching if(_target.nodeName!=="LI") return; if(this.prep) this.prep.style.backgroundColor="#ccc"; this.prep=_target; this.prep.style.backgroundColor="rgba(255,0,0,1)"; } setBgImage(_img){ //Set the background picture of the page this.container.style.backgroundImage=_img; } static styles(_list){ if(Main.styleCss) return; Main.styleCss=true; let page=Math.ceil(_list.length/Main.num); let clientW=Rem.getRem(document.documentElement.clientWidth); Utils.insertCss(".container",{ width:clientW+"rem", height:"100%", position:"relative", overflow:"hidden", backgroundSize:"100% 100%" }) Utils.insertCss(".menuContainer",{ width:clientW*page+"rem", height:"100%", position:"absolute", left:"0", transition:"all .3s" }) Utils.insertCss(".menuCon",{ width:Math.floor(clientW)+"rem", height:"100%", float:"left" }) Main.setMenuListStyle() Utils.insertCss(".menuDl",{ listStyle:"none", padding:"0rem", margin:`0rem ${(11-1.4*Main.lineNum)/(Main.lineNum*2)}rem`, float:"left" }) Utils.insertCss(".menuDl a",{ width:"0.8rem", padding:"0.2rem 0.3rem", float:"left", color:"#333", textDecoration:"none" }) Utils.insertCss(".menuDl .menuIcon",{ width:"0.8rem", height:"0.8rem", borderRadius:"50%" }) Utils.insertCss(".menuDl dd",{ margin:"0rem", textAlign:"center", color:"#fff", fontSize:"0.16rem" }) let leftIconList=(clientW-0.4*page)/2; Utils.insertCss(".iconList",{ height:"0.2rem", listStyle:"none", padding:"0rem", margin:"0rem", position:"absolute", left:leftIconList+"rem", bottom:"0.3rem" }) Utils.insertCss(".iconList li",{ width:"0.2rem", height:"0.2rem", borderRadius:"50%", backgroundColor:"#ccc", float:"left", margin:"0rem 0.1rem", cursor:"pointer" }) Utils.insertCss(".clearfix::after",{ content:"\".\"", display:"block", overflow:"hidden", visibility:"hidden", height:"0", clear:"both" }) } //menuList style static setMenuListStyle(){ //line indicates how many lines per page let clientH=document.documentElement.clientHeight; let line=Math.ceil(Main.num/Main.lineNum); let fs = parseFloat(getComputedStyle(document.documentElement).fontSize); let topMenuList=Rem.getRem((clientH-1.42*line*fs)/2); Utils.insertCss(".menuList",{ width:"11rem", fontSize:"0", margin:`${topMenuList}rem auto 0`, }) } }
Rem.js file: implement adaptive layout when browser window zooms.
export default class Rem { static init(){ Rem.defaultStyle(); Rem.resizeHandler(); window.addEventListener("resize", Rem.resizeHandler); } static resizeHandler() { let contW = Math.floor(document.documentElement.clientWidth); let fontS = (contW / screen.width) * 100; document.documentElement.style.fontSize = fontS + "px"; } static defaultStyle(){ document.documentElement.style.fontSize = "100px"; document.documentElement.style.height = "100%"; document.body.style.height = "100%"; document.body.style.fontSize = "16px"; document.body.style.padding = "0"; document.body.style.margin = "0"; } static getRem(size) { var fontSize = parseFloat(getComputedStyle(document.documentElement).fontSize); return size / fontSize; } }
Utils.js file: is a toolkit file.
export default class Utils{ static createE(elem,style,prep){ this.elem=document.createElement(elem); if(style) for(let prop in style) elem.style[prop]=style[prop]; if(prep) for(let prop in prep) elem[prop]=prep[prop]; return this.elem; } static appendTo(elem,parent){ if(parent.constructor===String) document.querySelector(parent).appendChild(elem); else parent.appendChild(elem); } static randomNum(min,max){ return Math.floor(Math.random*(max-min)+min); } static randomColor(alpha){ alpha=alpha||Math.random().toFixed(1); if(isNaN(alpha)) alpha=1; if(alpha>1) alpha=1; if(alpha<0) alpha=0; let col="rgba("; for(let i=0;i<3;i++){ col+=Utils.randomNum(0,256)+","; } col+=alpha+")"; return col; } static insertCss(select,styles){ if(document.styleSheets.length===0){ let styleS=Utils.createE("style"); Utils.appendTo(styleS,document.head); } let styleSheet=document.styleSheets[document.styleSheets.length-1]; let str=select+"{"; for(var prop in styles){ str+=prop.replace(/[A-Z]/g,function(item){ return "-"+item.toLocaleLowerCase(); })+":"+styles[prop]+";"; } str+="}" styleSheet.insertRule(str,styleSheet.cssRules.length); } static getIdElem(elem,obj){ if(elem.id) obj[elem.id]=elem; if(elem.children.length===0) return obj; for(let i=0;i<elem.children.length;i++){ Utils.getIdElem(elem.children[i],obj); } } }
Published 60 original articles, won praise 29, visited 20000+