SpringBoot+Vue3+Element Plus 打造分布式存储系统

biancheng1 · · 761 次点击 · · 开始浏览    

### download:[SpringBoot+Vue3+Element Plus 打造分布式存储系统](https://www.zxit666.com/6249/) 三则为细品兔图,鼠标击之,可得一黑盒,黑盒中位,即为兔图,鼠标复击之,即可关之。由之可见,其有动效,如何实之?需有二者,其一为定时器,其二乃以透明度为效,如是娓娓道来。 自译: 第三个局部则是细致的预览图片,经过运用鼠标点击图片,就能够得到一个黑色的背景遮罩,在黑色背景遮罩的中间位置,就是兔兔的图片,鼠标再次点击就能够关闭细致预览。从这里我们能够看到,这个关闭和翻开都是有动画效果的,那么我们如何完成这个动画效果呢?第一局部很显然我们需求用到定时器,第二局部就是经过修正透明度到达效果,接下来让我们逐个来看每一局部的完成吧。 其一,构之 HTML 元素: 自译: 第一步,当然是编写 html 元素。 <div class="rabbit-box"> <header class="rabbit-box-header"> <button type="button" class="rabbit-box-header-btn">换一换</button> </header> <div class="rabbit-box-album"></div> </div> 如上所示,应知外有容器元素,内有标题元素与兔图容器元素,其内更有一按钮元素,使之可更兔图,兔图容器之内,乃元素抽成,如之奈何? 自译: 正如上面所展现的,我们应该晓得最外层有一个容器元素,里面又有一个标题元素以及一个装满兔子图片的容器元素,在标题元素中还有一个按钮元素,能够让它来随机改换兔子图片,兔子图片内部的元素正好是动态生成的元素,我们应该怎样做呢? 使我等估之如下: 自译: 让我们猜想 html 元素构造应该如下所示: <div class="rabbit-box-album-item" data-title="..." data-content="..."> <img src="..." alt="图片加载中" class="rabbit-box-album-item-img" /> </div> 甚易,构之大成,因此画之美样,但其乃易,故可径直赏码矣。 自译: 太简单了,构建元素大功告成,因而我们只需求用 css 款式美化一下即可,不过由于这也同样简单,因而我们只需求直接查看代码即可。 * { margin: 0; padding: 0; box-sizing: border-box; } body, html { height: 100%; overflow: hidden; } body { overflow-y: auto; padding: 2em; background: linear-gradient(135deg, #f184e8 10%, #e209e9 90%); } .rabbit-box { width: 100%; max-width: 1200px; display: flex; justify-content: center; align-items: center; flex-direction: column; margin: auto; } .rabbit-box-header { width: 100%; background: linear-gradient(135deg, #ffc5e7 10%, #fa6cc4 90%); height: 60px; border-radius: 10px 10px 0 0; text-align: center; line-height: 60px; } .rabbit-box-header-btn { outline: none; border-radius: 4px; padding: 0.4rem 1rem; border: none; transition: all 0.4s cubic-bezier(0.075, 0.82, 0.165, 1); display: inline-block; color: #fff; cursor: pointer; background: linear-gradient(135deg, #f173bd 10%, #e71b92 90%); letter-spacing: 2px; font-size: 20px; font-family: '微软雅黑', '楷体'; } .rabbit-box-header-btn:hover, .rabbit-box-header-btn:active { background: linear-gradient(135deg, #f060b4 10%, #e60f8c 90%); } .rabbit-box-album { width: 100%; height: 100%; display: flex; flex-wrap: wrap; } .rabbit-box-album-item { width: 33.3333%; height: 300px; overflow: hidden; box-shadow: 0 0 12px rgba(0, 0, 0, 0.5); cursor: pointer; position: relative; } .rabbit-box-album-item::before, .rabbit-box-album-item::after { position: absolute; color: #fff; font-size: 15px; width: 100%; height: 50%; display: flex; justify-content: center; align-items: center; left: 0; transition: transform 0.4s ease-in-out; text-overflow: ellipsis; overflow: hidden; white-space: nowrap; } .rabbit-box-album-item::before { content: attr(data-title); top: 0; background-color: rgba(0, 0, 0, 0.85); transform: translateY(-100%) scale(0); } .rabbit-box-album-item::after { content: attr(data-content); bottom: 0; background-color: rgba(0, 0, 0, 0.65); border-top: 1px solid #fff; transform: translateY(100%) scale(0); } .rabbit-box-album-item:hover.rabbit-box-album-item::before, .rabbit-box-album-item:hover.rabbit-box-album-item::after { transform: translateY(0) scale(1); } .rabbit-box-album-item-img { display: block; width: 100%; height: 100%; object-fit: cover; } @media screen and (max-width: 900px) { .rabbit-box-album-item { width: 100%; height: 200px; } } ::-webkit-scrollbar { width: 4px; height: 4px; background-color: #f1f1f1; } ::-webkit-scrollbar-thumb { width: 4px; height: 4px; background-color: #ee4f9e; } 甚易,皆凡样也,故无需多言以述之,使我等望功码。 自译: 太简单了,都是一些常规的规划款式,因而没有必要说太多来解释,让我们来看功用代码的完成吧。 其一,有一结构函数,函数一对参,参内二属,一为 resources,二为 el,resources 乃对组,对内有三属,分为 src,title,content,望文生义,src 为兔图之源,title 为标题,content 为内容,el 则为容器元素,值乃字符,顾可得如下: 自译: 首先我们会创立一个结构函数,结构函数有一个对象参数,对象参数里面是二个属性,第一个是 resources,第二个则是 el,resources 为一个对象数组,对象里面分别有三个属性,分别是 src,title,content,从名字就能想到其中的含义,src 代表兔兔图片的途径,title 就是标题,content 就是内容,el 则代表是容器元素,是一个字符串,因而我们就能够得到如下代码: const resources = [ { src:"./images/rabbit-1.png", title:"心爱的兔兔-1", content:"雄兔脚扑朔,雌兔眼迷离。" }, { src:"./images/rabbit-2.png", title:"心爱的兔兔-2", content:"兔走乌驰人语静,满溪红袂棹歌初。" }, { src:"./images/rabbit-3.png", title:"心爱的兔兔-3", content:"白兔捣药成,问言与谁餐?" }, { src:"./images/rabbit-4.png", title:"心爱的兔兔-4", content:"兔丝附蓬麻,引蔓故不长。" }, { src:"./images/rabbit-5.png", title:"心爱的兔兔-5", content:"白兔捣药秋复春,嫦娥孤栖与谁邻。" }, { src:"./images/rabbit-6.png", title:"心爱的兔兔-6", content:"吴质不眠倚桂树,露脚斜飞湿寒兔。" }, { src:"./images/rabbit-7.png", title:"心爱的兔兔-7", content:"茕茕白兔,东走西顾。" }, { src:"./images/rabbit-8.png", title:"心爱的兔兔-8", content:"可笑常娥不了事,走却玉兔来人世。" }, { src:"./images/rabbit-9.png", title:"心爱的兔兔-9", content:"兔走乌驰人语静,满溪红袂棹歌初。" } ]; const rabbit = new RabbitAlbum({ resources: , el:".rabbit-box-album" }) 使我等见结构函数如下: 自译: 让我们来看看结构函数的完成如下: class RabbitAlbum { constructor(options) { this.animation = Object.create(null); this.initAnimation(); this.container = RabbitAlbum.$(options.el) || document.body; this.imageList = options.resources || []; this.createAlbum(); } } 如上初始所属,内有二方,其一为 initAnimation,意即初始动效,其二为 createAlbum,意即生兔图也,三属分为 animation,container,imgList,即动效,容器元素,兔图对组。 自译: 以上我们初始化一切的属性,里面有二个办法,第一个办法就是 initAnimation,意义就是初始化动画,第二个办法就是 createAlbum,意义就是生成兔子图片,三个属性分别是 animation,container,imgList,也就是动画效果,容器元素,兔兔图片对象数组。 有一$,乃是静方,使我等见之如下: 自译: 有一个$办法,就是一个静态办法,让我们来看看如下所示: RabbitAlbum.$ = (selector, el = document) => el.querySelector(selector); 甚易,其乃 document.querySelector 方包耳!。另有二静方,为 getCss,\_create,使我等见之如下: 自译: 太简单了,就是 document.querySelector 办法的包装而已。另外还有二个静态办法,那就是 getCss,\_create,让我们来看看如下所示: RabbitAlbum.getCss = (el, prop) => window.getComputedStyle(el, null)[prop]; RabbitAlbum._create = name => document.createElement(name); getCss 为 window.getComputedStyle 方包耳!,\_create 为 document.createElement 方包耳!甚易,如视 createAlbum 方,后见 initAnimation 方。 自译: getCss 就是 window.getComputedStyle 办法的包装而已,\_create 就是 document.createElement 办法的包装而已,接下来我们先来看 createAlbum 办法,最后再看 initAnimation 的完成。 createAlbum(){ const randomSort = this.imageList.sort((a,b) => Math.random() > 0.5 ? -1 : 1); let template = ''; randomSort.forEach(item => { template += ` <div class="rabbit-box-album-item" data-title="${item.title}" data-content="${item.content}"> <img src="${item.src}" alt="图片加载中" class="rabbit-box-album-item-img"> `; }); this.container.innerHTML = template; this.container.addEventListener('click',e => { if(e.target.className.includes('rabbit-box-album-item')){ if(e.target.firstElementChild){ const src = e.target.firstElementChild.getAttribute('src'); this.preview(src); } } }) } 其一,乱序兔图对组,编之生兔图元素,入 container 为子元素,为 container 元素增击事,断之乃图元素,而取 src 属,调 preview 方也。 自译: 首先将兔图对象数组打乱次第,遍历这个数组生成兔图元素,添加到 container 容器元素中作为子元素,然后给 container 元素添加点击事情,判别能否是图片元素,然后获取 src 属性,调用 preview 办法。 使我等见 preview 方如下: 自译: 让我们来看看 preview 办法如下: preview(src,time = 600){ const imgTag = RabbitAlbum._create('img'), imgMask = RabbitAlbum._create('div'); imgMask.style.cssText += 'position:fixed;left:0;top:0;right:0;bottom:0;background:rgba(0,0,0,0.5);z-index:9999;'; imgTag.style.cssText += 'position:absolute;left:50%;top:50%;transform:translate(-50%,-50%);width:auto;height:auto;border-radius:5px;'; imgMask.id = 'previewMask'; imgTag.src = src; imgMask.appendChild(imgTag); const mask = RabbitAlbum.$("#previewMask"); if (!mask) { document.body.appendChild(imgMask); this.animation.fadeIn(imgMask, time); } else { document.body.replaceChild(imgMask, mask); this.animation.fadeIn(imgMask, time); } imgMask.addEventListener('click', e => { const el = e.target.tagName.toLowerCase().indexOf('img') > -1 ? e.target.parentElement : e.target; this.animation.fadeOut(el, time); }, false) } 其终身 img 元素与 div 元素,分为增样,后入 body 元素,调 fadeIn 方见之,为 div 元素增击事,因此隐之。 自译: 第一步生成 img 和 div 元素,分别添加款式,然后添加到 body 元素中,然后调用 fadeIn 办法显现它们,并且为 div 元素添加点击事情,从而到达躲藏它们。 何知 fadeIn 方与 fadeOut 方焉? 如之奈何?使我等观之。其终身时管器,如下: 自译: 是不是有些熟习 fadeIn 办法和 fadeOut 办法?如何完成呢?让我们一同来看看吧,首先是需求创立一个时间管理器,如下: class TimerManager { constructor() { this.timers = []; this.args = []; this.isTimerRun = false; } add(timer, args) { this.timers.push(timer); this.args.push(args); this.timerRun(); } timerRun() { if (!this.isTimerRun) { const timer = this.timers.shift(), args = this.args.shift(); if (timer && args) { this.isTimerRun = true; timer(args[0], args[1]); } } } next() { this.isTimerRun = false; this.timerRun(); } } TimerManager.makeTimerManage = element => { if ( !element.TimerManage || element.TimerManage.constructor !== TimerManager ) { element.TimerManage = new TimerManager(); } }; TimerManager.runNext = element => { if (element.TimerManage && element.TimerManage.constructor === TimerManager) { element.TimerManage.next(); } }; 其效如何? 生组而存定时器,后逐个取出调之,甚易,使我等观 fadeIn 方与 fadeOut 方,二者所似,知其一便知其二也,皆以定时器增减 opacity 矣。 自译: 这个时间管理器的用途是什么呢?也就是创立一个数组存储定时器,然后每次都从这个数组当中取出一个,然后调用它,这很简单,让我们来说看看 fadeIn 与 fadeOut 办法的完成。两个办法的完成原理都很相似,晓得其中一个办法的完成便晓得另一个办法的完成,它们都是经过定时器增加或者是减少 opacity 即可。 fadeIn(element,time){ element.style.transition = "opacity" + time + " ms"; if (!Number(RabbitAlbum.getCss(element, 'opacity')) || !parseInt(RabbitAlbum.getCss(element, 'opacity')) <= 0) { element.style.display = "none"; element.style.opacity = 0; let curAlpha = 0, addAlpha = 1 * 100 / (time / 10), timer = null; let handleFade = function () { curAlpha += addAlpha; if (element.style.display === 'none'){ element.style.display = "block"; } element.style.opacity = (curAlpha / 100).toFixed(2); if (curAlpha >= 100) { if (timer) clearTimeout(timer); element.style.opacity = 1; TimerManager.runNext(element); } else { timer = setTimeout(handleFade, 10); } } handleFade(); } else { TimerManager.runNext(element); } } 甚易,后使我等观 initAnimation 方,如下: 很简单,最后让我们来看看 initAnimation 办法 的完成,如下所示: initAnimation(){ const _self = this; if(typeof this.animation['fadeIn'] !== 'function'){ this.animation['fadeIn'] = function(element,time = 400){ TimerManager.makeTimerManage(element); element.TimerManage.add(_self.fadeIn, arguments); return this; } } if(typeof this.animation['fadeOut'] !== 'function'){ this.animation['fadeOut'] = function(element,time = 400){ TimerManager.makeTimerManage(element); element.TimerManage.add(_self.fadeOut, arguments); return this; } } } 甚易,初始 fadeIn 方与 fadeOut 方,后入元素矣。 自译: 很简单,就是初始化 fadeIn 和 fadeOut 办法,把它们添加到元素当中就行了。 综上,可得作兔器也,使我等观之。

有疑问加站长微信联系(非本文作者))

入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

761 次点击  
加入收藏 微博
暂无回复
添加一条新回复 (您需要 登录 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传