import { inject, Transition } from 'vue'; import classNames from 'classnames'; import PropTypes from '../_util/vue-types'; import backTopTypes from './backTopTypes'; import addEventListener from '../vc-util/Dom/addEventListener'; import getScroll from '../_util/getScroll'; import BaseMixin from '../_util/BaseMixin'; import getTransitionProps from '../_util/getTransitionProps'; import { ConfigConsumerProps } from '../config-provider'; import scrollTo from '../_util/scrollTo'; function getDefaultTarget() { return window; } const props = backTopTypes(); const BackTop = { name: 'ABackTop', inheritAttrs: false, mixins: [BaseMixin], props: { ...props, visibilityHeight: PropTypes.number.def(400), }, setup() { return { configProvider: inject('configProvider', ConfigConsumerProps), }; }, data() { this.scrollEvent = null; return { visible: false, }; }, mounted() { this.$nextTick(() => { const getTarget = this.target || getDefaultTarget; this.scrollEvent = addEventListener(getTarget(), 'scroll', this.handleScroll); this.handleScroll(); }); }, beforeUnmount() { if (this.scrollEvent) { this.scrollEvent.remove(); } }, methods: { getCurrentScrollTop() { const getTarget = this.target || getDefaultTarget; const targetNode = getTarget(); if (targetNode === window) { return window.pageYOffset || document.body.scrollTop || document.documentElement.scrollTop; } return targetNode.scrollTop; }, scrollToTop(e) { const { target = getDefaultTarget } = this; scrollTo(0, { getContainer: target, }); this.$emit('click', e); }, handleScroll() { const { visibilityHeight, target = getDefaultTarget } = this; const scrollTop = getScroll(target(), true); this.setState({ visible: scrollTop > visibilityHeight, }); }, }, render() { const { prefixCls: customizePrefixCls, $slots } = this; const getPrefixCls = this.configProvider.getPrefixCls; const prefixCls = getPrefixCls('back-top', customizePrefixCls); const classString = classNames(prefixCls, this.$attrs.class); const defaultElement = (
); const divProps = { ...this.$attrs, onClick: this.scrollToTop, class: classString, }; const backTopBtn = this.visible ? (
{($slots.default && $slots.default()) || defaultElement}
) : null; const transitionProps = getTransitionProps('fade'); return {backTopBtn}; }, }; /* istanbul ignore next */ BackTop.install = function(app) { app.component(BackTop.name, BackTop); }; export default BackTop;