1. Introduction to project implementation
Vue Project Construction Refer to Webpack4 VUE Project Construction
Vuepress is the official document of vuepress.vuejs.org
Github Pages + gh-page
The project addressGithub.com/zxpsuper/vu…
File address zxpsuper.github. IO /vui-vue
Zxpsuper.github. IO /vui-vue/com…
In the stage of self exploration, looking forward to leaving your valuable advice!
2. Implement Throttle
- First, write a general function for anti-shake throttling
/** * @param {function} func function * @param {number} time * @param {Boolean} isDebounce is a security component * @param {this} CTX this points to */
const debounce = (func, time, isDebounce, ctx) = > {
var timer, lastCall, rtn;
if (isDebounce) {
rtn = (. params) = > {
if (timer) clearTimeout(timer);
timer = setTimeout((a)= > {
func.apply(ctx, params);
}, time);
};
} else {
rtn = (. params) = > {
const now = new Date().getTime();
if (now - lastCall < time && lastCall) return;
lastCall = now;
func.apply(ctx, params);
};
}
return rtn;
};
Copy the code
- Using Abstract Components
export default {
name: 'Throttle'.abstract: true.props: {
time: {
type: Number.default: 800,},events: {
type: String.default: 'click',},isDebounce: {
type: Boolean.default: false,
},
},
created() {
this.eventKeys = this.events.split(', '); // Separate events
this.originMap = {}; // Store events for rerender to compare with child events
this.debouncedMap = {}; // Save the anti-shake throttling event
},
render() {
const vnode = this.$slots.default[0];
this.eventKeys.forEach(key= > {
const target = vnode.data.on[key];
if (target === this.originMap[key] && this.debouncedMap[key]) {
vnode.data.on[key] = this.debouncedMap[key];
} else if (target) {
this.originMap[key] = target;
this.debouncedMap[key] = debounce(
target,
this.time,
this.isDebounce,
vnode
);
vnode.data.on[key] = this.debouncedMap[key]; // Override events for child components}});returnvnode; }};Copy the code
3. Use components
Global or component registration is required. Only the global registration code is shown here:
Vue.component("Throttle", Throttle);
Copy the code
Usage:
<Throttle :time="5000" isDebounce>
<span @click="decounceFunction">
<Button color="purple" light>If the button</Button>
</span>
</Throttle>
Copy the code
4. Existing problems and solutions
When a page element is updated (rendered) during the anti-shake throttling time (the page can be modified with a timer, such as a page countdown), this component executes again
this.debouncedMap[key] = debounce(target,this.time,this.isDebounce,vnode);
Copy the code
The current solution is to add v-once to the child element of this component, as follows:
<Throttle :time="5000" isDebounce>
<span @click="decounceFunction" v-once>
<Button color="purple" light>If the button</Button>
</span>
</Throttle>
Copy the code
There is a better way to solve this problem, please leave a comment in the comments section
5. Complete code
/* * @descript: a description component that can be used only if no other render is available during the waiting time. 2019-04-09 14:21:18 * @Last Modified by: super * @Last Modified time: 2019-10-24 16:37:43 */
const debounce = (func, time, isDebounce, ctx) = > {
var timer, lastCall, rtn;
if (isDebounce) {
rtn = (. params) = > {
if (timer) clearTimeout(timer);
timer = setTimeout((a)= > {
func.apply(ctx, params);
}, time);
};
} else {
rtn = (. params) = > {
const now = new Date().getTime();
if (now - lastCall < time && lastCall) return;
lastCall = now;
func.apply(ctx, params);
};
}
return rtn;
};
export default {
name: 'Throttle'.abstract: true.props: {
time: {
type: Number.default: 800,},events: {
type: String.default: 'click',},isDebounce: {
type: Boolean.default: false,
},
},
created() {
this.eventKeys = this.events.split(', ');
this.originMap = {};
this.debouncedMap = {};
},
render() {
const vnode = this.$slots.default[0];
this.eventKeys.forEach(key= > {
const target = vnode.data.on[key];
if (target === this.originMap[key] && this.debouncedMap[key]) {
vnode.data.on[key] = this.debouncedMap[key];
} else if (target) {
this.originMap[key] = target;
this.debouncedMap[key] = debounce(
target,
this.time,
this.isDebounce,
vnode
);
vnode.data.on[key] = this.debouncedMap[key]; }});returnvnode; }};Copy the code
conclusion
This article is a summary of the use of render and abstract components, if there are mistakes, hope to point out common progress.
More recommended
Advanced_front_end
Daily question
Webpack4 Build Vue application (createVue)
Canvas Advanced (1) Generation of two-dimensional code and scan code recognition
Canvas advanced (2) Write a NPM plug-in to generate a TWO-DIMENSIONAL code with logo
Canvas advanced (3) TS + Canvas rewrite “color discrimination” small game
Canvas advanced (four) to achieve a “scratch-off” game
VUI create log (a) – picture lazy load command implementation