Preface
Image loading optimization plays an important role in the performance of a website . So we use Vue To operate a wave .
remarks
The following optimization one 、 The two columns of optimization are encapsulated in Vue In the tool function of , So please read it carefully , Or if you copy it directly , Fallible .
resources
Vue.js
Element UI
Optimize one : Picture loading animation
Only after the image is loaded can the image be displayed , Loading animation ends . We use Element UI
Medium loading Components
To be used as a loaded animation . Suppose a variable loading
The initial value is true
, When the picture is loaded, it is false
.
// Image loading imgLoad:(src)=>{ let bgImg = new Image(); bgImg.src = src; // Get the background image of url bgImg.onerror = () => { console.log("img onerror"); }; bgImg.onload = () => { // After the background image is loaded successfully Remove loading console.log(" Loading complete "); return false }; },
Optimization II : Picture lazy loading
When the picture is in the view , Will ask for pictures . This optimization can not only be used in the home page of the website , It can also be used in web pages with more pictures , Save performance . Don't talk much , Let's achieve a wave of .
// Get the picture distance getRect(element) { const rect = element.getBoundingClientRect(); const top = !document.documentElement.clientTop ? document.documentElement.clientTop : 0; const left = !document.documentElement.clientLeft ? document.documentElement.clientLeft : 0; return { top: rect.top - top, bottom: rect.bottom - top, left: rect.left - left, right: rect.right - left } }, // Package picture lazy loading lazyload() { let img = document.getElementsByTagName("img"); let len = img.length; let n = 0; // Store where pictures are loaded , Avoid traversing from the first picture every time // Height of visible area const seeHeight = window.innerHeight||document.documentElement.clientHeight||document.body.clientHeight; for (let i = n; i < len; i++) { // If the distance between the picture and the top is less than the sum of the height of the visible area and the distance between the scroll bar and the top , Just show the picture let rectTop = this.getRect(img[i]).top; // there this.getRect() It's used to get the location of the picture . let rectBottom= this.getRect(img[i]).bottom; if (rectTop > 0 && rectTop < seeHeight && rectBottom > 0 && rectBottom < seeHeight) { // It's already in the view img[i].getAttribute("src") === ""?(img[i].setAttribute('class', 'opacity'),img[i].src = img[i].getAttribute("data-src")):n = i + 1; } else if(rectTop < seeHeight && rectBottom >= seeHeight){ // Entering the view img[i].getAttribute("src") === ""?(img[i].setAttribute('class', 'opacity'),img[i].src = img[i].getAttribute("data-src")):n = i + 1; } } }
The name of the setting class here opacity
You can set your own animation according to your favorite . This is what I write here , You can refer to it .
.opacity { animation: 0.3s ani linear; } @keyframes ani { 0% { opacity: 0; transform: translateX(-200px); } 100% { opacity: 1; transform: translateX(0px); } }
Integration Kit
We do Vue Scaffold project , Many repeated code segments or method functions are often used , So we can package it , Use it when you want to , It also avoids code redundancy .
1、 stay src Created in the root directory util Folder , It creates util.js;
2、 stay src In the root directory main.js Type the following code , introduce util.js, And global registration ;
import utils from './util/util' Vue.prototype.$utils=utils
3、 edit util.js;
export default { // Image loading imgLoad:(src)=>{ let bgImg = new Image(); bgImg.src = src; // Get the background image of url bgImg.onerror = () => { console.log("img onerror"); }; bgImg.onload = () => { // After the background image is loaded successfully Remove loading console.log(" Loading complete "); return false }; }, // Get element distance getRect(element) { const rect = element.getBoundingClientRect(); const top = !document.documentElement.clientTop ? document.documentElement.clientTop : 0; const left = !document.documentElement.clientLeft ? document.documentElement.clientLeft : 0; return { top: rect.top - top, bottom: rect.bottom - top, left: rect.left - left, right: rect.right - left } }, // Package picture lazy loading lazyload() { let img = document.getElementsByTagName("img"); let len = img.length; let n = 0; // Store where pictures are loaded , Avoid traversing from the first picture every time // Height of visible area const seeHeight = window.innerHeight||document.documentElement.clientHeight||document.body.clientHeight; for (let i = n; i < len; i++) { // If the distance between the picture and the top is less than the sum of the height of the visible area and the distance between the scroll bar and the top , Just show the picture let rectTop = this.getRect(img[i]).top; let rectBottom= this.getRect(img[i]).bottom; if (rectTop > 0 && rectTop < seeHeight && rectBottom > 0 && rectBottom < seeHeight) { img[i].getAttribute("src") === ""?(img[i].setAttribute('class', 'opacity'),img[i].src = img[i].getAttribute("data-src")):n = i + 1; } else if(rectTop < seeHeight && rectBottom >= seeHeight){ img[i].getAttribute("src") === ""?(img[i].setAttribute('class', 'opacity'),img[i].src = img[i].getAttribute("data-src")):n = i + 1; } } } }
example
We encapsulate the utility functions , So we use it , Use here this.$utils
Call each method .
application : Picture loading animation
We used it on a page like this ,this.bannerSrc
It's the picture address ,this.loading
Is the state of loading animation .
mounted() { if (!this.$utils.imgLoad(this.bannerSrc)) { this.loading = false; } }
application : Picture lazy loading
1、 Set up keep-alive
The page of
methods: { // Lazy loading pictures scrollView() { const fn = this.$utils.lazyload.bind(this.$utils); window.addEventListener("scroll", fn); // Leave component this.$once("hook:deactivated", function() { window.removeEventListener("scroll", fn); }); } }, activated() { this.scrollView(); }, mounted() { this.$utils.lazyload(); // initialization }
2、 Not set keep-alive
The page of
mounted() { this.$utils.lazyload(); window.addEventListener("scroll", this.$utils.lazyload.bind(this.$utils)); }, beforeDestroy(){ window.removeEventListener("scroll", this.$utils.lazyload.bind(this.$utils)); }
IntersectionObserver
This is a h5 Of api,IntersectionObserver. But the compatibility is not good , You can try .
const io = new IntersectionObserver(dom); let imgs = document.querySelectorAll('[data-src]'); function dom(entries){ entries.forEach((item) => { if(item.isIntersecting){ console.log(1) item.target.src = item.target.dataset.src io.unobserve(item.target) } }) } imgs.forEach((item)=>{ io.observe(item) })
Conclusion
If it works , Just pay attention ~
*
author :「Vam The golden bean road 」
Main areas :「 The front-end development 」
My WeChat :「maomin9761」
WeChat official account :「 The road ahead 」
*
This article is from the official account of WeChat The road ahead original https://www.helloworld.net/redirect?target=https://mp.weixin.qq.com/s/y0fz8d-9P12cW3F8QQLzXA, If there is any infringement , Please contact to delete .